RESTful API
HTTP
Client, like a web browser and server communicates using a HyperText Transfer Protocol (HTTP). The client sends a HTTP request to server side, which includes URL identifying the target server and also the method that defines the action required. HTTP Methods are also referred to as HTTP verbs.
Some commonly used methods and their associated actions are (full list of HTTP request methods):
Method | Description |
---|---|
GET | Get resource from server |
POST | Create a new resource |
PUT | Update an existing resource, or create if not exists |
DELETE | Delete an existing resource |
PATCH | Update a specified resource |
Server responds to the client request by providing the requested data or an error if the requested resource is not available.
We are mostly working with a JSON data in this course. Client, like a browser, Postman or Visual Studio Code - Rest Client is sending a request and server is responding with a JSON data.
REST
REST (REpresentational State Transfer) is an architectural style to provide communication between different computer systems. It is mostly used between the client and the server communication in web application. The main idea is that the client and the server is working independently without knowing about the other one. Communication that uses the REST are said to be stateless, which means that the server does not need to know anything about what state the client has and vice versa.
REST was defined in 2000 by Roy Fielding's dissertation. It’s not a standard but a set of recommendations and constraints for RESTful web services, which includes following:
- Uniform interface, Defines the interface between client and server, fundametal to RESTful design.
- Client-Server, Client makes an HTTP request to a URL hosted by Server, which returns a response.
- Stateless, Client request should contain all the information necessary to respond to a request.
- Cacheable, Response should be defined as cacheable or not.
- Layered system, Requesting client don't need to know whether it’s communicating with the actual server, a proxy, or any other intermediary.
- Code on demand, Server can temporarily extend client, Transfer logic to client, client executes logic.
One good link: What is RESTful API?
In this architecture, a REST server provides connectivity to resources, which helps client to access server application data. These resources are recognized by the URIs. In a web applications, these resources are used with HTTP-protocol requests.
In a server side, a server will receive requests, authenticate, processes them and returns a response to the caller for example with text, HTML, JSON or XML format.
Routes
You will need to create routes to your Node.js application. Routing refers to determining how a server side application responds to a client request to a particular endpoint, which is a URI (or path) and a specific HTTP request method (GET, POST, and so on). Each route can have one or more handler functions, which are executed when the route is matched. These handler functions can return text messages, HTML page or somekind of data like JSON, etc... to caller client. In a larger application you would have several routes to handle several URI's.
In other words, the application "listens" for requests that match the specified route(s) and method(s), and when it detects a match, it calls the specified callback function.
Route definition takes the following structure:
1 2 3 4 5 6 7 |
|
Example GET
request to /hello
path to respond with 'Hello Express!' text.
1 2 3 |
|
Routing methods
For a full list, see app.METHOD. You can also use app.all()
to handle all HTTP methods.
Usually application describes CRUD requests:
POST
request sends data (C, create)GET
request get’s data (R, read)PUT
request updates data (U, update)DELETE
request deletes data (D, delete)
Path
Route paths, in combination with a request method, define the endpoints at which requests can be made. Route paths can be strings, string patterns, or regular expressions.
Here are a few examples:
1 2 3 |
|
1 2 3 |
|
1 2 3 4 |
|
1 2 3 |
|
1 2 3 |
|
Parameters
Route parameters are named URL segments that are used to capture the values specified at their position in the URL. The captured values are populated in the req.params
object, with the name of the route parameter specified in the path as their respective keys.
For example get
request with users and todos:
1 |
|
To define routes with route parameters, simply specify the route parameters in the path of the route as shown below.
1 2 3 4 |
|
Route path is now
1 |
|
And params are inside request object.
1 |
|
Note
The name of route parameters must be made up of “word characters” ([A-Za-z0-9_]).
Handler callback
These routing methods specify a callback function (sometimes called "handler functions") called when the application receives a request to the specified route (endpoint) and HTTP method. In a below callback function only send response back to the caller.
1 2 3 |
|
Or you can use array functions:
1 2 3 |
|
The routing methods can have more than one callback function as arguments. With multiple callback functions, it is important to provide next as an argument to the callback function and then call next() within the body of the function to hand off control to the next callback.
1 2 3 4 5 6 7 |
|
Create a request to your localhost and you should see a 'Hello Express!' text in your browser and folloing text lines in your terminal.
1 2 3 |
|
Note
Remember send response to the client with one of the following Response methods or the client request will be left hanging.
Example - GET
Create a single GET
route to your application:
1 2 3 4 5 6 7 8 9 10 11 |
|
In above example, first parameter in the get
function is the route and second one is the event handler which handles all the HTTP GET calls to this route.
Now the response
object is used with send
method to send string content back to client application / browser. Express will automatically add content-type
header value as a text/html
and status code 200.
Test now http://localhost:3000 address in the browser and you should see Hello Express!
text in your browser. If you test some other "routes" like: http://localhost:3000/test, it won't work because that route is not served. You should get Cannot GET /test
text.
Lets add one more route to our app. Modify your application support /test
route too.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
|
Now both of the routes should work http://localhost:3000 and http://localhost:3000/test.
Remember:
- The
request
object is particular HTTP request from the client. - The
response
object contains all the information how and what server is responding to the client.
Create one more route, which returns some JSON to the caller browser. Now you can use json
method with response
object. This json
method sends JSON string back to caller browser and Express set header Content-type
value as a application/json
automatically.
1 2 3 4 5 6 7 8 9 10 11 |
|
Try now http://localhost:3000/json and check returned Content-Type from your browser's Inspector Network tab. It should be Content-Type: application/json; charset=utf-8
.
Example - POST, PUT, DELETE
Add the following GET
, POST
, PUT
and DELETE
routes to your application where URI (path) doesn't change, but different string value will be send back to the caller. Now you aren't sending any real data to the server side, just testing different methods from Postman.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
|
Note
You will create more routes in exercises.
Use Postman to test different RESTful HTTP request to your server.
Versioning
Express doesn’t offer built-in support for versioning routes. APIs only need to be up-versioned when a breaking changes are made:
- a change in the format of the response data for one or more calls
- a change in the request or response type (variable type)
- removing any part of the API
Note
There are mixed opinions around whether an API version should be included in the URL or in a header. Here are a few examples how you can do it.
Commonly used API versioning strategies are to use prefixing like /v1
and /v2
in the front of your resource name. Send requeset with correct URL to v1:
1 |
|
or v2:
1 |
|
And create end points with Express:
1 2 3 4 5 6 7 |
|
Another way is to use request parameters with query params. Send request with params:
1 |
|
And check request params in Express:
1 2 3 4 5 6 |
|
Or add a custom HTTP headers to your request:
1 2 |
|
And check headers in Express:
1 2 3 4 5 6 7 8 |
|
Use 3rd party npm's to handle versioning:
- express-version-route
- express-version-request
- express-routes-versioning
- etc... just google.
Example: use express-version-route
and express-version-request
npm:s.
Create a request:
1 2 |
|
And use Express and npms to detect different api version calls:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
|
Use HTTP status codes correctly
If something goes wrong while serving a request in a server side, set the correct status code for the response:
- 2xx, everything okay
- 3xx, resource was moved
- 4xx, request can't be fulfilled, client error (like requesting a resource that does not exist)
- 5xx, error in API side
List of HTTP response status codes
Using environmental variables
Now we are used only hardcoded values in your code - like application port. In a real-life applications we have configuration that varies from environment to environment - from local development all the way to the production environment.
You can use dotenv
package, which is a zero-dependency module that loads environment variables from a .env
file into process.env. You can use process.env property to return your value.
You can install dotenv as a dependency:
1 |
|
Now dotenv will be included your package.json
dependencies:
1 2 3 4 5 6 7 |
|
Create .env
file to your project folder and add a port number used.
1 |
|
Then in your index.js
file you'll require it.
1 2 |
|
Modify your code to use defined port.
1 2 3 |
|
Environment variables are used things like credentials, which is not wanted to be exposed to the outside world.
Note
Remember add .env
to .gitignore file.
Read more
- Express
- Express API
- Express Starter Examples
- Semantic versioning
- Routing
- Restful API naming conventions
- NPM - Express
Goals of this topic
Understand
- What Express is.
- Know how to create a simple Express application.
- Know how to use routing in Express.
- Know what environmental variables are and how to use them.