C# AspNetCore 2.1承载令牌身份验证-当前用户为空
我有一个应用程序,当用户登录时请求令牌。 然后通过以下标头传递该令牌:C# AspNetCore 2.1承载令牌身份验证-当前用户为空,c#,asp.net-core,asp.net-identity,jwt,entity-framework-core,C#,Asp.net Core,Asp.net Identity,Jwt,Entity Framework Core,我有一个应用程序,当用户登录时请求令牌。 然后通过以下标头传递该令牌: Authorization: Bearer <TOKEN> 要在用户登录时创建令牌,我提供了TokenProvider服务: public class RsaJwtTokenProvider : ITokenProvider { readonly IConfiguration configuration; readonly IDateFactory dateFactory; reado
Authorization: Bearer <TOKEN>
要在用户登录时创建令牌,我提供了TokenProvider
服务:
public class RsaJwtTokenProvider : ITokenProvider
{
readonly IConfiguration configuration;
readonly IDateFactory dateFactory;
readonly RsaSecurityKey _key;
readonly string _algorithm;
readonly string _issuer;
readonly string _audience;
public RsaJwtTokenProvider(
IConfiguration configuration,
IDateFactory dateFactory
)
{
this.configuration = configuration;
this.dateFactory = dateFactory;
var parameters = new CspParameters { KeyContainerName = configuration.GetSection("TokenAuthentication:SecretKey").Value };
var provider = new RSACryptoServiceProvider(2048, parameters);
_key = new RsaSecurityKey(provider);
_algorithm = SecurityAlgorithms.RsaSha256Signature;
_issuer = configuration.GetSection("TokenAuthentication:Issuer").Value;
_audience = configuration.GetSection("TokenAuthentication:Audience").Value;
}
public (string Token, int Expires) CreateToken(string userName, string UserId)
{
JwtSecurityTokenHandler tokenHandler = new JwtSecurityTokenHandler();
var claims = new List<Claim>()
{
new Claim(ClaimTypes.NameIdentifier, UserId),
new Claim(ClaimTypes.Name, userName)
};
ClaimsIdentity identity = new ClaimsIdentity(claims, "jwt");
int expiresIn = int.Parse(configuration.GetSection("TokenAuthentication:Validaty").Value);
DateTime expires = dateFactory.Now.AddMinutes(expiresIn).ToUniversalTime();
SecurityToken token = tokenHandler.CreateJwtSecurityToken(new SecurityTokenDescriptor
{
Audience = _audience,
Issuer = _issuer,
SigningCredentials = new SigningCredentials(_key, _algorithm),
Expires = expires,
Subject = identity
});
return (tokenHandler.WriteToken(token), expiresIn);
}
public TokenValidationParameters GetValidationParameters()
{
return new TokenValidationParameters
{
// The signing key must match!
ValidateIssuerSigningKey = true,
IssuerSigningKey = _key,
// Validate the JWT Issuer (iss) claim
ValidateIssuer = true,
ValidIssuer = _issuer,
// Validate the JWT Audience (aud) claim
ValidateAudience = true,
ValidAudience = _audience,
// Validate the token expiry
ValidateLifetime = true,
// If you want to allow a certain amount of clock drift, set that here:
ClockSkew = TimeSpan.Zero
};
}
}
用户的内容如下:
我做错了什么
屏幕截图声明(令牌创建)
更新
在的帮助下,我发现我的CurrentUser
属性中没有声明
将[Authorize]
放入控制器后,它开始工作。
但是,我也需要它来处理匿名操作。。。
有什么想法吗?如果我正确理解了您的问题,您将无法从
标识中找到当前登录的用户
您需要将Name
声明添加到您的ClaimsIdentity
,该声明将自动转换为Identity
属性的Name
属性
以下是一个例子:
var claims = new List<Claim>
{
new Claim(ClaimTypes.Name, "SomeName or Id")
};
更新:
我以前没有注意到您试图在授权过程中添加声明
(以及整个身份
)。事实并非如此。添加声明应该发生在身份验证内部,而不是授权内部。我不确定您的确切问题是什么。您的问题是无法从身份中获取当前登录用户是谁吗?@MohammedNoureldin是的,这是我的问题,那么请检查我的答案好吧,我明白了,不知怎么错过了。。。我会尽快给你反馈。在将反馈应用到我的CreateToken
之后,我的userManager
仍然检索空值。我会用它更新我的代码。@LeandroSoares,你的名称属性现在已经填充了吗?我想是的。。。检查问题末尾的屏幕截图。@LeandroSoares,起初我没有注意到您试图在授权过程中添加声明(以及整个身份)。事实并非如此。我猜你想做点什么,但用了错误的方法。你能描述一下你想要实现的目标吗?也许我能帮你更多。就目前而言,正如我所说,你不能做任何其他事情。添加声明应该发生在身份验证内部,而不是授权内部。
public string CurrentUser
{
get
{
var user = accessor.HttpContext?.User;
if (user != null)
return userManager.GetUserId(user);
return null;
}
}
var claims = new List<Claim>
{
new Claim(ClaimTypes.Name, "SomeName or Id")
};
ClaimsIdentity identity = new ClaimsIdentity(claims, "jwt");