MVC 6 404 未找到

MVC 6 404 Not Found

我想要一个通用的 404 Not Found 页面 (HTTP 200),而不是 HTTP 404 响应。我知道您可以使用

在 MVC 5 中进行设置
<customErrors mode="On">
  <error statusCode="404" redirect="~/Error/NotFound" />
</customErrors>

但我似乎无法弄清楚如何在 MVC 6 中执行此操作。我猜它应该在 UseMvc 路由 table 或自定义中间件中。

有一个名为 StatusCodePagesMiddleware 的中间件,我相信它已被添加 post-Beta3.

样本:https://github.com/aspnet/Diagnostics/blob/dev/samples/StatusCodePagesSample/Startup.cs

Startup.cs:

public class Startup
{
    public void Configure(IApplicationBuilder app)
    {
        // PICK YOUR FLAVOR.

        // app.UseErrorPage(ErrorPageOptions.ShowAll);
        app.UseStatusCodePages(); // There is a default response but any of the following can be used to change the behavior.

        // app.UseStatusCodePages(context => context.HttpContext.Response.SendAsync("Handler, status code: " + context.HttpContext.Response.StatusCode, "text/plain"));
        // app.UseStatusCodePages("text/plain", "Response, status code: {0}");
        // app.UseStatusCodePagesWithRedirects("~/errors/{0}"); // PathBase relative
        // app.UseStatusCodePagesWithRedirects("/base/errors/{0}"); // Absolute
        // app.UseStatusCodePages(builder => builder.UseWelcomePage());
        // app.UseStatusCodePagesWithReExecute("/errors/{0}");
    }
} 

project.json:

"dependencies": {
    "Microsoft.AspNet.Diagnostics": "1.0.0-*",
    // ....
}

请注意,如果您在 IIS(或 Azure)上托管,web.config 仍然有效,并且在某些托管场景中可能 可能 需要它。 (它应该放在 wwwroot 文件夹内

在Startupclass的Configure函数中,调用:

app.UseErrorPage(ErrorPageOptions.ShowAll);

更多生产就绪:

    if (string.Equals(env.EnvironmentName, "Development", StringComparison.OrdinalIgnoreCase))
    {
        app.UseBrowserLink();
        app.UseErrorPage(ErrorPageOptions.ShowAll);
        app.UseDatabaseErrorPage(DatabaseErrorPageOptions.ShowAll);
    }
    else
    {
        // Add Error handling middleware which catches all application specific errors and
        // send the request to the following path or controller action.
        app.UseErrorHandler("/Home/Error");
    }

您可以使用 UseStatusCodePagesWithReExecute 处理 404 错误 但是您需要先在配置管道的末尾设置状态代码。

public void Configure(IApplicationBuilder app)
    {
        app.UseIISPlatformHandler();

        if (string.Equals(_env.EnvironmentName, "Development", StringComparison.OrdinalIgnoreCase))
        {
            app.UseDeveloperExceptionPage();
            app.UseRuntimeInfoPage();
        } else
        {
            app.UseExceptionHandler("/Error");
        }
        app.UseStatusCodePagesWithReExecute("/Error/Status/{0}");

        app.UseStaticFiles();

        app.UseMvc();

        app.Use((context, next) =>
        {
            context.Response.StatusCode = 404;
            return next();
        });
    }

如果管道中没有任何东西可以处理它(这正是您想要的),这会将状态代码设置为 404。

然后您可以在控制器中以任何您想要的方式轻松捕获和处理响应。

[Route("error")]
public class ErrorController : Controller
{

[Route("Status/{statusCode}")]
    public IActionResult StatusCode(int statusCode)
    {

            //logic to generate status code response

            return View("Status", model);
    }
}

如果您有一个标准的 ASP.NET 5 Web 应用程序模板项目,您可以获得一个非常好的解决方案,该解决方案将在您提供您选择的 cshtml 文件的同时处理保持错误状态代码的问题。

Startup.cs,在Configure方法中

替换

app.UseExceptionHandler("/Error");

app.UseStatusCodePagesWithReExecute("/Home/Errors/{0}");

然后删除以下包罗万象:

app.Run(async (context) => 
{ 
   var logger = loggerFactory.CreateLogger("Catchall Endpoint"); 
   logger.LogInformation("No endpoint found for request {path}", context.Request.Path); 
   await context.Response.WriteAsync("No endpoint found - try /api/todo."); 
});

HomeController.cs

将当前的 Error 方法替换为以下方法:

public IActionResult Errors(string id) 
{ 
  if (id == "500" | id == "404") 
  { 
    return View($"~/Views/Home/Error/{id}.cshtml"); 
  }

  return View("~/Views/Shared/Error.cshtml"); 
}

这样您就可以添加您认为用户可以从中受益的错误文件(同时搜索引擎等仍会获得正确的状态代码)

现在在 ~Views/Home 文件夹中添加一个名为 Error 的文件夹 创建两个 .cshtml 文件。将第一个命名为 404.cshtml,将第二个命名为 500.cshtml.

给他们一些有用的内容,然后启动应用程序并编写类似 http://localhost:44306/idonthaveanendpointhere 的内容并确认设置有效。

同时按 F12 开发者工具并确认状态码为 404。

如果有人想使用 HTML 创建自定义 404 页面,您可以这样做:

Startup.cs

public class Startup
{
    public void Configure(IApplicationBuilder app)
    {        
        app.UseStatusCodePagesWithReExecute("/errors/{0}");
    }
}

project.json

"dependencies": {
    "Microsoft.AspNet.Diagnostics": "1.0.0-*",
    // ....
}

ErrorsController.cs

public class ErrorsController : Controller
{
    // ....

    [Route("/Error/{statusCode}")]
    public IActionResult ErrorRoute(string statusCode)
    {
        if (statusCode == "500" | statusCode == "404")
        {
            return View(statusCode);
        }

        return View("~/Views/Errors/Default.cshtml");
    }
}

之后剩下的就是在您的错误视图文件夹中创建 404.cshtml、500.cshtml 和 Default.cshtml,并根据您的喜好自定义 HTML。