I have been thinking about the idempotency of POST lately, and the
exchange with Steve Bjorg has prompted me to write about it. My current
direction is to treat a POST of null to a factory resource as
idempotent.
A null POST to a factory resource would create a resource that could be
PUT to safely. Either the null POST or the PUT could be repeated safely
if they time out. I'm cautious about using the POE specification due to
the way that it seems to use up the POST method for the created
resource, and doesn't really define a method for creating the temporary
resource in the first place. Null POST idempotency seems to me to be an
appropriate way of thinking about the problem: Add no state to be
demarcated by a temporary resource, then replace that null state with
the content I would have otherwise POSTed. The PUT also converts the
temporary resource into a resource with a normal lifetime.
Potential issues:
1. Idempotency of null POST
My biggest concern is about encoding the idempotency assumption into the
client. If it happened to be unsafe for a particular server, the client
could trigger unfortunate behaviour. For this reason it may be useful to
introduce a new method that performs this setup. I'm thinking something
like PREPARE might be appropriate.
2. Temporary Resource lifetime
Temporary resources would need to expire after some time to allow the
server to reclaim memory and other... well... resources. I suggest that
a rough timer would be the simplest approach: Sweep every 40s and
destroy temporary resources that are still present from the last sweep.
The exact mechanism and timing would be up to the server.
3. Temporary Resources cleaned up too soon
The client behaviour on seeing a 404 come back from PUT might be an
issue. Did the PUT succeed and has the resource been destroyed by normal
means, or did the resource timeout before a successful PUT? It may be
necessary to prevent a live resource from being converted to a 404 too
quickly. Perhaps keeping a 410 up for at least the normal lifetime of
the temporary would indicate to the client that its earlier PUT was
successful. This temporary resource lifetime would have to be long
enough to ensure all reasonable client activity worked correctly. If the
client sees a 404 it has no option but to return an error to its user
indicating that it doesn't know whether the PUT occured or not.
4. Overconsumption of server-side state
The final question is how to deal with clients that issue too many
PREPARE requests, thereby consuming unreasonable quanitities of
server-side resources. It may be important to impose a maximum PREPARE
rate based on source IP or other request characteristic.
G'day, I have been thinking about the idempotency of POST lately, and the exchange with Steve Bjorg has prompted me to write about it. My current direction is...
... Thanks for the links. Problems with POE: * The specification does not cover how the POE resource is created. Presumably, it is through a POST which could...
... Yes to both. I had another thought the other day: The model I am thinking about to achieve POE is based on the use of Atom and the inclusion of an ID in...
... Breaking the idempotency of GET is very bad ... Why not have a 'factory' GET, that redirects to a new location every time, e.g. --> GET /id/new <-- 302...
... Yes, but a) it is the server's responsibility and b) it is very controlled in this case. (Is there any harm in those HTML pages that show N-times visited ...
... Where does it say that GET is idempotent? My understanding was that GET is "safe," but not necessarily idempotent. Returning a new ID each time you do a...
... http://www.w3.org/Protocols/rfc2616/rfc2616-sec9.html#sec9.1.2 "9.1.2 Idempotent Methods Methods can also have the property of "idempotence" in that (aside...
... Hi Bill, It's not that. The safeness of GET can work against you, if the server is required to issue distinct ids. client A GET -------[cache] ------->...
Bill, ... Yes, that might be a problem (an ill-behaving cache should not confuse other peoples POSTs). ... Yes, but then we have the chicken-egg problem that...
... Not brain dead, it will work, as the point is you don't need a reliable single POST to start a reliable exchange - reliability is introduced using a...
... Well, ok. But this behavior is only appropriate if suggested as part of the spec. It contradicts HTTP in the sense that you as a client should know that...
... I see what you're saying. But if the client doesn't get a response, or gets a non-2xx response what should it do, according to HTTP? cheers Bill...
... At least not go into "Brute Force Retry Mode" :-) But I guess in this case it is ok. For my part, I'll follow the POST- to-POE-collection-factory road....
... Correct. If you're trying to solve this problem in a browser where only GET and POST are allowed then you can use that POST to create a new ID that is used...
... One of my REST design instincts is that whenever I see an ID used as part of a message exchange pattern, I wonder why it isn't a URL. I think ids in...
... Yes, exactly. Currently I am thinking about POST /poe-collection-factory 201 Created Location: /peo-collections/66525 Meaning the client requests the...
... Perhaps. You could guarantee delivery by having the client restart the exchange if the server indicates a timeout (or generally ending the exchange). It's...
... That's intentional :) ... Sending a POST to get the form is one way, but not the only. Another would be to use GET, and assure that the response isn't ...
... I agree. I think POE is sound, formally speaking. The chicken and egg problem I've see is that, because HTTP is asymmetric (clients always initiate), then...
... ... Well, let's start with a base problem statement: I have some state that I want to append to a resource. The right method according to HTTP is POST, but...
... I've found this approach useful in the past, but with a caveat; if you look for a specific value then that would be an implementation dependency. A...
... Yes, I was thinking about taking the POST-and-GET-to-check route instead of a special interaction pattern. In the case of APP this would be even simpler, ...
... But that would be an implementation dependency, so your client wouldn't be reusable with, say, non-APP resources. My approach is generic. ... Then it...
... I'm starting to like this approach. Let me have a go at rephrasing it as a concrete proposal: Problem statement: (same as before) I have some state that I...
... I'm not sure what you mean by "append", but this approach is useful for both POST(a) as well as POST(p). ... That would be more of a message id, which is...
Hmmm not sure if I'm over simplifying but in a nutshell these protocols are just trying to repeatedly POST/PUT to a resource identified by a unique id. I think...