当我在UI层使用延迟加载时,我遇到了会话问题。
我的代码片段(在DAO层中)
public List<Visites> GetVisitesClientQuery(string idClient)
{
using (ISession session = Repository.TSession())
{
var results = (from v in session.Query<Visites>()
where v.Clients.Idclient == idClient
select v);
return results.ToList<Visites>();
}
}
我在UI层中调用它:
var visites = VisiteManager.Instance.GetVisitesClientQuery(lstClients.SelectedValue.ToString());
foreach (Visites v in visites)
{
foreach (Factures f in v.Factures)
{
...
}
}
v.Factures是一个集合。
如果我在使用中调用它可以工作(会话打开)但在这种情况下它不起作用我发生了这个错误。
Initializing[NHibernateTest.BusinessObjects.Visites#036000007935]-
failed to lazily initialize a collection of role:
NHibernateTest.BusinessObjects.Visites.Factures, no session or session was closed
是否可以在UI层处理延迟加载调用?
答案 0 :(得分:4)
这里的问题是你在你的存储库(DAO层)中处理你的会话管理,这不是一个好主意。
NHibernate中的ISession
实现代表'Unit Of Work'。工作单元需要知道“用例”的“背景”才能成功使用这个概念。
但是,您的存储库没有使用它(存储库)的用例的“上下文”概念。 因此,你的DAO层不应该决定何时打开一个ISession,但它是你的'应用层'(甚至你的UI层,如果你没有应用层)应该这样做,因为那将是知道你的背景的层。
通过这样做,您确实可以有效地将会话用作UnitofWork。为了保存实体,您必须使用相同的会话来保存实体,就像您用来加载该实体的会话一样。 (否则,您需要将实体“锁定”到会话中)。 接下来,它还将解决您的延迟加载问题。 :)
答案 1 :(得分:1)
您应该热切地加载您将要使用的集合 session.Query()获取(X =&GT; x.Factures)。
这将使用Factures加载所有Visites。