<p>SHOW PROCESSLIST 显示当前活跃连接但默认限100条且需PROCESS权限;推荐用SHOW FULL PROCESSLIST或SELECT * FROM information_schema.PROCESSLIST,结合STATE分组统计可快速识别Sleep过长、Locked等异常状态。</p>

如何用 SHOW PROCESSLIST 查看当前 MySQL 会话数
直接执行 SHOW PROCESSLIST 就能看到所有活跃连接,但默认只显示前 100 条,且普通用户看不到其他用户的会话。想看到完整列表,得有 PROCESS 权限(通常只有 root 或监控账号具备)。
更稳妥的做法是用 SHOW FULL PROCESSLIST,它不截断 SQL 文本,对排查长查询特别有用。如果权限不够,会报错:Access denied; you need (at least one of) the PROCESS privilege(s) for this operation。
- 非 root 用户可改用
SELECT * FROM information_schema.PROCESSLIST,只要对information_schema有 SELECT 权限就能查,但返回结果里INFO字段对非自身会话为 NULL -
SHOW PROCESSLIST是即时快照,不带历史信息;它不等同于当前并发连接数,因为部分状态(如Sleep)可能已空闲但未断开 - 注意区分
Threads_connected(当前已建立的 TCP 连接数)和Threads_running(真正正在执行任务的线程数),后者更能反映真实负载
State 字段含义与典型问题识别
State 是判断连接是否异常的关键。不是所有 Sleep 都健康——如果大量连接卡在 Sleep 且 Time 值持续增长(比如 > 300 秒),大概率是应用没正确关闭连接,或连接池配置不合理。
常见危险状态:
-
Locked:表级锁等待,多见于 MyISAM 或未加索引的 UPDATE/DELETE -
Sending data:持续时间过长,说明查询扫描数据太多,需检查执行计划 -
Copying to tmp table:内存临时表溢出到磁盘,可能是排序/分组数据量超tmp_table_size -
Waiting for table metadata lock:DDL 操作(如ALTER TABLE)阻塞了 DML,尤其在大表上要小心
快速统计连接数并按状态分组
光看列表效率低,用聚合查询更直观:
SELECT STATE, COUNT(*) AS cnt FROM information_schema.PROCESSLIST GROUP BY STATE ORDER BY cnt DESC;
这能一眼看出有多少连接卡在 Sleep、Query 或 Locked。再配合 USER 和 HOST 字段,还能定位是哪个应用 IP 或账号拖慢了整体:
SELECT USER, HOST, STATE, COUNT(*) FROM information_schema.PROCESSLIST GROUP BY USER, HOST, STATE;
- 注意
information_schema.PROCESSLIST中的TIME单位是秒,不是毫秒 - 该表不支持
WHERE TIME > 60这类条件下推优化,大数据量时可能稍慢,但一般几百连接无压力 - 避免在业务高峰频繁轮询,单次查询即可,过度查询本身会增加线程调度负担
为什么 max_connections 没超,还是连不上?
即使 SHOW VARIABLES LIKE 'max_connections'; 显示还有余量,也可能因操作系统资源耗尽而拒绝新连接。重点检查:
-
ulimit -n:MySQL 进程能打开的文件描述符上限,每个连接至少占 2–3 个 fd -
net.core.somaxconn(Linux):内核层面 TCP 连接队列长度,太小会导致 SYN 包被丢弃 - 内存不足:
innodb_buffer_pool_size+ 线程堆栈 + 其他缓存超过物理内存,触发 OOM Killer 杀掉 mysqld - 连接未及时释放:应用端未调用
close(),或连接池maxIdle设置过大导致连接长期闲置却不回收
真正卡住的地方,往往不在 MySQL 配置里,而在 OS 层或应用连接管理逻辑中。


















