如何让ASP.NET Identity强制使用小写路由?
让ASP.NET Core Identity使用小写路由的解决方案
方法1:配置Cookie认证路径+Identity UI路由别名
如果使用的是官方Identity UI模板,可以直接指定Cookie认证的跳转路径,并为Identity页面配置小写路由别名,从根源上改变重定向目标:
builder.Services.AddIdentity<ApplicationUser, IdentityRole>(options => options.SignIn.RequireConfirmedAccount = true) .AddEntityFrameworkStores<IdentityUserDbContext>() .AddSignInManager() .AddDefaultTokenProviders(); // 配置Cookie认证的小写跳转路径 builder.Services.ConfigureApplicationCookie(options => { options.LoginPath = "/account/login"; options.LogoutPath = "/account/logout"; options.AccessDeniedPath = "/account/accessdenied"; // 按需添加其他Identity相关路径,如注册、找回密码等 }); // 为Identity区域页面绑定小写路由 builder.MapRazorPages() .AddRazorPagesOptions(options => { // 保留原有授权规则 options.Conventions.AuthorizeAreaFolder("Identity", "/Account/Manage"); options.Conventions.AuthorizeAreaPage("Identity", "/Account/Logout"); // 为每个Identity页面映射小写路由 options.Conventions.AddAreaPageRoute("Identity", "/Account/Login", "account/login"); options.Conventions.AddAreaPageRoute("Identity", "/Account/Logout", "account/logout"); options.Conventions.AddAreaPageRoute("Identity", "/Account/AccessDenied", "account/accessdenied"); options.Conventions.AddAreaPageRoute("Identity", "/Account/Register", "account/register"); options.Conventions.AddAreaPageRoute("Identity", "/Account/ForgotPassword", "account/forgotpassword"); });
方法2:自定义SignInManager重定向逻辑
如果需要更灵活的URL控制,可以重写SignInManager中生成重定向URL的方法,强制转换为小写:
首先创建自定义SignInManager:
public class LowercaseSignInManager<TUser> : SignInManager<TUser> where TUser : class { public LowercaseSignInManager( UserManager<TUser> userManager, IHttpContextAccessor contextAccessor, IUserClaimsPrincipalFactory<TUser> claimsFactory, IOptions<IdentityOptions> optionsAccessor, ILogger<SignInManager<TUser>> logger, IAuthenticationSchemeProvider schemes, IUserConfirmation<TUser> confirmation) : base(userManager, contextAccessor, claimsFactory, optionsAccessor, logger, schemes, confirmation) { } // 重写登录重定向方法,转换为小写 public override Task<string> RedirectToLoginAsync(string returnUrl = null) { var originalUrl = base.RedirectToLoginAsync(returnUrl).Result; return Task.FromResult(originalUrl.ToLowerInvariant()); } // 按需重写其他重定向方法 public override Task<string> RedirectToLogoutAsync(string returnUrl = null) { var originalUrl = base.RedirectToLogoutAsync(returnUrl).Result; return Task.FromResult(originalUrl.ToLowerInvariant()); } public override Task<string> RedirectToAccessDeniedAsync(string returnUrl = null) { var originalUrl = base.RedirectToAccessDeniedAsync(returnUrl).Result; return Task.FromResult(originalUrl.ToLowerInvariant()); } }
然后在Program.cs中替换默认的SignInManager:
builder.Services.AddScoped<SignInManager<ApplicationUser>, LowercaseSignInManager<ApplicationUser>>();
方法3:自定义Identity控制器的路由配置
如果是自己编写的Account控制器,直接在路由配置中指定小写路径即可:
// 为Account控制器配置小写路由 app.MapControllerRoute( name: "identity", pattern: "account/{action=Login}", defaults: new { controller = "Account" });
为什么LowercaseUrls = true不生效?
builder.Services.AddRouting(options => options.LowercaseUrls = true)仅对路由系统生成的常规链接(如Url.Action生成的地址)生效,但Identity的重定向URL是由Cookie认证选项或SignInManager的默认硬编码逻辑生成,并未经过该路由配置的小写转换,所以单独设置无法改变Identity的重定向路径。
内容的提问来源于stack exchange,提问作者Brad
相关产品推荐
相关产品推荐

