【问题标题】:Prevent duplicate entries in firestore防止firestore中的重复条目
【发布时间】:2020-03-24 18:10:44
【问题描述】:

我正在使用 firestore 为我的应用程序创建一个聊天,我将聊天存储在一个单独的集合中。我的文档结构如下:

{
    participant1: "kd94992nnd9",
    participant2: "49di9niso3s",
    p1Name: "...",
    p2Name: "...",
    messages: [/*messages are stored her*/],
    //Some metadata about the chats
}

如果已经存在具有 2 个用户 ID 的文档,我想确保不创建任何文档。我要在我的数据库结构中进行哪些更改才能在 Firestore 中做到这一点?

【问题讨论】:

  • 我会指出您的文档结构无法扩展。单个文档的最大大小为 1MB,如果消息列表变大,您将无法再添加。对于必须能够在没有特定界限的情况下增长的项目列表,它们应该作为单独的文档存在于自己的集合中。
  • 是的,我知道并且我打算将消息作为文档的子集合?你认为这会更好地扩展吗?
  • 它将无限扩展。聊天应用甚至不可能达到理论上的极限。

标签: android firebase google-cloud-firestore


【解决方案1】:

使用 Firestore,您只能保证文档 ID 的唯一性,而不是文档字段的内容。您可以做的是将两个参与者 ID 连接成一个字符串并将其用作文档 ID。然后,您将使用transaction 来确保在写入之前不存在具有该新复合 ID 的文档。

【讨论】:

  • 我有点想类似的解决方案。问题是 2 个 userId 可以以 2 种方式连接,例如 kd94992nnd949di9niso3s49di9niso3skd94992nnd9 因此仍然可以为任何 2 个参与者创建 2 个文档。我该怎么办?
  • 以可预测的方式对 ID 进行排序。
  • 我正在考虑按字母顺序对它们进行排序:) 问题是我的代码有 targetId 和 currentId(这取决于登录用户和用户想要聊天的用户)。顺序必然会根据谁发送第一条消息而改变。你有什么建议?
  • 当然,您可以按字母顺序对它们进行排序。任何适合你的东西。
【解决方案2】:

如果您将聊天存储在单独的集合中,如果存在 较早 聊天文档,您关心什么?如果您的架构结构为:

chatRecord: {
  participants: [
    {participantID},
    {participantID},
    ...
  ],
  messages: [/* array of messages */],
  dateTag: {timestamp}
}

...您可以简单地查询数组中的参与者ID;没有特定的聊天文档会变得特别大;您可以根据需要对它们进行排序。您可以在几乎任何参与者组合中查询、排序和连接您选择的任何特定时间段内的所有聊天。不单独存储每条消息的唯一原因是可能减少一次读取或写入的文档数量,但我怀疑这在聊天应用中会很重要。

请记住,这是 NoSQL - 您基本上鼓励在单独的文档中复制静态数据,例如参与者姓名,以便更快更有效地查询。 DRY 用于 SQL。 Firestore 的构建假设查询非常高效,以至于您真的不应该关心 documentID,也不应该尝试尽可能多地塞进任何单个文档中。

【讨论】:

    猜你喜欢
    • 2019-06-11
    • 1970-01-01
    • 2012-04-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-11-29
    • 2012-02-07
    • 1970-01-01
    相关资源
    最近更新 更多