You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

ASP.NET Core 6 MVC中如何将NotFound()重定向到自定义404页面

解决方案

原因分析

当Action中调用return NotFound()时,ASP.NET Core已经完成了端点匹配与响应内容的生成流程。你自定义的中间件在执行await next()后修改Request.Path并再次调用next(),此时端点路由系统已经完成工作,不会重新匹配新的路径,因此无法触发自定义404路由。

方法一:使用内置的UseStatusCodePagesWithReExecute中间件

这是ASP.NET Core官方提供的解决方案,专门用于在不修改URL的前提下,针对指定状态码重新执行路由处理:

  1. 移除你自定义的404中间件。
  2. 在Program.cs中添加以下代码,注意位置要放在UseStaticFiles()之后,UseRouting()之前:
app.UseStatusCodePagesWithReExecute("/404");
  1. 保留你已配置的404端点路由:
endPoints.MapControllerRoute(
    name: "404",
    pattern: "404",
    defaults: new { controller = "Error", action = "Error404" });

该中间件会在服务器检测到404状态码时,内部重新执行/404对应的路由逻辑,同时保持原URL不变,响应状态码仍为404。

方法二:通过ActionFilter拦截NotFoundResult

如果需要更灵活的控制,可以自定义ActionFilter,自动将所有NotFoundResult替换为自定义视图:

  1. 创建自定义过滤器类:
public class NotFoundRedirectFilter : IActionFilter
{
    public void OnActionExecuting(ActionExecutingContext context)
    {
        // 执行前无需处理
    }

    public void OnActionExecuted(ActionExecutedContext context)
    {
        // 检测到返回NotFoundResult时,替换为自定义视图
        if (context.Result is NotFoundResult)
        {
            context.Result = new ViewResult
            {
                ViewName = "Error404",
                StatusCode = StatusCodes.Status404NotFound,
                ViewData = context.Controller.ViewData
            };
        }
    }
}
  1. 在Program.cs中注册这个过滤器:
builder.Services.AddControllersWithViews(options =>
{
    options.Filters.Add<NotFoundRedirectFilter>();
});
  1. 确保你的Error控制器中存在Error404方法并返回对应的视图。

这种方式会直接在Action执行完成后替换结果,无需依赖中间件,同样能保持原URL和404状态码。


内容的提问来源于stack exchange,提问作者AlwaysNeedingHelp

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.13 20:30:51