Page speed waterfall diagram showing DNS, TCP, TLS, TTFB, and download timing phases
Web Performance

Page Speed and TTFB Explained — What Each Number Actually Means

Sunny Pal Singh · · 8 min read

When a page feels slow, Lighthouse tells you the score is 42. But which of the dozen metrics in that report actually matters for your specific problem? DNS, TCP, TLS, TTFB, FCP, LCP — each one measures a different bottleneck in a different part of the stack. This guide explains what each number means, what causes it to be high, and which ones you can improve without touching your infrastructure.

Most page speed investigations start and end in the wrong place. "My Lighthouse score is low" is not a diagnosis — it's a symptom. The score is a weighted average of several sub-scores, each driven by a different metric, each pointing to a different root cause. Knowing that your TTFB is 900ms is actionable. Knowing your Lighthouse score is 43 is not.

This guide walks through every major page speed metric in the order they appear in a network waterfall — from the moment a browser resolves a domain name to the moment the largest content element finishes loading — and explains what each one measures, what a good value looks like, and what causes it to be high.

Key Takeaways

  • Page speed is a chain of sequential phases — DNS, TCP, TLS, TTFB, download, parse, render. A bottleneck in any phase delays everything after it
  • TTFB (Time to First Byte) is the single most important server-side metric — it measures the gap between the request leaving the browser and the first byte of response arriving
  • LCP (Largest Contentful Paint) is the Core Web Vitals metric most correlated with perceived load speed — it measures when the largest visible element finishes rendering
  • DNS and TCP times are largely infrastructure-controlled — you fix them with CDN and server location, not code changes
  • Render-blocking scripts and missing image dimensions are HTML-level problems you can fix without server changes

The Page Load Waterfall: Phase by Phase

Every page load follows the same sequence of phases. Understanding what each phase measures tells you which part of the stack to fix when it's slow.

Phase 1: DNS Lookup

Before a browser can connect to your server, it needs to translate your domain name into an IP address. This is the DNS lookup — a query to a DNS resolver that typically takes 10–100ms. Repeated visits use cached DNS records and take near-zero time. First visits (or visits from users far from DNS servers) can take longer.

What causes high DNS time:

  • Short DNS TTL (time-to-live): if your TTL is set to 60 seconds, every user who hasn't visited in the last minute pays the full lookup cost
  • Geographically distant authoritative nameservers: DNS queries need to reach your nameserver and return; a nameserver in US East adds latency for users in Southeast Asia
  • Too many DNS lookups per page: each third-party domain (analytics, fonts, ads) requires its own DNS lookup if not preconnected

What good looks like: Under 50ms. Over 200ms consistently is worth investigating — usually a TTL or nameserver location issue.

Fix: Increase DNS TTL to 3600s or higher on records that rarely change. Use a CDN with distributed anycast DNS (Cloudflare, Fastly). Add <link rel="dns-prefetch"> for third-party domains you load on every page.

Phase 2: TCP Connection

After DNS resolves, the browser opens a TCP connection to your server. This requires a three-way handshake: SYN → SYN-ACK → ACK. Each round trip takes the network latency between client and server — typically 10–150ms depending on geographic distance.

What causes high TCP time:

  • Server located far from users: a server in London adds ~150ms round-trip for a user in Sydney
  • Missing HTTP/2 or HTTP/3: HTTP/1.1 opens a new TCP connection per resource; HTTP/2 multiplexes many requests over one connection, amortizing the handshake cost

What good looks like: Under 50ms for users in the same region as your server. Over 200ms points to geographic distance — the primary fix is a CDN with edge nodes closer to your users.

Phase 3: TLS Handshake

For HTTPS connections (which is every production site), the TCP connection is followed by a TLS handshake to negotiate encryption. This adds 1–2 additional round trips — typically 50–200ms on top of TCP.

What causes high TLS time:

  • TLS 1.2 vs TLS 1.3: TLS 1.2 requires 2 round trips to complete the handshake; TLS 1.3 completes in 1 (roughly halving the overhead)
  • No session resumption: for repeat visitors, TLS session tickets allow resuming an existing session without a full handshake
  • Slow certificate chain: an overly long certificate chain (intermediate CAs) requires additional downloads

