Amazon Web Services ブログ

AWS DMS 検証のみのタスクによるデータ検証の最適化

本ブログは「Optimize data validation using AWS DMS validation-only tasks」を翻訳したものとなります。

AWS Database Migration Service (AWS DMS) は、データを Amazon Web Services (AWS) に効率的かつセキュアに移行するのに役立ちます。Oracle や SQL Server などの広く使用されている商用データベースから、MySQL や PostgreSQL などのオープンソースデータベースにデータを移行できます。また、 AWS DMS は、さまざまなサポートされているソースから AWS に移行する際にデータを検証する機能を提供します。データの整合性と正確性は、移行プロジェクトが成功するかどうかを左右する重要な要件の1つであり、お客様から頻繁にお伺いするポイントです。この記事では、 AWS DMS のデータ検証機能について詳しく説明します。その利点、設定、およびユースケースを探ります。

AWS DMS によるデータ検証

AWS DMS のデータ検証機能は、ソースからターゲットへのデータ移行が正確に行われていることを確認するのに役立ちます。 AWS DMS の移行タスクで 全ロードのみ (既存データの移行) の移行タイプを選択した場合、完全ロードが完了した直後にデータ検証が開始されます。完全ロード + CDC (既存データの移行と継続的な変更のレプリケーション) の移行では、完全ロードが完了した直後に検証が開始され、その後、変更データキャプチャ (CDC) による増分変更を継続的に比較します。CDC のみのタスクで検証が有効になっている場合、新しいデータの検証を開始する前に、テーブル内の既存のすべてのデータが検証されます。

データ検証中、 AWS DMS はソースの各行とターゲットの対応する行を比較し、行が同じデータを含んでいるかを確認し、不一致があればレポートします。列の値の比較方法はデータ型によって異なります。たとえば、大きなバイナリオブジェクト (LOB) 列の比較にチェックサム関数が使用されますが、他のデータ型の場合は実際の値が使用されます。

AWS DMS コンソールまたは AWS Command Line Interface (AWS CLI) を使用して、移行タスクでデータ検証機能を有効にできます。詳細については、 Migration Validation (Part 2) – Introducing Data Validation in AWS Database Migration Service を参照してください。また、移行やデータレプリケーションを実行せずに、データのプレビューと検証のみを行う 検証のみのタスク を作成できます。この検証では、ソースとターゲットの両方で追加のリソースが消費され、ネットワークリソースも追加で必要となります。また、ソースとターゲットのテーブルに主キーまたは一意のインデックスが必要です。AWS DMS 検証を使用する前に、その制限事項を確認することをお勧めします。

ソリューション概要

この投稿では、以下のトピックについて説明します。

  1. AWS DMS 検証のみのタスクのユースケース(リレーショナルデータベース)
  2. AWS DMS 検証のみのタスク の構成と監視方法
  3. 検証のみのタスク: フルロードと CDC の比較
  4. 検証のみのタスクの最適化方法
  5. 検証が失敗するケースの対処方法

AWS DMS 検証のみのタスクのユースケース(リレーショナルデータベース)

AWS DMS で検証のみのタスクを使用するいくつかの一般的なユースケースは次のとおりです。

  • データを移行せずに検証を実行する – 検証のみのタスクを使用すると、データを複製することなく、ソースとターゲットのデータを検証できます。これは、検証ルールと設定をテストするのに役立ちます。
  • 検証を移行タスクから分離する – 個別の検証のみのタスクを作成することで、既存の移行タスクに影響を与えることなく、データを独立して検証できます。これにより、検証失敗が移行をブロックするのを防ぎ、また別のレプリケーションインスタンス (RI) で検証のみのタスクを実行することもできます。さらに、この別の RI では新機能を利用するために異なる DMS バージョンを使うこともできます。
  • 検証失敗のトラブルシューティング – 移行タスクで検証が失敗した場合、進行中の移行タスクと分離されている検証のみのタスクを使用することで、特定の失敗を調査してトラブルシューティングしやすくなります。
  • スケジュールされた検証 – 検証のみのタスクを定期的に実行することで、変更されるソースとターゲットのデータを検証できます。これにより、継続的に実行されるタスクと比較してソースとターゲットデータベースインスタンスの負荷を軽減できます。
  • 特定の時点でデータ行が一致しないことを迅速に確認する – 本番稼働切り替えを行う前または切り替えの最中にフルロードの検証のみのタスクを実行することで、新しいターゲットエンドポイントにアプリケーションを切り替える前にデータを検証できます。
  • データ修復スクリプト – 検証が失敗したテーブル向けのデータ修復スクリプトを作成した場合、フルロードのバリデーションのみのタスクを実行すると、スクリプトが対処可能な問題を迅速に検知できます。

