[英].NET 6.0 API + jwt-auth | API returns "invalid_token" error
我正在尝试将 jwt 实施到我的项目中。 在我更改代码之前它正在工作。 此更改不会影响授权,但不知何故令牌不再起作用。
当我从 jwt.io 检查令牌时,它显示“签名无效”。 当我尝试使用 Swagger 执行请求时,回复说
content-length: 0
date: Fri,02 Sep 2022 10:09:12 GMT
server: Kestrel
www-authenticate: Bearer error="invalid_token"
x-firefox-spdy: h2
秘密:tx9mcA4gnbigtP7ZRECnfhk9tWsHM9ZtXqbuFYWM23D3PMdRKwh74e24swqvrTh5
API/程序.cs
using System.Text;
using BlogProject.Business.MapperProfile;
using BlogProject.Business.Services.AuthenticationService;
using BlogProject.Business.Services.CommentService;
using BlogProject.Business.Services.PostService;
using BlogProject.Business.Services.TagService;
using BlogProject.Business.Services.UserService;
using BlogProject.DataAccess.Data;
using BlogProject.DataAccess.Repositories.Base;
using BlogProject.DataAccess.Repositories.Base.Interfaces;
using BlogProject.DataAccess.Repositories.Relations;
using BlogProject.DataAccess.Repositories.Relations.Interfaces;
using Microsoft.AspNetCore.Authentication.JwtBearer;
using Microsoft.EntityFrameworkCore;
using Microsoft.IdentityModel.Tokens;
using Microsoft.OpenApi.Models;
using Swashbuckle.AspNetCore.Filters;
var builder = WebApplication.CreateBuilder(args);
var isDevelopment = builder.Environment.IsDevelopment();
builder.Services.AddControllers();
builder.Services.AddCors();
builder.Services.AddAuthentication(options =>
{
options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
options.DefaultScheme = JwtBearerDefaults.AuthenticationScheme;
})
.AddJwtBearer(options =>
{
var key = builder.Configuration["JsonWebTokenKeys:IssuerSigningKey"];
var encodedKey = Encoding.UTF8.GetBytes(key);
var signingKey = new SymmetricSecurityKey(encodedKey);
options.RequireHttpsMetadata = false;
options.SaveToken = true;
options.TokenValidationParameters = new TokenValidationParameters
{
ValidateIssuerSigningKey = true,
IssuerSigningKey = signingKey,
ValidateIssuer = false,
ValidateAudience = false,
};
});
builder.Services.AddScoped<IJwtAuthenticationManager, JwtAuthenticationManager>();
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen(options =>
{
var openApiSecurityScheme = new OpenApiSecurityScheme
{
Description = "Standard Authorization header using the Bearer scheme (\"bearer {token}\")",
In = ParameterLocation.Header,
Name = "Authorization",
Type = SecuritySchemeType.ApiKey
};
options.AddSecurityDefinition("oauth2", openApiSecurityScheme);
options.OperationFilter<SecurityRequirementsOperationFilter>();
});
builder.Services.AddAutoMapper(typeof(MapProfile));
builder.Services.AddDbContext<BlogProjectDbContext>(
optionsBuilder =>
{
var connectionString = builder.Configuration.GetConnectionString("DefaultConnection");
optionsBuilder.UseNpgsql(connectionString);
optionsBuilder.EnableDetailedErrors(isDevelopment);
optionsBuilder.EnableSensitiveDataLogging(isDevelopment);
});
builder.Services.AddScoped<IPostRepository, EFPostRepository>();
builder.Services.AddScoped<ICommentRepository, EFCommentRepository>();
builder.Services.AddScoped<IUserRepository, EFUserRepository>();
builder.Services.AddScoped<ITagRepository, EFTagRepository>();
builder.Services.AddScoped<ICategoryRepository, EFCategoryRepository>();
builder.Services.AddScoped<IPostsEditorsRepository, EFPostsEditorsRepository>();
builder.Services.AddScoped<IPostsTagsRepository, EFPostsTagsRepository>();
builder.Services.AddScoped<IUsersCommentReactionsRepository, EFUsersCommentReactionsRepository>();
builder.Services.AddScoped<IUsersPostReactionsRepository, EFUsersPostReactionsRepository>();
builder.Services.AddScoped<IPostService, PostService>();
builder.Services.AddScoped<IUserService, UserService>();
builder.Services.AddScoped<ICommentService, CommentService>();
builder.Services.AddScoped<ITagService, TagService>();
builder.Services.AddScoped<ITagService, TagService>();
var app = builder.Build();
if (isDevelopment)
{
app.UseSwagger();
app.UseSwaggerUI();
}
app.UseCors(policyBuilder => policyBuilder.AllowAnyHeader().AllowAnyMethod().WithOrigins("http://localhost:3000"));
app.UseHttpsRedirection();
app.UseAuthentication();
app.UseAuthorization();
app.MapControllers();
app.Run();
业务/服务/AuthenticationService/JwtAuthenticationManager.cs
using System.IdentityModel.Tokens.Jwt;
using System.Security.Claims;
using System.Text;
using BlogProject.DataAccess.Repositories.Base.Interfaces;
using BlogProject.Entities.Base;
using Microsoft.Extensions.Configuration;
using Microsoft.IdentityModel.Tokens;
using JwtRegisteredClaimNames = Microsoft.IdentityModel.JsonWebTokens.JwtRegisteredClaimNames;
namespace BlogProject.Business.Services.AuthenticationService;
public class JwtAuthenticationManager : IJwtAuthenticationManager
{
private readonly IUserRepository _userRepository;
private readonly string _jwtTokenSecret;
private readonly string _jwtTokenSubject;
public JwtAuthenticationManager(
IConfiguration configuration,
IUserRepository userRepository)
{
_jwtTokenSecret = configuration["JsonWebTokenKeys:IssuerSigningKey"];
_jwtTokenSubject = configuration["JsonWebTokenKeys:Subject"];
_userRepository = userRepository;
}
public async Task<string?> GetJwtTokenAsync(string username)
{
var user = await _userRepository.ValidateUserAsync(username);
if(user == null) return null;
var securityKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(_jwtTokenSecret));
var credentials = new SigningCredentials(securityKey, SecurityAlgorithms.HmacSha256Signature);
var expireTime = DateTime.UtcNow.AddDays(1);
var token = new JwtSecurityToken(
claims : GetClaim(user),
expires : new DateTimeOffset(expireTime).DateTime,
signingCredentials : credentials);
var tokenHandler = new JwtSecurityTokenHandler();
var jwtString = tokenHandler.WriteToken(token);
return jwtString;
}
private IEnumerable<Claim> GetClaim(User user)
{
return new Claim[]
{
new Claim(JwtRegisteredClaimNames.Sub, _jwtTokenSubject),
new Claim(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString()),
new Claim(JwtRegisteredClaimNames.Iat, DateTime.UtcNow.ToString()),
new Claim("Id", user.Id.ToString()),
new Claim("UserName", user.Username),
new Claim("Email", user.Email),
new Claim("Role", user.Role)
};
}
}
API/Controller/UserController.cs:登录
[HttpGet("Login")]
public async Task<IActionResult> Login(string username, string password)
{
var response = await _userService.ValidateUserAsync(username, password);
if (response == null) return NotFound();
var tokenResponse = await _jwtAuthenticationManager.GetJwtTokenAsync(response.UserName);
if (tokenResponse == null) throw new Exception("Token is null");
response.Token = tokenResponse;
Ok(response);
}
这很尴尬。 最近我从 API 中删除了一些包。 看起来像删除“System.IdentityModel.Tokens.Jwt”以某种方式破坏了代码。 但是有一点我不明白。 它仍然在 jwt.io 处显示“无效签名”,但令牌有效。
是的,我将秘密粘贴到该领域。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.