Skip to content

chore: clear all runtime dependency vulnerabilities; 2.0.0-rc.2 - #1837

Merged
cliffhall merged 1 commit into
mainfrom
chore/dependabot-sweep
Jul 28, 2026
Merged

chore: clear all runtime dependency vulnerabilities; 2.0.0-rc.2#1837
cliffhall merged 1 commit into
mainfrom
chore/dependabot-sweep

Conversation

@cliffhall

Copy link
Copy Markdown
Member

Part of #1818. Clears every Dependabot alert that reaches users, then bumps to 2.0.0-rc.2 so the swept tree gets the same live-registry validation rc.1 received.

Why rc.2 rather than shipping 2.0.0: rc.1 validated a specific dependency tree — publish, pack, cold install, run. Changing dependencies invalidates that proof, so the tree that ships must be the tree that was validated.

Result

Zero prod-scope high/critical vulnerabilities across all five manifests:

Manifest prod high/critical
root 0
clients/web 0
clients/cli 0
clients/tui 0
clients/launcher 0

Lockfile-only — no ranges widened

Every fix was a stale lockfile pin inside an existing caret range. No package.json is touched and no major upgrade is involved, which keeps the risk surface to "do newer in-range patch versions still work" — answered by npm run ci below and by the rc.2 clean-room install.

Package Now Patched at
hono 4.12.32 4.12.27
fast-uri 3.1.4 3.1.3
postcss 8.5.23 8.5.18
brace-expansion 1.1.16 1.1.16
js-yaml 4.3.0 4.3.0
ws 8.21.0 / 8.21.1 8.21.0
flatted 3.4.3 3.4.2

What is deliberately left, and why

