11.4 二进制日志
二进制日志记录所有更新数据的SQL语句,其中也包含可能更新数据的SQL语句,例如DELETE语句执行过程中无匹配的行。二进制日志中还包含了与执行SQL语句相关的内容,例如SQL语句执行的时间、错误代码等。
11.4.1 二进制日志功能介绍
MySQL中的二进制日志主要有两个功能:数据恢复和数据复制。
数据恢复--MySQL本身具备数据备份和恢复功能。例如我们可以每天午夜12:00进行数据备份。但是,此类备份功能并不是对数据库的实时备份,如果数据库在下午17:00出现故障无法恢复,那么从前一天午夜12:00到当天下午17:00的数据库内容将丢失。通过二进制日志可以解决这个问题。可以通过前一天午夜12:00的数据库备份文件恢复数据库,然后使用二进制日志恢复从前一天午夜12:00到当天下午17:00的数据库内容。
数据复制--MySQL支持主从服务器间的数据复制功能,并通过该功能实现数据库的冗余机制以保证数据库的可用性和提高数据库的性能。MySQL正是通过主服务器的二进制日志来实现数据的传递。主服务器上的二进制日志内容会被发送到各个从服务器,并在每个从服务器上执行,从而保证了主从服务器之间数据的一致性。
在默认配置下,MySQL不记录二进制日志。可以通过设置参数--log-bin=[base_name]启用二进制日志功能,MySQL会将修改数据库内容的语句记录到以base_name-bin.0000X为名字的日志文件中。其中bin代表binary,后缀0000X为二进制日志文件顺序。每次MySQL启动时,日志文件顺序会自动加1。如果base_name未定义,MySQL将使用pid-file参数设置的值作为二进制日志文件的基础名字。
我们可以从前面介绍的二进制日志的功能(数据恢复和数据复制)看出,二进制日志主要是供MySQL内部使用的,并不是为了数据库管理员阅读使用。因此,二进制日志与前面介绍的几种日志一个重要的不同就是,二进制日志文件的格式不是文本格式,其内容不能通过记事本直接查看。但是,为了管理员的方便,MySQL也提供了一个名为mysqlbinlog的工具,用于查看和处理二进制日志文件的内容。mysqlbinlog的用法为直接在命令后面添加二进制日志文件作为参数,比如:$mysqlbinlog jason2-bin.000001,其中jason2-bin.000001为二进制日志文件。
该命令运行后的结果如下,为了方便阅读,只节选了一部分具有代表性的内容:
从第1~14行记录了一条对数据库更改操作的SQL语句(第12行):insert into t values ('12345')。第1行记录内容如表11-6所示。
表11-6 记录内容说明
090713 17:20:08 |
该SQL语句执行时间 |
server id 1 |
执行SQL语句的ServerID,在数据库复制情形下, server id用于标识每个MySQL服务器 |
end_log_pos 199 |
表示该条记录的终止位置为199, 对应日志文件中的第14行 |
Query |
SQL语句的类型 |
thread_id=1 |
发出SQL语句请求的线程ID。当每个客户端 连接到MySQL服务器时,MySQL会为该用户 分配一个唯一的ID,用以标识该用户的线程 |
exec_time=0 |
SQL语句执行的时间 |
error_code=0 |
SQL语句执行的错误代码。0表示SQL语句执行成功 |
日志的第2行表示切换到MySQL服务器的test数据库。第3~11行设置当前会话的一些环境变量,例如是否自动提交(session.autocommit)、是否检查外键约束(session.foreign_key_ checks)等。如果需要了解它们详细的参数和说明,可以参考MySQL使用手册的第5章第1小节。
日志第12行为该条记录的核心,即对数据库进行了更改操作的SQL语句(insert into t values ('12345'))。日志第14行表示该条日志记录的结束。
以上分析了MySQL二进制日志如何记录一条对数据库进行更改的SQL语句,对于其他SQL语句的记录格式与上面的类似。
前面提到,每次MySQL启动时,日志文件顺序会自动加1。例如当前二进制日志文件名为:jason2-bin.000001,停止并重启动MySQL后,二进制日志文件名为jason2-bin.000002,新的更改数据库的操作将被记录到新的文件中。旧的二进制日志文件用于进行数据库的复制或者恢复。
默认情况下,在数据库目录下还有一个索引文件用来记录已经使用的二进制日志文件的名字,该索引文件的名字为"hostname-bin.index"。下面是索引文件的内容:
索引文件最后一行表示当前正在使用的二进制日志名字。