Search code examples
castle-windsorfactory-method

How do I get the type of the depender when registering components with the UsingFactoryMethod() of Castle?


I'm struggling a bit with getting my bindings correct for my Castle Windsor container. The original problem concerns log4net and named loggers and a description can be found in this question: Setting the name of a log4net logger.

However, the issue is now narrowed down to this:

I have a class Log4NetAuditor which implements IAuditor. Some of my classes extend my abstract class AuditableComponent which has an property Auditor of type IAuditor. When I regiser IAuditor with Castle it knows how to resolve and set the Auditor for all my classes that extend AuditableComponent.

Now, I need the constructor of Log4NetAuditor to take a Type parameter. This type should be the type of the class extending AuditableComponent. I have tried to make this happen through a factory method, but I cannot work it out:

container.Register(Component.For<IAuditor>().ImplementedBy<Log4NetAuditor>()
        .UsingFactoryMethod(RegisterAuditor).LifeStyle.Transient);

private static IAuditor RegisterAuditor(IKernel kernel, ComponentModel model, CreationContext context)
{
    Type loggerType = //magic to find correct type happens here

    return new Log4NetAuditor(loggerType, kernel.Resolve<ILoggerFactory>());
}

I'm staring myself blind at this problem. Can anyone help?


Solution

  • Ha - I just came across my age-old question, so I thought I'd post the answer. The answer is taken from this question: Why have named logger in Log4Net?

    The key is to use the CreationContext in the factory method like so

    ...UsingFactoryMethod((kernel,context) => new MyInstance(context.Handler.ComponentModel.Implementation));
    

    Of course - add your lifestyle as required.