Skip to main content

RFC: SCA Remediation — Upgrade pdfjs-dist 3.11.174 → ≥4.2.67 (CVE-2024-4367)

Document Conventions (do not remove)

This RFC follows the Qontak RFC Template format for governance — the metadata table, Confluence sections 1–6, and Comment logs are mandatory.

It is also agent-execution-ready: §2 Repo Reading Guide, mermaid diagrams, and §4 Agent Execution Plan + Verification & Rollback Recipe must be complete before §7 Ready for agent execution: yes.

No PRD exception (tech-debt / security remediation). This RFC is self-contained: problem statement + success criteria + non-goals replace the PRD traceability matrix. Delivery & staffing live in the initiative's delivery/ folder.

Bucket item: A3 · Class: 🔴 Expedite · Epic: BOT-4620 · Jira Story: to be created

Metadata

FieldValueNotes
StatusIDEAYAML status: draft
DRIBaghiz FirdausaSingle accountable owner of this RFC
Teamchatbot
Author(s)Baghiz Firdausa
ReviewersTBDFE tech reviewer + infosec
Approver(s)TBD (infosec approver)Infosec approval required — actively-exploited CVE
Submitted Date2026-07-14
Last Updated2026-07-14
Target Release2026-Q3
Target Quarter2026-Q3
Deliverynot yet handed to deliveryUncomment delivery: frontmatter once timeline exists
Related../README.md (initiative bucket)No PRD — security remediation RFC
DiscussionTBDAdd Slack thread link

Type: frontend
Sub-type: enhancement (security)

Sections at a Glance

  1. Overview (problem statement, success criteria, scope, decisions)
  2. Technical Design (Repo Reading Guide → architecture → migration contract)
  3. High-Availability & Security
  4. Backwards Compatibility and Rollout Plan (Agent Execution Plan + Verification & Rollback Recipe)
  5. Concern, Questions, or Known Limitations
  6. Comment logs
  7. Ready for agent execution

1. Overview

Problem Statement

The chatbot-fe repository pins pdfjs-dist at version 3.11.174. This version is affected by CVE-2024-4367 (CVSS 8.8 — High), an actively-exploited arbitrary JavaScript execution vulnerability. When a user opens a malicious PDF in the chatbot's PDF viewer, the attacker can execute arbitrary JavaScript in the browser context of the hosting domain, leading to session token theft, data exfiltration, and unauthorized actions on behalf of the user.

SCA source: Internal SCA audit spreadsheet, "Exploitable CVEs" tab — chatbot-fe column, row: P2-High · pdfjs-dist · 3.11.174 → 4.2.67 · CVE-2024-4367 · HIGH · CVSS 0.9938.

The fix requires upgrading pdfjs-dist from 3.11.174 to ≥4.2.67, which is a major version bump (v3→v4) carrying breaking API changes that the implementation must handle.

CVE Summary

FieldValue
CVE IDCVE-2024-4367
GHSAGHSA-wgrm-67xf-hhpq
SeverityHIGH (CVSS 8.8)
Exploitability score0.9938 (near-maximum — actively exploited in the wild)
Affectedpdfjs-dist ≤ 4.1.392
Fix versionpdfjs-dist ≥ 4.2.67 (current latest: 6.1.200)
Root causefont_loader.js passes font data to eval() without type validation when isEvalSupported: true (default)
Attack vectorNetwork — user opens a malicious PDF in the browser; no special privilege required
Immediate workaroundSet isEvalSupported: false in the getDocument() options (disables JIT font compilation; performance regression on complex PDFs)
PatchRemoves eval() call entirely — mozilla/pdf.js PR #18015

Success Criteria

  1. pdfjs-dist is pinned at ≥4.2.67 in package.json and pnpm-lock.yaml.
  2. pnpm audit reports zero findings for CVE-2024-4367.
  3. The PDF viewer in chatbot-fe renders PDFs correctly in the browser (happy path validated).
  4. All existing tests pass (pnpm test).
  5. No console errors related to PDF.js worker version mismatch on page load.
  6. Build succeeds (pnpm build or equivalent).

Out of Scope

  • Other CVEs/vulnerabilities found by pnpm audit beyond CVE-2024-4367 (separate RFC).
  • Upgrading any other dependency not required as a peer dependency of pdfjs-dist ≥4.2.67.
  • Functional changes to the PDF viewer UI or behavior beyond what is required by the v3→v4 migration.
  • Performance optimisation of the PDF viewer.
  • Test runner migration (Jest → Vitest) — tracked as an open question; the execution plan includes a fallback for legacy-build if Jest is confirmed.

Assumptions

  1. chatbot-fe is a browser-based frontend app (not Node.js SSR) — the ESM migration path applies.
  2. The bundler is Vite or Webpack — must be confirmed by reading package.json before implementation (see §5 Open Questions).
  3. pdfjs-dist is imported directly (not only via a wrapper like react-pdf) — must be confirmed.
  4. pnpm test runs the test suite — command source must be verified from package.json scripts before running it in chunk acceptance criteria.
  5. The workaround (isEvalSupported: false) is NOT the chosen fix; the full upgrade is implemented.
  6. Target pin: 4.2.67 (minimum secure) or latest stable (6.1.200 as of 2026-07-14) — decided in Detail 1.B below.

Dependencies

DependencyTypeStatus
pdfjs-dist ≥4.2.67npm package upgradeAvailable on npm — no gating dependency
Bundler worker configInternal — bundler plugin / aliasNeeds implementer verification (Vite vs Webpack changes the workerSrc setup)
Test runner compatInternal — Jest vs Vitestv4 is ESM-only; Jest requires extra transform config; Vitest is fine natively

Design References

N/A — security remediation RFC. No Figma frames. No UI surface change intended; the PDF viewer renders identically after the upgrade.

Detail 1.A — PRD Traceability Matrix

No PRD — security remediation. Replaced by self-contained problem + success criteria + non-goals above (per checklist no-PRD exception).

PRD Section Coverage

N/A — no PRD. See §1 success criteria as the authority.

UI / Consumer Surface Coverage

SurfaceConsumerChange
PDF viewer component(s) in chatbot-feWeb — end user opening a PDF attachmentworkerSrc path updated; isEvalSupported remains default (true) — the eval path is removed at the library level by the patch

Role Coverage

N/A — no role-gated behavior change. The vulnerability and fix apply equally to all users who can open a PDF in the chatbot.

Detail 1.B — Decisions Closed

DecisionChosen optionAlternatives rejectedWhy rejected
Target version pin4.2.67 (minimum secure, conservative)Latest stable 6.1.2004.2.67 is the minimum that closes CVE-2024-4367; pinning to latest introduces unreviewed v4.x→v6.x API drift not validated in this RFC. Implementer may upgrade further if diff is confirmed clean, but 4.2.67 is the safe floor.
Fix approachFull package upgrade to ≥4.2.67Workaround only (isEvalSupported: false)Workaround disables JIT font compilation (performance regression on complex PDFs, possible rendering artifacts) and leaves the vulnerable code path present in the bundle. A version bump is the correct remediation.
ESM worker setupBundler-native new URL(…) patternInline worker string / CDN workerSrcCDN adds a network dependency; inline string is brittle. The new URL('pdfjs-dist/build/pdf.worker.min.mjs', import.meta.url) pattern is the Mozilla-recommended approach and is bundler-portable. Legacy build (pdfjs-dist/legacy/build/pdf.worker.min.mjs) is the fallback for CJS/Jest environments.

Detail 1.C — Per-Story Change Map

Story idStory titleLayer scopeChangesAcceptance criteriaRFC anchors
SCA-S01Upgrade pdfjs-dist to close CVE-2024-4367FE-onlypackage.json version pin; pnpm-lock.yaml; worker init code (all files importing pdfjs-dist, updating workerSrc path from .js.mjs ESM pattern); import path updates if using pdfjs-dist/build/pdf.jspdfjs-dist/build/pdf.mjspnpm audit = 0 findings for CVE-2024-4367; pnpm build exits 0; pnpm test passes; PDF renders in browser smoke test§1 CVE Summary · §2.1 architecture · §4.C chunks 1-4

2. Technical Design

Detail 2.0 — Repo Reading Guide (read this first)

Anti-hallucination notice. The chatbot-fe repository is private and was not readable by this RFC's author at draft time. The Source Verification table below marks every claim as UNVERIFIED — implementer must confirm before executing any chunk. Do not skip the reading-order step.

Repo Map (mermaid)

flowchart LR
subgraph chatbot_fe["chatbot-fe (repo)"]
pkg["package.json / pnpm-lock.yaml"]
entry["src/main.ts or similar entry"]
pdfInit["PDF viewer init file(s)\n(workerSrc config)"]
pdfComp["PDF viewer component(s)"]
bundler["vite.config.ts / webpack.config.js"]
tests["test files covering PDF viewer"]
end
pkg --> pdfComp
entry --> pdfInit
pdfInit --> pdfComp
bundler --> pdfInit
pdfComp --> tests

