物化视图刷新结合ADG的尝试

之前写过一篇 物化视图刷新结合ADG的尝试,想必绝大多数的朋友看完再没有深究,其实也有些朋友做了建议,让我尝试prebuilt来做。这种数据迁移方式用的比较少,但是个人感觉还是很不错的。如果迁移的表不是很多,这种迁移方式还是非常强大的。
如果一个表非常大,我目前的设想就是通过ADG备库来把数据首先同步到统计库中,然后在主库端通过物化视图日志来增量刷新。

使用物化视图 prebuilt的方式确实可以实现,我产生了几个疑问,物化视图日志该什么时候创建。创建的时间太早或者太晚,对于增量刷新是否有影响,如果没有影响,我都幻想着可能是替代ogg的一个神器了。我做了下面三个测试。

###同步测试,物化视图刷新基于rowid       
统计库创建两个db link,一个指向主库,一个指向ADG
主库新增一个表  create table ACCtest20.test_mv_pri as  select * from dba_objects where rownum<1001;   
SQL> select count(*)from ACCtest20.test_mv_pri;
  COUNT(*)
----------
      1000
ADG+统计库创建表基于ADG的db link  
create table test.test_mv_pri as select *from ACCtest20.test_mv_pri@public_test0;
主库增加一条数据
insert into ACCtest20.test_mv_pri(owner,object_id,object_name,object_type) values('test',1000001,'test','TABLE');
commit;
主库修改一条数据
SQL> select object_id from ACCtest20.test_mv_pri where rownum<2;
 OBJECT_ID
----------
        20
update ACCtest20.test_mv_pri set object_id=1000002 where object_id=20;
 commit;
主库创建物化视图日志
create materialized view log on ACCtest20.test_mv_pri with rowid;
主库查询
SQL> select count(*)from ACCtest20.MLOG$_TEST_MV_PRI;
  COUNT(*)
----------
         0
主库+统计库创建物化视图基于主库的db link
create materialized view test.test_mv_pri on prebuilt table refresh fast with rowid as select *from ACCtest20.test_mv_pri@public_test0;
create materialized view test.test_mv_pri on prebuilt table refresh fast with rowid as select *from ACCtest20.test_mv_pri@public_test0
       *
ERROR at line 1:
ORA-12058: materialized view cannot use prebuilt table                                
做到这一步发现已经完全不支持了,所以就放弃了rowid的方式。
继续做第二个测试。

###同步测试    基于主键刷新 物化视图日志在全量同步后创建   
统计库创建两个db link,一个指向主库,一个指向ADG
主库新增一个表 
create table ACCtest20.test_mv_pri as  select owner,object_id,object_name,object_type from all_objects where rownum<1001 and object_id is not null;   
alter table ACCtest20.test_mv_pri modify(object_id primary key);
SQL> select count(*)from ACCtest20.test_mv_pri;
  COUNT(*)
----------
      1000
ADG+统计库创建表基于ADG的db link  
create table test.test_mv_pri as select *from ACCtest20.test_mv_pri@public_test0;
主库增加一条数据
insert into ACCtest20.test_mv_pri(owner,object_id,object_name,object_type) values('test',1000001,'test','TABLE');
  commit;
主库修改一条数据
SQL> select object_id from ACCtest20.test_mv_pri where rownum<2;
 OBJECT_ID
----------
        2
update ACCtest20.test_mv_pri set object_id=1000002 where object_id=2;
commit;
主库创建物化视图日志
 create materialized view log on ACCtest20.test_mv_pri ;
主库查询
 SQL> select count(*)from ACCtest20.MLOG$_TEST_MV_PRI;
  COUNT(*)
----------
         0
SQL> select count(*)from ACCtest20.test_mv_pri ;
  COUNT(*)
----------
      1001         
主库+统计库创建物化视图基于主库的db link
create materialized view test.test_mv_pri on prebuilt table refresh fast as select *from ACCtest20.test_mv_pri@public_test0;                           
查看数据条数
SQL> select count(*)from test.test_mv_pri;
  COUNT(*)
