.Net Core3.0 WebApi 四:JWT权限验证 .Net Core3.0 WebApi 目录 什么是JWT 校验逻辑 授权过程 生成Token令牌 获取Token Swagger中开启JWT服务 JWT授权认证 API接口授权策略 解析Token 常见疑惑解析

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

.Net Core3.0 WebApi 目录

什么是JWT

之前也写过一篇,介绍JWT和oAuthor2的随笔。可以参考这篇。

设计安全的API-JWT与OAuthor2     、    OAuth2、OpenID Connect简介

这里还是简单介绍一下吧。

根据维基百科定义,JWT(读作 [/dʒɒt/]),即JSON Web Tokens,是一种基于JSON的、用于在网络上声明某种主张的令牌(token)。JWT通常由三部分组成: 头信息(header), 消息体(payload)和签名(signature)。它是一种用于双方之间传递安全信息的表述性声明规范。JWT作为一个开放的标准(RFC 7519),定义了一种简洁的、自包含的方法,从而使通信双方实现以JSON对象的形式安全的传递信息。

以上是JWT的官方解释,可以看出JWT并不是一种只能权限验证的工具,而是一种标准化的数据传输规范。所以,只要是在系统之间需要传输简短但却需要一定安全等级的数据时,都可以使用JWT规范来传输。规范是不因平台而受限制的,这也是JWT做为授权验证可以跨平台的原因。

如果理解还是有困难的话,我们可以拿JWT和JSON类比:

JSON是一种轻量级的数据交换格式,是一种数据层次结构规范。它并不是只用来给接口传递数据的工具,只要有层级结构的数据都可以使用JSON来存储和表示。当然,JSON也是跨平台的,不管是Win还是Linux,.NET还是Java,都可以使用它作为数据传输形式。

校验逻辑

1)客户端向授权服务系统发起请求,申请获取“令牌”。

2)授权服务根据用户身份,生成一张专属“令牌”,并将该“令牌”以JWT规范返回给客户端

3)客户端将获取到的“令牌”放到http请求的headers中后,向主服务系统发起请求。主服务系统收到请求后会从headers中获取“令牌”,并从“令牌”中解析出该用户的身份权限,然后做出相应的处理(同意或拒绝返回资源)

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

授权过程

首先我们需要一个具有一定规则的 Token 令牌,也就是 JWT 令牌(比如我们的公司门禁卡),//登录

然后呢,我们再定义哪些地方需要什么样的角色(比如领导办公室我们是没办法进去的),//授权机制

接下来,整个公司需要定一个规则,就是如何对这个 Token 进行验证,不能随便写个字条,这样容易被造假(比如我们公司门上的每一道刷卡机),//认证方案

最后,就是安全部门,开启认证中间件服务(那这个服务可以关闭的,比如我们电影里看到的黑客会把这个服务给关掉,这样整个公司安保就形同虚设了)。//开启中间件

生成Token令牌

我们需要在appsettings.json中配置jwt参数的值 【注意】 SecretKey必须大于16个,是大于,不是大于等于

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
{
  "Logging": {
    "LogLevel": {
      "Default": "Information",
      "Microsoft": "Warning",
      "Microsoft.Hosting.Lifetime": "Information"
    }
  },
  "AllowedHosts": "*",
  "ConnectionStrings": {
    "ConnectionString": "Data Source=127.0.0.1;Initial Catalog=db;User ID=uid;Password=123456;Pooling=True;Max Pool Size=512;Connect Timeout=500;",
    "JwtSetting": {
      "Issuer": "jwtIssuer", //颁发者
      "Audience": "jwtAudience", //可以给哪些客户端使用
      "SecretKey": "chuangqianmingyueguang" //加密的Key
    }
  }
}
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

在api层,Nuget添加包IdentityModel,Microsoft.AspNetCore.Authentication.JwtBearer,Microsoft.AspNetCore.Authorization

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

 webapi.core.models类库新建TokenModel类

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
/// <summary>
/// 令牌
/// </summary>
public class TokenModel
{
    /// <summary>
    /// Id
    /// </summary>
    public string Uid { get; set; }
    /// <summary>
    /// 角色
    /// </summary>
    public string Role { get; set; }

}
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

