ASP.Net Core 3.1+Identity Server 4中JWT Bearer Token验证失效求助
解决方法:移除默认Identity UI同时让JWT Bearer认证生效
你的问题核心在于:用AddIdentity<ApplicationUser, IdentityRole>替代AddDefaultIdentity后,ASP.NET Core默认的认证方案被设置为Cookie认证,而非JWT Bearer。当API收到Authorization: Bearer请求头时,认证系统会尝试用Cookie方案验证,自然找不到用户,进而触发重定向到登录页的逻辑。
下面是具体修复步骤和修改后的完整Startup代码:
关键调整思路
- 全局指定默认认证方案为JWT Bearer,让
[Authorize]特性优先使用令牌验证 - 修改Cookie认证的行为,让API在认证失败时返回401/403状态码而非重定向(符合API场景的预期)
- 移除不必要的Razor Pages相关配置,彻底清除默认UI的端点
修改后的Startup.cs代码
using Microsoft.AspNetCore.Authentication; using Microsoft.AspNetCore.Builder; using Microsoft.AspNetCore.Hosting; using Microsoft.EntityFrameworkCore; using Munchify.Web.Data; using Munchify.Web.Models; using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Hosting; using Microsoft.AspNetCore.Identity; using Microsoft.AspNetCore.Identity.UI.Services; using APIBackend.Web.Services; using Microsoft.AspNetCore.Authentication.JwtBearer; namespace APIBackend.Web { public class Startup { public Startup(IConfiguration configuration) { Configuration = configuration; } public IConfiguration Configuration { get; } public void ConfigureServices(IServiceCollection services) { services.AddDbContext<ApplicationDbContext>(options => options.UseSqlServer( Configuration.GetConnectionString("DefaultConnection"))); // 添加Identity核心功能,不包含默认UI services.AddIdentity<ApplicationUser, IdentityRole>(options => options.SignIn.RequireConfirmedAccount = true) .AddEntityFrameworkStores<ApplicationDbContext>() .AddDefaultTokenProviders(); // 调整Cookie认证行为:API场景下禁用重定向,返回标准HTTP状态码 services.ConfigureApplicationCookie(options => { options.Events.OnRedirectToLogin = context => { context.Response.StatusCode = StatusCodes.Status401Unauthorized; return Task.CompletedTask; }; options.Events.OnRedirectToAccessDenied = context => { context.Response.StatusCode = StatusCodes.Status403Forbidden; return Task.CompletedTask; }; }); // 配置Identity Server,绑定用户和数据库,启用API授权 services.AddIdentityServer() .AddApiAuthorization<ApplicationUser, ApplicationDbContext>(); // 设置默认认证方案为JWT Bearer,确保[Authorize]优先验证令牌 services.AddAuthentication(options => { options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme; options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme; }) .AddIdentityServerJwt(); services.AddTransient<IEmailSender, EmailSender>(); // 仅添加API控制器相关服务,移除Razor Pages(如果不需要的话) services.AddControllersWithViews(); // 若项目完全不需要Razor Pages,可删除下方注释行 // services.AddRazorPages(); } public void Configure(IApplicationBuilder app, IWebHostEnvironment env) { if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); app.UseDatabaseErrorPage(); } else { app.UseExceptionHandler("/Error"); app.UseHsts(); } app.UseHttpsRedirection(); app.UseStaticFiles(); app.UseRouting(); // 严格遵循中间件顺序:认证 → IdentityServer → 授权 app.UseAuthentication(); app.UseIdentityServer(); app.UseAuthorization(); app.UseEndpoints(endpoints => { endpoints.MapControllerRoute( name: "default", pattern: "{controller}/{action=Index}/{id?}"); // 若删除了AddRazorPages,同步删除下方映射 // endpoints.MapRazorPages(); }); } } }
修改细节说明
- 默认认证方案指定:通过
AddAuthentication设置全局默认的认证和挑战方案为JWT Bearer,确保所有带[Authorize]的控制器自动使用令牌验证。 - Cookie行为修正:重写Cookie认证的重定向事件,让API在认证失败时返回标准的401/403状态码,而非跳转到登录页面,符合API的无状态特性。
- 清理冗余配置:移除Razor Pages相关服务和端点映射,彻底清除默认Identity UI的入口。
额外验证建议
- 确认Identity Server已正确配置API资源和范围,移动端应用请求令牌时需包含对应API的范围。
- 用JWT解码工具验证令牌的有效性,确保
aud(受众)和scope(范围)与API配置匹配。 - 测试API调用时,确保请求头
Authorization: Bearer {token}格式正确。
内容的提问来源于stack exchange,提问作者Henrik Storck
相关产品推荐
相关产品推荐

