私はこれまで単体テストを実際に行ったことがなく、最初のテストでつまずいてつまずきました。問題は、 が_repository.Golfers.Count();
常にDbSet
が空であることを示していることです。
私のテストは単純です。新しいゴルファーを追加しようとしているだけです
[TestClass]
public class GolferUnitTest //: GolferTestBase
{
public MockGolfEntities _repository;
[TestMethod]
public void ShouldAddNewGolferToRepository()
{
_repository = new MockGolfEntities();
_repository.Golfers = new InMemoryDbSet<Golfer>(CreateFakeGolfers());
int count = _repository.Golfers.Count();
_repository.Golfers.Add(_newGolfer);
Assert.IsTrue(_repository.Golfers.Count() == count + 1);
}
private Golfer _newGolfer = new Golfer()
{
Index = 8,
Guid = System.Guid.NewGuid(),
FirstName = "Jonas",
LastName = "Persson"
};
public static IEnumerable<Golfer> CreateFakeGolfers()
{
yield return new Golfer()
{
Index = 1,
FirstName = "Bill",
LastName = "Clinton",
Guid = System.Guid.NewGuid()
};
yield return new Golfer()
{
Index = 2,
FirstName = "Lee",
LastName = "Westwood",
Guid = System.Guid.NewGuid()
};
yield return new Golfer()
{
Index = 3,
FirstName = "Justin",
LastName = "Rose",
Guid = System.Guid.NewGuid()
};
}
Entity Framework とコード ファーストを使用してデータ モデルを構築しました。コンテキストをテストするために、IDbSet の派生クラスをモックしました (正確に覚えていないオンラインの人々への失礼)
public class InMemoryDbSet<T> : IDbSet<T> where T : class
{
readonly HashSet<T> _set;
readonly IQueryable<T> _queryableSet;
public InMemoryDbSet() : this(Enumerable.Empty<T>()) { }
public InMemoryDbSet(IEnumerable<T> entities)
{
_set = new HashSet<T>();
foreach (var entity in entities)
{
_set.Add(entity);
}
_queryableSet = _set.AsQueryable();
}
public T Add(T entity)
{
_set.Add(entity);
return entity;
}
public int Count(T entity)
{
return _set.Count();
}
// bunch of other methods that I don't want to burden you with
}
コードをデバッグしてステップ実行すると、 をインスタンス化し_repository
て 3 人の偽のゴルファーで満たすことがわかりますが、add 関数からステップアウトすると、_respoistory.Golfers
は再び空になります。新しいゴルファーを追加すると、_set.Add(entity)
実行され、ゴルファーが追加されますが、再び_respoistory.Golfers
空です。ここで何が欠けていますか?
アップデート
ばかで申し訳ありませんが、コンテキストに を実装していませんでしset
たMockGolfEntities
。私が持っていなかった理由は、以前に試したのですが、方法がわからず、先に進んで忘れてしまったからです。では、どのように設定しIDbSet
ますか?これは私が試したものですが、Stack Overflow エラーが発生します。私はばかのように感じますが、set 関数の書き方がわかりません。
public class MockGolfEntities : DbContext, IContext
{
public MockGolfEntities() {}
public IDbSet<Golfer> Golfers {
get {
return new InMemoryDbSet<Golfer>();
}
set {
this.Golfers = this.Set<Golfer>();
}
}
}