jwt授权拓展类AddAuth:

using Microsoft.AspNetCore.Authentication.JwtBearer; using Microsoft.AspNetCore.Http; using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; using Microsoft.IdentityModel.Tokens; using Siia.MobileApi.Extensions.Jwt; using System; using System.Text; namespace Siia.MobileApi.Extensions { public static class AuthenticationExt { public static void AddAuth(this IServiceCollection services, IConfiguration configuration) { if (services == null) throw new ArgumentNullException(nameof(services)); JwtSettings jwtSettings = new JwtSettings(); services.Configure<JwtSettings>(configuration.GetSection("JwtSettings")); configuration.GetSection("JwtSettings").Bind(jwtSettings); services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme) .AddJwtBearer(o => { o.TokenValidationParameters = new TokenValidationParameters() { ValidateIssuerSigningKey = true, ValidateIssuer = true,//是否验证Issuer ValidateAudience = true,//是否验证Audience ValidateLifetime = true,//是否验证失效时间 ValidIssuer = jwtSettings.Issuer, ValidAudience = jwtSettings.Audience, //用于签名验证 IssuerSigningKey = new SymmetricSecurityKey(Encoding.ASCII.GetBytes(jwtSettings.SecretKey)), //注意这是缓冲过期时间,总的有效时间等于这个时间加上jwt的过期时间,如果不配置,默认是5分钟 //ClockSkew = TimeSpan.FromSeconds(4) }; }); services.AddTransient<IPassport, Passport>(PassportFactory); } private static Passport PassportFactory(IServiceProvider provider) { var httpAccessor = provider.GetService<IHttpContextAccessor>(); if (httpAccessor == null) { return null; } return new Passport(httpAccessor.HttpContext?.User); } } }
ConfigureServices中注入AddAuth: services.AddAuth(Configuration);

public void ConfigureServices(IServiceCollection services) { services.AddControllers(); services.AddSingleton<IHttpContextAccessor, HttpContextAccessor>(); services.AddSwagger(); services.AddAuth(Configuration); services.AddScoped<IJwt, Jwt>(); // Jwt注入 //json 序列化问题 services.AddControllers().AddNewtonsoftJson(options => { options.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver(); options.SerializerSettings.DateFormatString = "yyyy-MM-dd HH:mm:ss"; //指定时间的序列化格式 options.SerializerSettings.ReferenceLoopHandling = ReferenceLoopHandling.Ignore; //忽略循环引用 }); //解决中文被编码 services.AddSingleton(HtmlEncoder.Create(UnicodeRanges.All)); services.AddHttpClient("Siia.MobileApi"); //防止回收 services.AddQuartzHostedService() .AddQuartzJob<WeatherMonitoring>() .AddQuartzJob<HealthCheckJob>(); //services.AddSingleton<MessageQueueFunc>(); }
Configure中:
app.UseAuthentication();
app.UseAuthorization();
jwt,生成授权token:

using Microsoft.Extensions.Configuration; using Microsoft.IdentityModel.Tokens; using System; using System.Collections.Generic; using System.IdentityModel.Tokens.Jwt; using System.Security.Claims; using System.Text; namespace Siia.MobileApi.Extensions.Jwt { public class Jwt : IJwt { private JwtSettings _jwSetting = new JwtSettings(); public Jwt(IConfiguration configration) { configration.GetSection("JwtSettings").Bind(_jwSetting); } /// <summary> /// 生成Token /// </summary> /// <param name="Claims"></param> /// <returns></returns> public (string token, int expires) GetToken(Dictionary<string, string> Claims) { List<Claim> claims = new List<Claim>(); foreach (var item in Claims) { claims.Add(new Claim(item.Key, item.Value)); } var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(this._jwSetting.SecretKey)); var creds = new SigningCredentials(key, SecurityAlgorithms.HmacSha256); var expires = DateTime.Now.AddMinutes(_jwSetting.Lifetime); var securityToken = new JwtSecurityToken( issuer: this._jwSetting.Issuer, audience: this._jwSetting.Audience, claims: claims, expires: expires, signingCredentials: creds ); var token = new JwtSecurityTokenHandler().WriteToken(securityToken); return (token, _jwSetting.Lifetime * 60); } } }
IJwt:

public interface IJwt { (string token, int expires) GetToken(Dictionary<string, string> Claims); }
配置文件model:

internal class JwtSettings { public string Issuer { get; set; } public string Audience { get; set; } /// <summary> /// 加密key /// </summary> public string SecretKey { get; set; } /// <summary> /// 生命周期 /// </summary> public int Lifetime { get; set; } }
appsettings.json:

"JwtSettings": { "Issuer": "issuer", //随意定义 "Audience": "Audience", //随意定义 "SecretKey": "dnX51glQ09THNpjFFntQiHqIk1HcuYxJ", //随意定义 "Lifetime": 60 //单位分钟 }
登录信息Passport:

using System.Collections.Generic; using System.Security.Claims; using System.Text.Json; namespace Siia.MobileApi.Extensions { public class Passport : IPassport { public bool IsAuthenticated { get; set; } /// <summary> /// 用户Id /// </summary> public int UserId { get; set; } /// <summary> /// 用户名 /// </summary> public string UserName { get; set; } /// <summary> /// 拥有的角色Id /// </summary> public List<int> RoleIds { get; set; } /// <summary> /// 手机号 /// </summary> public string PhoneNumber { get; set; } /// <summary> /// 组织Id /// </summary> public int OrganizationId { get; set; } public Passport(ClaimsPrincipal user) { if (user != null && user.Identity.IsAuthenticated) { this.IsAuthenticated = true; this.UserId = this.GetValue(user, "userId", -1); this.UserName = user.FindFirst("userName")?.Value; this.PhoneNumber = user.FindFirst("phoneNumber")?.Value; this.RoleIds = this.GetValue(user, "roleIds"); this.OrganizationId= this.GetValue(user, "organizationId", -1); } else { this.IsAuthenticated = false; this.UserId = -1; } } private int GetValue(ClaimsPrincipal user, string type, int defaultValue) { if (user.FindFirst(type) == null) return defaultValue; return int.Parse(user.FindFirst(type).Value); } private List<int> GetValue(ClaimsPrincipal user, string type) { if (user.FindFirst(type) == null) return null; return JsonSerializer.Deserialize<List<int>>(user.FindFirst(type).Value); } } }
IPassport:

public interface IPassport { bool IsAuthenticated { get; } /// <summary> /// 用户Id /// </summary> int UserId { get; } /// <summary> /// 用户名 /// </summary> string UserName { get; } /// <summary> /// 拥有的角色Id /// </summary> List<int> RoleIds { get; } /// <summary> /// 手机号 /// </summary> public string PhoneNumber { get; set; } /// <summary> /// 组织Id /// </summary> public int OrganizationId { get; set; } }
获取授权token :

/// <summary> /// 账号密码用户登录接口 获取授权token /// </summary> /// <param name="request"></param> /// <returns></returns> [AllowAnonymous] [HttpPost("[action]")] public async Task<IActionResult> UserLogin([FromBody] AccountsLogin request) { //这里应该是需要去连接数据库做数据校验 var _result = await _accountsService.UserLogin(request.UserName, request.Password); if (_result == null || !(_result.Status ?? false)) { return Ok(ActionResponse.Fail(-1, _result.Message ?? "账号密码不正确")); } var clims = new Dictionary<string, string>(); clims.Add("userId", _result.Data.Id.ToString()); clims.Add("userName", _result.Data.UserName); clims.Add("organizationId", _result.Data.OrganizationId.ToString()); clims.Add("roleIds", JsonConvert.SerializeObject(_result.Data.RoleIdList)); var token = this._jwt.GetToken(clims); return Ok(ActionResponse.Succeed(new { token.token, token.expires, roleIds = _result.Data.RoleIdList })); }