最近写了个node小程序来爬取网页上的图片,不知道是不是我要抓取的内容是动态生成的,地址后缀是以.do
结尾而不是以.png/.jpg
结尾的原因,以为是个小case,没想到踩坑了!!!
在百度和bing上找了好久,都没找出来原因所在,后来换了种思路才解决,专门记下来给大家避雷!!!
以爬取png图片为例子,我原本的思路是axios.get
请求图片地址,然后把返回内容保存下来。
大致如下:
const fs = require('fs');
axios.get(img_url, { responseType: Buffer })
.then(async function (response) {
let d = response.data;
fs.writeFileSync(`${fileName}.png`, d);
}).catch(e => {
console.error(e);
});
复制代码
万万没想到,就这么短短几行的代码,踩到了天坑,图片显示不出来!
然后我先后把responseType
改成了ArrayBuffer
和String
还是不行,然后在想,会是文件编码的问题吗?
把writeFileSync
的encoding
乱改一通,从binary
、ascii
试到utf16le
都不行。
尼玛
然后开始上网找,先后安装了据说能够识别Buffer类型的FileType
,识别我axios取回来的buffer显示undefined
;安装了据说能够处理图片的shark
,显示格式出错;安装了据说处理png图片很专业的pngjs
,这个起码告诉我Error: Invalid file signature
用hexEditor可以看到编码(左:正常图,右:程序抓取)的确不一样。
行吧...然后试了n多方法,终于找到一种能行的!不用Buffer,直接用Stream!
const writer = fs.createWriteStream(img_save_path)
let response = await axios.get(url, {
responseType:"stream"
})
response.data.pipe(writer)
复制代码
然后就可以了。
不知道为毛。