Oracle数据库性能分析思路?从AWR报告开始
怎么看AWR报告里的Top 5 Timed Events
拿到一份AWR报告,从哪里入手最直接?答案无疑是“Top 5 Timed Events”这个部分。它就像一份数据库的“体检报告摘要”,清晰地列出了过去一段时间里,系统最耗时的五类等待事件。不过,这里有个关键点需要厘清:排名靠前,未必就等于“病入膏肓”。
免费影视、动漫、音乐、游戏、小说资源长期稳定更新! 👉 点此立即查看 👈
举个例子,db file sequential read(单块物理读)在OLTP系统中名列前茅,其实是常态,说明系统正在频繁地通过索引读取数据。但若是在一个数据仓库环境里,这个事件的占比突然飙升到40%以上,那就得敲响警钟了。这很可能意味着大量SQL没有利用好索引,或者分区裁剪(Partition Pruning)失效,导致系统不得不进行大量低效的单块扫描。
此外,报告里还常出现一些“干扰项”。比如,看到latch: shared pool或library cache lock等待,先别急着调整内存参数。它们往往指向同一个根源:硬解析过多。这时候,首要任务是检查应用程序是否规范地使用了绑定变量(Bind Variables)。另一个典型是enq: TX - row lock contention(行锁争用),只看它的总等待时间意义不大,必须结合ASH(Active Session History)报告,才能精准定位到具体的阻塞会话链,搞清楚到底是谁锁住了谁。
- 生成报告有讲究:建议使用
awr_report_text脚本生成文本版报告。HTML格式虽然美观,但有时会掩盖原始数据的精度,不利于细节分析。 - 对比才有价值:单独看一个快照期的Top 5,信息是孤立的。更有效的做法是,对比业务高峰时段与低谷时段的报告。如果某个等待事件的差异超过2倍,那它才真正值得你投入精力深挖。
- 理解指标本质:特别注意“Time(s)”这一列,它显示的是累计等待时间,而非单次平均耗时。像
log file sync(日志文件同步)这类事件,可能单次等待很短,但如果发生频率极高,累计起来的总时间同样会拖慢整体TPS(每秒事务数)。
SQL ordered by Elapsed Time 为什么不能直接信
这个列表很容易让人产生误解。它是按照SQL的总执行时间(Elapsed Time)来排序的。但问题在于,一条运行10分钟的报表SQL,一天只执行一次,它对系统造成的整体压力,可能远不如那条每秒执行5次、每次耗时200毫秒的“短小精悍”的SQL。
那么,应该关注什么?真正的“性能消耗大户”,往往是那些“每秒逻辑读”(Buffer Gets/Exec)和“每秒执行次数”(Executions/sec)双高的SQL。在实操中,建议先过滤掉module字段显示为SQL*Plus或TOAD的条目(这些通常是DBA或开发人员的临时手动操作),然后按Executions(执行次数)列进行倒序排查。如果某条SQL的执行次数是其他SQL的10倍以上,即使它的单次耗时排不进前20,也务必优先分析它。
- 追溯历史变化:利用
DBA_HIST_SQLSTAT视图,可以查看SQL执行计划的历史变化。如果发现plan_hash_value(执行计划哈希值)发生了突变,这通常伴随着性能的剧烈抖动,是重要的排查线索。 - 识别“坏SQL”:一个简单的经验法则是,如果一条SQL的“单次执行耗时”(Elapsed Time per Exec)大于1秒,同时“总执行次数”(Executions)又超过1000次,那么它基本可以被判定为需要优化的目标。
- 警惕硬解析:关注
Parse Calls(解析调用)与Executions(执行次数)的比值。如果这个比值接近1:1,说明几乎每次执行都伴随着一次硬解析,这强烈暗示应用程序没有有效使用绑定变量。
Buffer Gets和Physical Reads差10倍意味着什么
这两个指标的比值,是衡量数据库IO压力的一个核心风向标。Buffer Gets(逻辑读)代表从内存中读取数据块的次数,而Physical Reads(物理读)则代表必须从磁盘读取的次数。两者相差越大,说明内存命中率越高,物理IO压力越小。
通常,这个比值维持在10倍以上被认为是比较健康的。但如果比值跌到5以下,尤其是在SGA(系统全局区)配置充足的情况下,就需要高度警惕了。这大概率说明,某些SQL的执行计划选择了全表扫描(Full Table Scan),而放弃了本该使用的索引;或者,索引本身的选择性太差,被优化器(CBO)主动弃用了。
分析时,切忌只看总量。应该通过DBA_HIST_SEG_STAT视图,进一步钻取到具体的数据对象(如表、索引),查看它们的physical_reads情况。如果发现某张体积很小的表,其物理读次数却异常高,那它很可能就是性能瓶颈的源头。
- 深挖执行计划:检查相关SQL的执行计划,特别关注
access_predicates(访问谓词)和filter_predicates(过滤谓词)。这里常常隐藏着隐式的数据类型转换,导致索引失效。 - 锁定统计信息:对于核心业务表,可以考虑使用
DBMS_STATS.LOCK_TABLE_STATS过程锁定其统计信息,避免数据库自动收集统计信息时,因数据波动导致执行计划发生不可预知的突变。 - 关注直接路径读:如果等待事件中间出现了显著的
direct path read,这意味着有大容量数据的排序或哈希连接操作,绕过了Buffer Cache直接进行磁盘IO。在这种情况下,适当增加pga_aggregate_target(PGA聚合目标)的大小,可能比调整SGA更能有效提升性能。
AWR快照间隔设成1小时真合适吗
默认的1小时快照间隔,对于许多现代业务系统来说,可能过于粗放了。想象一个场景:在交易系统的“秒杀”活动中,峰值负载可能只持续了短短30秒,CPU使用率瞬间飙升至95%。如果快照间隔是1小时,这30秒的尖峰会被平均稀释到整个小时段里,在AWR报告中几乎无法被察觉,从而错失关键的性能诊断线索。
因此,对于OLTP这类对响应时间敏感的系统,建议将快照间隔缩短至15到30分钟。在已知的批处理窗口或压力测试期间,甚至可以临时调整为5分钟,以捕获更精细的性能画像。
当然,物极必反。快照并非越密越好。过于频繁的快照会迅速撑大SYSAUX表空间,而且生成和存储快照本身也会消耗一定的系统资源。实测表明,当快照间隔
- 规范调整设置:使用
DBMS_WORKLOAD_REPOSITORY.MODIFY_SNAPSHOT_SETTINGS存储过程来调整快照间隔和保留策略,切勿手动删除WRH$_基表中的记录,否则会导致DBA_HIST_*系列视图的数据关联断裂,影响历史分析。 - 手动捕获关键点:在预知的高峰业务期开始前,可以主动调用
DBMS_WORKLOAD_REPOSITORY.CREATE_SNAPSHOT手动创建一个快照,确保这个关键时间窗口能被精确捕获。 - 定期清理策略:对于问题诊断而言,保留最近7天的快照数据通常已经足够。可以使用
DBMS_WORKLOAD_REPOSITORY.DROP_SNAPSHOT_RANGE定期清理历史快照,以管理SYSAUX表空间的大小。
最后,必须强调一个在实际分析中最容易被忽略的要点:AWR与ASH的交叉验证。简单来说,AWR告诉你“系统哪里慢”(宏观趋势),而ASH则能告诉你“在慢的那个时间点,具体是哪些会话在做什么”(微观细节)。例如,当Top 5事件中间出现高企的cursor: pin S wait on X等待时,只看AWR你只能联想到共享池(Shared Pool)争用。但结合ASH分析,你或许就能直接定位到,是因为某个存储过程在循环中反复执行EXECUTE IMMEDIATE,从而引发了剧烈的游标争用。二者结合,方能构成完整的问题诊断拼图。
游乐网为非赢利性网站,所展示的游戏/软件/文章内容均来自于互联网或第三方用户上传分享,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系youleyoucom@outlook.com。
同类文章
PostgreSQL修改最大连接数的详细操作步骤
前言 和PostgreSQL打交道久了,多半都撞见过这个熟悉又头疼的错误:“sorry, too many clients already”。问题出在哪?很简单,默认情况下PostgreSQL把最大连接数设在了100。对个人项目或小规模测试来说,这个数字绰绰有余。可一旦放到生产环境,尤其是面对突发的
PostgreSQL中VACUUM操作的锁机制详细对比解析
PostgreSQL 中 VACUUM 操作的锁机制对比 说到 PostgreSQL 的维护和空间回收,绕不开 VACUUM。但你知道吗?同样是 VACUUM,不同执行方式背后的锁机制差异巨大,对数据库并发性的影响也截然不同。目前主要有三种:AutoVACUUM、手动 VACUUM 和 VACUUM
数据仓库中常用的元数据管理系统
大数据数仓领域的元数据管理系统 在构建和维护企业级数据仓库的过程中,选择合适的元数据管理工具至关重要,它能显著提升数据治理效率。这类系统不仅是数据的“身份证”和“说明书”,更是厘清数据血缘关系、保障数据质量、实现高效数据资产管理的核心平台。市场上的元数据管理解决方案主要分为开源工具、云平台内置服务以
docker安装Postgresql数据库及基本操作
单机部署 先来搭建一个单机版的环境,这是所有复杂架构的基础。操作其实很简单,跟着步骤走就行。 创建映射目录 mkdir data postgresql data 启动容器 docker run -d -p 5432:5432 --restart=always -v data postgr
MongoDB 插入操作机制详解之insert() 与 nInserted 的行为剖析(推荐)
概述 和MongoDB打交道,插入文档算是最家常便饭的操作了。但越是基础的动作,背后的细节往往越容易让人犯嘀咕。比如说,批量操作的时候,返回的结果到底该怎么看?那些看似简单的数字,你真的理解它的含义吗? 今天,我们就从一个常被讨论的Shell脚本片段入手,把insert()这个方法从里到外聊个明白。
- 日榜
- 周榜
- 月榜
1
2
3
4
5
6
7
8
9
10
相关攻略
2015-03-10 11:25
2015-03-10 11:05
2021-08-04 13:30
2015-03-10 11:22
2015-03-10 12:39
2022-05-16 18:57
2025-05-23 13:43
2025-05-23 14:01
热门教程
- 游戏攻略
- 安卓教程
- 苹果教程
- 电脑教程
热门话题

