我正在尝试创建存储在路径中的“未读消息”总数,例如
/messages/{my_id}/{friend_id}
通过创建在上述路径触发的云功能,当它被触发时,它将更新此路径:
/unread-messages-count/{my_id}
因此,如果/messages/123
包含以下数据:
{
"200": { "msg1": "...", "msg2": "..." },
"201": { "msg3": "...", "msg4": "...", "msg5": "..." },
}
我希望/unread-messages-count/123
最终拥有值5
。
当"201"
子树设置为null
时,我希望/unread-messages-count/123
最终得到值2
。
值必须一致,所以我在一个Cloud Function中使用了事务,并在/messages/{my_id}/{friend_id}
上使用了onWrite触发器:
onWrite((event) => {
let oldCount = event.data.previous.numChildren;
let newCount = event.data.current.numChildren;
let delta = newCount - oldCount;
let p = db.ref(`/unread-messages-count/${event.params.my_id}`).transaction((data) => {
let oldTotal = !data ? 0 : data;
let newTotal = oldTotal + delta;
return newTotal;
});
return Promise.all([p])
.then(() => { console.log('success'); });
}
到目前为止,它完美地运行(当有大量并发写入时,事务会被重试几次),但今天我遇到了一个奇怪的情况:current
包含0个孩子而previous
包含5个儿童,导致未读计数总数发生-5
次更改,但几秒钟后再次出现相同情况,导致未读计数总数发生另外-5
次更改,使其无效。
由于某种原因,似乎onWrite回调被触发了两次。这可能发生吗?
这样做的替代方法是什么?