zoukankan      html  css  js  c++  java
  • 10046事件sql_trace跟踪

    查看 sql 执行计划的方法有许多种, 10046 事件就是其中的一种. 与其他查看 sql 执行计划不同, 当我们遇到比较复杂的 sql 语句, 我们可以通过 10046 跟踪 sql 得到执行计划中每一个步骤的逻辑读, 物理读以及花费的时间等. 这种细粒度的跟踪对于我们分析 sql 性能尤其有用.

    10046:SQL到底是如何执行的: 
    10046 = 设置sql_trace=true; 10046 可以跟踪到等待事件&绑定变量;   tkprof 只解读(格式化)10046的trace文件
    10053:SQL为什么要这样执行:
    将语句执行涉及到的与成本相关的信息展示出来; 有表的各个index的成本的罗列(index的访问成本),罗列访问表的成本,展示为何是这个执行计划,10053使用的很少的。

    10046事件:
    > 跟踪会话执行的SQL的情况
    > 跟踪会话中的SQL的执行计划及等待事件
    > 可以通过TKPROF,TRCA等工具格式化trc文件

    打开10046事件跟踪:
    alter session set events = '10046 trace name context forever,level 12';

    关闭10046事件跟踪:
    alter session set events '10046 trace name context off';

    dump 控制文件结构:
    alter session set events 'immediate trace name controlf level 12';


    dump 数据文件头:
    alter session set events 'immediate trace name file_hdrs level 12';

    10053事件:
    优化器输入、计算输出的协议,把决策过程日志写入跟踪文件,可以看出优化器的工作原理,选择最佳执行计划的原因。
    打开10053事件跟踪:
    alter session set events '10053 trace name context forever,level 1';
    获得跟踪文件的位置:
    SQL> oradebug setmypid
    SQL> oradebug tracefile_name
    关闭10053事件跟踪:
    alter session set events '10053 trace name context off';

    event 10053跟踪文件的内容:
    > 优化语句相关表的查询块和对象标识符
    > 考虑到的查询转换
    > 缩写名称的注释
    > 绑定变量的结果
    > 优化器考虑到的参数(显式和隐式)
    > 系统统计信息
    > 表和索引的对象统计信息
    > 单表访问路径和成本
    > 执行计划
    > 谓语信息
    > 查询块的outline信息

    一般来说, 使用 10046 事件得到 sql 执行计划的步骤如下:
    1. 激活当前 session 10046 事件
    2. 在当前 session 中执行 sql 语句
    3. 关闭当前 session 10046 事件

    执行完上述步骤后, 通常会自动生成一个 trace 文件. 在 oracle 11g 中, trace 文件一般放在$ORACLE_BASE/diag/rdbms/{database_name}/$ORACLE_SID/trace 目录下. 如果使用 oradebug 激活跟踪 10046后, 可以使用 oradebug tracefile_name 得到刚刚生成的 trace 文件的完整路径.

    1. NAME                                 TYPE        VALUE  
    2. ------------------------------------ ----------- ------------------------------  
    3. background_dump_dest                 string      g:appdavidddiag dbmsdavid  
    4.                                                  david race  


    刚刚提到的 oradebug 激活跟踪 10046 事件, 我想大部分 dba 都会使用. oradebug 是个功能强大非常好用的工具, 使用 oradebug help 将会看到它的功能很多

    1. SQL> oradebug help  

    使用 oradebug 跟踪 10046 命令如下:

    1. SQL> oradebug setmypid  
    2. Statement processed.  
    3.   
    4. // 激活 10046 事件  
    5. SQL> oradebug event 10046 trace name context forever,level 12;  
    6. Statement processed.  
    7.   
    8. SQL> select /*+ leading(t3) use_merge(t4) */ *  
    9.   2  from t3, t4  
    10.   3  where t3.id = t4.t3_id and t3.n = 1100;  
    11.   
    12. 10 rows selected.  
    13.   
    14. // 在当前 session 关闭 10046 事件  
    15. SQL> oradebug event 10046 trace name context off;  
    16. Statement processed.  
    17.   
    18. // 使用 oradebug tracefile_name 可以直接看到生成的 trace 文件的位置  
    19. SQL> oradebug tracefile_name;  
    20. g:appdavidddiag dbmsdaviddavid racedavid_ora_2176.trc  


    其中, 10046 按照收集信息的内容分为以下等级:

     Level 0  停用SQL跟踪,相当于SQL_TRACE=FALSE
     Level 1  标准SQL跟踪,相当于SQL_TRACE=TRUE
     Level 4  在level 1的基础上增加绑定变量的信息
     Level 8  在level 1的基础上增加等待事件的信息
     Level 12  在level 1的基础上增加绑定变量和等待事件的信息

    分析读懂 trace 文件

    现在我们打开 g:appdavidddiag dbmsdaviddavid racedavid_ora_2176.trc 看看生成的 trace 文件的内容

    1. <pre name="code" class="sql"><pre name="code" class="sql"><pre name="code" class="sql"><pre name="code" class="sql" style="font-size:14px;">PARSING IN CURSOR #22 len=92 dep=0 uid=0 oct=3 lid=0 tim=900460923321 hv=1624778336 ad='34671d90' sqlid='g0rdyg9hdh9m0'  
    2. select /*+ leading(t3) use_merge(t4) */ *  
    3. from t3, t4  
    4. where t3.id = t4.t3_id and t3.n = 1100  
    5. END OF STMT  
    6. PARSE #22:c=0,e=10777,p=0,cr=0,cu=0,mis=1,r=0,dep=0,og=1,plh=3831111046,tim=900460923319  
    7. EXEC #22:c=0,e=29,p=0,cr=0,cu=0,mis=0,r=0,dep=0,og=1,plh=3831111046,tim=900460923482  
    8. WAIT #22: nam='SQL*Net message to client' ela= 2 driver id=1111838976 #bytes=1 p3=0 obj#=-1 tim=900460923512  
    9. FETCH #22:c=15625,e=23922,p=0,cr=119,cu=0,mis=0,r=1,dep=0,og=1,plh=3831111046,tim=900460947462  
    10. WAIT #22: nam='SQL*Net message from client' ela= 221 driver id=1111838976 #bytes=1 p3=0 obj#=-1 tim=900460947755  
    11. WAIT #22: nam='SQL*Net message to client' ela= 2 driver id=1111838976 #bytes=1 p3=0 obj#=-1 tim=900460947803  
    12. FETCH #22:c=0,e=71,p=0,cr=0,cu=0,mis=0,r=9,dep=0,og=1,plh=3831111046,tim=900460947864  
    13. STAT #22 id=1 cnt=10 pid=0 pos=1 obj=0 op='MERGE JOIN  (cr=119 pr=0 pw=0 time=28 us cost=193 size=1280 card=10)'  
    14. STAT #22 id=2 cnt=1 pid=1 pos=1 obj=0 op='SORT JOIN (cr=15 pr=0 pw=0 time=0 us cost=6 size=63 card=1)'  
    15. STAT #22 id=3 cnt=1 pid=2 pos=1 obj=83550 op='TABLE ACCESS FULL T3 (cr=15 pr=0 pw=0 time=0 us cost=5 size=63 card=1)'  
    16. STAT #22 id=4 cnt=10 pid=1 pos=2 obj=0 op='SORT JOIN (cr=104 pr=0 pw=0 time=11 us cost=187 size=650000 card=10000)'  
    17. STAT #22 id=5 cnt=10000 pid=4 pos=1 obj=83552 op='TABLE ACCESS FULL T4 (cr=104 pr=0 pw=0 time=8603 us cost=29 size=650000 card=10000)'  

    从上面的 trace 文件我们可以看出 sql 语句经过了 parse(解析) -> exec(执行) -> fetch(从游标中获取数据) 几个过程, 其中第一句说明了当前跟踪执行的 sql 语句的概况,比如使用游标号, sql 语句的长度, 递归深度等等基本信息:

    1. PARSING IN CURSOR #22 len=92 dep=0 uid=0 oct=3 lid=0 tim=900460923321 hv=1624778336 ad='34671d90' sqlid='g0rdyg9hdh9m0'  
     cursor  cursor number
     len  sql 语句长度
     dep  sql 语句递归深度
     uid  user id
     oct  oracle command type
     lid  privilege user id
     tim  timestamp,时间戳
     hv  hash id
     ad  sql address 地址, 用在 v$sqltext
     sqlid  sql id

    接着, 下面的语句说明了 sql 语句具体的执行过程以及每一个步骤消耗 CPU 的时间等性能指标

    1. PARSE #22:c=0,e=10777,p=0,cr=0,cu=0,mis=1,r=0,dep=0,og=1,plh=3831111046,tim=900460923319  
    2. EXEC #22:c=0,e=29,p=0,cr=0,cu=0,mis=0,r=0,dep=0,og=1,plh=3831111046,tim=900460923482  
    3. FETCH #22:c=15625,e=23922,p=0,cr=119,cu=0,mis=0,r=1,dep=0,og=1,plh=3831111046,tim=900460947462  
     c  CPU 消耗的时间
     e  Elapsed time 
     p  number of physical reads 物理读的次数
     cr  number of buffers retrieved for CR reads   逻辑读的数据块
     cu  number of buffers retrieved in current mode (current 模式读取的数据块)
     mis  cursor missed in the cache 库缓存中丢失的游标, 硬解析次数
     r  number of rows processed 处理的行数
     dep  递归深度
     og  optimizer mode 【1:all_rows, 2:first_rows, 3:rule, 4:choose】
     plh  plan hash value
     tim  timestamp 时间戳

    以及执行过程中的发生的等待事件

    1. WAIT #22: nam='SQL*Net message to client' ela= 2 driver id=1111838976 #bytes=1 p3=0 obj#=-1 tim=900460923512  
     nam  an event that we waited for 等待事件
     ela  此操作消耗的时间
     p3  block 块号
     trm  timestamp 时间戳

    最后显示的是该游标的执行计划

    1. STAT #22 id=1 cnt=10 pid=0 pos=1 obj=0 op='MERGE JOIN  (cr=119 pr=0 pw=0 time=28 us cost=193 size=1280 card=10)'  
    2. STAT #22 id=2 cnt=1 pid=1 pos=1 obj=0 op='SORT JOIN (cr=15 pr=0 pw=0 time=0 us cost=6 size=63 card=1)'  
    3. STAT #22 id=3 cnt=1 pid=2 pos=1 obj=83550 op='TABLE ACCESS FULL T3 (cr=15 pr=0 pw=0 time=0 us cost=5 size=63 card=1)'  
    4. STAT #22 id=4 cnt=10 pid=1 pos=2 obj=0 op='SORT JOIN (cr=104 pr=0 pw=0 time=11 us cost=187 size=650000 card=10000)'  
    5. STAT #22 id=5 cnt=10000 pid=4 pos=1 obj=83552 op='TABLE ACCESS FULL T4 (cr=104 pr=0 pw=0 time=8603 us cost=29 size=650000 card=10000  
     cnt  当前行源返回的行数
     pid  parent id of this row source 当前行源的父结点 id
     pos  position in explain plan 执行计划的位置
     obj  object id of row source (if this is a base object)
     op   the row source access operation

    例如, 执行步骤 merge join 消耗的逻辑读为 119, 物理读为 0, 耗费的时间为 28 us, 成本 cost 193,返回 10 条记录

    使用 tkprof 命令翻译 trace 文件

    我们也可以使用 tkprof 命令对 trace 文件进行翻译,得到一个容易理解的 trace 汇总报表文件

    1. C:Documents and Settingsdavidd> tkprof g:appdavidddiag dbmsdaviddavid racedavid_ora_2176.trc d: race.trc  
    2.   
    3. TKPROF: Release 11.2.0.1.0 - Development on Thu Dec 18 18:51:44 2014  
    4.   
    5. Copyright (c) 1982, 2009, Oracle and/or its affiliates.  All rights reserved.  


    tkprof 翻译的 trace 文件的汇总报表如下:

    1. Trace file: g:appdavidddiag dbmsdaviddavid racedavid_ora_2176.trc  
    2. Sort options: default  
    3.   
    4.   
    5. ********************************************************************************  
    6. count    = number of times OCI procedure was executed  
    7. cpu      = cpu time in seconds executing   
    8. elapsed  = elapsed time in seconds executing  
    9. disk     = number of physical reads of buffers from disk  
    10. query    = number of buffers gotten for consistent read  
    11. current  = number of buffers gotten in current mode (usually for update)  
    12. rows     = number of rows processed by the fetch or execute call  
    13. ********************************************************************************  
    14.   
    15.   
    16. select /*+ leading(t3) use_merge(t4) */ *  
    17. from t3, t4  
    18. where t3.id = t4.t3_id and t3.n = 1100  
    19.   
    20.   
    21. call     count       cpu    elapsed       disk      query    current        rows  
    22. ------- ------  -------- ---------- ---------- ---------- ----------  ----------  
    23. Parse        1      0.00       0.00          0          0          0           0  
    24. Execute      1      0.00       0.00          0          0          0           0  
    25. Fetch        2      0.00       0.00          0        119          0          10  
    26. ------- ------  -------- ---------- ---------- ---------- ----------  ----------  
    27. total        4      0.00       0.00          0        119          0          10  
    28.   
    29.   
    30. Misses in library cache during parse: 1  
    31. Optimizer mode: ALL_ROWS  
    32. Parsing user id: SYS  
    33.   
    34.   
    35. Rows     Row Source Operation  
    36. -------  ---------------------------------------------------  
    37.      10  MERGE JOIN  (cr=119 pr=0 pw=0 time=0 us cost=193 size=1280 card=10)  
    38.       1   SORT JOIN (cr=15 pr=0 pw=0 time=0 us cost=6 size=63 card=1)  
    39.       1    TABLE ACCESS FULL T3 (cr=15 pr=0 pw=0 time=0 us cost=5 size=63 card=1)  
    40.      10   SORT JOIN (cr=104 pr=0 pw=0 time=0 us cost=187 size=650000 card=10000)  
    41.   10000    TABLE ACCESS FULL T4 (cr=104 pr=0 pw=0 time=8733 us cost=29 size=650000 card=10000)  
    42.   
    43.   
    44.   
    45.   
    46. Elapsed times include waiting on following events:  
    47.   Event waited on                             Times   Max. Wait  Total Waited  
    48.   ----------------------------------------   Waited  ----------  ------------  
    49.   SQL*Net message to client                       2        0.00          0.00  
    50.   SQL*Net message from client                     2       20.23         20.23  
    51.   
    52.   
    53.   
    54.   
    55.   
    56.   
    57. ********************************************************************************  
    58.   
    59.   
    60. OVERALL TOTALS FOR ALL NON-RECURSIVE STATEMENTS  
    61.   
    62.   
    63. call     count       cpu    elapsed       disk      query    current        rows  
    64. ------- ------  -------- ---------- ---------- ---------- ----------  ----------  
    65. Parse        1      0.00       0.00          0          0          0           0  
    66. Execute      1      0.00       0.00          0          0          0           0  
    67. Fetch        2      0.00       0.00          0        119          0          10  
    68. ------- ------  -------- ---------- ---------- ---------- ----------  ----------  
    69. total        4      0.00       0.00          0        119          0          10  
    70.   
    71.   
    72. Misses in library cache during parse: 1  
    73.   
    74.   
    75. Elapsed times include waiting on following events:  
    76.   Event waited on                             Times   Max. Wait  Total Waited  
    77.   ----------------------------------------   Waited  ----------  ------------  
    78.   SQL*Net message to client                       3        0.00          0.00  
    79.   SQL*Net message from client                     3       20.23         30.20  
    80.   
    81.   
    82.   
    83.   
    84. OVERALL TOTALS FOR ALL RECURSIVE STATEMENTS  
    85.   
    86.   
    87. call     count       cpu    elapsed       disk      query    current        rows  
    88. ------- ------  -------- ---------- ---------- ---------- ----------  ----------  
    89. Parse        0      0.00       0.00          0          0          0           0  
    90. Execute      0      0.00       0.00          0          0          0           0  
    91. Fetch        0      0.00       0.00          0          0          0           0  
    92. ------- ------  -------- ---------- ---------- ---------- ----------  ----------  
    93. total        0      0.00       0.00          0          0          0           0  
    94.   
    95.   
    96. Misses in library cache during parse: 0  
    97.   
    98.   
    99.     1  user  SQL statements in session.  
    100.     0  internal SQL statements in session.  
    101.     1  SQL statements in session.  
    102. ********************************************************************************  
    103. Trace file: g:appdavidddiag dbmsdaviddavid racedavid_ora_2176.trc  
    104. Trace file compatibility: 11.1.0.7  
    105. Sort options: default  
    106.   
    107.   
    108.        1  session in tracefile.  
    109.        1  user  SQL statements in trace file.  
    110.        0  internal SQL statements in trace file.  
    111.        1  SQL statements in trace file.  
    112.        1  unique SQL statements in trace file.  
    113.      122  lines in trace file.  
    114.        0  elapsed seconds in trace file.  

    其中,Misses in library cache during parse :1   意思是解析的时候库缓存丢失游标,  也就是说发生了一次硬解析

    参考: http://www.eygle.com/archives/2005/10/aeearaw_traceia.html

           http://czmmiao.iteye.com/blog/1493765   tkprof 的使用

           http://czmmiao.iteye.com/blog/1493933   读懂trace

           

     

  • 相关阅读:
    jquery each() 方法跳出循环
    webpack 启动 vue
    HTML DOM insertBefore() 方法 问题
    浮动元素的高度怎么撑起
    jquery toggle 方法被废除的替代方法
    函数声明和函数表达式
    href与src 区别
    ThreadLocal用法
    《计算机网络》ISO/OSI参考模型分层协议
    解决Idea创建的maven Web项目无法连接mysql数据库
  • 原文地址:https://www.cnblogs.com/shengs/p/4959510.html
Copyright © 2011-2022 走看看