Autofac和Func工厂 [英] Autofac and Func factories
问题描述
我正在使用Caliburn.Micro和Autofac开发应用程序.
I'm working on an application using Caliburn.Micro and Autofac.
在我的合成根目录下,我现在面临Autofac的问题: 我必须将全局使用的IEventAggregator注入到我的FirstViewModel中,然后再注入第二个IEventAggregator,该IEventAggregator只能由该FirstViewModel及其子级使用.
In my composition root I'm now facing a problem with Autofac: I have to inject the globally used IEventAggregator into my FirstViewModel, and a second IEventAggregator that has to be used only by this FirstViewModel and it's children.
我的想法是将第二个作为Owned<IEA>
注入,并且它的工作原理是,容器提供了另一个IEA实例.
My idea was to make the second one be injected as Owned<IEA>
, and it works, the container provides a different instance of IEA.
public FirstViewModel(
IEventAggregator globalEA,
IEventAggregator localEA,
Func<IEventAggregator, SecondViewModel> secVMFactory) {}
当我必须向SecondViewModel提供事件聚合器时,问题就来了.
The problem comes when I have to provide the event aggregators to the SecondViewModel.
要创建SecondViewModel,我将工厂方法用作Func<IEA, SecondVM>
.
SecondViewModel的构造函数如下:
To create the SecondViewModel I use a factory method as Func<IEA, SecondVM>
.
The SecondViewModel's constructor is the following:
public SecondViewModel(IEventAggregator globalEA, IEventAggregator localEA) {}
我希望容器将第一个作为已注册的容器注入,第二个将是Func<IEA, SecVM>
的IEA参数.
I want the container to inject the first as the registered one, and the second will be the IEA parameter of the Func<IEA, SecVM>
.
这是我在容器中注册的功能:
this is the function I registered in the container:
builder.Register<Func<IEventAggregator, SecondViewModel>>(
c =>
(ea) =>
{
return new SecondViewModel(
c.Resolve<IEventAggregator>(),
ea);
}
);
但是当它被FirstViewModel
调用时,出现以下错误:
but when it gets called by the FirstViewModel
I get the following error:
Autofac.dll中发生了'System.ObjectDisposedException'类型的异常,但未在用户代码中处理
An exception of type 'System.ObjectDisposedException' occurred in Autofac.dll but was not handled in user code
其他信息:此解析操作已经结束.使用Lambda注册组件时,无法存储IComponentContext'c'参数到lambda.而是从"c"再次解析IComponentContext,或从基于Func<>的工厂解析以从中创建后续组件.
Additional information: This resolve operation has already ended. When registering components using lambdas, the IComponentContext 'c' parameter to the lambda cannot be stored. Instead, either resolve IComponentContext again from 'c', or resolve a Func<> based factory to create subsequent components from.
我不明白问题出在哪里,请您能帮助我,我想念什么?
I can't understand where the problem is, can you help me please, what am I missing?
谢谢.
推荐答案
您正在FirstViewModel
构造函数之外调用secVMFactory
,因此到那时处置ResolveOperation并在工厂方法中,c.Resolve
将抛出
You are calling secVMFactory
outside of your FirstViewModel
constructor so by that time the ResolveOperation is disposed and in your factory method the c.Resolve
will throw the exception.
幸运的是,异常消息非常具有描述性,并告诉您该怎么做:
Luckily the exception message is very descriptive and telling you what to do:
使用lambda注册组件时,IComponentContext'c' lambda的参数无法存储.相反,要么解决 再次从"c"获取IComponentContext
When registering components using lambdas, the IComponentContext 'c' parameter to the lambda cannot be stored. Instead, either resolve IComponentContext again from 'c'
因此,除了调用c.Resolve
之外,您还需要从c
解析IComponentContext
并将其用于工厂功能:
So instead of calling c.Resolve
you need to resolve the IComponentContext
from c
and use that in your factory func:
builder.Register<Func<IEventAggregator, SecondViewModel>>(c => {
var context = c.Resolve<IComponentContext>();
return ea => {
return new SecondViewModel(context.Resolve<IEventAggregator>(), ea);
};
});
这篇关于Autofac和Func工厂的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!