前后端分离项目中的jwt令牌应用

做为前后端分离项目中,授权认证常用token令牌做为身份认证的方式,对于jwt令牌的获取、验证、解析以及存储,分别示例如下:

需要安装两个nuget包,分别为:IdentityModel和Microsoft.AspNetCore.Authentication.JwtBearer

1、JWT令牌生成及获取

                    //写Session或Cookies换成JWT


                    IList<Claim> claims = new List<Claim> {
                        new Claim(JwtClaimTypes.Id,admin.AdminId.ToString()),
                        new Claim(JwtClaimTypes.Name,loginDto.UserName),
                        new Claim(JwtClaimTypes.Email,loginDto.UserName),
                        new Claim(JwtClaimTypes.Role,string.Join(",", ""))
                    };

                    //JWT密钥
                    var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(configuration["JwtConfig:Bearer:SecurityKey"]));

                    //算法
                    var cred = new SigningCredentials(key, SecurityAlgorithms.HmacSha256);

                    //过期时间
                    DateTime expires = DateTime.UtcNow.AddHours(10);


                    //Payload负载
                    var token = new JwtSecurityToken(
                        issuer: configuration["JwtConfig:Bearer:Issuer"],
                        audience: configuration["JwtConfig:Bearer:Audience"],
                        claims: claims,
                        notBefore: DateTime.UtcNow,
                        expires: expires,
                        signingCredentials: cred
                        );

                    var handler = new JwtSecurityTokenHandler();

                    //生成令牌
                    string jwt = handler.WriteToken(token);

2、JWT验证部分

JWT在Startup中的配置,主要用来使用固定的配置密钥对JWT的Token进行有效性验证。

            //数据库连接
            services.AddDbContext<SmsDBContext>(action => {
                action.UseSqlServer(Configuration.GetConnectionString("Default"));
            });

            services.AddCors(option =>
            {
                option.AddDefaultPolicy(policy =>
                {
                    //对应客户端withCredentials,需要设置具体允许的域名
                    policy.WithOrigins("http://web.a.com:88").AllowCredentials();
                    policy.AllowAnyMethod();
                    policy.AllowAnyHeader();
                });
            });

            services.AddAuthentication(option => {
                option.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
                option.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
            }).AddJwtBearer(
                option => {
                    option.TokenValidationParameters = new TokenValidationParameters
                    {
                        //是否验证发行人
                        ValidateIssuer = true,
                        ValidIssuer = Configuration["Authentication:JwtBearer:Issuer"],//发行人

                        //是否验证受众人
                        ValidateAudience = true,
                        ValidAudience = Configuration["Authentication:JwtBearer:Audience"],//受众人

                        //是否验证密钥
                        ValidateIssuerSigningKey = true,
                        IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(Configuration["Authentication:JwtBearer:SecurityKey"])),

                        ValidateLifetime = true, //验证生命周期

                        RequireExpirationTime = true, //过期时间

                        ClockSkew = TimeSpan.Zero   //平滑过期偏移时间
                    };
                }
            );

另外,还需要配置相应的认证中间件和授权中间件

        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
                app.UseSwagger();
                string ApiName = "Rbac.Core";
                app.UseSwaggerUI(c =>
                {
                    c.SwaggerEndpoint("/swagger/V1/swagger.json", $"{ApiName} V1");
                    c.SwaggerEndpoint("/swagger/gp/swagger.json", "登录模块");
                    c.SwaggerEndpoint("/swagger/mom/swagger.json", "业务模块");
                    c.SwaggerEndpoint("/swagger/dm/swagger.json", "其他模块");

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

            //app.UseHttpsRedirection();

            //静态文件中间件
            app.UseStaticFiles();

            //路由中间件
            app.UseRouting();

            //跨域
            app.UseCors();

            //认证中间件
            app.UseAuthentication();

            //授权中间件
            app.UseAuthorization();

            app.UseEndpoints(endpoints =>
            {
                endpoints.MapControllers();
            });
        }

经过上面配置,可以完成JWT令牌的生成及校验。

3、前端Axios的令牌保存及请求授权接口

前端接收到Api接口返回的token令牌后,应该把token保存起来,保存的位置可以是localStorage或sessionStorage,当访问授权接口时,从localStorage或sessionStorage中取出令牌,通过HTTP请求头进行访问。

import router from '../router'
import axios from 'axios'
let baseUrl = "http://localhost:5000/api";

axios.defaults.baseURL = baseUrl;
axios.defaults.headers.common['Authorization'] = `bearer ${localStorage.getItem('token')}`;

// 添加响应拦截器
axios.interceptors.response.use(function (response) {
    // 对响应数据做点什么
    return response;
  }, function (error) {
    router.push("/");
    return Promise.reject(error);
  });

export default {
    baseUrl,
    axios
}

 4、Swagger中的权限小锁配置

                //开启权限小锁
                options.OperationFilter<AddResponseHeadersFilter>();
                options.OperationFilter<AppendAuthorizeToSummaryOperationFilter>();
                options.OperationFilter<SecurityRequirementsOperationFilter>();

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

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值