今天一大早就收到同事昨晚发过来的信息:某省份的充电桩在昨晚22点到23点期间大量挂单即充电不能结算。首先想到的就是订单服务挂了,可查了数据一切正常。所以继续早跑,等上班回公司再查查原因。
来到公司查看了昨晚的项目日记情况,发现订单服务没有报错,但发现处理的数据慢。数据库占用比较高,查mysql慢日记一堆堆的,这明显不正常,很多简单的sql慢了十来秒,这说明数据库遇到问题了,直接查数据库日记,果然发现大量的InnoDB: page_cleaner报错,如下图:
从MySql数据库日记发现,大量的[Note] InnoDB: page_cleaner: 1000ms intended loop took 17248ms. The settings might not be optimal. (flushed=11 and evicted=0, during the time.)错误。
InnoDB 的 page_cleaner
是负责清理和刷新脏页到磁盘的组件。在日志中有多个条目表明 page_cleaner
的运行时间有从几秒到几十秒的,远远超过了预期的 1000 毫秒。
这些长时间的执行可能是因为系统资源不足(如 CPU 或 I/O)导致的。
再继续查,更严重的是发现在零晨2点时mysql崩了,如下图:
关闭客户端连接,关闭主从同步,关闭失败重新强制关闭客户端连接。
逐步关闭各个插件和功能模块。
mysql停止完成
mysql启动
崩掉重启后还是报错InnoDB: page_cleaner,说明服务器资源很严重,该项目上线后就再没看服务器状态,不可能一下会出现这种情况,再向翻查了前端时间的日记,果然断断续续有报这个错,这是慢慢积累下来的,经分析该MySql数据库共建了两个库,分别都有几张千万级别的大数据表没有作处理,查询或更新时占用大量的资源,那个千万级别的表设计也不合理,设置大量的列作为索引列,这些在更新时也占用资源。看了innodb_buffer_pool_size内存只有默认的4G,直接增加innodb_buffer_pool_size内存,由原来的4G直接加到8G,如下图:
重启后数据库进程由原来的20-90%占用下到1-5%左右,一切恢复正常,持续到观察到现在也是正常的,如下图:
后续工作要继续优化大表。