一个快速的注意之前,我跳进这一点。通常情况下,您希望避免使用“严格”模拟,因为它会进行脆弱的测试。如果发生任何你没有明确告诉犀牛会发生的事情,严格的模拟会抛出异常。此外,我认为您可能会误解犀牛在创建模拟电话时所做的事情。可以把它看作是一个自定义的对象,它既可以派生出来,也可以实现你定义的System.Type。如果你自己做的,将是这样的:
public class FakeUserType: User
{
//overriding code here
}
由于IsAdministrator可能只是用户类型公共财产,你不能在继承类型覆盖它。
就您的问题而言,您可以通过多种方式处理此问题。你可以在你的用户类实现IsAdministrator作为虚拟财产所提到如下aaronjensen:
public class User
{
public virtual Boolean IsAdministrator { get; set; }
}
这是一个不错的办法,但只有当你打算从你的用户类继承。此外,如果你不想伪造这个班的其他成员,他们也必须是虚拟的,这可能不是所期望的行为。
另一种完成此操作的方法是通过使用接口。如果它真的是你想要模拟的用户类,那么我会从中提取一个接口。你上面的例子会是这个样子:使用dependency injection and IOC
public interface IUser
{
Boolean IsAdministrator { get; }
}
public class User : IUser
{
private UserSecurity _userSecurity = new UserSecurity();
public Boolean IsAdministrator
{
get { return _userSecurity.HasAccess("AdminPermissions"); }
}
}
public void CreateSomethingIfUserHasAdminPermissions()
{
IUser user = _mocks.StrictMock<IUser>();
SetupResult.For(user.IsAdministrator).Return(true);
// do something with my User object
}
你可以得到,如果你想票友,但基本原则是一刀切相同。通常你希望你的类依赖于接口而不是具体的实现。
我希望这会有所帮助。我现在一直在使用RhinoMocks进行重要项目,所以不要犹豫,问我关于TDD和嘲笑的问题。
只是需要注意的是最后一个例子需要一个`_mocks.ReplayAll()`你做的IUSER存根任何事情之前。 – 2009-10-30 00:07:11