Item、ItemProductLine、および ProductLine の 3 つのドメイン モデルがあります。これらはそれぞれ、既存のデータベース テーブルにマップされます。ビューで使用するビューモデルもあります。
ドメイン モデル:
public class Item
{
public string itemId { get; set; }
public string itemDescription { get; set; }
public float unitPrice { get; set; }
// more fields
public virtual ItemProductLine itemProductLine { get; set; }
}
public class ItemProductLine
{
public string itemId { get; set; }
public String productLineId { get; set; }
// more fields
public virtual ProductLine productLine { get; set; }
}
public class ProductLine
{
public string productLineId { get; set; }
public string productLine { get; set; }
// more fields
}
モデルを見る:
public class ItemViewModel
{
public string itemNumber { get; set; }
public String itemDescription { get; set; }
public Double unitPrice { get; set; }
public string productLine { get; set; }
}
私の現在のクエリは次のとおりです。
from item in dbContext.Items
where unitPrice > 10
select new ItemViewModel()
{
itemNumber = item.itemNumber
itemDescription = item.itemDescription
unitPrice = item.unitPrice
productLine = item.itemProductLine.productLine.productLine
}
現在、コントローラーにこのクエリがありますが、コードをリファクタリングしています。クエリ コードをデータ アクセス層のリポジトリ クラスに配置したいと考えています。私が読んだことから、そのレイヤーのビューモデルを参照するべきではありません。に変更select new ItemViewModel()
するとselect new Item()
、次のエラーが返されます。
エンティティまたは複合型 'proj.DAL.Item' は、LINQ to Entities クエリでは構築できません。
私が見た解決策は、データ転送オブジェクト (DTO) を作成して、ドメイン モデルからビュー モデルにデータを転送することです。
ただし、これを行うと、データのコピーが 3 つになります。別のデータベース フィールドを追加して表示する必要がある場合は、3 つのファイルを更新する必要があります。私は DRY の原則に違反していると思います。DTO とビュー モデルを使用する場合、DRY 原則に違反することは避けられませんか? そうでない場合は、これをリファクタリングして DRY コードにする方法の例を提供できますか?