透過資料驗證部署驗證資料一致性

瞭解如何使用 OCI GoldenGate 驗證來源與目標資料庫之間的資料一致性。

開始之前

若要順利完成此快速啟動,您必須具備:

作業 1:設定環境

  1. 建立資料複製部署

  2. 建立來源 Oracle Autonomous AI Transaction Processing (ATP) 連線

  3. 建立目標 Autonomous AI Lakehouse (ALK) 連線

  4. 指定部署連線

  5. 使用 SQL 工具啟用補充日誌記錄:

    ALTER DATABASE ADD SUPPLEMENTAL LOG DATA
  6. 在 SQL 工具中執行下列查詢,以確保來源資料庫中所有表格的 support_mode=FULL

    select * from DBA_GOLDENGATE_SUPPORT_MODE where owner = 'SRC_OCIGGLL';

任務 2:建立整合式擷取

「整合式擷取」會擷取來源資料庫的持續變更。

  1. 在部署詳細資料頁面上,選取啟動主控台

  2. 如有必要,請輸入 oggadmin 作為您在建立部署時所使用的使用者名稱和密碼,然後選取登入

  3. 新增交易資料和檢查點表格:

    1. 開啟導覽功能表,然後選取資料庫連線

    2. 選取連線至資料庫 SourceDB

    3. 在導覽功能表中,選取 Trandata ,然後選取新增 Trandata (加號圖示)。

    4. 結構名稱中,輸入 SRC_OCIGGLL,然後選取提交

    5. 若要驗證,請在「搜尋」欄位中輸入 SRC_OCIGGLL,然後選取搜尋

    6. 開啟導覽功能表,然後選取資料庫連線

    7. 選取連線至資料庫 TargetDB

    8. 在導覽功能表中,選取檢查點,然後選取新增檢查點 (加號圖示)。

    9. 檢查點資料表中,輸入 "SRCMIRROR_OCIGGLL"."CHECKTABLE",然後選取提交

  4. 新增擷取

    備註:請參閱其他擷取參數選項,以取得可用於指定來源表格之參數的詳細資訊。

    在「擷取參數」頁面上,將下列行附加至 EXTTRAIL <trail-name> 下:

    -- Capture DDL operations for listed schema tables
    ddl include mapped
    
    -- Add step-by-step history of to the report file. Useful when troubleshooting.
    ddloptions report
    
    -- Write capture stats per table to the report file daily.
    report at 00:01
    
    -- Rollover the report file weekly. Useful when IE runs
    -- without being stopped/started for long periods of time to
    -- keep the report files from becoming too large.
    reportrollover at 00:01 on Sunday
    
    -- Report total operations captured, and operations per second
    -- every 10 minutes.
    reportcount every 10 minutes, rate
    
    -- Table list for capture
    table SRC_OCIGGLL.*;
  5. 檢查長時間執行的交易。在來源資料庫上執行下列命令檔:

    select start_scn, start_time from gv$transaction where start_scn < (select max(start_scn) from dba_capture);

    如果查詢傳回任何資料列,則您必須找出交易的 SCN,然後確認或倒回交易。

工作 3:使用 Oracle Data Pump (ExpDP) 匯出資料

