Please Explain About Insertable=False and Updatable=False in Reference to the JPA @Column Annotation

Please explain about insertable=false and updatable=false in reference to the JPA @Column annotation

You would do that when the responsibility of creating/updating the referenced column isn't in the current entity, but in another entity.

Hibernate: Where do insertable = false, updatable = false belong in composite primary key constellations involving foreign keys?

Let me answer step by step.

1. When do you need ` insertable = false, updatable = false`?

Let's look at the below mapping,

public class Zip {

@ManyToOne
@JoinColumn(name = "country_code", referencedColumnName = "iso_code")
private Country country = null

@Column(name = "country_code")
private String countryCode;

}

Here we are referring to the same column in the table using two different properties. In the below code,

Zip z = new Zip();

z.setCountry(getCountry("US"));
z.setCountryCode("IN");

saveZip(z);

What will Hibernate do here??

To prevent these kind of inconsistency, Hibernate is asking you to specify the update point of relationships. Which means you can refer to the same column in the table n number of times but only one of them can be used to update and all others will be read only.

2. Why is Hibernate complaining about your mapping?

In your Zip class you are referring to the Embedded id class ZipId that again contains the country code. As in the above scenario now you have a possibility of updating the country_code column from two places. Hence the error given by Hibernate is proper.

3. How to fix it in your case?

No. Ideally you want your ZipId class to generate the id, so you should not add insertable = false, updatable = false to the countryCode inside the ZipId. So the fix is as below modify the country mapping in your Zip class as below,

@ManyToOne
@JoinColumn(name = "country_code", referencedColumnName = "iso_code",
insertable = false, updatable = false)
private Country country;

Hope this helps your understanding.

Do CascadeType.ALL and insertable = false, updatable = false exclude each other?

They mean different things and do not conflict with each other.

So given the following mapping :

@Entity
@Table(name="player")
public class Player {

@ManyToOne(cascade = {CascadeType.PERSIST, CascadeType.MERGE})
@JoinColumn(name = "team_id", nullable = false, insertable = false, updatable = false)
Team team;

}
  • cascade means that when using EntityManager to persist() or merge() on a player , JPA will automatically call persist() / merge() on this player 's team too.

  • insertable and updatable is about if allow to assign a new team or update the team for a player . In term of the DB table , it is about if the value of Player table 's team_id column is allowed to be inserted or updated.

So one is about inserting/updating records in the Team table while another is about inserting/updating the value of the Player table 's team_id column , which are totally different things.

JPA @Id and insertable = false, updatable = false throws exception

You are currently saying with your JPA annotations that you have an @Id column that cannot be inserted or updated in any way. You must be able to set the id before inserting or updating, but JPA does not know how to do so. You will need to use the @GeneratedValue annotation on the @Id to tell JPA what strategy to use (one of: TABLE,SEQUENCE,IDENTITY,AUTO) if you do not want the id to be set in your code.

One To Many Unidirectional association insert query getting failed

This can be fixed by some small changes at Entity level:

Change-1:
Add nullable=false at your User entity, something like this:

@Entity 
@Table(name = "users")`
public class User{`

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "ID")
private long id;

@OneToMany(orphanRemoval = true,cascade = CascadeType.ALL, fetch=FetchType.EAGER)
@JoinColumn(name = "USER_ID", referencedColumnName = "ID", nullable = false)
private List<Address> address;
// other table columns
}

Change-2:
Add insertable = false and updatable = false at your Address entity, something like this

@Entity
@Table(name = "address")
public class Address{

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "ID")
private long id;

@Column(name = "USER_ID", insertable = false, updatable = false)
private long userId;
//other table columns
}

Use of nullable=false : It applies the not null constraint to the particular database column

To to know uses of insertable = false, updatable = false please refer this :Please explain about insertable=false and updatable=false in reference to the JPA @Column annotation



Related Topics



Leave a reply



Submit