# Node+Puppeteer+Chromium打印容器部署手册
# 背景
标准产品的CAP4报表等功能由于涉及很多后台算力,在进行报表打印时,均采用后端无头浏览器打印技术。
标准产品默认的后台打印使用PhantomJS技术,这种技术在信创环境支持较弱,同时随着PhantomJS不再维护,其功能在非信创环境下的兼容性也越来越差。
当项目上遇到无法使用默认的PhantomJS打印时,则需要考虑替代方案,目前市面推荐的是采用“Node+Puppeteer+Chromium”替代(后文均简称Puppeteer)。
Puppeteer: 是 Google Chrome 的 Headless 版本的一个工具,它提供了一个高级的 API 来控制 Chrome。与 PhantomJS 相比,Puppeteer 提供了更为强大的功能,并且是 Chrome 团队官方支持的项目。
哪些需要更换Puppeteer方案?
1、麒麟信创系统下,使用CAP4表单打印功能时(如报表打印、报表转发、CAP4表单转新闻公告空白或失败),提示“执行截图服务失败”。
2、客开使用htmltopdf接口,后台打印生成PDF进行归档操作失败,查看日志均体现在PhantomJS不可用。
3、移动端进行打印时,显示不全,上报BUG后研发建议更换为Puppeteer模式。
本文档提供详细安装部署步骤。
- 1、部署puppeteer的docker容器,记录容器ip和port
- 2、A8停服,打代码补丁
- 3、A8配置base/config/plugin.properties配置文件,见参考文件
- 4、启动A8服务,测试报表截图、表单转新闻、表单转公告功能
# Linux
# 先决条件
部署puppeteer之前必须先部署docker环境,请参考文档:https://open.seeyoncloud.com/v5doc/142/1190/2230.html 部署
# 一、puppeteer容器部署
# 1、下载镜像的压缩包
- amd64架构请下载:
链接: https://puppeteer-chromium.obs.cn-north-4.myhuaweicloud.com/amd64/puppeteer_chromium.tar.gz
wget https://puppeteer-chromium.obs.cn-north-4.myhuaweicloud.com/amd64/puppeteer_chromium.tar.gz
- arm64架构请下载:
链接: https://puppeteer-chromium.obs.cn-north-4.myhuaweicloud.com/arm64/puppeteer_chromium.tar.gz
wget https://puppeteer-chromium.obs.cn-north-4.myhuaweicloud.com/arm64/puppeteer_chromium.tar.gz
# 2、加载镜像到服务器
新建一个临时构建目录:例如 /tmp/puppeteer_chromium
,然后将第一步中下载的 puppeteer_chromium.tar.gz 放在 /tmp/puppeteer_chromium
目录下。然后执行以下命令:
cd /tmp/puppeteer_chromium # 切换目录
gzip -d -c puppeteer_chromium.tar.gz > puppeteer_chromium.tar # 解压
docker load -i puppeteer_chromium.tar # 导入镜像
docker images # 查看镜像
docker tag puppeteer_chromium:latest puppeteer_chromium:base # 重命名镜像,作为基础镜像
# 3、由于字体的版权原因,需要使用本地字体重新构建镜像
在 /tmp/puppeteer_chromium
目录中新建一个 fonts_local
目录,并需要手动放入字体文件,具体的字体文件可以从服务器上复制 ,用来存放字体文件。
fonts_local 中需要手动放进字体文件,具体的字体文件可以从服务器上复制
例如:
可以从linux服务器的 /usr/share/fonts/
下复制所有字体到 /tmp/puppeteer_chromium/fonts_local/
目录下;
也可以从windows服务器的 C:\Windows\Fonts\
下复制所有字体到 /tmp/puppeteer_chromium/fonts_local/
目录下;
字体文件的原则是可以多,不能少,少了某种字体可能会在打印时影响打印效果。
cd puppeteer_chromium # 切换目录
# 重构镜像
cat <<EOF > Dockerfile
FROM puppeteer_chromium:base
# 复制本地字体文件到系统字体目录
COPY fonts_local /usr/share/fonts/truetype/custom/
# 更新字体缓存
RUN fc-cache -f -v
# 启动应用(根据你的应用入口文件调整)
ENTRYPOINT ["java", "-jar", "util-0.2.3-SNAPSHOT.jar"]
CMD ["-Xms256m", "-Xmx512m"]
EOF
# 准备好了字体目录fonts_local才能运行下面
docker build -t puppeteer_chromium . # 重新构建镜像,注意命令行最后有个点表示当前目录
# 4、运行puppeteer容器
# 以下命令二选一
docker run -d --name puppeteer_chromium --restart always -p 16395:16395 puppeteer_chromium # 使用默认jvm参数运行:-Xms256m -Xmx512m
docker run -d --name puppeteer_chromium --restart always -p 16395:16395 puppeteer_chromium -Xms512m -Xmx1024m # 指定jvm参数运行
# 5、测试puppeteer容器
docker exec puppeteer_chromium node test.js "/app/chrome/chrome" "https://www.baidu.com" # 访问百度首页进行打印,内网环境可以访问其他网址
docker cp puppeteer_chromium:/app/puppeteer-test.png . # 从容器复制打印的图片到当前目录进行查看
如果能看到图片,代表容器部署成功,否则都是有问题的!!!
# 6、查看容器打印服务的日志
docker exec -it puppeteer_chromium bash # 进入容器
# 成功进入容器的标志是当前工作目录会改变,可以使用 ls 命令查看当前目录的文件列表,如下图表示成功
# 打印服务的日志在下图中的logs目录中
如果OA打印异常,但是下面的日志没有更新,则表示容器打印服务没有被成功调用到。
排查思路:
1、排查 base/conf/plugin.properties 配置文件中的配置是否正确
2、OA服务器到打印服务的网络是否畅通
3、查看OA的cap.log日志文件
# 7、高级扩展,非必须
可以参照以下 Dockerfile 重新构建自己的镜像
amd64
# 平台为 amd64
FROM --platform=linux/amd64 node:20.18.1-slim
WORKDIR /app
# 更新源并安装必要的包
RUN sed -i 's/deb.debian.org/mirrors.aliyun.com/' /etc/apt/sources.list.d/debian.sources && \
echo "deb http://mirrors.aliyun.com/debian buster main" > /etc/apt/sources.list && \
echo "deb http://mirrors.aliyun.com/debian-security buster/updates main" >> /etc/apt/sources.list && \
echo "deb http://mirrors.aliyun.com/debian buster-updates main" >> /etc/apt/sources.list && \
apt-get clean && \
apt-get update && \
apt-get install -y \
ca-certificates \
fonts-liberation \
libasound2 \
libatk1.0-0 \
libatk-bridge2.0-0 \
libcups2 \
libdbus-1-3 \
libdrm2 \
libgbm1 \
libgtk-3-0 \
libnspr4 \
libnss3 \
libxcomposite1 \
libxdamage1 \
libxrandr2 \
xdg-utils \
wget \
libx11-xcb1 \
libx11-6 \
libxext6 \
libxfixes3 \
libxrender1 \
libxcb1 \
libxss1 \
libxcb-dri3-0 \
libxtst6 \
vim \
locales \
--no-install-recommends && \
echo "zh_CN.UTF-8 UTF-8" >> /etc/locale.gen && \
locale-gen zh_CN.UTF-8 && \
echo "LANG=zh_CN.UTF-8" > /etc/default/locale && \
apt-get clean && \
rm -rf /var/lib/apt/lists/* && \
npm install puppeteer-core@23.11.1 --registry https://registry.npmmirror.com/
# 设置语言环境变量
ENV LANG=zh_CN.UTF-8 \
LANGUAGE=zh_CN:zh \
LC_ALL=zh_CN.UTF-8
# 更新字体缓存
RUN fc-cache -f -v
# 复制应用和其他必要文件
COPY chrome-linux64 /app/chrome
COPY jdk /app/jdk
COPY test.js /app/test.js
COPY util-0.2.3-SNAPSHOT.jar /app/util-0.2.3-SNAPSHOT.jar
COPY screenPdfCapture.js /app/screenPdfCapture.js
# 设置 Puppeteer 使用本地的 Chromium
ENV PUPPETEER_EXECUTABLE_PATH=/app/chrome/chrome
ENV PATH /app/jdk/bin:$PATH
EXPOSE 16395
# 启动应用
ENTRYPOINT ["java", "-jar", "util-0.2.3-SNAPSHOT.jar"]
CMD ["-Xms256m", "-Xmx512m"]
arm64
# 平台为 arm64
FROM --platform=linux/arm64 node:20.18.1-slim
WORKDIR /app
# 更新源并安装必要的包
RUN sed -i 's/deb.debian.org/mirrors.aliyun.com/' /etc/apt/sources.list.d/debian.sources && \
echo "deb http://mirrors.aliyun.com/debian buster main" > /etc/apt/sources.list && \
echo "deb http://mirrors.aliyun.com/debian-security buster/updates main" >> /etc/apt/sources.list && \
echo "deb http://mirrors.aliyun.com/debian buster-updates main" >> /etc/apt/sources.list && \
apt-get clean && \
apt-get update && \
apt-get install -y \
ca-certificates \
fonts-liberation \
libasound2 \
libatk1.0-0 \
libatk-bridge2.0-0 \
libcups2 \
libdbus-1-3 \
libdrm2 \
libgbm1 \
libgtk-3-0 \
libnspr4 \
libnss3 \
libxcomposite1 \
libxdamage1 \
libxrandr2 \
xdg-utils \
wget \
libx11-xcb1 \
libx11-6 \
libxext6 \
libxfixes3 \
libxrender1 \
libxcb1 \
libxss1 \
libxcb-dri3-0 \
libxtst6 \
vim \
locales \
--no-install-recommends && \
echo "zh_CN.UTF-8 UTF-8" >> /etc/locale.gen && \
locale-gen zh_CN.UTF-8 && \
echo "LANG=zh_CN.UTF-8" > /etc/default/locale && \
apt-get clean && \
rm -rf /var/lib/apt/lists/* && \
npm install puppeteer-core@23.11.1 --registry https://registry.npmmirror.com/
# 设置语言环境变量
ENV LANG=zh_CN.UTF-8 \
LANGUAGE=zh_CN:zh \
LC_ALL=zh_CN.UTF-8
# 更新字体缓存
RUN fc-cache -f -v
# 复制应用和其他必要文件
COPY chrome-linux64 /app/chrome
COPY jdk /app/jdk
COPY test.js /app/test.js
COPY util-0.2.3-SNAPSHOT.jar /app/util-0.2.3-SNAPSHOT.jar
COPY screenPdfCapture.js /app/screenPdfCapture.js
# 设置 Puppeteer 使用本地的 Chromium
ENV PUPPETEER_EXECUTABLE_PATH=/app/chrome/chrome
ENV PATH /app/jdk/bin:$PATH
EXPOSE 16395
# 启动应用
ENTRYPOINT ["java", "-jar", "util-0.2.3-SNAPSHOT.jar"]
CMD ["-Xms256m", "-Xmx512m"]
# 二、补丁包部署
下载链接: https://puppeteer-chromium.obs.cn-north-4.myhuaweicloud.com/puppeteer%E6%89%93%E5%8D%B0%E8%A1%A5%E4%B8%81.zip
1、**注意修改其中的 puppeteer打印补丁/A8配置文件 **
plugin.properties 配置文件放进A8的 base/conf 目录下,如果A8已经存在 plugin.properties 配置文件,请手动将补丁的配置项合并进去。
2、seeyon.zip才是补丁文件,解压放进A8的 webapps 目录下
3、补丁源码-cap-runtime.zip 文件是该补丁的源码,源码工程是cap-runtime,客开可以根据需要合并该补丁源码。
# Windows
# 安装node 20.18.1
下载地址:https://nodejs.org/en/download
选择msi或者二进制包都可以,二进制包类型的,建议将node加入环境变量
msi格式的直接安装即可
# 二进制包安装(可选)
将下载的node-v20.18.3-win-x64.zip 解压至 d:\node-v20.18.3-win-x64
打开系统属性,右键点击“此电脑”或“我的电脑”,选择“属性”,点击“高级系统设置”。 在“系统属性”窗口中,点击“环境变量”按钮。编辑系统变量: 在“系统变量”部分,找到并选择“Path”变量,然后点击“编辑”。 在“编辑环境变量”窗口中,点击“新建”按钮,添加 Node 的安装路径(例如:d:\node-v20.18.3-win-x64\)。
验证配置: 打开命令提示符(CMD),输入以下命令以验证 Node.js 和 npm 是否正确安装:
node -v
npm -v
# 如果安装成功,你将看到 Node.js 和 npm 的版本号。
# 安装puppeteer
新建目录d:\puppeteer_chromium
打开命令提示符(CMD),执行以下命令
cd /d d:\puppeteer_chromium
# 需要通外网
npm install puppeteer-core@23.11.1 --registry https://registry.npmmirror.com/
安装完成后会生成以下文件
# 下载chromium
将chromium下载并解压至d:\puppeteer_chromium
https://storage.googleapis.com/chrome-for-testing-public/131.0.6778.204/win64/chrome-win64.zip
# 验证测试
新建文件test.js
const puppeteer = require('D:/puppeteer_chromium/node_modules/puppeteer-core');
console.log(process.argv);
(async () => {
const browser = await puppeteer.launch({
headless: true,
executablePath: process.argv[2], // 确保这里提供的是正确的浏览器可执行文件路径
args: ['--no-sandbox', '--disable-setuid-sandbox'],
defaultViewport: {
width: 1245,
height: 700
}
});
const page = await browser.newPage();
await page.goto(process.argv[3]);
await page.screenshot({ path: 'puppeteer-test.png', fullPage: true });
await browser.close();
})();
打开CMD执行命令,会在当前目录生成一个png图片
node test.js d:\puppeteer_chromium\chrome-win64\chrome.exe http://www.baidu.com
# 补丁包部署
下载地址:https://puppeteer-chromium.obs.cn-north-4.myhuaweicloud.com/puppeteer%E6%89%93%E5%8D%B0%E8%A1%A5%E4%B8%81.zip
# 微服务启动
将补丁包内的docker容器
目录下的screenPdfCapture.js
和util-0.2.3-SNAPSHOT.jar
拷贝到d:\puppeteer_chromium
目录下
打开命令提示符
# 进入d:\puppeteer_chromium目录
cd /d d:\puppeteer_chromium
# 这里假设OA目录的jdk在 d:\Seeyon\A8\jdk,请根据客户实际OA环境替换路径
d:\Seeyon\A8\jdk\bin\java.exe -jar util-0.2.3-SNAPSHOT.jar
# 更新补丁
注意打补丁前先备份
将puppeteer打印补丁/补丁目录下对应版本的补丁更新到OA
将puppeteer打印补丁/A8配置文件/下的plugin.properties
配置文件合并到OA的base/conf/plugin.properties
注意填写路径时使用/
做路径分隔符
快速跳转
