Firebase 云函数 Firestore 触发器 onWrite 在本地测试时行为不符合预期



我正在使用Firebase Functions Shell在Node本地测试Firestore触发的Firebase Cloud Function。

使用 onWrite 触发器并通过从函数 shell 调用updateMonth({foo:'new'})传递新文档时,我无法获得对新文档的引用。

exports.updateMonth = functions.firestore
.document('users/{userId}').onWrite((change, context) => {
const document = change.after.exists ? change.after.data() : null;
console.log("change.after.exists", change.after.exists)
console.log("change.before.exists", change.before.exists)
const oldDocument = change.before.data();
console.log("Old:",oldDocument)
return true
})

当使用 before和 after 调用以模拟文档更新时,updateMonth({before:{foo:'old'},after:{foo:'new'}})它按预期工作。 但是,当只用updateMonth({foo:'new'})调用时,之前和之后的文档似乎都不存在:

i  functions: Preparing to emulate functions.
Warning: You're using Node.js v8.4.0 but Google Cloud Functions only supports v6.11.5.
+  functions: hi
+  functions: helloWorld
+  functions: updateMonth
firebase > updateMonth({before:{foo:'old'},after:{foo:'new'}})
'Successfully invoked function.'
firebase > info: User function triggered, starting execution
info: change.after.exists true
info: change.before.exists true
info: Old: { foo: 'old' }
info: Execution took 20 ms, user function completed successfully
firebase > updateMonth({foo:'new'})
'Successfully invoked function.'
firebase > info: User function triggered, starting execution
info: change.after.exists false
change.before.exists false
Old: undefined
Execution took 2 ms, user function completed successfully

我不确定如何获取对正在创建的新文档的引用。我希望在这种情况下,更改.after.exist是正确的。

使用 onWrite 和 onUpdate 触发器,您需要在所有情况下声明文档的"之前"和"之后"状态。 不能尝试通过省略"之前"或"之后"键来简化 API。 例如,如果您只想测试文档创建,请尝试以下操作:

updateMonth({
after:{foo:'new'}
})

此外,如果你的代码只对文档创建感兴趣,那么在 onCreate 触发器上编写可能比尝试在 onWrite 中找出文档状态更容易。 就个人而言,我避免使用onWrite并使用其他三个,因为它们更容易推断实际进行了哪些更改。

经过多次迭代,事实证明解决方案非常简单。 要成功模拟在使用 firebase 函数 shell 本地模拟云功能时触发 onWrite 的新文档创建,您需要显式提供 after 属性,如updateMonth({after:{foo:'newVal'}})所示:

firebase > updateMonth({after:{foo:'newVal'}})
'Successfully invoked function.'
firebase > info: User function triggered, starting execution
change.after.exists true
change.before.exists false
New: { foo: 'newVal' }
info: Execution took 291 ms, user function completed successfully

https://firebase.google.com/docs/functions/local-emulator#invoke_firestore_functions 的文档没有明确说明这一点,因此造成了混淆。也许这可能是添加到Firebase-tools的一个很好的增强功能firebase functions:shell。

最新更新