AWS DMS 検証のみのタスクをどのように構成して監視するか

AWS DMS コンソールを使用して検証専用のタスクを作成するには、AWS DMS タスクを作成する際に以下の設定を行います。

  1. TargetTablePrepMode を DO_NOTHING (検証専用タスクのデフォルト) に設定します。
  2. マイグレーションタイプを「既存のデータを移行する」または「データ変更のみをレプリケートする」に設定します。
  3. データ検証で「検証(データ移行なし)」を選択します。

または、 JSON エディタを使ってタスク設定を変更することができます:

"EnableValidation": true, 
"ValidationOnly": true,

データ検証が有効になっている場合、AWS DMS コンソールまたは Amazon CloudWatch検証の状態を監視できます。

テーブル内の一部のレコードがソースとターゲットで一致しない場合、検証状態は Mismatched records となり、ターゲットデータベースの awsdms_validation_failures_v1 テーブルで詳細を確認できます。このテーブルは、 ControlSchema で定義したスキーマまたはデータベースエンジンのデフォルトの場所に作成されます。レコードが ValidationSuspended または ValidationFailed 状態になった場合、 AWS DMS は同じテーブルに診断情報を書き込みます。

次のスクリーンショットは、 PostgreSQL の例(ターゲット)を示しています。

AWS DMS データ検証の監視の詳細については、Insights into AWS DMS resiliency and recovery scenarios with mitigations – Part 2 をご参照ください。

フルロードの検証のみ・ CDC の検証のみのタスク

前述のとおり、移行タイプには2種類あり、フルロードの検証のみのタスクと CDC の検証のみのタスクを作成できます。これら 2 種類のデータ検証プロセスと、主要なチューニング可能なパラメータについて、次のセクションで説明します。

フルロードの検証のみ

AWS DMS バージョン 3.4.6 以降では、フルロードの検証のみのタスクを使用すると、ソーステーブルとターゲットテーブルのすべての行を高速に比較し、検証エラーがあればすぐに報告し、検証が完了した後にタスクを停止します。

AWS DMS はデータを論理的にパーティション(デフォルトは 1 パーティションあたり 10,000 レコード)に分割し、複数の AWS DMS データ検証スレッド(デフォルトは 5 つ)を使用して対応するパーティション間のデータを比較します。データ検証エラーがある場合、ターゲットデータベースの制御テーブル (awsdms_control.awsdms_validation_failures_v1) にログが記録されます。次の図では、 Row n の列 coln の値が一致しないため、不一致レコードが報告されています。

次の表は、フルロードの検証タスクのみに関する重要なタスクパラメータを示しています。 AWS DMS のデータ検証タスクでサポートされているすべてのパラメータについては、「データ検証タスクの設定」を参照してください。

CDC の検証のみ

CDC の検証のみのタスクが開始されると、既存のデータを最初に検証し、次に CDC によって変更されたデータを検証し、不一致があれば報告します。また、継続的にレプリケーションされた変更を再検証します。 CDC の検証では、誤検出を防ぐために、失敗する前に不一致の行を再試行します。再試行を待つ時間は、タスク設定の RecordFailureDelayLimitInMinutes および RecordSuspendDelayInMinutes パラメータで設定された失敗再試行期間(分単位)に依存します。次の図では、時刻 T1 で、 AWS DMS 検証スレッドが Row n のデータ不一致を発見します。すぐに失敗を報告するのではなく、再試行し、進行中のデータ複製タスクが問題を修正することを期待します。

次の図の時間 T2 では、まだ障害再試行期間内ですが、 AWS DMS の検証スレッドが Row n のデータを再度比較し、データが一致していることを確認したためデータ検証の失敗は報告されません。 AWS DMS の検証タスクでは、新しいデータが見つかるとそれらをパーティションに分割し、データ検証スレッドを割り当てて、データを検証します。

