暂无图片
暂无图片
3
暂无图片
暂无图片
暂无图片

MySQL 加密binlog读取方式

原创 CuiHulong 2024-12-19
950

从8.0.14版本开始,MySQL可以加密磁盘上binlog文件和relay文件。这样保证binlog泄露导致的安全问题。为此,需要启用binlog_encryption参数(并确保有一个密钥环keyring)。

mysql> SET GLOBAL binlog_encryption=ON;
ERROR 3794 (HY000): Unable to recover binlog encryption master key, please check if keyring is loaded.

配置binlog加密方式如下文件设置密钥环:

[mysqld]
early-plugin-load=keyring_file.so
keyring_file_data=/opt/data8.0/keyring_file/keyring
binlog_encryption=ON

读取binlog内容

当开启加密属性之后,会马上切换新的binlog文件,之后通过mysqlbinlog方式本地读取,会提示无法读取“ERROR: Reading encrypted log files directly is not supported.”错误提示:

shell# mysqlbinlog mysql-bin.000002 | grep "^# at " ERROR: Reading encrypted log files directly is not supported.

从上述内容中说明,当binlog文件被加密后,mysqlbinlog无法直接读取,按照官方指导可以使用–read from remote server选项从服务器读取。

1.使用read-from-remote-server参数读取

shell# mysqlbinlog --user=root --password=123456 --socket=/opt/data8.0/data/mysql.sock \ --read-from-remote-server --base64-output=DECODE-ROWS -v -v \ mysql-bin.000002 BEGIN 。。。 ### INSERT INTO `w1`.`t1` ### SET ### @1=3 /* LONGINT meta=0 nullable=0 is_null=0 */ ### @2='C' /* VARSTRING(1020) meta=1020 nullable=1 is_null=0 */ # at 509 #241217 14:21:21 server id 129 end_log_pos 540 CRC32 0x9256dac0 Xid = 26 COMMIT/*!*/; 。。。

2.使用SHOW BINLOG命令行读取

SHOW BINLOG EVENTS命令可以以列表的形式显示日志中的事件信息。

mysql> SHOW BINLOG EVENTS IN 'mysql-bin.000002'; +------------------+-----+----------------+-----------+-------------+-----------------------------+ | Log_name | Pos | Event_type | Server_id | End_log_pos | Info | +------------------+-----+----------------+-----------+-------------+-----------------------------+ | mysql-bin.000002 | 4 | Format_desc | 129 | 126 | Server ver: 8.0.40, Binlog ver: 4 | | mysql-bin.000002 | 126 | Previous_gtids | 129 | 197 | 8f789b76-4024-11ef-b562-00163e23e2cc:1 | | mysql-bin.000002 | 197 | Gtid | 129 | 276 | SET @@SESSION.GTID_NEXT= '8f789b76-4024-11ef-b562-00163e23e2cc:2' | | mysql-bin.000002 | 276 | Query | 129 | 349 | BEGIN | | mysql-bin.000002 | 349 | Rows_query | 129 | 410 | # insert into t1(id,Name) values(3,'C') | | mysql-bin.000002 | 410 | Table_map | 129 | 462 | table_id: 116 (w1.t1) | | mysql-bin.000002 | 462 | Write_rows | 129 | 509 | table_id: 116 flags: STMT_END_F | | mysql-bin.000002 | 509 | Xid | 129 | 540 | COMMIT /* xid=26 */ | +------------------+-----+----------------+-----------+-------------+-----------------------------+ 8 rows in set (0.00 sec)

3.使用mysqlbinlog备份导出文件读取

如果使用mysqlbinlog备份加密的binlog文件,生成的文件副本是以未加密的格式存储的。

shell# mysqlbinlog --user=root --password=123456 --socket=/opt/data8.0/data/mysql.sock \ --read-from-remote-server --base64-output=DECODE-ROWS -v -v mysql-bin.000002\ --result-file=/tmp/mysqlbin.sql shell# less /tmp/mysqlbin.sql #241217 14:21:21 server id 129 end_log_pos 509 CRC32 0xb1d88abf Write_rows: table id 116 flags: STMT_END_F ### INSERT INTO `w1`.`t1` ### SET ### @1=3 /* LONGINT meta=0 nullable=0 is_null=0 */ ### @2='C' /* VARSTRING(1020) meta=1020 nullable=1 is_null=0 */ # at 509 #241217 14:21:21 server id 129 end_log_pos 540 CRC32 0x9256dac0 Xid = 26 COMMIT/*!*/;

4.离线加密binlog文件读取

需要原主库的keyring文件。
1.把原主库的keyring文件,拷贝到新节点。
2.把binlog文件拷贝的新的节点。
3.新节点mysql-bin.index文件,注册拷贝的binlog文件。
4.重新启动新节点MySQL服务。
可以通过mysqlbinlog 和 show event命令行,可以解读binlog内容了。

5.如何判断binlog是否加密

当然可以通过命令行查询参数 或 直接mysqlbinlog查看时候能正常显示。按照一些互网上研究,可以通过查看binlog文件的header (的前四个字节),可以判断出对binlog和relay文件是否进行加密。总结出未加密的文件已0xFE62696E的header信息,但加密文件已0xFD62696E的header信息。

shell# echo $( hexdump -v -e '/1 "%02X"' mysql-bin.000001 -n 4 ) FE62696E shell# echo $( hexdump -v -e '/1 "%02X"' mysql-bin.000002 -n 4 ) FD62696E

总结

虽然MySQL的binlog文件进行加密了。但可以通过hexdump命令研究规则,反解析binlog文件,并进行破解。

参考

http://mysql.taobao.org/monthly/2019/12/02/
https://dev.mysql.com/blog-archive/binary-log-encryption-at-rest/
https://dev.mysql.com/blog-archive/how-to-manually-decrypt-an-encrypted-binary-log-file/

最后修改时间:2025-01-07 16:42:28
「喜欢这篇文章,您的关注和赞赏是给作者最好的鼓励」
关注作者
【版权声明】本文为墨天轮用户原创内容,转载时必须标注文章的来源(墨天轮),文章链接,文章作者等基本信息,否则作者和墨天轮有权追究责任。如果您发现墨天轮中有涉嫌抄袭或者侵权的内容,欢迎发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

评论