I am trying to get the full object graph for one of my objects.
I am explicitly set FetchMode.Eager for all the relevant associations. Once I have retrieved my object, the session is closed/disposed and I then want to work disconnected.
However, when I try to access one of the collections (Transmittals) I get the following exception:
Quote:
NHibernate.LazyInitializationException: Failed to lazily initialize a collection - no session
In the instance I am using, there are no Transmittals for the Rfi, so the collection would be empty. I am wondering if NHibernate is seeing the empty collection and trying to do a Lazy Load?
Code:
/// <summary>
/// Gets the Rfi by id with all associated items populated.
/// </summary>
/// <param name="rfiID">The rfi ID.</param>
/// <returns></returns>
public override Rfi GetByIdWithAll(int rfiID)
{
IList results = null;
try
{
ICriteria criteria = localSession.CreateCriteria(typeof(Rfi));
//Set everything to eager to bring back the full object graph
criteria.SetFetchMode("Transmittals", FetchMode.Eager);
criteria.SetFetchMode("Documents", FetchMode.Eager);
criteria.SetFetchMode("SubProject", FetchMode.Eager);
criteria.SetFetchMode("SubProject.Project", FetchMode.Eager);
criteria.SetFetchMode("Project", FetchMode.Eager);
criteria.SetFetchMode("History", FetchMode.Eager);
criteria.SetFetchMode("WorkflowTasks", FetchMode.Eager);
criteria.Add(Expression.Eq("RfiID", rfiID));
criteria.SetResultTransformer(CriteriaUtil.DistinctRootEntity);
results = criteria.List();
// force items to be loaded.
// HACK: to overcome problem with the FetchMode.Eager not working!!!!!
if (results.Count > 0)
{
IList Documents = ((Rfi)results[0]).Documents;
IList Transmittals = ((Rfi)results[0]).Transmittals;
if (Documents.Count > 0)
{
Document doc = (Document)Documents[0];
int num = doc.Rfi.Documents.Count;
}
string sp1 = ((Rfi)results[0]).SubProject.SourceRefCode;
sp1 = ((Rfi)results[0]).SubProject.Project.SourceRefCode;
}
}
catch (Exception ex)
{
bool rethrow = ExceptionPolicy.HandleException(ex, ExceptionPolicyName.DataAccessPolicy);
if (rethrow)
{
throw;
}
}
if (results.Count > 0)
{
return (Rfi)results[0];
}
else
{
return null;
}
}
Here is the mapping:
Code:
<?xml version="1.0" encoding="utf-8" ?>
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.0" namespace="KBR.LAPD.DocumentManagement.Entities">
<class name="KBR.LAPD.DocumentManagement.Entities.Rfi, Entities" table="RFI">
<id name="RfiID" column="RFI_ID">
<generator class="sequence">
<param name="sequence">RFI_RFI_ID_SEQ</param>
</generator>
</id>
<version name="Version" column="VERSION"/>
<property name="RfiName" column="RFI_NAME" />
<property name="Description" column="RFI_DESC" />
<property name="RfiStatusID" column="RFI_STATUS_ID" />
<property name="PurchaseOrderNumber" column="PO_NUMBER" />
<property name="TransmittalMethodCode" column="XMTL_MTHD_CODE" />
<bag name="History" table="RFI_HISTORY" outer-join="true" fetch="join" lazy="false" cascade="all-delete-orphan">
<key column="RFI_ID"/>
<one-to-many class="KBR.LAPD.DocumentManagement.Entities.RfiAction, Entities"/>
</bag>
<many-to-one name ="Originator" class="KBR.LAPD.DocumentManagement.Entities.User, Entities" column="ORIGINATOR_USER_ID" />
<many-to-one name ="OwnerGroup" class="KBR.LAPD.DocumentManagement.Entities.Group, Entities" column="OWNER_GROUP_ID" />
<many-to-one name="TransmittalType" class="KBR.LAPD.DocumentManagement.Entities.TransmittalType, Entities" column="XMTL_TYPE_ID" fetch="select"/>
<many-to-one name="SubProject" class="KBR.LAPD.DocumentManagement.Entities.SubProject, Entities" column="SUB_PROJ_ID" outer-join="false" fetch="select" />
<bag name="Documents" table="DOC" order-by="DOC_ID" outer-join="true" fetch="join" lazy="false">
<key column="RFI_ID" />
<one-to-many class="KBR.LAPD.DocumentManagement.Entities.Document, Entities" />
</bag>
<bag name="Transmittals" outer-join="false" fetch="join" table="XMTL" lazy="true" order-by="TransmittalID" cascade="delete">
<key column="RFI_ID" />
<one-to-many class="KBR.LAPD.DocumentManagement.Entities.Transmittal, Entities"/>
</bag>
<bag name="WorkflowTasks" table="TASK" fetch="join" order-by="ExecutionOrder">
<key column="RFI_ID"/>
<one-to-many class="KBR.LAPD.DocumentManagement.Entities.WorkflowTask, Entities"/>
</bag>
</class>
</hibernate-mapping>