16.4.1.33 复制和事务

在同一事务中混合事务和非事务语句. 通常,应避免在复制环境中同时更新事务和非事务 table 的事务。您还应该避免使用访问事务 table(或临时 table)和非事务 table 并写入其中任何语句的任何语句。

服务器使用以下规则进行二进制日志记录:

  • 如果事务中的初始语句是非事务性的,则它们将立即写入二进制日志。事务中的其余语句将被缓存,直到提交事务后才写入二进制日志。 (如果回滚事务,则仅当高速缓存的语句进行了无法回滚的非事务性更改时,才会将其写入二进制日志.否则,将丢弃它们.)

  • 对于基于语句的日志记录,非事务性语句的日志记录受binlog_direct_non_transactional_updates系统变量影响。当此变量为OFF(默认值)时,日志记录如前所述。当此变量为ON时,将立即对事务中任何地方发生的非事务性语句(不仅是初始的非事务性语句)进行记录。其他语句保留在事务缓存中,并在事务提交时记录。 binlog_direct_non_transactional_updates对行格式或混合格式的二进制日志记录无效。

事务性,非事务性和混合语句. 要应用这些规则,如果服务器仅更改非事务性 table,则将其视为非事务性语句;如果仅更改事务性 table,则将其视为事务性。引用非事务处理 table 和事务处理 table 并更新所涉及 table 的任何的语句被视为“混合”语句。 (在某些过去的 MySQL 版本中,只有更新了*非事务 table 和事务 table 的语句才被认为是混合的.)事务提交时,将缓存和记录混合语句(例如事务语句)。

如果该语句还执行以下任一操作,则更新该事务 table 的混合语句将被视为不安全:

  • 更新或读取临时 table

  • 读取非事务 table,并且事务隔离级别小于 REPEATABLE_READ

如果在事务中更新事务 table 之后的混合语句执行以下任一操作,则被认为是不安全的:

有关更多信息,请参见第 16.2.1.3 节“二进制日志 Logging 安全和不安全语句的确定”

Note

混合语句与混合二进制日志记录格式无关。

在事务混合了对事务 table 和非事务 table 的更新的情况下,二进制日志中语句的 Sequences 是正确的,并且即使在ROLLBACK的情况下,所有需要的语句也会写入二进制日志。但是,当第二个连接在第一个连接事务完成之前更新了非事务 table 时,由于第二个连接更新是在执行后立即写入的,所以无论第一个连接正在执行的事务状态如何,都可以按 Sequences 注销语句。连接。

在源和副本上使用不同的存储引擎. 可以使用副本上的非事务 table 在源上复制事务 table。例如,您可以将InnoDB源 table 复制为MyISAM副本 table。但是,如果执行此操作,则副本会在BEGIN ... COMMIT块中间停止时会出现问题,因为副本会在BEGIN块的开头重新启动。

将事务从源上的MyISAMtable 复制到副本上的事务 table(例如使用InnoDB存储引擎的 table)也是安全的。在这种情况下,将复制源上发出的AUTOCOMMIT=1语句,从而在副本数据库上强制使用AUTOCOMMIT模式。

当副本的存储引擎类型为非事务性时,应避免源上的事务混合事务性和非事务性 table 的更新,因为它们会导致源事务性 table 和副本非事务性 table 之间的数据不一致。也就是说,此类事务可能导致特定于源存储引擎的行为,并可能导致复制不同步的影响。 MySQL 当前没有对此发出警告,因此,在将事务 table 从源复制到副本上的非事务 table 时,应格外小心。

在事务中更改二进制日志记录格式. 只要事务正在进行,binlog_formatbinlog_checksum系统变量为只读。

每个事务(包括autocommit个事务)都被记录在二进制日志中,就好像它以BEGIN语句开始,以COMMITROLLBACK语句结束一样。对于影响使用非事务性存储引擎(例如MyISAM)的 table 的语句,甚至都是如此。

Note

有关专门适用于 XATransaction 的限制,请参阅第 13.3.7.3 节“ XATransaction 限制”