using System; using System.Collections.Generic; using System.IdentityModel.Tokens.Jwt; using System.Security.Claims; using System.Text; using Microsoft.Extensions.Options; using Microsoft.IdentityModel.Tokens; using ZhiZhun.AuthenticationCenter.User; namespace ZhiZhun.AuthenticationCenter.Utility { /// /// 对称可逆加密 /// public class JWTHSService : IJWTService { private static Dictionary TokenCache = new Dictionary(); #region Option注入 private readonly JWTTokenOptions _JWTTokenOptions; public JWTHSService(IOptionsMonitor jwtTokenOptions) { this._JWTTokenOptions = jwtTokenOptions.CurrentValue; } #endregion public string GetToken(UserBasicInfo userModel) { return this.IssueToken(userModel); } /// /// 刷新token的有效期问题上端校验 /// /// /// public string GetTokenByRefresh(string refreshToken) { if (TokenCache.ContainsKey(refreshToken)) { string token = this.IssueToken(TokenCache[refreshToken], 60); return token; } else { return ""; } } /// /// 2个token 就是有效期不一样 /// /// /// public Tuple GetTokenWithRefresh(UserBasicInfo userInfo) { string token = this.IssueToken(userInfo, 60);//1分钟 string refreshToken = this.IssueToken(userInfo, 60 * 60 * 24);//24小时 TokenCache.Add(refreshToken, userInfo); return Tuple.Create(token, refreshToken); } /** * Claims (Payload) Claims 部分包含了一些跟这个 token 有关的重要信息。 JWT 标准规定了一些字段,下面节选一些字段: iss: The issuer of the token,token 是给谁的 sub: The subject of the token,token 主题 exp: Expiration Time。 token 过期时间,Unix 时间戳格式 iat: Issued At。 token 创建时间, Unix 时间戳格式 jti: JWT ID。针对当前 token 的唯一标识 除了规定的字段外,可以包含其他任何 JSON 兼容的字段。 * */ private string IssueToken(UserBasicInfo user, int second = 600) { var claims = new[] { new Claim(Microsoft.IdentityModel.JsonWebTokens.JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString()), new Claim("id", user.Id.ToString()), new Claim("name", user.UserName), new Claim("realName", user.RealName), new Claim("reviewerCode",user.ReviewerCode), new Claim("userTypeEnumName",user.UserTypeEnum.ToString()), new Claim("userTypeEnumInt",((int)user.UserTypeEnum).ToString()), new Claim("userTypeShortName",user.UserTypeShortName), new Claim("isAdmin",(user.UserTypeEnum==UserType.SuperAdmin).ToString()) }; var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(this._JWTTokenOptions.SecurityKey)); var creds = new SigningCredentials(key, SecurityAlgorithms.HmacSha256); var token = new JwtSecurityToken( issuer: this._JWTTokenOptions.Issuer, audience: this._JWTTokenOptions.Audience, claims: claims, expires: DateTime.Now.AddSeconds(second),//10分钟有效期 notBefore: null,//立即生效 DateTime.Now.AddMilliseconds(30),//30s后有效 signingCredentials: creds); string returnToken = new JwtSecurityTokenHandler().WriteToken(token); return returnToken; } } }