Two dev-scope clusters. Neither ships — the files allowlist is clients/*/build, clients/web/dist, scripts/install-clients.mjs.

eslint — 5 alerts × 5 lockfiles. A brace-expansion DoS reached via minimatch; the only fix is eslint@10.8.0, a major bump across every package that likely needs rule migration. The glob patterns involved come from the repo's own config and are never attacker-controlled.

vitest — 3 critical in clients/web. A genuine circular exact-pin knot:

  • @vitest/browser-playwright@4.1.0 requires @vitest/browser@"4.1.0" exactly
  • vitest@4.1.0 requires @vitest/browser-playwright@"4.1.0" exactly
  • @storybook/addon-vitest@10.2.19 constrains the set further

npm i fails ERESOLVE. Untangling it means moving Storybook too. The advisory (GHSA-p63j-vcc4-9vmv) also requires loading untrusted content into the test browser, and Browser Mode here runs Storybook play functions against this project's own components.

Both are real work that does not belong immediately before a release, and both will be filed as tracked issues rather than left implicit.

Verification

npm run ciexit 0. Full chain: validatecoverage (per-file ≥90 gate) → build-gate → smokes → Storybook (462 tests, 109 files).

🤖 Generated with Claude Code

https://claude.ai/code/session_01Txmv2qqv3yeKgRzoqXytzD

Sweeps every Dependabot alert that reaches users, then bumps to rc.2 so the
swept tree gets the same live-registry validation rc.1 got. Deliberate: rc.1
validated a specific dependency tree, and changing it invalidates that proof.

Result: **zero prod-scope high/critical vulnerabilities** across all five
manifests (root + four clients).

Achieved with lockfile changes ONLY — no package.json touched, no declared
range widened, no major upgrade. Every one of these was a stale lockfile pin
sitting inside an existing caret range:

  hono             → 4.12.32  (needed 4.12.27)
  fast-uri         → 3.1.4    (needed 3.1.3)
  postcss          → 8.5.23   (needed 8.5.18)
  brace-expansion  → 1.1.16   (needed 1.1.16)
  js-yaml          → 4.3.0    (needed 4.3.0)
  ws               → 8.21.0/1 (needed 8.21.0)
  flatted          → 3.4.3    (needed 3.4.2)

Two dev-scope clusters remain, both deliberately untouched — neither ships (the
`files` allowlist is `clients/*/build`, `clients/web/dist`, and
`scripts/install-clients.mjs`), and both need real work that does not belong
immediately before a release:

- eslint (5 alerts × 5 lockfiles): a `brace-expansion` DoS via `minimatch`,
  fixable only by eslint@10 — a major bump across every package, likely
  requiring rule migration. The glob patterns involved come from the repo's own
  config, never attacker-controlled.
- vitest (3 critical, clients/web): a circular exact-pin knot —
  `@vitest/browser-playwright@4.1.0` requires `@vitest/browser@"4.1.0"` exactly,
  `vitest@4.1.0` requires `@vitest/browser-playwright@"4.1.0"` exactly, and
  `@storybook/addon-vitest` constrains the set further. `npm i` fails ERESOLVE;
  untangling means moving Storybook too.

`npm run ci` passes on the swept tree — full chain including the coverage gate,
build gate, smokes, and 462 Storybook tests.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Txmv2qqv3yeKgRzoqXytzD
@cliffhall cliffhall added the v2 Issues and PRs for v2 label Jul 28, 2026
@cliffhall
cliffhall merged commit d5e35b5 into main Jul 28, 2026
6 checks passed
@cliffhall
cliffhall deleted the chore/dependabot-sweep branch July 28, 2026 05:59
cliffhall added a commit that referenced this pull request Jul 28, 2026
…visories; 2.0.0-rc.3 (#1841)

The #1837 sweep moved vite to 8.0.16 in the root and tui manifests but left
`clients/web` pinned at **8.0.0** — `npm update` reported "up to date" and only
an explicit install would move it. That left five open advisories, three high:

  GHSA-fx2h-pf6j-xcff  high    `server.fs.deny` bypass via Windows ADS
  GHSA-v2wj-q39q-566r  high    `server.fs.deny` bypassed with queries
  GHSA-p9ff-h696-f583  high    arbitrary file read via the dev server
  GHSA-v6wh-96g9-6wx3  medium  launch-editor NTLMv2 hash disclosure
  GHSA-4w7w-66w2-5vf9  medium  path traversal in optimized deps

These are worth fixing rather than dismissing as "dev-only". Unlike the other
remaining dev-scope alerts, `server.fs.deny` bypass is *remotely triggerable*: a
malicious page can read arbitrary files from anyone running `npm run dev`.
Published-package users are unaffected — they get the built `dist` and never
run vite — but contributors are.

Also raises the declared floor to `^8.1.5` in all three manifests that declare
vite. The root previously declared `^8.0.0`, which still *permitted* the
vulnerable 8.0.0 on a fresh resolve, so pinning the lockfile alone would have
left a regression path open.

Bumped to rc.3 rather than folding this into 2.0.0: vite builds the shipped
bundle, so changing it changes the artifact, and the tree that ships should be
the tree that was validated against the live registry. rc.2 validated a
different tree.

`npm run ci` passes — full chain including the coverage gate, build gate,
smokes, and 462 Storybook tests.


Claude-Session: https://claude.ai/code/session_01Txmv2qqv3yeKgRzoqXytzD

Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
@cliffhall cliffhall mentioned this pull request Jul 28, 2026
cliffhall added a commit that referenced this pull request Jul 28, 2026
The v2 go-live release (#1818, phase 5 of #1804).

This is byte-identical to 2.0.0-rc.3 apart from dropping the prerelease suffix,
which is what makes rc.3's validation meaningful: the tree that ships is the
tree that was validated against the live registry.

`2.0.0` has no hyphen, so the derivation added in #1834 resolves it to `latest`
— this is the release that takes the tag from 1.0.1.

Validated across three release candidates:

- rc.1 caught two publish-path defects invisible to every local check —
  `NODE_AUTH_TOKEN` pointing at a non-existent secret (shadowing OIDC trusted
  publishing) and a missing npm CLI upgrade (trusted publishing needs
  >= 11.5.1; Node 22 bundles 10.x). Both fixed in #1836.
- rc.2 validated the dependency sweep (#1837) that cleared every prod-scope
  advisory using lockfile-only changes.
- rc.3 validated the vite 8.1.5 bump (#1841) closing three high-severity
  dev-server file-read advisories.

Each RC was verified with a cold `node:22` container install driving the
published tarball end to end — install, `--help`, and a real `--cli tools/list`
against a live stdio server. `latest` remained on 1.0.1 throughout, proving the
`--tag` derivation.

Zero open Dependabot alerts at time of release.


Claude-Session: https://claude.ai/code/session_01Txmv2qqv3yeKgRzoqXytzD

Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

v2 Issues and PRs for v2

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant