Is lazy=“false” the only solution for “org.hibernate.LazyInitializationException: could not initialize proxy – no Session”

StackOverflow https://stackoverflow.com/questions/6106300

Question

“org.hibernate.LazyInitializationException: could not initialize proxy – no Session“ was giving me a lot of pain. Some of the old thread of stackoverflow has discussions about this particular problem. I followed those and solved the problem.

In my hibernate mapping xml I have added lazy="false" to classes tags and to the tags collections like set and list.

<class name="User" table="users" lazy="false">
    <id name="id" column="id">
        <generator class="native"/>
    </id>        
    <property name="type" column="type"/>         
    <many-to-one name="parent" column="parent"/>
    <property name="loginName" column="login_name" unique="true" not-null="true" index="idx_users_login_name" length="50"/>
    <property name="name" column="name" length="50"/>
    <property name="password" column="password"/>
    <property name="email" column="email" length="50"/>
    <property name="locale" column="locale" length="20"/>
    <property name="locked" column="locked"/>
    <many-to-one name="metadata" column="metadata_id"/>
    <set name="userSpaceRoles" cascade="all" inverse="true" lazy="false">
        <key column="user_id"/>
        <one-to-many class="UserSpaceRole"/>
    </set>      
</class>

<class name="UserSpaceRole" table="user_space_roles" lazy="false">
    <id name="id" column="id">
        <generator class="native"/>
    </id>
    <many-to-one name="user" column="user_id"/>
    <many-to-one name="space" column="space_id"/>
    <property name="roleKey" column="role_key" not-null="true"/>
</class>   

Thus the problem was solved.

  • Is lazy="flase" the only solution?
  • What happened if I set lazy="false"?
  • Should I specify lazy="false" in the class tag?

For more information I am using JBoss 4.2.0.GA and I was facing this problem whenever I restart the server.

Was it helpful?

Solution

Instead of using lazy="false" on the class element, you are better off using it on the collections. That is, for example, whenever you fetch a User object, since the collection to UserSpaceRole is marked as not-lazy, the collection will be fetched as well.

Using lazy="false" at the class element has some undesired consequences. Normally, when the collection is not lazy as I said above, the entire collection is fetched using either join, select or subselect, depending on your fetching strategy. For example, with select strategy, when you fetch a User from the db, hibernate issues two select statements: one for the user itself, and one for the collection. However, hibernate may choose to proxy the individual elements inside the collection.
With lazy="false", hibernate can't proxy those objects, and typically resorts to using a single query with a join between the two tables. That may not always be desired.

However, the correct approach is look at your architecture and understand why the exception occurred in the first place. You have tried to access a property or a collection from a detached object (see here) after you already closed the session. I'd look at the service layer and see how can I fetch all the data needed before closing the session and passing the objects to the caller.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top