Skip to content

feat(cli): CrUX field-data enrichment #82

Description

@nucliweb

Goal

Enrich synthetic measurements with CrUX (Chrome UX Report) field data, so users can compare what the CLI measured in a controlled environment against what real users experience at p75.

Usage

npx webperf-snippets https://web.dev --crux-key $CRUX_API_KEY
# or via environment variable
CRUX_API_KEY=xxx npx webperf-snippets https://web.dev

Output addition (human reporter)

Field data (CrUX p75, mobile)
  LCP    2800ms  🔴 Needs improvement   (synthetic: 2100ms)
  CLS     0.08   🟢 Good                (synthetic: 0.05)
  INP     220ms  🟡 Needs improvement   (synthetic: n/a)

Implementation

New file cli/src/crux.js:

export async function fetchCrux(url, apiKey) {
  const res = await fetch(
    `https://chromeuxreport.googleapis.com/v1/records:queryRecord?key=${apiKey}`,
    { method: "POST", body: JSON.stringify({ url, formFactor: "PHONE" }) }
  );
  const data = await res.json();
  const metrics = data.record?.metrics ?? {};
  return {
    lcp_p75: metrics.largest_contentful_paint?.percentiles?.p75,
    cls_p75: metrics.cumulative_layout_shift?.percentiles?.p75,
    inp_p75: metrics.interaction_to_next_paint?.percentiles?.p75,
  };
}

Files

  • cli/src/crux.js — new file, CrUX API client
  • cli/src/bin.js — fetch CrUX after measurement if key is present, merge into output
  • cli/src/reporters/human.js — add field-data section
  • cli/src/reporters/markdown.js — add field-data section

Acceptance criteria

  • Field data appears in both human and markdown output when key is provided
  • Graceful fallback if URL is not in CrUX dataset
  • Accepts key via --crux-key flag or CRUX_API_KEY env var

Metadata

Metadata

Assignees

No one assigned

    Labels

    cliCLI packageenhancementNew feature or requestv0.4Milestone v0.4

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions