Oracle 進階複製
最後更新:2018-12-07
來源:互聯網
上載者:User
三台資料庫的global_name如下:
Orcl16.com 192.168.100.16 (主要資料庫,即資料來源)
Orcl8.com 192.168.100.8 (複製資料庫)
Dtgdb.com 192.168.100.150(複製資料庫)
三台資料庫初始化參數的設定:
Global_names = true
Job_queue_process 的值要大於0
Open_links = 4 或更大 視串連數來定
要求:三個資料庫的scott模式表,索引的資料和結構都必須相同
應用程式使用者:scott
可用以下命令在每個網站上面修改工作群組
ALTER DATABASE RENAME global_name TO orcl16.Com;
建立主要站台:orcl16.com
CONNECT SYSTEM/xl1100@100.16 ------用system使用者連結100.16
CREATE USER repadmin IDENTIFIED BY repadmin; ------建立複製管理員repadmin帳號
BEGIN ------分配許可權給repadmin使用者
DBMS_REPCAT_ADMIN.GRANT_ADMIN_ANY_SCHEMA (
username => 'repadmin');
END;
/
GRANT DBA TO repadmin
GRANT COMMENT ANY TABLE TO repadmin;
GRANT LOCK ANY TABLE TO repadmin;
GRANT SELECT ANY DICTIONARY TO repadmin;
BEGIN
DBMS_DEFER_SYS.REGISTER_PROPAGATOR (
username => 'repadmin');
END;
/
BEGIN
DBMS_REPCAT_ADMIN.REGISTER_USER_REPGROUP (
username => 'repadmin',
privilege_type => 'receiver',
list_of_gnames => NULL);
END;
/
CONNECT repadmin/repadmin@100.16 ---------用repadmin 使用者登入100.16
BEGIN
DBMS_DEFER_SYS.SCHEDULE_PURGE (
next_date => SYSDATE,
interval => 'SYSDATE + 1/24', ----------添加PURGE 的任務SYSDATE + 1/24 間隔為一個小時
delay_seconds => 0);
END;
/
設定orcl8.com
CONNECT SYSTEM/xl1100@100.8
CREATE USER repadmin IDENTIFIED BY repadmin;
BEGIN
DBMS_REPCAT_ADMIN.GRANT_ADMIN_ANY_SCHEMA (
username => 'repadmin');
END;
/
GRANT COMMENT ANY TABLE TO repadmin;
GRANT LOCK ANY TABLE TO repadmin;
GRANT SELECT ANY DICTIONARY TO repadmin;
BEGIN
DBMS_DEFER_SYS.REGISTER_PROPAGATOR (
username => 'repadmin');
END;
/
BEGIN
DBMS_REPCAT_ADMIN.REGISTER_USER_REPGROUP (
username => 'repadmin',
privilege_type => 'receiver',
list_of_gnames => NULL);
END;
/
CONNECT repadmin/repadmin@100.8
BEGIN
DBMS_DEFER_SYS.SCHEDULE_PURGE (
next_date => SYSDATE,
interval => 'SYSDATE + 1/24',
delay_seconds => 0);
END;
/
設定dtgdb
CONNECT SYSTEM/xl1100@100.150
CREATE USER repadmin IDENTIFIED BY repadmin;
BEGIN
DBMS_REPCAT_ADMIN.GRANT_ADMIN_ANY_SCHEMA (
username => 'repadmin');
END;
/
GRANT DBA TO repadmin
GRANT COMMENT ANY TABLE TO repadmin;
GRANT LOCK ANY TABLE TO repadmin;
GRANT SELECT ANY DICTIONARY TO repadmin;
BEGIN
DBMS_DEFER_SYS.REGISTER_PROPAGATOR (
username => 'repadmin');
END;
/
BEGIN
DBMS_REPCAT_ADMIN.REGISTER_USER_REPGROUP (
username => 'repadmin',
privilege_type => 'receiver',
list_of_gnames => NULL);
END;
/
CONNECT repadmin/repadmin@100.150
BEGIN
DBMS_DEFER_SYS.SCHEDULE_PURGE (
next_date => SYSDATE,
interval => 'SYSDATE + 1/24',
delay_seconds => 0);
END;
/
建立資料庫鏈路(可用select * from global_name@orcl8.com檢查資料鏈路是否通)
100.16:
CONNECT SYSTEM/xl1100@100.16
CREATE PUBLIC DATABASE LINK orcl8.com USING 'orcl8'; ----------後面的orcl8為在TNS檔案中配置的名字
CREATE PUBLIC DATABASE LINK dtgdb.com USING 'dtgdb';
CONNECT repadmin/repadmin@100.16
CREATE DATABASE LINK orcl8.com CONNECT TO repadmin IDENTIFIED BY repadmin;
CREATE DATABASE LINK dtgdb.com CONNECT TO repadmin IDENTIFIED BY repadmin;
100.8:
CONNECT SYSTEM/xl1100@100.8
CREATE PUBLIC DATABASE LINK orcl16.com USING 'orcl16';
CREATE PUBLIC DATABASE LINK dtgdb.com USING 'dtgdb';
CONNECT repadmin/repadmin@100.8
CREATE DATABASE LINK orcl16.com CONNECT TO repadmin IDENTIFIED BY repadmin;
CREATE DATABASE LINK dtgdb.com CONNECT TO repadmin IDENTIFIED BY repadmin;
100.150:
CONNECT SYSTEM/xl1100@100.150
CREATE PUBLIC DATABASE LINK orcl16.com USING 'orcl16';
CREATE PUBLIC DATABASE LINK orcl8.com USING 'orcl8';
CONNECT repadmin/repadmin@100.150
CREATE DATABASE LINK orcl16.com CONNECT TO repadmin IDENTIFIED BY repadmin;
CREATE DATABASE LINK orcl8.com CONNECT TO repadmin IDENTIFIED BY repadmin;
建立jobs (定時執行PUSH任務)
CONNECT repadmin/repadmin@100.16
BEGIN
DBMS_DEFER_SYS.SCHEDULE_PUSH (
destination => 'orcl8.com',
interval => 'SYSDATE + (1/144)',
next_date => SYSDATE,
parallelism => 1,
execution_seconds => 1500,
delay_seconds => 1200);
END;
/
BEGIN
DBMS_DEFER_SYS.SCHEDULE_PUSH (
destination => 'dtgdb.com',
interval => 'SYSDATE + (1/144)',
next_date => SYSDATE,
parallelism => 1,
execution_seconds => 1500,
delay_seconds => 1200);
END;
/
CONNECT repadmin/repadmin@100.8
BEGIN
DBMS_DEFER_SYS.SCHEDULE_PUSH (
destination => 'orcl16.com',
interval => 'SYSDATE + (1/144)',
next_date => SYSDATE,
parallelism => 1,
execution_seconds => 1500,
delay_seconds => 1200);
END;
/
BEGIN
DBMS_DEFER_SYS.SCHEDULE_PUSH (
destination => 'dtgdb.com',
interval => 'SYSDATE + (1/144)',
next_date => SYSDATE,
parallelism => 1,
execution_seconds => 1500,
delay_seconds => 1200);
END;
/
CONNECT repadmin/repadmin@100.150
BEGIN
DBMS_DEFER_SYS.SCHEDULE_PUSH (
destination => 'orcl16.com',
interval => 'SYSDATE + (1/144)',
next_date => SYSDATE,
parallelism => 1,
execution_seconds => 1500,
delay_seconds => 1200);
END;
/
BEGIN
DBMS_DEFER_SYS.SCHEDULE_PUSH (
destination => 'orcl8.com',
interval => 'SYSDATE + (1/144)',
next_date => SYSDATE,
parallelism => 1,
execution_seconds => 1500,
delay_seconds => 1200);
END;
/
建立主工作群組
CONNECT repadmin/repadmin@100.16
BEGIN
DBMS_REPCAT.CREATE_MASTER_REPGROUP (
gname => 'mygrp'); ----------建立名為mygrp的組名
END;
/
BEGIN
DBMS_REPCAT.CREATE_MASTER_REPOBJECT (
gname => ' mygrp ', ----------組名
type => 'TABLE', ----------類型(此處類型為表)
oname => 'emp', ----------表(為sname使用者下的要參加複製的表)
sname => 'scott', ----------使用者(參加複製的使用者)
use_existing_object => TRUE,
copy_rows => FALSE);
END;
/
----------有多少個需要參加複製的表就要寫多少條以上的語句
BEGIN
DBMS_REPCAT.CREATE_MASTER_REPOBJECT (
gname => 'mygrp',
type => 'TABLE',
oname => 'dept',
sname => 'scott',
use_existing_object => TRUE,
copy_rows => FALSE);
END;
/
BEGIN
DBMS_REPCAT.CREATE_MASTER_REPOBJECT (
gname => 'mygrp',
type => 'TABLE',
oname => 'a',
sname => 'scott',
use_existing_object => TRUE,
copy_rows => FALSE);
END;
/
BEGIN
DBMS_REPCAT.CREATE_MASTER_REPOBJECT (
gname => 'mygrp',
type => 'TABLE',
oname => 'bonus',
sname => 'scott',
use_existing_object => TRUE,
copy_rows => FALSE);
END;
/
BEGIN
DBMS_REPCAT.CREATE_MASTER_REPOBJECT (
gname => 'mygrp',
type => 'TABLE',
oname => 'salgrade',
sname => 'scott',
use_existing_object => TRUE,
copy_rows => FALSE);
END;
/
添加複製網站
BEGIN
DBMS_REPCAT.ADD_MASTER_DATABASE (
gname => 'mygrp',
master => 'orcl8.com',
use_existing_objects => TRUE,
copy_rows => FALSE,
propagation_mode => 'ASYNCHRONOUS');
END;
/
BEGIN
DBMS_REPCAT.ADD_MASTER_DATABASE (
gname => 'mygrp',
master => 'dtgdb.com',
use_existing_objects => TRUE,
copy_rows => FALSE,
propagation_mode => 'ASYNCHRONOUS');
END;
/
啟用複製支援
BEGIN
DBMS_REPCAT.GENERATE_REPLICATION_SUPPORT (
sname => 'scott', --------------使用者名稱
oname => 'emp', --------------參與複製的表名
type => 'TABLE', --------------類型
min_communication => TRUE);
END;
/
------------以上內容有多少參與複製的表就要寫多少條
BEGIN
DBMS_REPCAT.GENERATE_REPLICATION_SUPPORT (
sname => 'scott',
oname => 'dept',
type => 'TABLE',
min_communication => TRUE);
END;
/
BEGIN
DBMS_REPCAT.GENERATE_REPLICATION_SUPPORT (
sname => 'scott',
oname => 'a',
type => 'TABLE',
min_communication => TRUE);
END;
/
BEGIN
DBMS_REPCAT.GENERATE_REPLICATION_SUPPORT (
sname => 'scott',
oname => 'bonus ',
type => 'TABLE',
min_communication => TRUE);
END;
/
BEGIN
DBMS_REPCAT.GENERATE_REPLICATION_SUPPORT (
sname => 'scott',
oname => ' salgrade ',
type => 'TABLE',
min_communication => TRUE);
END;
/
―――以上執行完後 可以通過select * from dbs_repcatlog;查看同步情況
DBA_REPCATLOG 視圖中管理請求的幾種狀態:
1) READY:表示請求準備被執行。如果長時間處於該狀態,可以手動執行DBMS_REPCAT.DO_DEFERRED_REPCAT_ADMIN 預存程序來執行請求。
2) AWAIT_CALLBACK:這種狀態只會出現在主體定義網站上,表示正在等待其它的主要站台執行請求並且返回結果。
3) ERROR:表示請求執行錯誤
4) DO_CALLBACK:這種狀態只會出現在非主體定義網站上,表示要通知主體定義網站請求執行的結果。
以下指令碼用於解決由於網路問題造成jobs失敗次數超過16次狀態變為broken後JOBS失效的問題(每個網站都要運行)
create or replace procedure change_job_broken is
BEGIN
declare
CURSOR my_broken_jobs is ------建立一個遊標
SELECT job FROM user_jobs WHERE broken = 'Y'; ------檢測user_jobs的broken狀態是否有為"Y"的
begin
FOR broken_job IN my_broken_jobs LOOP
BEGIN
dbms_job.broken(broken_job.job, FALSE); -------如果broken狀態為"Y"則通過此行將其改為"N"
EXCEPTION
WHEN OTHERS THEN
NULL;
END;
END LOOP;
END;
end;
/
然後可以在製作一個JOBS讓以上指令碼每天運行一次
variable n number;
begin
dbms_job.submit(:n,'change_job_broken;',sysdate,'sysdate+1');
commit;
dbms_job.run(:n);
commit;
end;
/
開始複製
BEGIN
DBMS_REPCAT.RESUME_MASTER_ACTIVITY (
gname => 'mygrp');
END;
/
停止複製
SQL>EXECUTE Dbms_Repcat. SUSPEND_MASTER_ACTIVITY (gname => 'mygrp');
所有工作完成後 啟動複製 然後在各個網站上面 用select * from dba_repgroup;檢查網站狀態 狀態為NORMAL時表示該網站正常。
相關視圖
" DBA_REPSITES ----複製網站情況
" DBA_REPGROUP -----複製組情況
" DBA_REPOBJECT ----複製對象情況
" DBA_REPCATLOG ---同步情況日誌
刪除複製
在主要站台上面執行
CONNECT repadmin/repadmin@100.16
-- 停掉進階複製
EXECUTE Dbms_Repcat.Suspend_Master_Activity(gname=>'MYGRP');
-- 刪除複製組
EXECUTE Dbms_Repcat.Drop_Master_Repobject('SCOTT', 'EMP', 'TABLE');
EXECUTE Dbms_Repcat.Drop_Master_Repobject('SCOTT', 'a', 'TABLE');
EXECUTE Dbms_Repcat.Drop_Master_Repobject('SCOTT', 'dept', 'TABLE');
EXECUTE Dbms_Repcat.Drop_Master_Repobject('SCOTT', 'bonus', 'TABLE');
EXECUTE Dbms_Repcat.Drop_Master_Repobject('SCOTT', 'salgrade', 'TABLE');
EXECUTE Dbms_Repcat.Remove_Master_Databases('MYGRP', 'orcl8.com');----刪除主要站台上面的組
EXECUTE Dbms_Repcat.Remove_Master_Databases('MYGRP', 'dtgdb.com');
在所有要刪除的網站上面執行
--刪除私人資料鏈路
CONNECT repadmin/repadmin@100.16;
EXECUTE Dbms_Repcat.Drop_Master_Repgroup('MYGRP');
DROP DATABASE LINK orcl8.com;
DROP DATABASE LINK dtgdb.com;
CONNECT repadmin/repadmin@100.8;
EXECUTE Dbms_Repcat.Drop_Master_Repgroup('MYGRP');
DROP DATABASE LINK orcl16.com;
DROP DATABASE LINK dtgdb.com;
CONNECT repadmin/repadmin@100.150;
EXECUTE Dbms_Repcat.Drop_Master_Repgroup('MYGRP');
DROP DATABASE LINK orcl16.com;
DROP DATABASE LINK orcl8.com;
----刪除JOBS
select job,what from user_jobs; ----------查詢job numbers
EXECUTE Dbms_Job.Remove(2); ------括弧內填寫剛查詢到的job numbers
EXECUTE Dbms_Job.Remove(3);
-- 刪除REPADMIN使用者,注意:必須先刪除網站下隸屬於該repadmin使用者的jobs和組mygrp 才能刪除使用者(就是必須先執行上面的刪除命令才能用下面的命令)
connect system/xl1100@100.16
EXECUTE Dbms_Defer_Sys.Unregister_Propagator(username=>'REPADMIN');
EXECUTE Dbms_Repcat_Admin.Revoke_Admin_Any_Schema(username=>'REPADMIN');
DROP USER repadmin CASCADE;
connect system/xl1100@100.8
connect system/xl1100@100.150
EXECUTE Dbms_Defer_Sys.Unregister_Propagator(username=>'REPADMIN');
EXECUTE Dbms_Repcat_Admin.Revoke_Admin_Any_Schema(username=>'REPADMIN');
DROP USER repadmin CASCADE;
--刪除公用的資料鏈路
connect system/xl1100@100.16
DROP PUBLIC DATABASE LINK orcl8.com;
DROP PUBLIC DATABASE LINK dtgdb.com;
connect system/xl1100@100.8
DROP PUBLIC DATABASE LINK orcl16.com;
DROP PUBLIC DATABASE LINK dtgdb.com;
connect system/xl1100@100.150
DROP PUBLIC DATABASE LINK orcl16.com;
DROP PUBLIC DATABASE LINK orcl8.com;
備忘:每次運行完repcat 包以後都應該執行一次commit,因為某些rep 的預存程序是不會
自動commit 的,同時這也是一個troubleshooting,一般的rep 指令碼都會較快的返回結果,
如果一條命令之後長時間沒有結果返回,那麼很可能是上面的命令沒有commit,取消掉當
前的命令,然後作一次commit,再重新執行,一般都能夠解決問題。
強制移除複製組
Sql>Truncate table system.def$_aqcall;
Sql>Exec dbms_repcat.drop_master_repgroup(gname=>'mygrp',all_sites=>true);
關於進階複製的相關內容還很多,比如進階複製中衝突的解決方案等等,以後可以一起討論.