Lion Smith
Lion Smith

Reputation: 655

how to retrieve image from firebase storage and display it on a webpage using google-cloud and node js

i store my image on firebase storage now i wanted to display it on my page

const firebase = require('./../config/firebase');
const gcloud = require('google-cloud');
const fs = require('fs');

var storage = gcloud.storage({
projectId: 'test-a1e76',
keyFilename: 'test-a1e76-firebase-adminsdk-7111d-124guy123eac.json',
});

var bucket = storage.bucket('test-a1e76.appspot.com');

this is how my set up looks like.

and this is my get method.

router.get('/image', function (req,res) {

    var remoteReadStream = bucket.file('download.png').createReadStream();
    var localWriteStream = fs.createWriteStream('/images/watchers/2jIompF9FUZ6A4LnpBcbpHWw8dx2/download.png');
    var ss = remoteReadStream.pipe(localWriteStream);
    res.send(ss);
})

i only tried this since it was written on the npm docs.of google-cloud works. i tried putting it inside get method to see how it works.

and after that i got this error..

Error: ENOENT: no such file or directory, open 'C:\images\test\2jIoasd24zd13ase121s2Ww8dx2\download.png'

this is my ajax get method

 $.ajax({
    url:'/user/image',
    type:'GET',
    success:function(data){
      console.log(data.path);

    }
  });

can anyone here guide my on how can i retrieve the images from firebase storage and display it on my webpage?. using this google-cloud npm? cause i read some thread that node js doesn't support firebase-storage so they use google-cloud instead.

Upvotes: 3

Views: 4234

Answers (3)

Sem
Sem

Reputation: 1397

I got it working this way.

var admin = require("firebase-admin");
...
app.get('/picture', async (req, res) => {
  const fileRef = admin.storage().bucket().file('03aead66e97f0d50ce549b6fffc1b6d7.svg');
  const hash = await fileRef.download()
  res.contentType(fileRef.metadata.contentType);
  res.end(hash[0], 'binary');
});

Upvotes: 1

Rawan-25
Rawan-25

Reputation: 1883

In the firebase function with node I use below code which is working perfectly

How do I upload a base64 encoded image (string) directly to a Google Cloud Storage bucket using Node.js?

const uuidv4 = require('uuid/v4');
const uuid = uuidv4();

    const os = require('os')
    const path = require('path')
    const cors = require('cors')({ origin: true })
    const Busboy = require('busboy')
    const fs = require('fs')
    var admin = require("firebase-admin");


    var serviceAccount = {
        "type": "service_account",
        "project_id": "xxxxxx",
        "private_key_id": "xxxxxx",
        "private_key": "-----BEGIN PRIVATE KEY-----\jr5x+4AvctKLonBafg\nElTg3Cj7pAEbUfIO9I44zZ8=\n-----END PRIVATE KEY-----\n",
        "client_email": "[email protected]",
        "client_id": "xxxxxxxx",
        "auth_uri": "https://accounts.google.com/o/oauth2/auth",
        "token_uri": "https://oauth2.googleapis.com/token",
        "auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
        "client_x509_cert_url": "https://www.googleapis.com/robot/v1/metadata/x509/firebase-adminsdk-5rmdm%40xxxxx.iam.gserviceaccount.com"
      }

    admin.initializeApp({
        credential: admin.credential.cert(serviceAccount),
        storageBucket: "xxxxx-xxxx" // use your storage bucket name
    });


    const app = express();
    app.use(bodyParser.urlencoded({ extended: false }));
    app.use(bodyParser.json());
app.post('/uploadFile', (req, response) => {
    response.set('Access-Control-Allow-Origin', '*');
    const busboy = new Busboy({ headers: req.headers })
    let uploadData = null
    busboy.on('file', (fieldname, file, filename, encoding, mimetype) => {
        const filepath = path.join(os.tmpdir(), filename)
        uploadData = { file: filepath, type: mimetype }
        console.log("-------------->>",filepath)
        file.pipe(fs.createWriteStream(filepath))
      })

      busboy.on('finish', () => {
        const bucket = admin.storage().bucket();
        bucket.upload(uploadData.file, {
            uploadType: 'media',
            metadata: {
              metadata: { firebaseStorageDownloadTokens: uuid,
                contentType: uploadData.type,
              },
            },
          })

          .catch(err => {
            res.status(500).json({
              error: err,
            })
          })
      })
      busboy.end(req.rawBody)
   });




exports.widgets = functions.https.onRequest(app);

Upvotes: 0

lesimoes
lesimoes

Reputation: 936

You need only show the image, right? There`s a dirty way to do.

1- Upload one image on your bucket e click on it (in Firebase console).

2- In the right side of screen shows info about your file.

3- Look for "Download Url" (or something like that) and click on it.

4- This is a url example:

https://firebasestorage.googleapis.com/v0/b/coffee-a7e8c.appspot.com/o/coffeeTrue.png?alt=media&token=7f44e575-414d-4d18-8f39-c94a23f6e014

As you can see there is a pattern: https://firebasestorage.googleapis.com/v0/b/NAME_FILE?alt=media&token=YOUR_TOKEN

Get your token and now you can show all images on your bucket only pass de name of file and your token (like this example).

This works because Firebase provides a Rest API for your services.

Remember: Do auth before or set-up open rules.

Example: Everyone can read. Only auth user can write.

service firebase.storage {
  match /b/{bucket}/o {
    match /{allPaths=**} {
      allow read: if request.auth == null;
      allow write: if request.auth != null;
    }
  }
}

Upvotes: 0

Related Questions