loganhuskins
loganhuskins

Reputation: 1469

Stream Response into HTTP Response

I have an API that is trying to make an HTTP request to an API that streams and image back to the me, then either stream that image back to the client making the request to me or wait until the image has been streamed to me and send it all at once.

I am using Express and request-promise.

Here's a shortened version of my code.

const express = require('express');
const router = express.Router();
const request = require('request-promise');

const imgFunc = async () => {
  try {
    const response = await request.get({
      method: 'GET',
      uri: `http://localhost:8080`,
    });
    return response;
  } catch(err) {
    console.log(err);
  }
};

router.get('/', async function(req, res, next) {
  try {
    const response = await imgFunc();
    return res.send(response);
  } catch (err) {
    console.log(err);
  }
});

module.exports = router;

The image that I get back is just what I assume is the binary data and I don't know if I need to do something at the request-promise level to make that right or when I send it back to the client.

The server that I have running at localhost:8080 mimics the actual server that I will be hitting when this is all said and done.

Upvotes: 18

Views: 43857

Answers (2)

Talha Noyon
Talha Noyon

Reputation: 854

you could pipe the streams directly through axios

const express = require('express');
const router = express.Router();
const axios = require("axios");

router.get('/', function(req, res) {
    const link = 'https://app.idesk360.com/media/logos/iDeskLoginTxt.png';
    const arrayBuffer = await axios.get(link, {responseType: 'stream'});
    const contentType = arrayBuffer.headers["content-type"];
    res.setHeader('content-type', contentType);
    arrayBuffer.data.pipe(res);
});

module.exports = router;

Upvotes: 3

skirtle
skirtle

Reputation: 29092

You could pipe the streams directly rather than using request-promise.

const express = require('express');
const router = express.Router();
const https = require('https');

router.get('/', function(req, res) {
    const url = 'https://www.gravatar.com/avatar/2ea70f0c2a432ffbb9e5875039645b39?s=32&d=identicon&r=PG&f=1';

    const request = https.get(url, function(response) {
        const contentType = response.headers['content-type'];

        console.log(contentType);

        res.setHeader('Content-Type', contentType);

        response.pipe(res);
    });

    request.on('error', function(e){
        console.error(e);
    });
});

module.exports = router;

Or using the request library on which request-promise is based:

const express = require('express');
const router = express.Router();
const request = require('request');

router.get('/', function(req, res) {
    const url = 'https://www.gravatar.com/avatar/2ea70f0c2a432ffbb9e5875039645b39?s=32&d=identicon&r=PG&f=1';

    request.get(url).pipe(res);
});

module.exports = router;

Upvotes: 27

Related Questions