55

I'm going to design a RESTful API soon, thus I need to describe it in order to enable other people to start implementing clients using it.

I've looked around a bit, but unfortunately, I've not found any standardized form of describing web-based RESTful services. What I'am looking for is something like JavaDoc, although it don't have to be generated out of any sort of code. I'm also not talking about something like WADL, I rather want to have some human-readable documentation I can hand out.

Due to the nature of RESTful web-based services, it should be quite easy to standardize a documentation. It should just list available ressources, corresponding URIs, allowed methods, content-types and describe the availabe actions. Do you have any suggestions therefore?

Thanks in advance & Greets

jldupont
  • 93,734
  • 56
  • 203
  • 318
b_erb
  • 20,932
  • 8
  • 55
  • 64
  • Related: [Standard methods for documenting a RESTful API](http://stackoverflow.com/questions/898321/standard-methods-for-documenting-a-restful-api/) – turtlemonvh Dec 04 '14 at 14:10

4 Answers4

68

Due to the nature of RESTful web-based services, it should be quite easy to standardize a documentation. It should just list available ressources, corresponding URIs, allowed methods, content-types and describe the availabe actions. Do you have any suggestions therefore?

This is absolutely the wrong way to go about documenting REST services.

One URI to rule them all

You should never enumerate URIs of the resources because that would encourage a client to hard code those URIs into the client code. This creates unnecessary coupling between the client and the server. URIs should be discovered based on navigating from the services root URI. The root URI is the only URI that should be documented. The documentation should focus on describing what information and links are in the representations that are returned. If you start with the representation that is returned from the root URI, you can describe the media type and what are the links that may be provided in that document.

Alias your URIs

It is important to use some kind of alias to create a layer of indirection between the client and the server. If you follow the atom:link standard for defining links then the rel attribute becomes the identifier. However, there are other ways of defining links, like, for example, the way images are embedded in html. An image tag can have an Id and a href. The Id tag should be used to identify the image that you wish to access the URL for.

The media types define your API

The end result is that you define all the endpoints in your API within the context of some representation. The complete API is defined by the set of returned representations and the links that connect them.

So you may ask, what is the difference? Why not just create the list of endpoints? Here are a few reasons,

Changeable URI space

Because those links are accessed by the client using an alias, this allows the entire URL structure of your site to be completely changeable without impacting the client. This makes all of the endless "what is the best way to structure my hierarchical URL" questions pretty much irrelevant. You can try it one way, and if it doesn't work, just change it, you won't break any client code or have to change any documentation!

Dynamic distribution

It is not just the path part of the URI that you can change. You could also change the host. Imagine that your app is starting to get a lot more usage than you expected, you can easily change the host of all image or video resources to point to a different server. You could even provide simple load balancing by returning different hosts. As RESTful APIs are stateless, it really does not matter which server responds to the request. This feature is useful for so many scenarios: moving HTTPS stuff onto a dedicated server, geographically distributing requests based on client location, vertically partitioning functions of the application onto different servers.

Explicit protocol

Just because a representation may return a link, does not mean that it always will. The server can only return the links that are allowed based on the current resource state. This can be really helpful when there is a specific protocol that needs to be followed when interacting with a server resource. The client code does not need to understand the rules of the protocol, it can just present to the user the links that have been made available by the server.

You can't autogen the interesting stuff

The reason why most automated efforts to document REST services are not effective is because the uniform interface removes the need to document the easy stuff. Once you understand HTTP (see RFC2616) you understand all of the mechanics of the API. All that is left is the really interesting domain specific information that cannot be generated.

Look on the bright side, the documentation should be much shorter. Any extra available time should be spent on providing examples of how to navigate the API for common scenarios.

Darrel Miller
  • 139,164
  • 32
  • 194
  • 243
  • 2
    Wow - that's a really insightful answer - very interesting, thanks! – brabster Jan 07 '10 at 20:15
  • 26
    Please provide a link to a good example of restful documentation. – Gili Jan 29 '10 at 06:10
  • @Gili I think the stackoverflow API checks all these boxes. But would like Darrel to verify – CVertex Apr 20 '11 at 04:07
  • @CVertex7 From what I can see, the StackOverflow API lists a bunch of URLs and says that they all return JSON. That's definitely not how you write documentation of a RESTful system. – Darrel Miller Apr 20 '11 at 11:36
  • @Gili Take a look at this: http://steamcannon.org/documentation/0.2.0/api.html – Darrel Miller Apr 20 '11 at 11:36
  • 2
    The link seems to be broken. I would really like to see an example of "One URI to rule them all". – Eric P Sep 28 '11 at 10:58
  • @ericp See http://rex.mslivelabs.com/ – Darrel Miller Sep 28 '11 at 11:18
  • 2
    I would be also interested by seeing the "One URL" sample. I think that a REST API should be fairly simple, and defining how to access to ressource and operation should be ok. Regarding the point about host and load balancing, it's now very easy to balance with the same entry point on different host, and it should be much better than have a s1.myapi.com and sometime s10.myapi.com -> same ressource should have same url. – tomsoft Mar 05 '12 at 14:26
  • @tomsoft That's a great point about the load balancing scenario creating multiple URIs for the same resource. That's the first time anyone has pointed that out to me. I guess I'll stick with the vertical partitioning argument only from now on :-) – Darrel Miller Mar 05 '12 at 15:31
  • @tomsoft Huddle is a good example of the one entry URL http://code.google.com/p/huddle-apis/wiki/RootUri – Darrel Miller Mar 05 '12 at 15:32
  • @DarrelMiller Understand the approach, but seems a little bit redundand for very few added value: – tomsoft Mar 07 '12 at 11:47
  • 5
    @DarrelMiller Understand the approach, but seems a little bit redundand for very few added value: When I access to a user, through /users/12345 I should check the friends link, which is obviously /users/12345/friends. So the API should send all the related operation to an object, in order to discover these links. This is a valid approach, but again, verbose. In my view, it seems to be much clearer saying that user URI is /users/ and operation available are friends, task, or whatever on this object. At the end of the day, the dev will use this URL to access to the ress – tomsoft Mar 07 '12 at 11:52
  • I have sought a long time for a good example of a RESTful API, and seems that http://kenai.com/projects/suncloudapis/pages/Home is exactly that. Do you agree? – jpsecher Feb 22 '13 at 21:19
  • @jps Yes the Suncloud docs are a good example. So is the huddle api. – Darrel Miller Feb 24 '13 at 23:59
  • 3
    This is a great way to create an overly complicated and bloated API that's difficult to use. There's no reason why your clients should have to discover the API programmatically from one root URL. – jcoffland Sep 19 '14 at 02:44
  • @jcoffland Have you tried it? My experience of building HTTP APIs for the last 8 years is that it is simpler to work with hypermedia API once you have the necessary tooling in place. – Darrel Miller Sep 19 '14 at 04:31
  • 2
    For most usecases, the scenario sketched in this answer is quite unrealistic. Most front-end developers will not be willing/capable to build a complex client that can discover the API from 1 URI. I think it's nice if you support discoverability, but to think that your clients will not break if you move url endpoints around is an illusion. And being discoverable is not excuse to not document and make available your current url endpoints. How else are developers going to find out what functionality is even supported? – wvdz Jun 27 '15 at 22:38
  • "Discoverability" seems the most pointless concept I've ever encountered in my entire career. If I'm consuming an API, I want to know the contract. What are the methods, what are the parameters, and what are the return types? Actually I couldn't care less about URLs full stop! – gusgorman Oct 29 '18 at 14:55
  • @gusgorman And yet, you continue to use web browsers and web sites. Fortunately we all have the freedom to choose the technology we want to use. – Darrel Miller Oct 29 '18 at 15:55
  • @DarrelMiller I honestly don't see what my use of web browsers and web sites has to do with the way I like to consume APIs when developing software? – gusgorman Oct 29 '18 at 16:04
  • @gusgorman As a user you are benefiting from the architectural properties of discoverability, evolvability, self-description. With a little effort it is possible to take some of these universally proven benefits and take advantage of them in your own applications. If you are not interested, that's fine, but I prefer if you don't go around telling people discoverability is pointless without understanding what benefits it can bring. – Darrel Miller Oct 29 '18 at 16:10
  • @DarrelMiller I am interested. But after years of working on and consuming RESTful APIS in software projects I am yet to see a single example of discoverability being useful. If you can point me to an example or any docs which give evidence of it being useful then I would be genuinely grateful. – gusgorman Oct 29 '18 at 17:04
  • @gusgorman Obviously this isn't the right place to have this conversation and if you want to have it elsewhere, I'm open to it, but allow me to ask one rhetorical question. What is the difference between the HTTP request/response that travels between a web browser and a web server and some other application using a HTTP library and a HTTP API? My belief is that there is no architectural distinction. Web browsers are ignorant about URLs and so can any HTTP API client. – Darrel Miller Oct 29 '18 at 19:43
  • @DarrelMiller agreed we are in the wrong place :) But to answer your question, i agree theoritically you could say there is no difference, but I don't think that is any help to a dev doing software development. The URLusually just doesn't matter in an API. Any client code that knows it should be encapsulated anyway, so that any code that is actually calling the service doesn't know anything about it or even whether the call is going over the wire or not. – gusgorman Oct 29 '18 at 22:49
12

There's no standard, just an open debate. There's an interesting article at InfoQ: Describing RESTful Applications.

Mirko N.
  • 10,537
  • 6
  • 38
  • 37
1

If you use something like JAX-RS you can use the actual JavaDoc of the implementation as your reference. Or doing annotation scanning and generating it automatically shouldn't be too hard also, though I don't know of a specific implementation.

Eran Medan
  • 44,555
  • 61
  • 184
  • 276
-9

If you're using the MVC pattern, the URL is usually represented as:

example.com/class/function/ID

These are pragmatic accessible pieces of information, meaning that you could still use JavaDoc and be able to document the RESTful approach, since each part of the URL is connected to the source code itself.

Luca Matteis
  • 29,161
  • 19
  • 114
  • 169
  • 2
    This example URL is not following the REST principles. There is no "class" or "function". – Sergi Oct 08 '15 at 20:49