Callback API 与 Core API
The Callback API:
启动事务,执行指定操作并提交(或在出错时中止)。
Automatically incorporates error handling logic for
TransientTransactionErrorandUnknownTransactionCommitResult.
The Core API:
需要显式调用以启动并提交事务。
Does not incorporate error handling logic for
TransientTransactionErrorandUnknownTransactionCommitResult, and instead provides the flexibility to incorporate custom error handling for these errors.
回调 API
回调 API 包含以下逻辑:
To retry the transaction as a whole if the transaction encounters a
TransientTransactionErrorerror.To retry the commit operation if the commit encounters an
UnknownTransactionCommitResulterror.
Starting in MongoDB 6.2, the server does not retry the transaction if it receives a TransactionTooLargeForCache error.
例子
Core API
核心事务 API 不包含标记为以下错误的重试逻辑:
TransientTransactionError. If an operation in a transaction returns an error labeledTransientTransactionError, the transaction as a whole can be retried.To handle
TransientTransactionError, applications should explicitly incorporate retry logic for the error.UnknownTransactionCommitResult. If the commit returns an error labeledUnknownTransactionCommitResult, the commit can be retried.To handle
UnknownTransactionCommitResult, applications should explicitly incorporate retry logic for the error.
例子
以下示例包含在出现暂时性错误时重试事务的逻辑,以及在出现未知提交错误时重试提交的逻辑:
驱动程序版本
事务错误处理
无论是何种数据库系统,无论是 MongoDB 还是关系型数据库,应用程序都应采取相应措施来处理事务提交期间的错误,并包含事务的重试逻辑。
TransientTransactionError
事务中的单独写入操作不可重试,无论 retryWrites 的值如何。如果操作遇到与标签相关的 "TransientTransactionError" 错误(例如主节点降级时),可以将事务作为一个整体进行重试。
回调 API 包含
"TransientTransactionError"的重试逻辑。The core transaction API does not incorporate retry logic for
"TransientTransactionError". To handle"TransientTransactionError", applications should explicitly incorporate retry logic for the error. To view an example that incorporates retry logic for transient errors, see Core API Example.
UnknownTransactionCommitResult
提交操作是可重试写入操作。如果提交操作遇到错误,那么无论 retryWrites 的值如何,MongoDB 驱动程序都会重试提交。
如果提交操作遇到标记为 "UnknownTransactionCommitResult" 的错误,则可以重试提交。
回调 API 包含
"UnknownTransactionCommitResult"的重试逻辑。核心事务 API 不包含
"UnknownTransactionCommitResult"的重试逻辑。要处理"UnknownTransactionCommitResult",应用程序应显式包含错误的重试逻辑。要查看包含未知提交错误的重试逻辑示例,请参阅 Core API 示例。
TransactionTooLargeForCache
6.2版本新增。
从 MongoDB 6.2 开始,服务器在收到 TransactionTooLargeForCache 错误后不会重试事务。此错误意味着缓存过小,重试可能会失败。
transactionTooLargeForCacheThreshold 阈值的默认值为 0.75。当事务使用超过 75% 的缓存时,服务器会返回 TransactionTooLargeForCache 而不是重试事务。
在 MongoDB 的早期版本中,服务器会返回 TemporarilyUnavailable 或 WriteConflict,而不是 TransactionTooLargeForCache。
使用 setParameter 命令修改错误阈值。
更多信息
mongosh 例子
The following mongosh methods are available for transactions:
注意
The mongosh example omits retry logic and robust error handling for simplicity's sake. For a more practical example of incorporating transactions in applications, see Transaction Error Handling instead.
// Create collections: db.getSiblingDB("mydb1").foo.insertOne( {abc: 0}, { writeConcern: { w: "majority", wtimeout: 2000 } } ) db.getSiblingDB("mydb2").bar.insertOne( {xyz: 0}, { writeConcern: { w: "majority", wtimeout: 2000 } } ) // Start a session. session = db.getMongo().startSession( { readPreference: { mode: "primary" } } ); coll1 = session.getDatabase("mydb1").foo; coll2 = session.getDatabase("mydb2").bar; // Start a transaction session.startTransaction( { readConcern: { level: "local" }, writeConcern: { w: "majority" } } ); // Operations inside the transaction try { coll1.insertOne( { abc: 1 } ); coll2.insertOne( { xyz: 999 } ); } catch (error) { // Abort transaction on error session.abortTransaction(); throw error; } // Commit the transaction using write concern set at transaction start session.commitTransaction(); session.endSession();