ITPub博客

首页 > Linux操作系统 > Linux操作系统 > ddl 导致分区表全局索引unusable

ddl 导致分区表全局索引unusable

原创 Linux操作系统 作者:shuangoracle 时间:2012-07-08 22:54:27 0 删除 编辑
上周五意外发现一个分区表的全局索引失效变为unusable,在监控SQL性能时有几个SQL因为这个索引而挂掉。
忽然想起是前一天进行测试时,对该表一个分区做了exchange交换分区操作。下面还原下场景:
create table test(id number,name varchar2(10))
partition by list(id)
(
 partition p1 values(1),
 partition p2 values(2),
 partition p3 values(3)
);
create index idx_test_id on test(id);--全局索引
create index idx_test_name on test(name) local;--本地索引
SQL> select table_name,index_name,status from user_indexes where table_name='TEST';
TABLE_NAME                     INDEX_NAME                     STATUS
------------------------------ ------------------------------ --------
TEST                           IDX_TEST_NAME                  N/A
TEST                           IDX_TEST_ID                    VALID
N/A表示是本地索引状态,VALID是全局索引状态。

1.交换分区(此时表中无数据)
SQL> create table t as select * from test;
表已创建。
SQL> alter table test exchange partition p1 with table t;
表已更改。
SQL> select table_name,index_name,status from user_indexes where table_name='TEST';
TABLE_NAME                     INDEX_NAME                     STATUS
------------------------------ ------------------------------ --------
TEST                           IDX_TEST_NAME                  N/A
TEST                           IDX_TEST_ID                    UNUSABLE
可以看到此时全局索引由valid变为unusable,本地索引状态没有变。

2.truncate分区
首先将全局索引重建:
alter index idx_test_id rebuild;
此时查看
SQL> select table_name,index_name,status from user_indexes where table_name='TEST';
TABLE_NAME                     INDEX_NAME                     STATUS
------------------------------ ------------------------------ --------
TEST                           IDX_TEST_NAME                  N/A
TEST                           IDX_TEST_ID                    VALID
直接truncate分区看看,
SQL> alter table test truncate partition p1;
表被截断。
SQL> select table_name,index_name,status from user_indexes where table_name='TEST';
TABLE_NAME                     INDEX_NAME                     STATUS
------------------------------ ------------------------------ --------
TEST                           IDX_TEST_NAME                  N/A
TEST                           IDX_TEST_ID                    VALID
直接truncate没有数据的分区p1,全局分区和本地分区索引状态都不变。
SQL> insert into test values(1,'a');
已创建 1 行。
SQL> alter table test truncate partition p1;
表被截断。
SQL> select table_name,index_name,status from user_indexes where table_name='TEST';
TABLE_NAME                     INDEX_NAME                     STATUS
------------------------------ ------------------------------ --------
TEST                           IDX_TEST_NAME                  N/A
TEST                           IDX_TEST_ID                    UNUSABLE
在p1分区插入数据后,再执行truncate分区,这时发现本地分区状态没有变,但是全局分区状态由valid变为unusable。

3.drop分区
首先将全局索引重建:alter index idx_test_id rebuild;
SQL> select table_name,index_name,status from user_indexes where table_name='TEST';
TABLE_NAME                     INDEX_NAME                     STATUS
------------------------------ ------------------------------ --------
TEST                           IDX_TEST_NAME                  N/A
TEST                           IDX_TEST_ID                    VALID
SQL> alter table test drop partition p1;
表已更改。
SQL> select table_name,index_name,status from user_indexes where table_name='TEST';
TABLE_NAME                     INDEX_NAME                     STATUS
------------------------------ ------------------------------ --------
TEST                           IDX_TEST_NAME                  N/A
TEST                           IDX_TEST_ID                    VALID
分区中没有数据时,执行drop分区不会影响全局索引状态。
SQL> insert into test values(2,'a');
已创建 1 行。
SQL> alter table test drop partition p2;
表已更改。
SQL> select table_name,index_name,status from user_indexes where table_name='TEST';
TABLE_NAME                     INDEX_NAME                     STATUS
------------------------------ ------------------------------ --------
TEST                           IDX_TEST_NAME                  N/A
TEST                           IDX_TEST_ID                    UNUSABLE

分区中有数据时执行drop分区,会改变全局索引状态。
而我们知道,全局索引和本地索引执行dml都不会改变索引状态;
但是从上面得知,在进行交换分区时会改变全局索引状态;当drop或truncate分区并且分区里有数据时,会改变全局索引状态。
但是他们都不改变本地索引状态。
有时你可能会忽然发现全局索引失效,其实这对于生产库来说是很可怕的事情。在操作时千万要小心,如果不得不进行会引起全局索引失效的操作,
那么操作完毕一定要记得将全局索引rebuild。

来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/24496749/viewspace-734921/,如需转载,请注明出处,否则将追究法律责任。

请登录后发表评论 登录
全部评论

注册时间:2010-08-25

  • 博文量
    84
  • 访问量
    207580