html-pdf-chrome CreateOptions 5分钟配好
【免费下载链接】html-pdf-chromeHTML to PDF or image (jpeg, png, webp) converter via Chrome/Chromium项目地址: https://gitcode.com/gh_mirrors/ht/html-pdf-chrome
html-pdf-chrome 让 Chrome 直接渲染 HTML,吐出 PDF 或图片。整套配置就收在一个 CreateOptions 对象里。输出和你浏览器里看到的一致。
它比 wkhtmltopdf 强的地方在 CSS3 和 JS 支持完整,不会出现渲染偏差。比 puppeteer 轻,不背大框架,还能直接挂到一个常驻的 Chrome 上复用。
🚀 如何复用 Chrome 实例
接法只有两条路,二选一。
第一条,连常驻 Chrome。你自己把 Chrome 拉起来,打开调试端口,Node 连上去。每次生成 PDF 都不用重启浏览器,最快。官方也推荐这么做。
第二条,自动拉起。不传 host 和 port,库自己用 chrome-launcher 起一个 Chrome,用完就杀掉。省事但慢,高频场景别用。
用 pm2 把常驻 Chrome 拉起来,崩了能自动重启:
pm2 start google-chrome \ --interpreter none \ -- \ --headless --disable-gpu \ --hide-scrollbars \ --remote-debugging-port=9222代码里写port: 9222就连上它。走自动拉起的话,改传chromePath或chromeFlags,指定二进制和启动参数。
📐 printOptions 常用 8 个字段怎么调
printOptions 原样透传给 Chrome 的 printToPDF。不用全设,最常调的是下面 8 个。
| 字段 | 类型 | 作用 | 踩坑提示 |
|---|---|---|---|
| landscape | boolean | false 竖版,true 横版 | 横版时记得和纸张宽高一起换 |
| printBackground | boolean | 印不印背景色和图片 | 默认 false,彩色表头想显示就得开 |
| marginTop/Bottom/Left/Right | number | 四边边距,单位英寸 | 开页眉页脚时上下边距得大于 0 |
| paperWidth/paperHeight | number | 纸张尺寸,单位英寸 | 默认美版 Letter;A4 是 8.27×11.69 |
| scale | number | 内容缩放,0.1 到 2 | 内容被裁就调小 |
| displayHeaderFooter | boolean | 渲不渲染页眉页脚 | 不开的话模板写了也白写 |
| headerTemplate/footerTemplate | string | 页眉页脚的 HTML | 可用 pageNumber、totalPages 占位 |
| pageRanges | string | 页码范围,如 "1-5" | 不写就打印全部页 |
页眉页脚模板用得多,看一段就懂:
const options: htmlPdf.CreateOptions = { port: 9222, printOptions: { displayHeaderFooter: true, headerTemplate: '<div class="title">月度报表</div>', footerTemplate: '<div>第 <span class="pageNumber"></span> 页 / ' + '<span class="totalPages"></span> 页</div>', marginTop: 0.5, marginBottom: 0.5, }, };占位类名写好,Chrome 自动填页码。模板里想放图片,得 base64 内联,外链加载不出来。
📱 截图想截手机效果就改哪三个数
传了 screenshotOptions,输出就是图片;不传就是 PDF。
screenshotOptions: { format: 'png', // png、jpeg 或 webp quality: 85, // 只对 jpeg 生效 clip: { x: 0, y: 0, width: 800, height: 600 }, // 裁剪区域 }, deviceMetrics: { width: 375, // 手机逻辑宽 height: 667, // 逻辑高 deviceScaleFactor: 2, // 2 倍清晰 mobile: true, },deviceMetrics 管视口。要手机效果就盯住width、height、deviceScaleFactor这三个数。前两个填手机逻辑分辨率,最后一个给 2 或 3,图才够锐。顺手把mobile设 true,让 Chrome 模拟移动端的 UA。
⏱️ 什么时候再转:五种 completionTrigger
页面打开后别急着转,等内容好了再动。completionTrigger 五种,挑一个:
| 触发方式 | 适合什么页面 | 超时怎么给 |
|---|---|---|
| Timer | 不知道等什么,就等固定时长 | 参数是毫秒:new CompletionTrigger.Timer(3000) |
| Element | 数据回来后才渲染的内容,SPA | 第二个参数:new CompletionTrigger.Element('#app', 5000) |
| Event | 页面会主动派发自定义事件 | 第三个参数:new CompletionTrigger.Event('rendered', '#chart', 5000) |
| LifecycleEvent | 等网络或绘制信号稳定 | 第二个参数:new CompletionTrigger.LifecycleEvent('networkIdle', 5000) |
| Variable | 你自己控制变量,完成后置 true | 第二个参数:new CompletionTrigger.Variable('pageReady', 5000) |
静态页用networkIdle就够。SPA 建议用Element等关键元素出现。超时比实际加载时间略大一点,外层timeout再做一道兜底。
🔧 端到端:报表 PDF 和移动截图
带鉴权的报表 PDF,靠请求头带 token:
import * as htmlPdf from 'html-pdf-chrome'; async function monthlyReport() { const options: htmlPdf.CreateOptions = { port: 9222, extraHTTPHeaders: { Authorization: 'Bearer report-token' }, printOptions: { landscape: true, printBackground: true, marginTop: 0.5, marginBottom: 0.5, }, completionTrigger: new htmlPdf.CompletionTrigger.Timer(2000), timeout: 60000, }; const html = '<h1>月度报表</h1><p>数据……</p>'; const pdf = await htmlPdf.create(html, options); await pdf.toFile('monthly-report.pdf'); }移动端整页截图,还是改 deviceMetrics 那三个数:
import * as htmlPdf from 'html-pdf-chrome'; async function mobileShot() { const options: htmlPdf.CreateOptions = { port: 9222, screenshotOptions: { format: 'png' }, deviceMetrics: { width: 375, height: 667, deviceScaleFactor: 2, mobile: true, }, completionTrigger: new htmlPdf.CompletionTrigger.LifecycleEvent('networkIdle'), }; const img = await htmlPdf.create('https://example.com/mobile', options); await img.toFile('mobile.png'); }结果用 toFile 落盘,也能用 toBase64、toBuffer、toStream 转成别的形态。
🚨 五个翻车现场
连不上 9222 端口,报 Connection refused。确认 Chrome 是用--remote-debugging-port=9222起的,代码里的 port 要一致。
中文和 emoji 变方块。HTML 没声明字符集。补上<meta charset="UTF-8">,并确认服务器装有中文字体。
页面没加载完就转了,图是空的或内容残缺。把默认等待换成networkIdle,或改用Element等关键元素。
内存一直涨,常驻 Chrome 越跑越肥。用 pm2 定时重启,或开启clearCache: true。
headful 下字体缺失,可见模式里部分字变方块。装上 fonts-noto-cjk 之类的字体包再试。
完整字段含义以源码为准,类型定义在 CreateOptions.ts,用法示例见 README.md。
配置心法:五句话
优先连常驻 Chrome,别每次都重启。 超时给得比加载时间大一点,留余量。 completionTrigger 跟页面类型走,别傻等。 挂上 console 处理器,先看到报错。 字符集写死 UTF-8,少踩乱码坑。
【免费下载链接】html-pdf-chromeHTML to PDF or image (jpeg, png, webp) converter via Chrome/Chromium项目地址: https://gitcode.com/gh_mirrors/ht/html-pdf-chrome
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考