【问题标题】:Node.js get image from web and encode with base64Node.js 从 Web 获取图像并使用 base64 进行编码
【发布时间】:2013-06-15 13:14:48
【问题描述】:

我正在尝试从网络上获取图像并使用 base64 对其进行编码。

到目前为止,我所拥有的基本上是:

var request = require('request');
var BufferList = require('bufferlist').BufferList;

bl = new BufferList(),

request({uri:'http://tinypng.org/images/example-shrunk-8cadd4c7.png',responseBodyStream: bl}, function (error, response, body) 
{
    if (!error && response.statusCode == 200) 
    {
        var type = response.headers["content-type"];
        var prefix = "data:" + type + ";base64,";
        var base64 = new Buffer(bl.toString(), 'binary').toString('base64');
        var data = prefix + base64;
        console.log(data);
    }
});

这似乎非常接近解决方案,但我无法让它发挥作用。它识别数据类型并给出输出:

data:image/png;base64

但是缓冲区列表“bl”似乎是空的。

提前致谢!

【问题讨论】:

  • 只是一个完全疯狂的猜测,但我认为 request() 可能正在使用一个标头,该标头指示可能被某些站点阻止的代理以最大程度地减少抓取。
  • @BrettZamir 你这么认为吗?用 200 响应阻止请求似乎非常讨厌......
  • 请问:require('request') 是什么?在文档中找不到。我所知道的只是 http/https。
  • @Sebastian,是的,这只是一个疯狂的猜测......但这是我反复出现的问题之一,所以只是将其作为一次性使用......
  • @SebastianG,如果您在文档中找不到需要的内容,那么这意味着它来自...? :D

标签: node.js encoding express base64


【解决方案1】:

BufferList 已过时,因为它的功能现在在 Node 核心中。这里唯一棘手的部分是设置请求不使用任何编码:

var request = require('request').defaults({ encoding: null });

request.get('http://tinypng.org/images/example-shrunk-8cadd4c7.png', function (error, response, body) {
    if (!error && response.statusCode == 200) {
        data = "data:" + response.headers["content-type"] + ";base64," + Buffer.from(body).toString('base64');
        console.log(data);
    }
});

【讨论】:

  • 很好用,谢谢!但是有一个问题,为什么 request 不设置为任何编码?如果我跳过 .defaults({ encoding: null }) 部分,我仍然会得到某种结果。
  • encoding: null 告诉 request 你想要一个缓冲区,而不是一个字符串。字符串会给您带来无法使用的乱码数据,因为 base64 的全部意义在于对二进制进行编码。我在自己的 StackOverflow 问题 stackoverflow.com/questions/16619980/… 中得到了关于编码的答案,所以我很乐意将其付诸实施。
  • 解决方案:从本地运行生产
  • 愿所有的上帝保佑你......我知道这是一个编码问题,但我正在努力寻找如何在请求库中禁用它......
  • @DanKohn new Buffer 现在已弃用。 nodejs.org/api/buffer.html
【解决方案2】:

如果有人在使用 axios 作为 http 客户端时遇到同样的问题,解决方法是在请求选项中添加 responseType 属性,值为 'arraybuffer':

let image = await axios.get('http://aaa.bbb/image.png', {responseType: 'arraybuffer'});
let returnedB64 = Buffer.from(image.data).toString('base64');

希望对你有帮助

【讨论】:

  • 非常感谢!帮我节省了很多时间和挫折!
  • 我对这个和 axios 有很多问题,结果是响应类型是它的原因。非常感谢!
【解决方案3】:

最新,截至 2017 年底

好吧,在阅读了上面的答案和一些研究之后,我知道了一种新方法,不需要安装任何软件包http 模块(是内置的)就足够了!

注意:我在 node 6.x 版本中使用过,所以我猜它也适用于以上版本。

var http = require('http');