次の表は、CDC 検証のみのタスクの重要なタスクパラメータを示しています。これは、前述の完全ロード検証のみのタスクで説明されたパラメータに加えて考慮する必要があります。 AWS DMS データ検証タスクでサポートされているすべてのパラメータについては、「データ検証タスクの設定」を参照してください。

どのように AWS DMS 検証のみのタスクを最適化するか

このセクションでは、 AWS DMS の検証のみのタスクのパフォーマンスを最適化できる複数の検証タスク設定について説明します。これらの設定は、本番環境で実装する前に検証環境でテストする必要があります。各検証タスクは独立しており、タスクごとに最適化が必要です。

  • ThreadCount: このパラメータは、 AWS DMS がデータ検証を実行する際に使用するスレッド数を指定します。デフォルトは 5 で、各スレッドは未検証のデータを処理して比較と検証を行います。より多くのスレッド数を設定すると、検証タスク全体のパフォーマンスが向上しますが、より多くのリソースがソースとターゲットのエンドポイントで消費されます。
  • PartitionSize: この設定は、各スレッドがソースとターゲットのインスタンスから読み取るレコード数を指定します。デフォルト値の 10,000 を増やすと、 AWS DMS が検証のためにより多くのレコードを読み取ることができますが、移行コンポーネントへの負荷が増加します。
  • RecordFailureDelayLimitInMinutes: このパラメータを使用すると、 AWS DMS が検証失敗を報告するまでの遅延を指定できます。通常、 AWS DMS はデータ変更がターゲットに複製されるまでの実際の遅延を許容するために、タスク待機時間の値を使用し、誤検出を防ぎます。この設定では、より高い値を定義できます。
  • ValidationQueryCdcDelaySeconds: これは、ソースとターゲットで最初の検証クエリが遅延する時間です。検証のみのタスクでは、デフォルト値は 180 秒です。ソースでの大量の更新により高い待機時間が発生する場合は、この値を大きくしてソースインスタンスへの再検証を減らすことができます。
  • FailureMaxCount: この設定は、タスクが中断される前の検証失敗の最大数を指定します。デフォルト値は 10,000 です。すべてのレコードを検証し続けたい場合は、この値をソーステーブルのレコード数より大きな値に設定します。一方、データの不一致を許容できない場合は、失敗が発生したときにタスクが迅速に中断されるように、より小さな値を使用できます。これにより、より厳格なデータ整合性チェックが行われます。
  • HandleCollationDiff: このオプションは、列の照合順序 (Collation) の違いがどのように処理されるかを制御します。デフォルトでは値は false で、列の照合順序の違いを無視します。これにより、データ検証で誤検出が発生する可能性があります。照合順序は、レコードの並び順やデータの比較方法を決定するため、データ検証の重要な側面です。たとえば、次の例は、文字列「 abcABC 」の ASCII 表現における大文字と小文字の区別のある並び替え順序と区別のない並び替え順序を示しています。

検証の失敗をどのように対処するか

このセクションでは、 AWS DMS の検証タスクで発生しうる、データ検証の失敗に関するいくつかの一般的なシナリオと、それらを修正する方法について説明します。

LOB が切り捨てられる場合

データベースをターゲットインスタンスに移行する際、 AWS DMS の移行タスク内で設定されている場合、 LOB データを含むデータをレプリケーションできます。 LOB データの移行のために、いくつかの構成可能な設定があります。デフォルトでは、 AWS DMS は制限付き LOB モードを使用し、それぞれの LOB の最大サイズは 32 KB です。デフォルトの構成を使用する場合、最大 LOB サイズを超えるデータはすべて切り捨てられます。

切り捨てられた LOB 列は、ソースとターゲットの値が異なるため、データ検証に失敗します。 CloudWatch ログで切り捨てられたログを検索することで、 LOB の切り捨てが発生していることを確認できます。切り捨てを回避するには、ソースデータベースの LOB サイズに合わせて最大 LOB サイズを設定します。 LOB サイズがわからない場合は、 inline LOB モード(エンドポイントがサポートしている場合)を選択して、小さな LOB と大きな LOB の両方を複製できます。検証専用タスクの ValidationPartialLobSize の値は、データ移行タスクの最大 LOB サイズと同じ値に設定することをお勧めします。

