.Net Core 3.1 JWT自定义验证失败的返回结果

这里Nuget使用的包分别是Newtonsoft.Json和Microsoft.AspNetCore.Authentication.JwtBearer
在这里插入图片描述
在这里插入图片描述
在Startup.cs中配置

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Authentication.JwtBearer;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.HttpsPolicy;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;
using Microsoft.IdentityModel.Tokens;
using Newtonsoft.Json;
using test.Jwt;

namespace test
{
    public class Startup
    {
        public Startup(IConfiguration configuration)
        {
            Configuration = configuration;
        }

        public IConfiguration Configuration { get; }

        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {
            services.AddControllers();
            //跨域设置
            services.AddCors(options => {
                options.AddPolicy("any", builder =>
                {
                    builder.WithOrigins("*");
                });
            });

            //加入Jwt鉴权
            services.Configure<JwtSettings>(Configuration.GetSection("JwtSettings"));
            JwtSettings setting = new JwtSettings();
            Configuration.Bind("JwtSettings", setting);
            JwtHelper.Settings = setting;

            //加入Jwt认证
            services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
            .AddJwtBearer(config =>
            {
                config.TokenValidationParameters = new TokenValidationParameters
                {
                    ValidateIssuer = true,//是否验证Issuer
                    ValidateAudience = true,//是否验证Audience
                    ValidateLifetime = true,//是否验证失效时间
                    ValidateIssuerSigningKey = true,//是否验证SecurityKey
                    ValidAudience = setting.Audience,
                    ValidIssuer = setting.Issuer,
                    IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(setting.SecretKey)),//获取SecurityKey
                    ClockSkew = TimeSpan.FromSeconds(1) //缓冲过期时间,总有效时间=过期时间+缓冲过期时间,不配置的话默认5分钟
                };
                config.Events = new JwtBearerEvents
                {
                    //权限验证失败后执行
                    OnChallenge = context =>
                    {
                        //终止默认的返回结果(必须有)
                        context.HandleResponse();
                        var result = JsonConvert.SerializeObject(new { Code = "401", Message = "验证失败" });
                        context.Response.ContentType = "application/json";
                        //验证失败返回401
                        context.Response.StatusCode = StatusCodes.Status401Unauthorized;
                        context.Response.WriteAsync(result);
                        return Task.FromResult(0);
                    }
                };
            });
        }

        // 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.UseHttpsRedirection();

            app.UseRouting();

            //加入跨域
            app.UseCors("any");

            //加入Jwt鉴权
            //注意它需要添加在app.UseAuthorization();之前,app.UseRouting();之后,顺序很重要,否则身份认证不会生效。
            app.UseAuthentication();

            app.UseAuthorization();

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

验证成功的状态:
在这里插入图片描述
自定义验证失败的状态:
在这里插入图片描述

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
在使用 JWT 进行身份验证时,通常会设置一个过期时间,以确保用户在一段时间内保持登录状态。当 JWT 过期时,用户需要重新登录并获取新的 JWT 令牌。为了避免用户频繁重新登录,我们可以使用刷新令牌的方式来延长用户的登录状态。 在 .NET Core 3.1 中,我们可以使用 JwtSecurityTokenHandler 类来生成和验证 JWT 令牌。下面是一个简单的 JwtHelper 类的实现,它支持生成、刷新和验证 JWT 令牌: ```csharp using Microsoft.IdentityModel.Tokens; using System; using System.IdentityModel.Tokens.Jwt; using System.Security.Claims; using System.Text; public class JwtHelper { private static readonly string secret = "your_secret_key_here"; private static readonly string issuer = "your_issuer_here"; private static readonly int expireMinutes = 30; private static readonly int refreshExpireMinutes = 60; public static string GenerateToken(string userId) { var securityKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(secret)); var credentials = new SigningCredentials(securityKey, SecurityAlgorithms.HmacSha256); var claims = new[] { new Claim(ClaimTypes.NameIdentifier, userId) }; var tokenDescriptor = new SecurityTokenDescriptor { Issuer = issuer, Audience = issuer, Subject = new ClaimsIdentity(claims), Expires = DateTime.UtcNow.AddMinutes(expireMinutes), SigningCredentials = credentials }; var tokenHandler = new JwtSecurityTokenHandler(); var token = tokenHandler.CreateToken(tokenDescriptor); return tokenHandler.WriteToken(token); } public static string RefreshToken(string token) { var tokenHandler = new JwtSecurityTokenHandler(); var securityKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(secret)); try { var claimsPrincipal = tokenHandler.ValidateToken(token, new TokenValidationParameters { ValidateIssuer = true, ValidateAudience = true, ValidIssuer = issuer, ValidAudience = issuer, IssuerSigningKey = securityKey, ValidateLifetime = false }, out SecurityToken validatedToken); var jwtToken = validatedToken as JwtSecurityToken; if (jwtToken == null || !jwtToken.Header.Alg.Equals(SecurityAlgorithms.HmacSha256, StringComparison.InvariantCultureIgnoreCase)) { throw new SecurityTokenException("Invalid token"); } var userId = claimsPrincipal.FindFirst(ClaimTypes.NameIdentifier).Value; return GenerateToken(userId); } catch(Exception ex) { throw new SecurityTokenException("Invalid token", ex); } } public static bool ValidateToken(string token) { var tokenHandler = new JwtSecurityTokenHandler(); var securityKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(secret)); try { var claimsPrincipal = tokenHandler.ValidateToken(token, new TokenValidationParameters { ValidateIssuer = true, ValidateAudience = true, ValidIssuer = issuer, ValidAudience = issuer, IssuerSigningKey = securityKey, ValidateLifetime = true, ClockSkew = TimeSpan.Zero }, out SecurityToken validatedToken); var jwtToken = validatedToken as JwtSecurityToken; if (jwtToken == null || !jwtToken.Header.Alg.Equals(SecurityAlgorithms.HmacSha256, StringComparison.InvariantCultureIgnoreCase)) { throw new SecurityTokenException("Invalid token"); } return true; } catch(Exception) { return false; } } } ``` 在上面的代码中,我们定义了一个静态的 secret 字符串来存储 JWT 的密钥,一个 issuer 字符串来存储 JWT 的发行者,以及一个 expireMinutes 和 refreshExpireMinutes 来分别设置 JWT 令牌和刷新令牌的过期时间。在 GenerateToken 方法中,我们使用 JwtSecurityTokenHandler 类来创建一个 JWT 令牌,并设置其过期时间和签名凭证。在 RefreshToken 方法中,我们首先验证传入的 JWT 令牌是否有效,并提取其中的用户 ID。然后,我们使用 GenerateToken 方法来生成一个新的 JWT 令牌。在 ValidateToken 方法中,我们验证传入的 JWT 令牌是否有效,并返回一个布尔值表示验证结果。 使用 JwtHelper 类非常简单,只需要调用其中的 GenerateToken、RefreshToken 和 ValidateToken 方法即可。下面是一个示例: ```csharp var token = JwtHelper.GenerateToken("user_id"); var isValid = JwtHelper.ValidateToken(token); var refreshedToken = JwtHelper.RefreshToken(token); ``` 需要注意的是,由于 JWT 令牌是无状态的,因此在刷新令牌时,我们需要使用一些外部存储机制(如数据库或缓存)来存储每个用户的刷新令牌。当用户请求刷新令牌时,我们可以从外部存储中检索出用户的刷新令牌,并验证其有效性后生成新的 JWT 令牌。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值