ASP.NET Core MVC 之依赖注入 Controller

  ASP.NET Core MVC 控制器应通过构造函数明确地请求它们地依赖关系,在某些情况下,单个控制器地操作可能需要一个服务,在控制器级别上的请求可能没有意义。在这种情况下,也可以将服务作为  Action 的参数。

  依赖注入是一种如 Dependency Inversion Principle 所示的技术,允许应用程序松散耦合的模块组成。

1.构造函数注入

  ASP.NET Core 内置的基于构造函数的依赖注入支持扩展到 MVC 控制器。通过只添加一个服务类型作为构造函数参数到控制器中,ASP.NET Core 将会尝试使用内置服务容器解析这个类型。服务通常(但不总是)使用接口定义。例如,如果应用程序定义一个检索时间的服务,然后依赖注入而不是硬编码:

  定义接口和实现:

namespace MVCTest.Services
{
    public interface IDateTime
    {
        DateTime Now { get; }
    }
    public class SystemDateTime: IDateTime
    {
        public DateTime Now
        {
            get { return DateTime.Now; }
        }
    }
}

  在 ConfigureServices 中注册服务到容器:

services.AddTransient<IDateTime, SystemDateTime>();

  在控制其中使用:

    public class DateTimeController : Controller
    {
        private IDateTime _dateTime;
        public DateTimeController(IDateTime dateTime)
        {
            _dateTime = dateTime;
        }
        // GET: DateTime
        public ActionResult Index()
        {
            var serverTime = _dateTime.Now;
            if (serverTime.Hour < 12)
            {
                ViewData["Message"] = "Good Morning";
            }
            return View();
        }
}

  ASP.NET Core 内置的依赖注入支持用于请求服务的类型只能有一个构造函数,如果多于一个会报异常。使用第三方实现替换默认依赖注入,可以实现支持多个构造函数。

2.使用 FromServices 操作注入

  有时,不需要在控制器为多个操作提供服务。在这种情况下,将服务注入到操作方法的参数是有意义的。通过 [FromServices] 标记参数来实现:

        public ActionResult Index([FromServices] IDateTime _dateTime)
        {
            var serverTime = _dateTime.Now;
            if (serverTime.Hour < 12)
            {
                ViewData["Message"] = "Good Morning";
            }
            return View();
        }

3.在控制器中访问设置

  在控制器中访问应用程序设置或者配置设置时常见的模式。此访问应当使用在 Configuration 中描述的访问模式。通常不应从控制器中使用依赖注入直接请求设置,更好的方式是请求 IOptions<T> 实例,T是你需要的配置类型。例如:

  创建选项类:

public class AppSettingOptions
    {
        public DefaultConnec ConnectionStrings { get; set; }
        public string AllowedHosts { get; set; }
    }

    public class DefaultConnec
    {
        public string DefaultConnection { get; set; }
    }

appsettings.json:

{
  "ConnectionStrings": {
    "DefaultConnection": "Data Source=.;Initial Catalog=Test;Integrated Security=True"
  },
  "Logging": {
    "LogLevel": {
      "Default": "Information"
    }
  },
  "AllowedHosts": "*"
}

  配置应用程序使用选项模型,在 ConfigureServices 中添加配置类到服务容器:

public Startup(IConfiguration configuration,IHostingEnvironment env)
        {
            //Configuration = configuration;
            var builder = new ConfigurationBuilder()
                .SetBasePath(Directory.GetCurrentDirectory())
                .AddJsonFile("appsettings.json",optional:true,reloadOnChange:true)
                //.AddJsonFile($"appsettings.{env.EnvironmentName}.json",optional:true)
                ;

            //配置环境变量
            //builder.AddEnvironmentVariables();
            Configuration = builder.Build();
        }

        public IConfiguration Configuration { get; }

        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {
            services.AddOptions();
            services.Configure<AppSettingOptions>(Configuration);
            //通过代码编写
            services.Configure<AppSettingOptions>(options=>
            {
                options.AllowedHosts = "test";
            });
        }

  示例是从 appsettings.json 读取设置,也可以在代码中添加设置。

  一旦指定了请类型的配置对象 AppSettingOptions,并将其添加到服务容器,就可以在控制器或操作方法通过请求 IOptions<AppSettingOptions>  的实例获取它:

    public class HomeController : Controller
    {
        private readonly IOptions<AppSettingOptions> _options;
        public HomeController(IOptions<AppSettingOptions> options)
        {
            _options = options;
        }
}

  遵循选项模式允许将设置和配置彼此分离,并且确保控制器遵循关注点分离,因为不需要知道如何在哪里找到设置信息。由于控制器类中没有静态附着或者直接实例化设置类,因此使得控制器更容易使用单元测试。

 

原文地址:https://www.cnblogs.com/afei-24/p/11367425.html

时间: 2024-08-01 05:52:17

ASP.NET Core MVC 之依赖注入 Controller的相关文章

ASP.NET Core中的依赖注入(2):依赖注入(DI)

参考页面: http://www.yuanjiaocheng.net/ASPNET-CORE/project-layout.html http://www.yuanjiaocheng.net/ASPNET-CORE/projectjson.html http://www.yuanjiaocheng.net/ASPNET-CORE/core-configuration.html http://www.yuanjiaocheng.net/ASPNET-CORE/core-middleware.htm