使用 Oracle Data Pump (ExpDP) 將資料從來源資料庫匯出至 Oracle Object Store。

  1. 建立 Oracle Object Store 儲存桶

    記下用於「匯出」和「匯入」命令檔的命名空間和儲存桶名稱。

  2. 建立認證權杖,然後將權杖字串複製並貼到文字編輯器以供日後使用。

  3. 在您的來源資料庫中建立證明資料,將 <user-name><token> 取代為您的 Oracle Cloud 帳戶使用者名稱和您在上一個步驟中建立的權杖字串:

    BEGIN
      DBMS_CLOUD.CREATE_CREDENTIAL(
        credential_name => 'ADB_OBJECTSTORE',
        username => '<user-name>',
        password => '<token>'
      );
    END;
  4. 在您的來源資料庫中執行下列命令檔,以建立「匯出資料」工作。請確定已相應地取代物件存放區 URI 中的 <region><namespace><bucket-name>SRC_OCIGGLL.dmp 是執行此命令檔時將建立的檔案。

    DECLARE
    ind NUMBER;              -- Loop index
    h1 NUMBER;               -- Data Pump job handle
    percent_done NUMBER;     -- Percentage of job complete
    job_state VARCHAR2(30);  -- To keep track of job state
    le ku$_LogEntry;         -- For WIP and error messages
    js ku$_JobStatus;        -- The job status from get_status
    jd ku$_JobDesc;          -- The job description from get_status
    sts ku$_Status;          -- The status object returned by get_status
    
    BEGIN
    
    -- Create a (user-named) Data Pump job to do a schema export.
    h1 := DBMS_DATAPUMP.OPEN('EXPORT','SCHEMA',NULL,'SRC_OCIGGLL_EXPORT','LATEST');
    
    -- Specify a single dump file for the job (using the handle just returned)
    -- and a directory object, which must already be defined and accessible
    -- to the user running this procedure.
    DBMS_DATAPUMP.ADD_FILE(h1,'https://objectstorage.<region>.oraclecloud.com/n/<namespace>/b/<bucket-name>/o/SRC_OCIGGLL.dmp','ADB_OBJECTSTORE','100MB',DBMS_DATAPUMP.KU$_FILE_TYPE_URIDUMP_FILE,1);
    
    -- A metadata filter is used to specify the schema that will be exported.
    DBMS_DATAPUMP.METADATA_FILTER(h1,'SCHEMA_EXPR','IN (''SRC_OCIGGLL'')');
    
    -- Start the job. An exception will be generated if something is not set up properly.
    DBMS_DATAPUMP.START_JOB(h1);
    
    -- The export job should now be running. In the following loop, the job
    -- is monitored until it completes. In the meantime, progress information is displayed.
    percent_done := 0;
    job_state := 'UNDEFINED';
    while (job_state != 'COMPLETED') and (job_state != 'STOPPED') loop
      dbms_datapump.get_status(h1,dbms_datapump.ku$_status_job_error + dbms_datapump.ku$_status_job_status + dbms_datapump.ku$_status_wip,-1,job_state,sts);
      js := sts.job_status;
    
    -- If the percentage done changed, display the new value.
    if js.percent_done != percent_done
    then
      dbms_output.put_line('*** Job percent done = ' \|\| to_char(js.percent_done));
      percent_done := js.percent_done;
    end if;
    
    -- If any work-in-progress (WIP) or error messages were received for the job, display them.
    if (bitand(sts.mask,dbms_datapump.ku$_status_wip) != 0)
    then
      le := sts.wip;
    else
      if (bitand(sts.mask,dbms_datapump.ku$_status_job_error) != 0)
      then
        le := sts.error;
      else
        le := null;
      end if;
    end if;
    if le is not null
    then
      ind := le.FIRST;
      while ind is not null loop
        dbms_output.put_line(le(ind).LogText);
        ind := le.NEXT(ind);
      end loop;
    end if;
      end loop;
    
      -- Indicate that the job finished and detach from it.
      dbms_output.put_line('Job has completed');
      dbms_output.put_line('Final job state = ' \|\| job_state);
      dbms_datapump.detach(h1);
    END;

作業 4:使用 Oracle Data Pump (ImpDP) 建立目標資料庫

