Turning an axios image stream into a string after Base64 Encoding it?

Viewed 2393

So far I have this:

const Fs = require('fs')  
const Path = require('path')  
const Axios = require('axios')
var {Base64Encode} = require('base64-stream');

const url = 'https://unsplash.com/photos/AaEQmoufHLk/download?force=true'

const response = await Axios({
      url,
      method: 'GET',
      responseType: 'stream'
    })

response.data.pipe(new Base64Encode())

This base 64 encodes the image. How can we turn that into a string. I tried something like this:

  function streamToString (stream) {
    const chunks = []
    return new Promise((resolve, reject) => {
      stream.on('data', chunk => chunks.push(chunk))
      stream.on('error', reject)
      stream.on('end', () => resolve(Buffer.concat(chunks).toString('utf8')))
    })
  }

const result = await streamToString(response.data.pipe(new Base64Encode()))

But it errors. Thoughts?

1 Answers

In your example you used the Base64encode module which already pumps out strings - so that made the above example fail (unless that was because of the top level await). You didn't actually need to convert the chunks to strings, since they already were strings, so a simple concatenation would do.

In fact the whole thing may be 10 times simpler with just using node.js streams:

const Axios = require('axios')
const {PassThrough} = require("stream");

const url = 'https://unsplash.com/photos/AaEQmoufHLk/download?force=true';

(async function() {
    const response = await Axios({
        url,
        method: 'GET',
        responseType: 'stream'
    });

    // we just pipe the data (the input carries it's own encoding)
    // to a PassThrough node stream that outputs `base64`.
    const chunks = response.data
        .pipe(new PassThrough({encoding:'base64'}));

    // then we use an async generator to read the chunks
    let str = '';
    for await (let chunk of chunks) {
        str += chunk;
    }

    // et voila! :)
    console.log(str);
})();
Related