RESTful API Design-Driven Approach
In this tutorial, you will learn the fundamentals of RESTful API design by applying REST principles and best practices.
Join the DZone community and get the full member experience.
Join For FreeIn this tutorial I will show you the fundamentals of designing a RESTful API specification by applying REST principles and best practices, then you’ll be ready to try my online tutorial: How to design a REST API with API Designer?
If you already know what is meant by API in the context of RESTful web services, you can skip to the next section. If not, read on.
Level-Set on API
The abbreviation API stands for Application Programming Interface this in itself, does not help us understand what it is, however in the context of web services, it can refer to one of two things:
- The RESTful API specification is written using a modeling language such as Open API specification or RAML (RESTful API Modeling Language) that defines a contract for how software components can interact with a service.
The implementation of a web service or microservice whose contract is designed by REST principles that describe how other services must interact with it.
In this post, I will use the first understanding of this term. Even though both are correct, the most technically relevant for this post is the first: an API is a contract for how software applications talk to each other.
Level-Set on REST
The acronym REST stands for REpresentational State Transfer. It is an architectural style used to represent the transmission of data from one application component to another. In the context of web services, we are talking about the representation of resources (i.e. data) transferred over HTTP by calling a URI that represents the data and via an HTTP method that represents the action to perform against the given data.
What Is RESTful API design?
RESTful API design is the activity of describing the behavior of a web service in terms of its data structures and the actions you allow other application components to perform on its data by the principles of REST. Those principles are covered later in this blog.
Why Design a RESTful API?
Imagine that you are an Architect (the kind the design building) and you set out to build an office block without a blueprint. You turn up on the first day with a truck full of bricks and some cement. What are the chances that you'll be successful and build a structure that conforms to code and more importantly, doesn't fall? It's about zero. Without a blueprint the chance of failure is high.
The same approach applies to web service development. You need a blueprint, or more appropriately, an API specification. This is necessary to evaluate the API design and solicit feedback before even starting to build the implementation.
In addition to providing a specification for the web service’s development, an API contract serves to document its expected behavior, data types, and security requirements.
You should now be satisfied that API design is necessary for a RESTful web service, and should start to wonder how is the best approach to actually designing an API specification.
API Design Tooling
The tooling chosen by an API designer has substantial influence over the designer’s productivity. Highly productive tools such as the Anypoint API Designer from MuleSoft is perfect for designing APIs with OAS (swagger) or RAML.
RESTful API Specification Language
There is a choice of modeling languages available to the API designer, each with its approach to describing a RESTful API, but each respecting the REST architectural style. The most widely adopted options are:
- RAML (RESTful API Modeling Language)
- OAS (Swagger)
API Blueprint
In this post, I will design an API using RAML (the RESTful API Modeling Language).
Design a REST API With RAML
To design a contract for a RESTful API I need to define the behavior of the underlying services in terms of to REST architectural style, this means identifying the following aspects:
- The endpoints (which represent the resource/data)
- The HTTP Method (which represent the actions on the data)
- The format of the HTTP request and response (in terms of the data structure)
- Optional
- any security requirements encapsulated as HTTP headers (e.g. OAuth authentication headers)
- HTTP caching requirements as HTTP headers
Use Case Context
Let's imagine that my organization has asked me to design an API that presents a representation of our employee’s data. The API should expose functionality that allows full CRUD capabilities for that employee data and the API specification should also document the user data type and provide examples.
Let’s get started by defining the header of the API specification.
Define the API Header
I must start with the header of the specification file. In the header, I define the title, the version, and the base URI.
#%RAML 1.0
title Employees API
baseUri http //example.com/api/ version
version v1
The base URI defines the absolute URL of the actual API implementation.
Define the Resources
Next, I want to define the endpoint URIs. These identify the resource that represents the employee data and against which CRUD functionality can be performed.
According to REST conventions, the resource URIs should be named as nouns that relate to the data it represents. The table below shows an example of how this might look for common resources:
Data type |
Resource URL |
Employee data |
/employees |
Product data |
/products |
Flight data |
/flights |
If the resource represents a collection the nous should be pluralized. The expectation is that an invocation of the GET /employees
endpoint returns a list of employees (even if the array contains only one employee). According to RAML syntax the resource URI it terminated with a colon :
xxxxxxxxxx
/employees
Use HTTP Methods With Resource URIs
There are five HTTP methods typically used by designers of RESTful APIs. They are mapped to CRUD functionality as shown below:
POST
(mapped to Create)GET
(mapped to Read)PUT
(mapped to Update)DELETE
(mapped to Delete)PATCH
(mapped to Partial update)
According to REST principles, the GET and POST (read and create) methods are used with a resource representation that is a single URI resource because they don't target a specifically identifiable resource, such as GET /employees
and POST /employees
. For the DELETE, PUT and PATCH (delete, update, partial update) methods are used with a resource representation that includes a URI variable that identifies the resource being changed, such as DELETE /employees/{employeeID}
and PUT /employees/{employeeID}
.
xxxxxxxxxx
/employees
get
post
/{employeeID}
put
delete
Define HTTP Requests
An essential aspect of designing a RESTful API is to provide sufficient details for clients to know how to make validated requests.
For example the POST /employee/{employeeId}
HTTP request is expected to have a body that contains the employees' details to be created in the target system. The API specification should include a data type definition and an example of employee data in a valid format.
It is also a convention to specify how the data will be represented. This is defined as a MIME type and can be one of many types including the most common types: JSON and XML
In the RAML below the employee GET, POST, and PUT endpoints are defined. You can see that an example of employee data is included in the specification as well as defining that the data is going to be formatted as JSON.
xxxxxxxxxx
/employees
get
post
body
application/json
example
{
"firstName" : "John",
"lastname" : "Smith"
}
/{employeeID}
put
body
application/json
example
{
"firstName" : "John",
"lastname" : "Smith"
}
delete
Define HTTP Responses and HTTP Status Codes
HTTP Status Codes are sent with the response to an HTTP request and indicate the status of the requests in one of five categories. The first digit of the status code identifies the status of the response.
- 1xx — Informational
- 2xx — Success
- 3xx — Redirection
- 4xx — Client Error
- 5xx — Server Error
Full details of all status codes can be found here HTTP Status Codes.
Let’s define a response for the GET and DELETE methods. Here I have defined a 200 code for the GET request to indicate success and a 204 response to indicate that the deletion was successful but the response body does not include a representation of the resource deleted.
xxxxxxxxxx
/employees
get
description Retrieve the list of all employees
responses
200
body
application/json
example
{
"firstName" : "John",
"lastname" : "Smith"
}
post
/{employeeID}
put
delete
responses
204
description The delete request has been successfully executed.
The Complete API Specification
Let’s put all the parts together and complete the API design:
xxxxxxxxxx
#%RAML 1.0
title Employees API
baseUri http //example.com/api/ version
version v1
/employees
get
description Retrieve a list of all employees
responses
200
body
application/json
example
{
"firstName" : "John",
"lastname" : "Smith"
}
post
body
application/json
example
{
"firstName" : "John",
"lastname" : "Smith"
}
/{employeeID}
put
body
application/json
example
{
"firstName" : "John",
"lastname" : "Smith"
}
delete
responses
204
description The delete request has been successfully executed.
Conclusion
In this post I have covered just the foundations of RESTful API Design with RAML, you have seen how to define resources, methods, requests, and responses. If you want to learn more about designing APIs I can highly recommend the tutorial: How to design your first API with API Designer.
Published at DZone with permission of Alex Theedom, DZone MVB. See the original article here.
Opinions expressed by DZone contributors are their own.
Comments