使用 Oracle Data Pump (ImpDP) 從來源資料庫匯出的 SRC_OCIGGLL.dmp,將資料匯入目標資料庫。

  1. 在您的目標資料庫中建立證明資料以存取 Oracle Object Store (使用前一節中的相同資訊)。

    BEGIN
      DBMS_CLOUD.CREATE_CREDENTIAL(
        credential_name => 'ADB_OBJECTSTORE',
        username => '<user-name>',
        password => '<token>'
      );
    END;
  2. 在目標資料庫中執行下列命令檔,以從 SRC_OCIGGLL.dmp 匯入資料。請確定已相應地取代物件存放區 URI 中的 <region><namespace><bucket-name>

    DECLARE
    ind NUMBER;  -- Loop index
    h1 NUMBER;  -- Data Pump job handle
    percent_done NUMBER;  -- Percentage of job complete
    job_state VARCHAR2(30);  -- To keep track of job state
    le ku$_LogEntry;  -- For WIP and error messages
    js ku$_JobStatus;  -- The job status from get_status
    jd ku$_JobDesc;  -- The job description from get_status
    sts ku$_Status;  -- The status object returned by get_status
    BEGIN
    
    -- Create a (user-named) Data Pump job to do a "full" import (everything
    
    -- in the dump file without filtering).
    h1 := DBMS_DATAPUMP.OPEN('IMPORT','FULL',NULL,'SRCMIRROR_OCIGGLL_IMPORT');
    
    -- Specify the single dump file for the job (using the handle just returned)
    -- and directory object, which must already be defined and accessible
    -- to the user running this procedure. This is the dump file created by
    -- the export operation in the first example.
    
    DBMS_DATAPUMP.ADD_FILE(h1,'https://objectstorage.<region>.oraclecloud.com/n/<namespace>/b/<bucket-name>/o/SRC_OCIGGLL.dmp','ADB_OBJECTSTORE',null,DBMS_DATAPUMP.KU$_FILE_TYPE_URIDUMP_FILE);
    
    -- A metadata remap will map all schema objects from SRC_OCIGGLL to SRCMIRROR_OCIGGLL.
    DBMS_DATAPUMP.METADATA_REMAP(h1,'REMAP_SCHEMA','SRC_OCIGGLL','SRCMIRROR_OCIGGLL');
    
    -- If a table already exists in the destination schema, skip it (leave
    -- the preexisting table alone). This is the default, but it does not hurt
    -- to specify it explicitly.
    DBMS_DATAPUMP.SET_PARAMETER(h1,'TABLE_EXISTS_ACTION','SKIP');
    
    -- Start the job. An exception is returned if something is not set up properly.
    DBMS_DATAPUMP.START_JOB(h1);
    
    -- The import job should now be running. In the following loop, the job is
    
    -- monitored until it completes. In the meantime, progress information is
    
    -- displayed. Note: this is identical to the export example.
    percent_done := 0;
    job_state := 'UNDEFINED';
    while (job_state != 'COMPLETED') and (job_state != 'STOPPED') loop
      dbms_datapump.get_status(h1,
        dbms_datapump.ku$_status_job_error +
        dbms_datapump.ku$_status_job_status +
        dbms_datapump.ku$_status_wip,-1,job_state,sts);
        js := sts.job_status;
    
      -- If the percentage done changed, display the new value.
      if js.percent_done != percent_done
      then
        dbms_output.put_line('*** Job percent done = ' \|\|
        to_char(js.percent_done));
        percent_done := js.percent_done;
      end if;
    
      -- If any work-in-progress (WIP) or Error messages were received for the job, display them.
      if (bitand(sts.mask,dbms_datapump.ku$_status_wip) != 0)
      then
        le := sts.wip;
      else
        if (bitand(sts.mask,dbms_datapump.ku$_status_job_error) != 0)
        then
          le := sts.error;
        else
          le := null;
        end if;
      end if;
      if le is not null
      then
        ind := le.FIRST;
        while ind is not null loop
          dbms_output.put_line(le(ind).LogText);
          ind := le.NEXT(ind);
        end loop;
      end if;
    end loop;
    
    -- Indicate that the job finished and gracefully detach from it.
    dbms_output.put_line('Job has completed');
    dbms_output.put_line('Final job state = ' \|\| job_state);
    dbms_datapump.detach(h1);
    END;

