Home > database >  Uploading a file from front-end to firebase storage via cloud functions
Uploading a file from front-end to firebase storage via cloud functions

Time:10-28

I am trying to achieve the following:

  1. User selects file on website
  2. User calls Firebase Cloud function and passes file into the function
  3. Cloud function uploads the file that to storage.

So far I am able to do all of the above, however, when I try to access the above file in storage, a file with no extension is downloaded. The original file was a pdf, but I am still unable able to open it with PDF viewers. It appears I am storing something in storage, although I am not exactly sure what.

Here is an example of how my front-end code works:

const getBase64 = file => new Promise((resolve, reject) => {
  const reader = new FileReader();
  reader.readAsDataURL(file);
  reader.onload = () => resolve(reader.result);
  reader.onerror = error => reject(error);
});

var document_send = document.getElementById('myFile')
var send_button = document.getElementById('send_button')

send_button.addEventListener('click', async () => {
  var sendDocument = firebase.functions().httpsCallable('sendDocument')
  try {
    await sendDocument({
      docu: await getBase64(document_send.files[0])
    })
  } catch (error) {
    console.log(error.message);
  }
})

Here is an example of how my cloud function works:

const functions = require("firebase-functions");
const admin = require("firebase-admin");

exports.sendDocument = functions.https
  .onCall((data, context) => {
    return admin.storage().bucket()
      .file("randomLocationName")
      //.file("randomLocationName" ".pdf") - tried this also
      .save(data.docu);
  })
  .catch((error) => {
    console.log(error.message);
    return error;
  });
});

I do not receive an error message as the function runs without error.

CodePudding user response:

The save() function seems to take either a string or Buffer as first parameter.

> save(data: string | Buffer, options?: SaveOptions)

The issue arises when you pass the base64 string directly instead of a Buffer. Try refactoring the code as shown below:

return admin.storage().bucket()
  .file("randomLocationName"   ".pdf") // <-- file extension required
  .save(Buffer.from(data.docu, "base64"));

Cloud Functions also have a 10 MB max request size so you won't be able to upload large images that way. You can use Firebase client SDKs to upload files directly, restrict access using security rules and use Cloud Storage Triggers for Cloud Function in case you want to process the file and update the database. Alternatively, use signed URLs for uploading the files if you are using GCS without Firebase.

  • Related