node.js - Direct post to AWS S3 from ReactNative (iOS) with signed request -


i trying recreate heroku example of uploading user submitted images in react native, keep getting 400 errors aws.

the images ios camera roll. have uri image , base64 encoded version of image. mime type image/jpeg. far, have set heroku stated, having trouble making file send proper shape. i've added code below clarification.

i using react-native-image-picker select images camera roll

client side code

module.exports = react.createclass({ ...  openphotos() { // called on button press, opens camera roll     imagepicker.showimagepicker(options, (response) => {       if (response.didcancel) return;       if (response.error) return alert.alert('imagepicker error: ', response.error);       this.getsignedrequest(response);     });   }, getsignedrequest(pickerresp) {   // image uri pickerresp.uri `data:image/jpg;base64,${pickerresp.data}`   var file = {     uri: pickerresp.uri, // works `data:image/jpg;base64,${pickerresp.data}`,     name: `${this.props.email}.jpg`,     type: 'image/jpeg'   };   var body = new formdata();   body.append('file', file);    fetch(`${api.test_api}sign-s3?file-name=${file.name}.jpg&file-type=${file.type}`, {     method: "get"   }).then(response => response.json()).then(data => {     alert.alert("got signed request",data.url);     fetch(data.signedrequest, { method: 'put', body: body }).then(resp => resp.json()).then(data => {       this.setstate({uploadedfile: true});       this.props.tosignup();     }).catch(err => alert.alert("server error", "could not upload profile photo."))   }).catch(err => {     alert.alert('s3 signed request error',"look @ logs");     console.log(err);   }) },  ... }; 

server side code

aws npm package : [aws-sdk]

// signature upload client side s3 apirouter.get('/sign-s3', function(req, res) {   console.log('signing s3')   const s3 = new aws.s3(); // automatically loads key , secret   const filename = req.query['file-name'];   const filetype = req.query['file-type'];   const s3params = {     bucket: s3_bucket,     key: filename,     expires: 60,     contenttype: filetype,     acl: 'public-read'   };    s3.getsignedurl('putobject', s3params, (err, data) => {     if(err) return console.log(err)     const returndata = {       signedrequest: data,       url: `https://${s3_bucket}.s3.amazonaws.com/${filename}`     };     console.log(returndata)     res.json(returndata);   }); }); 

fetch(`${api.test_api}sign-s3?file-name=${file.name}.jpg&file-type=${file.type}

the fetch request here adding .jpg onto end of filename described, when try upload s3, rejected because payload doesn't match prior request. also, xmlhttprequest suggested heroku works fine file structured have it, base64 data instead (below).

var file = {   uri: `data:image/jpg;base64,${pickerresp.data}`, //pickerresp.uri,   type: 'image/jpeg',   name: `${this.props.email}.jpg`, }; 

the following xml http request send image in encoded form s3, simple request or image src property can access file.

function uploadfile(file, signedrequest, url, cb) {   const xhr = new xmlhttprequest();   xhr.open('put', signedrequest);   xhr.onreadystatechange = function() {     if (xhr.readystate === 4) {       if(xhr.status === 200) {         cb()       } else {         alert('could not upload file.');       }     }   };   xhr.send(file); }; 

Comments

Popular posts from this blog

java - SSE Emitter : Manage timeouts and complete() -

jquery - uncaught exception: DataTables Editor - remote hosting of code not allowed -

java - How to resolve error - package com.squareup.okhttp3 doesn't exist? -