----------
      1000
增量刷新数据,查看数据条数是否完全同步
 exec dbms_mview.refresh('test.test_mv_pri','F');
SQL> select count(*)from test.test_mv_pri;
  COUNT(*)
----------
      1000
所以得到的结论是,在物化视图快速刷新的场景中,在本次测试中,在全量同步数据之后创建物化视图日志,快速刷新可能数据不一致,在全量同步的过程中,任何的dml操作可能都会丢失。

###同步测试    基于主键刷新  物化视图日志在全量同步前创建   
统计库创建两个db link,一个指向主库,一个指向ADG
主库新增一个表 
create table ACCtest20.test_mv_pri as  select owner,object_id,object_name,object_type from all_objects where rownum<1001 and object_id is not null;   
alter table ACCtest20.test_mv_pri modify(object_id primary key);
SQL> select count(*)from ACCtest20.test_mv_pri;
  COUNT(*)
----------
      1000
主库创建物化视图日志
create materialized view log on ACCtest20.test_mv_pri ;      
ADG+统计库创建表基于ADG的db link  
create table test.test_mv_pri as select *from ACCtest20.test_mv_pri@public_test0;
主库增加一条数据
insert into ACCtest20.test_mv_pri(owner,object_id,object_name,object_type) values('test',1000001,'test','TABLE');
commit;
主库修改一条数据
SQL> select object_id from ACCtest20.test_mv_pri where rownum<2;
 OBJECT_ID
----------
        2
update ACCtest20.test_mv_pri set object_id=1000002 where object_id=2;
commit;

主库查询
SQL> select count(*)from ACCtest20.MLOG$_TEST_MV_PRI;
  COUNT(*)
----------
         3
SQL> select count(*)from ACCtest20.test_mv_pri ;
  COUNT(*)
----------
      1001         
主库+统计库创建物化视图基于主库的db link
create materialized view test.test_mv_pri on prebuilt table refresh fast as select *from ACCtest20.test_mv_pri@public_test0;                           
查看数据条数
 SQL> select count(*)from test.test_mv_pri;
  COUNT(*)
----------
      1000
增量刷新数据,查看数据条数是否完全同步
 exec dbms_mview.refresh('test.test_mv_pri','F');
SQL> select count(*)from test.test_mv_pri;
  COUNT(*)
----------
      1000
主库查询
select count(*)from ACCtest20.MLOG$_TEST_MV_PRI;
  COUNT(*)
----------
         0      
###数据不一致 #############
主库继续插入一条数据
 insert into ACCtest20.test_mv_pri(owner,object_id,object_name,object_type) values('test',1000003,'test','TABLE');
commit;
增量刷新数据,查看数据条数是否完全同步
SQL> select count(*)from ACCtest20.test_mv_pri ;
  COUNT(*)
----------
      1002
结论,在这种场景中,可能会有数据丢失的情况。主要原因就是统计库的物化视图创建时间晚于源库的物化视图日志时间。
我这种测试不是说物化视图prebuilt的方式不好,而是在这种场景中还是会有一些影响。如果通过主库全量同步数据,再增量刷新肯定是没有问题的。我这个场景只是想通过ADG来实现间接的全量刷新,不是主流的使用方法。

时间: 2024-09-15 10:48:02

物化视图刷新结合ADG的尝试的相关文章

物化视图刷新原理与性能诊断

参考文档:Materialized View Refresh: Locking, Performance, Monitoring (文档 ID 258252.1) How to Monitor the Progress of a Materialized View Refresh (MVIEW) (文档 ID 258021.1) 1.名词解释: 基表 指的是英文里面的Master Table和Master Materialized View,并不只是只一个表,而是创建MView的时候所需要用到的

[20150705]12c物化视图刷新Out of place2

