Trying to access FirestoreAdminClient from Cloud Run service using firebase-admin. ERROR: 7 PERMISSION_DENIED: The caller does not have permission

╄→尐↘猪︶ㄣ 提交于 2021-02-11 12:47:29

问题


I've got the following code for a an API endpoint that is supposed to trigger a Firestore backup using firebase-admin.

This is how I'm initializing firebase-admin;

import * as admin from "firebase-admin";

admin.initializeApp({
  credential: admin.credential.cert(
    SERVICE_ACCOUNT as admin.ServiceAccount
)});

The service account key is a JSON I've downloaded using the default firebase-admin service account:

This is the backup.ts API request handler.

export const backupData: RequestHandler = async (req, res) => {
  try {

    const PROJECT_ID = process.env.PROJECT_ID;
    
    const client = new admin.firestore.v1.FirestoreAdminClient();
    const DB_NAME = client.databasePath(PROJECT_ID, "(default)");

    const BUCKET = `gs://${PROJECT_ID}.appspot.com`;
    const FOLDER = `firestore-backup`;
    const FULL_PATH = `${BUCKET}/${FOLDER}`;

    const responses = await client.exportDocuments({
      name: DB_NAME,
      outputUriPrefix: FULL_PATH,
      collectionIds: [] // CAN LIST SPECIFIC COLLECTIONS
    });

    const response = responses[0];
    return res.sendStatus(200);
  } else 
    return res.sendStatus(403);
  }
  catch(err) {
    console.error(err.message || DEFAULT_ERROR_MSG);
    return res.sendStatus(500);
  }
};

The weird thing is:

It works perfectly on my dev environment. I mean, I run my local server and hit localhost:8080/api/backup (which is the correct endpoint) and everything works correctly and the backup is triggered.

But after I deploy it to my cloud run service, it no longer works.

This is the error I'm getting on my cloud run service:

7 PERMISSION_DENIED: The caller does not have permission

Do I need to add more permissions to that service account? But why does it work with that very same service account on my local dev environment? Should I not use a service account when I'm initializing it on my cloud run service? Don't know what to do here.


UPDATE 1:

I've just tried to initialize it like this, but got the same results:

admin.initializeApp({
  credential: admin.credential.cert(SERVICE_ACCOUNT),
  databaseURL: `https://${PROJECT_ID}.firebaseio.com`,
  storageBucket: `${PROJECT_ID}.appspot.com`
});

Also, just followed this doc tutorial and added these roles both to my firebase-admin and PROJECT_ID@appspot.gserviceaccount.com. Still not working:

  • Cloud Datastore Import Export Admin
  • Storage Admin

UPDATE 2:

Following this doc, I've just tried to initialize the firebase-admin without any parameters. Still same result:

admin.initializeApp();

UPDATE 3:

Following the previous docs and this doc, I've added the IAM roles of Cloud Datastore Import Export Admin and Storage Admin to my PROJECT_NUMBER-compute@developer.gserviceaccount.com service account. Still same results.


CONCLUSION

It just worked. But I've done so many attempts that I'm not really sure of what made it work. I'm guessing it was what I did on UPDATE 3. Will check that out and answer tomorrow.


回答1:


I can confirm that UPDATE 3 that I described on the question did the trick. Because I've reverted the changes I made on UPDATE 1 and 2 and it's still working fine.

It seems that while on my local environment, firebase-admin is using the firebase-adminsdk@PROJECT_ID.iam.gserviceaccount.com service account to call the FirestoreAdminClient API. That's why it works I guess. Or maybe it's using my gcloud logged account which is my owner email. I'm not really sure.

But once you are in Cloud Run environment, even though firebase-admin is being initialized with that very same service account, it seems that it kind of overrides that and uses the xxxxxxxxx-compute@developer.gserviceaccount.com. So that's the one that needs the permissions.

I got that idea from Cloud Run Service Identity and Cloud Run IAM roles, that says:

And the roles needed I got from: Firebase DOCS - Scheduled exports:

This is the final config:



来源:https://stackoverflow.com/questions/66032943/trying-to-access-firestoreadminclient-from-cloud-run-service-using-firebase-admi

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!