Camel is closing JPA sessions
So I was writing a simple Camel route where I was fetching a JPA-backed entity on one step and then using it on another. While executing that second step, I got this error:
org.hibernate.LazyInitializationException: could not initialize proxy - no Session
Wait – I already fetched that object in step 1. Why is Hibernate (my JPA provider) complaining about anything? After poking around with it, I figured it out – it is the lazy-loading the OneToMany
property on my entity and when it gets to the next step of the route, the entityManager
is closed. I could put an eager fetch on the entire entity, but I didn’t want to do that for all the other places my entity is used. I also could have used the id on the entity to re-fetch the entire entity, but that is another database round-trip.
The solution I used was to use a named entity graph, which is stepped through on this post. We use Spring Data-JPA, in which you can put it on the JpaRepository
like this:
interface SomeEntityRepository implements JpaRepository { @EntityGraph(type = EntityGraph.EntityGraphType.LOAD) SomeEntity findById(Long id) // other queries}
Using this will only do an eager fetch when you use findById
and not when you run findAll
or any other queries.
Another method would be to use the ElementCollection
annotation instead of the OneToMany
property. They are similar, but not the same. So use with some caution.
These JPA problems aren’t limited to Camel, but it seemed to really be an issue in our case. I have a sample project to play with if you are interested.