added explicit inputs (tooling, monitoring platforms, env vars), decision points (baseline variance, trade-off resolution, reproduction cases), output contract (file location, required sections, file structure), outcome signal (measurable success criteria), and edge cases (rate limits, measurement noise, high variance). preserved original Chinese procedure structure and diagnostic framework.
frontend performance optimization
intent
use measurable, evidence-driven methods to locate frontend performance bottlenecks and converge optimization recommendations to the user's critical path, build artifacts, and runtime behavior. apply this skill when diagnosing slowness in initial load, interaction delay, scroll jank, memory growth, network waterfalls, bundle bloat, or visual stability. do not apply this skill to guess-and-check optimization or to chase single Lighthouse scores at the expense of real user experience.
inputs
project artifacts:
- build configuration (webpack, Vite, Next.js, Nuxt, etc.), entry points, and chunk boundaries
- dependency tree (node_modules listing or lock file) and source map files
- routing map and component hierarchy (especially lazy/dynamic imports)
- existing performance reports (Lighthouse JSON, CI artifacts, RUM dashboards, local profiler traces)
runtime context:
- target route(s), device profile (mobile, desktop, tablet), network condition (4G, WiFi, offline), browser version, and reproduction steps
- current performance metrics (if any): LCP, CLS, INP, FID, TTFB, FCP, DOMContentLoaded, load event, main thread utilization
- monitoring platform connection (optional): access to RUM data, real user metrics, or error tracking (env var
PERFORMANCE_MONITORING_URL if present)
tooling access:
- Lighthouse CLI or bundled Lighthouse (v11+)
- browser DevTools (Performance tab, Memory profiler, React/Vue Profiler)
- source map explorer or bundle analyzer (webpack-bundle-analyzer, esbuild-visualizer, source-map-explorer)
- optional: local proxy or HAR capture for network waterfall inspection
procedure
lock down the experience goal
- input: user description of slowness, affected route, device context, reproduction steps
- output: categorized problem statement (first load, interaction latency, scroll jank, memory growth, network waterfall, bundle size, or visual stability)
- clarify whether the issue affects 100% of traffic or a subset (geo, device, network, browser)
- record baseline metrics if available; if none exist, establish a measurement baseline before proposing solutions
- decision: if no reproduction case is available, do not proceed to optimization; request a URL, HAR file, or video demo first
establish measurement baseline
- input: project scripts, build config, dependencies, prior performance reports, or RUM data
- output: documented baseline metrics (LCP, CLS, INP, JS bundle size gzip/brotli, main thread blocking time, optional: memory heap snapshots or flame graphs)
- for page experience, prioritize Lighthouse (desktop and mobile runs), DevTools Performance trace (5-10 second real navigation), React/Vue Profiler (if applicable), or RUM percentiles (p50, p95, p99)
- for bundle size, inspect build output, source maps, duplicate dependencies, first-screen chunk composition, and dynamic import boundaries
- for runtime jank, look for long tasks (>50ms), repeated renders, expensive computations, synchronous loops, layout thrashing, and large lists without virtualization
- if production monitoring, platform metrics, or CI artifacts exist, use them to confirm affected route, device segment, time window, and traffic volume before diving into source code
- edge case: if baseline metrics show variance >30% between runs, repeat measurements; high variance suggests environmental noise (other processes, network jitter) rather than code issues
layer-by-layer diagnosis
- input: baseline metrics, source code, build artifacts, network HAR
- output: bottleneck map with root cause, affected code location, and estimated impact (ms or bytes)
loading layer: identify critical CSS, fonts, images, render-blocking scripts, preload/prefetch hints, and cache headers
- check if render-blocking scripts are necessary or can be deferred
- check if fonts block paint; use font-display swap or preload with high priority
- check if hero images are optimized (format, responsive sizes, native lazy loading)
rendering layer: check for unstable keys, overly broad Context scope, unnecessary effects, redundant computations, and oversized component trees
- look for missing key props or changing key values in lists
- check for Context consumers at the root or high in the tree when only a leaf needs updates
- check for effects that trigger on every render (missing or wrong dependency array)
- look for computations inside render that could be memoized or moved outside
- check for large unvirtualized lists
data layer: check for serial requests, duplicate requests, oversized payloads, missing pagination, and lack of caching strategy
- look for request waterfall chains (A blocks B blocks C) that could be parallelized
- look for identical requests within a page load or user session
- check for responses >1MB; consider chunking or compression
- check if endpoints support ETag, conditional requests, or client-side caching
main thread: check for JSON/CSV parsing, image manipulation, complex filtering/sorting, synchronous compression, and deep object cloning
- profile DevTools Performance tab to identify tasks >50ms blocking user interaction
- use flame graph to find hottest functions during critical user interactions
- check for synchronous work in event handlers or initialization
resource cleanup layer: check for event listeners, timers, subscriptions, WebGL/Canvas resources, and object URLs that are not released
- look for listeners attached in component mount without cleanup
- look for timers (setInterval, setTimeout) without explicit cancellation
- look for canvas or WebGL contexts retained after navigation
- look for createObjectURL without revokeObjectURL
form optimization recommendations
- input: bottleneck map from step 3
- output: prioritized list of changes, each with location, estimated impact, implementation steps, and verification method
- bind every recommendation to a code location, component name, chunk name, or request endpoint
- prioritize high-frequency critical paths and p95 user experience; do not sacrifice first-screen budget for low-frequency background tasks
- start with low-risk, high-reward changes: lazy loading, deduplication, caching, size hints, virtual lists, stable references, and resource cleanup
- for changes that sacrifice maintainability (minification, unsafe optimizations), document the trade-off and provide rollback or alternative approach
- gate recommendations with these checks before implementation:
- is there metric evidence supporting the change (before/after comparison plan)?
- can the bottleneck be traced to a specific route, component, chunk, or API?
- can a frontend engineer verify the fix without backend or DevOps changes?
- is there a smaller or simpler change that achieves the same goal?
verify and regression test
- input: optimization changes, test checklist
- output: post-optimization metrics, comparison table, regression test results
- rebuild and re-run affected build and test commands
- re-collect performance metrics (Lighthouse, Performance trace, bundle analyzer) and compare to baseline
- confirm that loading, empty state, error, offline, reduced-motion, and mobile-specific states are not broken by optimization
- if metrics improve by <5%, re-evaluate whether the change is necessary or whether measurement error is significant
- edge case: if optimization breaks a feature or increases metrics in another area, evaluate trade-off or find alternative approach
decision points
no baseline metrics available
- if the user has no prior measurements and the problem is vague (e.g., "slow"), collect a baseline first (Lighthouse run, DevTools trace, or RUM snapshot) before proposing optimization. do not optimize blindly.
affected traffic is <1% of total
- if monitoring data shows the issue is isolated to a device, geo, browser, or network condition affecting <1% of traffic, prioritize differently. consider whether the optimization cost (engineering time, new dependencies, maintenance burden) justifies fixing an edge case. document the decision.
optimization requires new dependency or major refactor
- if the recommendation requires adding a large package or rewriting core logic, propose it only if the performance gain is >20% or if the metric is critical (e.g., LCP at 5s vs. target 2.5s). provide rollback plan and alternative approaches. do not add dependencies to fix minor issues.
metric variance is high (>30% between runs)
- if baseline measurements show high variance, investigate environmental factors (other processes, network jitter, CPU throttling). repeat measurements with controlled conditions or request a production RUM dataset instead of synthetic testing. do not make optimization decisions on unreliable data.
optimization improves one metric but regresses another
- if code change reduces LCP but increases CLS (e.g., skeleton screens causing layout shift), weigh the trade-off. prioritize metrics aligned with real user satisfaction and business goals. document the decision and consider hybrid approaches.
production monitoring unavailable or user lacks access
- if the user cannot access RUM dashboards or production metrics, rely on synthetic testing (Lighthouse, DevTools) and ask for reproduction steps or user session recordings. if neither is available, narrow scope to testing only on a specific route and device.
user requests optimization without reproduction case
- if "slow" is reported but no URL, route, or steps are provided, request specific reproduction data (URL, device, network condition, what interaction is slow) before proceeding. do not diagnose without evidence.
output contract
format: markdown report saved as reports/performance-review-YYYY-MM-DD-HHmmss.md
required sections:
- executive summary: one-paragraph overview of problem, current metrics, and key recommendation
- baseline metrics: measured LCP, CLS, INP, bundle size (gzip/brotli), main thread blocking time, and data layer latency; include conditions (device, network, browser, Lighthouse mode)
- bottleneck analysis: root cause for each major slow area (loading, rendering, data, main thread, cleanup), with code location and estimated impact (ms or bytes)
- optimization recommendations: ordered list, each with:
- location (file, component, API endpoint)
- current behavior and metric impact
- proposed change and expected improvement
- implementation effort (small/medium/large)
- verification plan (how to measure before/after)
- risks or trade-offs (if any)
- verification results (post-implementation): comparison table of baseline vs. optimized metrics
- regression checklist: confirmed states tested (loading, error, empty, offline, mobile, reduced-motion)
- remaining risks or future work: items out of scope or lower priority
file structure:
reports/
performance-review-2025-01-15-143022.md
outcome signal
- baseline metrics are documented and agreed upon by stakeholder
- every optimization recommendation has a code location and measurable impact target (e.g., "reduce LCP by 300ms via lazy-loading below-fold images")
- post-optimization metrics show improvement on the critical metric (LCP, CLS, INP, or bundle size) without regression on others
- user can reproduce the improvement locally (via Lighthouse, DevTools, or bundle analyzer output)
- regression tests pass; no features are broken and no accessibility or offline experience is degraded
- report is saved and timestamped in
reports/ directory with clear before/after comparison