http.get('http://tinypng.org/images/example-shrunk-8cadd4c7.png', (resp) => {
    resp.setEncoding('base64');
    body = "data:" + resp.headers["content-type"] + ";base64,";
    resp.on('data', (data) => { body += data});
    resp.on('end', () => {
        console.log(body);
        //return res.json({result: body, status: 'success'});
    });
}).on('error', (e) => {
    console.log(`Got error: ${e.message}`);
});

希望对你有帮助!

另外,请查看更多关于 http.get(...) here 的信息!

【讨论】:

  • 这行得通。我必须在我的解决方案中同时使用 http 和 https 模块,因为现在大多数资源都是 https。不幸的是,您需要手动检查要使用的模块。见stackoverflow.com/a/45215071/4978821
  • 对我来说最好的答案!
【解决方案4】:

如果您知道图像类型,则它是带有 node-fetch 包的单行代码。可能不适合所有人,但我已经将 node-fetch 作为依赖项,所以如果其他人也有类似情况:

await fetch(url).then(r => r.buffer()).then(buf => `data:image/${type};base64,`+buf.toString('base64'));

【讨论】:

  • 简洁明了!
  • 效果很好! .buffer 已被弃用。这是新的方式:const blob = await response.arrayBuffer(); return `data:${response.headers.get("content-type")};base64,${Buffer.from(blob).toString("base64")}`;
【解决方案5】:

您可以使用base64-stream Node.js 模块,它是一个流式 Base64 编码器/解码器。这种方法的好处是可以转换图片,无需将整个内容缓存到内存中,也无需使用请求模块。

var http = require('http');
var base64encode = require('base64-stream').Encode;

http.get('http://tinypng.org/images/example-shrunk-8cadd4c7.png', function(res) {
    if (res.statusCode === 200)
        res.pipe(base64encode()).pipe(process.stdout);
});

【讨论】:

    【解决方案6】:

    如果您使用的是 axios,那么您可以按照以下步骤操作

    var axios = require('axios');
    const url ="put your url here";
    const image = await axios.get(url, {responseType: 'arraybuffer'});
    const raw = Buffer.from(image.data).toString('base64');
    const base64Image = "data:" + image.headers["content-type"] + ";base64,"+raw;
    

    您可以使用 decode base64 进行检查。

    【讨论】:

      【解决方案7】:

      另一种使用节点获取的方法,它分解了每个变量的步骤:

      const fetch = require('node-fetch');
      
      const imageUrl = "Your URL here";
      const imageUrlData = await fetch(imageUrl);
      const buffer = await imageUrlData.buffer();
      const contentType = await imageUrlData.headers.get('content-type');
      const imageBas64 = 
      `data:image/${contentType};base64,`+buffer.toString('base64');
      

      【讨论】:

        【解决方案8】:

        我用于将图像加载和编码为 base64 字符串 node-base64-image npm 模块。

        下载并编码图像:

        var base64 = require('node-base64-image');
        
        var options = {string: true};
        base64.base64encoder('www.someurl.com/image.jpg', options, function (err, image) {
            if (err) {
                console.log(err);
            }
            console.log(image);
        });
        

        编码本地图像:

        var base64 = require('node-base64-image');
        
        var path = __dirname + '/../test.jpg',
        options = {localFile: true, string: true};
        base64.base64encoder(path, options, function (err, image) {  
            if (err) { console.log(err); }  
            console.log(image);  
        }); 
        

        【讨论】:

        【解决方案9】:

        Oneliner:

        Buffer.from(
            (
              await axios.get(image, {
              responseType: "arraybuffer",
            })
          ).data,
          "utf-8"
        ).toString("base64")
        

        【讨论】:

          猜你喜欢
          • 2017-03-20
          • 1970-01-01
          • 1970-01-01
          • 2017-11-02
          • 2018-10-26
          • 1970-01-01
          • 1970-01-01
          • 2013-10-08
          • 2011-09-05
          相关资源
          最近更新 更多