Start learning free

LESSON 32 OF 173 · BACKEND: YOUR FIRST API

Shop Statistics in TypeScript

Practice

A shop owner likes a quick summary of the shop: how many products it has, the lowest and the highest price, and the average price. None of these numbers is stored. Your route works them out from the products on every request, so they always match the shop.

All four come from an array of prices, of type number[]. length counts the items, and Math.min and Math.max find the smallest and the largest. They take separate numbers, not an array, so three dots spread the array into separate numbers: Math.min(...ages). TypeScript has no built-in function that adds up an array, so a loop does it. The average is the total divided by the count. Math.round only rounds to a whole number, so to keep 2 decimal places you multiply by 100, round, then divide by 100. The same on other numbers:

const ages: number[] = [30, 25, 40];
console.log(ages.length, Math.min(...ages), Math.max(...ages));   // 3 25 40
let total: number = 0;
for (const age of ages) {
  total += age;
}
console.log(Math.round((total / ages.length) * 100) / 100);   // 31.67

An empty array has no average: 0 divided by 0 is NaN, "not a number", and Math.min with no numbers gives Infinity. Both are of type number, so the compiler doesn't complain, and nothing crashes. Since JSON can't hold either of them, res.json happens to send null in their place. Don't leave that to chance: when the shop has no products, answer the count 0 and null for the other three. null means "no value".

Your code must answer these requests, in this order:

GET /stats  →  200  {"count": 4, "cheapest": 2, "most_expensive": 29, "average_price": 12.5}
DELETE /products/1  →  204
GET /stats  →  200  {"count": 3, "cheapest": 2, "most_expensive": 29, "average_price": 12.67}
DELETE /products/2, then /products/3, then /products/4  →  204 each
GET /stats  →  200  {"count": 0, "cheapest": null, "most_expensive": null, "average_price": null}
POST /products  {"name": "Chair", "price": 45, "category": "furniture"}  →  201
GET /stats  →  200  {"count": 1, "cheapest": 45, "most_expensive": 45, "average_price": 45}

Your task: add a route for GET /stats that answers count, cheapest, most_expensive and average_price (rounded to 2 places), with null for the last three when the shop is empty.


Assignment
Follow the Coding Tutorial to build the GET /stats route: collect the prices, add them up, work out the average, answer the four keys, and handle an empty shop.


Hint
Check for an empty array right after the first loop, before you add the prices up. For the rounding, multiply by 100 inside Math.round and divide by 100 outside it.


STEP 1 OF 11
    Ctrl + Enter to check

    Shop Stats in TypeScript

    Keep going with TypeScript1,600+ step-by-step lessons, from your first line of code to coding interviews. Free to start.
    Start learning free