HTTP 200或404是否为空列表?

时间:2015-05-13 14:25:25

标签: rest http http-status-codes

我知道这是一个相当常见的问题,但我找不到满足我的答案。

我现在已经使用django rest框架了一段时间,但除了给出的示例之外,这几乎是无关紧要的。它的默认行为是在访问具有空列表项的路由时返回带有空列表资源的HTTP 200。 例如:如果我们有/articles/这样的路线来访问文章列表但它不包含任何项目我们会得到如下json的响应:

{"count":0, "next":null, "previous":null, "items": []}

哪个非常好。我们在/ articles /中找到了我们要查找的资源,它恰好没有任何项目。

如果我们访问路线/articles/?page=1,我们会得到完全相同的回复。

到目前为止一切顺利。现在我们尝试访问/articles/?page=2,响应代码也会发生变化。现在得到一个404,就好像找不到资源一样,错误消息说该页面没有结果。与?page = 1 ...

的情况相同

我对这种行为非常满意,但今天我开始质疑这个设计。 ?page=1案例与?page=2的情况有何不同?还有什么,你怎么知道这个请求是否有效"何时发出HEAD请求?在包含任何结果的意义上是有效的。

这在过滤列表检查特定字段的可用性(例如向HEAD发出/users/?username=ted请求)的情况下非常有用。

  • 200响应显然意味着理解请求并找到了项目。
  • 404意味着请求被理解,但在该位置/ URI没有找到任何项目(AFAIK查询参数也是URI的一部分)
  • 如果无法理解请求,将返回400语法错误,并返回422语义错误。

这是一个好设计吗?为什么大多数人似乎不同意它并且有什么缺点?

4 个答案:

答案 0 :(得分:11)

我会选择200因为资源是articles。 虽然ted中的users查询同样适用,但users是资源,只要它存在,我200就可以了。 如果您GET users/ted 404,那么410 (GONE)dhcp-uris-3626:foundation johndcowan$ sass --watch ruby(3631,0x7fff7d721300) malloc: *** error for object 0x7faac2801808: incorrect checksum for freed object - object was probably modified after being freed. *** set a breakpoint in malloc_error_break to debug Abort trap: 6 一样好,如果过去有一个名为ted的用户(可能更适用于文章而不是用户)。

答案 1 :(得分:3)

  1. 因为我们可以使用空的page1,所以没有空的page2。
  2. 这是由UI考虑因素驱动的(第1页必须存在!),然而,它决定了响应代码。

答案 2 :(得分:0)

200只表示请求已成功。响应返回的信息取决于请求中使用的方法,例如:  GET在响应中发送与所请求资源相对应的实体;

HEAD对应于所请求资源的实体标题字段在响应中发送,没有任何消息体;

POST一个描述或包含行动结果的实体;

跟踪包含终端服务器收到的请求消息的实体。 404 - 服务器没有找到与Request-URI匹配的任何内容 - 在这种情况下,我认为这意味着我们没有找到列出文章的页面。 那就是200。 - 但也许可以理解返回的内容并格式化已经返回0篇文章的消息。

答案 3 :(得分:0)

这实际上归结为“null vs 空集合”论点。 null 的情况也是 HTTP 404 的情况,空集合的情况也是 HTTP 200 的情况。

<块引用>

如果我们有一个诸如 /articles/ 之类的路由来访问文章列表但它不包含任何项目

假设这是一个全局的文章列表,即:

<块引用>

http://mywebsite/articles

那么这个响应永远不能为空,因此永远不应该是 404。文章的全局列表总是存在的,因此集合总是非空的,无论它是否包含元素。

这里的一个简单示例是考虑 SQL 查询。如果表存在,即使是空的,查询也会返回结果(无论是否为空),所以使用200。如果表本身不存在,你会得到一个查询错误,所以404。< /p>

但是如果文章包含在另一个资源中,例如他们的作者:

<块引用>

http://mywebsite/authors/johndoe/articles

现在我们进入了 null(因此 404)可能有意义的部分。

  • 如果 johndoe 存在并且有文章,则返回一个非空列表
  • 如果 johndoe 存在并且没有文章,则返回一个空列表和 HTTP 状态 200
  • 如果 johndoe 不存在,则返回 null 和 HTTP 状态 404

这会向用户传达正确的响应。 200 表明数据被正确获取,而 404 表明所请求的资源根本不存在。


请注意,在引用特定文章而不是列表时,这略有不同。当返回特定资源(或不返回)而不是列表时,404 是“无项目”响应的唯一正确 HTTP 状态。

<块引用>

http://mywebsite/article/1

在这里,您要么返回文章,要么返回null

<块引用>

http://mywebsite/authors/johndoe/articles/1

在这里,当 作者 johndoe 或文章 1 不存在时,您将返回 404。