JPA Cascade Types Explained
Fast recall
Quick revision
Core answer
Whether you understand entity lifecycle propagation and can judge when automatic cascading is safe versus dangerous
Reaching for CascadeType.ALL by default without realising REMOVE will delete children when the parent is deleted
Contrast a case where cascade fits (Order and OrderItems) with one where it's dangerous (Department and Employees)
Interview-ready guide
Interview answer
For example, Order can cascade PERSIST to new OrderItem objects because the items belong to that order. A ManyToOne from OrderItem to shared Product should normally not cascade REMOVE: deleting one line item must not delete the product used by other orders. Whether MERGE is needed depends on how detached graphs are accepted and updated.
JPA Cascade Types Explained
Direct Answer
A cascade setting on an association tells JPA which EntityManager operations should propagate from that entity to the associated entity: PERSIST, MERGE, REMOVE, REFRESH, DETACH, or ALL. The direction is the direction of the mapped association carrying cascade. Cascades do not automatically define database ON DELETE actions, ownership of the foreign key, or orphan removal.
Code Example
// Composition: OrderItem belongs entirely to Order -> cascade ALL + orphanRemoval
@Entity
class Order {
@Id @GeneratedValue private Long id;
@OneToMany(mappedBy = "order",
cascade = CascadeType.ALL, // save/update/delete propagate
orphanRemoval = true) // removing from list deletes the row
private List<OrderItem> items = new ArrayList<>();
}
// Association: Employee outlives the Department -> NO cascade REMOVE
@Entity
class Department {
@Id @GeneratedValue private Long id;
@OneToMany(mappedBy = "department",
cascade = { CascadeType.PERSIST, CascadeType.MERGE }) // never REMOVE
private List<Employee> employees = new ArrayList<>();
}
// DANGER: cascade REMOVE from child to parent deletes the shared parent!
@Entity
class BadEmployee {
@ManyToOne(cascade = CascadeType.REMOVE) // deleting one employee deletes the dept
@JoinColumn(name = "department_id")
private Department department;
}
Match the cascade to ownership: full cascade for owned children, persist/merge for associations, never REMOVE from child to parent.
Common Mistakes & Pitfalls
- CascadeType.ALL everywhere — copy-pasting
cascade = ALLthen deleting a Department wipes 50 employees, because ALL includes REMOVE. - Cascading REMOVE on @ManyToOne — putting REMOVE on Employee's @ManyToOne to Department means deleting one Employee tries to delete the Department, hitting a constraint violation or orphaning others. Never cascade REMOVE from child to parent.
- Forgetting orphanRemoval — with only PERSIST/MERGE, removing an OrderItem from the list won't delete the row; it lingers forever. Use
orphanRemoval = truefor true composition.
Check your understanding
Answer these without looking back at the article.
- What is orphanRemoval in JPA?
- What is the difference between CascadeType.REMOVE and orphanRemoval?
- When should you NOT use CascadeType.REMOVE?
Looking for a structured roadmap?
Every module on this page is also part of the full Java backend interview track.