数値・タイムスタンプが切り捨てられる場合

数値とタイムスタンプのデータは、通常データベースエンジンによって異なるスケールと精度を持っており、明示的に定義されていない場合、それぞれのデフォルト値は異なります。以下では、数値とタイムスタンプに関する潜在的な問題と、それらを修正する方法を示す一般的な例をいくつか説明します。

Oracle データベースがソースの場合

Oracle データベースの移行において、数値データ型である NUMBER 型の移行でスケールと精度が明示的に指定されていない場合、 AWS DMS はデフォルトでデータを小数点 10 桁で切り捨てます。そのため、小数点 10 桁を超える既存のデータが移行される場合、ターゲットで数値が切り捨てられます。例えば、データ 123456.123456789012123456.1234567890 に切り捨てられます。データが切り捨てられるのを避けるためには、 移行タスクのエンドポイントの追加接続属性 (ECA) パラメータ NumberDataTypeScale に適切な値を設定します。デフォルト値は 10 ですが、この例では 12 に設定してデータ切り捨てを回避します。これらのパラメータ設定の詳細については、 AWS DMS のドキュメントを参照してください。

PostgreSQL がソース・ターゲットの場合

PostgreSQL から PostgreSQL への移行において、精度やスケールが定義されていない数値データ型の列にデータが格納されている場合、AWS DMS は全体で 28 桁、小数点 6 桁でデータを切り捨てます。切り捨てを回避するには、移行時に数値データを文字列型としてマッピングするために、ソースとターゲットの両エンドポイントの ECA に MapUnboundedNumericAsString=true を定義します。

タイムスタンプデータについて

Oracle は、 TIMESTAMP 型のデータ型で 1 秒あたり最大 9 桁の小数部 (= ナノ秒単位 ) をサポートしています。 SQL Server は、 TIME 型のデータ型で1秒あたり最大 7 桁の小数部をサポートしています。このデータが MySQL や PostgreSQL などのターゲットにマップされる場合、両方とも TIMESTAMP 型のデータ型で 1 秒あたり最大 6 桁の小数部をサポートします。その場合、ソースデータベース ( 例えば Oracle) で TIMESTAMP(7) から TIMESTAMP(9) と定義されたデータ型に対して、 AWS DMS のデータ検証タスクが不一致レコードを報告します。同じ問題が、 Oracle の TIMESTAMP WITH TIME ZONETIMESTAMP WITH LOCAL TIME ZONE など TIMESTAMP 型の別種、または SQL Server の DATEIME2DATETIMEOFFSET にも当てはまる可能性があります。データの切り捨てがビジネス上許容できる場合は、後で示すようにカスタム関数を使ってオーバーライドの検証ルールを設定できます。

トリガーやスケジューラによってターゲットのデータが更新される場合

AWS DMSはソースからターゲットデータベースにデータを移行し、レプリケーションによってデータを同期させます。 AWS DMS 以外で発生する変更は、データの不整合のリスクを高め、データ検証エラーの原因となる可能性があります。これらの変更の一部は、意図せずに発生します。例えば:

  • ターゲットでデータベーストリガーが有効になっている場合、 AWS DMS タスクがターゲットテーブルに DML による変更を加えるとデータが更新される可能性があります。ベストプラクティスとして、データ移行フェーズではトリガーを無効にし、カットオーバー移行のみ有効にすることが推奨されます。ターゲットが PostgreSQL の場合、パラメータ session_replication_role=replica を使ってトリガーと外部キー制約を無効にできます。
  • ターゲットデータベース上で実行されるスケジューラジョブがデータを変更する可能性があります。初期のスキーマ変換時に、スケジューラジョブもターゲットに移行できます。しかしながら、これらのジョブが有効になっていると、ターゲットのデータが変更されてデータ検証に影響を与え、複雑なトラブルシューティングが必要になる可能性があります。ベストプラクティスとして、ターゲットデータを変更する可能性のあるスケジューラジョブ(内部データベースのスケジューラジョブまたはアプリケーションの一部として予定されている外部ジョブ)を移行中は無効にすることが推奨されます。

