Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What is the proper REST response code for a valid request but an empty data?

For example you run a GET request for users/9 but there is no user with id #9. Which is the best response code?

  • 200 OK
  • 202 Accepted
  • 204 No Content
  • 400 Bad Request
  • 404 Not Found
like image 382
IMB Avatar asked Jul 31 '12 18:07

IMB


People also ask

Should I return a 404 or empty list?

If you are expecting list of user object, the best solution is returning an empty list ([]) with 200 OK than using a 404 or a 204 response.

Can an HTTP response be empty?

The "empty reply from server" error indicates that a zero length response was received - no HTTP headers or content, simply a closed TCP connection with no HTTP payload transmitted. One common cause of this problem is attempting to make a plain HTTP request against the HTTPS (TLS / SSL) web server port.

Should Put return 200 or 204?

200 OK - This is the most appropriate code for most use-cases. 204 No Content - A proper code for updates that don't return data to the client, for example when just saving a currently edited document. 202 Accepted - If the update is done asynchronous, this code can be used.

What is a 204 response?

The HTTP 204 No Content success status response code indicates that a request has succeeded, but that the client doesn't need to navigate away from its current page. This might be used, for example, when implementing "save and continue editing" functionality for a wiki site.


2 Answers

I strongly oppose 404 in favour of 204 or 200 with empty data. Or at least one should use a response entity with the 404.

The request was received and properly processed - it did trigger application code on the server, thus one cannot really say that it was a client error and thus the whole class of client error codes (4xx) is not fitting.

More importantly, 404 can happen for a number of technical reasons. E.g. the application being temporarily deactivated or uninstalled on the server, proxy connection issues and whatnot.

Sure, the 5xx error class exists for such cases, but in reality the affected middleware components often have no way to know that the error is on their side and then just assume that the error is on the client side, and then respond with a 404 instead of 500/503.

Therefore based on the status code alone the client cannot distinguish between a 404 that means "empty result set" and a 404 that means "something is seriously wrong, report this error to the ops team".

This can be fatal: Imagine an accounting service in your company that lists all the employees that are due to an annual bonus. Unfortunately, the one time when it is called it returns a 404. Does that mean that no-one is due for a bonus, or that the application is currently down for a new deployment?

-> For applications that need to know that a requested resource positively does not exist instead of just being temporarily unaccessible, 404 without response entity therefore is pretty much a no-go.

Also, many client frameworks respond to a 404 by throwing an exception with no further questions asked. This forces the client developer to catch that exception, to evaluate it, and then to decide based on that whether to log it as an error that is picked up by e.g. a monitoring component or whether to ignore it. That doesn't seem pretty to me either.

The advantage of 404 over 204 is that it can return a response entity that may contain some information about why the requested resource was not found. But if that really is relevant, then one may also consider using a 200 OK response and design the system in a way that allows for error responses in the payload data. Alternatively, one could use the payload of the 404 response to return structured information to the caller. If he receives e.g. a html page instead of XML or JSON that he can parse, then that is a good indicator that something technical went wrong instead of a "no result" reply that may be valid from the caller's point of view. Or one could use a HTTP response header for that.

Still i would prefer a 204 or 200 with empty response though. That way the status of the technical execution of the request is separated from the logical result of the request. 2xx means "technical execution ok, this is the result, deal with it".

I think in most cases it should be left to the client to decide whether an empty result is acceptable or not. By returning 404 without response entity despite of a correct technical execution the client may decide to consider cases to be errors that simply are no errors.

Another quick analogy: Returning 404 for "no result found" is like throwing a DatabaseConnectionException if a SQL query returned no results. It can get the job done, but there are lots of possible technical causes that throw the same exception which then would be mistaken for a valid result.

Another perspective: From an operations point of view a 404 may be problematic. Since it can indicate a connectivity problem rather than a valid service response, i would not want a fluctuating number of "valid" 404s in my metrics/dashboards that might conceal genuine technical issues that should be investigated and fixed.

Edit: Wow, this has caused a lot of controversy. Here is another argument against 404: Strictly from a HTTP spec (RFC7231) point of view, 404 does not even mean that a resource does not exist. It only means that the server has no current representation of the requested resource available, and this even may be only temporary. So strictly by HTTP spec, 404 is inherently unreliable regarding the nonexistence of a requested thing. If you want to communicate that the requested thing positively does not exist, do not use 404.

like image 112
Jens Wurm Avatar answered Sep 21 '22 04:09

Jens Wurm


TL;DR: Use 404

See This Blog. It explains it very well.

Summary of the blog's comments on 204:

  1. 204 No Content is not terribly useful as a response code for a browser (although according to the HTTP spec browsers do need to understand it as a 'don't change the view' response code).
  2. 204 No Content is however, very useful for ajax web services which may want to indicate success without having to return something. (Especially in cases like DELETE or POSTs that don't require feedback).

The answer, therefore, to your question is use 404 in your case. 204 is a specialized reponse code that you shouldn't often return to a browser in response to a GET.

The other response codes that are even less appropriate than 204 and 404:

  1. 200 should be returned with the body of whatever you successfully fetched. Not appropriate when the entity you're fetching doesn't exist.
  2. 202 is used when the server has begun work on an object but the object isn't fully ready yet. Certainly not the case here. You haven't begun, nor will you begin, construction of user 9 in response to a GET request. That breaks all sorts of rules.
  3. 400 is used in response to a poorly formatted HTTP request (for instance malformed http headers, incorrectly ordered segments, etc). This will almost certainly be handled by whatever framework you're using. You shouldn't have to deal with this unless you're writing your own server from scratch. Edit: Newer RFCs now allow for 400 to be used for semantically invalid requests.

Wikipedia's description of the HTTP status codes are particularly helpful. You can also see the definitions in the HTTP/1.1 RFC2616 document at www.w3.org

like image 33
Chris Pfohl Avatar answered Sep 21 '22 04:09

Chris Pfohl