首页 > 其他分享 >.net6webapi中配置Jwt实现鉴权验证

.net6webapi中配置Jwt实现鉴权验证

时间:2023-08-14 22:25:42浏览次数:36  
标签:net6webapi 中间件 Jwt app jwt 鉴权 token new public

JWT(Json Web Token)

jwt是一种用于身份验证的开放标准,他可以在网络之间传递信息,jwt由三部分组成:头部,载荷,签名。头部包含了令牌的类型和加密算法,载荷包含了用户的信息,签名则是对头部和载荷的加密结果。

jwt鉴权验证是指在用户登录成功后,服务器生成一个jwt令牌并返回给客户端,客户端在后续的请求中携带该令牌,服务通过令牌的签名来确定用户的身份和权限。这种方式可以避免在每个请求中都需要进行身份验证,提高了系统的性能和安全性。

jwt具有以下优点:

1.无状态:jwt令牌包含了所有必要的信息,服务器不需要再每个请求中都进行身份验证,避免了服务器存储会话信息的开销。

2.可扩展性:jwt令牌可以包含任意的信息,可以根据需要添加自定义的字段。

3.安全性:jwt令牌使用签名来保证数据的完整性和真实性,防止数据被篡改或伪造。

4.跨平台:jwt令牌是基于json格式的,可以再不同的变成语言和平台之间进行传递和解析。

如何在webapi中使用JWT?

1.首先在项目中添加如下两个包

dotnet add package Microsoft.AspNetCore.Authentication.JwtBearer
dotnet add package System.IdentityModel.Tokens.Jwt

也可以直接在Nuget包管理工具中搜索

2.创建JwtOptions模型类,同时在appsetting.json中添加对应配置

复制代码
    public class JwtOptions
    {
        /// <summary>
        /// 签发者
        /// </summary>
        public string Issuer { get; set; }

        /// <summary>
        /// 接收者
        /// </summary>
        public string Audience { get; set; }

        /// <summary>
        /// 密钥
        /// </summary>
        public string Key { get; set; }

        /// <summary>
        /// 过期时间
        /// </summary>
        public int ExpireSeconds { get; set; }
    }
复制代码 复制代码
  "JWT": {
    "Issuer": "签发方",
    "Audience": "接受方",
    "Key": "A86DA130-1B95-4748-B3B2-1B6AA9F2F743",//加密密钥
    "ExpireSeconds": 600 //密钥过期时间
  }
复制代码

3.创建JWTExtensions静态类,添加AddJWTAuthentication扩展方法

复制代码
    public static class JWTExtensions
    {
        public static AuthenticationBuilder AddJWTAuthentication(this IServiceCollection services, JwtOptions jwtOptions)
        {
            return services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
                .AddJwtBearer(x =>
                {
                    x.TokenValidationParameters = new()
                    {
                        ValidateIssuer = true,//是否验证发行商
                        ValidateAudience = true,//是否验证受众者
                        ValidateLifetime = true,//是否验证失效时间
                        ValidateIssuerSigningKey = true,//是否验证签名键
                        ValidIssuer = jwtOptions.Issuer,
                        ValidAudience = jwtOptions.Audience,
                        IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(jwtOptions.Key))
                    };
                });
        }
    }
复制代码

4.创建SwaggerGenOptionsExtensions静态类,添加AddAuthenticationHeader扩展方法,为swagger增加Authentication报文头

 

复制代码
    public static class SwaggerGenOptionsExtensions
    {
        /// <summary>
        /// 为swagger增加Authentication报文头
        /// </summary>
        /// <param name="option"></param>
        public static void AddAuthenticationHeader(this SwaggerGenOptions option)
        {
            option.AddSecurityDefinition("Authorization",
                new OpenApiSecurityScheme
                {
                    Description = "Authorization header. \r\nExample:Bearer 12345ABCDE",
                    Name = "Authorization",
                    In = ParameterLocation.Header,
                    Type = SecuritySchemeType.ApiKey,
                    Scheme = "Authorization"
                }
                ); ;

            option.AddSecurityRequirement(new OpenApiSecurityRequirement()
            {
                {
                    new OpenApiSecurityScheme
                    {
                        Reference=new OpenApiReference
                        {
                            Type=ReferenceType.SecurityScheme,
                            Id="Authorization"
                        },
                        Scheme="oauth2",
                        Name="Authorization",
                        In=ParameterLocation.Header,
                    },
                    new List<string>()
                }
            });
        }
    }
