如何用Firestore更新一个“对象数组”?
如何用Firestore更新一个“对象数组”?
我目前正在尝试使用Firestore,但卡在一个非常简单的问题上:\"更新数组(也称为子文档)\"。
我的DB结构非常简单。例如:
proprietary: "John Doe", sharedWith: [ {who: "first@test.com", when:timestamp}, {who: "another@test.com", when:timestamp}, ],
我正在尝试(但没有成功)将新记录推入shareWith
对象数组中。
我尝试了:
// With SET firebase.firestore() .collection('proprietary') .doc(docID) .set( { sharedWith: [{ who: "third@test.com", when: new Date() }] }, { merge: true } ) // With UPDATE firebase.firestore() .collection('proprietary') .doc(docID) .update({ sharedWith: [{ who: "third@test.com", when: new Date() }] })
这些查询都无效,它们会覆盖我的数组。
答案可能很简单,但我找不到它...
编辑于 2018年8月13日: 现在,Cloud Firestore支持原生的数组操作。请参见下面的Doug的答案。
目前,在Cloud Firestore中没有办法更新单个数组元素(或添加/删除单个元素)。
这里的代码:
firebase.firestore() .collection('proprietary') .doc(docID) .set( { sharedWith: [{ who: "third@test.com", when: new Date() }] }, { merge: true } )
它表示将proprietary/docID
文档设置为sharedWith = [{who:"third@test.com", when: new Date()}]
,但不影响任何基础文档属性。它非常类似于您提供的update()
调用,但set()
调用将创建文档(如果不存在),而update()
调用将失败。
因此,您有两个选项来实现您希望实现的功能。
选项1 - 设置整个数组
使用在DB中读取当前数据所需的整个数组内容调用set()
。如果您担心并发更新,可以在事务中完成所有操作。
选项2 - 使用子集合
您可以使sharedWith
成为主文档的子集合。然后,添加单个项将如下所示:
firebase.firestore() .collection('proprietary') .doc(docID) .collection('sharedWith') .add({ who: "third@test.com", when: new Date() })
当然,这会带来新的限制。您将无法根据共享对象查询文档,也无法在一个操作中获取文档和所有sharedWith
数据。
Firestore现在有两个函数可以让您更新数组而无需重写整个数组。
链接:https://firebase.google.com/docs/firestore/manage-data/add-data,特别是https://firebase.google.com/docs/firestore/manage-data/add-data#update_elements_in_an_array
更新数组中的元素
如果文档包含一个数组字段,则可以使用arrayUnion()和arrayRemove()来添加和删除元素。arrayUnion()将元素添加到数组中,但仅添加之前不存在的元素。arrayRemove()删除每个给定元素的所有实例。