Firebase Firestore: get document ID after adding d

2019-08-05 13:16发布

I add data to Firestore like this:

db
    .collection('foo')
    .add({foo: 'bar'})
    .then(docRef => {
      console.log('Added Foo: ', docRef.id)
      // do some stuff here with the newly created foo and it's id.
    })
    .catch(console.error)

After the document creation, I would like to work with the new doc or specially it's ID. The document is stored in the local database with a valid ID.

But how do I get the ID after the document creation? The promise will not be resolved until the data has synced with the server.

2条回答
冷血范
2楼-- · 2019-08-05 13:31

You can get Id even before you are saving locally. You just use this way to write data.

      // Add a new document with a generated id.
     var newCityRef = db.collection("cities").doc();
      var id = newCityRef.key;
      // later...
       newCityRef.set(data);

For the web, offline persistence is disabled by default. To enable persistence, call the enablePersistence method

firebase.firestore().enablePersistence()
  .then(function() {
      // Initialize Cloud Firestore through firebase
      var db = firebase.firestore();
  })
  .catch(function(err) {
      if (err.code == 'failed-precondition') {
          // Multiple tabs open, persistence can only be enabled
          // in one tab at a a time.
          // ...
      } else if (err.code == 'unimplemented') {
          // The current browser does not support all of the
          // features required to enable persistence
          // ...
      }

To check whether you're receiving data from the server or the cache, use the fromCache property on the SnapshotMetadata in your snapshot event. IffromCache is true, the data came from the cache and might be stale or incomplete. If fromCache is false, the data is complete and current with the latest updates on the server.

By default, no event is raised if only the SnapshotMetadata changed. If you rely on the fromCache values, specify the includeMetadataChanges listen option when you attach your listen handler.

db.collection("cities").where("state", "==", "CA")
  .onSnapshot({ includeQueryMetadataChanges: true }, function(snapshot) {
      snapshot.docChanges.forEach(function(change) {
          if (change.type === "added") {
              console.log("New city: ", change.doc.data());
          }

          var source = snapshot.metadata.fromCache ? "local cache" : "server";
          console.log("Data came from " + source);
      });
  });

So if you add new data and you have offline enabled your data will be added to cache and can be listened by the listeners.

 

  });

查看更多
放我归山
3楼-- · 2019-08-05 13:33

I came across this workaround that does the job for me.

db
    .collection('foo')
    .where('fooCreator', '==', currentUserId)
    .onSnapshot(querySnapshot => {
      querySnapshot.docChanges.forEach(change => {
        if (change.type === 'added' && change.doc._document.hasLocalMutations) {
          const fooId = change.doc.id
          const foo = change.doc.data()
          // do something with foo and fooId
        }
      })
    })

It works, but I don't really like it because of:

  1. I need to subscribe to all changes
  2. I used change.doc._document.hasLocalMutations to check if it is a newly created item
查看更多
登录 后发表回答