top | item 6187811

Let's remove verbs from HTTP 2.0

113 points| bslatkin | 12 years ago |onebigfluke.com

136 comments

order
[+] tl|12 years ago|reply
Arguing to replace a well-defined single idiom (verbs) with some arbitrary combination of URI, custom headers, request body contents is exactly the opposite of what you want. Using defined verbs instead of having each site do their own slightly different thing makes APIs easier to discover / consume.

Also, I feel like "Execution in the Kingdom of Nouns" is semi-relevant here: http://steve-yegge.blogspot.com/2006/03/execution-in-kingdom...

[+] ianb|12 years ago|reply
> Arguing to replace a well-defined single idiom (verbs) with some arbitrary combination of URI, custom headers, request body contents is exactly the opposite of what you want.

It may not be what you want, but it is what you'll get. It's what you'll get now, and in the future. There isn't much in the way of discoverable APIs that adhere to the data model suggestion in the HTTP spec, and that's becoming more true as time goes on. As HTTP APIs become more popular they have become less normalized. It's natural: if you want to expose something, you want to expose it as it is. Not many things adhere to the verb structure of HTTP, I'm not sure anything does unless it was designed to be HTTP from the ground up – which isn't how you should design an API, you should design it to do something useful from the ground up.

[+] metaphorm|12 years ago|reply
I think the argument was to remove just the unused verbs. I think GET, POST, and HEAD are the ones that make up 99.9% of all use on the web and those are the ones the author thinks should be the only verbs in HTTP.
[+] generj|12 years ago|reply
"Execution in the Kingdom of Nouns" is excellent. Anyone who hasn't read it should do so immediately.

I want some expansion of verbs, counterbalanced with the elimination of some of the less useful verbs.

The focus should be towards forcing webbrowsers away from GET and POST.

OPTIONS should be made mandatory.

[+] manarth|12 years ago|reply
"Practically speaking there are only two HTTP verbs: read and write, GET and POST."

And thus spoke someone who has never built a REST API, never used curl -I, and probably hasn't used anything other than a web browser to access HTTP content.

Sure, for the most part, we're all kinda new to REST, and we're slowly learning to construct good REST architecture. Sure, there's some redundant weird shit like SPACEJUMP. But we should aim to improve education and encouragement of the use of verbs such as PUT and DELETE, rather than abandon best practice because "no-one's going to use it" or YAGNI, when we can clearly see in talk after expert talk that these are the practices that are being recommended and already put to good use.

Not to mention the plethora of proxies, web servers, and tools that already support these accepted, recognised, standards-defined techniques.

[+] dewitt|12 years ago|reply
"And thus spoke someone who has never built a REST API"

Here are Brett's projects: http://www.onebigfluke.com/

Maybe you've heard of some of them? PubSubHubbub, Google App Engine, Camlistore, Google Consumer Surveys.

[+] seiji|12 years ago|reply
In my mind, two HTTP methods exist: encode things in the URI or encode things in the body of a request.

Go read the RFC definition of PUT and report back. I can never understand it. If anything, PUT needs to be retired in favor of something unambiguously specific like CREATE. In fact, why not go all the way and make all HTTP methods just CREATE, READ, UPDATE, DELETE? That's the only change I (as a nobody) could get behind.

We're not kinda new to REST. REST has formally been around since 2000 and people have been using it heavily since a little before 2008.

Browsers seem to not want to support anything other than GET/POST in forms, so we hack it with running other methods over GET with _method params. Why bother? Just use GET/POST and let the endpoint denote what your intentions are, then have the server side code validate, perform the operations, return results, etc.

