本文介绍了Rhino Mocks-Testing Repository层返回“对象引用未设置为实例".错误的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

谨慎起见,我首先说我是Rhino Mocks的新手,而且更喜欢模拟.

Its prudent that I firstly say I'm new to both Rhino Mocks and to mocking more generally.

考虑到这一点,我试图对Linq to SQL存储库层进行单元测试,以确保数据上下文上的正确方法被命中,并且LINQ to SQL正在正确过滤.

With that in mind i'm attempting to Unit test my Linq to SQL repository layer to ensure that the correct methods on the datacontext are being hit, and that the LINQ to SQL is filtering correctly.

〜为清晰起见而编辑〜

有问题的方法-'GetRecordWhere'-在存储库类中定义.它在DataContextWrapper上调用方法"GetTable",这是我围绕Linq to SQL DataContext(自动生成)的自定义包装程序,该方法是为了使DataContext可模拟而实现的.

The method in question - 'GetRecordWhere' - is defined in the Repository class.It calls the method - 'GetTable' - on the DataContextWrapper which is my custom wrapper around the Linq to SQL DataContext (auto-generated) which was implemented to make the DataContext mockable.

public interface IDataContextWrapper : IDisposable
{
    IQueryable<TName> GetTable<TName>() where TName : class;
}

public class DataContextWrapper : IDataContextWrapper
{
    public IQueryable<TName> GetTable<TName>() where TName : class
    {
        return _db.GetTable<TName>().AsQueryable();
    }
}

public class Repository :  IRepository
{
    public T GetRecordWhere<T>(Expression<Func<T, bool>> predicate) where T : class
    {
        return _dataContext.GetTable<T>().Where(predicate).SingleOrDefault();
    }
}

当尝试对'GetTable'方法进行存根以提供可查询的结果集时,会引发我当前面临的错误.可以使用'GetRecordWhere'方法来查询该结果集.

The error I am currently faced with is thrown when attempting to stub the 'GetTable' method to provide a queryable result set which can be queryed using the 'GetRecordWhere' method.

ArgumentNullExcpetion:值不能为null.参照该行抛出:

The ArgumentNullExcpetion: value cannot be null. is thrown with reference to the line:

Arg<Expression<Func<Billing, bool>>>.Is.Anything

..我也尝试过使用Is.NotNull和一个特定的谓词.

.. which I have also tried with Is.NotNull and a specific predicate.

单元测试示例:

    _dataContext = MockRepository.GenerateMock<IDataContextWrapper>();

    [Test]
    public void GetRecordWhere()
    {
        // Arrange
        var billing = new Billing { BillingId = 1 };
        var billingQueryList = new List<Billing> {billing};
        const int testId = 1;

       _dataContext.Stub(x => x.GetTable<Billing>()
                .Where(Arg<Expression<Func<Billing, bool>>>.Is.Anything)
                .SingleOrDefault())
                .Return(billing);

        _intRepository = new Repository(_dataContext);

        // Act
        var result = _intRepository.GetRecordWhere<Billing>(x => x.BillingId == testId);

        // Assert
        Assert.IsNotNull(result);
        Assert.AreEqual(result.BillingId, testId);
        _dataContext.AssertWasCalled(x => x.GetTable<Billing>());
    }

这是我对RhinoMocks的理解上的失败吗?

Is this a failing in my understanding of RhinoMocks?

感谢您的帮助!

推荐答案

任何要使用Rhino.Mocks进行模拟的方法都必须是虚拟的,因此Rhino.Mocks可以对其进行拦截并提供您定义的存根/模拟行为.查看您对GetTable的定义,它不是虚拟的,因此无法被模拟.

Any method that you want to mock with Rhino.Mocks needs to be virtual so Rhino.Mocks can intercept it and provide the stubbed/mocked behavior you define. Looking at your definition of GetTable, it is not virtual and therefore can't be mocked.

更新:

不要链接"您的方法模拟.只需定义您要方法执行的操作并返回值即可:

Don't "chain" your method mocks. Just define what you want the method to do and return the value:

_dataContext.Stub(x => x.GetTable<Billing>()).Return(billingQueryList.AsQueryable());

我只是将您的示例代码插入到单元测试中,并且通过上述存根设置,测试通过了.

I just plugged your sample code into a unit test and with the above stub setup, the test passes.

这篇关于Rhino Mocks-Testing Repository层返回“对象引用未设置为实例".错误的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-20 17:54