.NET Core API在Startup配置开关:仅保留健康检查路由其余返回404
解决方案
核心思路
通过appsettings.json的配置开关,结合条件注册路由或全局中间件拦截实现需求,无需修改任何控制器代码,新增控制器自动适配规则。
步骤1:添加配置开关
在appsettings.json中新增控制项:
{ "DisableControllers": true // true=仅保留健康检查路由;false=正常启用所有路由 }
步骤2:选择适配的实现方案
根据你的.NET版本选择对应写法:
方案一:条件注册路由(推荐,性能更优)
控制器路由仅在开关关闭时注册,开启时直接不存在对应路由,自然返回404。
.NET 6+ 顶语句写法(Program.cs)
var builder = WebApplication.CreateBuilder(args); // 读取配置开关 var disableControllers = builder.Configuration.GetValue<bool>("DisableControllers"); // 添加健康检查服务(如果还没加) builder.Services.AddHealthChecks(); // 添加控制器服务(始终添加,只是路由注册有条件) builder.Services.AddControllers(); var app = builder.Build(); // 其他中间件配置(比如UseHttpsRedirection、UseAuthorization等) app.UseHttpsRedirection(); app.UseAuthorization(); // 始终注册健康检查路由 app.MapHealthChecks("/health"); // 仅当开关关闭时,注册控制器路由 if (!disableControllers) { app.MapControllers(); // 如果是用传统路由模板,替换为:app.MapControllerRoute("default", "{controller=Home}/{action=Index}/{id?}"); } app.Run();
.NET 5及以前 Startup.cs 写法
public class Startup { public IConfiguration Configuration { get; } public Startup(IConfiguration configuration) { Configuration = configuration; } public void ConfigureServices(IServiceCollection services) { services.AddHealthChecks(); services.AddControllers(); } public void Configure(IApplicationBuilder app, IWebHostEnvironment env) { if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); } app.UseHttpsRedirection(); app.UseRouting(); app.UseAuthorization(); app.UseEndpoints(endpoints => { // 始终注册健康检查路由 endpoints.MapHealthChecks("/health"); var disableControllers = Configuration.GetValue<bool>("DisableControllers"); // 条件注册控制器路由 if (!disableControllers) { endpoints.MapControllers(); // 或者传统路由:endpoints.MapControllerRoute("default", "{controller=Home}/{action=Index}/{id?}"); } }); } }
方案二:全局中间件拦截(更灵活)
通过中间件在请求到达路由匹配前拦截,非健康检查请求直接返回404,适合需要动态调整拦截规则的场景。
.NET 6+ 写法(Program.cs)
var builder = WebApplication.CreateBuilder(args); var disableControllers = builder.Configuration.GetValue<bool>("DisableControllers"); builder.Services.AddHealthChecks(); builder.Services.AddControllers(); var app = builder.Build(); // 先注册拦截中间件(必须放在路由相关中间件之前) if (disableControllers) { app.Use(async (context, next) => { // 仅允许健康检查路由,可根据实际路由调整路径判断逻辑 if (!context.Request.Path.StartsWithSegments("/health")) { context.Response.StatusCode = StatusCodes.Status404NotFound; return; } await next(); }); } app.UseHttpsRedirection(); app.UseAuthorization(); // 正常注册所有路由 app.MapHealthChecks("/health"); app.MapControllers(); app.Run();
关键说明
- 两种方案均无需修改任何控制器代码,新增控制器自动遵循规则;
- 若健康检查路由不是
/health,需同步修改代码中的路径判断逻辑; - 方案一性能更优,因为控制器路由未注册,不会触发路由匹配流程;方案二更灵活,可快速扩展允许访问的路由列表。
内容的提问来源于stack exchange,提问作者trinny
相关产品推荐
相关产品推荐

