The task is to make CRUD operations in Firestore after I make an API call to Cloud Function, which later should trigger a Firestore function to get a set of items in Cards collection.
Here are some rules:
- There should be no user authentication needed
- It shouldn't need to have a service account with granted permissions
The purpose behind the "rules" is to legitimate operations happening in Cloud Functions as it was an authorized admin itself (Because they are deployed to Firebase safe environment anyways right?). Since the plan is to host the project as a Cloud Function, we should be required to have firebase-admin SDK.
For so far, I tried to implement the same with firebase-functions but it only worked if the rule was not restricted publicly being as:
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
match /Cards/{card}{
allow write,read: if false;
}
}
}
Since this works, but the rule is "insecure" I'd like to do these operations only as "admin" would through Cloud Functions. Here is some code that returns an empty array of documents, even though I have data in it viewable from web GUI.
import { getFirestore } from "firebase-admin/firestore";
import * as admin from "firebase-admin";
const GetCard = (cardID: string)=> {
require("../../path-to-the-file.json");
admin.initializeApp({
credential: admin.credential.cert(serviceAccount),
});
getFirestore()
.collection("Cards")
.get()
.then((cardsSnapshot) => {
cardsSnapshot.forEach((card) => {
console.log("card from collection: ", JSON.stringify(card.data()));
});
});
};
EDIT: the reason why I decided to use adminSDK even though Cloud Functions don't need it was the error I was getting:
Error adding document: [FirebaseError: Missing or insufficient permissions.] {
> code: 'permission-denied',
> customData: undefined,
> toString: [Function (anonymous)]
> }
After running this code:
import { initializeApp } from "firebase/app";
import { collection, getDocs, getFirestore } from "firebase/firestore";
const GetCard = (cardID: string): Promise<Card> => {
const firebaseConfig = {...CONFIGS...};
const app = initializeApp(firebaseConfig);
const db = getFirestore(app);
getDocs(collection(db, "Cards"))
.then((querySnapshot) => {
querySnapshot.forEach((doc) => {
console.log(`${doc.id} => ${doc.data()}`);
});
})
.catch((e) => {
console.error("Error adding document: ", e);
});
};