ASP.NET Core中的依赖注入(5): ServiceProvider实现揭秘 【解读ServiceCallSite 】

通过上一篇的介绍我们应该对实现在ServiceProvider的总体设计有了一个大致的了解,但是我们刻意回避一个重要的话题,即服务实例最终究竟是采用何种方式提供出来的.ServiceProvider最终采用何种方式提供我们所需的服务实例取决于最终选择了怎样的ServiceCallSite,而服务注册是采用的ServiceDescriptor有决定了ServiceCallSite类型的选择.我们将众多不同类型的ServiceCallSite大体分成两组,一组用来创建最终的服务实例,另一类则与生命周

ASP.NET Core中的依赖注入(5):ServicePrvider实现揭秘【补充漏掉的细节】

到目前为止,我们定义的ServiceProvider已经实现了基本的服务提供和回收功能,但是依然漏掉了一些必需的细节特性.这些特性包括如何针对IServiceProvider接口提供一个ServiceProvider对象,何创建ServiceScope,以及如何提供一个服务实例的集合. 一.提供一个ServiceProvider对象 我们知道当将服务类型指定为IServiceProvider接口并调用ServiceProvider的GetService方法是,ServiceProvider对象本

ASP.NET Core中的依赖注入(5): ServiceProvider实现揭秘 【总体设计 】

本系列前面的文章我们主要以编程的角度对ASP.NET Core的依赖注入系统进行了详细的介绍,如果读者朋友们对这些内容具有深刻的理解,我相信你们已经可以正确是使用这些与依赖注入相关的API了.如果你还对这个依赖注入系统底层的实现原理具有好奇心,可以继续阅读这一节的内容. 目录一.ServiceCallSite 二.Service 三.ServiceEntry 四.ServiceTable 五.ServiceProvider 作为DI容器的体现,ServiceProvider是ASP.NET Co

ASP.NET Core MVC 之控制器(Controller)

操作(action)和操作结果(action result)是 ASP.NET MVC 构建应用程序的一个基础部分. 在 ASP.NET MVC 中,控制器用于定义和聚合一组操作.操作是控制器中处理传入请求的一种方法.控制器提供了一种逻辑方式,将相似的操作组织起来,允许一些通用的规则(例如路由,缓存,授权)使用共同的应用.传入的请求通过 路由 映射到操作. ASP.NET Core MVC 中,控制器可以是任何以 “Controller” 结尾或继承自以 “Controller” 结尾的可实例化

ASP.NET Core中的依赖注入(1):控制反转(IoC)

ASP.NET Core在启动以及后续针对每个请求的处理过程中的各个环节都需要相应的组件提供相应的服务,为了方便对这些组件进行定制,ASP.NET通过定义接口的方式对它们进行了"标准化",我们将这些标准化的组件称为服务,ASP.NET在内部专门维护了一个DI容器来提供所需的服务.要了解这个DI容器以及现实其中的服务提供机制,我们先得知道什么是DI(Dependence Injection),而一旦我们提到DI,又不得不说IoC(Inverse of Control). 目录 一.流程控

ASP.NET Core 中的依赖注入 [共7篇]

一.控制反转(IoC) ASP.NET Core在启动以及后续针对每个请求的处理过程中的各个环节都需要相应的组件提供相应的服务,为了方便对这些组件进行定制,ASP.NET通过定义接口的方式对它们进行了“标准化”,我们将这些标准化的组件称为服务,ASP.NET在内部专门维护了一个DI容器来提供所需的服务.要了解这个DI容器以及现实其中的服务提供机制,我们先得知道什么是DI(Dependence Injection),而一旦我们提到DI,又不得不说IoC(Inverse of Control)… [

asp.net core 系列 3 依赖注入

一. 依赖注入概述 在软件设计的通用原则中,SOLID是非常流行的缩略语,它由5个设计原则的首字母构成:单一原则(S).开放封闭原则(O).里氏替换原则(L).接口分离原则(I).依赖反转原则(D).本篇介绍依赖反转原则以及在ASP.NET Core中的实现. 直接依赖是指:当一个类需要另一个类协作来完成工作的时候就产生了依赖.举例比如:模块 A 调用模块 B 中的函数,而模块 B 又调用模块 C 中的函数,则编译时 A 取决于 B,而 B 又取决于 C.这是有严重的依赖关系,不属于松散耦合.

ASP.NET CORE MVC 2.0 项目中引用第三方DLL报错的解决办法 - InvalidOperationException: Cannot find compilation library location for package

目前在学习ASP.NET CORE MVC中,今天看到微软在ASP.NET CORE MVC 2.0中又恢复了允许开发人员引用第三方DLL程序集的功能,感到甚是高兴!于是我急忙写了个Demo想试试,我的项目结构如下: 可以看到解决方案中就两个项目,AspNetCoreWebApp就是一个ASP.NET CORE MVC 2.0的项目,而MyNetCoreLib是一个.Net Core 2.0的类库项目,为了体现AspNetCoreWebApp是通过程序集来引用MyNetCoreLib的,我还在解