WebApi.Core.Infrastructure项目Helper文件夹,新建JwtHelper.cs

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
public class JwtHelper
{
    /// <summary>
    /// 颁发JWT字符串
    /// </summary>
    /// <param name="tokenModel"></param>
    /// <returns></returns>
    public static string IssueJwt(TokenModel tokenModel)
    {
        string iss = ConfigHelper.GetSectionValue("ConnectionStrings:JwtSetting:Issuer");
        string aud = ConfigHelper.GetSectionValue("ConnectionStrings:JwtSetting:Audience");
        string secret = ConfigHelper.GetSectionValue("ConnectionStrings:JwtSetting:SecretKey");
        //var claims = new Claim[] //old
        var claims = new List<Claim>
            {
             /*
             * 特别重要:
               1、这里将用户的部分信息,比如 uid 存到了Claim 中,如果你想知道如何在其他地方将这个 uid从 Token 中取出来,请看下边的SerializeJwt() 方法
               2、你也可以研究下 HttpContext.User.Claims ,具体的你可以看看 Policys/PermissionHandler.cs 类中是如何使用的。
             */

            new Claim(JwtRegisteredClaimNames.Jti, tokenModel.Uid.ToString()),
            new Claim(JwtRegisteredClaimNames.Iat, $"{new DateTimeOffset(DateTime.Now).ToUnixTimeSeconds()}"),
            new Claim(JwtRegisteredClaimNames.Nbf,$"{new DateTimeOffset(DateTime.Now).ToUnixTimeSeconds()}") ,
            //这个就是过期时间,目前是过期1000秒,可自定义,注意JWT有自己的缓冲过期时间
            new Claim (JwtRegisteredClaimNames.Exp,$"{new DateTimeOffset(DateTime.Now.AddSeconds(1000)).ToUnixTimeSeconds()}"),
            new Claim(ClaimTypes.Expiration, DateTime.Now.AddSeconds(1000).ToString()),
            new Claim(JwtRegisteredClaimNames.Iss,iss),
            new Claim(JwtRegisteredClaimNames.Aud,aud),


           };

        // 可以将一个用户的多个角色全部赋予;
        claims.AddRange(tokenModel.Role.Split(',').Select(s => new Claim(ClaimTypes.Role, s)));



        //秘钥 (SymmetricSecurityKey 对安全性的要求,密钥的长度太短会报出异常)
        var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(secret));
        var creds = new SigningCredentials(key, SecurityAlgorithms.HmacSha256);

        var jwt = new JwtSecurityToken(
            issuer: iss,
            claims: claims,
            signingCredentials: creds);

        var jwtHandler = new JwtSecurityTokenHandler();
        var encodedJwt = jwtHandler.WriteToken(jwt);

        return encodedJwt;
    }

    /// <summary>
    /// 解析
    /// </summary>
    /// <param name="jwtStr"></param>
    /// <returns></returns>
    public static TokenModel SerializeJwt(string jwtStr)
    {
        var jwtHandler = new JwtSecurityTokenHandler();
        JwtSecurityToken jwtToken = jwtHandler.ReadJwtToken(jwtStr);
        object role;
        try
        {
            jwtToken.Payload.TryGetValue(ClaimTypes.Role, out role);
        }
        catch (Exception e)
        {
            Console.WriteLine(e);
            throw;
        }
        var tm = new TokenModel
        {
            Uid = jwtToken.Id.ToString(),
            Role = role != null ? role.ToString() : "",
        };
        return tm;
    }
}
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

获取Token

UserController新建Login接口,用来获取token

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
/// <summary>
/// 登录
/// </summary>
/// <param name="role">用户</param>
/// <returns></returns>  
[HttpGet]
public IActionResult Login(string role)
{
    string jwtStr = string.Empty;
    bool suc = false;

    if (role != null)
    {
        // 将用户id和角色名,作为单独的自定义变量封装进 token 字符串中。
        TokenModel tokenModel = new TokenModel { Uid = "abcde", Role = role };
        jwtStr = JwtHelper.IssueJwt(tokenModel);//登录,获取到一定规则的 Token 令牌
        suc = true;
    }
    else
    {
        jwtStr = "login fail!!!";
    }

    return Ok(new
    {
        success = suc,
        token = jwtStr
    });
}
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

运行项目,使用swagger 调试login接口

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

 可以看到成功的获取了Token

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

Swagger中开启JWT服务

我们要测试 JWT 授权认证,就必定要输入 Token令牌,那怎么输入呢,平时的话,我们可以使用 Postman 来控制输入,就是在请求的时候,在 Header 中,添加Authorization属性,

但是我们现在使用了 Swagger 作为接口文档,那怎么输入呢,别着急, Swagger 已经帮我们实现了这个录入 Token令牌的功能。

