【问题标题】:How to add values to Firebase Firestore without overwriting?如何在不覆盖的情况下向 Firebase Firestore 添加值?
【发布时间】:2018-08-29 04:14:10
【问题描述】:

我有两个活动,我分别从这两个活动向 Firestore 添加数据。但是,每当我向 Firestore 添加第二个活动数据时,它都会覆盖第一个活动数据。我在两个活动中使用了以下代码:

 firebaseFirestore.collection("Users").document(user_id).set(data)

如何停止覆盖?我想将两个活动数据保存在同一个user_id

【问题讨论】:

  • user_id下方的每个活动再添加一个孩子
  • 如何添加孩子。你能告诉我..@Dumbo

标签: java android firebase firebase-realtime-database google-cloud-firestore


【解决方案1】:

试试这个直接更新

db.collection('cities').doc('restaurants').update({ rating:"3.2" });

只有字段等级会改变,其余字段保持不变。

假设您有 3 个字段,并且只想更改其中的 2 个,您也可以用不同的方式进行此操作

// You get the document 'restaurants' and then do the below
db.collection('cities').doc('restaurants').get().then((doc) => {

    // Get the rating field string, parse it to a float, remove 0.4 from it and
    // set it to a tmp variable
    var tmpRating = parseFloat(doc.data()['rating']) - 0.4;

    // Get the array of strings field 'menu' and set it to a tmp variable
    var tmpMenu = doc.data()['menu'];

    // Push 'spaghetti' string to the tmp array of strings( Can also put an
    // adapting string variable instead of a specific string like 'spaghetti'
    tmpMenu.push('spaghetti');

    // Update only the specific fields 'rating' and 'menu' and keep the rest unchanged.
    db.collection('cities').doc(doc.id).update({
        rating: toString(tmpRating), // Don't forget to separate them by commas
        menu: tmpMenu
    });
});

【讨论】:

    【解决方案2】:

    根据文档,您可以将{merge:true} 用作第二个参数,根据我的经验,问题通常在于您尝试使用相同的密钥存储不同的数据。

    即使使用{merge: true} 也会始终使用您传入的值更新当前键。

    Merge:true 仅当密钥不存在时才有效。我相信文档中的每个键都必须是唯一的。

    为了测试它尝试使用不同的键传递(保持{merge: true} 作为第二个参数)数据,它将合并到现有的。

    【讨论】:

      【解决方案3】:

      有两种方法可以实现这一目标。第一个是使用Map:

      Map<String, Object> map = new HashMap<>();
      map.put("yourProperty", "yourValue");
      firebaseFirestore.collection("Users").document(user_id).update(map);
      

      如您所见,我使用了update() 方法而不是set() 方法。

      第二种方法是像这样使用模型类的对象:

      YourModelClass yourModelClass = new YourModelClass();
      yourModelClass.setProperty("yourValue");
      firebaseFirestore.collection("Users").document(user_id)
          .set(yourModelClass, SetOptions.mergeFields("yourProperty"));
      

      如您所见,我使用了set() 方法,但我将SetOptions.mergeFields("yourProperty") 作为第二个参数传递,这意味着我们只对特定字段进行更新。

      【讨论】:

      • 你实现了更新值而不覆盖吗?
      • ....我明白了,但是稍后我又遇到了另一个问题。我在布局中使用了 ScrollView。但它不会滚动全部内容。滚动后,它仍然在底部留下一些可滚动的部分。它在屏幕底部形成了一个不寻常的小空白。我该如何解决它
      • 这基本上是另一个问题。为了遵守本社区的规则,请再次提出新问题,以便我和其他用户可以帮助您。
      • 我的回答对您有帮助吗?
      • @NadeemShaikh 我认为answer 可能会有所帮助。
      【解决方案4】:

      如果您知道用户文档已经存在于 firestore 中,那么您应该使用

      firebaseFirestore.collection("Users").document(user_id).update(data)
      

      如果你不知道文档是否存在,那么你可以使用

      firebaseFirestore.collection("Users").document(user_id).set(data, {merge:true})
      

      这将执行数据的深度合并

      您也可以使用子集合来做到这一点

      【讨论】:

        【解决方案5】:

        我建议您再添加一个文档或集合,以便为单个用户存储更多的数据值。
        您可以为这两个活动创建一个文档引用:

        firebaseFirestore.collection("Users").document(user_id+"/acitivity1").set(data);
        //and  
        firebaseFirestore.collection("Users").document(user_id+"/acitivity2").set(data);
        

        或者你可以为它创建一个子集合:

        firebaseFirestore.collection("Users").document(user_id)
                          .collection("Activities").document("acitivity1").set(data);
        //and
        firebaseFirestore.collection("Users").document(user_id)
                          .collection("Activities").document("acitivity2").set(data);
        

        更多关于分层数据there

        【讨论】:

          猜你喜欢
          • 2015-10-11
          • 2010-09-27
          • 1970-01-01
          • 2021-11-27
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2018-07-15
          • 2013-01-21
          相关资源
          最近更新 更多