fix(pdf): make write_pdf Chrome acquisition self-healing and fail clearly#550
fix(pdf): make write_pdf Chrome acquisition self-healing and fail clearly#550wonderwhy-er wants to merge 1 commit into
Conversation
…arly write_pdf could fail on Windows (and any OS) with an opaque "Failed to launch the browser process" on machines without system Chrome. Three issues combined: 1. installChrome() downloaded the 'stable' Chrome-for-Testing build into DC's private cache, while md-to-pdf's bundled Puppeteer looks for a different PINNED build in the default cache. The two never aligned. 2. On any install failure, getChromePath() cached `undefined` for the whole process, so a single transient failure (offline/proxy/locked-down network) permanently disabled PDF generation until restart. 3. When getChromePath() returned undefined, parseMarkdownToPdf silently fell through to md-to-pdf's bundled Puppeteer, which resolves the pinned build in a cache DC never populates -> opaque launch error. Fixes: - Install the Chrome build PINNED by the co-bundled puppeteer-core (falls back to 'stable' if the pin can't be read), so the downloaded browser is guaranteed compatible with the launcher and lives where it's expected. - Do not cache `undefined` on install failure; leave the cache unset so the next write_pdf retries the download. - Replace the silent bundled-Puppeteer fallback with an actionable error that includes the underlying install failure reason. Verified: auto-fetch downloads a working Chrome (~19s) and now targets the pinned build; project builds clean.
|
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: defaults Review profile: CHILL Plan: Pro Run ID: 📒 Files selected for processing (1)
📝 WalkthroughWalkthroughModifies Chrome resolution logic in the PDF markdown tool: adds tracking of the last Chrome installation error, prefers a pinned puppeteer-core Chrome revision during installation with stable-channel fallback, avoids permanently caching install failures, and throws an actionable error while unconditionally wiring executablePath in parseMarkdownToPdf. ChangesChrome Resolution and Error Handling
Estimated code review effort: 3 (Moderate) | ~20 minutes Sequence Diagram(s)sequenceDiagram
participant Caller
participant parseMarkdownToPdf
participant getChromePath
participant lastChromeError
Caller->>parseMarkdownToPdf: request PDF generation
parseMarkdownToPdf->>getChromePath: resolve Chrome executable
getChromePath->>getChromePath: attempt install / lookup
alt install fails
getChromePath->>lastChromeError: store error
getChromePath-->>parseMarkdownToPdf: return undefined
parseMarkdownToPdf->>lastChromeError: read last error
parseMarkdownToPdf-->>Caller: throw actionable error
else path resolved
getChromePath-->>parseMarkdownToPdf: return chromePath
parseMarkdownToPdf->>parseMarkdownToPdf: set launch_options.executablePath
parseMarkdownToPdf-->>Caller: continue PDF generation
end
Possibly related PRs
Suggested labels: 🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✨ Finishing Touches📝 Generate docstrings
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
Problem
write_pdfcould fail with an opaque "Failed to launch the browser process" on machines without system Chrome — even though the codebase does have logic to download Chrome automatically. Investigation on a Windows box (with the Puppeteer-pinned Chrome build removed to simulate a fresh machine) traced it to three combining issues:installChrome()downloaded thestableChrome-for-Testing build into Desktop Commander's private cache, whilemd-to-pdf's bundled Puppeteer looks for a different, pinned build in the default cache (~/.cache/puppeteer). The two resolution paths never aligned, so DC's own install could never satisfy the fallback.getChromePath()cachedundefinedfor the entire process lifetime. A single transient failure (offline, proxy, locked-down network) permanently disabled PDF generation until restart — no retry.getChromePath()returnedundefined,parseMarkdownToPdfsilently omittedexecutablePathand letmd-to-pdffall through to bundled Puppeteer, which hunts for the pinned build in a cache DC never populates → the opaque launch error the user actually sees.The auto-fetch mechanism itself works (verified: downloads a working Chrome in ~19s). The failures came from these three gaps around it.
Fixes (all in
src/tools/pdf/markdown.ts)installChrome()now resolves the Chrome build pinned by the co-bundledpuppeteer-core(viaPUPPETEER_REVISIONS), falling back to thestablechannel if the pin can't be read. The downloaded browser is now guaranteed compatible with the launcher and lives where it's expected.undefinedon install failure. Leaving the cache unset lets the nextwrite_pdfretry the download instead of short-circuiting forever.Verification
puppeteer-corepin rather than driftingstable).npm run buildcompiles clean (no TS errors).read_file/write_file/edit_block/list_directory/PDF read + write all continue to work on Windows.Notes
executablePathand PDFs generate as before.Summary by CodeRabbit