Measure first

Devtools, Network tab, tick "Disable cache", reload. Two numbers matter: the total transferred, and the largest single item.

Then look at when things happen. A page that's slow because of a 4MB image needs a completely different fix from one that's slow because the server took six seconds to respond.

Split the problem

Slow server response — the first request takes seconds before anything else starts. The problem is on the server: usually a database query, often an N+1 loop, sometimes a slow third-party call made during the request.

Fast response, slow page — the HTML arrives quickly and the page still takes ages. The problem is what the page loads: images, fonts, scripts.

That single distinction determines everything you do next, and the waterfall shows it immediately.

The usual culprits

Images. Almost always the biggest win. Unresized photos, wrong format, no lazy loading.

Blocking scripts in the head delaying first paint.

Too many separate requests, particularly third-party ones. Every analytics, chat and font script is a connection to somewhere else.

Fonts blocking text rendering. font-display: swap.

N+1 queries on the server.

slow-page.txt
My page is slow. Measurements: time to first byte <n>, total
transferred <n>, largest item <what and how big>, fully loaded <n>.

Here's the waterfall in order: <list the biggest items with sizes and
timings>

Tell me the single biggest win available and how to do it. Then the
second. Don't give me a general checklist — tell me what to change
given these specific numbers.

Know when to stop

Under a second on a phone on 4G is finished. Chasing 300ms is effort better spent elsewhere, and the user cannot tell.

Test on a throttled connection, not your broadband. Devtools can simulate slow 4G, and it changes what you prioritise entirely.