在SwaggerSetUp.cs的AddSwaggerSetup方法的AddSwaggerGen服务中,增加以下代码:

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
 public static class SwaggerSetUp
 {
     public static void AddSwaggerSetup(this IServiceCollection services)
     {

         if (services == null) throw new ArgumentNullException(nameof(services));

         var ApiName = "Webapi.Core";

         services.AddSwaggerGen(c =>
         {
             c.SwaggerDoc("V1", new OpenApiInfo
             {
                 // {ApiName} 定义成全局变量,方便修改
                 Version = "V1",
                 Title = $"{ApiName} 接口文档——Netcore 3.0",
                 Description = $"{ApiName} HTTP API V1",

             });
             c.OrderActionsBy(o => o.RelativePath);

             // 获取xml注释文件的目录
             var xmlPath = Path.Combine(AppContext.BaseDirectory, "Webapi.Core.xml");
             c.IncludeXmlComments(xmlPath, true);//默认的第二个参数是false,这个是controller的注释,记得修改

             var xmlModelPath = Path.Combine(AppContext.BaseDirectory, "Webapi.Core.Model.xml");//这个就是Model层的xml文件名
             c.IncludeXmlComments(xmlModelPath);

             // 在header中添加token,传递到后台
             c.OperationFilter<SecurityRequirementsOperationFilter>();

             #region Token绑定到ConfigureServices
             c.AddSecurityDefinition("oauth2", new OpenApiSecurityScheme
             {
                 Description = "JWT授权(数据将在请求头中进行传输) 直接在下框中输入Bearer {token}(注意两者之间是一个空格)"",
                 Name = "Authorization",//jwt默认的参数名称
                 In = ParameterLocation.Header,//jwt默认存放Authorization信息的位置(请求头中)
                 Type = SecuritySchemeType.ApiKey
             });
             #endregion

         });

     }
 }
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

运行项目,就可以看到这个Token的入口了:

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

 .Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

JWT授权认证

Setup文件夹新建AuthorizationSetup.cs,新建注册服务方法

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
namespace WebApi.Core.Api.SetUp
{
    public static class AuthorizationSetup
    {
        public static void AddAuthorizationSetup(this IServiceCollection services)
        {
            if (services == null) throw new ArgumentNullException(nameof(services));

            // 1【授权】、这个和上边的异曲同工,好处就是不用在controller中,写多个 roles 。
            // 然后这么写 [Authorize(Policy = "Admin")]
            services.AddAuthorization(options =>
            {
                options.AddPolicy("User", policy => policy.RequireRole("User").Build());
                options.AddPolicy("SystemOrAdmin", policy => policy.RequireRole("Admin", "System"));

            });

            //读取配置文件
            var symmetricKeyAsBase64 = ConfigHelper.GetSectionValue("ConnectionStrings:JwtSetting:SecretKey");
            var keyByteArray = Encoding.ASCII.GetBytes(symmetricKeyAsBase64);
            var signingKey = new SymmetricSecurityKey(keyByteArray);
            var Issuer = ConfigHelper.GetSectionValue("ConnectionStrings:JwtSetting:Issuer");
            var Audience = ConfigHelper.GetSectionValue("ConnectionStrings:JwtSetting:Audience");



            // 令牌验证参数
            var tokenValidationParameters = new TokenValidationParameters
            {
                ValidateIssuerSigningKey = true,
                IssuerSigningKey = signingKey,
                ValidateIssuer = true,
                ValidIssuer = Issuer,//发行人
                ValidateAudience = true,
                ValidAudience = Audience,//订阅人
                ValidateLifetime = true,
                ClockSkew = TimeSpan.FromSeconds(30),
                RequireExpirationTime = true,
            };

            //2.1【认证】、core自带官方JWT认证
            // 开启Bearer认证
            services.AddAuthentication(o =>
            {
                o.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
                o.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;

            })
             // 添加JwtBearer服务
             .AddJwtBearer(o =>
             {
                 o.TokenValidationParameters = tokenValidationParameters;
                 o.Events = new JwtBearerEvents
                 {
                     OnAuthenticationFailed = context =>
                     {
                         // 如果过期,则把<是否过期>添加到,返回头信息中
                         if (context.Exception.GetType() == typeof(SecurityTokenExpiredException))
                         {
                             context.Response.Headers.Add("Token-Expired", "true");
                         }
                         return Task.CompletedTask;
                     }
                 };
             });
        }
    }
}
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

startup.cs的ConfigureServices方法添加验证服务

//jwt授权验证
services.AddAuthorizationSetup();

