1

Duplicate Question explanation: This question is not a duplicate of this one because I am trying to submit the image via a lambda function not straight to S3. I have to go through lambda to verify the user and permissions as well as make DB calls to find out where the data should be stored and to update the DB on the data location.

I am trying to use Lambda to put a binary image into S3. The image gets posted to an API gateway endpoint and proxied to the lambda function. The function successfully puts the data into an S3 object, but when I download and read the object (via console) it is always corrupted, sometimes smaller than the input object, and unable to be opened.

I think corruption has something to do with the multipart/form-data and something potentially being added onto the file/encoding the file, but I can't exactly figure out how to extract the image data directly.

How do I properly put the multipart/form-data image into S3?

React Native code to post to lambda

const body = new FormData();
body.append('photo', {
  uri: image.image,
  name: image.name,
  type: image.type,
});

fetch('https://ov2eat1o5h.execute-api.us-east-1.amazonaws.com/dev/uploadImage', {
  method: 'POST',
  headers: {
    Authorization: token,
    'Content-Type': 'multipart/form-data',
  },
  body,
})
  .then(response => response.json())
  .then(responseJson => {
    console.log(responseJson);
  })
  .catch(error => {
    console.error(error);
  });

Lambda code:

const AWS = require('aws-sdk');

exports.handler = async event => {
  const s3 = new AWS.S3();
  const params = {
    Body: event.body,
    Bucket: 'projectr.app',
    Key: 'exampleobject.jpg',
  };
  const response = await s3.putObject(params).promise();
  console.log(response);
};

Corrupted Image

Other things tried:

parse-multipart: always returns an empty array

const boundary = event.headers['content-type'].slice(20);
let {body} = event;
if (event.isBase64Encoded) {
  body = Buffer.from(event.body, 'base64');
}
const parts = multipart.Parse(body, boundary);

for (let i = 0; i < parts.length; i++) {
  const part = parts[i];
  console.log(`PART ${i}: ${part}`);
}

Defining ContentType in S3 params: no descernable difference.

const params = {
  Body: event.body,
  Bucket: 'projectr.app',
  Key: 'exampleobject.jpg',
  ContentType: 'multipart/form-data',
};
Reid
  • 4,376
  • 11
  • 43
  • 75
  • Possible duplicate of [API Gateway - Post multipart\form-data](https://stackoverflow.com/questions/41756190/api-gateway-post-multipart-form-data) – Anon Coward Sep 16 '19 at 17:35
  • @AnonCoward Explanation explaining the differences edited into question. – Reid Sep 16 '19 at 17:53
  • Is there a reason the answer in the duplicated question can't be used to parse the multipart upload? – Anon Coward Sep 16 '19 at 17:56
  • @AnonCoward yeah, there isn't any code in that answer. How am I supposed to copy code from SO when there isnt any code??? Just kidding. Let me give that a try and see if I cant get it working. – Reid Sep 16 '19 at 18:12
  • In your putObject call, you should supply an appropriate ContentType. – jarmod Sep 16 '19 at 18:54
  • @AnonCoward I can not get parse-multipart to function in any meaningful way. It always returns an empty array. – Reid Sep 16 '19 at 19:19
  • @Reid Did you get any solution ? I am also facing the same issue – moazzam Jul 20 '20 at 09:01

0 Answers0