RAML all the REST APIs!

Sebastian Henneberg
synsugar
Published in
5 min readJan 22, 2016

Representational State Transfer (REST) is the de-facto standard for information exchange of web services. One could imagine that there are plenty of powerful alternatives to specify REST APIs. Unfortunately, REST never had such a thing like SOAP had with WSDL.

But I have good news: There is a promising tool on the horizon! Its called RAML 1.0 and it comes with an easy syntax, powerful features and many productivity tools.

First things first! REST API specs should be deeply integrated in the development workflow. This includes design, sharing, collaboration, exploration, testing and documentation. When it comes to combine all these aspects, we have to chose between Swagger, API Blueprint and RAML.

Swagger vs. API Blueprint vs. RAML

All environments come with custom editors and/or plugins for popular editors like Atom, Sublime and vim. The editors support syntax highlighting, auto-completion and inspections with more or less helpful error messages. The environments also share tools to easily access and explore deployed APIs. Some also provide tools to start simple mock servers based on the specs. Swagger even allows us to go the other way around: Generate specs from annotated code which is supported for different programming languages and web frameworks!

RAML API Designer in Atom and api-workbench plugin

The spec itself is written either in Markdown (API Blueprint) or YAML (Swagger & RAML). In comparison, I prefer YAML because it is more concise and clutter-free. The ecosystems of Swagger and API Blueprint are great. RAML is bit behind in terms of tool support. However, I prefer RAML because it is a extraordinary specification language.

RAML ships with a bunch of features to keep our spec DRY (Don’t Repeat Yourself). So let’s jump right in and design a tiny API to give us a feel of its expressiveness.

API specification with RAML

We start by defining some global characteristics like title, baseUri, supported protocols and the primary media type. All properties should be pretty self-explanatory. But don’t forget to add comment in the first line to tell the RAML parser the spec version we are about to use.

Next, we start through with the first endpoint which provides a list of users. First, we define the endpoint by defining the /users postfix which will be appended to the previously defined baseUri. The operation GET /users has one valid response which is the success case with HTTP status 200. The response body is specified as array of user objects. Each user object contains the properties id, name and gender with detailed description via primitives and enums. Additionally, an example is provided which can be encoded as JSON which simplifies manual testing.

Usually, types are shared by different REST operations, endpoints or even APIs. RAML covers this requirement by extracting named type definitions. Types allow us to define a dedicated type for Gender, User and even the Users collection. Types allow to create associations, nesting, create hierarchies, introduce discriminators and many more.

Types also come with some syntactic sugar to keep the specs short and concise. Every named type is an object by default. Optional properties can be expressed by a trailing question mark and arrays have a shorthand syntax of [].

Right now, we would have an empty array of users since we don’t provide any way to add them. Let’s create the operation POST /users which accepts UsersBase types. UserBase requires a name and an optional Gender. Besides the successful response, we also add a response with status 400 in case the payload is incorrect. Therefore, we introduce another named type Error.

In addition, we want to allow updates to existing users. The userId is an mandatory parameter which is part of the URI. The operation PUT /users/{userId} expects UserBase type and responds as User type in case of success. Otherwise, the responses 400 and 404 might occur. Both utilize the previously defined Error type.

Similar to types, we are able to extract behaviour of REST endpoints and operations. Multiple features can be used to extract behaviour. Traits enable to attach arbitrary behaviour and metadata similar to mixins. ResourceTypes are specialized traits to add behaviour with the ability to reference custom parameters and the resourcePath. We define the behaviour of the response 400 as BadRequest trait and the behaviour of the response 404 as NotFound resourceType. Traits are attached by using is while resourceTypes are attached using the type attribute.

We totally forgot to secure our API! Let fix this by wrapping access with OAuth 1. We define this on the document root with securityScheme. Defined securitySchemes can be attached to endpoints and/or operations using securedBy. We set it just once to the root endpoint /users to wrap everything underneath.

You might wonder how to handle the growing size of our spec. Fortunately, RAML provides different ways to modularize the spec by extracting particular parts to external files. In our example, we extract types, traits and resourceTypes.

The presented API is available on GitHub. The individual commits correspond with the incremental changes developed above.

RAML 1.0 provides many more sophisticated features. Annotations allow to attach metadata which can be used for a variety of use cases. Overlays and Extensions are another great feature. Both allow us to refine our specification. This could be used to translate the API spec in different languages.

RAML API Console in Atom with api-workbench plugin

RAML comes with some minor pain points. I encountered limitations with the modularization system. However, the flexibility and focus on the DRY principle makes RAML to the best REST specification language to my knowledge. I’m sure the team behind RAML will do its best to eliminate the remaining quirks and the community will stabilize and extend tool support.

What do you think about RAML? Do you prefer Swagger, API Blueprint or another environment? If so, why?

Sebastian offers IT coaching and consulting at synsugar. He’s passionate about web technologies and likes to contribute to open source. Connect with him via @s_henneberg or @synsugarIT.

--

--

Sebastian Henneberg
synsugar

Coach for Digitalization at @synsugarIT, Software Engineer, Web Worker, Technology & Gadget lover