Register a concrete type in the auto-mocking container

By default, SpecsFor's auto-mocking container will create mock objects for your class's dependencies. However, you can easily change this behavior to inject your own mock or fake object or to inject a concrete type. Consider this trivial domain:

public class CarFactory
    {
        private readonly IEngineFactory _engineFactory;

        public CarFactory(IEngineFactory engineFactory)
        {
            _engineFactory = engineFactory;
        }

        public Car BuildMuscleCar()
        {
            return new Car
            {
                Engine = _engineFactory.GetEngine("V8")
            };
        }
    }

    public class Car
    {
        public Engine Engine { get; set; }
    }

    public class Engine
    {
    public string Maker { get; set; }
        public string Type { get; set; }
    }

    public interface IEngineFactory
    {
        Engine GetEngine(string engineType);
    }

    public class RealEngineFactory : IEngineFactory
    {
        public Engine GetEngine(string engineType)
        {
            return new Engine
            {
                Maker = "Real Engines, Inc",
                Type = engineType
            };
        }
    }

Now let's say we wanted to write integration specs against our CarFactory, so we want our specs to also use RealEngineFactory. We can tell SpecsFor to use RealEngineFactory instead of a mock by overriding the ConfigureContainer method:

protected override void ConfigureContainer(IContainer container)
            {
                container.Configure(cfg =>
                {
                    cfg.For<IEngineFactory>().Use<RealEngineFactory>();
                });
            }

Now our system under test will receive an instance of RealEngineFactory instead of a mock.

Here's what our full specs look like:

public class ContainerConfigurationSpecs
    {
        public class when_a_concrete_type_is_registered_in_the_container : SpecsFor<CarFactory>
        {
            private Car _car;

            protected override void ConfigureContainer(IContainer container)
            {
                container.Configure(cfg =>
                {
                    cfg.For<IEngineFactory>().Use<RealEngineFactory>();
                });
            }

            protected override void When()
            {
                _car = SUT.BuildMuscleCar();
            }

            [Test]
            public void then_the_cars_engine_was_made_by_the_real_engine_factory()
            {
                _car.Engine.Maker.ShouldEqual("Real Engines, Inc");
            }
        }
    }

Did this page help you?