You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Aurora Postgres持续出现pg_statistic autovacuum超时问题

问题根因

核心原因是全局存在长时间未推进的最老事务ID(xmin=4230263474),阻塞了vacuum的死元组清理逻辑。
PostgreSQL的vacuum清理死元组的前提是:死元组对当前所有存活的事务/会话都不可见。只要有一个会话持有比死元组xmin更老的backend_xmin,这些死元组就会被判定为「cannot be removed yet」,无法被清理。
你看到pg_statistic表死元组堆积速度快、autovacuum反复触发,是因为pg_statistic是存储列统计信息的系统目录表,每次ANALYZE(包括自动触发的统计信息更新)都会高频更新表数据,死元组产生速度远高于普通业务表,一旦xmin被卡住,死元组会快速累积,autovacuum每次启动都做无用功,就会持续刷你看到的vacuum日志。手动执行VACUUM仅耗时5秒就完成,也能证明表本身不存在锁阻塞、IO瓶颈,纯粹是可见性规则限制导致无法清理死元组。

异常日志截图

排查与修复步骤
  • 首先定位持有最老xmin的会话,执行以下SQL查询:
SELECT pid, usename, application_name, state, query, xact_start, age(backend_xmin) AS xmin_age
FROM pg_stat_activity
WHERE backend_xmin IS NOT NULL
ORDER BY xmin_age DESC
LIMIT 10;
  • 常见导致xmin长时间不推进的场景:
    • 业务侧存在未正常提交/回滚的长事务,比如代码逻辑漏写commit、事务被阻塞后一直挂起
    • 存在积压未消费的逻辑复制槽,复制槽会持久持有消费位点对应的xmin,不消费就不会推进
    • 存在长期未处理的两阶段提交事务
    • Aurora特有场景:只读副本上运行的慢查询/长事务,会在主实例上持有对应xmin,哪怕主实例本身没有长事务,只读节点的长查询也会阻塞主节点的vacuum清理
  • 定位到异常会话/复制槽/两阶段事务后,终止异常会话、删除无用复制槽、提交/回滚两阶段事务即可,xmin推进后下次vacuum运行就能正常清理堆积的死元组。
临时缓解方案

如果暂时无法定位xmin卡住的源头,可以手动执行带FREEZE参数的vacuum临时清理可冻结的死元组,释放空间,但该操作无法解决根因,不处理xmin卡住的问题死元组会再次堆积:

VACUUM FREEZE pg_catalog.pg_statistic;

内容的提问来源于stack exchange,提问作者adnan kamili

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.02 09:24:34