Pebellslearn by building
0%
RoadmapsMatrixCoursesSandboxSign in
The Server Half  ›  Lesson

A Node Server: Routes and Handlers

Node.js 14 minA Node.js server listens on a port and matches each request's method and path to a handler, which reads the request's params, query and body and sends exactly one response, with middleware running first for shared work.

A Node Server: Routes and Handlers

At the other end of fetch('/api/plants') sits a Node.js program that has been waiting on a port. Its whole job is to read each request, pick the right piece of code for it, and send exactly one answer back. Sprout uses Express, the most common small web framework for Node, but every server framework follows the same shape.

The rule

A route is a method plus a path; its handler turns a request into a response.

import express from 'express';

const app = express();
app.use(express.json());                      // middleware: parse JSON bodies

app.get('/api/plants', async (req, res) => {
  const plants = await listPlants(req.user.id);
  res.json(plants);                           // 200 by default
});

app.post('/api/plants', async (req, res) => {
  const plant = await createPlant(req.user.id, req.body);
  res.status(201).json(plant);
});

app.listen(3000, () => console.log('Sprout API on port 3000'));
  • app.listen(3000) claims port 3000 and waits. Unlike a script, the process keeps running until it is stopped.
  • Routes. GET /api/plants and POST /api/plants share a path but are different routes, because the method differs.
  • req is the incoming request: req.params holds pieces of the path (/api/plants/:id), req.query holds the part after ?, req.body holds the parsed JSON, and headers and cookies are there too.
  • res is how you answer: choose a status, send a body. Every request needs exactly one response; a code path that sends none leaves the browser waiting until it gives up.
  • Middleware runs before handlers, for many routes at once: parsing JSON, logging, checking the login. It is registered with app.use, and order matters. JSON must be parsed before any handler reads req.body.

req.user is filled in by the login middleware you will meet in Section 4. For now, read it as "the person asking".

A single Node process can serve many users at once because handlers await slow work such as database queries. While one request waits for PostgreSQL, the process gets on with others.

The shortcut

To find the code behind any request, read its method and path in the Network tab, then search the server for that route. PATCH /api/plants/7 leads straight to app.patch('/api/plants/:id', ...).

A request finds its handlerStep 1 of 4
  1. It arrives

    PATCH /api/plants/7 with the body {"name":"Boston fern"}.

Watch the quotes in that third step: path parameters always arrive as strings. '7' is not 7, so convert with Number(req.params.id) before any arithmetic or strict comparison.

Drills

Answer fast — trust the rule.

quick drill

Which two things identify a route?

quick drill

A handler reads req.body.name, but it is always undefined even though the browser sends JSON. What is most likely missing?

quick drill

One branch of a handler returns without calling any res method. What does the browser experience on that branch?

quick drill

For the route /api/plants/:id, what is req.params.id for a request to /api/plants/42?

Remember

  • A route is a method plus a path; its handler turns a request into a response.
  • Shortcut: read method and path in the Network tab, then search the server for that route.
  • Trap: path parameters are strings, and a branch that never responds leaves the browser hanging.

Practice — level up

0/1 solved

Write your answer, then compare it with a rubric and a model answer.

ExplainOnly the thirsty ones

Sprout wants a filtered list: GET /api/plants?thirsty=true. Explain whether this is a new route or the existing one, where the handler finds the thirsty flag and what type it is, and what the response should be when no plant is thirsty.