Skip to content

Close two known security holes in the libraries the app ships - #537

Merged
isaacammonbarlow-max merged 2 commits into
masterfrom
deps-pdfjs-router
Sep 5, 2026
Merged

isaacammonbarlow-max merged 2 commits into
masterfrom
deps-pdfjs-router

Conversation

@isaacammonbarlow-max

Copy link
Copy Markdown
Collaborator

Two HIGH advisories were showing in npm audit --omit=dev. This clears both, one commit per package.

Package Before After
pdfjs-dist 6.1.200 6.3.289
react-router-dom 7.18.1 7.18.3
react-router (transitive, pinned by react-router-dom) 7.18.1 7.18.3

npm audit --omit=dev now reports found 0 vulnerabilities.

1. pdfjs-dist — the one that matters

GHSA-hq66-cqwq-w95j, high:
"PDF.js: Arbitrary JavaScript execution upon opening a malicious PDF". Vulnerable
range >=5.6.83 <6.2.108; we were on 6.1.200.

This is a real exposure, not a paper one. The app opens builder plansets in pdf.js
(lib/install/pdf.ts, the planset viewer, the project map, the plan tracer, the
schedule and placement readers), and since the Monday connector went live those
PDFs arrive from another company's board rather than from someone in this office.
A booby-trapped sheet was a way to run code inside the app.

^6.2.108 resolves to 6.3.289 — npm only publishes 6.1.200, 6.2.108 and 6.3.289
in that range, and 6.3.289 is the latest 6.x.

Changelog items checked (v6.2.108 and v6.3.289)

Every [api-minor] change across those two releases is a return type moving from
a plain object to a Map/Set:

This app calls none of them. What it does call is unchanged: getDocument,
getPage, getViewport, page.render({ canvas, canvasContext, viewport }),
getTextContent, getAnnotations({ intent }), numPages, and OPS. Checked
each against the shipped types/src/display/api.d.ts — RenderParameters still
accepts both canvas and canvasContext, and canvasContext is not deprecated.

