title: Why does @Transactional(propagation = Propagation.SUPPORTS, readOnly = true) fix Hibernate Lazy Loading Exceptions?
body: <p>I switched an app I am working on from using AspectJ load time weaving to using Spring CGlib proxies and right after I did that there were many parts of the code where I started to get hibernate lazy loading exceptions where in the past there were no exceptions being thrown.</p>
  
  <p>I have been able to resolve these lazy loading exceptions by adding <code>@Transactional(propagation = Propagation.SUPPORTS, readOnly = true)</code> to bunch of previously public methods that did not have any transactional attributes on them but called spring repositories to read data from the database.</p>
  
  <p>Anyone know why adding <code>@Transactional(propagation = Propagation.SUPPORTS, readOnly = true)</code> eliminates the hibernate lazy loading exceptions and why these annotations were not required with AspectJ load time weaving but are are required with out?</p>
  
  <p><strong>Update 2</strong> 
  <strong>I believe that removing AspectJ was NOT the issue</strong>, but the issue was was that I did not really understand the actual behavior of the SUPPORTS propagation. In particular how SUPPORTS interacted with the JPA EntityManager and so I removed a bunch a SUPPORTS propagation which caused the lazy loading exceptions. After reading through the source code for the Spring Transaction Manager It all became clear as to what to do. The key idea that the spring documentation does not really point out very well is that @Transactional annotations are used as synchronization points that tie life cycle of an EntityManager to the start and end of a transactional method. Also highly recommend this series of articles at <a href="http://www.ibm.com/developerworks/java/library/j-ts1/" rel="noreferrer">http://www.ibm.com/developerworks/java/library/j-ts1/</a> and this blog post <a href="http://doanduyhai.wordpress.com/2011/11/21/spring-persistencecontext-explained/" rel="noreferrer">http://doanduyhai.wordpress.com/2011/11/21/spring-persistencecontext-explained/</a></p>
  
  <p><strong>Update 1</strong> </p>
  
  <p>This is not a case of calls to private @Transactional methods not going through the AOP proxy. These issues are happening with public methods that are being called from other services. </p>
  
  <p>Here is an example of the code structure, where I see the problem occurring. </p>
  
  <pre><code>@Service
  public class FooService 
  {
     @Autowired
     private BarService barService;
  
     public void someMethodThatOnlyReads() {
        SomeResult result = this.barService.anotherMethodThatOnlyReads()
  
        // the following line blows up with a HibernateLazyLoadingEcxeption 
       // unless there is a @Transactional supports annotation on this method
        result.getEntity().followSomeRelationship(); 
      }
  
  }
  
  @Service
  public class BarService 
  {
     @Autowired
     private BarRepository barRepo;
  
     public SomeResult anotherMethodThatOnlyReads()
     {
        SomeEntity entity =  this.barRepo.findSomeEntity(1123);
        SomeResult result = new SomeResult();
        result.setEntity(entity);
        return result; 
      }
  }
  
  @Repository
  public class BarRepository 
  {
     @PersistenceContext
     private EntityManager em;
  
     public SomeEntity findSomeEntity(id Integer)
     {
        em.find(SomeEntity.class,id);
     }
  }
  </code></pre>