Autofac - 单例接口解析为瞬态

Autofac - Singleton interface resolved as transient

我正在构建 WPF 应用程序并将 Autofac 用作 IoC 容器。这个场景有点难以描述,但我会尝试在下面给出相关的代码:

我的应用引导程序包含以下代码以在我的应用中注册视图模型:

builder.RegisterAssemblyTypes(assemblySource)
       .Where(type => type.Name.EndsWith("ViewModel"))
       .Where(type => !string.IsNullOrWhiteSpace(type.Namespace) && type.Namespace.Contains("ViewModels"))
       .AssignableTo<INotifyPropertyChanged>()
       .AsSelf()
       .InstancePerDependency();

(请注意我必须进行的 InstancePerDependency() 调用,因为我显示了一个视图的许多实例)

然后我有以下代码来注册一个开放泛型的实现者:

builder.RegisterAssemblyTypes(assemblySource)
       .AsClosedTypesOf(typeof(INotificationHandler<>))
       .AsSelf()
       .SingleInstance();

为了避免将容器传递到我的事件调度程序中,我将它传递给一个委托,如下所示:

builder.Register<ServiceFactory>(ctx => { return t => Container.Resolve(t ); });

最后一段代码给我带来了一个问题:它导致实现 INotificationHandler 接口的 ViewModel 在每次调用时都创建了实例,而我只需要解析一次实例,并且实现这一通用接口的 ViewModel 将在整个应用程序中只创建一个实例。

问题是:如何使 Autofac 解析实现 INotificationHandler<T> 接口的 ViewModel 的单个实例,同时保持要创建的其他 ViewModel PerDependency

谢谢。

您需要在第一次注册时排除实现 INotificationHandler<> 的 ViewModel。因此,将您的首次注册更改为:

builder.RegisterAssemblyTypes(Assembly.GetEntryAssembly())
            .Where(type => type.Name.EndsWith("ViewModel"))
            .Where(type => !string.IsNullOrWhiteSpace(type.Namespace) && type.Namespace.Contains("ViewModels"))
            .Where(type => !type.IsAssignableFrom(typeof(INotificationHandler<>)))
            .AssignableTo<INotifyPropertyChanged>()
            .AsSelf()
            .InstancePerDependency();