JWT(core3.1版本测试)
什么是 JSON Web 令牌?
JSON Web Token (JWT) 是一个开放标准 ( RFC 7519 ),它定义了一种紧凑且自包含的方式,用于在各方之间以 JSON 对象的形式安全传输信息。此信息可以验证和信任,因为它是数字签名的。JWT 可以使用密钥(使用HMAC算法)或使用RSA或ECDSA的公钥/私钥对进行签名。
虽然 JWT 可以加密以在各方之间提供保密性,但我们将专注于签名令牌。签名的令牌可以验证其中包含的声明的完整性,而加密的令牌会向其他方隐藏这些声明。当使用公钥/私钥对对令牌进行签名时,签名还证明只有持有私钥的一方才是签署它的一方。
什么时候应该使用 JSON Web Tokens?
以下是 JSON Web 令牌有用的一些场景:
-
授权:这是使用 JWT 最常见的场景。用户登录后,每个后续请求都将包含 JWT,从而允许用户访问该令牌允许的路由、服务和资源。单点登录是当今广泛使用 JWT 的一项功能,因为它的开销很小并且能够在不同的域中轻松使用。
-
信息交换:JSON Web 令牌是在各方之间安全传输信息的好方法。因为可以对 JWT 进行签名(例如,使用公钥/私钥对),所以您可以确定发件人就是他们所说的那个人。此外,由于使用标头和有效负载计算签名,您还可以验证内容没有被篡改。
1.创建一个webapi的项目(我创建的是core3.1的)
2.首先引用2个包:①:Microsoft.AspNetCore.Authentication.JwtBearer;②:JWT
3.在ConfigureServices 中配置JWT
public void ConfigureServices(IServiceCollection services) { services.AddControllers(); #region 配置JWT var issurer = "Nuctech.CHN";//发行人 var audience = "Api.Auth";//受众人 var secret = "Nuc#techjjfa3bchn";//密钥 /* 一. TokenValidationParameters的参数默认值: 1. ValidateAudience = true, ----- 如果设置为false,则不验证Audience受众人 2. ValidateIssuer = true , ----- 如果设置为false,则不验证Issuer发布人,但建议不建议这样设置 3. ValidateIssuerSigningKey = false, 4. ValidateLifetime = true, ----- 是否验证Token有效期,使用当前时间与Token的Claims中的NotBefore和Expires对比 5. RequireExpirationTime = true, ----- 是否要求Token的Claims中必须包含Expires 6. ClockSkew = TimeSpan.FromSeconds(300), ----- 允许服务器时间偏移量300秒,即我们配置的过期时间加上这个允许偏移的时间值,才是真正过期的时间(过期时间 +偏移值)你也可以设置为0,ClockSkew = TimeSpan.Zero */ //配置认证服务 services.AddAuthentication(x => { x.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme; x.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme; }).AddJwtBearer(y => { y.TokenValidationParameters = new TokenValidationParameters { //是否验证发行人 ValidateIssuer = true, ValidIssuer = issurer,//发行人 //是否验证受众人 ValidateAudience = true, ValidAudience = audience, //是否验证密钥 ValidateIssuerSigningKey = true, IssuerSigningKey = new SymmetricSecurityKey(Encoding.ASCII.GetBytes(secret)), ValidateLifetime = true,//验证过期时间 RequireExpirationTime = true //过期时间 }; }); #endregion }
4.在Configure 中写入(认证在前,授权在后,有顺序的)
public void Configure(IApplicationBuilder app, IWebHostEnvironment env) { if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); } app.UseHttpsRedirection(); app.UseRouting(); app.UseAuthentication();//认证 app.UseAuthorization();//授权 app.UseEndpoints(endpoints => { endpoints.MapControllers(); }); }
5.创建一个 TestInfo 控制器,并写入如下代码
[Route("api/[controller]")] [ApiController] public class TestInfo : ControllerBase { private readonly IConfiguration _configuration; public TestInfo(IConfiguration configuration) { _configuration = configuration; } [Authorize] [HttpGet] public IActionResult UserInfo() { return Ok(new { Name = "chn", Age = 18 }); } [HttpPost] public IActionResult GetToken(User u) { if (u == null || string.IsNullOrEmpty(u.LoginName) || string.IsNullOrEmpty(u.LoginPwd)) { return Ok(new { code = -1, msg = "用户名或密码不能为空" }); } //验证用户 if (u.LoginName != "chn" && u.LoginPwd != "admin") { return Ok(new { code = -1, msg = "用户名或密码错误" }); } //验证成功,构建Token string strToken = GenerateToken(u); //返回信息 return Ok(new { code = 1, msg = "Success", data = new { LoginName = u.LoginName, Token = strToken, Expire = 3600, TokenType = JwtBearerDefaults.AuthenticationScheme } }); } private string GenerateToken(User u) { //这里也是从配置文件读取的,和上面读取的一致,否则开启对应验证的话会不通过 string secret = "Nuc#techjjfa3bchn"; string issuer_z = "Nuctech.CHN"; string audience_z = "Api.Auth"; //指定加密算法 var securityKey = new SigningCredentials(new SymmetricSecurityKey(Encoding.ASCII.GetBytes(secret)), SecurityAlgorithms.HmacSha256); //可以在Token里增加信息,但这里不要加私密信息,比如密码等这种数据 var claims = new Claim[] { new Claim("UserName", u.LoginName) }; //组装数据 SecurityToken securityToken = new JwtSecurityToken( issuer: issuer_z,//颁发者 audience: audience_z,//接收者 signingCredentials: securityKey,//组装的秘钥 expires: DateTime.Now.AddSeconds(30),//有效时间 claims: claims ); //生成Token return new JwtSecurityTokenHandler().WriteToken(securityToken); } } public class User { public string LoginName { get; set; } public string LoginPwd { get; set; } }
6.启动程序,利用postman工具进行测试
先拿到token,如下图:
然后再把token复制到 get请求中
总结:如果没有token直接请求get接口,会报401的错!!!
posted on 2022-06-22 16:40 泰坦尼克号上的活龙虾 阅读(217) 评论(0) 收藏 举报