.runTransaction(async transaction => {
const newContractUid = uuid();
const newContractRef = firestore
.collection(COLLECTION_CONTRACTS)
.doc(newContractUid);
const creatorRef = firestore.collection(COLLECTION_USERS).doc(creatorId);
const recipientRef = firestore
.collection(COLLECTION_USERS)
.doc(recipientId);
const [creator, recipient, newContractDoc] = [
await transaction.get(creatorRef),
await transaction.get(recipientRef),
await transaction.get(newContractRef)
];
if (newContractDoc.exists) {
console.warn("Attempted to create contract with already taked UUID");
return Promise.reject(
"Attempted to create contract with already taken UUID"
);
}
contractData.creationDate = Date.now().toString();
transaction.set(newContractRef, contractData);
// Update recipient and creator with contract relations
transaction.update(creatorRef, {
contracts: _.concat(creator.data().contracts, newContractUid)
});
transaction.update(recipientRef, {
contracts: _.concat(recipient.data().contracts, newContractUid)
});
})
我有这段代码可以在我的Firestore中创建新合同。然后,它将合同与两个用户(创建者和接收者)相关联。
但是我担心这行代码:
transaction.update(creatorRef, {
contracts: _.concat(creator.data().contracts, newContractUid)
});
在交易发生时,另一个用户是否有可能写到creator.data()字段并使此处的数据无效。还是在交易期间拥有写锁?
编辑:
嗯,我在firebase文档中看到了
例如,如果某个事务读取文档,而另一个客户端修改了这些文档中的任何一个,则Cloud Firestore重试该事务。此功能可确保交易在最新且一致的数据上运行。
我认为这意味着我在这种情况下很安全,但是我不确定
答案 0 :(得分:2)
Firestore事务可防止并发写入。如果它检测到冲突的写入,则会重试该事务,因此对于单个写入操作,您的事务处理程序可能会被调用多次。