EFCore使用中间件进行登录认证

发布时间 2023-08-16 21:31:28作者: 如果生活可以ctrl+z

如何实现中间件(Middleware)用户登录验证

中间件(Middleware)是ASP.NET Core中的一个重要特性。所谓中间件就是嵌入到应用管道中用于处理请求和响应的一段代码。它又被称为管道模型。

中间件的执行顺序是:内置中间件优先-其次自定义中间件

1.首先我们需要创建WebApi

IMG_256

这是小编的API,然后找到Program.cs

IMG_257

//输入:
app.UseMiddleware(typeof(MyMiddleware));

typeof后的命名无需和上图一致自己定义 使用 typeof 关键字可以获取到一个类型的对象,而不是实例化该类型的对象 这样可以将中间件类型作为参数传递给 app.UseMiddleware() 方法,让 ASP.NET Core 框架能够在请求管道中创建和使用该中间件的实例。 这句话的意思是使用中间件,UseMiddleware方法用于将中间件添加到应用程序的请求处理管道中;

2.创建自定义中间件

复制typeof后的名称进行自定义中间件的创建:

右键WebApi后添加一个clss(类)

之后继承 IMiddleware:它是一个中间件库接口,继承后可以使用中间件内置的方法

IMG_258

然后我们实现接口

之后我们会得到一个构造函数

   public class MyMiddleware : IMiddleware
  {  
       public Task InvokeAsync(HttpContext context, RequestDelegate next)
      {      
             throw new NotImplementedException();
      }
  }

3.配置中间件

这个构造函数有两个返回值一个是next(context)传递,一个是Task.CompletedTask终止传递;

然后我们先获取请求我的购物车查询接口

   public class MyMiddleware : IMiddleware
  {  
       public Task InvokeAsync(HttpContext context, RequestDelegate next)
      {      
            var path=context.Request.Path.Value.ToLower();
      }
  }

现在path中就获取到了我们每个请求的方法接口,然后我们进行判断 根据自己业务需求,判断接口,我这里判断的是请求我的购物车查询接口时,判断有无令牌

   public class MyMiddleware : IMiddleware
  {
       private readonly IBaseRepository<UserModel> user;

       public MyMiddleware(IBaseRepository<UserModel> user)
      {
           this.user = user;
      }
       //判断当前信息要不要传递给API
       //判断前要先找出我们业务需要的数据
       //例如: 请求我的购物车查询接口时,如果用户没有登录,
       //那么API即使查询也是无数据的,所以是不需要让API执行查询操作的
       //获取当前请求的接口名称,判断如果请求的是我的购物车接口,就需要获取登录的用户信息,没有登录就不再把请求传递给API
       public Task InvokeAsync(HttpContext context, RequestDelegate next)
      {      
           //获取到请求的方法接口
           var path=context.Request.Path.Value.ToLower();

           //判断是否是业务需要的方法接口
           if (path== "/api/Shop/GetMyShop".ToLower())
          {
               //如果是获取Vue传递过来的请求中是否有token
               var token = context.Request.Headers["token"].ToString();

               //若token为空直接取消执行
               if (token=="")
              {
                   return Task.CompletedTask;
              }

               //若有则和数据库进行对比,查看数据库中是否有此token
               var list = user.GetAll().FirstOrDefault(x => x.Token == token);

               //若找到了
               if (list!=null)
              {
                   //允许执行
                   return next(context);
              }

               //否则直接取消执行
               return Task.CompletedTask;
          }

           //若不是需要的接口方法,则允许执行
          return next(context);
      }
  }

4.前台传递请求时需带上headers,并将token在headers中传递至服务端

Vue传值:

GetMyShop() {
    //前台传值方式:
    this.axios
      .get("http://localhost:5233/api/Shop/GetMyShop", {
        params: {
          User_Id: sessionStorage.getItem("uid"),
        },
        headers: {
          token: sessionStorage.getItem("token"),
        },
      })
      .then((res) => {
        this.tableData = res.data;
      });
  },