Start learning free

LESSON 128 OF 173 · BACKEND: SPEED

Only the Columns You Need

Practice

The product list shows each product's id, name and price; the product's own page, GET /products/{id}, shows the rest. Yet SELECT * reads and sends every column of every product on every visit: today a category and a stock, tomorrow perhaps a long description, all copied from the database and sent for nothing.

Name the columns you need. RowToDict(reader) makes one key per column the query asked for, so the answer, and anything you cache, shrinks with the query. A column added to the table later won't slip in either. For example, a route that only needs names and stock:

app.MapGet("/stock", () => {
    var cmd = RunQuery("SELECT name, stock FROM products");
    using var reader = cmd.ExecuteReader();
    var result = new List<Dictionary<string, object>>();
    while (reader.Read()) {
        result.Add(RowToDict(reader));
    }
    return Results.Json(result);
});

When a query joins two tables, write each column with its table's name in front, like orders.status, so it's clear which table it comes from. Columns used only in WHERE or ON don't need to be in the SELECT: the database uses them, the route never reads them.

Your code must give these answers:

GET /products            →  200  [{"id": 1, "name": "Mug", "price": 12}, {"id": 2, "name": "Notebook", "price": 7}, {"id": 3, "name": "Lamp", "price": 29}, …, {"id": 8, "name": "Gift card", "price": 50}]
GET /products/8          →  200  {"category": null, "id": 8, "name": "Gift card", "price": 50, "stock": 999}
GET /customers/3/orders  →  200  [{"id": 4, "items": [{"product_id": 5, "quantity": 1}, {"product_id": 1, "quantity": 1}], "ordered": "2026-04-18", "status": "shipped"}, {"id": 7, "items": [{"product_id": 1, "quantity": 4}, {"product_id": 2, "quantity": 2}], "ordered": "2026-05-30", "status": "paid"}]
GET /customers/5/orders  →  200  []
GET /debug/queries       →  200  {"queries": 4}

Your task: in the /products GET route, ask only for id, name and price. In the orders route, write the query's first piece with the five columns the route reads instead of SELECT *, each with its table's name in front.


Assignment
Follow the Coding Tutorial to make the product list and the orders query ask only for the columns they use.


Hint
The orders route reads id, ordered and status from orders, and product_id and quantity from order_items. Separate the names with commas and keep the space at the end of the piece.


STEP 1 OF 2
    Ctrl + Enter to check