RobinBobin / react-native-google-drive-api-wrapper

This wrapper facilitates the use of the Google Drive API in React Native projects.
110 stars 43 forks source link

Base64 support #3

Closed alp1396 closed 5 years ago

alp1396 commented 6 years ago

Hi, Robin. You can just add one line (or add new createFileMultipartBase64 function) for base64 support. in Files.js -> createFileMultipart() just one additional header: Content-Transfer-Encoding: base64\n\n; It would be nice to have that feature because react-native-fs reads binary files (and images) in base64 only. https://github.com/alp1396/react-native-google-drive-api-wrapper/commit/f3b10c5f85fd9de8ea05c3a04d33a2434f1ab933

RobinBobin commented 6 years ago

Hi, Alex!

Thanks for the feedback. It's really pleasant to see my package is of some use for someone :) .

I have some time right now, so I'll add this feature. I'll update as soon as it's ready.

RobinBobin commented 6 years ago

Alex, could you explain what do you need it for, please?

Doesn't my code (as it is now) allow to upload base64 to gdrive?

alp1396 commented 6 years ago

I have been tried to upload base64 data, that comes from react-native-fs openFile() but it doesn't work as expected. Upload process has no errors, but the target file on Google Drive account, has exactly the same base64 formatted data instead of original binary. It is work well only if I add content-transfer-encoding header. It seems that Google service then know that base64 is used only for transfer, and when upload is complete Google decodes base64 to original binary (or whatever it was been before) data and store it to target file. (as I suppose, but not sure in details...) Content-Transfer-Encoding: base64\n\n; in your code (Files.js -> createFileMultipart() function)

alp1396 commented 6 years ago

So it would be nice if createFileMultipart() will contain an optional parameter "isBase64", for example. And if it True, then additional headers are added to the fetch command.

RobinBobin commented 6 years ago

Oh, I see!

But doesn't it seem logical to you? If you upload base64 data and NOT binary - you get a file with base64 on GDrive. If you convert base64 from react-native-fs.openFile() to binary and supply this binary data to createFileMultipart(), I'm pretty sure you'll get a binary file on GDrive. If that's not the case, please tell me.

What do you think about it?

RobinBobin commented 6 years ago

On the other hand, adding the mentioned header can be thought of as "converting base64 to binary yourself" :) .

Thank's for the idea, I'll do it right now.

RobinBobin commented 6 years ago

I've just commited. Could you be so kind to install it from github and test it please? If everything's fine I'll publish to npm.

Thanks.

alp1396 commented 6 years ago

Yeah. I know) But the react-native-fs reads binary as base64, as described there: https://github.com/itinance/react-native-fs#readfilefilepath-string-encoding-string-promisestring And when I upload an image to google drive, it should be binary because i need to view those image. Isn't it? And, the opening uploaded file from Google Drive web-interface, or when downloading it locally to PC, goes to be invalid image. Because inside of this file still base64.

Anyway, thank you for response. It's just an mention, not an issue. ))) I've done my trouble by hands, and it works. Just maybe it helps someone.)

alp1396 commented 6 years ago

Wow. Thx. I'll check it out.

uendar commented 5 years ago

@alp1396 Did you fix the base 64 issue, I have the same issue here and I tried to add the Content-Transfer-Encoding: base64\n\n; to header but no success. Can tou send the code of createFileMultipart() how it look after you add the Content-Transfer-Encoding: base64\n\n; ?

alp1396 commented 5 years ago

@uendar I've just added an modified function of createFileMultipart()

createFileMultipartBase64(data64, mediaType, metadata) {
     const ddb = `--${this.params.boundary}`;
     const ending = `\n${ddb}--`;

     let body = `\n${ddb}\n` +
        `Content-Type: ${GDrive._contentTypeJson}\n\n` +
        `${JSON.stringify(metadata)}\n\n${ddb}\n` +
        `Content-Type: ${mediaType}\n` +
        `Content-Transfer-Encoding: base64\n\n`;

     body += `${data64}${ending}`;

     return fetch(
        `${uploadUrl}?uploadType=multipart`, {
           method: "POST",
           headers: GDrive._createHeaders(
              `multipart/related; boundary=${this.params.boundary}`,
              body.length),
           body
    });
}

right inside of a @RobinBobin Files.js code. And It works for me.

And I've seen that author changed the source code to fix this issue. But I've not tested it yet, because my problem was solved already))