6.4交易生命周期

建立新连接时,THD->事务成员初始化为空状态。如果语句使用任何表,则所有受影响的引擎都在语句引擎列表中注册。在非自动车辆模式下,相同的引擎在正常事务列表中注册。在该语句的末尾,服务器发出语句列表中所有引擎的提交或回滚。此时,引擎的事务标志(如果有的话)从语句列表传播到正常事务的列表。提交/回滚完成后,声明列表已清除。它将被下一个陈述再次填写,并在下一个陈述的结束时再次清空。

普通事务以类似的方式提交(通过在thd->事务中检查所有引擎。所有列表),但在不同的时间:

  • 当用户发出SQL Commit语句时

  • 隐含地,当服务器开始处理DDL语句或设置AutoCommit = {0 | 1}语句

正常交易也可以回滚:

  • 当用户播放SQL Roldback语句时

  • 当其中一个存储引擎通过设置thd-> transaction_rollback_request请求回滚

For example, the latter condition may occur when the transaction in the engine was chosen as a victim of the internal deadlock resolution algorithm and rolled back internally.在这种情况下,服务器可以做的很少,并且唯一的选择是在所有其他参与引擎中回滚交易,并向用户发送错误。

从上面的用例中,它遵循,当存在未完成的语句交易时,从未提交正常交易。在大多数情况下,没有冲突,因为正常事务的提交由独立的管理或DDL语句发出,因此不存在先前语句的未完成的语句事务。此外,通过正常交易运行的所有语句都禁止在存储的函数中,触发器,因此,在子句中没有发生冲突的情况。当服务器显式必须在进行正常事务之前必须提交语句事务时,剩余的罕见情况是错误处理案例(参见例如SQLCOM_LOCK_TABLES)。

在提交语句或正常事务时,服务器要么使用两阶段提交协议,或独立地发出每个引擎中的提交。仅当以下情况时,服务器使用两阶段提交协议:

  • 所有参与引擎都支持两阶段提交(通过提供手持人::准备PSEA API呼叫),以及

  • 至少两个引擎中的事务修改数据(即,不是只读)

请注意,两阶段提交用于语句事务,即使语句事务无论如何都不耐用。这确保了多引擎事务中数据的逻辑一致性。例如,想象一下,MySQL支持删除的唯一约束检查​​,直到语句结束。在这种情况下,其中一个引擎中的提交可以产生er_dup_key,并且MySQL应该能够优雅地中止其他参与者的陈述事务。

在进行正常事务后,THD-> Transaction.all列表已清除。

当连接关闭时,将回滚当前的正常事务(如果有的话)。