Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to enforce that HTTP client uses conditional requests for updates?

Tags:

rest

http

In a (proper RMM level 3) RESTful HTTP API, I want to enforce the fact that clients should make conditional requests when updating resources, in order to avoid the lost update problem. What would be an appropriate response to return to clients that incorrectly attempt unconditional PUT requests?

I note that the (abandoned?) mod_atom returns a 405 Method Not Allowed with an Allow header set to GET, HEAD (view source) when an unconditional update is attempted. This seems slightly misleading - to me this implies that PUT is never a valid method to attempt on the resource. Perhaps the response just needs to have an entity body explaining that If-Match or If-Unmodified-Since must be used to make the PUT request conditional in which case it would be allowed?

Or perhaps a 400 Bad Request with a suitable explanation in the entity body would be a better solution? But again, this doesn't feel quite right because it's using a 400 response for a violation of application specific semantics when RFC 2616 says (my emphasis):

The request could not be understood by the server due to malformed syntax.

But than again, I think that using 400 Bad Request for application specific semantics is becoming a widely accepted pragmatic solution (citation needed!), and I'm just being overly pedantic.

like image 591
Day Avatar asked Sep 12 '25 18:09

Day


2 Answers

Following Jan's request for clarification on 27th September 2011, the HTTPbis working group published a new Internet-Draft on 18th October 2011, with the brand new 428 Precondition Required status, specifically to address the situation described in my question.

As of April 2012, this is now published as RFC 6585 (Additional HTTP Status Codes - an update of RFC 2616 (HTTP/1.1)). Full quote of section 3:

428 Precondition Required

The 428 status code indicates that the origin server requires the request to be conditional.

Its typical use is to avoid the "lost update" problem, where a client GETs a resource's state, modifies it, and PUTs it back to the server, when meanwhile a third party has modified the state on the server, leading to a conflict. By requiring requests to be conditional, the server can assure that clients are working with the correct copies.

Responses using this status code SHOULD explain how to resubmit the request successfully. For example:

HTTP/1.1 428 Precondition Required
Content-Type: text/html

<html>
   <head>
      <title>Precondition Required</title>
   </head>
   <body>
      <h1>Precondition Required</h1>
      <p>This request is required to be conditional;
      try using "If-Match".</p>
   </body>
</html>

Responses with the 428 status code MUST NOT be stored by a cache.

Prior to the introduction of this new status code, Julian Reschke (a member of the HTTPbis working group) had recommended using a 403 Forbidden for the situation that is now covered by 428.

like image 77
Day Avatar answered Sep 15 '25 08:09

Day


To my best knowledge, this is not properly defined.

I requested clarification: http://lists.w3.org/Archives/Public/ietf-http-wg/2011JulSep/0515.html

like image 41
Jan Algermissen Avatar answered Sep 15 '25 09:09

Jan Algermissen