Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Save object in database if it does not already exist (Hibernate & Spring)

I'm working on a Hibernate/Spring application to manage some movies.

The class movie has a many to many relationship with the class genre. Both of these classes have generated id's using the GeneratedValue annotation.

The genre is saved through the movie object by using @Cascade(CascadeType.SAVE_UPDATE) I have placed a unique constraint on the genre's type attribute (which is it's name; "Fantasy" for example).

What I would like to do now is have Hibernate check if there is already a genre with type "Fantasy" and if there is, use that genre's id instead of trying to insert a new record. (The latter would obviously throw an error)

Finally what I need is something like select-before-update but more like select-before-save.

Is there such a function in Hibernate?

Some code:

Movie class

@Entity
public class Movie {

@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private int id;

private String name;

@Lob
private String description;

@Temporal(TemporalType.TIME)
private Date releaseDate;

@ManyToMany
@Cascade(CascadeType.SAVE_UPDATE)
private Set<Genre> genres = new HashSet<Genre>();

.... //other methods

Genre class

@Entity
public class Genre {

@Column(unique=true)
private String type;

@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private int id

....//other methods
like image 236
Mike Avatar asked Jan 14 '13 15:01

Mike


People also ask

How do you save an object in Hibernate?

The save() method INSERTs an object in the database. It will persist the given transient instance, first assigning a generated identifier. It returns the id of the entity created. The saveOrUpdate() calls either save() or update() on the basis of identifier exists or not.

Can we save list of objects in Hibernate?

To save list of object, you need to iterate by objects, something like this -> How to insert multiple rows into database using hibernate? Save this answer. Show activity on this post. I would further recommend to use another Hibernate command to avoid an Out Of Memory error...

Does Hibernate update if no changes?

Hibernate always updates all database columns mapped by my entity, even the ones that I didn't change.

What is Hibernate save method return?

Hibernate save method returns the generated id immediately, this is possible because primary object is saved as soon as save method is invoked. If there are other objects mapped from the primary object, they gets saved at the time of committing transaction or when we flush the session.


2 Answers

You may be over-thinking this. Any select-before-update/select-before-save option is going to result in 2 DB round trips, the first for the select, and the second for the insert if necessary.

If you know you won't have a lot of genres from the outset, you do have a couple of options for doing this in 1 RT most of the time:

  1. The Hibernate second-level cache can hold many if not all of your Genres, resulting in a simple hashtable lookup (assuming a single node) when you check for existence.
  2. You can assume all of your genres are already existing, use session.load(), and handle the new insert as a result of the row not found exception that gets thrown when you reference a genre that doesn't already exist.

Realistically, though, unless you're talking about a LOT of transactions, a simple pre-query before save/update is not going to kill your performance.

like image 195
Peter Bratton Avatar answered Sep 27 '22 20:09

Peter Bratton


I haven't heard of such a function in Hibernate select-before-update/select-before-save In situations like these you should treat Hibernate as if it was JDBC.

First if you want to know if you even have such a Genre you should query for it.

if you do. then the SAVE_UPDATE will not create a new one when you add it to a movie. if you don't, Hibernate will create a new Genre row in the database and add the connection to the many_to_many table for you.

like image 39
Gleeb Avatar answered Sep 27 '22 18:09

Gleeb