Description of problem: When a detached instance is merged/updated and its associations are navigated, 'LazyInitializationException: could not initialize proxy - no Session' is raised while accessing a property for an associated entity Version-Release number of selected component (if applicable): How reproducible: Consistently Steps to Reproduce: 1. Create instances of three classes where TestClass1 has one associated TestClass2 instance and the TestClass2 instance has one associated TestClass3 instance 2. In a new session load TestClass1 by ID, navigate to TestClass2 then close the session 3. In a new session, update/merge TestClass1 from step 2, re-retrieve the updated/merged TestClass1 from the session by ID, navigate the associations to the TestClass3 entity and access one of its properties Actual results: The following exception is raised: org.hibernate.LazyInitializationException: could not initialize proxy - no Session at org.hibernate.proxy.AbstractLazyInitializer.initialize(AbstractLazyInitializer.java:164) at org.hibernate.proxy.AbstractLazyInitializer.getImplementation(AbstractLazyInitializer.java:285) at org.hibernate.proxy.pojo.javassist.JavassistLazyInitializer.invoke(JavassistLazyInitializer.java:185) at TestClass3_$$_jvstaf8_2.getName(TestClass3_$$_jvstaf8_2.java) at Test1.test(Test1.java:50) ... Expected results: The attribute access is expected to be successful Additional info: Testcase (see pom.xml) is for: <version>4.2.7.SP4-redhat-1</version> <!-- EAP 6.2.3 --> Testcase also verified with both of the following: <!-- <version>4.2.7.SP5-redhat-1</version> --> <!-- EAP 6.2.4 --> <!-- <version>4.3.5.Final</version> -->
Created attachment 922644 [details] Testcase
his is not a bug. When Session.update( testClass1 ) is executed: If testClass1.testClass2 is not initialized, the uninitialized proxy is reattached to the Session; this happens regardless of whether the update operation is cascaded to the association. Hibernate does this because it is safe to do. Hibernate knows that the association has not been updated (because it is unitialized). Since the session contains the proxy it can safely be initialized later (in the same session). If testClass1.testClass2 is initialized, the initialized proxy is reattached to the Session only if the update operation is cascaded to the associaton. When the update operation is not cascaded to the association, it is not safe for Hibernate to reattach proxy because Hibernate has no way of knowing if the initialized proxy state has been updated by the application; reattaching an initialized proxy would implicitly cascade the update operation to the association. In the test case, testClass1.testClass2 is not reattached to the Session, so testClass1.testClass2.testClass3 also will not be attached to the Session. When the test tries to initialize the proxy, Hibernate will throw LazyInitializationException because the proxy (testClass1.testClass2.testClass3) is not attached to the Session. There are 2 ways to deal with this: 1) configure @org.hibernate.annotations.Cascade({ org.hibernate.annotations.CascadeType.SAVE_UPDATE}) for the lazy association 2) call Session.update( testClass1.testClass2 ) to reattach the testClass1.testClass2; if testClass1.testClass2.testClass3 is uninitialized, it will also be attached to the Session; then it will be safe to initialize testClass1.testClass2.testClass3. When Session.merge( testClass1 ) is executed, and the merge operation is not cascaded the association, the state from testClass1.testClass2 is ignored. It does not matter whether testClass1.testClass2 has already been initialized. The merge result will contain an uninitialized proxy for the lazy association.
Created attachment 924621 [details] Annotated test case showing expected behavior