MySQL服务器二进制日志
二进制日志包含描述数据库更改(例如表创建操作或表数据更改)的“事件”。它还包含针对可能进行了更改的语句的事件(例如,DELETE
不匹配任何行的a),除非使用基于行的日志记录。二进制日志还包含有关每个语句花费该更新数据多长时间的信息。二进制日志有两个重要目的:
- 对于复制,主复制服务器上的二进制日志提供了要发送到从属服务器的数据更改的记录。主服务器将其二进制日志中包含的事件发送到其从属服务器,从属服务器执行这些事件以对主服务器进行相同的数据更改。请参见“复制实现的详细信息”。
- 某些数据恢复操作需要使用二进制日志。还原备份后,将重新执行在执行备份后记录的二进制日志中的事件。这些事件使数据库从备份开始就保持最新状态。请参见“使用二进制日志进行时间点(增量)恢复”。
二进制日志不用于诸如SELECT
或SHOW
不修改数据的语句。要记录所有语句(例如,确定问题查询),请使用常规查询日志。请参见“mysqldumpslow 汇总慢查询日志文件”。
运行启用了二进制日志记录的服务器会使性能稍微降低。但是,二进制日志在使您能够设置复制和进行还原操作方面的好处通常超过了这种较小的性能下降。
二进制日志可以抵抗意外的暂停。仅记录或读取完整的事件或事务。
服务器将重写写在二进制日志中的语句中的密码,以使它们不会以纯文本的形式出现。另
从MySQL 8.0.14开始,可以对二进制日志文件和中继日志文件进行加密,从而有助于保护这些文件以及其中包含的潜在敏感数据,使其免受外部攻击者的滥用,并防止未经授权的用户参见其所在的操作系统被存储。通过将binlog_encryption
系统变量设置为,可以在MySQL服务器上启用加密ON
。有关更多信息,请参见“加密二进制日志文件和中继日志文件”。
以下讨论描述了一些影响二进制日志记录操作的服务器选项和变量。有关完整列表,请参见“二进制记录选项和变量”。
默认情况下启用二进制日志记录(log_bin
系统变量设置为ON)。例外是,如果默认情况下禁用二进制日志记录,但可以通过指定选项启用mysqld,则通过使用--initialize
or --initialize-insecure
选项通过调用mysqld手动初始化数据目录--log-bin
。
要禁用二进制日志记录,可以在启动时指定--skip-log-bin
或--disable-log-bin
选项。如果指定了这些选项中的一个并且--log-bin
也指定了该选项,则后面指定的选项优先。
在--log-slave-updates
和--slave-preserve-commit-order
选项需要二进制日志。如果禁用二进制日志记录,请忽略这些选项,或者指定--log-slave-updates=OFF
和--skip-slave-preserve-commit-order
。当指定--skip-log-bin
或时,MySQL默认禁用这些选项--disable-log-bin
。如果指定--log-slave-updates
或--slave-preserve-commit-order
连同--skip-log-bin
或者--disable-log-bin
,发出警告或错误信息。
该选项用于指定二进制日志文件的基本名称。如果不提供该选项,则MySQL将使用二进制日志文件的默认基本名称。为了与早期版本兼容,如果提供的选项不带字符串或带空字符串,则基本名称默认为,使用主机名。建议您指定一个基本名称,以便在主机名更改时,可以轻松地继续使用相同的二进制日志文件名(请参见第B.4.7节“ MySQL中的已知问题”)。如果您在日志名称中提供扩展名(例如),则该扩展名将被静默删除并忽略。--log-bin[=base_name]
--log-bin
binlog
--log-bin
host_name-bin
--log-bin=base_name.extension
mysqld在二进制日志基本名称后附加数字扩展名,以生成二进制日志文件名。每次服务器创建新的日志文件时,该数目都会增加,从而创建了有序的文件系列。每次服务器启动或刷新日志时,服务器都会在系列中创建一个新文件。在当前日志的大小达到后,服务器还会自动创建一个新的二进制日志文件max_binlog_size
。max_binlog_size
与使用大型事务相比,二进制日志文件可能会变得更大,因为一个事务被整体写入文件中,而切勿在文件之间分割。
为了跟踪使用了哪些二进制日志文件,mysqld还创建了一个二进制日志索引文件,其中包含二进制日志文件的名称。默认情况下,该名称与二进制日志文件具有相同的基本名称,扩展名为'.index'
。您可以使用该选项更改二进制日志索引文件的名称。当mysqld运行时,您不应该手动编辑该文件。这样做会使mysqld混淆。--log-bin-index[=file_name]
术语“二进制日志文件”通常表示包含数据库事件的单独编号文件。术语“二进制日志”共同表示一组编号的二进制日志文件加上索引文件。
二进制日志文件和二进制日志索引文件的默认位置是数据目录。您可以使用该--log-bin
选项来指定替代位置,方法是在基本名称中添加前导绝对路径名以指定其他目录。当服务器从二进制日志索引文件中读取一个条目(该文件跟踪已使用的二进制日志文件)时,它将检查该条目是否包含相对路径。如果是这样,则将路径的相对部分替换为使用--log-bin
选项。二进制日志索引文件中记录的绝对路径保持不变;在这种情况下,必须手动编辑索引文件以启用新路径。二进制日志文件的基本名称和任何指定的路径都可以用作log_bin_basename
系统变量。
在MySQL 5.7中,启用二进制日志记录时必须指定服务器ID,否则服务器将无法启动。在MySQL 8.0中,server_id
系统变量默认设置为1。启用二进制日志记录后,可以使用此默认ID启动服务器,但是如果您未使用server_id
系统变量显式指定服务器ID,则会发出参考消息。对于复制拓扑中使用的服务器,必须为每个服务器指定一个唯一的非零服务器ID。
具有足以设置受限制的会话系统变量的特权的客户机(请参见“系统变量特权”)可以通过使用SET sql_log_bin=OFF
语句禁用其自身语句的二进制记录。
默认情况下,服务器记录事件的长度以及事件本身,并使用它来验证事件是否正确写入。您还可以通过设置binlog_checksum
系统变量使服务器为事件编写校验和。从二进制日志回读时,默认情况下,主服务器使用事件长度,但可以通过启用master_verify_checksum
系统变量使它使用校验和。从属I / O线程还验证从主控接收到的事件。通过启用slave_sql_verify_checksum
系统变量,可以在从中继日志中读取时使从属SQL线程使用校验和(如果可用)。
二进制日志中记录的事件的格式取决于二进制日志格式。支持三种格式类型:基于行的日志,基于语句的日志和基于混合的日志。使用的二进制日志记录格式取决于MySQL版本。有关日志记录格式的一般说明,有关二进制日志格式的详细信息,请参见 MySQL内部知识:二进制日志。
服务器使用--binlog-do-db
和--binlog-ignore-db
选项相同的方式评估--replicate-do-db
和--replicate-ignore-db
选项。有关如何完成此操作的信息,请参见“数据库级复制和二进制日志记录选项的评估”。
复制从属服务器在log_slave_updates
默认情况下启用系统变量的情况下启动,这意味着从属服务器会将从复制主服务器收到的所有数据修改写入其自己的二进制日志。必须启用二进制日志才能使此设置生效(请参见“复制从站选项和变量”)。此设置使从属服务器可以充当链式复制中其他从属服务器的主服务器。
您可以使用RESET MASTER
语句删除所有二进制日志文件,或者使用删除它们的子集PURGE BINARY LOGS
。请参见“ RESET语句”和“ PURGE BINARY LOGS语句”。
如果使用复制,则在确保没有从属仍需要使用它们之前,不应删除主服务器上的旧二进制日志文件。例如,如果您的从属服务器从未运行超过三天,则可以每天一次在主服务器上执行mysqladmin flush-logs,然后删除超过三天的任何日志。您可以手动删除文件,但是最好使用PURGE BINARY LOGS
,它还会为您安全地更新二进制日志索引文件(并且可以使用date参数)。请参见“ PURGE BINARY LOGS语句”。
您可以使用mysqlbinlog实用程序显示二进制日志文件的内容。当您要重新处理日志中的语句以进行恢复操作时,此功能很有用。例如,您可以从二进制日志更新MySQL服务器,如下所示:
shell>mysqlbinlog log_file | mysql -h server_name
mysqlbinlog也可用于显示复制从中继日志文件的内容,因为它们使用与二进制日志文件相同的格式编写。有关 mysqlbinlog实用程序及其使用方法的更多信息,请参见“ mysqlbinlog-处理二进制日志文件的实用程序”。有关二进制日志和恢复操作的更多信息,请参见“使用二进制日志进行时间点(增量)恢复”。
在语句或事务完成之后但在释放任何锁或完成任何提交之前,立即执行二进制日志记录。这样可以确保日志以提交顺序记录。
非事务表的更新在执行后立即存储在二进制日志中。
在未提交的事务中,所有更改事务表(例如表)的更新(UPDATE
,DELETE
或INSERT
)都会InnoDB
被缓存,直到COMMIT
服务器接收到一条语句。此时,mysqld在COMMIT
执行之前将整个事务写入二进制日志。
对非事务表的修改不能回滚。如果回滚的事务包括对非事务表的修改,则记录整个事务ROLLBACK
并在末尾添加一条语句,以确保复制对这些表的修改。
当处理事务的线程启动时,它将binlog_cache_size
为缓冲区语句分配一个缓冲区。如果语句大于此值,则线程将打开一个临时文件来存储事务。当线程结束时,将删除临时文件。从MySQL 8.0.17开始,如果服务器上的二进制日志加密处于活动状态,则对临时文件进行加密。
所述Binlog_cache_use
状态变量表明,用这种缓冲液(和可能的一个临时文件),用于存储语句事务的数目。该Binlog_cache_disk_use
状态变量显示有多少交易实际上不得不使用临时文件。这两个变量可用于调整binlog_cache_size
到足够大的值,从而避免使用临时文件。
所述max_binlog_cache_size
系统变量(默认4GB,这也是最大)可被用来限制用于高速缓存的多语句事务的总大小。如果事务大于此多个字节,它将失败并回滚。最小值是4096。
如果使用二进制日志和基于行的日志记录,则并发插入将转换为CREATE ... SELECT
或INSERT ... SELECT
语句的普通插入。这样做是为了确保您可以通过在备份操作期间应用日志来重新创建表的精确副本。如果您使用基于语句的日志记录,则原始语句将被写入日志。
二进制日志格式具有一些已知的局限性,可能会影响从备份的恢复。请参见“复制功能”。
如“存储的程序二进制日志记录”中所述完成存储程序的二进制日志记录。
请注意,由于复制功能的增强,MySQL 8.0中的二进制日志格式与以前的MySQL版本有所不同。请参见“ MySQL版本之间的复制兼容性”。
如果服务器无法写入二进制日志,刷新二进制日志文件或将二进制日志同步到磁盘,则复制主数据库上的二进制日志可能会变得不一致,并且复制从数据库可能会与主数据库失去同步。所述binlog_error_action
系统变量控制,如果这种类型的误差与二进制日志遇到所采取的行动。
- 默认设置,
ABORT_SERVER
使服务器停止二进制日志记录并关闭。此时,您可以确定并纠正错误原因。重新启动后,将继续进行恢复,就像服务器意外停止一样(请参见“处理复制从设备的意外停止”)。 - 该设置
IGNORE_ERROR
提供了与旧版本MySQL的向后兼容性。使用此设置,服务器将继续进行中的事务并记录错误,然后停止二进制日志记录,但继续执行更新。此时,您可以确定并纠正错误原因。要恢复二进制日志记录,log_bin
必须再次启用,这需要重新启动服务器。仅在需要向后兼容性且二进制日志在此MySQL服务器实例上为非必需时才使用此选项。例如,您可能只将二进制日志用于服务器的间歇审核或调试,而不将其用于从服务器复制或将其用于时间点还原操作。
默认情况下,二进制日志在每次写入(sync_binlog=1
)时都会同步到磁盘。如果sync_binlog
未启用它,并且操作系统或计算机(不仅是MySQL服务器)崩溃,则二进制日志的最后一条语句可能会丢失。为防止这种情况,请sync_binlog
在每个N
提交组之后启用系统变量以将二进制日志同步到磁盘。请参见“服务器系统变量”。最安全的值为sync_binlog
1(默认值),但这也是最慢的。
在早期的MySQL版本中,即使发生崩溃,即使sync_binlog
设置为1 ,表内容和二进制日志内容之间也可能存在不一致的情况。例如,如果您使用InnoDB
表并且MySQL服务器处理一条COMMIT
语句,它将编写许多准备好的语句。将事务按顺序发送到二进制日志,同步二进制日志,然后将事务提交到中InnoDB
。如果服务器在这两个操作之间崩溃,则事务将InnoDB
在重新启动时回滚,但仍存在于二进制日志中。通过InnoDB
在XA事务中启用对两阶段提交的支持,在以前的版本中解决了此问题。在8.0.0及更高版本中,InnoDB
始终启用对XA事务中的两阶段提交的支持。
InnoDB
XA事务中对两阶段提交的支持可确保二进制日志和InnoDB
数据文件同步。但是,MySQL服务器也应配置为InnoDB
在提交事务之前将二进制日志和日志同步到磁盘。该InnoDB
日志由缺省同步,并sync_binlog=1
保证了二进制日志是同步的。隐式InnoDB
支持XA事务中的两阶段提交的效果sync_binlog=1
是,崩溃后重新启动时,在回滚事务后,MySQL服务器将扫描最新的二进制日志文件以收集事务xid
值并计算事务中的最后一个有效位置。二进制日志文件。然后,MySQL服务器会告诉InnoDB
完成将已成功写入二进制日志的所有准备好的事务,并将二进制日志截断到最后一个有效位置。这样可以确保二进制日志反映InnoDB
表的确切数据,因此从服务器与主服务器保持同步,因为它没有收到已回滚的语句。
如果MySQL服务器在崩溃恢复时发现二进制日志短于其应有的时间,则它至少缺少一个成功提交的InnoDB
事务。如果sync_binlog=1
在请求时磁盘和文件系统进行了实际的同步(某些情况下没有这样做),则该情况就不会发生,因此服务器将输出一条错误消息。在这种情况下,此二进制日志不正确,应从主数据的新快照重新开始复制。The binary log file_name is shorter than its expected size
解析二进制日志时,以下系统变量的会话值将写入二进制日志并由复制从属服务器遵循:
sql_mode
(除了NO_DIR_IN_CREATE
不复制模式外;请参见“复制功能”)foreign_key_checks
unique_checks
character_set_client
collation_connection
collation_database
collation_server
sql_auto_is_null
二进制记录格式
服务器使用几种日志记录格式在二进制日志中记录信息:
- MySQL中的复制功能最初是基于SQL语句从主服务器到从服务器的传播。这称为基于语句的日志记录。您可以通过使用启动服务器来使用此格式
--binlog-format=STATEMENT
。 - 在基于行的日志记录(默认)中,主服务器将事件写入二进制日志,以指示各个表行的影响方式。您可以通过以开头使服务器使用基于行的日志记录
--binlog-format=ROW
。 - 还有第三个选项:混合日志记录。对于混合日志记录,默认情况下使用基于语句的日志记录,但是在某些情况下,日志记录模式会自动切换为基于行,如下所述。通过使用option 启动mysqld,可以使MySQL显式使用混合日志记录
--binlog-format=MIXED
。
日志记录格式还可以通过使用的存储引擎来设置或限制。这有助于消除在使用不同存储引擎的主服务器和从服务器之间复制某些语句时出现的问题。
使用基于语句的复制时,复制不确定性语句可能会出现问题。在确定给定语句对于基于语句的复制是否安全时,MySQL确定是否可以保证可以使用基于语句的日志记录来复制该语句。如果MySQL无法做出此保证,它将标记该语句为潜在不可靠的对象并发出警告,以语句格式登录该语句可能并不安全。
您可以通过使用MySQL的基于行的复制来避免这些问题。
设置二进制日志格式
您可以通过使用启动MySQL服务器来显式选择二进制日志记录格式。支持的值为:--binlog-format=type
type
STATEMENT
使日志记录基于语句。ROW
使日志记录基于行。这是默认值。MIXED
使日志记录使用混合格式。
日志记录格式也可以在运行时进行切换,尽管请注意,在许多情况下您无法执行此操作,如本节后面所述。设置binlog_format
系统变量的全局值,以为更改之后连接的客户端指定格式:
mysql>SET GLOBAL binlog_format = 'STATEMENT'; mysql>SET GLOBAL binlog_format = 'ROW'; mysql>SET GLOBAL binlog_format = 'MIXED';
单个客户端可以通过将会话值设置为来控制其自己的语句的日志记录格式binlog_format
:
mysql>SET SESSION binlog_format = 'STATEMENT'; mysql>SET SESSION binlog_format = 'ROW'; mysql>SET SESSION binlog_format = 'MIXED';
更改全局binlog_format
值需要足够的特权来设置全局系统变量。更改会话binlog_format
值需要足够的特权来设置受限制的会话系统变量。请参见“系统变量特权”。
客户端可能要基于每个会话设置二进制日志记录的原因有几个:
- 对数据库进行许多小更改的会话可能要使用基于行的日志记录。
- 执行与
WHERE
子句中的许多行匹配的更新的会话可能要使用基于语句的日志记录,因为记录几条语句比记录多行会更有效。 - 有些语句在主服务器上需要大量执行时间,但导致仅修改了几行。因此,使用基于行的日志记录来复制它们可能是有益的。
当您无法在运行时切换复制格式时,会有一些例外情况:
- 无法从存储的函数或触发器中更改复制格式。
- 如果
NDB
启用了存储引擎。 - 如果会话具有打开的临时表,则无法更改会话(
SET @@SESSION.binlog_format
)的复制格式。 - 如果任何复制通道都有打开的临时表,则不能全局(
SET @@GLOBAL.binlog_format
或SET @@PERSIST.binlog_format
)更改复制格式。 - 如果当前正在运行任何复制通道应用程序线程,则不能全局(
SET @@GLOBAL.binlog_format
或SET @@PERSIST.binlog_format
)更改复制格式。
在任何这些情况下尝试切换复制格式(或尝试设置当前复制格式)都会导致错误。但是,您可以随时使用PERSIST_ONLY
(SET @@PERSIST_ONLY.binlog_format
)更改复制格式,因为此操作不会修改运行时全局系统变量值,并且仅在服务器重新启动后才生效。
不存在任何临时表时,建议不要在运行时切换复制格式,因为仅在使用基于语句的复制时才记录临时表,而在基于行的复制和混合复制中,则不会记录它们。
在复制进行过程中切换复制格式也会导致问题。每个MySQL Server可以设置自己的并且只能设置自己的二进制日志记录格式(无论binlog_format
是全局范围还是会话范围,都为true )。这意味着更改复制主服务器上的日志记录格式不会导致从属服务器更改其日志记录格式以匹配。使用STATEMENT
模式时,binlog_format
不会复制系统变量。在使用MIXED
或ROW
记录模式时,它会被复制,但被从属设备忽略。
复制从站无法将以ROW
日志记录格式接收的二进制日志条目STATEMENT
转换为在其自己的二进制日志中使用的格式。因此,如果主服务器需要,则从服务器必须使用ROW
或MIXED
格式化。将主服务器上的二进制日志记录格式从更改STATEMENT
为ROW
或MIXED
正在进行复制到从属服务器时,其STATEMENT
格式会导致复制失败,并显示以下错误,例如错误执行行事件:'无法执行语句:由于语句位于行中,因此无法写入二进制日志格式,BINLOG_FORMAT = STATEMENT。”将从站上的二进制日志记录格式更改为STATEMENT
当主服务器仍在使用时格式化MIXED
或ROW
格式化也会导致相同类型的复制失败。为了安全地更改格式,必须停止复制并确保在主服务器和从服务器上都进行了相同的更改。
如果使用InnoDB
表,并且事务隔离级别为READ COMMITTED
或READ UNCOMMITTED
,则只能使用基于行的日志记录。这是可能的更改日志格式STATEMENT
,但在运行时引线这样做非常迅速地错误,因为InnoDB
不能再进行插入。
将二进制日志格式设置ROW
为时,使用基于行的格式将许多更改写入二进制日志。但是,某些更改仍然使用基于语句的格式。实例包括所有DDL(数据定义语言)语句,例如CREATE TABLE
,ALTER TABLE
,或DROP TABLE
。
使用基于行的二进制日志记录时,binlog_row_event_max_size
系统变量及其相应的启动选项--binlog-row-event-max-size
对行事件的最大大小设置了软限制。默认值为8192字节,并且只能在服务器启动时更改该值。如果可能,将二进制日志中存储的行分组为大小不超过此设置的值的事件。如果事件无法拆分,则可以超过最大大小。
该--binlog-row-event-max-size
选项可用于能够进行基于行的复制的服务器。行以块大小存储在二进制日志中,块大小不超过此选项的值。该值必须是256的倍数。默认值为8192。
警告当使用基于语句的日志记录进行复制时,如果以一种不确定的方式修改数据的方式设计语句,则主服务器和从服务器上的数据可能会有所不同。也就是说,它由查询优化器决定。通常,即使在复制之外,这也不是一个好习惯。有关此问题的详细说明,请参见第B.4.7节“ MySQL中的已知问题”。
有关复制从站保存的日志的信息,请参见“复制中继和状态日志”。
混合二进制记录格式
当以MIXED
日志记录格式运行时,服务器在以下情况下自动从基于语句的记录切换为基于行的记录:
- 当一个函数包含时
UUID()
。 当一个或多个带有
AUTO_INCREMENT
列的表被更新并且触发器或存储的函数被调用时。像所有其他不安全的语句一样,如果会生成警告binlog_format = STATEMENT
。有关更多信息,请参见“InnoDB中的AUTO_INCREMENT处理”。
- 当视图主体需要基于行的复制时,创建视图的语句也将使用它。例如,当创建视图的语句使用该
UUID()
函数时,就会发生这种情况。 - 当涉及到UDF的调用时。
- 使用
FOUND_ROWS()
或时ROW_COUNT()
。(缺陷#12092,缺陷#30244) - 使用
USER()
,CURRENT_USER()
或时CURRENT_USER
。(错误#28086) - 当涉及的表之一是
mysql
数据库中的日志表时。 - 使用该
LOAD_FILE()
功能时。错误39701) 当一条语句引用一个或多个系统变量时。错误#31168)
例外。以下系统变量(仅与会话范围一起使用)不会导致切换日志记录格式:
uto_increment_increment
uto_increment_offset
character_set_client
character_set_connection
character_set_database
character_set_server
collation_connection
collation_database
collation_server
foreign_key_checks
identity
last_insert_id
lc_time_names
pseudo_thread_id
sql_auto_is_null
time_zone
timestamp
unique_checks
有关确定系统变量范围的信息,请参见“使用MySQL服务器系统变量”。
有关复制如何处理的信息
sql_mode
,请参见“复制功能”。
在早期版本中,当使用混合二进制日志记录格式时,如果按行记录一条语句,并且执行该语句的会话具有任何临时表,则所有后续语句均被视为不安全,并以基于行的格式记录,直到所有临时表该会话正在使用中的已删除。从MySQL 8.0开始,对临时表的操作不会以混合二进制日志格式记录,并且会话中临时表的存在不会影响每个语句所使用的日志模式。
注意如果尝试使用基于语句的日志记录执行语句,则应使用基于行的日志记录来生成警告。在客户端(在的输出中
SHOW WARNINGS
)和mysqld错误日志中均显示该警告。SHOW WARNINGS
每次执行该语句时,都会向表中添加一条警告。但是,仅将为每个客户端会话生成警告的第一条语句写入错误日志,以防止泛滥该日志。
除了上述决定外,各个引擎还可以确定更新表中信息时使用的日志记录格式。单个引擎的日志记录功能可以定义如下:
- 如果引擎支持基于行的日志记录,则称该引擎具有行记录功能。
- 如果引擎支持基于语句的日志记录,则该引擎被称为具有语句记录能力。
给定的存储引擎可以支持一种或两种日志格式。下表列出了每个引擎支持的格式。
储存引擎 | 支持行记录 | 支持语句记录 |
---|---|---|
ARCHIVE | 是 | 是 |
BLACKHOLE | 是 | 是 |
CSV | 是 | 是 |
EXAMPLE | 是 | 没有 |
FEDERATED | 是 | 是 |
HEAP | 是 | 是 |
InnoDB | 是 | 当事务隔离级别为REPEATABLE READ 或时为“是”SERIALIZABLE ;没有其他。 |
MyISAM | 是 | 是 |
MERGE | 是 | 是 |
NDB | 是 | 没有 |
是否一个语句是要记录与要使用的是根据语句的类型所确定的记录模式(安全,不安全,或二进制注入),二进制日志记录格式(STATEMENT
,ROW
,或MIXED
),并且存储发动机的记录功能(具有陈述能力,具有行能力,或者两者都没有)。(二进制注入是指记录必须使用ROW
格式记录的更改。)
可能会在有或没有警告的情况下记录语句;失败的语句不会记录,但是会在日志中生成错误。如下决策表所示。 Type, binlog_format, SLC和 RLC列概述了条件,而Error / Warning 和Logged as列表示相应的操作。SLC 代表“有语句记录能力”,而 RLC代表“有行记录能力”。
Type | binlog_format | SLC | RLC | Error / Warning | Logged as |
---|---|---|---|---|---|
* | * | No | No | Error: Cannot execute statement: Binary logging is impossible since at least one engine is involved that is both row-incapable and statement-incapable. | - |
Safe | STATEMENT | Yes | No | - | STATEMENT |
Safe | MIXED | Yes | No | - | STATEMENT |
Safe | ROW | Yes | No | Error: Cannot execute statement: Binary logging is impossible since BINLOG_FORMAT = ROW and at least one table uses a storage engine that is not capable of row-based logging. | - |
Unsafe | STATEMENT | Yes | No | Warning: Unsafe statement binlogged in statement format, since BINLOG_FORMAT = STATEMENT | STATEMENT |
Unsafe | MIXED | Yes | No | Error: Cannot execute statement: Binary logging of an unsafe statement is impossible when the storage engine is limited to statement-based logging, even if BINLOG_FORMAT = MIXED . | - |
Unsafe | ROW | Yes | No | Error: Cannot execute statement: Binary logging is impossible since BINLOG_FORMAT = ROW and at least one table uses a storage engine that is not capable of row-based logging. | - |
Row Injection | STATEMENT | Yes | No | Error: Cannot execute row injection: Binary logging is not possible since at least one table uses a storage engine that is not capable of row-based logging. | - |
Row Injection | MIXED | Yes | No | Error: Cannot execute row injection: Binary logging is not possible since at least one table uses a storage engine that is not capable of row-based logging. | - |
Row Injection | ROW | Yes | No | Error: Cannot execute row injection: Binary logging is not possible since at least one table uses a storage engine that is not capable of row-based logging. | - |
Safe | STATEMENT | No | Yes | Error: Cannot execute statement: Binary logging is impossible since BINLOG_FORMAT = STATEMENT and at least one table uses a storage engine that is not capable of statement-based logging. | - |
Safe | MIXED | No | Yes | - | ROW |
Safe | ROW | No | Yes | - | ROW |
Unsafe | STATEMENT | No | Yes | Error: Cannot execute statement: Binary logging is impossible since BINLOG_FORMAT = STATEMENT and at least one table uses a storage engine that is not capable of statement-based logging. | - |
Unsafe | MIXED | No | Yes | - | ROW |
Unsafe | ROW | No | Yes | - | ROW |
Row Injection | STATEMENT | No | Yes | Error: Cannot execute row injection: Binary logging is not possible since BINLOG_FORMAT = STATEMENT . | - |
Row Injection | MIXED | No | Yes | - | ROW |
Row Injection | ROW | No | Yes | - | ROW |
Safe | STATEMENT | Yes | Yes | - | STATEMENT |
Safe | MIXED | Yes | Yes | - | STATEMENT |
Safe | ROW | Yes | Yes | - | ROW |
Unsafe | STATEMENT | Yes | Yes | Warning: Unsafe statement binlogged in statement format since BINLOG_FORMAT = STATEMENT . | STATEMENT |
Unsafe | MIXED | Yes | Yes | - | ROW |
Unsafe | ROW | Yes | Yes | - | ROW |
Row Injection | STATEMENT | Yes | Yes | Error: Cannot execute row injection: Binary logging is not possible because BINLOG_FORMAT = STATEMENT . | - |
Row Injection | MIXED | Yes | Yes | - | ROW |
Row Injection | ROW | Yes | Yes | - | ROW |
当确定产生警告时,将产生标准的MySQL警告(并且可以使用来使用SHOW WARNINGS
)。该信息也被写入mysqld错误日志。每个客户端连接的每个错误实例仅记录一个错误,以防止泛滥日志。日志消息包含尝试的SQL语句。
如果从属服务器已log_error_verbosity
设置为显示警告,则从属服务器会将错误消息打印到错误日志中,以提供有关其状态的信息,例如二进制日志和中继日志坐标(从其开始工作时,切换到另一个中继日志时,它会在断开连接,对于基于语句的日志记录不安全的语句等之后重新连接。
更改MySQL数据库表的日志记录格式
mysql
可以直接(例如,使用INSERT
或DELETE
)或间接地(例如使用GRANT
或CREATE USER
)修改数据库中授权表的内容。mysql
使用以下规则将影响数据库表的语句写入二进制日志:
mysql
根据binlog_format
系统变量的设置,直接记录直接更改数据库表中数据的数据操作语句。这适用于语句,如INSERT
,UPDATE
,DELETE
,REPLACE
,DO
,LOAD DATA
,SELECT
,和TRUNCATE TABLE
。mysql
不管的值如何,都将间接更改数据库的语句记录为语句binlog_format
。这涉及语句,例如GRANT
,REVOKE
,SET PASSWORD
,RENAME USER
,CREATE
(所有形式的除外CREATE TABLE ... SELECT
),ALTER
(所有形式的),和DROP
(各种形式)。
CREATE TABLE ... SELECT
是数据定义和数据处理的组合。该CREATE TABLE
部分是利用语句格式记录,且SELECT
部分是根据的值记录binlog_format
。