Configure方法添加如下代码:

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
    if (env.IsDevelopment())
    {
        app.UseDeveloperExceptionPage();
    }

    app.UseSwagger();
    app.UseSwaggerUI(c =>
    {
        c.SwaggerEndpoint($"/swagger/V1/swagger.json", "WebApi.Core V1");

        //路径配置,设置为空,表示直接在根域名(localhost:8001)访问该文件,注意localhost:8001/swagger是访问不到的,去launchSettings.json把launchUrl去掉,如果你想换一个路径,直接写名字即可,比如直接写c.RoutePrefix = "doc";
        c.RoutePrefix = "";
    });

    app.UseRouting();

    app.UseAuthentication();

    app.UseAuthorization();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapControllers();
        //endpoints.MapControllerRoute(
        //    name: "default",
        //    pattern: "{controller=Home}/{action=Index}/{id?}"
        //    );
    });
}
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

API接口授权策略

这里可以直接在api接口上,直接设置该接口所对应的角色权限信息:

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
 /// <summary>
 /// 需要Admin权限
 /// </summary>
 /// <returns></returns>
 [HttpGet]
 [Authorize(Roles = "Admin")]
 public IActionResult Admin()
 {
     return Ok("hello admin");
 }


 /// <summary>
 /// 需要System权限
 /// </summary>
 /// <returns></returns>
 [HttpGet]
 [Authorize(Roles = "System")]
 public IActionResult System()
 {
     return Ok("hello System");
 }
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

运行项目,获取一个Admin权限的token,并放到swagger 的权限验证按钮里面

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

 .Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

 请求admin方法,可以访问

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

 请求system方法,访问失败,权限不足

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

 但是如果我们的接口需要对应多个角色的时候,我们就可以直接写多个:

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
/// <summary>
/// 需要System和Admin权限
/// </summary>
/// <returns></returns>
[HttpGet]
[Authorize(Policy = "SystemOrAdmin")]

public IActionResult SystemAndAdmin()
{
    return Ok("hello SystemOrAdmin");
}
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

 这里有一个情况,如果角色多的话,不仅不利于我们阅读,还可能在配置的时候少一两个role,比如这个 api接口1 少了一个 system 的角色,再比如那个 api接口2 把 Admin 角色写成了 Adnin 这种不必要的错误,那怎么办呢,欸!这个时候就出现了基于策略的授权机制:

我们在 AuthorizationSetup 中可以这么设置:

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

 这样的话,我们只需要在 controller 或者 action 上,直接写策略名就可以了:

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
/// <summary>
/// 需要System和Admin权限
/// </summary>
/// <returns></returns>
[HttpGet]
[Authorize(Policy = "SystemOrAdmin")]

public IActionResult SystemAndAdmin()
{
    return Ok("hello SystemOrAdmin");
}
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

运行项目,分别请求system和admin的token,发现都可以访问这个请求

解析Token

添加一个接口用来解析token:

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析
/// <summary>
/// 解析Token
/// </summary>
/// <returns></returns>
[HttpGet]
[Authorize]
public IActionResult ParseToken()
{
    //需要截取Bearer 
    var tokenHeader = HttpContext.Request.Headers["Authorization"].ToString().Replace("Bearer ", "");
    var user = JwtHelper.SerializeJwt(tokenHeader);
    return Ok(user);

}
.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

运行项目,生成一个Token,然后调用解析方法,可以看到程序解析了我们的Token

.Net Core3.0 WebApi 四:JWT权限验证
.Net Core3.0 WebApi 目录
什么是JWT
校验逻辑
授权过程
生成Token令牌
获取Token
Swagger中开启JWT服务
JWT授权认证
API接口授权策略
解析Token
常见疑惑解析

常见疑惑解析

1、JWT里会存在一些用户的信息,比如用户id、角色role 等等,这样会不会不安全,信息被泄露?

答:JWT 本来就是一种无状态的登录授权认证,用来替代每次请求都需要输入用户名+密码的尴尬情况,存在一些不重要的明文很正常,只要不把隐私放出去就行,就算是被动机不良的人得到,也做不了什么事情。

2、生成 JWT 的时候需要 secret ,但是 解密的时候 为啥没有用到 secret ?

答:secret的作用,主要是用来防止 token 被伪造和篡改的,想想上边的那个第一个问题,用户得到了你的令牌,获取到了你的个人信息,这个是没事儿的,他什么也干不了,但是如果用户自己随便的生成一个 token ,带上你的uid,岂不是随便就可以访问资源服务器了,所以这个时候就需要一个 secret 来生成 token,这样的话,就能保证数字签名的正确性。