Also checked, because these are the pieces of the integration that are easy to
break on a pdf.js bump:

  • Import paths. pdfjs-dist/legacy/build/pdf.mjs and
    pdfjs-dist/legacy/build/pdf.worker.min.mjs both still exist in the published
    package. We deliberately use the legacy build so older Safari/Chrome can open
    plansets, so a rename there would have been silent breakage.
  • The worker. GlobalWorkerOptions.workerSrc is still the way to point at it,
    and pdfWorkerEntry.ts (our polyfill wrapper, imported as ?worker&url) still
    resolves — the built bundle contains pdfWorkerEntry-*.js.
  • The types path. pdfjs-dist/types/src/display/api is unchanged, which is
    what nine files here import PDFDocumentProxy and TextItem from.
  • lib/mapPolyfill.ts is still load-bearing, more so than before. 6.2.108
    added more Map.prototype.getOrInsertComputed callers, including one in
    CanvasGraphics.prototype._getPattern (Use getOrInsertComputed in the CanvasGraphics.prototype._getPattern method mozilla/pdf.js#21590) — main-thread rendering code.
    The polyfill covers exactly that.

No Vite config change was needed.

2. react-router-dom — noise removal, not a fix

GHSA-qwww-vcr4-c8h2, high:
"React Router: RSC Mode CSRF Bypass Allows Action Execution Before 400 Response".
Vulnerable range 7.12.0–7.18.1.

Not exploitable here. This is a Vite single-page app: BrowserRouter +
Routes/Route, useNavigate, useLocation, useParams, useSearchParams.
No server, no React Server Components, no router actions, no data router. Bumped
anyway so the audit reads clean and the next advisory that is real does not get
buried under a permanent red line.

Stayed inside major 7 deliberately: react-router 8 removed the react-router-dom
package outright, which is what all 60 files here import from. That is a
migration, not a security bump. react-router is not a direct dependency and
stays that way — react-router-dom@7.18.3 depends on the exact matching
react-router@7.18.3, so bumping the package we actually import carries it.

Changelog items checked (7.18.2 and 7.18.3)

The one worth a second look is remix-run/react-router#15446, since it touches hooks.tsx and
components.tsx and so applies in declarative mode: it makes programmatic
navigation reject external destinations. Grepped every navigate(...) call and
every <Link>/<NavLink to=...> in src/ — all of them are in-app paths
(/projects/:id/..., /warehouse, navigate(-1), and so on). Nothing points at
http…, mailto: or tel:, so nothing changes.

Gate

gate-generic.sh on this branch, port 5183: ALL GREEN.

  • vitest: 334 files, 4778 tests passed
  • oxlint: exactly 26 warnings
  • build: clean
  • five python suites + the census bash suite: all exit 0
  • e2e: 237 passed, 1 skipped, 0 failed, no flakes (9.3m) — clean on the first pass, no solo reruns needed

The extraction and planset specs are the ones that carry this change, since they
are what actually drives pdf.js over a real planset.

ETimpson314 and others added 2 commits September 4, 2026 19:21
pdfjs-dist 6.1.200 -> 6.3.289.

GHSA-hq66-cqwq-w95j (high): "Arbitrary JavaScript execution upon opening
a malicious PDF", affecting pdfjs-dist >=5.6.83 <6.2.108. This one is real
for us: the app opens builder plansets in pdf.js, and since the Monday
connector landed those PDFs arrive from another company's board rather
than from someone in this office.

Checked the pdf.js release notes for v6.2.108 and v6.3.289 against how we
use the library. Every documented api-minor change is a return type moving
to Map/Set — getDestinations, getViewerPreferences, getOpenAction,
getJSActions, getFieldObjects, getPermissions, and StructElementNode's
tableAttributes. We call none of them. What we do use is unchanged:
getDocument, getPage, getViewport, page.render({ canvas, canvasContext,
viewport }), getTextContent, getAnnotations, numPages and OPS. The legacy
build paths and the worker filename are the same, so pdf.ts's import, the
?worker&url entry in pdfWorkerEntry.ts and the workerSrc assignment all
still point at real files, and the types still live at
pdfjs-dist/types/src/display/api.

The Map polyfill stays load-bearing: 6.2.108 added more
Map.prototype.getOrInsertComputed calls, including one in CanvasGraphics,
which is main-thread rendering code.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
react-router-dom 7.18.1 -> 7.18.3 (which pins react-router 7.18.1 -> 7.18.3).

GHSA-qwww-vcr4-c8h2 (high): "RSC Mode CSRF Bypass Allows Action Execution
Before 400 Response", affecting react-router 7.12.0 through 7.18.1. It is
not exploitable here — this is a Vite single-page app with no server, no
React Server Components and no router actions — but leaving a known-high
advisory sitting in the audit means the next one that IS real gets lost in
the noise. Bumped so `npm audit --omit=dev` reads zero.

Stayed inside major 7 on purpose: react-router 8 removed the
react-router-dom package entirely, which is what every screen here imports
from. That is a migration, not a security fix.

Read the 7.18.2 and 7.18.3 notes for anything that touches a plain
BrowserRouter app. 7.18.2 is only the RSC CSRF hardening. 7.18.3 is faster
route matching for long paths, stricter validation of action request
origins (server-side, so nothing here), and stricter validation of
client-side navigation targets — that last one rejects programmatic
navigation to external destinations, and every navigate() and <Link> in
this app goes to an in-app path, so nothing changes.

react-router is not listed as a direct dependency and stays that way;
react-router-dom depends on the exact matching version, so bumping the one
we actually import carries it.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
@vercel

vercel Bot commented Sep 5, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated
infinity-windows Ready Ready Preview Sep 5, 2026 1:33am UTC

Request Review

@isaacammonbarlow-max
isaacammonbarlow-max merged commit 31eb3cd into master Sep 5, 2026
9 checks passed
@isaacammonbarlow-max
isaacammonbarlow-max deleted the deps-pdfjs-router branch September 5, 2026 01:49

This branch was successfully deployed

1 active deployment
Preview — be4ec0d1 Deployed Sep 5, 2026 by vercel[bot]
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.

2 participants