作業 5:新增並執行非整合式 Replicat

  1. 新增並執行 Replicat

    參數檔畫面上,使用下列指令碼取代 MAP *.*, TARGET *.*;

    -- Capture DDL operations for listed schema tables
    ddl include mapped
    
    -- Add step-by-step history of ddl operations captured
    -- to the report file. Very useful when troubleshooting.
    ddloptions report
    
    -- Write capture stats per table to the report file daily.
    report at 00:01
    
    -- Rollover the report file weekly. Useful when PR runs
    -- without being stopped/started for long periods of time to
    -- keep the report files from becoming too large.
    reportrollover at 00:01 on Sunday
    
    -- Report total operations captured, and operations per second
    -- every 10 minutes.
    reportcount every 10 minutes, rate
    
    -- Table map list for apply
    DBOPTIONS ENABLE_INSTANTIATION_FILTERING;
    MAP SRC_OCIGGLL.*, TARGET SRCMIRROR_OCIGGLL.*;

    注意:DBOPTIONS ENABLE_INSTATIATION_FILTERING 會對使用 Oracle Data Pump 匯入的表格啟用 CSN 篩選。如需詳細資訊,請參閱 DBOPTIONS Reference

  2. 執行來源資料庫的插入:

    1. 返回 Oracle Cloud 主控台,然後使用導覽功能表返回 Oracle AI DatabaseAutonomous AI Transaction Processing ,然後瀏覽 SourceDB

    2. 在「SourceDB 詳細資訊」頁面上,選取資料庫動作,然後選取 SQL

    3. 輸入下列插入,然後選取執行命令檔

      Insert into SRC_OCIGGLL.SRC_CITY (CITY_ID,CITY,REGION_ID,POPULATION) values (1000,'Houston',20,743113);
      Insert into SRC_OCIGGLL.SRC_CITY (CITY_ID,CITY,REGION_ID,POPULATION) values (1001,'Dallas',20,822416);
      Insert into SRC_OCIGGLL.SRC_CITY (CITY_ID,CITY,REGION_ID,POPULATION) values (1002,'San Francisco',21,157574);
      Insert into SRC_OCIGGLL.SRC_CITY (CITY_ID,CITY,REGION_ID,POPULATION) values (1003,'Los Angeles',21,743878);
      Insert into SRC_OCIGGLL.SRC_CITY (CITY_ID,CITY,REGION_ID,POPULATION) values (1004,'San Diego',21,840689);
      Insert into SRC_OCIGGLL.SRC_CITY (CITY_ID,CITY,REGION_ID,POPULATION) values (1005,'Chicago',23,616472);
      Insert into SRC_OCIGGLL.SRC_CITY (CITY_ID,CITY,REGION_ID,POPULATION) values (1006,'Memphis',23,580075);
      Insert into SRC_OCIGGLL.SRC_CITY (CITY_ID,CITY,REGION_ID,POPULATION) values (1007,'New York City',22,124434);
      Insert into SRC_OCIGGLL.SRC_CITY (CITY_ID,CITY,REGION_ID,POPULATION) values (1008,'Boston',22,275581);
      Insert into SRC_OCIGGLL.SRC_CITY (CITY_ID,CITY,REGION_ID,POPULATION) values (1009,'Washington D.C.',22,688002);
    4. 在 OCI GoldenGate 部署主控台中,選取擷取名稱 (UAEXT) ,然後選取統計資料。確認已列出 SRC_OCIGGLL.SRC_CITY 與 10 個插入。

    5. 回到「總覽」畫面,選取 Replicat 名稱 (REP) ,然後選取統計資料。確認已列出 SRCMIRROR_OCIGGLL.SRC_CITY 與 10 個插入

工作 6:建立資料驗證資源

  1. 建立資料驗證伺服器部署

  2. 建立 2 個資料驗證代理程式部署

  3. 建立 GoldenGate 連線

  4. 將「任務 1」中建立的可承諾量連線指派給其中一個代理程式部署

  5. 將在任務 1 中建立的 ALK 連線指派給其他代理程式部署。

  6. 指定 GoldenGate 連線至伺服器部署。

  7. 部署變成作用中後,請複查資料驗證環境:

    1. 在伺服器部署的詳細資訊頁面上,選取啟動主控台

    2. 在導覽功能表中,選取連線

    3. 在「連線」頁面上,確認您的代理程式出現在清單中,且其狀態為「作用中」。

作業 7:建立群組與比較組

在伺服器部署中,建立比較組態:

  1. 在導覽功能表中,選取群組與比較組

  2. 在「群組和比較組」頁面上,選取建立

  3. 在「建立群組」和「比較組」的組態頁面中,依下列方式完成欄位,然後選取下一步

    1. 輸入名稱

    2. 來源目標連線的個別下拉式清單中選取。

    3. 來源目標目錄的個別下拉式清單中選取。

    4. 新增比較組

  4. 複查對應規則,然後選取下一步

  5. 複查對應頁面,然後選取產生比較組

  6. 儲存群組。

