2017-10-20 216 views
1

我需要此IService是可重用的。每当IService被注入到构造函数中,我都需要Service.Dependent来引用注入类的类型。获取对通用类型服务的从属服务的引用

builder.Register<Service>(c => 
     { 
      var a = new Service(); 
      a.Dependent = c.Resolve<CallingType??>(TypedParameter.From(a)); 
      return a; 
     }).As<IService>(); 

interface IService {} 

class Service : IService { 
    BaseClass Dependent {get; set;} 
} 


class SomeClass : BaseClass { 
    SomeClass(IService service) { 
     service.Dependent //This should be type BaseClass of SomeClass 
    } 
} 

回答

2

Autofac支持open generic registrationcircular dependencies
所以它可以像做:

builder.RegisterGeneric(typeof (Service<>)) 
    .As(typeof (IService<>)) 
    .InstancePerLifetimeScope() 
    .PropertiesAutowired(PropertyWiringOptions.AllowCircularDependencies); 
builder.RegisterType<SomeClass>() 
    .InstancePerLifetimeScope(); 

而且container.Resolve<IService<SomeClass>>()将返回你的SomeClass注入实例,它会递归收到此Service实例服务。

似乎在注册期间没有提取被调用者类型的选项。 对于您更新的示例自定义Registration Source可能会有所帮助。
这是继承自BaseType类型的“通用”注册。 但它看起来像过度工程。

public class HandlerRegistrationSource : IRegistrationSource 
{ 
    public IEnumerable<IComponentRegistration> RegistrationsFor(
    Service service, 
    Func<Service, IEnumerable<IComponentRegistration>> registrationAccessor) 
    { 
    var swt = service as IServiceWithType; 
    if(swt == null || !typeof(BaseClass).IsAssignableFrom(swt.ServiceType)) 
    { 
     // It's not a request for the BaseClass type, so skip it. 
     return Enumerable.Empty<IComponentRegistration>(); 
    }   
    var registration = new ComponentRegistration(
     Guid.NewGuid(), 
     new DelegateActivator(swt.ServiceType, (c, p) => 
     { 
      var myService = c.Resolve<IService>(); 
      ... 
     } 
     ... 
    } 
    ... 
} 
+0

有没有办法做到这一点,我更新的例子。 autofac是否有办法在注册时使用反射来引用调用类型? –

+0

@CodyBouche,我已经更新了我的答案。 – Kote