TL; DR 我应该使用Transaction.getAll()
还是使用for循环并使用Transaction.get()
请考虑以下架构:
- someTopLevelCollection
- accountId1
- projects
- tasks
- users
- accountId2
- projects
- tasks
- users
每当在项目中创建一个项目/任务时,分别在task子集合中,在用户集合中的计数器都会更新,例如projectsCount和taskCount。
对用户的引用作为userId的数组保存在项目和任务中,如下所示:
注意:为简洁起见,其他字段已删除
项目/任务结构:
{
"name": "someName",
"status": "someStatus",
"users": [
"userId1",
"userId2",
....
],
...
}
现在,我需要使用交易更新针对用户数组内所有userId的计数器。
方法1:
const accountId = context.params.accountId;
const userIds = snapshot.data().users;
userIds.forEach(userId => {
const userDocRef = db.collection(someTopLevelCollection)
.doc(accountId)
.collection('users')
.doc(userId);
let transaction = db.runTransaction(transaction => {
return transaction.get(userDocRef)
.then(doc => {
const snapshotData = doc.data();
let newCounterValue = snapshotData[counterName] + 1;
transaction.update(userDocRef, {counterName: newCounterValue});
return Promise.resolve(`Incremented ${counterName} to ${newCounterValue}`);
});
}).then(result => {
console.log('Transaction success!', result);
return true;
}).catch(err => {
console.error('Transaction failure:', err);
return false;
});
});
方法2:
const accountId = context.params.accountId;
const userIds = snapshot.data().users;
let userDocRefs = [];
userIds.forEach(userId => {
const userDocRef = db.collection(someTopLevelCollection)
.doc(accountId)
.collection('users')
.doc(userId);
userDocRefs.push(userDocRef)
});
let transaction = db.runTransaction(transaction => {
return transaction.getAll(userDocRefs)
.then(docs => {
docs.forEach(doc => {
const snapshotData = doc.data();
let newCounterValue = snapshotData[counterName] + 1;
transaction.update(doc.ref, {counterName: newCounterValue});
});
return Promise.resolve('Completed transaction successfully');
});
}).then(result => {
console.log('Transaction success!', result);
return true;
}).catch(err => {
console.error('Transaction failure:', err);
return false;
});
以下是我的问题:
getAll()
低于外部而外部发生文档更改时
执行,将再次获取所有文档以进行维护
一致性。如果是这样,使用getAll()的用例是什么?谢谢。