2

これは、DDD、TDD、およびリポジトリ/ UnitOfWorkパターンについて多くのことを読んだ後、自分のアプリケーションを作成する最初の試みです。

.NET4.0でEntityFramework、MVC 4を使用しています(このアプリケーションを実行するサーバーはWindows 2003です)

これは基本的な簡略化されたパターンロジックです(元のロジックはIRepository、IUnitOfWork、GenericRepositoryを使用し、IEntityインターフェイスでEF POCOを拡張して、共通IDフィールドへのアクセスを提供します。ただし、この簡略化された例で質問できます)

View -> ViewModel -> Controller <- UnitOfWork <- Repository <- EntityFramework <- Database

意見

Model.Employee.GetSeniority()

EmployeeDetailsViewModel

Employee e { get; set; }

従業員

DateTime dateHired { get; set; }
TimeSpan GetSeniority()
{
    return DateTime.Today - dateHired;
}

コントローラーEmployeeDetails()

using(var unitOfWork = new UnitOfWork) {
    return View(EmployeeDetailsViewModel model = new EmployeeDetailsViewModel {
        e = unitOfWork.GetEmployeRepository().Find(o=>o.id == id)
    });
}

UnitOfWork GetEmployeRepository()

return (_employeeRepository ?? _employeeRepository = new EmployeeRepository(this.dbContext));

リポジトリFind()

dbContext.Configuration.EnableProxyCreation = false;
Employee e = dbContext.Employees.Where(expression);
dbContext.Configuration.EnableProxyCreation = true;
return e;

すべてが実際に正しく機能します。問題は、ここで何かがひどく間違っているように感じ、どのレイヤーで修正する必要があるのか​​わからないことです。

多くの人(こんにちはダリン)から、常にViewModelsをビューに渡し、モデルを渡さないように提案された後、私はこれを始めました。しかし、私がしていること(私は思う)はそれほど良くはありません。モデルをビューモデルにカプセル化するだけです。最初は、Find()メソッドがオブジェクトを取得する前にプロキシをオフにし、永続性を無視するPOCOになるため、それほど悪くはありませんでした。しかし、POCOにロジックを追加したいので、何か問題があるように感じます。

問題は、私のビジネスロジックがどこにあるか、そして私の従業員POCOをDTOオブジェクトにマップする必要があるという事実にあると思います。ただし、どこで従業員POCOをEmployeeDTOに転送する必要がありますか?それはリポジトリ、コントローラー、または他の何かのタスクである必要がありますか?また、ビジネスロジックをどこに配置すればよいかわかりません(例に表示されているGetSeniority()のように単純です)。それは部分的なクラスを介してEFPOCOに追加する必要がありますか、それともDTOに含める必要がありますか?または、Employee-> EmployeeDTO転送に別の欠落しているステップがありますか?

4

1 に答える 1

3

これは素晴らしい質問です。あなたは素晴らしい分離を見つけようとしているようです。私は問題を解決します。データアクセスとUI表示があり、その間にビジネスロジックがあります。ドメインモデルアプローチを使用したい場合は、ここでそれを構築する方法を説明します。

  • EntityFrameworkエンティティクラスをリポジトリの外部に公開しないでください。リポジトリからDto(POCO)またはドメインオブジェクトを返すことを選択できます。Dtoをさらに分離したい場合は、それで問題ありません。Dtoをドメインオブジェクトに変換するには、サービスレイヤーなどの別のレイヤーが必要です。

  • ドメインオブジェクトにビジネスロジックを配置します。したがって、Domain.Employee.GetSenority()はドメインオブジェクトにあります。

  • ドメインオブジェクトに適合しないロジックは、UnitOfWorkまたはサービスレイヤーに存在できます。

  • コントローラでドメインオブジェクトをViewModelに変換します。この時点で、Employee.GetSenority()をMyViewModel.Senorityプロパティにマップします。基本的に、ViewModelはDtoであり、通常はそれほど多くないビュー固有のロジックのみが含まれています。

  • リポジトリはどこにありますか。UnitOfWorkパターンをそのまま使用することも、単にServiceLayerクラスを作成することもできます。ここで重要なのは、これらを他の種類のアプリケーションで使用できるようにすることです。たとえば、デスクトップまたはWindows 8スタイルのアプリを作成する場合、ドメインエンティティとともにこれらのいずれかを再利用することをお勧めします。

あなたはこれを楽しんでいると確信しています。幸運を。

于 2012-10-16T16:14:25.723 に答える