2

我正在尝试解决 Autofac IoC 容器的问题。

我的 Web 应用程序包含以下部分:

  1. Web应用程序
  2. 核心(共享)库。
  3. 模块

每个模块都有对核心库的引用(包括下面的代码),并且每个模块都必须能够注册自己的类型。因此我需要在应用程序和模块之间有一个共享容器。

我有以下容器的代码:

public static class DependencyContainer
    {
        public static IContainer Container { get; private set; }

        public static ContainerBuilder Builder { get; private set; }

        public static void RegisterType<TFrom, TTo>() where TTo : TFrom
        {
            Builder.RegisterType<TTo>().As<TFrom>();
        }

        public static T ResolveType<T>()
        {
            return Container.Resolve<T>();
        }

        public static void InitContainer()
        {
            Builder = new ContainerBuilder();
            Container = Builder.Build();
        }
    }

此容器位于主(核心)库中。当应用程序启动时,它会从 global.asax 调用 InitContainer()。在此之后,我尝试使用 RegisterType() 方法从我的应用程序模块中注册一个新类型。

但在此之后我无法解析任何类型。它只是抛出此类型未注册的异常。

这段代码的主要思想是,我将能够仅使用一个共享容器从任何模块和 Web 应用程序中解析任何类型。

有人可以帮我解决这个问题吗?在多个库之间使用一个共享的 IoC 容器是否有更优雅的架构解决方案?

提前致谢!

4

2 回答 2

4

您的设计导致Service Locator 反模式。防止在核心库中定义容器并让每个人都引用它。使用依赖注入并在Composition Root中配置容器,即应用程序的启动路径(在您的情况下,组合根将成为 Web 应用程序的一部分)。

您可以利用Autofac 模块功能,并在组合根目录中注册此模块。

builder.RegisterModule(new CarTransportModule());

但是你也可以将你的模块注册类定义为静态的,这更简单:

MyApp.SomeModule.SomeModuleBootstrapper.Register(builder);
于 2012-05-24T11:07:37.937 回答
2

问题解决了——我们只需要在注册所有依赖项之后调用 container.Build() ......

于 2012-05-26T06:00:32.277 回答