【问题标题】:How to update a node without overwriting all the child nodes with Google Cloud Function using a update Object?如何使用更新对象更新节点而不用 Google Cloud Function 覆盖所有子节点?
【发布时间】:2018-10-12 20:07:33
【问题描述】:

我正在使用 Google Cloud 函数更新“Rooms/{pushId}/ins”,该函数从多个“门/{MACaddress}/ins”获取新的 In 数据。 目前的功能是这样的:

exports.updateRoomIns = functions.database.ref('/doors/{MACaddress}').onWrite((change, context) => {
    const beforeData = change.before.val(); // data before the write (data of all the doors child nodes)
    const afterData = change.after.val(); // data after the write (data of all the doors child nodes)
    const roomPushKey = afterData.inRoom; // get the right room
    const insbefore = beforeData.ins;
    const insafter = afterData.ins; // get the after data of only the "ins" node
    console.log(insafter);

    if (insbefore != insafter) {
        const updates = {}; 

“const updates = {}”正上方的行创建一个空对象(稍后)填充,并(稍后)更新“rooms/{roompushkey}/ins”节点...

我认为问题可能出在“更新”常量上,因为每次函数运行时都会将这个对象重新定义为一个整体......

代码继续...

        updates['/rooms/' + roomPushKey + '/ins'] = insafter; // populate the "INS" object with the values taken from the "/doors/{MACaddress/ins"
        return admin.database().ref().update(updates); // do the update
    } else {
    return
    }
});

如果我只有一扇门,这会起作用,但由于我有几扇门具有不同的 Ins 数据,所以每次我更新单个“Door/{MACaddress/Ins”时,整个“Rooms/{pushId}/Ins”被最后更新的门上的任何数据替换...我知道 update 方法应该用于此目的,我有点想保留这个“更新”对象以将数据散开到以后的其他路径。这可能吗?有关如何解决此问题的任何建议?

这是我的数据结构:

root: { 
  doors: {
    111111111111: {
       MACaddress: "111111111111",
       inRoom: "-LBMH_8KHf_N9CvLqhzU", // I will need this value for the clone's path
       ins: {
          // I am creating several "key: pair"s here, something like:
          1525104151100: true,
          1525104151183: true,
       }
    },
    222222222222: {
       MACaddress: "222222222222",
       inRoom: "-LBMH_8KHf_N9CvLqhzU", // I will need this value for the clone's path
       ins: {
          // I am creating several "key: pair"s here, something like:
          2525104157710: true,
          2525104157711: true,
       }
    }
  },
  rooms: {
    -LBMH_8KHf_N9CvLqhzU: {
      ins: {
        // I want the function to clone the same data here:
        1525104151100: true,
        1525104151183: true,
      }
    }
  }

【问题讨论】:

    标签: javascript firebase firebase-realtime-database google-cloud-functions


    【解决方案1】:

    根据我之前对您的相关问题 (How to clone a node to another path based on a reference value from the initial path on Google Cloud Functions?) 的回答进行详细说明,我将修改代码如下:

    exports.updateRoom = functions.database.ref('/doors/{MACaddress}').onWrite((change, context) => {
        const afterData = change.after.val(); // data after the write
    
        const roomPushKey = afterData.inRoom;
        const ins = afterData.ins;
    
        const updates = {};
    
        Object.keys(ins).forEach(key => {
            updates['/rooms/' + roomPushKey + '/ins/' + key] = true;
        });
    
        return admin.database().ref().update(updates);
    
    }).catch(error => {
        console.log(error);
        //+ other rerror treatment if necessary
    
    });
    

    换句话说,不是替换完整的 ins 对象,而是在现有的 ins 节点中添加新的子节点。

    【讨论】:

    • 再次感谢 Renaud,但这不是克隆“Ins”中“key: pair”的完整列表,而是替换“Rooms/{pushId}/Ins”中的最后一个键forEach 循环...例如:Ins: { 2525104157711 }
    • 试试这个:Object.keys(ins).forEach(key => { updates['/rooms/' + roomPushKey + '/ins/' + key] = true; });
    • @JoaoAlvesMarrucho Alexander 是对的,我的回答有误。感谢亚历山大发现它。我会更新答案,但你当然不必接受!
    • @JoaoAlvesMarrucho 关于您的数据模型,您必须查询现有的 ins 并遍历对象以检测它是否存在
    • @JoaoAlvesMarrucho 我已经找到了答案,请参阅那里。希望对您有所帮助。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2023-03-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-08-24
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多