我试图用ASP.NET Core做一个非常简单的JWT承载认证实现。我从控制器返回一个响应,如下所示:
var identity = new ClaimsIdentity();
identity.AddClaim(new Claim(ClaimTypes.Name, applicationUser.UserName));
var jwt = new JwtSecurityToken(
_jwtOptions.Issuer,
_jwtOptions.Audience,
identity.Claims,
_jwtOptions.NotBefore,
_jwtOptions.Expiration,
_jwtOptions.SigningCredentials);
var encodedJwt = new JwtSecurityTokenHandler().WriteToken(jwt);
return new JObject(
new JProperty("access_token", encodedJwt),
new JProperty("token_type", "bearer"),
new JProperty("expires_in", (int)_jwtOptions.ValidFor.TotalSeconds),
new JProperty(".issued", DateTimeOffset.UtcNow.ToString())
);
我有传入请求的Jwt中间件:
app.UseJwtBearerAuthentication(new JwtBearerOptions
{
AutomaticAuthenticate = true,
AutomaticChallenge = true,
TokenValidationParameters = tokenValidationParameters
});
这似乎可以通过authorize属性保护资源,但声明永远不会出现。
[Authorize]
public async Task<IActionResult> Get()
{
var user = ClaimsPrincipal.Current.Claims; // Nothing here
答案 0 :(得分:15)
您不能在ASP.NET Core应用程序中使用ClaimsPricipal.Current
,因为它不是由运行时设置的。您可以阅读https://github.com/aspnet/Security/issues/322了解更多信息。
相反,请考虑使用由User
公开的ControllerBase
属性。
答案 1 :(得分:9)
访问User.Claims
而不是ClaimsPrinciple.Current.Claims
。
From Introduction to Identity at docs.asp.net:
来自MVC存储库的...在
HomeController.Index
操作方法中,您可以查看User.Claims
详细信息。
Here is the relevant source code:
public ClaimsPrincipal User
{
get
{
return HttpContext?.User;
}
}
答案 2 :(得分:3)
作为ASP.NET Core 2.0的一部分,您可以像上面描述的Shaun一样阅读JWT声明。如果您只是在寻找用户ID(请确保您已使用&#34; Sub&#34;声明名称将其添加为声明的一部分),那么您可以根据您的使用情况使用以下两个示例来阅读:
读取用户ID声明:
public class AccountController : Controller
{
[Authorize]
[HttpGet]
public async Task<IActionResult> MethodName()
{
var userId = _userManager.GetUserId(HttpContext.User);
//...
return Ok();
}
}
阅读其他声明:
public class AccountController : Controller
{
[Authorize]
[HttpGet]
public async Task<IActionResult> MethodName()
{
var rolesClaim = HttpContext.User.Claims.Where( c => c.Type == ClaimsIdentity.DefaultRoleClaimType).FirstOrDefault();
//...
return Ok();
}
}
答案 3 :(得分:1)
通过此解决方案,使用Jwt令牌时,您可以在控制器中访问User.Identiy
及其声明:
步骤1:创建一个JwtTokenMiddleware:
public static class JwtTokenMiddleware
{
public static IApplicationBuilder UseJwtTokenMiddleware(
this IApplicationBuilder app,
string schema = "Bearer")
{
return app.Use((async (ctx, next) =>
{
IIdentity identity = ctx.User.Identity;
if ((identity != null ? (!identity.IsAuthenticated ? 1 : 0) : 1) != 0)
{
AuthenticateResult authenticateResult = await ctx.AuthenticateAsync(schema);
if (authenticateResult.Succeeded && authenticateResult.Principal != null)
ctx.User = authenticateResult.Principal;
}
await next();
}));
}
}
第2步:在Startup.cs中使用它:
public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
app.UseAuthentication();
app.UseJwtTokenMiddleware();
}