上个月处理了一起 Oracle 19c RAC 的 SYSAUX 表空间 99% 告警,AWR 快照连续两天没有生成,业务方反馈数据库偶尔出现 ORA-135 报错,部分夜间批量任务也受到影响。排查到最后,基本确认是 AWR 内部数据异常:WRM$_SNAPSHOT 里的快照记录和 WRH$ 明细表对不上,手动调用 DBMS_WORKLOAD_REPOSITORY.DROP_SNAPSHOT_RANGE 清理历史快照还会触发 ORA-01555。当时评估了几种方案之后,决定直接重建 AWR。整个过程踩了不少坑,从 RAC 切单实例、清理 AWR 数据、恢复到集群状态,每一步都有讲究。今天把这套步骤按实际执行顺序整理出来,希望能帮到同样被 AWR 问题折磨的兄弟。
先说清楚一个概念:AWR 重建不是常规操作,能做的前提是问题定位准确。如果是 SYSAUX 表空间整体损坏,或者数据库出了其他更底层的问题,单纯重建 AWR 并不能解决根本故障。本文更适合你在确认“AWR 这部分的字典表、快照数据异常,且常规清理手段已经失效”的场景下参考。另外,不管是 11g、12c 还是 19c,这套思路基本通用,本次操作环境是 Oracle 19.17 的 2 节点 RAC。
1. 为什么需要重建AWR:场景与前置判断
1.1 AWR在RAC架构里的特殊地位
AWR(Automatic Workload Repository)是 Oracle 性能诊断体系的底座。默认每小时由 MMON 后台进程自动生成一次快照,把当时的等待事件、SQL 统计、会话活动、系统统计等信息写到 SYSAUX 表空间中一组以 WRM$、WRH$、WRI$ 开头的表里,保留周期默认 8 天。DBA 日常跑 awrrpt.sql 生成性能报告,看到的 Top SQL、段统计、IO 趋势都来源于这些表。
RAC 环境下的 AWR 比单实例要复杂。所有实例共享同一个数据库,SYSAUX 表空间也是共享的,每个节点的 MMON 都会往同一组 AWR 表里写数据。快照的对齐、全局数据的汇聚、节点间时钟偏差的处理,都需要内部机制去协调。一旦 AWR 表的数据出现逻辑混乱,受影响的不只是单个节点,而是整个集群的性能诊断能力。这也是为什么 RAC 里 AWR 出问题,不能只盯着那个报错的节点看,要从全局角度判断是哪个环节坏了。
1.2 触发重建的典型故障场景
结合我自己遇到的案例,以下场景最可能走到“重建”这一步:
- SYSAUX 表空间剩余空间持续告警,AWR 数据写入失败,快照无法生成。
- 查询 dba_hist_snapshot 直接报 ORA-00942、ORA-04063、ORA-00600 等错误,说明基础字典表或者相关对象已经损坏。
- 手动删除历史快照时长时间卡住,甚至报 ORA-01555,典型原因是 UNDO 太小,或者 AWR 内部清理逻辑触发了大事务回滚。
- 做过跨大版本升级或迁移之后,AWR 相关对象状态异常,大量失效对象没有恢复。
- ASH 或者某个 WRH$ 明细表异常膨胀,单个表占了十几个 GB,常规清理已经无法释放空间。
这些场景共同的特点是:常规的 AWR 维护手段(比如调整保留策略、手工 purge、删除旧快照)已经失效或不可控,只能通过重建让 AWR 回到一个干净、可用的初始状态。
1.3 动手前必须先做的三个确认
不要一看 AWR 报错就动手重建。执行之前,至少要确认三件事:
第一,问题确实出在 AWR 本身。可以先尝试 SELECT COUNT(*) FROM dba_hist_snapshot,如果报错,再看 alert 日志里有没有 AWR 相关的 ORA-00600、ORA-07445。同时确认 MMON 进程是否异常。排除掉实例级内存、ASM 磁盘空间的问题之后,再考虑重建。
第二,SYSAUX 表空间本身是否健康。AWR 的所有数据都在 SYSAUX 里,如果 SYSAUX 的数据文件有坏块或者表空间损坏,重建 AWR 也白搭。所以重建前要对 SYSAUX 做一次 RMAN 备份,并记录当前表空间大小。
第三,是否必须保留历史 AWR 数据。如果公司有合规要求,需要保留一年以上的性能数据,那重建前就要先用 awrextr.sql 把需要的历史快照导出,重建后再用 awrload.sql 导入。如果只是需要最近的报告,建议在重建前先跑一次 awrrpt.sql 把当前的问题时段报告导出来存档,避免重建后彻底丢失。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 重建前准备:备份、停机窗口与参数基线
2.1 SYSAUX表空间备份
重建 AWR 属于有损操作,虽然理论上只影响 AWR 数据,但谁也保不准执行过程中会不会误伤其他对象。我是强烈建议先做一次 RMAN 备份,确保可以随时回滚。
RMAN 备份命令很简单:
bash复制rman target /
BACKUP TABLESPACE SYSAUX FORMAT '/backup/sysaux_%U.bak' PLUS ARCHIVELOG;
如果数据库比