文字セットと照合順序 (collation) の設定について

データ移行中、データは複数回デコードとエンコードされます。ソースデータベースからデータを読み取り、レプリケーションインスタンスでデータを処理し、最終的にターゲットデータベースのロケール設定に基づいてデータをターゲットデータベースに書き込みます。変換の際に、Unicode から Latin 文字セットなどの不適切な構成が設定されている場合、データ検証タスクは欠損の可能性がある変換を記録するために、これらを ValidationFailed として報告する可能性があります。
また、アクセント・ケースセンシティブは、移行タスクでデータエラーの原因となる可能性があります。例えば、ソースデータベースがアクセント・ケースセンシティブを持つように構成されており(これはデフォルトの動作です)、 NAME 列を主キーとするテーブルに AAAAaaaaáááá の 3 つのレコードがあるとします。これらのレコードがアクセントとケースを区別しない MySQL データベース (utf8mb4_0900_ai_ci の照合順序など) のようなターゲットデータベースに書き込まれると、重複キーエラーが発生します。これは、アクセントとケースの違いを無視して同じレコードとして扱われるためです。これらのレコードは、一意制約違反エラーにより、 awsdms_validation_failures_v1 コントロールテーブルに FAILURE_TYPE を MISSING_TARGET として表示されます。

変換ルールとフィルタールールの影響

AWS DMS には、データ移行の一環で既存のスキーマとデータを変換するための強力な変換ルールがあり、フィルター条件が満たされた場合にのみターゲットデータベースにデータを移行するためのフィルタールールもサポートされています。データ移行タスクで使用されるこれらのルールは、意図せずにターゲットデータベースでデータの不整合を引き起こす可能性があります。データ検証のみのタスクを作成する場合、これらのルールの副作用としてデータ検証の問題が発生しないように、同じ変換とフィルターのルールを使用することが重要です。データ検証のみのタスクに変換またはフィルターのルールを含める場合、 AWS DMS はまず規則を適用し、次にデータを検証し、不一致のレコードについて失敗を報告します。 例えば、移行タスクで、ソースの COL1 をターゲットの col2 に変更する変換ルールを設定したとします。しかし、同じ変換ルールがないデータ検証のみのタスクを作成した場合、 TargetTablePrepModeDO_NOTHING であるため、 AWS DMS は必要なテーブルメタデータを認識できません。このシナリオでは、 AWS DMS は COL1col2 を検証の対象から除外します。別のシナリオでは、データ移行にフィルターのルールを適用するが、データ検証のみのタスクではフィルターのルールを省略すると、レコードはソースデータベースに存在するが、フィルターのルールのために AWS DMS によってターゲットに移行されません。その結果、検証エラーが発生します。

データ検証でオーバーライドルールを活用する方法

データ検証中に、この投稿で説明されているようなさまざまな検証エラーが発生する可能性があります。たとえば、ソースとターゲットのエンジン間で文字セットが異なるため、同じデータが移行されているにもかかわらず、 RECORD_DIFF とともに Mismatched records エラーが発生する可能性があります。または、AWS DMS のデータ検証で使用される組み込み関数がソースデータベースのバージョンでサポートされていないことにより、 ValidationFailed として CloudWatchLogs に <No authorized routine named ‘HASH’ of type ‘FUNCTION’ having compatible arguments was found> や <pg_catalog.timezone(unknown, json)> などのエラーが表示される可能性があります。このような場合に備え、 AWS DMS のデータ検証では、マッピングルールの validation ルールタイプにオーバーライド検証関数を提供しています。この機能により、ソースとターゲットのエンジンでサポートされているデータベース関数を使用して、独自の検証ルールを追加できます。 たとえば、前述の Oracle から MySQL への移行におけるタイムスタンプデータの切り捨てケースでは、次のオーバーライドルールがカスタム関数を使用してデータを比較します。このルールは、 Oracleの to_char 関数を使用してソース列のタイムスタンプ値を YYYY-MM-DD HH:MM:SS.ffffff 形式に変換し、MySQLの date_format 関数を使用してターゲット列の値を同じ形式に変換します。

