← CodeClarityLab Home
Browse by Category
+ added · updated 7d
← Back to glossary

Performance API & User Timing

javascript ES2015 Intermediate
debt(d5/e3/b3/t5)
d5 Detectability Operational debt — how invisible misuse is to your safety net

Closest to 'specialist tool catches it' (d5), because detection requires DevTools inspection, Lighthouse audits, or RUM tools (chrome-devtools, lighthouse, datadog-rum listed in detection_hints). Absence of performance instrumentation is not caught by default linters; automated detection is explicitly marked 'no' in the term metadata. A developer using Date.now() instead of performance.now() won't trigger a compiler error or default linter warning.

e3 Effort Remediation debt — work required to fix once spotted

Closest to 'simple parameterised fix' (e3), because the quick_fix is straightforward: replace Date.now() calls with performance.mark()/measure() and wire them to your analytics endpoint. This is a pattern swap within a single component (instrumentation layer), not a cross-cutting refactor. However, if marks are left uncleaned (a common mistake), remediation requires touching multiple measurement sites, pushing toward e5 in worst case.

b3 Burden Structural debt — long-term weight of choosing wrong

Closest to 'localised tax' (b3), because Performance API adoption is localised to the monitoring/instrumentation layer and doesn't force architectural changes across the codebase. It applies only to 'web' contexts (single applies_to context). Once instrumentation is in place, most of the codebase remains unaffected; only the RUM/monitoring pipeline feels the weight of maintaining marks and measures.

t5 Trap Cognitive debt — how counter-intuitive correct behaviour is

Closest to 'notable trap' (t5), because the misconception is explicitly documented: 'console.time() is sufficient for performance measurement' is a documented gotcha that most developers eventually learn (console.time is dev-only, imprecise; performance.now() is production-grade, microsecond precision). Additionally, common_mistakes reveal non-obvious traps: not clearing marks causes buffer accumulation, measuring sub-1ms operations is unreliable due to JS engine optimisations, and PerformanceObserver vs polling has subtle behavioural differences.

About DEBT scoring →

Also Known As

performance.now() User Timing API PerformanceObserver

TL;DR

Browser APIs for measuring JavaScript execution time with high precision — performance.now(), performance.mark(), performance.measure(), and the PerformanceObserver.

Explanation

The Performance API provides sub-millisecond timing. performance.now() returns time since page load with microsecond precision — unlike Date.now() it is monotonic and not affected by system clock changes. User Timing: performance.mark('start') places a named timestamp; performance.measure('task', 'start', 'end') calculates duration between marks. PerformanceObserver listens for performance entries (paint, navigation, resource, longtask). Use for: profiling critical code paths, measuring custom metrics for RUM (Real User Monitoring), and detecting long tasks that block the main thread.

Common Misconception

console.time() is sufficient for performance measurement — console.time() is imprecise and only for development; performance.now() provides microsecond precision and works in production for RUM metrics.

Why It Matters

Finding which part of a large JS operation is slow requires precise measurement — performance.mark() + measure() pinpoints the exact bottleneck without guessing.

Common Mistakes

  • Using Date.now() for timing — it is millisecond precision and affected by system clock skew.
  • Not clearing marks after measurement — marks accumulate in the performance buffer.
  • Measuring too small operations — JS engine optimisations make micro-benchmarks unreliable below 1ms.
  • Not using PerformanceObserver for continuous monitoring — polling performance.getEntries() misses entries.

Code Examples

✗ Vulnerable
// Imprecise timing:
const start = Date.now();
doHeavyWork();
console.log(Date.now() - start + 'ms'); // Milliseconds only, unreliable
✓ Fixed
// Precise User Timing:
performance.mark('heavy-work-start');
doHeavyWork();
performance.mark('heavy-work-end');
performance.measure('heavy-work', 'heavy-work-start', 'heavy-work-end');

const [measure] = performance.getEntriesByName('heavy-work');
console.log(measure.duration.toFixed(3) + 'ms'); // Microsecond precision

// Observe long tasks (> 50ms) that block main thread:
const observer = new PerformanceObserver(list => {
    list.getEntries().forEach(entry => {
        console.warn('Long task:', entry.duration, 'ms');
    });
});
observer.observe({ entryTypes: ['longtask'] });

Added 16 Mar 2026
Edited 22 Mar 2026
Views 27
Rate this term
No ratings yet
🤖 AI Guestbook educational data only
| |
Last 30 days
0 pings F 1 ping S 0 pings S 0 pings M 0 pings T 0 pings W 0 pings T 0 pings F 0 pings S 0 pings S 0 pings M 0 pings T 0 pings W 1 ping T 0 pings F 3 pings S 0 pings S 0 pings M 0 pings T 0 pings W 0 pings T 0 pings F 1 ping S 0 pings S 0 pings M 0 pings T 0 pings W 0 pings T 0 pings F 1 ping S
No pings yesterday
Amazonbot 7 Perplexity 6 Unknown AI 2 Majestic 1 ChatGPT 1 Ahrefs 1 Google 1
crawler 19
DEV INTEL Tools & Severity
🟡 Medium ⚙ Fix effort: Medium
⚡ Quick Fix
Use performance.mark() and performance.measure() to instrument critical user flows — these timings appear in browser DevTools and can be sent to your PHP analytics endpoint
📦 Applies To
javascript ES2015 web
🔗 Prerequisites
🔍 Detection Hints
No client-side performance instrumentation; Date.now() used for timing instead of performance.now(); no custom marks in DevTools
Auto-detectable: ✗ No chrome-devtools lighthouse datadog-rum
⚠ Related Problems
🤖 AI Agent
Confidence: Low False Positives: High ✗ Manual fix Fix: Low Context: File

✓ schema.org compliant