Autofac:解析后获取构造函数参数(OnActivated/OnActivating)
Autofac: Get constructor parameter after resolve (OnActivated/OnActivating)
我有以下结构:
class SomeViewModel
{
public SomeViewModel(SomeService service)
{
service.SetViewModel(this); // <- Move this call to Autofac
}
}
class SomeService
{
public void SetViewModel(object viewModel)
{
//...
}
}
我不想在每个 ViewModel 中手动调用 service.SetViewModel
,而是想将此调用移至 IoC 容器 (Autofac)。我试过使用 OnActivated
但没有可用参数:
builder.Register<SomeViewModel>
.AsSelf()
.OnActivated(e =>
{
var service = e.Parameters
.OfType<SomeService>()
.FirstOrDefault(); // <- There are no parameters
service.SetViewModel(e.Instance);
});
是否可以将 SomeViewModel
构造函数中的调用 service.SetViewModel(this);
移动到某种 Autofac 注册中?
我同意@Steven。但即使我们将其分开,如果有多个视图模型共享同一个服务怎么办?哪一个将获得服务 - "last wins"?您需要再仔细考虑一下这个设计。
既然您已收到警告...您的解决方案可能如下:
...
builder.Register(s => CreateViewModel(s, svc => new SomeViewModel(svc))).AsSelf();
}
private T CreateViewModel<T>(IComponentContext ctx, Func<SomeService, T> createInstance) {
var svc = ctx.Resolve<SomeService>();
var instance = createInstance(svc);
svc.SetViewModel(instance);
return instance;
}
我有以下结构:
class SomeViewModel
{
public SomeViewModel(SomeService service)
{
service.SetViewModel(this); // <- Move this call to Autofac
}
}
class SomeService
{
public void SetViewModel(object viewModel)
{
//...
}
}
我不想在每个 ViewModel 中手动调用 service.SetViewModel
,而是想将此调用移至 IoC 容器 (Autofac)。我试过使用 OnActivated
但没有可用参数:
builder.Register<SomeViewModel>
.AsSelf()
.OnActivated(e =>
{
var service = e.Parameters
.OfType<SomeService>()
.FirstOrDefault(); // <- There are no parameters
service.SetViewModel(e.Instance);
});
是否可以将 SomeViewModel
构造函数中的调用 service.SetViewModel(this);
移动到某种 Autofac 注册中?
我同意@Steven。但即使我们将其分开,如果有多个视图模型共享同一个服务怎么办?哪一个将获得服务 - "last wins"?您需要再仔细考虑一下这个设计。
既然您已收到警告...您的解决方案可能如下:
...
builder.Register(s => CreateViewModel(s, svc => new SomeViewModel(svc))).AsSelf();
}
private T CreateViewModel<T>(IComponentContext ctx, Func<SomeService, T> createInstance) {
var svc = ctx.Resolve<SomeService>();
var instance = createInstance(svc);
svc.SetViewModel(instance);
return instance;
}