Card 02/ 07

WalkthroughDifficulty: Advanced1 min

One Entity, Traced Through Every State

One Employee, followed from new to managed, to detached, and back to managed again through merge() — checking its real state at every step with EntityManager.contains(), not assuming it.

Following one entity through the lifecycle

Step 1 of 3

Transient, then persist()

java
Employee emp = new Employee("Alex");
System.out.println("before persist(): contains? " + em.contains(emp));
em.persist(emp);
System.out.println("after persist(): contains? " + em.contains(emp));

Managed, then detach()

java
Employee found = em.find(Employee.class, emp.id);
System.out.println("found, contains? " + em.contains(found));
em.detach(found);
System.out.println("after detach(), contains? " + em.contains(found));

Detached, then merge()

java
found.name = "merged-name";
Employee managed = em.merge(found);
System.out.println("merge() returned a " + (managed == found ? "SAME" : "DIFFERENT") + " instance");
text
before persist(): contains? false
after persist(): contains? true
found, contains? true
after detach(), contains? false
merge() returned a DIFFERENT instance
run in a container, Spring Boot 3.3.4 — real EntityManager.contains() checks at each step

contains() is the ground truth for whether the persistence context is actually watching an object — not a guess based on which method you called last. merge() returning a different instance is the detail the next card is entirely about.