すべてのクエリ ロジックをリポジトリ内に保持しながら、Mark Oreta と luksan が提案することを行うことができます。
組織コンストラクターにa を渡し、Lazy<ICollection<Product>>
それらが提供するロジックを使用するだけです。遅延インスタンスの value プロパティにアクセスするまで評価されません。
アップデート
/*
First, here are your changes to the Organisation class:
Add a constructor dependency on the delegate to load the products to your
organization class. You will create this object in the repository method
and assign it to the Person.Organization property
*/
public class Organisation
{
private readonly Lazy<ICollection<Product>> lazyProducts;
public Organisation(Func<ICollection<Product>> loadProducts){
this.lazyProducts = new Lazy<ICollection<Product>>(loadProducts);
}
// The underlying lazy field will not invoke the load delegate until this property is accessed
public virtual ICollection<Product> Products { get { return this.lazyProducts.Value; } }
}
ここで、リポジトリ メソッドで Person オブジェクトを構築するときに、組織プロパティにOrganisation
遅延読み込みフィールドを含むオブジェクトを割り当てます。
したがって、モデル全体を見ることなく、次のようになります
public Person GetById(int id){
var person = context.People.Single(p => p.Id == id);
/* Now, I'm not sure about the cardinality of the person-organization or organisation
product relationships, but let's assume you have some way to access the PK of the
organization record from the Person and that the Product has a reference to
its Organisation. I may be misinterpreting your model, but hopefully you
will get the idea
*/
var organisationId = /* insert the aforementioned magic here */
Func<ICollection<Product>> loadProducts = () => context.Products.Where(product => product.IsActive && product.OrganisationId == organisationId).ToList();
person.Organisation = new Organisation( loadProducts );
return person;
}
このアプローチを使用すると、製品のクエリProducts
はインスタンスのプロパティにアクセスするまで読み込まれずOrganisation
、すべてのロジックをリポジトリに保持できます。あなたのモデルについて間違った仮定をしている可能性は十分にありますが (サンプル コードは完全ではないため)、パターンの使用方法を理解するには十分だと思います。不明な点があればお知らせください。