質問: contextx.Client.Select(c => c.Person.EMail).FirstOrDefault(); ``` 上の最後の行では、電子メールxxxx@gmail.comを返すことはできません。代わりに、常にnullが返されます。 何か案は?
回答: ### あなたの直接の質問に答える あなたが尋ねた特定の質問について、私は2つのことを提案します: 1. `contextx.Client.ToArray()`を見て、あなたが本当にそのコレクションにいくつのメンバーがいるかを見てください。 `Client`コレクションが実際に空である可能性があります。その場合、実際にはnullが返されます。または、Clientコレクションの最初の要素に`EMail` null値がある可能性があります。 2. `contextx.SaveChanges()` `Client`コレクションを照会する前に`contextx.SaveChanges()`を呼び出すと、ビヘイビアーはどのように変化しますか? `SaveChanges`を呼び出すと、新しく挿入された値がコレクションに存在するかどうかが分かります。これは必須ではありませんが、Effortと`DbContext`間には奇妙なやりとりがあるかもしれません。 **編集:** `SaveChanges()`は答えになることが判明。 ### 一般的なテストの提案 "unit-testing"タグでこの質問にタブを当てたので、ユニットテストの実務家とコーチとして10年間勤めてきたことに基づいて、一般的なユニットテストのアドバイスを提供します。 *ユニット*テストは、単独で、アプリケーションの様々な小さな部品をテストについてです。通常これは、単体テストがいくつかのクラスと同時に対話することを意味します。これは、ユニットテストが外部ライブラリや依存関係(データベースなど)に依存すべきでないことを意味します。逆に、 *統合*テストではシステムの多くの部分を一度に実行し、データベースなどの外部依存関係が発生する可能性があります。 これは専門用語では不明瞭ですが、テストの実際の目的をチームの他のメンバーに伝えるためには重要です。 この場合、DbContextに依存する機能の単体テストを実際に行っているか、データアクセスレイヤーをテストしようとしているかのどちらかです。直接DbContextに依存するものの単体テストを書く場合は、DbContextへの依存関係を解除する必要があります。下の「 **DbContextの依存関係を解除**する」でこれについて説明します。それ以外の場合は、エンティティのマッピング方法など、DbContextの統合テストを実際に試みています。この場合、私は常にこれらのテストを分離し、実際の(ローカル)データベースを使用するのが最良であることを発見しました。プロダクションで使用しているのと同じ種類のローカルにインストールされたデータベースを使用したいと思うかもしれません。しばしば、SqlExpressはうまく動作します。テストがデータベースのインスタンスを指すようにして、テストが完全にゴミ箱に入るようにします。各テストを実行する前に、既存のデータをすべて削除します。既存のデータが矛盾することなく、必要なデータをセットアップできます。 ### DbContextへの依存を破る だから、あなたのビジネスロジックが`DbContext`にアクセスすることに依存しているときに、単体テストを書くにはどうすればよいですか? **あなたはそうしない。** データ永続性のためにEntity Frameworkを使用する私のアプリケーションでは、 `DbContext`へのアクセスが別のデータアクセスプロジェクトに含まれていることを確認します。通常は、Repositoryパターンを実装するクラスを作成し、それらのクラスは`DbContext`依存することができます。この場合、 `IClientRepository`インターフェイスを実装する`ClientRepository`を作成します。インタフェースは次のようになります。 ``` public interface IClientRepository { Client GetClientByEMail(string email); } ``` 次に、メソッドにアクセスする必要のあるクラスは、基本的なスタブ/モック/その他を使用して単体テストできます。 `DbContext`嘲笑することについて何も心配する必要はありません。データアクセスレイヤーが含まれており、実際のデータベースを使用して完全にテストできます。データアクセスレイヤのテスト方法に関するいくつかの提案については、上記を参照してください。 追加の利点として、このインタフェースの実装は、単一の統一された場所で電子メールアドレスで`Client`を見つけることが何を意味するかを定義します。 `IClientRepository`インターフェイスを使用すると、「システム内の`Client`エンティティをどのように照会するのですか?」という質問にすぐに答えることができます。 `DbContext`依存する`DbContext`は、ドメインクラスが接続文字列に依存してどこでもADO.Netコードを持つことを可能にすることとほぼ同じテスト問題の規模です。つまり、実際のデータストアを作成しなければならないということです。しかし、特定のデータアクセスアセンブリ内の`DbContext`へのアクセスが含まれている場合は、 `DbContext`記述がずっと簡単になります。 プロジェクトの構成に関しては、通常、データアクセスプロジェクトでEntity Frameworkへの参照のみを許可します。私はエンティティを定義する別のコアプロジェクトを用意します。また、コアプロジェクトでデータアクセスインターフェイスを定義します。次に、具体的なインターフェイス実装がデータアクセスプロジェクトに組み込まれます。ソリューションのほとんどのプロジェクトは、単にコアプロジェクトに依存するだけで、実際にはトップレベルの実行可能ファイルまたはWebプロジェクトのみがデータアクセスプロジェクトに依存する必要があります。