12

I started to use moq but from my understanding I always have to mock up all the methods that could be called even if I really do not care about them.

Sometimes it takes so long to mockup stuff you forget what you want to do. So I been looking at auto mocking but I am not sure what one I should use.

AutoFixture as an auto-mocking container

Automocking

I don't get how to use the first one at all. I sort of get the second one but never really tried it.

I am not sure if one is better than the other. The only thing I know is I am using AutoFixtures already what is a dependency of the first one.

So maybe in the long run it makes sense to go with the first one but like I said I can't find any basic tutorials on how to use it.

Edit

I am trying to follow "Nikos Baxevanis" examples but I am running into errors.

Failure: System.ArgumentException : A matching constructor for the given arguments was not found on the mocked type.
  ----> System.MissingMethodException : Constructor on type 'DatabaseProxyded46c36c8524889972231ef23659a72' not found.


var fixture = new Fixture().Customize(new AutoMoqCustomization());
        var fooMock = fixture.Freeze<Mock<IFoo>>();
       // fooMock.Setup(x => x.GetAccounts(It.IsAny<IUnitOfWork>()));
        var sut = fixture.CreateAnonymous<AdminService>();

        sut.Apply();
        fooMock.VerifyAll();

I think it is because of my petapoco unitOfWork property

PetaPoco.Database Db { get; }

Not sure if I got to mock this up somehow or what.

chobo2
  • 83,322
  • 195
  • 530
  • 832
  • About the exception that you get, there is nothing wrong with the way you use AutoFixture and Auto-Mocking. I would be happy to help further if you can include in your question the source code for all the types used by the test. – Nikos Baxevanis Oct 19 '12 at 20:44
  • Ya I been walking through the code and the problem is in my service layer method(the method I am trying to unit test). A call is made. Eventhough I have a unit of work that is an interface the property Db is not a interface and that is causing it to crash. I have to mock it out but the petapoco does not have an interface. So I to wrap it I guess – chobo2 Oct 19 '12 at 20:48

1 Answers1

26

While I have never used moq-contrib Automocking, I could probably provide some information on using AutoFixture as an auto-mocking container.

Currently there is support for Moq, Rhino Mocks, FakeItEasy, and NSubstitute. Just install the appropriate extension AutoMoq, AutoRhinoMocks, AutoFakeItEasy, and AutoNSubstitute.

Once you have installed one of the extensions for Auto Mocking the extra call is:

var fixture = new Fixture()
    .Customize(new AutoMoqCustomization());

(or if you are using Rhino Mocks)

var fixture = new Fixture()
     .Customize(new AutoRhinoMockCustomization());

(or if you are using FakeItEasy)

var fixture = new Fixture()
     .Customize(new AutoFakeItEasyCustomization());

(or if you are using NSubstitute)

var fixture = new Fixture()
     .Customize(new AutoNSubstituteCustomization());

Example 1

public class MyController : IController
{
    public MyController(IFoo foo)
    {
    }
}

public interface IFoo
{
}

Here is how to use AutoFixture to create instances of MyController class:

var fixture = new Fixture()
    .Customize(new AutoMoqCustomization());

var sut = fixture.CreateAnonymous<MyController>();

Now, if you inspect the sut variable you will see the the IFoo is a mocked instance (having a type name similar to Castle.Proxies.IFooProxy).

Example 2

This examples extends the previous one.

You can instruct AutoFixture to use your own, pre-configured, mocked instance:

var fooMock = fixture.Freeze<Mock<IFoo>>();
// At this point you may setup expectation(s) on the fooMock.

var sut = fixture.CreateAnonymous<MyController>();
// This instance now uses the already created fooMock.
// Verify any expectation(s).

That's basically it - but it can go further!

Below are the previous examples using AutoFixture decleratively with the xUnit.net extension.

Example 1

[Theory, AutoMoqData]
public void TestMethod(MyController sut)
{
    // Start using the sut instance directly.
}

Example 2

[Theory, AutoMoqData]
public void TestMethod([Frozen]Mock<IFoo> fooMock, MyController sut)
{
   // At this point you may setup expectation(s) on the fooMock.
   // The sut instance now uses the already created fooMock.
   // Verify any expectation(s).
}

You may find more information on this blog post which contains links to everything related around AutoFixture, xUnit.net, and Auto Mocking.

Hope that helps.

Nikos Baxevanis
  • 10,868
  • 2
  • 46
  • 80
  • What is Freeze? I don't get it. Your 2nd example is showing how to mockup everything but if you want to start passing in your own stuff then that is what you do? – chobo2 Oct 13 '12 at 17:25
  • 1
    You may `Freeze` an instance of a type so that when AutoFixture needs to create an instance of the same type it will _reuse_ the already created one. You may find more information about this feature [here](http://blog.ploeh.dk/2010/03/17/AutoFixtureFreeze.aspx). – Nikos Baxevanis Oct 13 '12 at 17:54
  • 1
    Keep in mind that `Freeze` is needed only if you need to set an expectation to a mocked instance which is a dependency of the requested type. (Of course, you may have to freeze more than one type instances depending on the scenario.) – Nikos Baxevanis Oct 13 '12 at 18:00
  • Hmm ok, Got to play around with it but my undestanding of is correct right? That these will make a fake mockup of all methods(that have an interfaces) right? Then the methods you care about can then go further and setup them up with moq setup function? I also don't 100% get what is going on here var fooMock = fixture.Freeze>(); Why did you go out of your way to mock IFoo where in the 1st example you did not. – chobo2 Oct 15 '12 at 17:12
  • 3
    On `Example 1` we don't really care to setup an expectation on the `IFoo` mock. We just go ahead and ask AutoFixture to create an instance of the `MyController` type. This will automatically inject a mocked instance of `IFoo` type. On `Example 2`, we *do* want to setup and expectation so we manually create a mocked instance and we _Freeze_ it - telling AutoFixture to _reuse_ the already created instance when requesting the `MyController` type. (If we don't do that, the expectation would fail since the `MyController` is going to use another instance - not the one that we setup the expectation.) – Nikos Baxevanis Oct 15 '12 at 19:13
  • Would it be bad to just create the fixture in the constructor and then use it through all the tests? – chobo2 Oct 19 '12 at 20:10
  • @ Nikos Baxevanis - Been trying to get your code examples to work in my project but I keep getting an error. See my OP. – chobo2 Oct 19 '12 at 20:30
  • In this particular scenario, I would strongly suggest to let AutoFixture handle the object creation including any of the dependencies. Your unit tests are more robust that way - e.g. if for some reason you modify the constructor(s) there are less chances for compile time erros. – Nikos Baxevanis Oct 19 '12 at 20:41
  • I been playing around with your examples and I wanted to confirm that order seems to matter? I tried making the controller object first then the IFooMock and my unit tests failed(since I used moq verify and said the method should only be called once). I am thinking it first made the automock then it made the mock that I told it to make thus calling each method twice? – chobo2 Oct 22 '12 at 16:03
  • 2
    Yes, that is expected because first you requested the `MyController` type (so AutoFixture supplied an auto-mocked instance for the `IFoo` dependency) and after you created a _new_ mock of `IFoo` (which is a different instance of the one that was passed in the `MyController`). When you need to set an expectation on a mock _Freeze_ it _before_ you request a type that depends on the mocked object. That way, AutoFixture will _reuse_ the already created mock and the expectation will succeed. – Nikos Baxevanis Oct 22 '12 at 21:23