简体   繁体   中英

Stubbing a method which is called in class constructor in RhinoMocks

My class has a method like this:

internal virtual Something CreateSomething(){...}

It was done this way so that in testing I can stub CreateSomething() to return a mock object:

var something = ...; //some mock object
var t = MockRepository.GenerateStub<MyObject>();
t.Stub(x => x.CreateSomething()).Return(something);

This worked fine but now CreateSomething() is called in the class constructor, before it was called later on, so by the time I stub the method my object is already created.

Is there a workaround that doesn't involve changing the design, to pass stub methods in at construction time? If not I can consider changing the design to use construction-injection (which I'm sure some of you are itching to suggest anyway!) but I'd rather see if Rhino supports this use-case first.

There is no way to stub the method before it is invoked from its class constructor. This is C# limitation. And this is reasonable.
In general it is a bad practice to call virtual method from the constructor, because likely the result will not be what is expected. See details here: Virtual member call in a constructor .

So, I highly recommend to either make this method non-virtual, or avoid its invocation from the constructor.
Anyway in such situation it won't work as virtual.

Regarding you question about testing the method, which is called from constructor.
I presume, this is a private method. Otherwise it could be tested as a regular public method.
As it is private, then there is no need to test this particular method in isolation. I recommend to follow general approach in testing constructors and testing private methods: Do not test private methods.
Test the public visible effect instead. That could be:

  • Public property initialization
  • Mocked dependencies invocation or properties access
  • Exception thrown
  • etc.

Please also find more details about this topic by the links below:
Is it important to unit test a constructor?
Unit testing private methods in C#

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM