Skip to content

feat(#275): bundle-size report + CI artifact on every PR#277

Merged
BorisTyshkevich merged 1 commit into
mainfrom
feat/bundle-size-report-275
Jul 17, 2026
Merged

feat(#275): bundle-size report + CI artifact on every PR#277
BorisTyshkevich merged 1 commit into
mainfrom
feat/bundle-size-report-275

Conversation

@BorisTyshkevich

Copy link
Copy Markdown
Collaborator

What & why

Closes #275.

CI now reports what contributes to the single self-contained dist/sql.html on every PR, so bundle growth is caught early instead of via occasional manual comparisons.

npm run size-report builds the production artifact once — through the same buildArtifact the release uses, so the measured bytes are byte-for-byte the shipped dist/sql.html — and emits:

  • bundle-size-report.json — machine-readable
  • bundle-size-report.md — human-readable
  • esbuild-meta.json — raw esbuild metafile

The report includes:

  • raw / gzip / Brotli sizes for the artifact, JS bundle, and minified CSS (deterministic compression: gzip level 9, Brotli quality 11)
  • top-30 input modules by contributed output bytes
  • ownership totals reported separately: hand-written src/**, generated src/generated/**, and each external npm package (scoped and unscoped grouped correctly, nested deps attributed to the leaf package)
  • entry-point / chunk totals (modelled as a list even though the single-file build has one chunk, so it stays useful if hosted builds later add code splitting)
  • absolute + percentage deltas vs. a base report when one is supplied (--base)

Honesty in the report: percentages are of raw contributed output bytes; gzip/Brotli are measured per whole artifact only, with an explicit note that compression is not additive across modules.

CI: a new size job runs on every PR, best-effort-builds the PR base commit in a worktree to produce base deltas (fully tolerant — the base predates this tooling on the first PR, which just means "no deltas"), and uploads the report + metafile as an artifact. Reporting only — no bundle-size budget fails the build in this issue; thresholds are a follow-up once baseline variance is known.

Refactor: build.mjs now exports buildArtifact / esbuildOptions and only runs the release build when invoked as a script. Release output is unchanged — verified byte-identical (same sha256 as origin/main's build) across direct, absolute-path (bundle.sh-style), and ASB_VERSION invocations. The script-detection guard uses a realpath comparison so a symlinked checkout can't silently skip the release build (found and fixed in self-review).

Pure attribution/formatting lives in build/size-report-lib.mjs, unit-tested in tests/unit/size-report.test.js (build tooling sits outside the src/** coverage gate, tested via the same tests/unit precedent as schema-build.test.js).

Checklist

  • npm test passes (the per-file coverage gate is non-negotiable) — 2915 passing
  • Tests added/updated in the same change as the code
  • npm run build succeeds (single-file dist/sql.html) — output byte-identical to main
  • Layers kept honest: pure logic in build/size-report-lib.mjs, I/O in the runner
  • No new runtime dependency (zlib is a Node builtin; esbuild metafile is dev-only, pure metadata)
  • CHANGELOG.md ([Unreleased]) updated
  • Reconciled affected tracked work — Add bundle-size report and CI artifact for every pull request #275 is standalone tooling, not on the Roadmap to 1.0.0 #68 roadmap; no ADR affected

🤖 Generated with Claude Code

https://claude.ai/code/session_01XP1KN94N969SVMNFPdVtGg

Add `npm run size-report`: build the production artifact once via the shared
`buildArtifact` (byte-for-byte the shipped dist/sql.html) and emit a
machine-readable bundle-size-report.json, a human-readable bundle-size-report.md,
and the raw esbuild-meta.json. The report records raw/gzip/Brotli sizes for the
artifact, JS bundle, and minified CSS; attributes JS output bytes to input
modules and npm packages (hand-written src/**, generated src/generated/**, and
each external package separately); lists the top-30 modules and entry-point/chunk
totals; and, given a base report (--base), appends absolute + percentage deltas.

Pure attribution/formatting lives in build/size-report-lib.mjs, unit-tested in
tests/unit/size-report.test.js. A new CI `size` job produces the report on every
PR — with best-effort deltas vs. the PR base (base commit built in a worktree,
tolerant of the tooling not existing on the base) — and uploads it as an
artifact. Reporting only: no bundle-size budget fails the build yet.

build.mjs is refactored to export `buildArtifact`/`esbuildOptions` (release output
unchanged, verified byte-identical) and only runs the release build when invoked
as a script — guarded with a realpath comparison so a symlinked checkout can't
silently skip it.

Closes #275

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XP1KN94N969SVMNFPdVtGg
@BorisTyshkevich
BorisTyshkevich merged commit 6b03338 into main Jul 17, 2026
9 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Add bundle-size report and CI artifact for every pull request

1 participant