1

I'm trying to work out why some of my test cases (using RhinoMocks 3.6 Build 20) aren't working, and I've narrowed the issue down to the following minimal unit test:

public interface ITest
{
    string Something { get; }
}

[Test]
public void TestStub()
{
    var mockery = new MockRepository();
    var testItem = mockery.Stub<ITest>();
    testItem.Stub(x => x.Something).Return("Hello");
    Assert.AreEqual("Hello", testItem.Something);
}

This fails with the message:

Expected: "Hello" But was: null

Any ideas what I'm doing wrong here? I've found a few examples on SO and the Rhino Wiki on how to stub read-only properties, and as far as I can tell, this should work fine.

Cheers in advance.

EDIT: Based on sll's advice below, I tried replacing

testItem.Stub(x => x.Something).Return("Hello");

with

testItem.Expect(x => x.Something).Return("Hello");

and the test still fails in the same manner.

Edit 2: I've got this working by adding the line

mockery.ReplayAll();

before the Assert - but I thought this was no longer required (from the wiki: "Mocks/stubs returned from MockRepository.GenerateMock() and MockRepository.GenerateStub() are returned in replay mode, and do not require explicit move to replay mode.")

AlexC
  • 1,646
  • 1
  • 14
  • 26

3 Answers3

1

Try out generating Mock instead:

var testItem = MockRepository.GenerateMock<ITest>();     
testItem.Expect(x => x.Something).Return("Hello");     
Assert.AreEqual("Hello", testItem.Something); 

Als make sure you shared entire test method, perhaps you ignored some lines of code? Try out usign Repeat.Any() perhaps proeprty accessed before you are doing expectation.

testItem.Expect(x => x.Something).Return("Hello").Repeat.Any();     

On example page Stub() used for methods, and suggested using Mock's Expect() for properties:

Using Expect() to set up properties

The Expect() extention method can be used to set up expectations and return values for properties.

sll
  • 61,540
  • 22
  • 104
  • 156
  • I'm aware that generating a mock works, but all the documentation I've seen suggests that the case above should work (eg http://stackoverflow.com/questions/2090191/stubbing-a-read-only-property-with-rhino-mocks and http://stackoverflow.com/questions/1087619/how-to-setup-return-value-for-a-readonly-property-using-rhinomocks-in-vb-net). I'm not setting the expectation on the stub (that would be a call to Expect), I'm (trying to) stub the property. – AlexC Apr 03 '12 at 10:03
  • Ary you using RhinoMocks 3.5? – sll Apr 03 '12 at 10:05
  • Documentation is not clear but from examples we can see that `Stub's Stub()` used for methods and `Mock's Expect()` for proeprties, perhaps this is how we should do as well – sll Apr 03 '12 at 10:10
  • Still fails - original question updated. EDIT: Oh I see you mean use Mock for the item. I dont think that's the solution - a lot of googling suggests that stubs CAN be used for read only properties. – AlexC Apr 03 '12 at 10:13
  • have you created a mock before setting `Expect()`? also perhaps you give us a part of real test? Try out adding `Return(..).Repeat.Any()` – sll Apr 03 '12 at 10:19
  • Nope - nothing else was done in this test case. I've got this working by adding the line mockery.ReplayAll() before the Assert - but I thought this was no longer required (from the wiki: Mocks/stubs returned from MockRepository.GenerateMock() and MockRepository.GenerateStub() are returned in replay mode, and do not require explicit move to replay mode.) – AlexC Apr 03 '12 at 10:25
1

Got it:

From the RhinoMocks 3.6 Blog Post comments:

09/03/2009 05:34 PM by Kurt Harriger

FYI,

I had a few dozen tests fail after upgrading to v 3.6 from code like this:

var mocks = new MockRepository();

var something = mocks.Stub

something.Stub(x=>x.DoSomething() ).Return(true);

something.DoSomething();

The root cause of the problem appears that mock.Stub/Mock/etc no longer returns the mock in replay mode. To fix replaced mock.Stub with MockRepository.GenerateStub.

Ayende Rahien 09/03/2009 06:50 PM by Ayende Rahien

Kurt,

That is actually expected, that should have never worked

So, by changing the test to:

    [Test]
    public void TestStub()
    {
        var testItem = MockRepository.GenerateStub<ITest>();
        testItem.Stub(x => x.Something).Return("Hello");
        Assert.AreEqual("Hello", testItem.Something);
    }

this now works.

Cheers

AlexC
  • 1,646
  • 1
  • 14
  • 26
-1

You are just setting the value so you would expect to do this like this:

public interface ITest
{
    string Something { get; }
}

[Test]
public void TestStub()
{
    var mockery = new MockRepository();
    var testItem = mockery.Stub<ITest>();
    testItem.Something = "Hello";
    Assert.AreEqual("Hello", testItem.Something);
}

No need to Stub with Func.

Davin Tryon
  • 66,517
  • 15
  • 143
  • 132
  • 1
    This wont compile - "Something" is read-only, so the "testItem.Something = "Hello";" line will cause a compile time error. – AlexC Apr 03 '12 at 10:06