Existing Code Anchors

The agent must read every file below before writing any code. Mark each as found / path-differs / not-found.

Path (to verify)Why the agent reads itWhat pattern it teaches
package.jsonConfirm pdfjs-dist version pin, bundler (vite/webpack), test script name, lock file formatExact pnpm test / pnpm build command; whether react-pdf wraps pdfjs-dist
pnpm-lock.yamlConfirm resolved pdfjs-dist version; detect duplicate pdfjs-dist instances that would cause API/worker version mismatchDedup requirement
Files containing import.*pdfjs-dist or require.*pdfjs-distFind every usage site; find current workerSrc setupv3 pattern to replace with v4
Files containing GlobalWorkerOptions or workerSrcFind the exact worker init fileCurrent worker config pattern
vite.config.ts (or webpack.config.js)Confirm bundler + any PDF-related aliases or pluginsWorker bundling approach
Test file(s) covering PDF renderingUnderstand test runner (Jest vs Vitest) + any pdfjs mock setupESM transform config requirement

Patterns to Follow

ConcernPattern in repoReference fileDeviation in this RFC?
Worker initCurrent GlobalWorkerOptions.workerSrc assignmentFile with workerSrc (to be found)Yes — path changes from .js to .mjs per v4 contract
Import pathsCurrent import … from 'pdfjs-dist/build/pdf'Same fileYes — path changes to pdfjs-dist/build/pdf.mjs per v4 contract
Package managementpnpm + pnpm-lock.yamlpackage.jsonNone

Reading Order for the Agent

  1. package.json — confirm version, bundler, scripts
  2. pnpm-lock.yaml — confirm resolved pdfjs-dist version; detect duplicates
  3. grep -r 'pdfjs-dist' src/ --include='*.ts' --include='*.tsx' --include='*.js' --include='*.vue' -l — find all import sites
  4. Each file found in step 3 — read the full import and workerSrc setup
  5. vite.config.ts or webpack.config.js — confirm bundler + any worker plugin
  6. Test file(s) that mock or use pdfjs — confirm test runner and any transform config

Source Verification (anti-hallucination — implementer fills this before chunk 1)

Anchor / pattern / contractVerified byEvidence
pdfjs-dist current version in package.jsonUNVERIFIEDImplementer: read package.json and record exact version string
Worker init file path and workerSrc assignmentUNVERIFIEDImplementer: grep result + file path + line number
Bundler type (Vite / Webpack)UNVERIFIEDImplementer: read package.json devDependencies for vite or webpack
Test runner (Jest / Vitest)UNVERIFIEDImplementer: read package.json devDependencies and test script
All import sites for pdfjs-distUNVERIFIEDImplementer: paste grep output

Design ↔ Code Mapping

N/A — no Figma frames. No visual change.

Detail 2.1 — Architecture (mermaid)

Before upgrade — v3 import pattern

flowchart LR
comp["PDF Viewer Component"] -->|"import pdfjsLib from 'pdfjs-dist/build/pdf'"| lib["pdfjs-dist v3\npdf.js (CJS/UMD)"]
init["Worker init file"] -->|"GlobalWorkerOptions.workerSrc = pdfjsWorker"| worker["pdf.worker.min.js"]
lib --> worker

After upgrade — v4 import pattern (ESM)

flowchart LR
comp["PDF Viewer Component"] -->|"import pdfjsLib from 'pdfjs-dist/build/pdf.mjs'"| lib["pdfjs-dist v4\npdf.mjs (ESM)"]
init["Worker init file"] -->|"GlobalWorkerOptions.workerSrc = new URL('pdfjs-dist/build/pdf.worker.min.mjs', import.meta.url)"| worker["pdf.worker.min.mjs"]
lib --> worker

Security state machine — isEvalSupported

stateDiagram-v2
[*] --> v3_vulnerable
v3_vulnerable: v3 vulnerable — eval() present, isEvalSupported true by default
v3_vulnerable --> workaround: set isEvalSupported false
v3_vulnerable --> upgraded: upgrade to v4.2.67 or higher
workaround: Workaround only — eval() disabled (REJECTED)
upgraded: v4 patched — eval() removed, CVE-2024-4367 closed
upgraded --> [*]

