3
votes

I'm looking for some confirmation of expected behaviour for the way the Firestore Emulator REST API handles unauthenticated requests as I think I may have found some possible inconsistencies.

I've been playing around with the Firestore Emulator REST API using Postman for a personal project. If I run the Emulator (firebase emulators:start --only=firestore), I'm able to make the following requests successfully WITHOUT needing to pass any Bearer token in the Authorization header with the request:

  • GET http://localhost:8080/v1/projects/<MY_PROJECT_ID>/databases/(default)/documents/ (Returns all documents)
  • DELETE http://localhost:8080/v1/projects/<MY_PROJECT_ID>/databases/(default)/documents/<COLLECTION_ID>/<DOCUMENT_ID> (Deletes an individual document)
  • POST http://localhost:8080/v1/projects/<MY_PROJECT_ID>/databases/(default)/documents/<COLLECTION_ID> (Creates a new document in a collection)
  • PATCH http://localhost:8080/v1/projects/<MY_PROJECT_ID>/databases/(default)/documents/<COLLECTION_ID>/<DOCUMENT_ID> (Updates a document)

However, when I try and get a list of collection IDs as described here using the following request, I get the following error:

  • POST http://localhost:8080/v1/projects/<MY_PROJECT_ID>/databases/(default)/documents:listCollectionIds

Response is:

{
    "error": {
        "code": 403,
        "message": "Metadata operations require admin authentication.",
        "status": "PERMISSION_DENIED"
    }
}

If I pass a Bearer token, this request will then run successfully. I generated the token using gcloud auth application-default print-access-token (as described here).

Please note, I've set my Firestore Rules to allow all reads and writes for all documents to make things simpler for now:

service cloud.firestore {
  match /databases/{database}/documents {
    match /{document=**} {
      allow read, write: if true
    }
  }
}

The docs give details for authentication, however, the context they describe this in is for making requests against https://firestore.googleapis.com/v1/ rather than when using the Emulator.

I'd expect all requests to the Emulator API to not require any authentication, but it seems that some do and some do not and I haven't been able to find any other details in the documentation around how the Emulator should work.

At the moment, I'm not sure if this is a bug and I should file an issue on GitHub, or whether it is expected behaviour and I should just pass a Bearer token with every request to be safe.

Any help would be appreciated. Thanks.

1
If the API is not working the way you expect, file an issue on GitHub. github.com/firebase/firebase-tools - Doug Stevenson

1 Answers

1
votes

This matches the behavior of the real API. When you send a request without an auth token, you're attempting to authenticate through the security rules system. Certain methods do not support authentication through security rules, because you would probably not want end-users calling them. These are mostly database administration methods, hence the error description. For example, you would not want end-users calling any indexing methods.

listCollectionIds is one of these administrative methods. This is also why this feature is not supported by the web, iOS, and Android SDKs.