【Net Core系列】(一)控制反转、依赖注入及使用Autofac IOC容器

7 篇文章 1 订阅

1.控制反转

(1)定义

控制:控制对象的创建、实例化;控制对象之间的依赖关系
反转:由于应用程序不是主动创建对象,而是被动地等待对象容器注入所需要的资源,因此称之为反转

(2)好处

松耦合

2.依赖注入

实现控制反转的一种方式

3.区别与联系

控制反转(Inversion of Control,缩写为IoC):

使用对象容器反过来控制应用程序所需要的外部资源的一种程序开发思想。
面向对象编程中的一种设计原则,是一种设计思想。

依赖注入(Dependency Injection,简称DI):

实现控制反转最常用的方式。
依赖注入是一种具体的实施方法,容器创建好实例后再注入调用者称为依赖注入。

4.Autofac使用例子

说明

该例子可实现自动加载程序集,在控制器中自动通过属性注册类、实现接口,达到依赖注入的效果

建立工程

环境

.Net 5

新建.Net 5工程,切换启动项
在这里插入图片描述

nuget依赖包

Autofac 6.4.6
Autofac.Extensions.DependencyInjection 8.0.0

在这里插入图片描述

Program.cs:引入Autofac创建服务工厂组件

using Autofac.Extensions.DependencyInjection;
using Microsoft.AspNetCore.Hosting;
using Microsoft.Extensions.Hosting;

namespace AutoContainerCore.Api
{
    public class Program
    {
        public static void Main(string[] args)
        {
            CreateHostBuilder(args).Build().Run();
        }

        public static IHostBuilder CreateHostBuilder(string[] args) =>
            Host.CreateDefaultBuilder(args)
                .UseServiceProviderFactory(new AutofacServiceProviderFactory())//引入Autofac创建服务工厂组件
                .ConfigureWebHostDefaults(webBuilder =>
                {
                    webBuilder.UseStartup<Startup>();
                });
    }
}

Startup.cs:添加一个ConfigureContainer方法

这个方法的作用加载名称为(工程名+.IBusiness)/(工程名+.Business)的程序集,并注册实现里面的接口;
所以接下来必须要再创建这样名称的两个工程

public void ConfigureContainer(ContainerBuilder builder)
        {

            var serviceName = AppDomain.CurrentDomain.FriendlyName.Replace(".Api", "").Replace(".API", "");

            Assembly[] assArr = new Assembly[]
            {
                Assembly.Load(new AssemblyName(serviceName+".IBusiness")),
                Assembly.Load(new AssemblyName(serviceName+".Business"))
            };

            foreach (var ass in assArr)
            {
                //找到Business结尾且为非抽象类
                var serviceTypes = ass.GetTypes()
                .Where(t => !t.GetTypeInfo().IsAbstract);

                foreach (var serviceType in serviceTypes)
                {
                    foreach (var interType in serviceType.GetInterfaces())
                    {
                        var sname = serviceType.Name;
                        var Iname = interType.Name;

                        builder.RegisterType(serviceType).As(interType)
                            .InstancePerDependency()//默认模式,每次调用,都会重新实例化对象;每次请求都创建一个新的对象;
                            .AsImplementedInterfaces()//自动以其实现的所有接口类型暴露(包括IDisposable接口);可以把一个类注册给它实现的全部接口
                            .InstancePerLifetimeScope()//同一个Lifetime生成的对象是同一个实例
                            .PropertiesAutowired();//支持属性注入的方法;
                    }
                }
                //控制器实例的注入 
                var sss = typeof(Startup).GetTypeInfo().Assembly.DefinedTypes;
                var controllerTypes = typeof(Startup).GetTypeInfo().Assembly.DefinedTypes.
                    Where(x => x.IsClass && typeof(ControllerBase).GetTypeInfo()
                    .IsAssignableFrom(x))//	返回一个值,该值指示是否可以将指定类型分配给当前类型
                    .Select(x => x.AsType())
                    .ToArray();
                builder.RegisterTypes(controllerTypes);
            }
        }

创建AutoContainerCore.IBusiness类库项目

编写一个接口

using System.Threading.Tasks;

namespace AutoContainerCore.IBusiness
{
    public interface IUserBusiness
    {
        Task<string> Debug();
    }
}

在这里插入图片描述

创建AutoContainerCore.Business类库项目

引入IBusiness接口

在这里插入图片描述

AutoContainerCore.Business项目新建业务类UserBusiness,并实现接口
using AutoContainerCore.IBusiness;
using System;
using System.Threading.Tasks;

namespace AutoContainerCore.Business
{
    public class UserBusiness : IUserBusiness
    {
        public async Task<string> Debug()
        {
            await Task.CompletedTask;
            return "test";
        }
    }
}

在这里插入图片描述

在AutoContainerCore.Api项目中引入

注意:必须两个项目都引入,否则会报错

AutoContainerCore.IBusiness
AutoContainerCore.Business
在这里插入图片描述

在AutoContainerCore.Api项目的controller中依赖注入,调用接口的方法

using AutoContainerCore.IBusiness;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Logging;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;

namespace AutoContainerCore.Api.Controllers
{
    [ApiController]
    [Route("[controller]")]
    public class WeatherForecastController : ControllerBase
    {
        /// <summary>
        /// 属性依赖
        /// </summary>
        public IUserBusiness _iUserBusiness { get; }
        private static readonly string[] Summaries = new[]
        {
            "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
        };

        private readonly ILogger<WeatherForecastController> _logger;

        /// <summary>
        /// 构造函数中的依赖注入
        /// </summary>
        /// <param name="logger"></param>
        /// <param name="userBusiness"></param>
        public WeatherForecastController(ILogger<WeatherForecastController> logger, IUserBusiness userBusiness)
        {
            _logger = logger;
            _iUserBusiness = userBusiness;
        }

        [HttpGet]
        public IEnumerable<WeatherForecast> Get()
        {
            var rng = new Random();
            return Enumerable.Range(1, 5).Select(index => new WeatherForecast
            {
                Date = DateTime.Now.AddDays(index),
                TemperatureC = rng.Next(-20, 55),
                Summary = Summaries[rng.Next(Summaries.Length)]
            })
            .ToArray();
        }
        /// <summary>
        /// 调用接口方法
        /// </summary>
        /// <returns></returns>
        [HttpPost("Debug")]
        public async Task<string> Debug()
        {
            var result = await _iUserBusiness.Debug();
            return result;
        }
    }
}


在这里插入图片描述

运行

swagger调用debug
看到返回值为test
在这里插入图片描述

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值