Detail 2.2 — Sequence

Happy path — PDF renders after upgrade

sequenceDiagram
actor U as User
participant C as PDF Viewer Component
participant W as PDF.js Worker (v4)
participant S as File Storage / CDN

U->>C: opens PDF attachment
C->>W: load worker via workerSrc (pdf.worker.min.mjs)
W-->>C: worker ready
C->>S: GET pdf file url
S-->>C: binary PDF data
C->>W: pdfjsLib.getDocument(data)
W-->>C: PDFDocumentProxy
C->>U: render pages
Note over W: eval() code path removed in v4\nCVE-2024-4367 closed

Failure path — worker version mismatch (must not occur post-upgrade)

sequenceDiagram
participant C as PDF Viewer Component
participant W as PDF.js Worker

C->>W: load worker
W-->>C: Error: API version X does not match Worker version Y
Note over C,W: Caused by duplicate pdfjs-dist in lockfile\nFix: pnpm dedupe

Detail 2.3 — Database Model

N/A — frontend-only package upgrade. No client-side storage change.

Detail 2.4 — APIs Consumed

No backend API change. The PDF viewer consumes a file URL (storage/CDN) — unchanged.

Endpoint / resourceMethodStatusChange
PDF file URL (storage/CDN)GETexistsnone — unchanged

3. High-Availability & Security

Security Analysis

ItemAssessment
CVE closedCVE-2024-4367 — eval() removed in v4.2.67+; the vulnerable code path no longer exists in the bundle
ExploitabilityCVSS 8.8 / exploitability 0.9938 — near-maximum; active exploitation confirmed in the wild
Attack surfaceAny user who can open a PDF in chatbot-fe. No auth bypass required — the attack is triggered purely by opening a crafted PDF
Post-upgrade riskNo new CVEs known for pdfjs-dist 4.2.67 as of 2026-07-14 (latest 6.1.200 has 0 open CVEs)
isEvalSupported after upgradeThe eval() call is removed at the library level in v4 — the option is irrelevant. No code change needed for this flag
Workaround deploymentIf the upgrade is blocked, deploy isEvalSupported: false as a hotfix immediately while the upgrade is prepared. See §4.B
Infosec approverRequired in Approver(s) row before merge — actively-exploited CVE

Availability

Package upgrade only — no service, database, or network change. Availability impact is limited to a failed build or test regression, both caught in CI before any deployment.

Role × Endpoint Authorization

N/A — no new endpoint or permission change.

State Surface Contract

N/A — no state change beyond the library version.


4. Backwards Compatibility and Rollout Plan

Backwards Compatibility

The upgrade is a major version bump (v3 → v4). Breaking changes that affect chatbot-fe:

Breaking changev3 behaviorv4 behaviorMitigation in this RFC
Worker file extensionpdf.worker.min.jspdf.worker.min.mjsUpdate workerSrc to .mjs path
ESM-onlyCJS / UMD availableESM .mjs onlyUse new URL(…, import.meta.url) worker pattern; or legacy/ build if CJS needed
Import pathpdfjs-dist/build/pdfpdfjs-dist/build/pdf.mjsUpdate all import statements
Jest incompatibilityJest works with CJS buildJest fails with ESM-only packageChunk 4 handles Jest ESM transform config; or migrate to Vitest (out of scope)
Worker/API version mismatchSingle version resolvesDuplicate pdfjs-dist in lockfile throwsRun pnpm dedupe post-upgrade (Chunk 2)

Rollout Plan

Single-step: one PR, one branch, merged after CI green. No feature flag needed — security fix with no user-visible behavior change.

Agent Execution Plan

Prerequisites before starting Chunk 1: Complete the Reading Order (§2.0) and fill the Source Verification table. Do not proceed to any code change until every UNVERIFIED row has concrete evidence.

Chunk 0 — Repo grounding (no code change)

Goal: Fill the Source Verification table; confirm all assumptions.

Steps:

  1. Read package.json — record exact pdfjs-dist version, bundler, test script, lock file format.
  2. grep -r 'pdfjs-dist' src/ --include='*.ts' --include='*.tsx' --include='*.js' --include='*.vue' -l — list all import files.
  3. Read each file from step 2 — find GlobalWorkerOptions.workerSrc assignment; record file path and line.
  4. Read vite.config.ts or webpack.config.js — confirm bundler.
  5. Read test files that import pdfjs-dist or mock it — confirm test runner (Jest/Vitest).
  6. Fill the Source Verification table in §2.0.

