MySQL日志记录每个操作详情(mysql下日志)

MySQL日志:记录每个操作详情

在MySQL数据库中,日志是一个非常重要的概念。当我们需要追踪某些SQL语句的执行情况,或者需要恢复意外删除的数据时,日志起到了至关重要的作用。MySQL中提供了多种日志模式,如二进制日志、慢查询日志、错误日志等。其中,二进制日志是最为常用的日志模式,本文将会介绍如何记录MySQL的每个操作详情。

一、启用二进制日志

要启用MySQL的二进制日志,我们需要在MySQL配置文件my.cnf中加入以下内容:

[mysqld]
log-bin=/var/log/mysql/mysql-bin.log

其中log-bin指定了二进制日志文件记录的位置和文件名。一旦启用了二进制日志,MySQL会记录所有数据的更改,包括数据表的添加、删除和修改、数据记录值的添加、删除和修改等所有操作,并将这些操作以二进制文件形式写到log-bin文件中。

启动MySQL服务后,可以使用以下命令查看当前是否启用了二进制日志:

mysql> show variables like 'log_bin';

二、查看二进制日志

我们可以使用mysqlbinlog命令来查看MySQL的二进制日志。例如,使用以下命令查看从2021年8月1日到今天的二进制日志:

mysqlbinlog --start-datetime='2021-08-01' /var/log/mysql/mysql-bin.log

这将显示在2021年8月1日到今天之间所有的二进制操作,包括添加、删除和修改数据。

三、解析二进制日志

二进制日志是以二进制格式存储的,不能直接查看其中记录的操作内容,需要通过解析才能得到有用的信息。

MySQL提供了自带的binary log解析库,即mysqlbinlog,可以用来解析二进制日志。另外,我们还可以使用第三方的工具,例如Binlogpaser、Canal等。

以下是使用python脚本解析MySQL二进制日志的示例:

“`python

import pymysql

import os

import struct

class BinlogParser:

def __init__(self, host, port, user, password, log_file):

self.log_file = log_file

self.log_pos = 4

self.conn = pymysql.connect(host=host, port=port, user=user, password=password)

self.cursor = conn.cursor()

def __del__(self):

self.cursor.close()

self.conn.close()

def read_event(self):

“”” 读取一个二进制事件 “””

self.cursor.execute(‘SELECT LOAD_FILE(“{}”)’.format(self.log_file))

data = self.cursor.fetchone()[0]

event_header = struct.unpack(‘

event_body = data[self.log_pos+19:self.log_pos+event_header[0]]

self.log_pos += event_header[0]

return (event_header, event_body)

def parse_event(self):

“”” 解析二进制事件 “””

header, body = self.read_event()

event_type = header[4]

if event_type == 19:

“”” Table_map_event “””

table_id = struct.unpack(‘

table_name_len = body[8]

table_name = body[9:9+table_name_len].decode(‘utf-8’)

table_column_count = body[9+table_name_len+1]

table_column_types = body[9+table_name_len+2:]

column_types = [table_column_types[i] for i in range(0, len(table_column_types), 2)]

# 将解析结果返回

return {

‘event_type’: ‘Table_map_event’,

‘table_id’: table_id,

‘table_name’: table_name,

‘column_types’: column_types

}

elif event_type == 33:

“”” Write_rows_event “””

pass

# TODO 解析 Write_rows_event 的内容

elif event_type == 30:

“”” Update_rows_event “””

pass

# TODO 解析 Update_rows_event 的内容

elif event_type == 31:

“”” Delete_rows_event “””

pass

# TODO 解析 Delete_rows_event 的内容

else:

pass

# TODO 解析其它类型的事件

if __name__ == ‘__mn__’:

parser = BinlogParser(‘localhost’, 3306, ‘root’, ‘password’, ‘/var/log/mysql/mysql-bin.000001’)

while True:

event = parser.parse_event()

if not event:

break

# 处理 Table_map_event 事件

if event[‘event_type’] == ‘Table_map_event’:

print(‘Table_map_event: table_id={}, table_name={}, column_types={}’.format(

event[‘table_id’], event[‘table_name’], event[‘column_types’]))


上面的示例代码可以解析table_map_event类型的二进制事件,读者可以参考MySQL的官方文档和协议,自行解析其它类型的二进制事件。

数据运维技术 » MySQL日志记录每个操作详情(mysql下日志)