Some dirty business is happening in the AMF Servlet...
Im calling a DAO method that is supused to retrieve a list of DTO without any children through a remote object from java to flex:
public List<NivelesPlantillasDto> getList()throws HibernateException{
logger.info("getList()");
List<NivelesPlantillasDto> list = new ArrayList<NivelesPlantillasDto>();
Session session = null;
try{
session = SessionFactory.getInstance().openSession();
list=(List<NivelesPlantillasDto>)session.createQuery("from NivelesPlantillasDto").list();
}catch(HibernateException HE){
logger.info(HE.getMessage(),HE);
if (session!=null && session.isConnected())
session.close();
throw HE;
}
if (session.isConnected())
session.close();
return list;
}
And this is the hbm.xml
<hibernate-mapping>
<class name="architecture.dto.NivelesPlantillasDto" table="nivelesplantillas">
<id name="pkNivelPlantilla" type="int">
<column name="PKNIVELPLANTILLA" />
<generator class="identity" />
</id>
<property name="plantilla" type="java.lang.String">
<column name="PLANTILLA" />
</property>
<set name="habilidadesList" table="habilidades" inverse="true" lazy="true">
<key foreign-key="FKNIVELESPLANTILLAS" not-null="true">
<column name="FKNIVELESPLANTILLAS" sql-type="int"/>
</key>
<one-to-many class="architecture.dto.HabilidadesDto"/>
</set>
<set name="nivelesList" table="niveles" inverse="true" cascade="merge,delete-orphan" order-by="indice" lazy="true">
<key foreign-key="FKNIVELESPLANTILLAS" not-null="true">
<column name="FKNIVELESPLANTILLAS" sql-type="int"/>
</key>
<one-to-many class="architecture.dto.NivelesDto"/>
</set>
<property name="activo" type="boolean">
<column name="ACTIVO" />
</property>
</class>
</hibernate-mapping>
This error comes up after closing the session, because, Hibernate tries to load all the children of this class when the object is being deserialized on the AMF Servlet, I can see the query of every children by leaving the session open. So there are 2 fixes for this error to go away, one is to set lazy="false"
in both one-to-many relations, and the second is leaving the session open until AMF finishes to load all the children, but that's not what I want. Why am I forced to load every child?
Edit: Ok, i just fixed this in an ugly way... I did a clone of the list retrieved, so when this one gets deserialized, it doesn't trigger any Hibernate query. Is there a way to tell LCDS wich collections are being lazy loaded?
Not that I know of. I think you should consider implementing the "Open Session in View" pattern - yours is an appropriate use case for that.
Update
Based on the "answer" provided by the OP I'd like to point that there may be a better approach to lazy loading and the
size
operation. Hibernate supports extra-lazy collections which only issue aselect count(...
statement against the database instead of loading the entire collection if all you need is to get the size of it. Just add this annotation:See http://www.frightanic.com/2010/11/21/extra-lazy-one-to-many-mapping-with-hibernate/ for details.