首页IT科技node.js canvas(使用node-canvas在服务端渲染echarts图表解析)

node.js canvas(使用node-canvas在服务端渲染echarts图表解析)

时间2025-09-21 20:41:13分类IT科技浏览6210
导读:踩了很长时间的坑,总算是能跑起来了 但是如果要我给echarts的SSR一个评价,那就是不好用……可能是我太菜了。而且,因为我是Windows用户,这个过程对Windows极其不友好。...

踩了很长时间的坑              ,总算是能跑起来了

但是如果要我给echarts的SSR一个评价                       ,那就是不好用……可能是我太菜了                。而且        ,因为我是Windows用户           ,这个过程对Windows极其不友好                      。

友情提示:入坑请慎重

在服务端渲染图表                      ,绕不开的一个问题就是            ,没有DOM怎么绘图?这个主要有两种解决方案        ,一个是用那些headless的浏览器去渲染                      ,然后进行截图;另一个就是在Node环境下模拟DOM元素                ,比如我在这里想用canvas    ,就得装个node-canvas;如果想用SVG                      ,就得用JSDOM一类的库       。我这里主要是用的canvas                    ,所以就用node-canvas了            。

首先,需要安装node-canvas和echarts                       。echarts不用多说                  ,但是有一点                        ,不建议使用官方推荐的node-echarts    ,版本陈旧              ,而且依赖的库新版本的Node(12.x)不支持          。

node-canvas安装请参考官方文档                       ,因为安装流程比较复杂        ,尤其是Windows用户:https://github.com/Automattic/node-canvas/wiki/Installation:-Windows

当然           ,因为众所周知的原因                      ,最后一步用npm install安装node-canvas是个问题            ,因为它预编译的安装包好像是在AWS上        ,大概率会卡在这里:

node-pre-gyp WARN Using request for node-pre-gyp https download

或者                      ,还有可能卡在这里:

node-pre-gyp info install unpacking Release/ node-pre-gyp info install unpacking Release/canvas.exp node-pre-gyp info install unpacking Release/canvas.ilk

然后还有可能直接报错        。解决方案就是                ,加个–build-from-source    ,不用他编译好的                      ,而是在我们本机进行编译:

npm install canvas --verbose --build-from-source

在这个过程中                    ,还有可能报错,比较常见的有这些

1                、找不到node-gyp                        。

决办法:npm install -g node-gyp                  ,装一个就是了              。不过一般来说会自带才对……

2                      、fatal error C1083: 无法打开包括文件: “cairo.h                ”: No such file or directory    。

解决方法:参考官方文档安装GTK 2                        ,并放在合适的路径                        。

3       、fatal error C1083: 无法打开包括文件: “jpeglib.h                      ”: No such file or directory

解决方法:参考官方文档安装libjpeg-turbo    ,并放在合适的路径                  。

注意              ,对于Windows用户                       ,一定要安装for VC++的版本        ,不要装成for gcc的版本。

4            、Error: Cannot find module ../build/Release/canvas.node

解决方法:进入node_modules/canvas目录           ,然后使用node-gyp configure build手动编译                    。

5                       、gyp: binding.gyp not found

解决方法:同4                      。还有一种可能是缺少windows-build-tools                      ,这个在第7点中说    。

6          、node.lib已损坏                。

解决方法:升级Node版本            ,或者尝试Node安装包的repair功能                      。大概率是Node没装好        ,或者你使用了canvas-prebuilt这个已经废弃的库       。实测升级到最新版本12.16.1可以修复            。

7        、与windows-build-tools相关的一系列错误                       。

解决方法:npm install --global --production windows-build-tools

但是在此过程中可能会出现一系列问题          。可能会卡在这里:

Python 2.7.16 is already installed, not installing again.

也有可能卡在这里:

Successfully installed Python 2.7

或者提示安装完了                      ,但一直没有退出                ,请往下看        。

第一次卡住的时候    ,尝试重复一遍install                      ,如果解决了那自然最好                    ,如果没解决,甚至报错:

Error: EBUSY: resource busy or locked

那么我们可能是遇到了同样的问题                        。

