【问题标题】:HTTP code for an error in processing a request处理请求时出错的 HTTP 代码
【发布时间】:2021-02-16 12:45:00
【问题描述】:

假设我们有一个客户端发出的 HTTP 请求。端点存在并且可由客户端访问(这排除了 401、403、404 和 405)。请求有效负载是有效的(这排除了 400)。服务器运行良好,能够处理请求并返回响应(这排除了 5xx)。

错误出现在请求的处理过程中。此类错误的示例可能包括:

  • 业务验证错误。
  • 查询数据库中不存在的实体。假设数据库查找只是请求处理管道的一部分(例如,不是客户端请求本身)。
  • 处理原始客户端请求的服务器发出内部 HTTP 请求失败。在这种情况下,处理服务器正常运行,而内部 HTTP 请求可能返回 5xx。假设内部 HTTP 请求只是请求处理管道的一部分(例如,不是客户端请求本身)。

为这些响应分配的适当 HTTP 代码是什么?

我见过 API 文档使用 402 (Stripe) 和 422 (PayPal),但我还没有遇到任何明确的内容。

欢迎来自社区的想法!谢谢。

【问题讨论】:

    标签: api rest express http


    【解决方案1】:

    为这些响应分配的适当 HTTP 代码是什么?

    两个重要的想法

    首先 - 您的 API 是一个外观,旨在使您的服务/业务逻辑/等看起来只是另一个符合 HTTP 的文档存储(也称为“统一接口”约束)。出于设计您的响应的目的,您的资源的具体性质和实施细节并不重要。

    第二 - 状态码的重点是通用组件(想想浏览器、网络缓存、反向代理、蜘蛛......)如何理解该状态码。我们正在尝试帮助这些组件对响应的性质进行广泛分类。 (这就是为什么 5xx 类中的代码相对较少的原因之一;如果服务器处理请求失败,通用组件可以做的改变并不多)。

    事情是这样的:如果两个状态代码的通用处理没有显着不同。 403 Forbidden409 Conflict 具有与之相关的不同语义,但这些代码的标准化处理差异(如果有的话)非常微妙。

    您应该努力使 4xx 与 5xx 正确。准确识别要使用的 4xx 代码通常不太重要。


    业务验证错误

    这里的常见选择是409 Conflict(您的请求与我的数据副本不一致)或403 Forbidden(我理解您的请求,但我不会满足它)。

    如果问题是请求本身中的数据(即:有人提交了错误的表单),您更有可能看到 422 Unprocessable Entity(是的,我接受 application/json,但不接受 this 应用程序/json)。


    查询数据库中不存在的实体。

    实现细节无关紧要;能否将问题追溯到 HTTP 请求?

    如果问题追溯到 URI(我们解析目标 uri 以获取一些信息,并使用该信息在我们的数据存储中查找信息),那么404 Not Found 通常是一个不错的选择。如果问题追溯到请求的正文(我们希望表单中的某些选项与枚举列表中的条目匹配,但事实并非如此),那么409 Conflict 是合理的。

    如果服务器的数据完全发出,那么您可能正在查看500 Internal Server Error


    处理原始客户端请求的服务器发出失败的内部 HTTP 请求。

    服务器无法连接到其他 HTTP 服务器纯粹是实现细节,例如无法连接到数据库或文件系统。

    除非失败是由于请求中的信息造成的,否则您最终会得到500 Internal Server Error

    【讨论】:

      【解决方案2】:

      这可能是使用自定义错误响应代码的地方,只要您尊重已经定义的响应代码。例如,您可以将 600 定义为您的响应代码,并在您的 API 文档中详细指定这些自定义代码的含义。有关所有现有代码的更多信息,我会参考 Iana:http://www.iana.org/assignments/http-status-codes/http-status-codes.xhtml

      现在,如果您的目标是保持在现有的 http 响应范围内,我会推荐以下内容:

      • 无法处理的故障:状态 422
      • 授权失败:状态 403

      无法处理可能意味着很多事情,例如上述业务验证错误。

      【讨论】:

        【解决方案3】:

        业务验证错误。

        这可能是 400、422、403、409,具体取决于业务验证的含义。

        查询数据库中不存在的实体。假设数据库查找只是请求处理管道的一部分(例如,不是客户端请求本身)。

        听起来像 400、409 或 422。

        处理原始客户端请求的服务器发出失败的内部 HTTP 请求。在这种情况下,处理服务器正常运行,而内部 HTTP 请求可能返回 5xx。假设内部 HTTP 请求只是请求处理管道的一部分(例如,不是客户端请求本身)。

        客户端不知道/不关心内部 http 请求。关键是它失败了,这是一个错误/系统故障,所以这是一个 5xx 错误。

        选择 HTTP 状态码时要记住的最重要的一点是:

        1. 确保您的通用类正确,因此 4xx 和 5xx 取决于此是客户端/服务器错误。
        2. 如果您需要更具体的内容,请问问自己为什么。如果您的客户收到 400 或 409,是否能够做出更好的决定?如果不是,也许它并不那么重要。

        我写了很多关于错误代码 here 的文章,建议你阅读一堆 4xx 条目。

        还有来自 HTTP 标准的作者之一的出色 blog post,它更多地表明为案例找到完美的状态代码并不那么重要

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2016-04-18
          • 1970-01-01
          • 1970-01-01
          • 2016-09-07
          • 2017-12-30
          • 1970-01-01
          • 2016-03-20
          相关资源
          最近更新 更多