工作 8:建立和執行比較工作

  1. 在導覽功能表中,選取工作

  2. 在「工作 (Jobs)」頁面上,選取建立 (Create)

  3. 在「建立工作」頁面上,依下列方式完成欄位,然後選取送出

    1. 輸入工作的名稱

    2. 選取新增群組,選取在任務 7 中建立的群組,然後選取新增並儲存

  4. 在導覽功能表中,選取執行工作

  5. 在「執行工作 (Run Job)」頁面上,選取步驟 3 中建立的工作和預設設定檔,然後選取執行工作 (Run Job)

任務 9:分析結果

  1. 在導覽功能表中,選取監督工作

  2. 選取已完成的工作

  3. 選取您的工作以檢視其明細,然後驗證下列項目:

    • 未將任何資料列標示為不同步
    • 未報告遺漏或額外的列

在此階段,會同步來源與目標資料庫。

工作 10:介紹資料不一致

在本作業中,您可以使用 SRCMIRROR_OCIGGLL.SRC_CITY 表格,將受控制的不一致引入目標資料庫。

  1. 驗證目標的現有資料。在目標 ALK SQL 工作表中,輸入下列項目:

    SELECT CITY_ID, CITY, REGION_ID, POPULATION
    FROM SRCMIRROR_OCIGGLL.SRC_CITY
    WHERE CITY_ID BETWEEN 1000 AND 1009
    ORDER BY CITY_ID;
  2. 清除工作表,然後輸入下列內容以產生不相符的資料:

    UPDATE SRCMIRROR_OCIGGLL.SRC_CITY
    SET POPULATION = 999999
    WHERE CITY_ID = 1003;
    
    COMMIT;
  3. 清除工作表,然後輸入下列內容以導入遺漏的資料列:

    DELETE FROM SRCMIRROR_OCIGGLL.SRC_CITY
    WHERE CITY_ID = 1005;
    
    COMMIT;
  4. 清除工作表,然後輸入下列內容以導入額外的資料列:

    INSERT INTO SRCMIRROR_OCIGGLL.SRC_CITY (CITY_ID, CITY, REGION_ID, POPULATION)
    VALUES (1010, 'Test City', 99, 123456);
    
    COMMIT;
  5. 清除工作表,然後輸入下列內容以驗證導入的問題:

    SELECT CITY_ID, CITY, REGION_ID, POPULATION
    FROM SRCMIRROR_OCIGGLL.SRC_CITY
    WHERE CITY_ID BETWEEN 1000 AND 1010
    ORDER BY CITY_ID;

    您應注意下列事項:

    • CITY_ID 1003 的目標群組不正確
    • 遺漏 CITY_ID 1005
    • CITY_ID 1010 僅存在於目標中

任務 11:使用 Veridata 修復資料差異

現在來源與目標之間有一些資料差異,您可以重新執行比較並加以修復。

  1. 在「伺服器」建置主控台導覽功能表中,選取執行工作

  2. 選取您的「比較」工作,然後選取執行工作

  3. 在導覽功能表中,選取監督工作

  4. 選取「比較」工作即可檢視其詳細資訊。請確認下列事項:

    • 資料列被標示為不同步
    • 差異包括:
      • 缺少列
      • 額外資料列
      • 資料欄不相符
  5. 在「工作詳細資訊」頁面中,尋找 SRC_CITY=SRC_CITY,然後選取「比較組」名稱以檢視其詳細資訊。

  6. 在「比較組」詳細資訊中,選取不同步的資料列,然後複查差異。

  7. 選取修復

  8. 修復工作對話方塊中,選取修復所有不同步的資料列,然後選取提交

    這會建立將目標與來源同步的「修復工作」。

  9. 在導覽功能表中,選取監督修復工作。尋找修復工作並監控工作直到完成為止。

  10. 修復工作完成後,請選取該工作以檢視其詳細資料。請確認下列事項:

    • 已視需要更新、插入或刪除列。
    • 未發生錯誤。
  11. 重新執行比較。

    1. 在導覽功能表中,選取工作

    2. 選取您的「比較」工作,然後選取執行工作

    3. 回瀏覽至監督工作,然後等待工作完成。

    4. 工作完成後,請檢視其詳細資訊以確認下列項目:

      • 未將任何資料列標示為不同步
      • 沒有遺漏的資料列
      • 沒有額外的資料列
      • 沒有資料欄不相符

來源和目標資料集現在已完全同步。