FluentNHibernateを使用しています。実行時に、データが入力されている場合とされていない場合があるレイジーコレクション/プロパティを持つオブジェクトがあります。そのオブジェクトをシリアル化する予定であり、その前にすべてのコレクション/プロパティを設定する必要があります。実行時にオブジェクトを「熱心にロード」するにはどうすればよいですか?
2 に答える
マッピングに関係がすでに設定されている場合は、クエリに参加する方法を指定する必要はありません。Fetch(ディープフェッチでも)を使用して、簡単にロードするパスを指定できます。
session.QueryOver<MasterEnt>()
.Where(x => x.Id == 2)
.Fetch(x => x.DetailEntList)
.Eager().List();
ICriteria
を介してロードを使用および操作できますNHibernate.ICriteria.SetFetchMode(string, NHibernate.FetchMode)
。
例:
DetailEnt.cs:
using System;
using System.Collections.Generic;
using System.Text;
namespace FetchTest
{
public class DetailEnt
{
private Int32? id;
/// <summary>
/// Entity key
/// </summary>
public virtual Int32? Id
{
get { return id; }
set { id = value; }
}
private String description;
/// <summary>
/// Description
/// </summary>
public virtual String Description
{
get { return description; }
set { description = value; }
}
private MasterEnt rIMaster;
/// <summary>
/// Gets or sets the RI master.
/// </summary>
/// <value>
/// The RI master.
/// </value>
public virtual MasterEnt RIMaster
{
get { return rIMaster; }
set { rIMaster = value; }
}
}
}
MasterEnt.cs:
using System;
using System.Collections.Generic;
using System.Text;
namespace FetchTest
{
public class MasterEnt
{
private Int32? id;
/// <summary>
/// Entity key
/// </summary>
public virtual Int32? Id
{
get { return id; }
set { id = value; }
}
private String description;
/// <summary>
/// Description
/// </summary>
public virtual String Description
{
get { return description; }
set { description = value; }
}
private ICollection<DetailEnt> detailEntList;
/// <summary>
/// <see cref="RIDetailEnt"/> one-to-many relationship.
/// </summary>
public virtual ICollection<DetailEnt> DetailEntList
{
get { return detailEntList; }
set { detailEntList = value; }
}
}
}
実行時に熱心な負荷を強制する:
NHibernate.ISession ss = GetSessionFromSomeWhere();
NHibernate.ICriteria crt = ss.CreateCriteria<MasterEnt>();
crt
.Add(NHibernate.Criterion.Expression.IdEq(17))
//here is "force eager load at runtime"
.SetFetchMode("DetailEntList", NHibernate.FetchMode.Join);
MasterEnt mEnt = crt.UniqueResult<MasterEnt>();
この場合、「hbm」を使用しました。ただし、ロジックは同じである必要があります。
編集:
「NHibernate2.1.2」と「NHibernate.Linq」を使用
INHibernateQueryable<MasterEnt> nhq = null;
IList<MasterEnt> masterList = null;
nhq = (INHibernateQueryable<MasterEnt>)(
from master in session.Linq<MasterEnt>()
where master.Id == 2
select master);
nhq.Expand("DetailEntList");
masterList = nhq.ToList<MasterEnt>();
QueryOver<T>Left.JoinQueryOver
NHibernate 3から
:
IQueryOver<MasterEnt> query = session.QueryOver<MasterEnt>()
.Left.JoinQueryOver<DetailEnt>(m => m.DetailEntList)
.Where(m => m.Id == 2);
masterList = query.List<MasterEnt>();
「FluentNHibernate」または「hbm」を使用する場合、これらのクエリはこのように独立して機能します。
そのためのコードをいくつか作成しました。すぐにファイルへのリンクを投稿します。
編集2:
q_10303345_1350308.7z(NUnitで実行可能)にコードを投稿しました。「dependencies\readme.txt」に依存関係についての説明があります。dllの依存関係はNuGetによって読み込まれます。