tags:

views:

202

answers:

4

Why does an HTTP PUT request have to contain a representation of a 'whole' state and can't just be a partial?

I understand that this is the existing definition of PUT - this question is about the reason(s) why it would be defined that way.

i.e:

What is gained by preventing partial PUTs?

Why was preventing idempotent partial updates considered an acceptable loss?

A: 

Because, I guess, this would have translated in inconsistent "views" when multiple concurrent clients access the state. There isn't a "partial document" semantics in REST as far as I can tell and probably the benefits of adding this in face of the complexity of dealing with that semantics in the context of concurrency wasn't worth the effort.

If the document is big, there is nothing preventing you from building multiple independent documents and have an overarching document that ties them together. Furthermore, once all the bits and pieces are collected, a new document can be collated on the server I guess.

So, considering one can "workaround" this "limitations", I can understand why this feature didn't make the cut.

jldupont
Apologies - I don't understand the point about inconsistent views produced by partial idempotent updates differing in behaviour from 'full' idempotent updates. I am also uncertain as to the suggested increase in complexity, from a protocol definition point of view.
Mike
A: 

One reason might be that the reason for partial GETs, is because an initial get for the whole document was interrupted part way, so the client can attempt to fetch the missing portion, but in the case of a PUT, the server has no way to reconnect with the client to fetch the portion of the document that was not yet recieved.

Semantically, PUT is normally considered a new document, with its own ID, which the server returns to the client once the put completes. PUT doesn't have an obvious way to amend documents, only to add new documents (possibly at a preexisting resource)

TokenMacGuy
PUT is considered update to an existing resource, POST is creating new resource. RFC 2616 specifies exactly the operations for POST and PUT. Paragraph 2.5, POST method requests the enclosed entity to be accepted as a new subordinate of the requested URL. Pargraph 2.6, PUT method requests the enclosed entity to be stored at the specified URL
Franci Penov
+4  A: 
Jan Algermissen
Hi Jan, as I said already; "I understand that this is the existing definition of PUT - this question is about the reason(s) why it would be defined that way". Your example in the 2nd paragraph implies that the partial update is non-idempotent - obviously this is what PATCH is for. I am interested in *idempotent* partial updates - i.e. a partial PUT.
Mike
Hi Mike, see my edit to my answer.
Jan Algermissen
Note that PATCH is defined only in HTTP 1.0 (RFC 2068) and is removed (along with LINK/UNLINK) from HTTP 1.1.
Franci Penov
PATCH is being re-added. Also; Jan - idempotency doesn't need to depend on any specific set of media types with regard to its definition in the protocol, the semantics of a method are a function of it's definition as part of a uniform interface.. I'm still struggling to work out what is actually lost by changing the definition of PUT to something as simple as 'an idempotent change of state' (i.e. one that doesn't prevent partials).
Mike
@Mike, as I tried to explain above: You cannot define a partial update to be idempotent without taking the particular media type into account. The idempotency depends on the media type used and since you cannot define method semantics to depend on media type semantics, an update can only be idempotent for the general case if it is a full replacement. A method that specifies a partial update MUST be defined non-idempotent. IOW, you simply cannot ever define an "'an idempotent change of state' (i.e. one that doesn't prevent partials)". It is a contradiction in itself.
Jan Algermissen
@Franci, here is the PATCH I-D: http://tools.ietf.org/html/draft-dusseault-http-patch
Jan Algermissen
@Mike, here is another way to state my point: If the final state of the resource is not explicit in the message semantics then the final state of the resource depends on its current state. If that is the case, a message can never be idempotent because we can never say that sending it N times will result in a certain state. The state after N requests depends always on a prior resource state. Hence only methods that are definitive about the final state can be idempotent. Partial update semantics can never be. Better now?
Jan Algermissen
If the partial update request effects the portion of the resource it is aimed at in the same way every time then the request is idempotent. No?
Mike
"The idempotency depends on the media type used and since you cannot define method semantics to depend on media type semantics" - The idempotency does not depend on the media type; every PUT request would be idempotent. What would depend on the media type is discerning whether or not the request is a partial or not; but this would not conflict with a definition of PUT as "an idempotent change of state".
Mike
@Mike, how do you know that the effect is aimed the same way every time? How do you know what the state of the resource will be after your partial update? Maybe it helps if you try to write the definition of your PUTPARTIAL method? E.g. "The PUTPARTIAL method requests that the enclosed entity....". What would you write?
Jan Algermissen
A: 

Short answer: ACIDity of the PUT operation and the state of the updated entity.

Long answer:

RFC 2616 : Paragraph 2.5, "POST method requests the enclosed entity to be accepted as a new subordinate of the requested URL". Paragraph 2.6, "PUT method requests the enclosed entity to be stored at the specified URL".

Since every time you execute POST, the semantic is to create a new entity instance on the server, POST constitutes an ACID operation. But repeating the same POST twice with the same entity in the body still might result in different outcome, if for example the server has run out of storage to store the new instance that needs to be created - thus, POST is not idempotent.

PUT on the other hand has a semantic of updating an existing entity. There's no guarantee that even if a partial update is idempotent, it is also ACID and results in consistent and valid entity state. Thus, to ensure ACIDity, PUT semantic requires the full entity to be sent. Even if it was not a goal for the HTTP protocol authors, the idempotency of the PUT request would happen as a side effect of the attempt to enforce ACID.

Of course, if the HTTP server has close knowledge of the semantic of the entities, it can allow partial PUTs, since it can ensure through server-side logic the consistency of the entity. This however requires tight coupling between the data and the server.

Franci Penov
"There's no guarantee that even if a partial update is idempotent, that it is also atomic" - Hmm, I don't understand that. How might an idempotent update be non-atomic?
Mike
I implied ACIDness when I said atomicity. In other words, I consider an operation "atomic" if at the end of it the entity is in valid and consistent state. Should've used ACID explicitly instead of atomic.
Franci Penov