[20150705]12c物化视图刷新Out of place2.txt --11G物化视图刷新有1个参数atomic_refresh. --如果为false,采用的方式是truncate,再使用/*+ append */ 提示insert.这样redo最少,但是刷新期间无法访问. --如果为true,采用的方式是delete,再insert.这样产生许多redo与undo.这样在刷新期间访问没问题,最多有点慢. --自己做一个测试: --12c在这个基础上引入1个参数Out of place,

[20150629]物化视图刷新atomic_refresh.txt

[20150629]物化视图刷新atomic_refresh.txt --11G物化视图刷新有1个参数atomic_refresh. --如果为false,采用的方式是truncate,再使用/*+ append */ 提示insert.这样redo最少,但是刷新期间无法访问. --如果为true,采用的方式是delete,再insert.这样产生许多redo与undo.这样在刷新期间访问没问题,最多有点慢. --自己做一个测试: 1.建立测试环境: SCOTT@test> @ver1 PORT

特殊的物化视图刷新

现在有一个需求,某个环境中存在两个用户,一个用户中存在物化视图,另一个用户中存在源表,根据业务的需要,需要做一种特别的物化视图刷新. 物化视图用户中的物化视图为CORP_NAME 源数据用户中的表为ADD_CORP_NAME 可能数据刷新是没有问题,关键就是在于CORP_NAME中的字段要比ADD_CORP_NAME多一些.CORP_NAME           ADD_CORP_NAME CORP_ID               |  CORP_ID            SYS_CREAT

oracle如何利用触发器对物化视图刷新进行定制

物化视图的刷新其实和普通的SQL执行没有什么本质的区别,因此也可以通过在物化视图上创建触发器的方式,对刷新操作进行定制. 正好前两天有人在BLOG上问我,如果在物化视图添加一个时间戳列,并在物化视图更新的时候,自动维护这个列.其实很简单,通过触发器就可以达到这个目的: SQL> CREATE TABLE T (ID NUMBER PRIMARY KEY, NAME VARCHAR2(30)); 表已创建. SQL> INSERT INTO T SELECT ROWNUM, TNAME FROM

物化视图刷新失败导致日志表异常增大

整理自:http://blog.itpub.net/231499/viewspace-63714/ 今天在检查时,发现某个物化视图日志占用的空间超过150M,再检查看,该物化视图日志表的记录数有150W,由于其对应的物化视图没有会刷新一次,结合业务量分析可知:物化视图日志不能正常清除. 下面的解决步骤 --在源库查询物化视图对应日志条目个数SQL> select count(1) from MLOG$_ITEM_TAG; COUNT(1)----------532515 --在物化视图端刷新物化

物化视图刷新的问题及分析

最近现场需要搭建一套全新的环境,对于数据字典的管理采用了物化视图,因为数据量不大,采用了全量刷新的方式.因为有好几套环境,有几套环境是通过db link和主节点的表创建的物化视图,这几个节点间的网络情况不好,刷新一个稍微大一些的表或者带有lob字段的表时,速度会很慢,因为有好几套环境,一套一套的等待刷新完得花费不少的时间,所以自己想写一个shell脚本让它在后台慢慢跑,这样过一段时间再看看日志保证数据都已经刷新完毕就可以了. 原本采用的方式是 create materialized view x

【物化视图】根据物化视图日志快速刷新物化视图的过程

先来再次分析一下物化视图日志的结构. yang@rac1>create table t (id number ,name varchar2(30),val number); Table created. yang@rac1>create materialized view log on t with rowid,sequence (id,name) including  new values; Materialized view log created. yang@rac1>desc m

oracle基于COMMIT SCN的物化视图日志快速刷新的方法

11.2中物化视图日志可以指定COMMIT SCN,这时物化视图刷新就不需要时间戳了,这篇简单描述Oracle是如何实现通过COMMIT SCN来进行刷新的. 建立一个测试环境: SQL> SELECT * FROM V$VERSION; BANNER -------------------------------------------------------------------------------- Oracle Database11gEnterprise Edition Relea