ASP.NET Core Web API添加Authorize属性后Postman返回401未授权
JWT认证401未授权问题排查
问题现象
ASP.NET Core Web API控制器添加[Authorize]属性后,Postman请求返回401未授权错误;移除该属性后请求可正常执行。
相关配置与代码
认证方案配置
services.AddAuthentication(option => { option.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme; option.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme; option.DefaultScheme = JwtBearerDefaults.AuthenticationScheme; }) .AddJwtBearer(options => { options.SaveToken = true; options.RequireHttpsMetadata = false; options.TokenValidationParameters = new Microsoft.IdentityModel.Tokens.TokenValidationParameters() { ValidateIssuer = true, ValidateAudience = true, ValidIssuer = Configuration["JWT:ValidAudience"], ValidAudience = Configuration["JWT:ValidIssuer"], IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(Configuration["JWT:Secret"])) }; });
中间件管道配置
app.UseHttpsRedirection(); app.UseRouting(); app.UseCors(); //自定义CORS配置 app.UseAuthentication(); //认证中间件 app.UseAuthorization(); //授权中间件 app.UseEndpoints(endpoints => { endpoints.MapControllers(); });
控制器代码
[Route("api/[controller]")] [ApiController] [Authorize]//(Roles = UserRoles.Admin)] public class ValuesController : ControllerBase { // GET: api/<ValuesController> [HttpGet] public IEnumerable<string> Get() { return new string[] { "value1", "value2" }; } }
appSettings.json配置
"JWT": { "ValidAudience": "User", "ValidIssuer": "https://localhost:44336", "Secret": "ThisIsMySecretKEYadadasdasd939239" // 备注:需16字符以上(当前满足要求) }
登录生成JWT代码
public async Task<TokenModel> SignIn(SignInModel model) { var user = await _context.FindByNameAsync(model.UserName); if (user != null && await _context.CheckPasswordAsync(user, model.Password)) //测试密码:Rocko@135 { var authClaims = new List<Claim> { new Claim(ClaimTypes.Name, user.UserName), new Claim(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString()) }; var userRoles = await _context.GetRolesAsync(user); foreach (var userRole in userRoles) { authClaims.Add(new Claim(ClaimTypes.Role, userRole)); } var securityKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(_configuration["JWT:Secret"])); var credentials = new SigningCredentials(securityKey, SecurityAlgorithms.HmacSha256); var token = new JwtSecurityToken( issuer: _configuration["JWT:ValidIssuer"], audience: _configuration["JWT:ValidAudience"], expires: DateTime.Now.AddDays(2), claims: authClaims, signingCredentials: credentials); return new TokenModel { Token = new JwtSecurityTokenHandler().WriteToken(token), Expiration = token.ValidTo, Username = user.UserName }; } else { return new TokenModel { Token = null, Expiration = null, Username = string.Empty }; } }
生成的JWT令牌内容
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJodHRwOi8vc2NoZW1hcy54bWxzb2FwLm9yZy93cy8yMDA1LzA1L2lkZW50aXR5L2NsYWltcy9uYW1lIjoiUm9ja28iLCJqdGkiOiI0NTQ2MjhkMy1jMGM1LTQ1MTUtODQ0My1kMDQ4Y2ZhNzM1NWYiLCJodHRwOi8vc2NoZW1hcy5taWNyb3NvZnQuY29tL3dzLzIwMDgvMDYvaWRlbnRpdHkvY2xhaW1zL3JvbGUiOiJBZG1pbiIsImV4cCI6MTcxMTA1NDkzNSwiaXNzIjoiaHR0cHM6Ly9sb2NhbGhvc3Q6NDQzMzYiLCJhdWQiOiJVc2VyIn0.FQBlJENwQWzuvQ1NwzRBaTuk7I3h2YBPxhWo1vT7PUw
问题原因及修复方案
核心错误:认证配置中Issuer与Audience赋值颠倒
在AddJwtBearer的TokenValidationParameters里,ValidIssuer错误地赋值为Configuration["JWT:ValidAudience"],而ValidAudience赋值为Configuration["JWT:ValidIssuer"],导致令牌校验时Issuer和Audience不匹配,触发401错误。修复代码
修改认证配置中的TokenValidationParameters部分:options.TokenValidationParameters = new Microsoft.IdentityModel.Tokens.TokenValidationParameters() { ValidateIssuer = true, ValidateAudience = true, ValidIssuer = Configuration["JWT:ValidIssuer"], // 改为正确的Issuer配置 ValidAudience = Configuration["JWT:ValidAudience"], // 改为正确的Audience配置 IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(Configuration["JWT:Secret"])) };其他验证点
- 中间件顺序正确:
UseAuthentication在UseAuthorization之前,符合ASP.NET Core认证流程要求。 - JWT生成代码正确:Issuer和Audience均使用了正确的配置项,令牌内容中的
iss和aud与appSettings.json一致。 - Secret长度满足要求:当前Secret长度远大于16字符,符合HmacSha256算法的密钥要求。
- 中间件顺序正确:
内容的提问来源于stack exchange,提问作者Rocko
相关产品推荐
相关产品推荐

