JPA / Hibernate Cascade Types - CascadeType.DETACH

In this post, we will discuss the usage of JPA CascadeType.DETACH with an example.

Cascading is the way to achieve this. When we perform some action on the target entity, the same action will be applied to the associated entity.

JPA Cascade Types:

All JPA-specific cascade operations are represented by the javax.persistence.CascadeType enum containing entries:

  • ALL - cascades all entity state transitions
  • PERSIST - cascades the entity persist operation.
  • MERGE - cascades the entity merge operation.
  • REMOVE - cascades the entity to remove operation.
  • REFRESH - cascades the entity refresh operation.
  • DETACH - cascades the entity detach operation.

Hibernate Cascade Types:

Hibernate supports three additional Cascade Types along with those specified by JPA. These Hibernate-specific Cascade Types are available in org.hibernate.annotations.CascadeType:
  • SAVE_UPDATE - cascades the entity saveOrUpdate operation.
  • REPLICATE - cascades the entity replicate operation.
  • LOCK - cascades the entity lock operation.

JPA / Hibernate Cascade Types - CascadeType.DETACH

The detach operation removes the entity from the persistent context. When we use CascaseType.DETACH, the child entity will also get removed from the persistent context.
Consider we have Person and Address JPA entities:

Person.java

@Entity
public class Person {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private int id;
    private String name;
    @OneToMany(mappedBy = "person", cascade = CascadeType.ALL)
    private List<Address> addresses;
    // getters and setters
}

Address.java

@Entity
public class Address {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private int id;
    private String street;
    private int houseNumber;
    private String city;
    private int zipCode;
    @ManyToOne(fetch = FetchType.LAZY)
    private Person person;
   
    // getter and setter methods
}

CascadeType.DETACH Example

The following snipper demonstrates when we use CascaseType.DETACH, the child entity will also get removed from the persistent context:

Person person = new Person();
person.setName("Admin");

Address address = new Address();
address.setCity("Mumbai");
address.setHouseNumber(23);
address.setStreet("Rural");
address.setZipCode(123456);
address.setPerson(person);

person.setAddresses(Arrays.asList(address));
session.persist(person);
session.flush();
session.detach(person);

Here, we can see that after detaching a person, neither person nor address exists in the persistent context.

References

Comments