Menu
CoddyTech

Query Strings

Part of the Express Basics section of Coddy's Node.js journey. Lesson 5 of 23.

A list page often needs options, like which recipes to show, and a new route for each option would be too many.

app.get('/books', (req, res) => {
    const { author } = req.query;
    res.send(author ? 'Books by ' + author : 'All books');
});

The query string is the part of the URL after ?, and Express puts it in req.query, an object. const { author } = req.query is short for const author = req.query.author. GET /books?author=Austen gives req.query.author === 'Austen'. With no ? it is undefined. Several options join with &: /books?author=Austen&year=1813.

A route parameter is part of the path and names one thing. A query option filters or sorts a list, and can be left out.

challenge icon

Challenge

Easy

Visitors want to see only vegan recipes, or only dinners, without a new page for each tag.

  1. In server.js, change the /recipes route. Read the tag option from the query string. Each recipe in data.js has a tags list, like ['vegan', 'soup'].
  2. When a tag is given, send only the titles of the recipes whose tags include it, one title per line, as the route does now.
  3. When no tag is given, send every title, as before.
  4. When no recipe has the tag, send an empty response with status 200.

Try it: Press Run and send /recipes?tag=vegan. You should see two lines: Tomato Soup and Lentil Curry. Send /recipes?tag=dinner: Lentil Curry and Fish & Chips. Send /recipes?tag=dessert: an empty response, since no recipe has that tag. Send /recipes: all four titles.

Try it yourself

import express from 'express';
import { recipes } from './data.js';

const app = express();

app.get('/', (req, res) => {
    res.send('Welcome to Recipe Box');
});

// type('text') sends plain text, so each title shows on its own line.
app.get('/recipes', (req, res) => {
    res.type('text').send(recipes.map((recipe) => recipe.title).join('\n'));
});

app.get('/recipes/:id', (req, res) => {
    const recipe = recipes.find((r) => r.id === Number(req.params.id));
    if (!recipe) {
        res.status(404).send('No such recipe');
        return;
    }
    res.send(recipe.title);
});

app.get('/about', (req, res) => {
    res.send('Recipe Box collects family recipes.');
});

app.listen(3000, () => {
    console.log('Recipe Box is running on port 3000');
});

All lessons in Express Basics

Practice on your own: Express playground