.Net Core 项目使用JWT鉴权实现身份验证功能(一)

354 阅读3分钟

一共分为四个步骤:

在开始之前先引入一个Nuget包 : (Microsoft.AspNetCore.Authentication.JwtBearer)

第一步 : 先在appsettings.json配置文件中书写 jwt 权限的配置信息

"JwtConfig": {  //内容随便写都行
    "Issuer": "www.adsfsadfasdf", //授予人
    "Audience": "www.adsfsadfasdf", //接收人
    "SecretKey": "nadjhfgkadshgoihfkajhkjdhsfaidkuahfhdksjaghidshyaukfhdjks" //密钥
}

第二步 : 注册jwt身份验证服务

.net6以下的项目在Staup文件中书写

.net6以上的项目在Program文件中书写

下面以我的.net6项目为例: 先在Program文件的 var builder = WebApplication.CreateBuilder(args); 这一行代码下 书写 以下代码

//注册jwt身份验证服务
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
    .AddJwtBearer(options =>
    {
        options.TokenValidationParameters = new TokenValidationParameters()
        {
            //验证发布者
            ValidateIssuer = true,
            ValidIssuer = builder.Configuration\["JwtConfig:Issuer"],
            //验证接收者
            ValidateAudience = true,
            ValidAudience = builder.Configuration\["JwtConfig:Audience"],
            //验证是否过期
            ValidateLifetime = true,
            //验证私钥
            IssuerSigningKey = new SymmetricSecurityKey(
            Encoding.UTF8.GetBytes(builder.Configuration\["JwtConfig:SecretKey"]))
        };
    });

在 var app = builder.Build(); 这一行代码下面书写读取appsettings.json文件配置信息数据

JwtUtil.Issuer = app.Configuration\["JwtConfig:Issuer"];
JwtUtil.Audience = app.Configuration\["JwtConfig:Audience"];
JwtUtil.SecretKey = app.Configuration\["JwtConfig:SecretKey"];

在 app.UseAuthorization(); 这一行代码上面 写以下代码来启动身份验证

//启用身份验证
app.UseAuthentication();

第三步 : 书写JWT身份验证辅助类 JwtUtil类

using Microsoft.IdentityModel.Tokens;
using NPOI.SS.Formula.Functions;
using System.IdentityModel.Tokens.Jwt;
using System.Security.Claims;
using System.Text;
namespace ReadJson\_.Net6.\_0.Utils
{
    /// <summary>
    /// JWT身份验证辅助类
    /// </summary>
    public class JwtUtil
    {
        /// <summary>
        /// 颁发机构
        /// </summary>
        /// <value></value>
        public static string Issuer { get; set; }
        /// <summary>
        /// 授予人
        /// </summary>
        /// <value></value>
        public static string Audience { get; set; }
        /// <summary>
        /// 密钥
        /// </summary>
        /// <value></value>
        public static string SecretKey { get; set; }


        /// <summary>
        /// 颁发jwt鉴权
        /// </summary>
        /// <param name="uId">用户id</param>
        /// <param name="role">权限</param>
        /// <returns></returns>
        public static string IssueJwt(string uId, string role)
        {
            //Payload,存放用户信息,下面我们放了一个用户id
            var claims = new[]
            {
                /*
                * 特别重要:
                1、这里将用户的部分信息,比如 uid 存到了Claim 中,如果你想知道如何在其他地方将这个 uid从 Token 中取出来,
                   请看下边的SerializeJwt() 方法,或者在整个解决方案,搜索这个方法,看哪里使用了!
                2、你也可以研究下 HttpContext.User.Claims ,具体的你可以看看 Policy/PermissionHandler.cs 类中是如何使用的。
                */
                #region Claim 属性说明
                 /**  Claim 属性说明
                 * jti  : 鉴权id,防止重复
                 * iat  : 鉴权颁发时间
                 * nbf  : 暂时不知道是干啥的时间
                 * exp  : 鉴权过期时间
                 * iss  : 鉴权颁发人,主体
                 * aud  : 鉴权的接收者
                 * role :鉴权的角色
                 */
                #endregion
               
                new Claim(JwtRegisteredClaimNames.Jti, uId), //如果是最简单运行的验证服务,只要这一行就行,下面的几个 new Claim 都可以不写
                new Claim(JwtRegisteredClaimNames.Iat, $"{new DateTimeOffset(DateTime.Now).ToUnixTimeSeconds()}"),
                new Claim(JwtRegisteredClaimNames.Nbf, $"{new DateTimeOffset(DateTime.Now).ToUnixTimeSeconds()}") ,
                //这个就是过期时间,目前是过期2分钟,可自定义,注意JWT有自己的缓冲过期时间
                new Claim (JwtRegisteredClaimNames.Exp, $"{new DateTimeOffset(DateTime.Now.AddMinutes(2)).ToUnixTimeSeconds()}"),
                new Claim(JwtRegisteredClaimNames.Iss, Issuer),
                new Claim(JwtRegisteredClaimNames. Aud, Audience + DateTime.Now.ToString()),
                new Claim(ClaimTypes.Role, role) //添加访问权限

            };
            //Signature
            //取出私钥并以utf8编码字节输出
            var secretByte = Encoding.UTF8.GetBytes(SecretKey);
            //使用非对称算法对私钥进行加密
            var signingKey = new SymmetricSecurityKey(secretByte);
            //使用HmacSha256来验证加密后的私钥生成数字签名
            //Header,选择签名算法
            var signingAlogorithm = SecurityAlgorithms.HmacSha256;
            var signingCredentials = new SigningCredentials(signingKey, signingAlogorithm);
            //生成Token
            var Token = new JwtSecurityToken(
                    issuer: Issuer,        //发布者
                    audience: Audience,    //接收者
                    claims: claims,        //存放的用户信息
                    notBefore: DateTime.Now,             //发布时间
                    expires: DateTime.Now.AddMinutes(2), //有效期设置为2分钟
                    signingCredentials                      //数字签名
                );
            //生成字符串token
            string TokenStr = new JwtSecurityTokenHandler().WriteToken(Token);

            return TokenStr;
        }
    }
}

第四步 : 在接口中使用JWT身份验证服务

image.png 如上图中所示,只需添加这个特性便可给接口开启身份验证服务

image.png 如上图所示,这是我没有登录获取token访问接口 报错401 无法访问

image.png 如上图所示,这是我登录获取的token

image.png 如上图,访问接口在Header中添加我的token
注意:特别重要!!! 一定要在 token前面添加 Bearer单词 并加一个空格 再写token

image.png 如上图所示,我添加token之后 成功访问接口了,并获取到接口数据了

当然jwt鉴权身份验证服务不仅限于此的使用,还有更广泛,更深层次的使用方式,欢迎大家到评论区互相讨论!!!

如果想知道我图中绑定token的那个小窗口是如何打开的,可以参考一下我的另一个文章: .Net Core 项目给Swagger 配置身份验证token绑定方法 - 掘金 (juejin.cn)