ASP.NET Core指定专属认证策略时仍触发默认认证处理器的问题
问题场景
在ASP.NET Core 6应用中配置了两种认证方案及对应授权策略:
- 默认认证方案(
FirstAuth)用于多数控制器 - 第二种认证方案(
SecondAuth)仅用于单个控制器
配置代码如下:
builder.Services.AddAuthentication(FirstAuthDefaults.AuthenticationScheme) .AddScheme<FirstAuthSchemeOptions, FirstAuthHandler>( FirstAuthDefaults.AuthenticationScheme, options => { }) .AddScheme<SecondAuthSchemeOptions, SecondAuthHandler>( SecondAuthDefaults.AuthenticationScheme, options => { }); builder.Services.AddAuthorization(options => { AuthorizationPolicy policy2 = new AuthorizationPolicyBuilder(SecondAuthDefaults.AuthenticationScheme) .RequireAuthenticatedUser() .RequireRole("RoleName") .Build(); options.AddPolicy(SecondAuthDefaults.Policy, policy2); AuthorizationPolicy defaultAuthorizationPolicy = new AuthorizationPolicyBuilder(FirstAuthDefaults.AuthenticationScheme) .RequireAuthenticatedUser() .Build(); options.DefaultPolicy = defaultAuthorizationPolicy; });
多数控制器使用[Authorize]属性调用默认策略,运行正常;单个控制器使用[Authorize(Policy = SecondAuthDefaults.Policy)]指定专属策略。但实际运行时,访问该控制器端点时,FirstAuthHandler的HandleAuthenticateAsync仍会执行。
疑问:是否需手动在[Authorize]中覆写AuthenticationSchemes?默认认证方案仍被调用的原因是什么?
解答
默认认证方案被执行的原因
ASP.NET Core的认证中间件(UseAuthentication)默认会使用AddAuthentication中设置的默认认证方案执行认证逻辑,无论你在授权策略中指定了哪个认证方案。
你在授权策略中指定SecondAuthDefaults.AuthenticationScheme,只是告诉授权系统:只有通过该方案认证的用户身份,才能通过当前策略的授权检查,但这不会改变认证中间件的行为——它依然会优先执行默认的FirstAuth方案。
解决方案
如果你希望使用SecondAuth策略的端点仅执行SecondAuthHandler,而不触发FirstAuthHandler,需要在[Authorize]属性中显式指定AuthenticationSchemes,覆盖默认的认证方案:
[Authorize(Policy = SecondAuthDefaults.Policy, AuthenticationSchemes = SecondAuthDefaults.AuthenticationScheme)]
如果你的业务允许FirstAuthHandler执行,但仅用SecondAuth的身份进行授权检查,那么当前的策略配置是有效的——授权阶段会忽略FirstAuth的认证结果,只验证SecondAuth的身份是否符合策略要求。
内容的提问来源于stack exchange,提问作者Chris