What good looks like: Under 100ms. Consistently over 300ms suggests TLS 1.2 without session resumption or a CDN without TLS termination at the edge.

HTTP/2 vs HTTP/1.1 detection: HTTP/2 cannot be detected by setting ALPN in a normal HTTP request — the binary framing causes parse errors. The Page Speed Inspector uses a separate TLS ALPN probe to detect HTTP/2 support without making a full HTTP request, so the detection is accurate even on servers with complex configurations.

TTFB — The Most Important Single Metric

TTFB (Time to First Byte) is the time from when the browser sends its HTTP request to when the first byte of the response arrives. It includes the network round trip plus the time your server spends generating the response.

TTFB is where server-side performance lives. A slow database query, a slow server-side render, a slow origin behind a CDN that missed cache — all of these show up as high TTFB.

TTFB range Classification What it typically means
Under 200ms Good (green) Server-side generation is fast; CDN cache likely hitting
200–600ms Needs improvement (amber) Some server-side latency; CDN may be missing or not caching
Over 600ms Poor (red) Slow server-side render, slow database, no CDN, or CDN misconfiguration
Over 1800ms CWV failure threshold Google classifies TTFB >1800ms as a Core Web Vitals failure

What causes high TTFB:

  • Slow server-side rendering: the server is doing expensive work — database queries, API calls, template rendering — before sending any response bytes
  • No CDN or CDN cache miss: every request hitting your origin server adds the round-trip to the origin plus origin processing time
  • Redirect chains: each redirect adds a full TTFB before the final page even starts loading. A 3-hop chain with 200ms TTFB per hop adds 600ms before any content arrives. See our redirect chain guide for how to find and fix chains.
  • Slow hosting: shared hosting under load, underpowered VPS, or poorly-configured serverless cold starts

Fixes in priority order:

  1. Add a CDN (Cloudflare, Vercel Edge, Fastly) with aggressive caching for static and semi-static pages
  2. Audit slow database queries — most high TTFB on dynamic pages traces to one or two slow queries
  3. Collapse redirect chains so the first request goes directly to the final URL
  4. Enable HTTP/2 (multiplexing) and TLS 1.3 at your CDN or origin

Compression — The Low-Effort TTFB Multiplier

Before discussing render metrics, it's worth calling out compression separately. Gzip and Brotli compress HTML, CSS, and JavaScript before sending them over the wire. A 200KB HTML file compressed to 40KB downloads 5× faster — improving everything from download time to rendering start.

What to check: the Content-Encoding response header. Values: gzip, br (Brotli), zstd. No Content-Encoding header means the response is uncompressed — a common misconfiguration on origin servers behind CDNs.

What good looks like: Brotli is preferred (15–20% better compression than gzip). Any compression is far better than none.

FCP — First Contentful Paint

FCP (First Contentful Paint) measures when the browser renders the first piece of DOM content — any text, image, canvas, or non-white background. It's the first moment the user sees something happening on the page.

FCP is affected by everything before it — DNS, TCP, TLS, TTFB — plus render-blocking resources in the <head>. A script or stylesheet with no defer or async attribute blocks parsing and delays FCP even after all bytes have downloaded.