复制代码

5.创建IJwtService接口及实现JwtService类,其为构建token服务

    public interface IJwtService
    {
        string BuildToken(IEnumerable<Claim> claims, JwtOptions options);
    }
复制代码
    public class JwtService : IJwtService
    {
        public string BuildToken(IEnumerable<Claim> claims, JwtOptions options)
        {
            //过期时间
            TimeSpan timeSpan = TimeSpan.FromSeconds(options.ExpireSeconds);//token过期时间
            var securityKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(options.Key));//加密的token密钥
            var credentials = new SigningCredentials(securityKey, SecurityAlgorithms.HmacSha256Signature);//签名证书,其值为securityKey和HmacSha256Signature算法
            var tokenDescriptor = new JwtSecurityToken(options.Issuer, options.Audience, claims, expires: DateTime.Now.Add(timeSpan), signingCredentials: credentials);//表示jwt token的描述信息,其值包括Issuer签发方,Audience接收方,Claims载荷,过期时间和签名证书
            return new JwtSecurityTokenHandler().WriteToken(tokenDescriptor);//使用该方法转换为字符串形式的jwt token返回
        }
    }
复制代码

6.将上述服务尽数注册

复制代码
builder.Services.AddControllers();
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
builder.Services.AddScoped<IJwtService, JwtService>();
JwtOptions jwtOpt = builder.Configuration.GetSection("JWT").Get<JwtOptions>();
builder.Services.AddJWTAuthentication(jwtOpt);
builder.Services.Configure<SwaggerGenOptions>(c =>
{
    c.AddAuthenticationHeader();
});

var app = builder.Build();
app.UseSwagger();
app.UseSwaggerUI();
app.UseHttpsRedirection();
app.UseAuthentication();//注意,一定得先启动这个
app.UseAuthorization();
//以下回答来自GPT
//app.UseAuthentication()是启用身份验证中间件,它会验证请求中的身份信息,并将身份信息存储在HttpContext.User属性中。而app.UseAuthorization()是启用授权中间件,它会检查HttpContext.User中的身份信息是否有访问当前请求所需的权限。
//一定要先启用身份验证中间件再启用授权中间件,因为授权中间件需要使用身份验证中间件存储的身份信息来进行权限验证。如果没有启用身份验证中间件,授权中间件将无法获取到身份信息,从而无法进行权限验证。
app.MapControllers();
app.Run();
复制代码

7.在控制器中添加[ApiController]特性开启jwt鉴权,在登录接口中返回token

复制代码
    [ApiController]
    [Route("[controller]/[action]")]
    [Authorize]
    public class WeatherForecastController : ControllerBase
    {
        private static readonly string[] Summaries = new[]
        {
        "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
    };

        private readonly ILogger<WeatherForecastController> _logger;
        //jwt服务

        private readonly IJwtService _jwtService;

        private readonly IConfiguration _configuration;

        public WeatherForecastController(ILogger<WeatherForecastController> logger, IJwtService jwtService, IConfiguration configuration)
        {
            _logger = logger;
            _jwtService = jwtService;
            _configuration = configuration;
        }

        [HttpGet]
        public IEnumerable<WeatherForecast> Get()
        {
            return Enumerable.Range(1, 5).Select(index => new WeatherForecast
            {
                Date = DateTime.Now.AddDays(index),
                TemperatureC = Random.Shared.Next(-20, 55),
                Summary = Summaries[Random.Shared.Next(Summaries.Length)]
            })
            .ToArray();
        }

        //AllowAnonymous允许匿名访问
        [AllowAnonymous, HttpGet]
        public string GetToken()
        {
            var jwtopntion = _configuration.GetSection("JWT").Get<JwtOptions>();
            List<Claim> claims = new List<Claim>();
            claims.Add(new Claim(ClaimTypes.Name, "用户1"));
            claims.Add(new Claim(ClaimTypes.Role, "超级管理员"));
            return _jwtService.BuildToken(claims, jwtopntion);
        }
    }
复制代码

效果测试

 

直接调用Get方法返回401,鉴权失败

 

 调用GetToken方法,取得token

 点击右上角绿色按钮

 value中输入的值为bearer,空一格,加上之前取得的token,点击授权

 调用成功