网上有两种方案                  ,我放在这里做个参考                        ,虽然对我来说都没用就是了:

1                        、先安装一个旧版本npm install --global --production windows-build-tools@4.0.0    ,然后重新npm install -g --production windows-build-tools              ,就可以了              。

2              、针对resource busy or locked的报错                       ,先在任务管理器里kill掉BuildTolls_Full.exe这个进程        ,然后去C:\Users\<你的用户名>\.windows-build-tools里找到build-tools-log.txt           ,在这个文件的最后增加一行:

Variable: IsInstalled = 1

保存后重新install    。

但是这两种对我来说都没用                        。后来                      ,我无意中看到一个方法            ,死马当活马医        ,居然成了……说起来也很迷幻                      ,加个–verbose就好了:

npm install --global --production --verbose windows-build-tools

到了这里                ,基本上就可以开始了                  。其实方法并不神秘    ,主要就是这么一个方法:

const path = require(path) const { createCanvas } = require(canvas) const echarts = require(echarts) function generateImage(options) { const canvas = createCanvas(600, 600) // 600 * 600的canvas const ctx = canvas.getContext(2d) ctx.font = 12px echarts.setCanvasCreator(() => canvas) // 使用node-canvas const chart = echarts.init(canvas) options.animation = false options.textStyle = { fontSize: 12 } chart.setOption(options) // 就是echarts的options return chart.getDom().toBuffer() // 返回buffer }

这里也可以用fs.writeFileSync来进行文件读写                      ,不过我更倾向于返回buffer流                    ,个人爱好而已。

不过,返回buffer流的话                  ,前端需要一些处理                        ,以axios为例    ,需要设置responseType为blob              ,然后用createObjectURL来处理blob                       ,然后把url放到img里去:

const { data } = await axios.get(/api/chart, { responseType: blob }) URL.createObjectURL(data) // 放进img.src的url

最终效果差不多是这样:

同时        ,服务端渲染还面临着服务端不支持中文导致乱码           ,图片不清晰等问题                      ,这些我还没有特别好的处理办法            ,只能看情况进行处理                    。

我只说说我试过有用的办法

1    、针对乱码问题        ,node-canvas 2.x提供了一个导入字体的方法registerFont()                      ,可以指定中文字体                      。但是我并不喜欢这个方法                ,平白无故增加静态资源的数量    。

据说在服务器上装好中文字体可以解决    ,但在我这里没用                。

2                        、图片不清晰                      ,可以在init的时候增大像素比:

echarts.init(canvas, null, {devicePixelRatio: 2});

但是这又有一个问题                    ,这么弄出来的图片大小会翻倍                      。本来我用SSR就是希望提高性能,为了清晰度还得牺牲性能                  ,就有点本末倒置了       。

总的来说                        ,目前我还没有发现对echarts进行SSR的好处    ,可能用那些更轻量的图表库配合SVG效果会比较好              ,比如D3            。可能有用的场景就是显示那些对清晰度要求不太高的图表                       ,比如图表的动态缩略图        ,因为有时候可能会有这样的需求           ,虽然是缩略图或者是示意图                      ,也希望能够动态更新            ,因为前后数据变化可能比较大                       。

以上为个人经验        ,希望能给大家一个参考                      ,也希望大家多多支持本站          。

参考资料

https://github.com/Automattic/node-canvas/issues/1468#issuecomment-522961098

https://github.com/mapbox/node-pre-gyp/issues/477#issuecomment-534231739

声明:本站所有文章                ,如无特殊说明或标注    ,均为本站原创发布        。任何个人或组织                      ,在未征得本站同意时                    ,禁止复制                  、盗用、采集                    、发布本站内容到任何网站                      、书籍等各类媒体平台                        。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理              。

创心域SEO版权声明:以上内容作者已申请原创保护,未经允许不得转载,侵权必究!授权事宜、对本内容有异议或投诉,敬请联系网站管理员,我们将尽快回复您,谢谢合作!

展开全文READ MORE
vmware12安装教程图解(关于VMware12 下安装与配置CentOS 6.5 64位 的方法图文教程) monitor program(monitor.exe是什么进程 有什么作用 monitor进程查询)