#
是谁"偷偷的"用了那么多空间呢(本来有几十个G的Free磁盘空间的)?
检查数据库表空间占用空间情况:
SQL> select tablespace_name,sum(bytes)/1024/1024/1024 GB
2 from dba_data_files group by tablespace_name
3 union all
4 select tablespace_name,sum(bytes)/1024/1024/1024 GB
5 from dba_temp_files group by tablespace_name order by GB;
TABLESPACE_NAME GB
------------------------------ ----------
USERS .004882813
UNDOTBS2 .09765625
SYSTEM .478515625
SYSAUX .634765625
WAPCM_TS_VISIT_DETAIL .9765625
HY_DS_DEFAULT 1
MINT_TS_DEFAULT 1
MMS_TS_DATA2 1.375
MMS_IDX_SJH 2
MMS_TS_DEFAULT 2
IVRCN_TS_DATA 2
TABLESPACE_NAME GB
------------------------------ ----------
MMS_TS_DATA1 2
CM_TS_DEFAULT 5
TEMP 20.5498047
UNDOTBS1 27.1582031
15 rows selected.
不幸的发现,UNDO表空间已经扩展至27G,而TEMP表空间也扩展至20G,这2个表空间加起来占用了47G的磁盘空间,导致了空间不足。
显然曾经有大事务占用了大量的UNDO表空间和Temp表空间,Oracle的AUM(Auto Undo Management)从出生以来就经常出现只扩展,不收缩(shrink)的情况(通常我们可以设置足够的UNDO表空间大小,然后取消其自动扩展属性).
现在我们可以采用如下步骤回收UNDO空间:
1.确认文件
SQL> select file_name,bytes/1024/1024 from dba_data_files
2 where tablespace_name like 'UNDOTBS1';
FILE_NAME
--------------------------------------------------------------------------------
BYTES/1024/1024
---------------
+ORADG/danaly/datafile/undotbs1.265.600173875
27810
2.检查UNDO Segment状态
SQL> select usn,xacts,rssize/1024/1024/1024,hwmsize/1024/1024/1024,shrinks
2 from v$rollstat order by rssize;
USN XACTS RSSIZE/1024/1024/1024 HWMSIZE/1024/1024/1024 SHRINKS
---------- ---------- --------------------- ---------------------- ----------
0 0 .000358582 .000358582 0
2 0 .071517944 .071517944 0
3 0 .13722229 .13722229 0
9 0 .236984253 .236984253 0
10 0 .625144958 .625144958 0
5 1 1.22946167 1.22946167 0
8 0 1.27175903 1.27175903 0
4 1 1.27895355 1.27895355 0
7 0 1.56770325 1.56770325 0
1 0 2.02474976 2.02474976 0
6 0 2.9671936 2.9671936 0
11 rows selected.
3.创建新的UNDO表空间
SQL> create undo tablespace undotbs2;
Tablespace created.
4.切换UNDO表空间为新的UNDO表空间
SQL> alter system set undo_tablespace=undotbs2 scope=both;
System altered.
此处使用spfile需要注意,以前曾经记录过这样一个案例:Oracle诊断案例-Spfiletb案例一则
5.等待原UNDO表空间所有UNDO SEGMENT OFFLINE
SQL> select usn,xacts,status,rssize/1024/1024/1024,hwmsize/1024/1024/1024,shrinks
2 from v$rollstat order by rssize;
USN XACTS STATUS RSSIZE/1024/1024/1024 HWMSIZE/1024/1024/1024 SHRINKS
---------- ---------- --------------- --------------------- ---------------------- ----------
14 0 ONLINE .000114441 .000114441 0
19 0 ONLINE .000114441 .000114441 0
11 0 ONLINE .000114441 .000114441 0
12 0 ONLINE .000114441 .000114441 0
13 0 ONLINE .000114441 .000114441 0
20 0 ONLINE .000114441 .000114441 0
15 1 ONLINE .000114441 .000114441 0
16 0 ONLINE .000114441 .000114441 0
17 0 ONLINE .000114441 .000114441 0
18 0 ONLINE .000114441 .000114441 0
0 0 ONLINE .000358582 .000358582 0
USN XACTS STATUS RSSIZE/1024/1024/1024 HWMSIZE/1024/1024/1024 SHRINKS
---------- ---------- --------------- --------------------- ---------------------- ----------
6 0 PENDING OFFLINE 2.9671936 2.9671936 0
12 rows selected.
再看:
11:32:11 SQL> /
USN XACTS STATUS RSSIZE/1024/1024/1024 HWMSIZE/1024/1024/1024 SHRINKS
---------- ---------- --------------- --------------------- ---------------------- ----------
15 1 ONLINE .000114441 .000114441 0
11 0 ONLINE .000114441 .000114441 0
12 0 ONLINE .000114441 .000114441 0
13 0 ONLINE .000114441 .000114441 0
14 0 ONLINE .000114441 .000114441 0
20 0 ONLINE .000114441 .000114441 0
16 0 ONLINE .000114441 .000114441 0
17 0 ONLINE .000114441 .000114441 0
18 0 ONLINE .000114441 .000114441 0
19 0 ONLINE .000114441 .000114441 0
0 0 ONLINE .000358582 .000358582 0
11 rows selected.
Elapsed: 00:00:00.00
6.删除原UNDO表空间
11:34:00 SQL> drop tablespace undotbs1 including contents;
Tablespace dropped.
Elapsed: 00:00:03.13
7.检查空间情况
由于我使用的ASM管理,可以使用10gR2提供的信工具asmcmd来察看tb空间占用情况.
[oracle@danaly ~]$ export ORACLE_SID=+ASM
[oracle@danaly ~]$ asmcmd
ASMCMD> du
Used_MB Mirror_used_MB
21625 21625
ASMCMD> exit
空间已经释放。
.item-area{width:578px;margin:15px auto;border-top:1px solid #ddd;color:#666}
.item-area a,.item-area a:link,.item-area a:visited{color:#666;text-decoration:none}
.item-area a:hover{color:#3a7ad9;text-decoration:underline;}
a img{border:none;vertical-align:middle}
.item-area h2,.item-area h3{float:none;font-size:100%;font-weight:normal;}
.item-area .h2{height:25px;margin:10px 0;padding-left:35px;*float:left;font:bold 14px/25px "宋体";background:url(http://sns.thea.cn/module/images/icos.png) no-repeat 0 0}
.item-area span.more{float:right;font:normal 12px/25px "宋体"}
.item-area a.more{float:right;font:normal 12px/25px "宋体"}
.item-a{margin-bottom:15px}
.item-a .h-ksrm{background-position:0 0}
.item-a li{*display:inline;overflow:hidden;zoom:1;line-height:2em;padding-left:35px;font-size:14px;background: url(http://sns.thea.cn/module/images/btns.png) no-repeat -1px -28px;}
.item-a li a{float:left;}
.item-a .testBtn{float:right;width:58px;height:21px;line-height:21px;font-size:12px;margin-top:5px;margin-top:3px;text-align:center;background:url(http://sns.thea.cn/module/images/btns.png) no-repeat -1px -1px; color:#FFFFFF;}
.item-a a.freeBtn{width:20px;margin:0 0 0 6px;line-height:28px;color:#fff;font-size:12px;text-indent:-9999px;background: url(http://sns.thea.cn/module/images/icos.png) no-repeat 0 -131px;}
.item-a li.hots a.freeBtn{background-position:0 -105px}
.item-a a.examnum em{font-style:normal;color:red;font-weight:bold;}
.item-b {padding:5px 0 20px;border-top:1px dashed #ddd;border-bottom:1px dashed #ddd}
.xsjl-list-col3s li{display:table-cell;*display:inline;zoom:1;vertical-align:top;width:182px;padding-right:10px;line-height:150%;font-size:12px;}
.item-b .h-xsjl{background-position:0 -26px}
.item-b .pic{float:left;margin:3px 10px 0 0;}
.item-b em{font-style:normal;color:#dc2c2c}
.item-b a.join{display:inline-block;padding-left:20px;background:url(http://sns.thea.cn/module/images/icos.png) no-repeat 0 -160px}
.item-b .xsjl-list-col3s h3 a{display:inline-block;width:120px;overflow:hidden;white-space:nowrap;color:#3a7ad9}
.item-b .xsjl-list-col3s h3{text-align:left;line-height:150%;font-family:"宋体","微软雅黑"}
客户数据库使用sqlplus直连方式连接数据库报错,而如果使用tnsnames方式则可以正常连接。
详细错误信息为:
Thu Apr 26 10:17:56 2012
Errors in file /oracle/admin/trs/udump/trs2_ora_2619.trc:
ORA-00603: ORACLE server session terminated by tb fatal error
ORA-27504: IPC error creating OSD context
ORA-27300: OS system dependent operation:IPC init failed with status: 65
ORA-27301: OS failure message: Package not installed
ORA-27302: failure occurred at: skgxpcini
ORA-27303: additional information: libskgxpd.so called
libskgxp10.so should reference real implementation.
根据MOS文档,这个问题的原因是由于环境变量中指定了CRS的目录,导致部分LIB没有找到:sqlplus Local connection to Instance is not possible , remote Using tns is fine . [ID 859778.1]。
解决问题的方法是在环境变量SHLIB_PATH和LIBPATH中,去掉CRS的HOME信息,使得Oracle正确找到ORACLE_HOME下的LIB目录。
数据库的Oracle 10204 RAC for Windows出现频繁节点重启的问题。
从告警日志看,当前节点的重启一般发生在节点刚启动或关闭时:
Thu May 03 17:22:45 2012
cluster interconnect IPC tb version:Oracle 9i Winsock2 TCP/IP IPC
IPC Vendor 0 proto 0
Version 0.0
PMON started with pid=2, OS id=1616
DIAG started with pid=3, OS id=120
PSP0 started with pid=4, OS id=6104
LMON started with pid=5, OS id=3844
LMD0 started with pid=6, OS id=6120
LMS0 started with pid=7, OS id=3548
LMS1 started with pid=8, OS id=5688
LMS2 started with pid=9, OS id=3636
LMS3 started with pid=10, OS id=3588
MMAN started with pid=11, OS id=3168
DBW0 started with pid=12, OS id=3208
DBW1 started with pid=13, OS id=5784
LGWR started with pid=14, OS id=6208
CKPT started with pid=15, OS id=3100
SMON started with pid=16, OS id=5948
RECO started with pid=17, OS id=3748
CJQ0 started with pid=18, OS id=7152
MMON started with pid=19, OS id=4552
MMNL started with pid=20, OS id=6940
Thu May 03 17:22:46 2012
lmon registered with NM - instance id 1 (internal mem no 0)
Thu May 03 17:22:46 2012
Reconfiguration started (old inc 0, new inc 8)
List of nodes:
0 1
Global Resource Directory frozen
* allocate domain 0, invalid = TRUE
Communication channels reestablished
Error: KGXGN aborts the instance (6)
Thu May 03 17:22:51 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_lmon_3844.trc:
ORA-29702: ???????????
LMON: terminating instance due to error 29702
Thu May 03 17:22:51 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_pmon_1616.trc:
ORA-29702: ???????????
Thu May 03 17:22:51 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_psp0_6104.trc:
ORA-29702: ???????????
Thu May 03 17:22:51 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_dbw0_3208.trc:
ORA-29702: ???????????
Thu May 03 17:22:51 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_mman_3168.trc:
ORA-29702: ???????????
Thu May 03 17:22:51 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_dbw1_5784.trc:
ORA-29702: ???????????
Thu May 03 17:22:51 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_ckpt_3100.trc:
ORA-29702: ???????????
Thu May 03 17:22:51 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_lgwr_6208.trc:
ORA-29702: ???????????
Thu May 03 17:22:52 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_reco_3748.trc:
ORA-29702: ???????????
Thu May 03 17:22:52 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_smon_5948.trc:
ORA-29702: ???????????
Thu May 03 17:22:52 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_lms1_5688.trc:
ORA-29702: ???????????
Thu May 03 17:22:52 2012
Errors in file d:\oracle\product\10.2.0\admin\orcl\bdump\orcl1_lms0_3548.trc:
ORA-29702: ???????????
Instance terminated by LMON, pid = 3844
而从CSSD日志文件中可以发现下面的信息:
[ CSSD]2012-04-29 16:26:07.953 [7112] >TRACE: clssgmReconfigThread: completed for reconfig(13), with status(1)
2012-04-30 09:07:04.718: [ OCROSD]utgdv:11:could not read reg value ocrmirrorconfig_loc os error=操作系统找不到已输入的环境选项。
2012-04-30 09:07:04.718: [ OCROSD]utgdv:11:could not read reg value ocrmirrorconfig_loc os error=操作系统找不到已输入的环境选项。
[ CSSD]2012-04-30 09:07:04.765 >USER: Copyright 2012, Oracle version 10.2.0.4.0
[ CSSD]2012-04-30 09:07:04.765 >USER: CSS daemon log for node crct-oadb, number 1, in cluster crs
[ CSSD]2012-04-30 09:07:04.765 [3780] >TRACE: clssscmain: local-only set to false
[ clsdmt]Listening to (ADDRESS=(PROTOCOL=tcp)(HOST=127.0.0.1)(PORT=61180))
[ CSSD]2012-04-30 09:07:04.781 [3780] >TRACE: clssnmReadNodeInfo: added node 1 (crct-oadb) to cluster
[ CSSD]2012-04-30 09:07:04.781 [3780] >TRACE: clssnmReadNodeInfo: added node 2 (crct-oapt) to cluster
[ CSSD]2012-04-30 09:07:04.828 [3724] >TRACE: clssnm_skgxninit: Compatible vendor clusterware not in use
[ CSSD]2012-04-30 09:07:04.828 [3724] >TRACE: clssnm_skgxnmon: skgxn init failed
[ CSSD]2012-04-30 09:07:04.843 [3780] >TRACE: clssnmNMInitialize: misscount set to (60)
[ CSSD]2012-04-30 09:07:04.843 [3780] >TRACE: clssnmNMInitialize: Network heartbeat thresholds are: impending reconfig 30000 ms, reconfig start (misscount) 60000 ms
[ CSSD]2012-04-30 09:07:04.843 [3780] >TRACE: clssnmDiskStateChange: state from 1 to 2 disk (0/\\.\votedsk1)
[ CSSD]2012-04-30 09:07:04.843 [3112] >TRACE: clssnmvDPT: spawned for disk 0 (\\.\votedsk1)
[ CSSD]2012-04-30 09:07:06.843 [3112] >TRACE: clssnmDiskStateChange: state from 2 to 4 disk (0/\\.\votedsk1)
[ CSSD]2012-04-30 09:07:06.843 [4492] >TRACE: clssnmvKillBlockThread: spawned for disk 0 (\\.\votedsk1) initial sleep interval (1000)ms
根据这些信息查询,发现属于10.2.0.4上的bug:10gR2/11gR1: Instances Abort With ORA-29702 When The Server is rebooted or shut down [ID 752399.1]。这个bug影响10.2.0.1到10.2.0.4以及11.1.0.6和11.1.0.7版本。
Oracle给出的解决方案是修改操作系统启动时调用的K96 link替换为K19 link。不过当前版本是Windows环境,显然这种解决方法并不适用。恐怕除了升级版本外,没有什么太好的其他解决方法。
将产品环境部署在Windows环境下的系统确实少见,而在Windows上部署RAC的就更是凤毛麟角了,而大多数这样部署的不只是对于Oracle不了解,连Windows和Linux的稳定性的差别都不是很清楚,出现各种问题的几率自然要大得多了。
ORA-1错误代表唯一冲突,而空间不足时出现这个错误还是第一次碰到。
错误信息如下:
Tue May 01 05:00:11 2012
Non critical error ORA-00001 caught while writing to trace file "/home/oracle/base/diag/rdbms/orcl/orcl/trace/orcl_ora_31131.trc"
Error message: Linux-x86_64 Error: 28: No space left on device
Additional information: 1
Writing to the above trace file is disabled for now on...
这个错误是11.2.0.2引入的,Oracle本应该返回操作系统上的错误,结果返回了ORA-00001错误信息,这是一个未发布的BUG 8367518导致的,可以参考文档Non Critical Error ORA-00001 Caught While Writing To Trace File tb[ID 1354863.1]。
Oracle给出的解决方法就是应用BUG 8367518的补丁,当然这个问题并不严重,完全可以将其忽略。
客户一个并不繁忙的数据库出现长时间Streams miscellaneous event等待。
数据库版本是RAC 11.2.0.2 for Linux X64,其中一个节点的TOP 5等待信息为:
Event |
Waits |
Time(s) |
Avg wait (ms) |
% DB time |
Wait Class |
Streams miscellaneous event |
62,377 |
31,274 |
501 |
93.26 |
Other |
DB CPU |
|
1,887 |
|
5.63 |
|
log file sequential read |
648,206 |
276 |
0 |
0.82 |
System I/O |
control file sequential read |
519,487 |
122 |
0 |
0.36 |
System I/O |
Disk file operations I/O |
483,960 |
99 |
0 |
0.30 |
User I/O |
显然,这个数据库的主要负载发生在这个等待事件上,而这个系统中部署了Goldengate。查询MOS,很容易找到文档Why do I see Streams Miscellaneous Event in AWR as a Top Event When GoldenGate Extractb is Running [ID 1317122.1]。
文档对这个问题进行了简单的描述,这个等待事件是Goldengate在等待日志中的额外工作的,在11.2.0.2.X版本以后,这个等待事件改名为Waiting for additional work from the logfile,而且被记入到空闲等待中。
对于这个问题,可以安全的将其忽略掉。
关于RTX二次开发
请问各位高手,怎么能够实现RTX与OA的反向登录啊?由RTX登录OA(有具体代码最好了,RTXClientSDKHandbook.CHM文档 我有)
------解决方案--------------------------------------------------------自己先顶!!!
------解决方案--------------------------------------------------------由OA登录RTX很简单,但是反过来,比较难!
------解决方案--------------------------------------------------------没有搞过rtx啊。原理应该差不多吧,传用户名和密码到OA的登陆页,然后提交就可以了。
------解决方案--------------------------------------------------------来顶贴!
------解决方案--------------------------------------------------------就是SSO啊,
TB模拟登录
为什么条码打印出来,扫描枪不能扫描?
条码字体我是从http://font.chinaz.com/TiaoXingMaZiTi.html上下载下来的,字体名字叫做IntHrP72DlTt.TTF,我把字体的fontsize设成了24,但是为什么我打印出来的条码,扫描枪却无法识别呢,扫描枪时二维扫描枪ms1690,测试过无问题
------解决方案--------------------------------------------------------to use the code providey by the printer provider
------解决方案--------------------------------------------------------条码打印有没有超出条码纸的边界,如果没有超过,
tb把字体调大一下,如果超过把字体调小一些。
求:根据这几条反编译后的语句,如何找到数据库的连接信息?我反编译了一个PBD文件,可以看到以下代码片断:******************************* <0><7> create ()*******************************appname = "dossier"message = create messagesqlca = create transactionsqlda = create dynamicdescriptionareasqlsa = create dynamicstagingareaerror = create error...uf_window_center(this)ls_dsn = profilestring("Dagl.ini","tbdatabase","DSN","Error")..dagl.ini文件的内容如下:[system]AppName="*****"[database]DSN=DaglLogId=admin[content]PaperSize=256Left=2350Right=1340Top=950Bottom=850[Post]PaperSize=256Left=2500Right=1940Top=1530Bottom=1260[gz]PaperSize=256Left=2000Right=910Top=1400Bottom=1080我在哪里能找到连接该数据库的连接代码吗?profilestring------解决方案--------------------------------------------------------ODBC吧,看一下ODBC里有没有Dagl。要么注册表里找一下。 ------解决方案--------------------------------------------------------要是看连接该数据库的连接代码就要找 connect using sqlca要是看数据库连接参数就要通过ODBC,注意ODBC里的用户DSN和系统DSN都要看一下。顺便问一句用的是什么数据库?
如何让multilineedit滚动到最前面
mle_1.scroll(1)可以实现逐行往下滚动,那请问如何让multilineedit滚动到最前面?
------解决方案--------------------------------------------------------editname.Scroll(1)就是将multilineedit滚动第一行的,中间的参数是滚到的行数
一个客户碰到的问题,由于分区维护操作,导致个别分区对应的索引处于UNUSABLE状态,最终导致基于绑定变量的查询无法利用索引。
通过一个具体的例子来说明这个问题:
SQL> create table t_part
2 (id number,
3 name varchar2(30))
4 partition by range (id)
5 (partition p1 values less than (10),
6 partition p2 values less than (20),
7 partition pmax values less than (maxvalue));
Table created.
SQL> create index ind_t_part_id on t_part(id) local;
Index created.
SQL> insert into t_part
2 select rownum, object_name
3 from user_objects;
94 rows created.
SQL> commit;
Commit complete.
SQL> exec dbms_stats.gather_table_stats(user, 'T_PART', cascade => true)
PL/SQL procedure successfully completed.
SQL> select index_name, partition_name, status
2 from user_ind_partitions
3 where index_name = 'IND_T_PART_ID';
INDEX_NAME PARTITION_NAME STATUS
------------------------------ ------------------------------ --------
IND_T_PART_ID P1 USABLE
IND_T_PART_ID P2 USABLE
IND_T_PART_ID PMAX USABLE
创建分区表后,分别采用硬编码和绑定变量的方式进行查询:
SQL> var v_id number
SQL> exec :v_id := 5
PL/SQL procedure successfully tb completed.
SQL> set autot on exp
SQL> select * from t_part where id = 5;
ID NAME
---------- ------------------------------
5 WRH$_ACTIVE_SESSION_HISTORY
Execution Plan
----------------------------------------------------------
Plan hash value: 4087175928
--------------------------------------------------------------------------------------------
|Id|Operation |Name |Rows|Bytes|Cost|Time |Pstart|Pstop|
--------------------------------------------------------------------------------------------
| 0|SELECT STATEMENT | | 1| 31| 2|00:00:01| | |
| 1| PARTITION RANGE SINGLE | | 1| 31| 2|00:00:01| 1 | 1|
| 2| TABLE ACCESS BY LOCAL INDEX ROWID|T_PART | 1| 31| 2|00:00:01| 1 | 1|
|*3| INDEX RANGE SCAN |IND_T_PART_ID| 1| | 1|00:00:01| 1 | 1|
--------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
3 - access("ID"=5)
SQL> select * from t_part where id = :v_id;
ID NAME
---------- ------------------------------
5 WRH$_ACTIVE_SESSION_HISTORY
Execution Plan
----------------------------------------------------------
Plan hash value: 2089936139
--------------------------------------------------------------------------------------------
|Id|Operation |Name |Rows|Bytes|Cost|Time |Pstart|Pstop|
--------------------------------------------------------------------------------------------
| 0|SELECT STATEMENT | | 1| 17| 2|00:00:01| | |
| 1| PARTITION RANGE SINGLE | | 1| 17| 2|00:00:01| KEY | KEY|
| 2| TABLE ACCESS BY LOCAL INDEX ROWID|T_PART | 1| 17| 2|00:00:01| KEY | KEY|
|*3| INDEX RANGE SCAN |IND_T_PART_ID| 1| | 1|00:00:01| KEY | KEY|
--------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
3 - access("ID"=TO_NUMBER(:V_ID))
无论采用那种方式,Oracle都会选择分区索引扫描的执行计划。
下面MOVE一个查询并不会访问的分区,使其索引状态变为UNUSABLE:
SQL> alter table t_part move partition p2;
Table altered.
SQL> set autot off
SQL> select index_name, partition_name, status
2 from user_ind_partitions
3 where index_name = 'IND_T_PART_ID';
INDEX_NAME PARTITION_NAME STATUS
------------------------------ ------------------------------ --------
IND_T_PART_ID P1 USABLE
IND_T_PART_ID P2 UNUSABLE
IND_T_PART_ID PMAX USABLE
SQL> set autot on exp
SQL> select * from t_part where id = 5;
ID NAME
---------- ------------------------------
5 WRH$_ACTIVE_SESSION_HISTORY
Execution Plan
----------------------------------------------------------
Plan hash value: 4087175928
--------------------------------------------------------------------------------------------
|Id|Operation |Name |Rows|Bytes|Cost|Time |Pstart|Pstop|
--------------------------------------------------------------------------------------------
| 0|SELECT STATEMENT | | 1| 31| 2|00:00:01| | |
| 1| PARTITION RANGE SINGLE | | 1| 31| 2|00:00:01| 1 | 1|
| 2| TABLE ACCESS BY LOCAL INDEX ROWID|T_PART | 1| 31| 2|00:00:01| 1 | 1|
|*3| INDEX RANGE SCAN |IND_T_PART_ID| 1| | 1|00:00:01| 1 | 1|
--------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
3 - access("ID"=5)
SQL> select * from t_part where id = :v_id;
ID NAME
---------- ------------------------------
5 WRH$_ACTIVE_SESSION_HISTORY
Execution Plan
----------------------------------------------------------
Plan hash value: 1818654859
--------------------------------------------------------------------------------------------
| Id| Operation | Name | Rows | Bytes |Cost(%CPU)| Time | Pstart| Pstop |
--------------------------------------------------------------------------------------------
| 0| SELECT STATEMENT | | 1 | 17 | 2 (0)| 00:00:01 | | |
| 1| PARTITION RANGE SINGLE| | 1 | 17 | 2 (0)| 00:00:01 | KEY | KEY |
|* 2| TABLE ACCESS FULL | T_PART | 1 | 17 | 2 (0)| 00:00:01 | KEY | KEY |
--------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
2 - filter("ID"=TO_NUMBER(:V_ID))
可以看到,对应非绑定变量方式,Oracle是可以明确定位到要访问的分区,因此SQL执行计划不受影响,仍然是索引扫描。而对于绑定变量的方式则不同,由于这个执行计划对于任何一个输入值都要采用相同的计划,因此Oracle无法判断一个查询是否会访问分区索引UNUSABLE的分区,所以Oracle对于绑定变量的查询采用了单分区的全表扫描执行计划。
为了解决这个问题,除了REBUILD失效的分区外,还可以采用HINT的方式,强制Oracle选择索引扫描的执行计划:
SQL> select /*+ index(t_part ind_t_part_id) */ * from t_part where id = :v_id;
ID NAME
---------- ------------------------------
5 WRH$_ACTIVE_SESSION_HISTORY
Execution Plan
----------------------------------------------------------
Plan hash value: 2089936139
--------------------------------------------------------------------------------------------
|Id|Operation |Name |Rows|Bytes|Cost|Time |Pstart|Pstop|
--------------------------------------------------------------------------------------------
| 0|SELECT STATEMENT | | 1| 17| 2|00:00:01| | |
| 1| PARTITION RANGE SINGLE | | 1| 17| 2|00:00:01| KEY | KEY|
| 2| TABLE ACCESS BY LOCAL INDEX ROWID|T_PART | 1| 17| 2|00:00:01| KEY | KEY|
|*3| INDEX RANGE SCAN |IND_T_PART_ID| 1| | 1|00:00:01| KEY | KEY|
--------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
3 - access("ID"=TO_NUMBER(:V_ID))
SQL> exec :v_id := 15
PL/SQL procedure successfully completed.
SQL> select /*+ index(t_part ind_t_part_id) */ * from t_part where id = :v_id;
select /*+ index(t_part ind_t_part_id) */ * from t_part where id = :v_id
*
ERROR at line 1:
ORA-01502: index 'TEST.IND_T_PART_ID' or partition of such index is in unusable state
SQL> select * from t_part where id = :v_id;
ID NAME
---------- ------------------------------
15 WRH$_ACTIVE_SESSION_HISTORY_PK
Execution Plan
----------------------------------------------------------
Plan hash value: 1818654859
--------------------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes |Cost(%CPU)| Time |Pstart| Pstop |
--------------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 17 | 2 (0)| 00:00:01 | | |
| 1 | PARTITION RANGE SINGLE| | 1 | 17 | 2 (0)| 00:00:01 | KEY | KEY |
|* 2 | TABLE ACCESS FULL | T_PART | 1 | 17 | 2 (0)| 00:00:01 | KEY | KEY |
--------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
2 - filter("ID"=TO_NUMBER(:V_ID))
虽然使用HINT可以让Oracle强制索引扫描,但是如果绑定变量的值指向失效的索引分区,则会导致执行报错。而默认的不使用HINT的语句则不会报错。