(Still rambling: I think one reason REST methods (not URL structure) bother me is it allows lazy (or inexperienced, or incapable) server side programmers to just allow what the client wants. Oh, the client wants to DELETE? Sure. They know what they're doing. No ACL/ownership checks needed). Removing the ability of the client to forcefully say "CREATE/DELETE" may (may) remind the programmer (who is in an outsourced operation in CantProgramistan) they are responsible for the data, not the client asking (asking, not demanding) for operations on the data.)

[+] josephscott|12 years ago|reply
Spoken like someone who has never looked at any of the other stuff that Brett Slatkin has worked on. PubSubHubbub to name just one.
[+] YellowRex|12 years ago|reply
These best part of the post is Tim Bray's response, where he says he would keep PUT and DELETE because they're idempotent, but declined to defend the rest.
[+] thezilch|12 years ago|reply
Huh? DELETE is rarely necessary nor semantic in HTTP. Personally, it's usually more often...

  -d"status=0" /document/<id>/
Even on an FS, you are more likely semantically switching off its visibility or its fd and not necessarily destroying the underlying bits. The resources are then collected and destroyed at a later and in batch, kept forever in a deactivated state, or written over.

And PUT is often a disaster, because few resources show all its properties in public, and if you're not replacing the resource, is PUT the right semantic?

[+] dragonwriter|12 years ago|reply
I can't agree with the assertion that the methods defined in HTTP since 1.0 are bike-shedding. I'll agree that lots of the the HTTP methods defined in standards other than HTTP are unnecessary cruft (particularly in light of the REST model) -- WebDAV and friends particularly -- but I don't see why you'd want to eliminate any of the HTTP/1.1 verbs (or PATCH) in HTTP/2.0, except maybe replacing HEAD with a no-content media-type in the Accept header for a GET request, and maybe dropping CONNECT and TRACE (though I suspect that there may be cases where they are used and critical, I've just never seen it.)
[+] Eiwatah4|12 years ago|reply
CONNECT is used to get a raw socket connection through a HTTP proxy. There'd be no way to get SSL/TLS to work with a proxy without it (save using SOCKS instead of HTTP to talk to the proxy).
[+] stormbrew|12 years ago|reply
There are two valid reasons I can think of why the verbs need to be specified somewhere for universal agreement:

- So that proxies can potentially retry idempotent requests if the upstream fails. Retrying a partially sent GET should be ok, while retrying a partially sent POST is a terrible idea. It's nice in theory, but in practice only reverse proxies at the application endpoint really have the information necessary to make this decision, since many sites have non-idempotent GETs.

- Because it affects whether or not there's a request or response body. GETs have no request body but should have a response body. POST/PUT/etc. should have both a request and response body. HEADs have neither a request nor response body. At the moment the only way for an intermediary to know whether a request is finished is because it understands these methods, and this is also true of any extension methods (which is why proxies should generally fail on unknown methods).

Mostly it comes down to an issue of routing. And in the end, the ability to have working proxies was an important factor in the popularity of the web imo.

But really the first issue is largely moot already and the latter could be fixed in the protocol so that presence or absence of a body could be signalled in the protocol itself (probably is in http2.0 actually).

All of that aside, though, http2.0 may never fully replace http1.1. I think there may even be a large portion of the web development community that is hoping it won't. In which case, interop will keep those verbs in place forever.

[+] Eiwatah4|12 years ago|reply
> At the moment the only way for an intermediary to know whether a request is finished is because it understands these methods, and this is also true of any extension methods

I read the HTTP 1.1 RFC differently. Requests must indicate a body with a Content-Length or Transfer-Encoding header. Responses always have a body (sometimes of length 0), unless it is a response to a HEAD request or has one of a very small number of response codes. http://tools.ietf.org/html/rfc2616#section-4.3

[+] meddlepal|12 years ago|reply
As I understand it... Only convention is the reason GET does not usually a body. The spec doesn't prevent it.
[+] javajosh|12 years ago|reply
When you think about it, any application can represent every piece of information coming from the outside world in unified data structure. That is, there is no real difference between headers, parameters, and body content (except, of course, in those cases where it is self-referential - for example, when a header tells you how to interpret the rest of the message. But even then one can write a totally generic function that does that first pass for you). When modeled this way, there's really not even a useful difference between GET and POST. These days all GETs cause writes to occur anyway, even if they are just analytics.

Indeed, I'm constantly surprised that there aren't more "grand unified APIs" for dealing with HTTP. If there were, then we'd have better consensus on just how useless a lot of the HTTP spec has become, verbs included. It reminds me of the Java Servlet API - much of it became worthless with the advent of Struts and SpringMVC, as the front controller pattern better fit the mental model of people writing applications.

That said, GET, POST and HEAD are probably worth keeping around, because at least the first two imply something about the kind of idempotency your callers should expect, which is useful.

[+] sopooneo|12 years ago|reply
Is HEAD really used a lot? I don't know that I've ever used it except to try it once. Is it used in API call? If so, why? Thanks for any help on this.
[+] _greim_|12 years ago|reply
While we're at it, let's remove HTTP headers and request bodies, and just stuff everything into the URL. I've written tons of shitty webapps that do exactly that, so it logically follows that we should force everyone to do it.
[+] AsymetricCom|12 years ago|reply
I was thinking something more along the lines of proprietary extensions to HTML5. Isn't that what everyone's doing now?
[+] yxhuvud|12 years ago|reply
If anything, I'd rather have a HTML spec that allows forms to do the other resource oriented verbs.
[+] aeden|12 years ago|reply
Yes! Why is support for PUT and DELETE not specified in HTML specs? Also, why hasn't a browser implementation gone ahead and added support for both of those verbs as an extension beyond the spec?
[+] nobodysfool|12 years ago|reply
HTTP and HTML are two different things. If you don't like HTML you are welcome to use a different markup format.

This post is all about how the author thinks the other verbs are useless, and they are pretty much useless in the browser. However, HTTP is not just for browsers...

[+] bslatkin|12 years ago|reply
TIL: I shit you not – SPACEJUMP was once an HTTP verb
[+] ghayes|12 years ago|reply
...and <BLINK> was a HTML element. Let's not throw out the baby with the bathwater.
[+] hcarvalhoalves|12 years ago|reply
I'm forced to agree. It's pretty much a consensus that the best specs are the smallest ones. You want just the right amount of abstraction to be useful, not try to cover all possible use cases. Inevitably, people will build another layer of abstraction on top.
[+] mythz|12 years ago|reply
Adding un-necessary VERBS adds complexity that imposes additional knowledge and burden that increases the surface area that web servers, server software, intermediaries, HTTP Clients, client libraries, browsers, etc need to know in order to support it.

What are the call-semantics of the new VERB? Will it be widely used correctly and can we even rely on the spec'ed definition? There's no value adding new VERBs that have the same semantics as POST but just has additional metadata to indicate what the action is. Lessons from WS-* should be not to try add specifications and written unified/concepts for everything but to keep a simple and minimal but flexible specification, that most APIs can operate within.

[+] jared314|12 years ago|reply
Adding unnecessary verbs to the standard does create problems, but having a few standard verbs and controlled customization is fantastic. The trouble with custom verbs, like you touched on, is the inability to advertise their contract. I would argue that the OPTIONS verb does not give back enough information to make it useful. Either the OPTIONS verb needs to return more information, or an additional verb should be standardized to allow for discovery and use. The level of specification is a good debate to have, because WS-* was to much specification and REST is almost too little.
[+] makmanalp|12 years ago|reply
I think until we have a way of doing automated service discovery for REST (and OPTIONS is a very lame excuse, knowing what verbs I can use gives me nothing), having 10 bajillion verbs for slightly different semantics doesn't matter. Having a small and standardized set of verbs helps developers, and that's all that matters.

And even if we can do automated discovery, what does that really give us? What software is there that automatically crawls unknown APIs, discovers functionality, and then does something useful with it? The semantics of the commands matter, and it's hard to infer that unless you're a human. No amount of HTTP verbs will fix that. For now, good documentation is fine.

[+] davewiner|12 years ago|reply
That's why you should be careful about adding concepts because you can't remove them without breakage.
[+] aut0mat0n1c|12 years ago|reply
The key difference between POST and PUT & DELETE is idempotency. To quote wikipedia "This is a very useful property in many situations, as it means that an operation can be repeated or retried as often as necessary without causing unintended effects. With non-idempotent operations, the algorithm may have to keep track of whether the operation was already performed or not."

Read Fielding's dissertation please, or any distributed systems text on the basics of RPC. HTTP is for more than just CRUD websites.

[+] neonlex|12 years ago|reply
I also strongly disagree. The real problem is that browsers can't use them as good as they should. If you take for example a RESTful API, the verbs make totally sense and especially one of the mentioned verbs. PATCH is a great verbs if you use it like it was specified. I personally like the idea of giving more freedom to chose the verbs. Imagine you could use for a Twitter API something like: FOLLOW /users/123
[+] pbreit|12 years ago|reply
> The real problem is that browsers can't use them as good as they should

That's the obvious inevitability of having too many superfluous options. And one of the main thrusts of the article.

[+] fleitz|12 years ago|reply
Yes, it would be horrible if you instead had to do: POST /user/123/follow
[+] seliopou|12 years ago|reply
The HTTP specification in no way restricts the verbs that you can use to those that are in common use. But at some point somebody, somewhere, decided that the only ones allowed were the ones that the specification explicitly mentioned. And so people just shoehorn their applications into frameworks built around what the HTTP specification defines, rather than allows.

Ain't nobody got time for defining semantics.

[+] smsm42|12 years ago|reply
Javascript can use them just fine. Browsers without JS can't do a lot of useful things, that's why JS exists.
[+] manarth|12 years ago|reply
Thinking about it further, it's an interesting question. A typical HTTP system has 3 roles: the client, the intermediaries (proxy/proxies/CDNs/caches), and the application (which combines the server, and any edge devices with knowledge and behaviour that is specific to the application).

Currently, the business rules are governed by a complex interrelationship between the request method, request headers, and response headers (including response status).

Although request and response bodies may be present, I've not come across any system where the contents of the body affect the business logic of intermediaries.

Yes, this could be simplified. But chucking out the request methods is both a low-hanging fruit, but also a short-term saving. Much of the complexity is in the request or response headers (such as Vary), whilst the request method provides a consistent and simple community standard.

One of the common limitations I come across is caching of content that varies according to the individual user (or perhaps the role(s) that user has access to within the site).

Most web systems send a plethora of cookies - for google analytics, web tracking, advertising, a dozen other things, and eventually for the session. But the proxy-controls that can be sent are limited to "Vary: cookie". This reduces the cache-potential massively. If I were to request one improvement in the HTTP 2 protocol, it would be the ability to vary according to a particular named cookie, rather than the entire cookie header.

Oh, and yes, I am aware of the ability to parse the cookie in a proxy, extract the proper key-val params, and vary according to that…but it adds unnecessary complexity to the application, and you can't currently expect uncontrolled downstream proxies to accommodate this practice.

[+] shawkinaw|12 years ago|reply
Removing DELETE and PUT would be a terrible idea, every REST API would break.
[+] Timmmmbob|12 years ago|reply
I thought someone would say this and I'm afraid it's bullshit. You can just put the REST operations in the URL. This also has the advantage that you aren't artificially restricting yourself to CRUD operations. Some operations do not map to those, e.g. logging out (DELETE user? ... No... DELETE session? I guess?).

I explained in more detail here: http://stackoverflow.com/questions/2191049/what-is-the-advan...

[+] smartician|12 years ago|reply
Maybe I'm completely off, but in my opinion HTTP verbs are semantically on a lower level. I know that the classic OSI model only has seven layers, and HTTP is in layer seven, but for me, the actual web application using HTTP is in a layer above that.

There are side effects to using those verbs that depend on browser and web server used. For example there may be cases where want to use POST instead of GET even for simple data retrieval, just because you're transmitting a credit card number or other sensitive information and you don't want it to be stored in the web server logs or the browser history. Or the parameters might exceed the maximum length for GET requests. In those cases, it would be a pain to make a semantic distinction between the request verbs on the server level. They should be interchangeable.

Another example is that in IIS 7 you have to jump through quite a few configuration hoops to get PUT and DELETE to work.

[+] icebraining|12 years ago|reply
For example there may be cases where want to use POST instead of GET even for simple data retrieval, just because you're transmitting a credit card number or other sensitive information and you don't want it to be stored in the web server logs or the browser history.

If you're transmitting any information to the server to be processed/stored, sensitive or not, you shouldn't be using GET at all, per the spec.

GET params are nice for stuff like filtering and parameterizing the rendering of the representation, but surely a CC number is not adequate for such use cases.

[+] courtneycouch0|12 years ago|reply
I think HEAD is incredibly useful and really critical for things like caching. While you could use GET or POST in place of things like PUT and DELETE, using HTTP headers, you would have to do some work to reap the same benefits you get from HEAD already in retrieving meta data.

For implementing things like a CDN, HEAD requests are absolutely critical. Also most developers probably use it with some high frequency using curl.