Creating an Express API Server
Introducing Express
You might have heard of Express before, and with good reason. It's a popular framework for NodeJS that enables you to quickly create server-side applications.
It empowers your applications to listen on a port, to respond to HTTP requests like GET/POST/PUT and the like, and to define API endpoints.
The first step to creating a quick little web server with Express is to install it with this command
npm install express
Once that completes you're good to go, you're ready to start spinning up application servers left and right.
Adding an API Router
We've got our server up and running — great! However, we want our server to be more capable, so let's upgrade it by building an API with it.
We can get started on that by creating a new file. I'm going to define an API that just serves and handles fruit so the file will be called apiRouter.ts
.
Add the following code
import * as express from 'express';
export const apiRouter = express.Router();
let fruits = ['Apple', 'Berry', 'Cherry',
'Dragonfruit', 'Grape', 'Strawberry'];
apiRouter.get('/fruits', (request, response) => {
response.json(fruits);
});
In this small snippet, we're just creating a new router with Express and defining the endpoint /fruits
to respond with our list of fruits.
You can then modify your server code from earlier to use this newly created fruit router. It'll end up looking like this
...
// Import our fruit router into the server code
import { apiRouter } from './apiRouter';
...
...
// Tell the server to use the fruits router for any routes directed at "/api"
server.use('/api', apiRouter);
...
You've done it — you've built a small API in your server!
Now you can visit http://localhost:4000/api/fruits and you'll see the list of fruits returned to you in the browser.
Express Server — Initialize!
Now that we've got Express installed, we can write our quick little server. Open a new file wherever your project is and add this snippet of code
import * as express from 'express';
// Create the Express server
const server = express();
// Define a port variable. If you have an environment variable called PORT set, that'll be used
// Otherwise, 4000 will be used
const port = process.env.PORT || 4000;
// Have our server handle the route "/"
server.use('/', (request, response) => {
response.json(`You just hit the root of application "/"`);
});
// Tell the server to listen on our port
server.listen(port, () => {
console.log(`Hey! This awesome server is listening on port ${port}`);
});
The first thing we do is import the express
package — simple enough right?
Next, we use Express to create a new server and define a port variable.
Lastly, we tell our server handle the application root path "/" and then we have our server listen on the port we defined.
You can run your application and visit http://localhost:4000/. You'll see a response from your new server — right in the browser.
An API Endpoint for Add Operations
To add a new fruit, include this code in your apiRouter.ts
.
apiRouter.get('/fruits/add', (request, response) => {
// Grab the fruit from the rquest
const { fruit } = request.query;
// If there was a fruit, add it
if (fruit) {
// Add the fruit and respond with the new list
fruits = [ ...fruits, fruit ].sort();
response.json(fruits);
}
// Else, let the requetser know they didn't provide a fruit
else {
response.status(404).json(`D'oh! You didn't give us any fruit to add!`);
}
});
In the above code, we defined the /fruits/add
sub-endpoint to handle adding a new fruit. We respond with a status code of 404 to indicate that a fruit to add wasn't provided.
You can now add a new fruit by pasting this in your browser
http://localhost:4000/api/fruits/add?fruit=Peach
Going Further — Endpoints
So far, we've done the following
- Understood how Express works and installed it
- Created a server with Express
- Defined an API that is invoked by the "/api" path which returns us a list of fruits
There's one final task before we can pat ourselves on the back, and that is to define a few additional endpoints in our API.
Let's add
- An endpoint for adding a new fruit
- An endpoint for deleting a fruit
We'll use use sub-endpoints of the /api/fruits
path to execute these tasks for us, so that you can continue running the requests in your browser.
An API Endpoint for Delete Operations
To delete a fruit, include this code in your apiRouter.ts
apiRouter.get('/fruits/delete', (request, response) => {
// Grab the fruit from the rquest
const { fruit } = request.query;
// If there was a fruit provided in the request
if (fruit) {
// Locate the index of the fruit to delete
const indexOfFruit = fruits.findIndex((fruitInList) =>
fruitInList.toLowerCase() === fruit.toLowerCase());
// If the index exists, delete it from the list
if (indexOfFruit > -1) {
// Remove the fruit and respond with the new list
fruits.splice(indexOfFruit, 1).sort();
response.json(fruits);
}
// Else, the fruit to delete wasn't in our list
else {
response.status(404).json(`D'oh! We didn't have the fruit you wanted to delete!`);
}
}
// Else, let the requetser know they didn't provide a fruit
else {
response.status(404).json(`D'oh! You didn't give us any fruit to delete!`);
}
});
In the above code, we added a /fruits/delete
endpoint to handle deleting a new fruit. We respond with a status code of 404 to indicate that a fruit to delete wasn't provided.
You can now delete a fruit by pasting this in your browser
http://localhost:4000/api/fruits/delete?fruit=Peach
There you have it — a full-fledged Express server with a defined (albeit small) API!