如何设置Autofac注册

时间:2014-02-27 17:46:58

标签: asp.net-mvc-5 autofac

我是依赖注入的新手,我决定使用autofac,因为它似乎拥有对MVC5最好的“开箱即用”支持(其他人可能会更好,但我是新手)

我正在创建简单的使用场景,并且在wiki中我在application_start中的global.asax中获得了以下代码

protected void Application_Start()
{
    var builder = new ContainerBuilder();
    builder.RegisterControllers(typeof(MvcApplication).Assembly);
    builder.RegisterType<ArtistController>().InstancePerHttpRequest();
    builder.RegisterType<ArtistService>().As<IArtistService>().SingleInstance();
    builder.RegisterType<ArtistRepository>().As<IArtistRepository>().SingleInstance();
    builder.RegisterType<BandMemberRepository>().As<IBandMemberRepository>).SingleInstance();
    var container = builder.Build();
    DependencyResolver.SetResolver(new AutofacDependencyResolver(container));



    AreaRegistration.RegisterAllAreas();
    FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
    RouteConfig.RegisterRoutes(RouteTable.Routes);
    BundleConfig.RegisterBundles(BundleTable.Bundles);
 }

在我的ArtistController我有这个

私人IArtistService _artistService;

然后我有一些检索和更新数据的代码,非常简单。这工作正常,我开始了解整个概念。

我的问题是,我是否必须手动注册我使用的所有具体类?我的应用程序最终会成长,我会有很多很多课程,所以这将是一个痛苦的管理。我碰到过这个

builder.RegisterSource(new AnyConcreteTypeNotAlreadyRegisteredSource());

据我所知,应该为我注册一切,但它没有用。我做错了吗?


好的,谢谢你的建议。

autofac网站显示了使用lambdas的示例,因此我将其添加到global.asax

builder.RegisterAssemblyTypes(typeof(MvcApplication).Assembly)
               .Where(t => t.Name.EndsWith("Repository"))
               .AsImplementedInterfaces();

builder.RegisterAssemblyTypes(typeof(MvcApplication).Assembly)
               .Where(t => t.Name.EndsWith("Service"))
               .AsImplementedInterfaces();

但是没有用,有什么想法吗?

1 个答案:

答案 0 :(得分:0)

我通过使用以下属性对其进行大多数(90%以上)注册:

[AttributeUsage(AttributeTargets.Class)]
[JetBrains.Annotations.MeansImplicitUse]
public class AutoRegisterAttribute : Attribute {}

然后我使用这个模块来注册这些类:

public class AutoRegisterModule : Module
{
    private readonly Assembly[] _assembliesToScan;

    public AutoRegisterModule(params Assembly[] assembliesToScan)
    {
        _assembliesToScan = assembliesToScan;
    }

    protected override void Load(ContainerBuilder builder)
    {
        builder.RegisterAssemblyTypes(_assembliesToScan)
            .Where(t => t.GetCustomAttribute<AutoRegisterAttribute>(false) != null)
            .AsSelf()
            .AsImplementedInterfaces()
            .InstancePerLifetimeScope();
    }

    public static AutoRegisterModule ForCallingAssembly()
    {
        return new AutoRegisterModule(Assembly.GetCallingAssembly());
    }
}

因此,当我构建容器时,我通常会这样做:

builder.RegisterModule(AutoRegisterModule.ForCallingAssembly());