Time to First Byte (TTFB)
Measures the time between the request and the first byte of the response.
Check Your Site's Time to First Byte
Enter your website URL on the homepage to see your real TTFB performance data.
What is TTFB?
Time to First Byte (TTFB) measures the time between the browser requesting a page and receiving the first byte of information from the server. It's a fundamental metric that affects all other loading metrics.
TTFB Thresholds
≤ 800ms
Good
≤ 1.8s
Needs Improvement
> 1.8s
Poor
Quick Wins for TTFB
- Enable a CDN (Cloudflare free tier is a great start)
- Add caching headers to static assets
- Use static generation for content that doesn't change frequently
- Enable HTTP/2 on your server
- Audit and eliminate unnecessary redirects
What TTFB Includes
TTFB is the sum of several network phases:
Common Causes of Poor TTFB
1. Slow Server Processing
Complex server-side rendering, slow database queries, or inefficient application code can delay the response.
2. No Caching
Without caching, every request requires the server to generate a fresh response, which is much slower than serving cached content.
3. Geographic Distance
Users far from your server experience higher latency due to the physical distance data must travel.
4. Network Congestion
Overloaded servers, insufficient bandwidth, or network issues between client and server slow down response times.
5. Multiple Redirects
Each redirect adds a full round trip, significantly increasing TTFB. Common culprits: HTTP→HTTPS, www→non-www, trailing slash redirects.
How to Improve TTFB
1. Use a CDN
- Serve content from edge servers closest to users
- Popular CDNs: Cloudflare, Fastly, AWS CloudFront, Vercel Edge
- Cache static assets and HTML at the edge
- Use edge functions for dynamic content
Example: Vercel Edge Config
// next.config.js
module.exports = {
// Enable Edge runtime for API routes
experimental: {
runtime: 'edge',
},
}
// Or per-route
export const runtime = 'edge';2. Implement Caching
- Use browser caching with proper Cache-Control headers
- Implement server-side caching (Redis, Memcached)
- Cache database query results
- Use stale-while-revalidate patterns
Example: Cache-Control headers
// Static assets (1 year) Cache-Control: public, max-age=31536000, immutable // HTML pages (revalidate) Cache-Control: public, max-age=0, s-maxage=3600, stale-while-revalidate=86400 // API responses Cache-Control: private, max-age=60
3. Optimize Server Performance
- Use connection pooling for databases
- Optimize database queries (indexes, query plans)
- Enable HTTP/2 or HTTP/3
- Use efficient server frameworks
- Scale horizontally with load balancing
Example: Prisma connection pooling
// Use connection pooling in serverless
const prisma = new PrismaClient({
datasources: {
db: {
url: process.env.DATABASE_URL + '?connection_limit=5&pool_timeout=10'
}
}
})4. Use Static Generation
- Pre-render pages at build time (SSG)
- Use Incremental Static Regeneration (ISR)
- Static pages have near-zero server processing time
- Perfect for marketing pages, blog posts, documentation
Example: Next.js ISR
// app/blog/[slug]/page.tsx
export const revalidate = 3600; // Revalidate every hour
export async function generateStaticParams() {
const posts = await getPosts();
return posts.map(post => ({ slug: post.slug }));
}5. Eliminate Redirects
- Link directly to final URLs (include https://, trailing slashes)
- Use HSTS preload to skip HTTP→HTTPS redirect
- Consolidate redirect chains into single redirects
Example: HSTS Header
Strict-Transport-Security: max-age=31536000; includeSubDomains; preload
Measuring TTFB
Using the web-vitals library
import { onTTFB } from 'web-vitals';
onTTFB((metric) => {
console.log('TTFB:', metric.value);
// Send to analytics
analytics.track('TTFB', {
value: metric.value,
rating: metric.rating,
navigationType: metric.navigationType,
});
});
// You can also use the Navigation Timing API
const [navigation] = performance.getEntriesByType('navigation');
console.log('TTFB:', navigation.responseStart - navigation.requestStart);