开发者

How to assert a private method on concrete class is called (TypeMock/NMock/etc..)?

开发者 https://www.devze.com 2022-12-21 09:56 出处:网络
I am trying to write a unit test for the \'IsUnique\' function in the class below that looks like this:

I am trying to write a unit test for the 'IsUnique' function in the class below that looks like this:

class Foo
{
    public bool IsUnique(params...)
    {
       ValidateStuffExists(params);
       return CheckUniqueness(params);
    }

    private void ValidateStuffExists(params)
    {
      //does some validation
    }

    private bool CheckUniqueness(params)
    {
       //does logic to determine if its unique per params
       return result;
    }

}

The only thing I want to test here is that ValidateStuffExists and CheckUniqueness is called and passed the arguments. That's all this function does so it's all I'm going to test (I'll bend the 'test public behavior only' psuedo-rule and test the private methods here, because its either have one big complicated method/tests or testing 2 private methods).

I am open to any mocking library. I use NMock and didn't think it was up for the Task - so I downloaded TypeMock as I've done reading and heard that this was the best and that it could mock out even concrete classes / non interface method calls...

I'm doing something like this in my test and it throws exception at the 'Isolate.WhenCalled' line:

        C开发者_高级运维rmEntityUniqueValidator_Accessor target = new CrmEntityUniqueValidator_Accessor(); // TODO: Initialize to an appropriate value
        DynamicEntity entity = null; // TODO: Initialize to an appropriate value
        string[] propertyNames = null; // TODO: Initialize to an appropriate value

        bool tru = true;
        Isolate.WhenCalled(() => target.CheckUniqueness(entity, propertyNames, null, null)).WillReturn(tru);

        target.ValidatePropertiesExist(entity, propertyNames);

        Isolate.Verify.WasCalledWithArguments(() => target.ValidatePropertiesExist(entity, propertyNames));
        Isolate.Verify.WasCalledWithArguments(() => target.CheckUniqueness(entity, propertyNames, null, null));

This throws an exception like "*** WhenCalled does not support using a method call as an argument."

Even though I'm able to do the same thing with a CLR class - I can mock out DateTime.Now doing this (code works):

        DateTime endOfWorld = new DateTime(2012, 12, 23);
        Isolate.WhenCalled(() => DateTime.Now).WillReturn(endOfWorld);
        DateTime dt = DateTime.Now;

        Assert.AreEqual(dt, endOfWorld);

Anyone have any advice here? Do I have to split these 2 methods into a seperate class and make an interface is the only way? or complicate my method/tests??? There must be something I'm missing here... Thanks much for any help in advance.

EDIT: I guess I'm trying to mock out the 2 private methods in the class for the one unit test. How could I do this without having to split out those 2 methods into a seperate class / interface?


try Isolate.NonPublic.WhenCalled(object,"nonpublic method").IgnoreCall

or Isolate.Verify.NonPublic.WasCalled(object,"method"..


RhinoMocks has the AssertWasCalled method which may serve the purpose of guaranteeing that a method calls another method... but I'm not sure you can do that on a private function of the same class you are unit testing. I think you could only do that if the two methods you wanted to stub were in another dependency class that was injected.

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号