[转载]在线重定义
转载:http://www.itpub.net/thread-2096594-1-1.html
ORACLE提供了一个DBMS_REDEFINITION包用于在线重定义操作,主要包含三个过程:
DBMS_REDEFINITION.START_REDEF_TABLE
这个过程首先会创建一个快速刷新的物化视图作为过渡表,然后将源表的数据加载到过渡表中,并在源表上创建物化视图日志,以支持快速刷新同步数据
DBMS_REDEFINITION.SYNC_INTERIM_TABLE
用来把源表中的数据同步到过渡表
DBMS_REDEFINITION.FINISH_REDEF_TABLE
这个过程的操作步骤比较多,也是做在线重定义时需要特别注意的,但其执行时间通常是非常短的:
- 先调用一次DBMS_REDEFINITION.SYNC_INTERIM_TABLE,同步数据
- 锁定源表,锁定之后表数据不再允许发生变化
- 再调用一次DBMS_REDEFINITION.SYNC_INTERIM_TABLE,同步数据
- 交换源表和过渡表的表名
- 删除物化视图和物化视图日志
- 释放表锁资源
将普通表改造成分区表
- 在线重定义的操作过程
- 将一个2000万数据量的表进行重定义,需要多长时间
- 在线重定义期间,表相关的操作是否受影响,又是如何影响的
使用在线重定义技术,以下情况是需要注意的:
如果离线操作能够解决问题,就不要用在线重定义例如一些静态数据、历史数据的归档迁移,可使用CTAS、alter table move、或导出导入完成
表空间至少要留有比源表所用空间更大的剩余空间
在线重定义的操作过程耗时较长,但对业务的影响最小
要注意源表上的事务操作,如果过于频繁,可能会发生较严重的等待
1、检查用户权限
运行DBMS_REDEFINITION包需要以下权限:
- Execute privilege to DBMS_REDEFINITION
- Create any table
- Alter any table
- Drop any table
- Lock any table
- Select any table
- Create any index
- Create any trigger
可进入用户后执行以下SQL进行检查确认:
select * from session_privs;
2、模拟创建一个源表,并插入测试数据
3、模拟业务发生场景,一直持续到所有操作结束
按查询更新插入比例为7:1:2模拟,TPS为10,即每秒发生7笔查询、1笔更新、2笔插入操作,这个负载并不算大,但是变更通常选在空闲时间段,而且对于单表来说已经算很高的负载了。
4、按需求创建一个已分区的中间表
以上步骤完成准备工作,开始执行在线重定义过程。
5、检查源表是否具备在线重定义的条件
6、开始在线重定义,这一步相当于初始化工作,耗时比较长
7、在中间表上创建约束和索引并收集统计信息
这一步提前做,可以防止重定义完成后,新表没有可用索引,而产生性能问题。
oracle提供了dbms_redefinition.copy_table_dependents过程,用于复制源表上的索引、约束、触发器、权限等依赖关系
到中间表,但是这个包存在的BUG也不少,可以选择性使用。
这一步执行之后,可以再做一次手工同步刷新,耗时15秒
8、手工同步数据,将上一步执行中将产生的数据先做同步刷新
9、完成在线重定义过程,执行后,中间表和源表的表名互换
10、删除中间表,并将索引重命名回来
此时的中间表已经是原来未分区的普通表,而源表已经变成了分区表
至此,使用在线重定义进行表分区改造的工作已经完成。通过各个步骤的耗时情况可以看到,在我们模拟压力的情况下,整个过程耗时12分钟,而最关键的finish_redef_table步 骤,也就是会锁表的步骤,只有2秒就完成了。监控数据库的活动会话、DBTIME等数据,没有感觉到数据库的明显变化。
接下来把模拟压力增加到TPS 100,即每秒发生7笔查询、1笔更新、2笔插入操作,整个操作过程源表上DML的变化趋势图如下:
DML操作略有波动,但每一秒钟都存在DML操作,也就是说在这种压力之下,锁表的时间仍然是毫秒级。这组数据也 论证了使用在线重定义进行分区表改造的可行性和稳定性。