Ola*_*son 5 c# jwt adal .net-core
我正在为我的 .NET Core 项目使用Microsoft.AspNetCore.Authentication.JwtBearer和System.IdentityModel.Tokens.Jwt包。
在配置服务时,我正在向OnTokenValidated事件添加逻辑。
services
.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddJwtBearer(jwtBearerOptions =>
{
// ... set TokenValidationParameters ...
jwtBearerOptions.Events = new JwtBearerEvents()
{
OnTokenValidated = (tokenValidatedContext) =>
{
JwtSecurityTokenHandler jwtSecurityTokenHandler = new JwtSecurityTokenHandler();
string tokenWithoutSignature = jwtSecurityTokenHandler.WriteToken(tokenValidatedContext.SecurityToken);
// ... full token from request? ...
}
};
});
Run Code Online (Sandbox Code Playgroud)
由于我知道上下文只返回没有签名的令牌,我想知道我怎么做
tokenWithoutSignature字符串中如果这是不可能的:
我正在以这种方式生成新令牌
public string GenerateAccessToken(IDictionary<string, object> payload)
{
SymmetricSecurityKey symmetricSecurityKey = new SymmetricSecurityKey(Convert.FromBase64String("secret from config"));
SecurityTokenDescriptor tokenDescriptor = new SecurityTokenDescriptor
{
Claims = payload,
Expires = DateTime.Now, // value from config
SigningCredentials = new SigningCredentials(symmetricSecurityKey, SecurityAlgorithms.HmacSha256Signature)
};
JwtSecurityTokenHandler tokenHandler = new JwtSecurityTokenHandler();
SecurityToken securityToken = tokenHandler.CreateToken(tokenDescriptor);
string token = tokenHandler.WriteToken(securityToken);
return token;
}
Run Code Online (Sandbox Code Playgroud)
也许我可以找回
在这个方法中?
如果没有任何效果:
因为我知道不记名令牌总是包含三个部分,例如
header.payload.signature
我可以将字符串段拆分为一个数组,从数组中取出第一个和第二个元素并创建一个新的字符串
第一个字符串 + 。+ 第二个字符串
那应该给我没有签名的令牌。有没有更好的想法来从完整的令牌中切断签名?
我为什么要达到这个目标?
这个问题是基于这个的
来自 OnTokenValidated 事件侦听器的 TokenValidatedContext 的安全令牌缺少最后一个字符串段
我正在处理访问和刷新令牌。在验证期间,我必须将请求中的令牌与数据库中的令牌进行比较。数据库中的令牌也包含签名。所以我面临着与上面链接相同的问题。
这就是为什么我考虑了多种解决方案并将它们写在这里。如果TokenValidatedContext无法将签名返回给我,似乎我必须将 JWT 存储到没有签名的数据库中。而且对于这种情况,我需要将签名与生成的 JWT 分开。
在不使用刷新令牌的情况下,我只将用户的最长会话生命周期存储到数据库中。流程就是基于这个思路
只将生命周期最长的 JWT 的时间存储到数据库中,而不是整个 JWT
通过使用刷新令牌,我想出了以下流程。由于您知道 OnTokenValidated 处理验证逻辑,因此以下逻辑是附加的。我有一个数据库表
用户名 | access_token | refresh_token | refresh_token_expires_at
主键是username+access_token的复合键。刷新令牌只是一些像这样生成的随机字符串
public string GenerateRefreshToken()
{
var randomNumber = new byte[32];
using (var rng = RandomNumberGenerator.Create())
{
rng.GetBytes(randomNumber);
return Convert.ToBase64String(randomNumber);
}
}
Run Code Online (Sandbox Code Playgroud)
这就是为什么我要为它存储一个额外的到期日期。它应该能够在一段时间后过期。
登录中
将生成的访问和刷新令牌及其用户的到期时间存储到数据库中。将完整的访问令牌或没有签名的访问令牌存储到数据库(取决于此问题的解决方案)。
命中受保护的端点
检查数据库中是否存在该用户的访问令牌。
点击刷新端点
检查数据库刷新令牌是否已过期。如果没有,请将其与请求中的刷新令牌进行比较。如果一切正常,请从数据库中删除旧的访问和刷新令牌,并将新生成的访问和刷新令牌存储到数据库中。
退出
从数据库中删除该访问权限及其连接的刷新令牌。
| 归档时间: |
|
| 查看次数: |
313 次 |
| 最近记录: |