Search code examples
.netrhino-mocks

RhinoMocks: override a stubbed property


Unfortunately the following pattern does not work in RhinoMocks:

[SetUp]
public void SetUp ()
{
    obj.Stub(s => s.Prop).Returns("a suitable default for all tests");
}

[Test]
public void VerySpecificTest ()
{
    obj.Stub(s => s.Prop).Returns("specific value, valid only for this single test");
}

It does not even throw an exception (which is particularly bad), the user just does not know why the second Stub() call does not have any effect whatsoever.

However, is there a way to make this work? How to "overwrite" a single property return?


Solution

  • IIRC, the supported way to override a previously recorded behavior of a stub or mock is to fall back Rhino Mocks' older API: you can use BackToRecord to cause the stub to forget its previously recorded behavior, then use Replay to go back to playback mode, then stub the property again:

    [SetUp]
    public void SetUp ()
    {
        obj.Stub(s => s.Prop).Returns("a suitable default for all tests");
    }
    
    [Test]
    public void VerySpecificTest ()
    {
        // Clear recorded expectations and immediately go back to replay mode.
        obj.BackToRecord();
        obj.Replay();
    
        // Now setup a new expectation.
        obj.Stub(s => s.Prop).Returns("specific value, valid only for this single test");
    }
    

    The drawback to this method is that BackToRecord causes the stub to forget all the expectations set up for it (not only the one you might want to override). There are a few hackarounds that avoid this (e.g., to use Repeat, or to set up the initial Stub using a lambda so that you can change the returned value later on; see e.g., How to clear previous expectations on an object? for some of these), but there is no supported API for this.