{
    "rule-type": "validation",
    "rule-id": "1",
    "rule-name": "1",
    "rule-target": "column",
    "object-locator": {
      "schema-name": "SCHEMA_NAME",
      "table-name": "TABLE_NAME",
      "column-name": "COLUMN_NAME"
    },
    "rule-action": "override-validation-function",
    "source-function": "to_char(cast(${column-name} as timestamp(6)), 'YYYY-MM-DD HH24:MI:SS.FF6')”
    "target-function": "date_format(${column-name}, '%Y-%m-%d %H:%i%:%s.%f')"
}

以下は、 IBM Db2 から PostgreSQL への移行時に特定の列のデータ長を比較する例です。

{
    "rule-type": "validation",
    "rule-id": "2",
    "rule-name": "2",
    "rule-target": "column",
    "object-locator": {
      "schema-name": "SCHEMA_NAME",
      "table-name": "TABLE_NAME",
      "column-name": "COLUMN_NAME"
    },
    "rule-action": "override-validation-function",
    "source-function": "length(${column-name})",
    "target-function": "length(${column-name})"
}

次の検証ルールは、ソースとターゲットの列をテキストに変換し、 UTF8 でエンコーディングし、 MD5 ハッシュを計算し、ハッシュを大文字に変換し、最終的な出力型を VARCHAR(64) に設定した後、比較します。これは、 PostgreSQL から PostgreSQL への移行など、可変のデータベース間で一貫性のある一意の識別子として比較するのに役立つ可能性があります。

{
  "rule-type": "validation",
  "rule-id": "3",
  "rule-name": "3",
  "rule-target": "column",
  "object-locator": {
    "schema-name": "SCHEMA_NAME",
    "table-name": "TABLE_NAME",
    "column-name": "COLUMN_NAME"
  },
  "rule-action": "override-validation-function",
  "source-function": "CAST (upper(md5(convert_to(CAST ('${column-name}' AS text), 'UTF8'))) AS VARCHAR(64))",
  "target-function": "CAST (upper(md5(convert_to(CAST ('${column-name}' AS text), 'UTF8'))) AS VARCHAR(64))"
}

AWS DMS は MD5 暗号化ハッシュを使用して、 SYS.DBMS_CRYPTO.HASH(TO_CLOB("COLUMN_NAME"), 2) などのLOBを検証します。ソースの Oracle で Federal Information Processing Standards (FIPS) (DPFIPS_140 = true) を有効にすると、バージョンによっては HASH_MD5 が機能しない可能性があります。この場合、 PostgreSQL 移行のために次のオーバーライドルールを検討できます。

{
  "rule-type": "validation",
  "rule-id": "4",
  "rule-name": "4",
  "rule-target": "column",
  "object-locator": {
    "schema-name": "SCHEMA_NAME",
    "table-name": "TABLE_NAME",
    "column-name": "COLUMN_NAME"
  },
  "rule-action": "override-validation-function",
  "source-function": "dbms_lob.getlength(${column-name})"
  "target-function": "coalesce(char_length(${column-name}),0)"
}

クリーンアップ

この投稿に沿ってテスト環境を作成した場合は、 AWS DMS リソースのクリーンアップ に記載された情報を使用して、この投稿で提案されたソリューションのテストに使用した環境を削除してください。

まとめ

この投稿では、 AWS DMS のデータ検証のみのタスクの活用、監視、最適化、および一般的なユースケースの処理方法を示しました。ソースとターゲットのデータベースとデータ移行の要件によっては、 AWS DMS のデータ検証のみのタスクを検討し、移行に高い信頼性を持つことができます。

本ブログについてご質問がある場合は、AWS サポートにお問い合わせください


投稿者について

Jay Shin / Database Migration Specialist in DMA (Database Migration Accelerator)
シンガポールを拠点として、クラウドネイティブのデータベースサービスを活用してお客様のデータベース移行とモダナイゼーションの加速を支援しています。

Donghua Luo / Senior RDS Specialist Solutions Architect
AWSクラウドのデータベースサービスを活用して、AWSのお客様がより高い柔軟性、スケーラビリティ、および回復力を実現できるよう支援しています。


Barry Ooi / Senior Database Specialist Solution Architect
AWSでのお客様のジャーニーの一環として、クラウドネイティブサービスを使用してデータプラットフォームを設計、構築、実装することが専門です。データ分析とデータの可視化に興味を持っています。