【案例】MySQL table_open_cache配置过小导致thread running过高告警

前言

mysql突然接到thread running过高的告警。首先分析监控指标并未发现明显异常。进入mysql执行show processlist发现大量SQL处于opening tables和closing tables状态。初步怀疑是table_open_cache 参数设置过小。紧接着调大table_open_cahe参数后,告警恢复正常。

现象

1、mysql版本8.0.22
2、thread running迅速增长至500
3、执行show processlist发现大量SQL处于opening tables和closing tables状态

问题

本文主要以问题为切入点。

  • 为什么thread running会突增
  • 为什么执行processlist是会有大量的opening tables和closing tables。
  • 为什么调整完table_open_cahe后就恢复正常了。

分析

1、thread running很高通常意味着数据库正在处理大量的并发连接或查询。先查看指标监控,分析数据库是否存在性能瓶颈。检查cpu,内存,io等指标,并未发现明显异常,用户也未反馈异常。证明当前实例还能正常提供服务。无需紧急介入恢复,可以先分析原因。初步确定排查方向通常有以下几种可能:慢查询,事务锁,连接泄露等。

2、进一步验证猜想:登录mysql实例,查看当前有哪些线程正在运行。

show processlist;

发现有大量的线程长时间处于opening tables状态。表明数据库在处理查询时,频繁的打开与关闭表。

3、正常情况下mysql默认有了表缓存,不应该出现频繁的打开与关闭表。难道是配置太低了?

# 查看配置
SHOW VARIABLES LIKE 'table_open_cache%';

结果显示为:512。而table_open_cache_instances 为16

4、查看 Open_tables Opened_tables 的值

SHOW GLOBAL STATUS LIKE 'Open_tables';
SHOW GLOBAL STATUS LIKE 'Opened_tables';

发现 Open_tables 的值为 512,与 table_open_cache 相等,而 Opened_tables 的值非常高,表明表缓存频繁地被填满并清理。

5、这个实例业务有1000张表,明显大于open_tables。怀疑是open_tables被打满了

6、调大 table_open_cache 参数值,减少业务表频繁打开和关闭。

SET GLOBAL table_open_cache=2048;
SET GLOBAL table_open_cache_instances=128;

注意:这个数值需要根据mysql的实例规格来确定,设置过大可能导致内存不够用。通常 max_connections 和table_open_cache_instances 的默认比例为(1:16)。

7、结果验证:发现 “opening table” 状态的查询进程数量显著减少,thread
running 告警恢复。

原理

在没有表缓存实例的情况下,所有的客户端会话共享一个全局的表缓存。这意味着,当多个会话同时访问数据库时,它们可能会争用同一个表的缓存条目,从而导致锁竞争和性能下降。

表缓存实例的引入,通过将全局表缓存分割成多个较小的缓存区域,为每个会话提供了更独立的资源,从而减少了会话间的锁竞争,提高了数据库的可伸缩性。

通过设置 table_open_cache_instances,可以将打开的表缓存划分为多个较小的缓存实例。这样,每个会话只需要锁定它需要访问的一个实例,而不是整个表缓存。这有助于减少会话间的锁竞争,特别是在并发访问量高的情况下,可以显著提高数据库的并发处理能力。

总结

最终通过调整table_open_cachetable_open_cache_instances参数,恢复异常告警。核心原因为参数配置过小,无法满足高并发场景下的查询访问。

  • 23
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
在 Linux 系统中,buff/cache 是操作系统用来缓存磁盘数据的一种机制。当应用程序需要读取磁盘上的数据时,Linux 会先将这些数据缓存到内存中,以提高磁盘读取速度。当应用程序需要使用内存时,缓存数据会被清除,将内存返还给应用程序使用。 如果 buff/cache 内存占用过高,有几种可能的解决办法: 1. 调整 vm.dirty_ratio 和 vm.dirty_background_ratio 参数 vm.dirty_ratio 指定了内存中脏数据所占的最大比例,默认值为 20,意味着当内存中脏数据占用超过 20% 时,系统会开始写入磁盘。vm.dirty_background_ratio 指定了内存中脏数据所占的最小比例,默认值为 10,意味着当内存中脏数据占用低于 10% 时,系统会开始写入磁盘。 可以通过修改这两个参数的值来调整 buff/cache 内存占用。例如,将 vm.dirty_ratio 和 vm.dirty_background_ratio 的值都设置为 5,则系统会更频繁地把脏数据写入磁盘,从而减少内存中的缓存数据。 2. 调整 swappiness 参数 swappiness 是一个控制系统将内存中的数据交换到交换空间的程度的参数。默认值为 60,意味着当内存使用率达到 60% 时,系统会开始把一些数据写入交换空间。可以通过修改 swappiness 的值来调整系统的交换行为,从而影响 buff/cache 内存的占用。 例如,将 swappiness 的值设置为较低的 10,则系统会更倾向于保留内存中的缓存数据,从而减少交换行为,降低 buff/cache 内存占用。 3. 增加物理内存 如果系统中物理内存不足,buff/cache 内存占用就会相对较高。可以通过增加物理内存来减少 buff/cache 内存占用,从而提高系统的性能。 需要注意的是,增加物理内存并不是万能的解决办法,可能存在其他因素导致的 buff/cache 内存占用过高问题。在调整系统参数和增加物理内存之前,需要仔细分析系统的性能瓶颈和内存使用情况,找出问题的根本原因。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值