根据documentation,我可以将激活事件用于"将实例切换为另一个实例或将其包装在代理中,"但我还没有能够让它发挥作用。
以下是我尝试的内容:
[TestFixture]
public class ReplaceInstanceTest
{
public interface ISample { }
public class Sample : ISample { }
public class ProxiedSample : ISample {
private readonly ISample _sample;
public ProxiedSample(ISample sample) {
_sample = sample;
}
}
[Test]
public void ReplaceInstance_can_proxy_for_interface_type()
{
var builder = new ContainerBuilder();
builder.RegisterType<Sample>()
.As<ISample>()
.OnActivating(x =>
x.ReplaceInstance(new ProxiedSample(x.Instance)))
.SingleInstance();
var container = builder.Build();
var sample = container.Resolve<ISample>();
Assert.That(sample, Is.InstanceOf<ProxiedSample>());
}
}
上述结果导致了类强制转换异常,因为autofac正在尝试将ProxiedSample
强制转换为Sample
实例,而不是。{/ p>
是否可以在ActivatingEvent上使用ReplaceInstance
来代理autofac(2.6或3.0)中的对象?
我知道可以使用RegisterDecorator,但我的实际配置包括配置和条件代理,因此我更愿意使用激活事件,如果可能的话。
答案 0 :(得分:1)
Travis在autofac列表detailing some of the challenges surrounding this上回复。在他的评论和NSGaga的建议之间,我提出了以下解决方法:
[Test]
public void ReplaceInstance_can_proxy_for_interface_type_when_using_multi_stage_registration()
{
var builder = new ContainerBuilder();
builder.RegisterType<Sample>().AsSelf();
builder.Register(c => (ISample)c.Resolve<Sample>())
.OnActivating(x => x.ReplaceInstance(new ProxiedSample(x.Instance)))
.SingleInstance();
var container = builder.Build();
var sample = container.Resolve<ISample>();
Assert.That(sample, Is.InstanceOf<ProxiedSample>());
}
可以使注册更紧凑:
builder.Register<ISample>(c => new Sample()).OnActivating(/*...*/);
这种方法的缺点是,如果Sample
构造函数更改,则注册也必须更改,我通过额外注册具体类型避免了这种情况。