Home > Castle Windsor, Unit Testing > Testing Windsor component registrations

Testing Windsor component registrations

Having previously used Windsor on other projects and experienced the pain of debugging incomplete or invalid component registration via YSOD, I decided to be a little more proactive in my approach to container configuration on my current project.  This time round I have a suite of tests that (hopefully) cover all of the components that should be registered, and already these tests have exposed one problem that has arisen due to my ignorance around the NHibernate Facility.

In general, testing component registrations is as simple as resolving all of the types for a given service and ensuring the count matches some value you have determined via other means, like so:

        [Then]
        public void all_of_the_controllers_in_the_assembly_should_be_registered()
        {
            var controllerAssembly = typeof( RegistrationController ).Assembly;
            var controllerCount =
                controllerAssembly.GetExportedTypes()
                    .Where( t => t.IsSubclassOf( typeof( Controller ) ) && !t.IsAbstract )
                    .Count();
            var registeredControllerCount = _container.ResolveAll<Controller>().Length;
            registeredControllerCount.ShouldEqual( controllerCount );
        }

(_container is an IWindsorContainer instance and the [Then] attribute is from my customised xUnit BDD implementation)

The problem occurs when you try to use the same approach with open generic types such as IValidator<> – ResolveAll returns and array and you can’t create an array of open generic types. To get around this you need to retrieve the collection of handlers for the components rather than the components themselves (this is based on the assumption that a handler is generated for every registration – which I cannot disprove so I will go with it for now).

Using this approach, I can ensure the registration of all my IValidator<> instances with the following:

        [Then]
        public void all_of_the_validators_in_the_assembly_should_be_registered()
        {
            var validatorAssembly = typeof( RegistrationCommandValidator ).Assembly;
            var validatorCount =
                validatorAssembly.GetExportedTypes()
                    .Where( t => t.IsSubclassOf( typeof( IValidator<> ) ) && !t.IsAbstract && !t.IsInterface )
                    .Count();
            // Can't use ResolveAll as there is no way to create an array of an open type
            var registeredValidatorCount = _container.Kernel.GetHandlers( typeof( IValidator<> ) ).Length;
            registeredValidatorCount.ShouldEqual( validatorCount );
        }

The only difference to the first test is the call to _container.Kernel.GetHandlers( ... ) instead of _container.ResolveAll<...>().

  1. No comments yet.
  1. No trackbacks yet.