Archive for the ‘Hibernate’ Category.

Hibernate - Insert Before Delete


deadlock

Today I faced a problem that I already had faced some time before, but I didn’t documented that in blog entry or even in my “ProblemsThatCanNotBeForgotten.TXT”. So that’s the time for that.

The problem is: I have an entity called Team who has a List of Players (other entity). I’m trying to move an Player from one team to the other at the same transaction. Follow some code:


Original Team.java

After load this Entity by the JPA/Hibernate engine and have the tables created this is the structure and the indexes created:


table_team_player_one2many

The Problem

As happens in the real world some teams wants to trade their players, so the software has to be able to transfer one player from one team to another.
The code wich do this is very simple, just remove a player from one collection’s player team from the seller team and then insert the remove player to the buyer team.
After the transfer, the application apply this changes on the Database with merge(entity) call.


Call that merge a Team

Doing this a message telling that it’s impossible to insert a duplicate row blows up on the console.

This is because Hibernate does the INSERT statement BEFORE the DELETE.

After looking at Internet I didn’t find anything to solve that. Just a workaround that fixes that. But as I said, it’s a workaround.

Solving (woking it around)

To solve that problem I changed the reference from Team to Player from @OneToMany to @ManyToMany. The problem with this approach is that I lose the rule in the DB that has the control over the unicity of a player belonging to just one Team.

This is how the code and the table at the DB look like:


New Team.java


table_team_player_many2many

Table without the constraint

Controlling domain data with Hibernate and Enum

It is common to have a field into the table that his domain is no bigger to created a domain table just for that field and let it “free” as a String is a bit insecure.

A possible solution - if possible in your company - could be the creation of a big table for all simple domain data such as: gender(M/F) conditional(Yes/No) and so on.

But talking about Hibernate and Java (1.5+) we could use a more sophisticated solution such as Enuns.

Let’s start our sample defining the Enum and the Client class:


Client class


Gender enum

The annotation @Enumerated has just one param and it can had two values:

  1. EnumType.ORDINAL
  2. EnumType.STRING

The difference between them are not visible from the Object’s point of view. For this field will be associated an Enum with all it’s structure.
However, the difference between ORDINAL and STRING can be seen when you take a look at the database. When you define ORDINAL the position defined in Enum for that value will be stored. Starting from zero (zero based). For instance if you define the EnumType as ORDINAL and create an object like this:

And store it in database the record stored will looks like this:
enum_ordinal

On the other hand, if the definition of the EnumType is defined as STRING, for the same creation code will produce this record in the database:
enun_string