【问题标题】:How to return custom 404 response when id not found找不到 id 时如何返回自定义 404 响应
【发布时间】:2017-08-08 14:35:37
【问题描述】:

我一直想知道在以下情况下最好的错误响应代码是什么:

public IActionResult Index(Guid id)
{
    var entity = _dbContext.Entities.Find(id);
 
    if (entity == null)
    {
         return NotFound(); //??
    }
    return View(entity)
}

404 - Not Found 似乎最合适,但是,从调试的角度来看,不存在的 ID 和错误的控制器/动作名称是非常不同的错误。

无论如何,我决定返回带有更多解释性消息的自定义错误页面,这样我就可以区分 404 和 404。

Controller的Action如何返回自定义404页面,其他情况下返回默认404?

我想避免返回 HttpResponseMessage,因为我需要更改 Action 的返回类型。

PS:在 cmets 中,您可以投票支持 404 和其他您将在这种特殊情况下使用的响应代码。

【问题讨论】:

  • 你试过 return RedirectToAction("FourZeroFourpage"); ?
  • 重定向到操作返回 302,这不是我想要的
  • 您已经使用了最好的方法。 if (entity == null) { return NotFound(); //?? }

标签: c# asp.net-core asp.net-core-mvc


【解决方案1】:

先看看this question

理论上您不应该使用 HttpStatus-codes 作为应用程序错误代码。

但是,在公共网站上,404 有一个特定的含义:

无法找到请求的资源,但可能在 未来。客户端的后续请求是允许的。

调用/getresource/347d2f3a-bd0f-4d0b-8c05-2e7f3f8f265e 是一种资源。如果这不可用,则应使用 404。如果可用,则使用 200。完全可以。

Google 甚至说,你应该发送 404。来自google support

为不存在的页面返回 404 或 410 以外的代码(或 将用户重定向到另一个页面,例如主页,而不是 返回 404) 可能有问题。首先,它告诉搜索引擎 在那个 URL 上有一个真实的页面。因此,该 URL 可能是 已爬网并将其内容编入索引。由于 Googlebot 花费的时间 在不存在的页面上,您的唯一 URL 可能不会被发现为 快速或经常访问,您网站的抓取覆盖率可能 受影响(另外,您可能不希望您的网站在 搜索查询

为了实现,我会抛出一个自定义的NotFoundException(如果您想设置更有意义的信息),其中包含您需要的所有数据,并通过ExceptionFilterAttribute 全局处理它。在那里你可以把它变成一个 404 响应。

当然,您可以让最初的异常冒泡到ExceptionFilterAttribute,但是您没有那么多可能让它变得有意义。

【讨论】:

  • 要点,为什么我会抛出异常然后使用异常过滤器变成404响应而不是直接返回NotFound,比如IActionResult response = View("_CustomError"); response.responseCode = 404; return response
  • 因为你写了 我想避免返回 HttpResponseMessage,因为我需要更改 Action 的返回类型。。也因为你不需要在 ControllerContext/有一个 HttpContext 来这样做(例如你可以在你的服务层使用它)。
  • 在 asp.net 团队中有一些关于 HttpExceptions 的讨论,他们认为它是反模式,这就是他们在 mvc 核心中避免它的原因
  • 推理很好:它的控制器负责确定http响应。从另一层这样做违反了 SRP。尽管在许多情况下它只是实用的。
  • 为什么会抛出NotFoundException违反SRP,当这个层被告知要访问一个项目时,却找不到?
【解决方案2】:

您可以使用CreateResponse extension method 并执行以下操作:

return Request.CreateResponse(HttpStatusCode.NotFound, "foobar");

我以前用过HttpStatusCode.NoContent 做类似的事情。这实际上取决于您的业务逻辑是什么以及您希望如何处理这些情况。 NoContent 将导致成功的 http 调用,而 NotFound 将是一个错误。 NotFound 将触发您的默认 MVC 错误页面路由(如果您有该设置),NoContent 不会。这是可以通过正常使用/遍历应用程序的响应,还是仅在恶意用户篡改 url 时才会发生的响应?所有这些都是我在确定要返回的 http 状态代码时考虑的因素。希望这会有所帮助!

【讨论】:

  • 'Request.CreateResponse' 在 asp.net 核心中不存在。我想避免返回 HttpResponseMessage,因为我需要更改 Action 的返回类型。
猜你喜欢
  • 2022-10-02
  • 2017-08-10
  • 2015-04-27
  • 2021-01-08
  • 2021-05-10
  • 2019-10-28
  • 2011-01-21
  • 2015-10-01
  • 1970-01-01
相关资源
最近更新 更多