Unit testing 如何包含关联实体

Unit testing 如何包含关联实体,unit-testing,entity-framework-4,typemock-isolator,Unit Testing,Entity Framework 4,Typemock Isolator,我想为下面的方法“GetByEmail”创建测试用例 公共用户GetByEmail(字符串电子邮件,bool includeUserRoles=false,bool includeUserType=false) { 表达式whereClause=u=>u.Email==Email; 返回GetQuery(where子句,includeUserRoles,includeUserType).FirstOrDefault(); } 私有IQueryable GetQuery(表达式where子句,

我想为下面的方法“GetByEmail”创建测试用例

公共用户GetByEmail(字符串电子邮件,bool includeUserRoles=false,bool includeUserType=false) { 表达式whereClause=u=>u.Email==Email; 返回GetQuery(where子句,includeUserRoles,includeUserType).FirstOrDefault(); } 私有IQueryable GetQuery(表达式where子句, bool includeUserRoles=false,bool includeUserType=false) { IQueryable query=base.GetQuery(where子句); 如果(包括用户角色) query=query.Include(u=>u.UserRoles); if(includeUserType) query=query.Include(u=>u.UserType); 返回查询; } 受保护的IQueryable GetQuery(表达式谓词),其中T:EntityBase { 返回谓词!=null? CreateObjectSet()。其中(谓词): CreateObjectSet(); } 受保护的IObjectSet CreateObjectSet(),其中T:EntityBase { 返回_context.CreateObjectSet(); } 公共静态IQueryable包含(此IQueryable源、表达式属性) { var objectQuery=源作为objectQuery; if(objectQuery!=null) { var propertyPath=GetPropertyPath(属性); 返回objectQuery.Include(propertyPath); } 返回源; } 下面是我的测试用例方法-

[Fact] 
private void GetByEmail_PassedEmailAddress_RelatedUser() 
{ 
  //Created fake context 
  var fakeContext = Isolate.Fake.Instance<Entities>(); 

  //Created fake Repository and passed fakeContext to it 
  var fakeRepository = Isolate.Fake.Instance<Repository>(Members.CallOriginal,   ConstructorWillBe.Called, fakeContext);

  //Created fake in memory collection of User 
  var fakeUsers = GetUsers(); 

  Isolate.WhenCalled(() => fakeContext.Context.CreateObjectSet<User>()) 
         .WillReturnCollectionValuesOf(fakeUsers); 

  var User = Isolate.Invoke.Method(fakeRepository, "GetByEmail", "abc@xyz.com", true, true);

  Assert.True(User != null); 
} 
[事实]
private void GetByEmail\u PassedEmailAddress\u RelatedUser()的
{ 
//创建假上下文
var fakeContext=Isolate.Fake.Instance();
//创建了假存储库并将假上下文传递给它
var fakeRepository=Isolate.Fake.Instance(Members.CallOriginal,ConstructorWillBe.Called,fakeContext);
//创建了用户的内存中的伪集合
var fakeUsers=GetUsers();
隔离.WhenCalled(()=>fakeContext.Context.CreateObjectSet())
.将返回收集值(伪造用户);
var User=Isolate.Invoke.Method(fakeRepository,“GetByEmail,”abc@xyz.com“,真的,真的);
Assert.True(User!=null);
} 
在上面的测试用例方法中,我成功地获得了通过电子邮件的用户,但无法包含关联用户的其他实体


请让我知道,我如何才能包括与相关用户的其他实体

Include
是泄漏的抽象-它仅适用于EF和linq to实体,不能成功用于linq to对象。您知道单元测试需要填充关系,因此
GetUsers
方法必须准备数据。这就是模拟/伪造的一个要点——您不会考虑模拟方法的内部实现。您只需返回应该返回的内容


顺便问一下,你考试的目的是什么?看起来您正在尝试测试一个模拟-这是错误的。Mock提供了正确的数据,您只需要它来测试依赖于Mock组件的另一个功能。

我以用户身份返回IQueryable。我是不是应该退些别的东西而不是我能退的。private IQueryable GetUsers(){var list=new list{new User(){UserID=1,FirstName=“abc”,LastName=“xyz”,UserEmail=”abc@xyz.com},新用户(){UserID=2,FirstName=“lmn”,LastName=“ijk”,UserEmail=”lmn@ijk.com“},新用户(){UserID=3,FirstName=“pqr”,LastName=“stu”,UserEmail="pqr@stu“},};返回列表。AsQueryable();}”返回IQueryable会使您的存储库几乎不可模拟,您的依赖代码也几乎不可单元测试。我就这个问题写了多篇文章。请检查或。
IQueryable
是使用EF开发应用程序的方法,但目前可能无法确保您在模拟的
IQueryable
上的单元测试将测试您的真实代码我通常的建议是要么隐藏
IQueryable
,要么使用RealDB的集成测试。
[Fact] 
private void GetByEmail_PassedEmailAddress_RelatedUser() 
{ 
  //Created fake context 
  var fakeContext = Isolate.Fake.Instance<Entities>(); 

  //Created fake Repository and passed fakeContext to it 
  var fakeRepository = Isolate.Fake.Instance<Repository>(Members.CallOriginal,   ConstructorWillBe.Called, fakeContext);

  //Created fake in memory collection of User 
  var fakeUsers = GetUsers(); 

  Isolate.WhenCalled(() => fakeContext.Context.CreateObjectSet<User>()) 
         .WillReturnCollectionValuesOf(fakeUsers); 

  var User = Isolate.Invoke.Method(fakeRepository, "GetByEmail", "abc@xyz.com", true, true);

  Assert.True(User != null); 
}