隐藏

.Net Core 自动扫描注入之Scrutor批量依赖注入

发布:2022/3/29 15:45:48作者:管理员 来源:本站 浏览次数:1309

.NET Core中依赖注入已经是最常见的编程方式,所以基于约定进行自动依赖注入非常有必要,可以简化工作量和减少出错的概率,


目前进行自动扫描注入的工具为Scrutor,通过一个接口锚点进行自动扫描注入,如下述的IAutoInject,IScopedAutoInject   等接口就是锚点


分为2种注入方式:


1.接口实现类型的注入,如services.AddSingleton<IHttpContextAccessor, HttpContextAccessor>();


2.注入自身    services.AddScoped<RequestToHttpHelper>();


其中:


1.IAutoInject :默认以接口和实现的方式注入Scoped 例:services.AddScoped<ITest, TestImplment>();


2.IScopedAutoInject  :以接口和实现的方式注入Scoped(同上)例:services.AddScoped<ITest, TestImplment>();


3.ISingletonAutoInject:自动注入接口和实现Singleton类型 例:services.AddSingleton<ITest, TestImplment>();


4.ITransientAutoInject:自动注入接口和实现Transient类型  例:services.AddTransient<ITest, TestImplment>();


5.ISelfScopedAutoInject:自动注入自身Scoped类型  例:services.AddScoped<Test>();


6.ISelfSingletonAutoInject:自动注入自身Singleton类型 例:services.AddSingleton<Test>();


7.ISelfTransientAutoInject:自动注入自身Transient类型 例:services.AddTransient<Test>();


代码如下:



using Microsoft.Extensions.DependencyInjection;

using Scrutor;

using System.Reflection;

using System.Collections.Generic;

using System.Linq;

using Microsoft.AspNetCore.Http;


namespace NetCore3WebApiTemplate

{

   public static class RegisterService

   {

       public static void RegisterComponents(IServiceCollection services)

       {

           

           //自动注入IAutoInject

           services.Scan(x =>

           {

               var entryAssembly = Assembly.GetEntryAssembly();

               var referencedAssemblies = entryAssembly.GetReferencedAssemblies().Select(Assembly.Load);

               var assemblies = new List<Assembly> { entryAssembly }.Concat(referencedAssemblies);


               x.FromAssemblies(assemblies)

                   .AddClasses(classes => classes.AssignableTo(typeof(IAutoInject)))

                       .AsImplementedInterfaces()

                       .WithScopedLifetime()

                       //接口注册Scoped

                   .AddClasses(classes => classes.AssignableTo(typeof(IScopedAutoInject)))

                       .AsImplementedInterfaces()

                       .WithScopedLifetime()

                   //接口注册Singleton

                   .AddClasses(classes => classes.AssignableTo(typeof(ISingletonAutoInject)))

                         .AsImplementedInterfaces()

                         .WithSingletonLifetime()

                  //接口注册Transient

                   .AddClasses(classes => classes.AssignableTo(typeof(ITransientAutoInject)))

                         .AsImplementedInterfaces()

                         .WithTransientLifetime()

                   //具体类注册Scoped

                   .AddClasses(classes => classes.AssignableTo(typeof(ISelfScopedAutoInject)))

                         .AsSelf()

                         .WithScopedLifetime()

                   //具体类注册Singleton

                   .AddClasses(classes => classes.AssignableTo(typeof(ISelfSingletonAutoInject)))

                         .AsSelf()

                         .WithSingletonLifetime()

                   //具体类注册Transient

                   .AddClasses(classes => classes.AssignableTo(typeof(ISelfTransientAutoInject)))

                         .AsSelf()

                         .WithTransientLifetime();

           });

       }

   }

}




using System;

using System.Collections.Generic;

using System.Text;


namespace NetCore3WebApiTemplate

{

   /// <summary>

   /// 自动注入扫描点默认为Scoped

   /// </summary>

   public interface IAutoInject

   {

   }


   /// <summary>

   ///  自动注入接口和实现Scoped类型

   /// </summary>

   public interface IScopedAutoInject

   {


   }


   /// <summary>

   /// 自动注入接口和实现Singleton类型

   /// </summary>

   public interface ISingletonAutoInject

   {


   }


   /// <summary>

   /// 自动注入接口和实现Transient类型

   /// </summary>

   public interface ITransientAutoInject

   {


   }


   /// <summary>

   /// 自动注入自身Scoped类型

   /// </summary>

   public interface ISelfScopedAutoInject

   {


   }


   /// <summary>

   /// 自动注入自身Singleton类型

   /// </summary>

   public interface ISelfSingletonAutoInject

   {


   }


   /// <summary>

   /// 自动注入自身Transient类型

   /// </summary>

   public interface ISelfTransientAutoInject

   {


   }

}




使用方式如下:



public class TestImplment:ITest,IAutoInject

{

   

}





public class CompanyController : ControllerBase

  {

      private readonly ITest test;


      public CompanyController(ITest test)

      {

          this.test= test;

      }

  }




在startup的ConfigureServices的方法追加RegisterService.RegisterComponents(services);即可,代码如下



/// <summary>

       /// This method gets called by the runtime. Use this method to add services to the container.

       /// </summary>

       /// <param name="services"></param>

       public void ConfigureServices(IServiceCollection services)

       {

          //注册服务

           RegisterService.RegisterComponents(services);

      }




注意:RegisterService所在项目需要引用需要扫描的注入接口和类,不然无法扫描到。