RDS MySQL General log常见问题

本文列举开启general log的常见问题供您参考。

背景信息

基于以下原因,RDS MySQL选择TABLE作为general log的默认存储格式:

  1. 保存为FILE格式用户无法进行查询,因为用户无法直接访问RDS MySQL的文件。

  2. general log和slow log同时受log_output参数影响,RDS MySQL在采集slow log时使用了rotate的机制,需要保存为TABLE格式。

General log占据大量存储空间

问题描述

RDS MySQL实例存储空间已满,通过如下排查,确认为general log文件过大导致。

  1. 查看实例存储空间使用量,sys_data_size文件过大。详情请参见查看监控信息

  2. 查看实例参数,实例已开启general_log(运行参数值为ON)。详情请参见查看实例参数

  3. 连接RDS MySQL实例并执行如下语句,查询发现general log文件过大。连接实例的详细请参见连接RDS MySQL实例

    SELECT table_schema AS '数据库', table_name,SUM(data_length + index_length + data_free)/1024/1024 AS "表大小MB",SUM(DATA_FREE)/1024/1024 AS "碎片大小MB"
    FROM information_schema.TABLES
    WHERE table_name='general_log'
    说明
    • 此SQL语句会从information_schema 数据库的TABLES表中检索mysql.general_log表的数据,然后将其转换成以MB为单位的大小。

    • 此SQL语句获得的数据为抽样数据,和实际数据存在一定误差。

问题原因

当RDS MySQL开启了general log后,该文件记录了用户的所有操作,包括每条SQL语句的执行细节,无论是查询、插入、更新还是删除操作。当访问量大或者长时间不清理general log文件时,会占用大量的存储空间,导致存储空间耗尽。

General log导致性能问题

问题描述

连接数上升,CPU使用率升高。通过SHOW PROCESSLIST或者查看innodb_trx表等方式,可见大量连接处于Waiting for table level lock状态。

问题原因

RDS MySQL选择TABLE作为general log的默认存储格式,各线程写general log是串行写入的。这是因为写general log除了需要加MDL锁以外,还需要加表锁。也正是该表锁导致了“Waiting for table level lock”状态的出现。

General log导致RTO变长

问题描述

实例崩溃恢复时间变长,在此期间实例处于无法连接状态。

问题原因

实例非正常Shutdown ,general log的Crash标记位会置为true,导致实例重启后进入到自动恢复的逻辑,当表很大时,恢复时间很长,此过程中实例无法连接。

解决方法

清理general log文件

  1. 关闭general log(运行参数值设为OFF),以防止产生新的日志。详情请参见设置实例参数

  2. 使用高权限账号连接RDS MySQL实例并执行如下语句,清理general log文件。连接实例的详细信息请参见连接RDS MySQL实例

    说明

    RDS MySQL 5.6版本实例不支持通过TRUNCATE命令清理general log文件。

    TRUNCATE TABLE mysql.general_log;

后续维护

  • 建议只在调试或跟踪问题时临时开启general log,使用完成之后请及时关闭general log。

  • 建议您开启SQL洞察和审计,该功能可以自动记录和分析来自数据库内核的SQL语句,以及SQL语句的执行账号、IP地址、执行详情等信息,对实例性能没有影响。并且SQL洞察和审计数据存储在数据库自治服务DAS中,不占用RDS MySQL存储空间。

  • 扩容实例存储空间,详情请参见变更配置。您也可以开启存储空间自动扩容,在实例存储空间达到设定的阈值时,系统会自动扩容存储空间,详情请参见设置存储空间自动扩容