Acceptance criteria:

  • Source Verification table has zero UNVERIFIED rows.
  • Bundler and test runner are confirmed.
  • All pdfjs-dist import sites are listed.

Chunk 1 — Upgrade the package

Files:

  • package.json
  • pnpm-lock.yaml (generated)

Commands:

pnpm add pdfjs-dist@4.2.67
# confirm lockfile updated
grep 'pdfjs-dist' pnpm-lock.yaml | head -5

Acceptance criteria:

  • package.json dependencies show pdfjs-dist: "4.2.67" (or "^4.2.67").
  • pnpm-lock.yaml resolves pdfjs-dist to 4.2.67 with no duplicate version entries.

Chunk 2 — Deduplicate lockfile

Goal: Ensure no transitive dependency pulls in a second pdfjs-dist version (worker/API mismatch).

Commands:

pnpm dedupe
grep -A2 'pdfjs-dist' pnpm-lock.yaml | grep 'version'

Acceptance criteria:

  • Exactly one pdfjs-dist version resolved in pnpm-lock.yaml.

Chunk 3 — Update worker init and import paths

Files: All files found in Chunk 0 step 2 that contain pdfjs-dist imports or workerSrc.

Pattern to apply:

Replace v3 worker init:

// BEFORE (v3)
import pdfjsWorker from 'pdfjs-dist/build/pdf.worker.entry';
GlobalWorkerOptions.workerSrc = pdfjsWorker;

With v4 ESM pattern:

// AFTER (v4 — Vite / Webpack 5 with asset modules)
import { GlobalWorkerOptions } from 'pdfjs-dist';
GlobalWorkerOptions.workerSrc = new URL(
'pdfjs-dist/build/pdf.worker.min.mjs',
import.meta.url
).toString();

If bundler is CJS / legacy (Webpack 4 or Jest environment) — use legacy build:

import { GlobalWorkerOptions } from 'pdfjs-dist/legacy/build/pdf.mjs';
GlobalWorkerOptions.workerSrc = new URL(
'pdfjs-dist/legacy/build/pdf.worker.min.mjs',
import.meta.url
).toString();

Replace import paths (if present):

// BEFORE
import * as pdfjsLib from 'pdfjs-dist/build/pdf';
// AFTER
import * as pdfjsLib from 'pdfjs-dist'; // preferred top-level ESM
// or if explicit build path needed:
import * as pdfjsLib from 'pdfjs-dist/build/pdf.mjs';

Acceptance criteria:

  • No remaining references to pdf.worker.min.js (old CJS worker extension).
  • No remaining references to pdfjs-dist/build/pdf.worker.entry (v3 worker entry shim).
  • GlobalWorkerOptions.workerSrc is set using the new URL(…, import.meta.url) pattern.

Chunk 4 — Fix test runner ESM compatibility (if Jest)

Condition: Only required if test runner confirmed as Jest (step 5 of Chunk 0).

pdfjs-dist v4 is ESM-only. Jest requires a transform config to handle it.

Option A — Add ESM transform to Jest config:

// jest.config.js — add to transformIgnorePatterns (allow pdfjs-dist to be transformed)
transformIgnorePatterns: [
'/node_modules/(?!pdfjs-dist)'
],

Option B — Mock pdfjs-dist in tests (if PDF viewer is not under test):

// In jest setup file or individual test:
jest.mock('pdfjs-dist', () => ({
GlobalWorkerOptions: { workerSrc: '' },
getDocument: jest.fn().mockResolvedValue({ numPages: 1, getPage: jest.fn() }),
}));

If test runner is Vitest: No action needed — Vitest handles ESM natively.

Acceptance criteria:

  • pnpm test exits 0.
  • No SyntaxError: Cannot use import statement in a module or similar ESM parse errors in test output.

Chunk 5 — Verify build and audit

Commands:

pnpm build # confirm no build error
pnpm audit # confirm CVE-2024-4367 no longer reported

Acceptance criteria:

  • pnpm build exits 0 with no PDF.js-related errors.
  • pnpm audit output does NOT list CVE-2024-4367 or pdfjs-dist ≤4.1.392.

Verification & Rollback Recipe

Pre-merge verification

# 1. No old pdfjs-dist version in lockfile
grep 'pdfjs-dist' pnpm-lock.yaml | grep 'version'
# Expected: single entry at 4.2.67 (or higher)

