The Performance Paradox
Everyone wants fast websites. Few measure them. Fewer enforce budgets.
The typical cycle: build fast → add features → performance degrades → panic optimize → repeat.
We broke the cycle with performance budgets as code.
What Is a Performance Budget?
A budget defines the maximum acceptable values for key metrics:
{
"budgets": [
{ "metric": "LCP", "threshold": 2500, "unit": "ms" },
{ "metric": "INP", "threshold": 200, "unit": "ms" },
{ "metric": "CLS", "threshold": 0.1, "unit": "score" },
{ "metric": "TTFB", "threshold": 800, "unit": "ms" },
{ "metric": "total-blocking-time", "threshold": 300, "unit": "ms" },
{ "metric": "js-bundle-size", "threshold": 170, "unit": "kb" },
{ "metric": "css-bundle-size", "threshold": 50, "unit": "kb" },
{ "metric": "image-weight", "threshold": 500, "unit": "kb" },
{ "metric": "third-party-count", "threshold": 10, "unit": "count" }
]
}These aren't aspirations. They're gates.
Enforcement Pipeline
Every PR runs through our performance gate:
# .github/workflows/performance.yml
jobs:
performance-budget:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Build
run: npm run build
- name: Lighthouse CI
run: npx lhci autorun --config=.lighthouserc.json
- name: Bundle Analysis
run: npx bundlesize
- name: Regression Check
run: npx perf-budget-check --baseline=mainFail the build if:
- Any Core Web Vital exceeds threshold
- Bundle size increases > 5% without approval
- New third-party added without security review
Tooling Stack
- Lighthouse CI: Lab data in CI
- WebPageTest: Real device testing on PR
- BundleSize: JS/CSS size limits
- Perf-Budget-Check: Compares against baseline branch
- SpeedCurve: Production RUM monitoring
- Custom Dashboard: Team-level performance visibility
Culture: Make It Easy to Do Right
Budgets fail when they're police. They succeed when they're guardrails.
What we provide:
- Component library: Pre-optimized, lazy-loaded, tree-shakeable
- Image component: Automatic WebP/AVIF, responsive sizes, blur placeholders
- Font strategy: Self-hosted, subset, preload, font-display: swap
- Third-party registry: Approved vendors with performance SLAs
- Performance office hours: Weekly drop-in for questions
The Results
Across 50+ projects:
- 94% of PRs pass performance gate on first try
- Median LCP: 1.2s (budget: 2.5s)
- Median bundle: 140kb (budget: 170kb)
- Zero performance regressions in production for 18 months
- Performance review time: 2 hours → 15 minutes
The Budget Evolution
Budgets aren't static. We review quarterly:
- Tighten when team consistently beats budget
- Relax (rarely) with documented justification
- Add new metrics as browser APIs evolve (INP replaced FID)
- Segment by page type (marketing vs app vs checkout)
Start Small
Don't boil the ocean.
- Measure current state (Lighthouse, WebPageTest, RUM)
- Set budget at current P75 (not ideal, achievable)
- Enforce in CI for one metric (LCP)
- Add metrics monthly
- Celebrate wins, investigate misses
Want performance budgets that work? Talk to us.