What good looks like: Under 1.8s on mobile (Google's "good" threshold). Over 3s is classified as "poor".

Top fixes:

  • Mark non-critical scripts as defer or async — they'll be fetched without blocking parsing
  • Load non-critical stylesheets with media="print" onload="this.media='all'" pattern
  • Inline critical CSS (the CSS needed to render above-fold content) directly in the <head> so the browser doesn't wait for an external file

LCP — Largest Contentful Paint

LCP (Largest Contentful Paint) is the Core Web Vitals metric most correlated with perceived speed. It measures when the largest visible content element (usually the hero image or the main heading) finishes rendering. It's the moment the page feels "loaded".

LCP range Classification
Under 2.5s Good
2.5–4.0s Needs improvement
Over 4.0s Poor

What causes poor LCP:

  • Hero image not preloaded: the browser discovers the LCP image only after parsing the HTML, then has to fetch it. A <link rel="preload" as="image"> tells the browser to fetch it before parsing — the most impactful single change for most sites with image-based LCP elements
  • Hero image lacking dimensions: without explicit width and height attributes, the browser can't reserve space. It paints layout, then shifts when the image loads — this triggers CLS and delays LCP
  • LCP image lazy-loaded: images with loading="lazy" are intentionally deferred — if the LCP element is lazy-loaded, it won't start fetching until the page is partially rendered, guaranteeing a poor LCP
  • Large uncompressed image: a 2MB hero image takes far longer to download than a 200KB WebP equivalent

CrUX vs lab data: Lighthouse shows lab LCP (synthetic test from a single location). CrUX (Chrome User Experience Report) shows real-user LCP from actual Chrome users visiting your site. Lab data is useful for development; CrUX is what Google uses for rankings. The Page Speed Inspector shows both.

CLS — Cumulative Layout Shift

CLS measures how much the page layout shifts during load — elements moving as images, ads, or fonts render. A page that shifts text under your cursor as you're about to click is a high CLS page. Google's threshold for "good" CLS is 0.1 (a score, not milliseconds).

Most common causes of high CLS:

  • Images without width and height attributes — the browser can't reserve space until the image loads, then reflows layout
  • Ads or embeds with no reserved height — inserting a banner ad into the page pushes content down
  • Web fonts causing FOUT (Flash of Unstyled Text) — adding font-display: swap eliminates the invisible text phase but can cause a shift when the custom font loads and has different metrics than the fallback

HTML-Level Checks That Affect All Speed Metrics

Beyond the network and server phases, the HTML structure of the page has a major impact on rendering speed. These are the checks the Page Speed Inspector surfaces:

  • Render-blocking scripts: any <script> in the <head> without defer or async blocks parsing until the script downloads and executes
  • Render-blocking stylesheets: synchronous <link rel="stylesheet"> blocks rendering until the stylesheet fully downloads
  • Images missing dimensions: images without width/height attributes cause layout reflow (contributing to CLS)
  • Below-fold images without lazy loading: images not visible on initial load should use loading="lazy" — they don't need to be fetched immediately and their download competes with above-fold resources
  • Missing preconnect hints: third-party domains (fonts, analytics) require DNS + TCP + TLS before they can send the first byte. A <link rel="preconnect"> starts this process as soon as the browser parses the <head> — before it even encounters the actual resource request
  • Fonts missing font-display: without font-display: swap or font-display: optional, browsers show invisible text while the font loads (FOIT — Flash of Invisible Text), a visible content delay
  • Oversized DOM: a DOM with more than 1500 nodes is slow to parse, style, and reflow. DOM size above 800 elements starts to affect interactivity (INP)

Measure Your TTFB, LCP, and HTML Issues in One Pass

Free, no signup. The Page Speed Inspector gives you DNS, TCP, TLS, TTFB, compression, cache policy, HTTP version, DOM size, render-blocking scripts, missing dimensions, and CrUX real-user data — all from one URL.

Try the Page Speed Inspector Free →
SP

Sunny Pal Singh

Fellow · Technical Director — AI Infrastructure, Cloud Orchestration & Network Automation

Sunny is a Fellow and Technical Director specialising in AI infrastructure, cloud orchestration, and network automation. With hands-on depth across AWS, Azure, GCP, Red Hat OpenStack, and OpenShift, he leads high-performing teams of architects and engineers building transformative solutions at scale. He built ByteWaveNetwork to bring the same engineering rigour to everyday web tooling.

Affiliate disclosure: Some links on this page may be affiliate links. We only mention tools we've personally used and have an honest opinion about. Affiliate revenue helps keep ByteWaveNetwork's tools free and maintained. We are not paid by any of the tools compared in this article for favorable coverage.

Choose design