Search code examples
node.jslambda

How can I write a Lambda function in node.js that returns binary data?


I want to write a Lambda function in node.js that returns binary data. I'd like for the response header to be "application/octet-stream", but it isn't absolutely necessary.

It appears to be the case that the response header is always "application/json" and there isn't any way to change it.

The documentation for the callback function says: "The callback function takes two arguments: an Error and a response. The response object must be compatible with JSON.stringify."

I don't want anybody to "stringify" my data or convert it to JSON. I just want to return a buffer of bytes exactly as-is.


Solution

  • I think that you have two options, return a base64 encoded string or do a redirect to S3 which contains your binary blob.

    Your response is always a JSON object but you can specify the content-type and you can use base64 to encoding to send binary data through API Gateway.

    Base64 Encoding

    Without knowing much about your code consider this example:

    exports.handler = async (event) => {
        const result = Buffer.from('Hello World!', 'utf8')
        return {
          statusCode: 200,
          headers: {
            'Content-Type': 'application/octet-stream'
          },
          body: result.toString('base64'), // SGVsbG8gV29ybGQh
          isBase64Encoded: true
        }
    }
    

    You're returning an object but specifying the body is a base64 encoded string which API Gateway should transform into an octet-stream.

    You may need to configure API Gateway to allow */* media types. Here is an article with more details.

    S3 Redirect

    The other option, which would make more sense for large binary objects, would be to write your binary objects into S3 as files and then return a statusCode: 302 with a redirect url to a signed S3 url.

    Something like this:

    exports.handler = async (event) => {
        return {
          statusCode: 302,
          headers: {
            'Location': 'http://example.com/example.png'
          }
        }
    }