grokky
grokky

Reputation: 9265

Autofac factory that resolves instances without depending on the container

I have a factory that creates validator instances. I pass in an object to validate, and it gives me the validator that I can use to validate it.

public class ValidatorFactory : IValidatorFactory
{


  public ValidatorFactory(IComponentContext container) { _container = container; }
  private readonly IComponentContext _container;


  public IValidator create(object objectToValidate)
  {
    var validatorType = typeof(IValidator<>).MakeGenericType(new Type[] { objectToValidate.GetType() });

    object validator;
    _container.TryResolve(validatorType, out validator);

    return validator as EntityValidatorI;
  }


}

It works, but I need to pass in the container IComponentContext.

Is there a better way where I don't need to do that?

Autofac has "Implicit Relationship Types" but I'm unsure how to use them here, as the type would only be known at runtime.

Upvotes: 1

Views: 221

Answers (1)

Vignesh.N
Vignesh.N

Reputation: 2666

you can do something like below, Instead of injecting IComponentContext into your main classes, inject a generic Func method.
The code below might not compile as I quickly just wrote it here but I hope you get the idea.

public class ValidatorFactory : IValidatorFactory
{
  public ValidatorFactory(Func<Type, IValidator> factory) { _factory = factory; }
  private readonly Func<Type, IValidator> _factory;


  public IValidator create(object objectToValidate)
  {
    var validatorType = typeof(IValidator<>).MakeGenericType(new Type[] { objectToValidate.GetType() });

    return _factory(validatorType);
  }
}

public  static class YourBootstrapperClass{

    public static void Register(ContainerBuilder containerBuilder){

        containerBuilder.Register(ctx => new ValidatorFactory(type => { 
                object validator;
                containerBuilder.TryResolve(validatorType, out validator);
                return validator;
         })).As<IValidatorFactory>();
    }
}

Upvotes: 1

Related Questions