# 2. No old worker extension referenced in source
grep -r 'pdf.worker.min.js' src/
# Expected: 0 matches

# 3. No old worker entry shim
grep -r 'pdf.worker.entry' src/
# Expected: 0 matches

# 4. Audit clean
pnpm audit 2>&1 | grep -i 'CVE-2024-4367'
# Expected: no output (CVE not found)

# 5. Tests pass
pnpm test
# Expected: exit 0

# 6. Build passes
pnpm build
# Expected: exit 0

Post-deploy smoke test

  1. Open chatbot-fe in a browser.
  2. Open any PDF attachment in the chatbot interface.
  3. Confirm: PDF renders correctly (pages visible, scrollable).
  4. Confirm: Browser console has no PDF.js worker errors or version mismatch errors.
  5. (Optional, security team) Open a crafted CVE-2024-4367 PoC PDF and confirm no JS execution occurs.

Rollback

If the upgrade causes a build or rendering regression that blocks a release:

  1. Revert the branch / revert the PR.
  2. Immediately deploy the workaround in a hotfix branch on the current 3.11.174:
    // All getDocument() calls — add isEvalSupported: false
    pdfjsLib.getDocument({ url: pdfUrl, isEvalSupported: false });
  3. File an incident. The workaround reduces exploitability but does not close the CVE — the upgrade must be retried.

5. Concern, Questions, or Known Limitations

Open Questions (implementer must resolve before Chunk 1)

#QuestionImpactOwner
OQ-1What is the exact bundler? (vite, webpack, other?)Determines exact workerSrc setup (Vite native ESM vs Webpack asset module)Implementer — read package.json devDependencies
OQ-2Is pdfjs-dist imported directly, or via react-pdf / another wrapper?If via react-pdf, the fix may be to upgrade react-pdf (which bundles pdfjs-dist) rather than pdfjs-dist directly — different package pin, different worker setupImplementer — grep -r 'react-pdf' package.json
OQ-3What is the test runner? (Jest / Vitest / other?)Chunk 4 approach differs — Vitest: no action; Jest: ESM transform neededImplementer — read package.json scripts + devDependencies
OQ-4Are there multiple pdfjs-dist usage sites or just one?More sites = more files to update in Chunk 3Implementer — grep result from Chunk 0
OQ-5Does pnpm-lock.yaml already have duplicate pdfjs-dist entries from transitive deps?If yes, pnpm dedupe may not suffice and pnpm overrides may be neededImplementer — scan lockfile before upgrade

Known Limitations

  • chatbot-fe is private — this RFC was authored without reading the actual source. All Existing Code Anchors are marked UNVERIFIED; the Source Verification table must be filled before execution begins.
  • Target pin is conservative (4.2.67 not latest 6.1.200) — closes CVE-2024-4367 at minimum scope. Further v4.x/v5.x/v6.x API changes are not analysed in this RFC. Upgrading beyond 4.2.67 is the implementer's decision after reviewing the changelog.
  • Other pnpm audit findings excluded — this RFC closes only CVE-2024-4367. Additional critical/high findings from pnpm audit are tracked separately.

6. Comment Logs

DateAuthorComment
2026-07-14Baghiz FirdausaRFC drafted. All mermaid blocks validated with mmdc — see validation note below. chatbot-fe source unread (private repo); Source Verification table left UNVERIFIED for implementer to fill before execution.

Mermaid validation: All 5 mermaid blocks in this RFC were validated with npx @mermaid-js/mermaid-cli mmdc before saving. All blocks parse without errors.


7. Ready for Agent Execution

Ready for agent execution: NO

Blockers before execution can start

#BlockerRequired action
B-1Source Verification table is entirely UNVERIFIEDImplementer must run Chunk 0 (repo grounding) and fill every row with concrete evidence
B-2OQ-1 (bundler) unresolvedDetermines Chunk 3 worker init pattern
B-3OQ-2 (direct vs react-pdf) unresolvedDetermines which package to upgrade
B-4OQ-3 (test runner) unresolvedDetermines Chunk 4
B-5DRI not assignedAssign a DRI before pull-in
B-6Infosec approver not assignedRequired for actively-exploited CVE

Ready once

All blockers above are resolved. After Chunk 0 fills Source Verification, re-evaluate §7 and flip to yes before opening Chunk 1.


Optional second pass: hand this RFC to rfc-reviewer for a scored review after blockers are resolved.