Search code examples
.netunit-testingrhino-mockshttpcontexthttp-caching

How to simulate a call to HttpContext.Cache["MyKey"] with Rhino Mocks?


Short version:

How to get Rhino Mocks to simulate a call to HttpContext.Cache["MyKey"] and return expected data?

Long version:

I need to simulate a return value from the HttpContext.Cache with Rhino Mocks. I'm using the following code in the TestInitialize method of my (Visual Studio) unit test

// All these are fields on my Unit test class.
foo = new Foo();
mock = new MockRepository();
context = mocks.DynamickMock<HttpContextBase>();
var cache = context.Stub(x => x.Cache).Return(HttpRuntime.Cache);

So far so good. Now I tried the two followings:

cache.Stub(x => x["MyKey"]).Return(foo);

and

context.Stub(x => x.Cache["MyKey"]).Return(foo);

The first one won't even compile. Visual Studio tells me that I can't "apply indexing with [] to an expression of type 'Rhino.Mocks.Interfaces.IMethodOptions'".

The second one compiles but I get a NullReferenceException. I guess this is because I didn't call yet mock.ReplayAll();. When I move this line inside my test (before or after mock.ReplayAll()) I still get a NullReferenceException. The exception does not have any inner exception. However, when I hover on the Cache of x.Cache, I get the following error message as a value for x.Cache: "'x.Cache' threw an exception of type System.InvalidOperationException" and the message of the said exception is "*Previous method 'HttpContextBase.get_Cache();' requires a return value or an exception to throw.*".

Well, I think I understand why it happens as long as mock.ReplayAll() hasn't been called but I don't know why it happens after.

So in a word, how can I get this to work? How to get Rhino Mocks to simulate a call to HttpContext.Cache["MyKey"] and return expected data?


Solution

  • Ok, actually there is no need to stub it. After calling mocks.ReplayAll() I just need to insert whatever I want into cache using

    _context.Cache.Insert("MyKey", foo);
    

    The only drawback is that there seems to be no way to use this in the initialization method of the test.