标签:net6webapi,中间件,Jwt,app,jwt,鉴权,token,new,public
From: https://www.cnblogs.com/Leo_wl/p/17629918.html

相关文章

  • NextJS - 使用 next-auth 配置 JWT token
    Nextjs中有很多身份验证选项,例如Supabase、Firebase、Userbase等等。我们将重点关注NextAuth.js以及通过凭证提供程序在现有Django后端和Next.js之间实现JWT会话的打字稿。我们将尽力专注于我们的用例以节省时间,因此我们将省略所有未使用的选项和功能。为什么选择N......
  • 操作过滤器—MVC中使用操作过滤器实现JWT权限认证
    前言上一篇文章分享了授权过滤器实现JWT进行鉴权,文章链接:授权过滤器—MVC中使用授权过滤器实现JWT权限认证,接下来将用操作过滤器实现昨天的JWT鉴权。一、什么是操作过滤器?​与授权过滤器大部分一样,只是执行的时机和继承的接口有所不同。操作过滤器是在Action执行的前和后进......
  • JWT授权
     jwt:头部(Header)、载荷(Payload)和标记(Signature)头部:主要是规定生成token加密方式的类型和算法,载荷:可以存储一些用户身份信息标记:主要作用防篡改,验证令牌的真实性和完整性 引用jwt包appsettings里: //jwt秘钥  "Jwt": {    "SecretKey": "jiangjianhaotest12......
  • json web token(jwt)详解
    1.jsonwebtoken是什么?JSONWebToken(JWT)是一个开放标准(RFC7519),它定义了一种紧凑的、自包含的方式,用于作为JSON对象在各方之间安全地传输信息。该信息可以被验证和信任,因为它是数字签名的。 2.什么时候你应该用JSONWebTokens下列场景中使用JSONWebToken是......
  • 授权过滤器—MVC中使用授权过滤器实现JWT权限认证
    一、什么是过滤器?过滤器定义:​过滤器与中间件很相似,过滤器(Filters)可在管道(pipeline)特定阶段(particularstage)前或后执行操作,可以将过滤器视为拦截器(interceptors)。在.NETMVC开发中,权限验证是非常重要的一部分。通过使用授权过滤器可以很方便地实现权限验证功能。这篇主要分......
  • 浅尝 JWT 整合到 Spring Boot
    本文,我们将JWT整合到SpringBoot中。JWT是什么?JWT->JSONWebTokenJWT是一种开放标准(RFC7519),用于在网络应用中传递声明信息。JWT到一大优势是它的可扩展性和自包含性。它可以在各个系统之间进行安全传输和验证,因为它包含了所有必要的信息,并且经过签名保证了数据的完整性......
  • go使用jwt生成token
    常见的认证方式一般用户认证主流的方式大致上分为基于session和基于token这两种。基于sesion的认证方式用户向服务器发送用户名和密码。服务器验证通过后,在当前对话(sesion)里面保存相关数据,比如用户角色、登录时间等等。服务器向用户返回一个session_id,写入用户的Co......
  • JAVA安全-JWT安全&预编译CASE注入
    通过前期的WEB漏洞的学习,掌握了大部分的安全漏洞的原理及利用,但在各种脚本语言开发环境的差异下,会存在新的安全问题,其中脚本语言类型PHP,Java,Python等主流开发框架会有所差异。Javaweb-SQL注入攻击-预编译机制绕过1. SQL注入的防御---防御sql注入:1.session2.参数绑......
  • Gin框架dgrijalva/jwt-go实例(JWT用户认证)
    1.什么是JWTJWT(JSONWebToken)是一个非常轻巧的规范,这个规范允许我们使用JWT在用户和服务器之间传递安全可靠的信息,一个JWT由三部分组成,Header头部,Claims载荷,Signature签名JWT原理类似我们加盖公章或手写签名的的过程,合同上写了很多条款,不是随便一张纸随便写啥都可以的,......
  • RTSP/Onvif视频服务器LntonNVR(源码版)视频平台鉴权功能应用场景
    LntonNVR平台是基于RTSP/Onvif协议的视频接入、处理及分发平台,可以分发出RTSP、RTMP、WS-FLV、HTTP-FLV、HLS、WebRTC等格式的视频流,还可以提供API接口,便于用户调用集成。用户也能够直接将流地址放到第三方播放器进行播放。那么,该如何限制非管理员用户的播放权限呢?考虑到用户的使......