使用 HTTP 状态来传达应用程序情况
The use of HTTP status to communicate application circumstances
假设我向犯罪登记册提问:http://server/demographics/party/{partyId} 而那个人在该系统上不为人所知。
那是一个错误吗?这不是好事吗?
当 returning 404 时,它是一个错误代码,Restlet 已将其实现为特定的 URL 无法解析为到服务器资源的路由(处理 class), 一个错误的情况。
在我看来,如果系统理解一个调用,并且能够无误地处理它,它应该 return 200 (HTTP-ok),并且它应该 return 信息: "We don't know this person".
最好的事情是什么?
return404 状态代码没有任何错误。它只是意味着 "you asked for a resource, and it doesn't exist"。如果它执行 return 200,它必须以某种方式 return 一个额外的状态代码,告诉您一切正常,但找不到资源。这是不必要的,因为 404 已经是那个意思了。
状态 500 通常 return 表示 "something went wrong, I can't tell you if the resource exists or not"。现在,如果您 return 将 404 表示为那个意思,那将是一个错误。
它是好是坏与 HTTP 或 REST 没有任何关系。顺便说一句,如果登记册是一份包含灾难幸存者的文件,你可能会发现找不到你要找的人是很糟糕的,除非这个人是你的岳母,除非你真的爱你的岳母. (这是一个玩笑,对于那些不明白的人)。
Web 服务可以以产生任何一种响应的方式实现。
如果它的实施方式更符合 HTTP/Rest,那么“404 未找到”将是未找到内容的适当响应。这就是 404 状态的用途。
将您的请求视为 'I assume this record exists, and I want to see it',将 404 响应视为 'You are in error that record does not exist'。
可能会有所帮助
如果这个 URL 将被代码使用(而不是在浏览器中显示),那么如果您不区分响应状态,那么您将不得不添加额外的信息到响应正文以使差异明显。
如果这个 URL 将在浏览器中显示给用户,那么服务器仍然能够在响应正文中显示 404 的内容。
请阅读:http://archive.oreilly.com/pub/post/restful_error_handling.html#__federated=1
引用:
结论:
- 人类可读的错误消息:基于 REST 的 Web 服务的主要吸引力之一是您可以打开任何浏览器,输入正确的 URL,然后立即看到响应——无需特殊工具。但是,HTTP 错误代码并不总是提供足够的信息。例如,如果我们采用上面的选项 1,并请求无效的图书 ID,我们将返回 404 错误代码。从开发人员的角度来看,我们是否真的输入了错误的主机名或无效的图书 ID?目前还不清楚。在选项 3 (DAS) 中,我们得到一个没有任何信息的空白页面。要查看实际的错误代码,您需要 运行 网络嗅探器,或通过代理指向您的浏览器。由于所有这些原因,我认为选项 4 有很多好处。它显着降低了新开发人员的门槛,并使与 Web 服务相关的所有信息都可以在 Web 浏览器中直接查看。
- 特定于应用程序的错误:选项 1 的缺点是无法在浏览器中直接查看。它还具有将所有 HTTP 错误代码映射到应用程序特定错误代码的额外缺点。 HTTP 状态代码特定于文档检索和发布,这些可能不会直接映射到您的应用程序域。例如,其中一个 DAS 错误代码与无效的基因组坐标相关(序列坐标超出 bounds/invalid)。在这种情况下,我们将映射到什么 HTTP 错误代码?
- 机器可读的错误代码:作为第三个标准,错误代码应该很容易被其他应用程序读取。例如,XooMLe 应用程序 return 仅返回人类可读的错误消息,例如"Invalid Google API key supplied"。解析 XooMLe 响应的应用程序必须搜索此特定错误消息,而这可能非常脆弱——例如,XooMLe 服务器可能只是将消息更改为 "Invalid Key Supplied"。错误代码,例如 DAS 提供的代码,对于编程控制和轻松创建异常非常重要。例如,如果 XooMLe returned 一个 1001 错误代码,客户端应用程序可以进行快速查找并立即抛出 InvalidKeyException。
根据这三个标准,这是我对最佳错误处理选项的投票:
- 使用 HTTP 状态代码来解决与 HTTP 相关的问题,而不是与您的 Web 服务相关的问题。
- 发生错误时,总是 return 详细说明错误的 XML 文档。
- 确保 XML 错误文档包含错误代码和人类可读的错误消息。例如:
1001
提供的 Google API 密钥无效
通过遵循这三个简单的做法,您可以让其他人更轻松地使用您的服务,并在出现问题时做出反应。新开发人员可以通过简单的 Web 浏览器轻松查看有效和无效请求,并且程序可以轻松(并且更稳健)提取错误代码并采取适当的行动。
Amazon.com 网络服务 API 遵循 returned XML 文档的方法可以指定一个 ErrorMsg 元素。
XooMLe 也遵循这种方法。 (XooMLe 为现有的基于 Google API 的 SOAP 提供了一个 RESTful API 包装器)。
另一种方法是通过 DAS(分布式注释系统),如果没有 HTTP-error,它总是 returns 200,并且在 HTTP-header 中有错误信息,这是不太有利的,因为它不是人类可读,因为浏览器不显示 HTTP-header.
假设我向犯罪登记册提问:http://server/demographics/party/{partyId} 而那个人在该系统上不为人所知。 那是一个错误吗?这不是好事吗?
当 returning 404 时,它是一个错误代码,Restlet 已将其实现为特定的 URL 无法解析为到服务器资源的路由(处理 class), 一个错误的情况。
在我看来,如果系统理解一个调用,并且能够无误地处理它,它应该 return 200 (HTTP-ok),并且它应该 return 信息: "We don't know this person".
最好的事情是什么?
return404 状态代码没有任何错误。它只是意味着 "you asked for a resource, and it doesn't exist"。如果它执行 return 200,它必须以某种方式 return 一个额外的状态代码,告诉您一切正常,但找不到资源。这是不必要的,因为 404 已经是那个意思了。
状态 500 通常 return 表示 "something went wrong, I can't tell you if the resource exists or not"。现在,如果您 return 将 404 表示为那个意思,那将是一个错误。
它是好是坏与 HTTP 或 REST 没有任何关系。顺便说一句,如果登记册是一份包含灾难幸存者的文件,你可能会发现找不到你要找的人是很糟糕的,除非这个人是你的岳母,除非你真的爱你的岳母. (这是一个玩笑,对于那些不明白的人)。
Web 服务可以以产生任何一种响应的方式实现。
如果它的实施方式更符合 HTTP/Rest,那么“404 未找到”将是未找到内容的适当响应。这就是 404 状态的用途。
将您的请求视为 'I assume this record exists, and I want to see it',将 404 响应视为 'You are in error that record does not exist'。
可能会有所帮助如果这个 URL 将被代码使用(而不是在浏览器中显示),那么如果您不区分响应状态,那么您将不得不添加额外的信息到响应正文以使差异明显。
如果这个 URL 将在浏览器中显示给用户,那么服务器仍然能够在响应正文中显示 404 的内容。
请阅读:http://archive.oreilly.com/pub/post/restful_error_handling.html#__federated=1
引用:
结论:
- 人类可读的错误消息:基于 REST 的 Web 服务的主要吸引力之一是您可以打开任何浏览器,输入正确的 URL,然后立即看到响应——无需特殊工具。但是,HTTP 错误代码并不总是提供足够的信息。例如,如果我们采用上面的选项 1,并请求无效的图书 ID,我们将返回 404 错误代码。从开发人员的角度来看,我们是否真的输入了错误的主机名或无效的图书 ID?目前还不清楚。在选项 3 (DAS) 中,我们得到一个没有任何信息的空白页面。要查看实际的错误代码,您需要 运行 网络嗅探器,或通过代理指向您的浏览器。由于所有这些原因,我认为选项 4 有很多好处。它显着降低了新开发人员的门槛,并使与 Web 服务相关的所有信息都可以在 Web 浏览器中直接查看。
- 特定于应用程序的错误:选项 1 的缺点是无法在浏览器中直接查看。它还具有将所有 HTTP 错误代码映射到应用程序特定错误代码的额外缺点。 HTTP 状态代码特定于文档检索和发布,这些可能不会直接映射到您的应用程序域。例如,其中一个 DAS 错误代码与无效的基因组坐标相关(序列坐标超出 bounds/invalid)。在这种情况下,我们将映射到什么 HTTP 错误代码?
- 机器可读的错误代码:作为第三个标准,错误代码应该很容易被其他应用程序读取。例如,XooMLe 应用程序 return 仅返回人类可读的错误消息,例如"Invalid Google API key supplied"。解析 XooMLe 响应的应用程序必须搜索此特定错误消息,而这可能非常脆弱——例如,XooMLe 服务器可能只是将消息更改为 "Invalid Key Supplied"。错误代码,例如 DAS 提供的代码,对于编程控制和轻松创建异常非常重要。例如,如果 XooMLe returned 一个 1001 错误代码,客户端应用程序可以进行快速查找并立即抛出 InvalidKeyException。
根据这三个标准,这是我对最佳错误处理选项的投票:
- 使用 HTTP 状态代码来解决与 HTTP 相关的问题,而不是与您的 Web 服务相关的问题。
- 发生错误时,总是 return 详细说明错误的 XML 文档。
- 确保 XML 错误文档包含错误代码和人类可读的错误消息。例如: 1001 提供的 Google API 密钥无效
通过遵循这三个简单的做法,您可以让其他人更轻松地使用您的服务,并在出现问题时做出反应。新开发人员可以通过简单的 Web 浏览器轻松查看有效和无效请求,并且程序可以轻松(并且更稳健)提取错误代码并采取适当的行动。 Amazon.com 网络服务 API 遵循 returned XML 文档的方法可以指定一个 ErrorMsg 元素。 XooMLe 也遵循这种方法。 (XooMLe 为现有的基于 Google API 的 SOAP 提供了一个 RESTful API 包装器)。 另一种方法是通过 DAS(分布式注释系统),如果没有 HTTP-error,它总是 returns 200,并且在 HTTP-header 中有错误信息,这是不太有利的,因为它不是人类可读,因为浏览器不显示 HTTP-header.