SE の雑記

SQL Server の情報をメインに Microsoft 製品の勉強内容を日々投稿

SQL Database のデータベースをリージョン間で移行するにはどうするか??

without comments

Windows Azure Advent Calendar 2013 8 日目の内容になります。

今年の大きな話題として、Azure の日本のデータセンターが発表されました。
Windows Azureデータセンターを日本国内2拠点に設置へ
Windows Azureの国内リージョンは来年「2014年前半」に開始予定、日本マイクロソフトが明らかに

今までアジアだと香港 (東アジア) / シンガポール (東南アジア) のデータセンターを使うことが多かったのかと思いますが、日本のデータセンターができると東日本サブリージョン (東日本 : Japan East) と、西日本サブリージョン (西日本 : Japan West) を使うことが多くなってくるのかと思います。
# Windows Azure Datacenter IP Ranges には Japan East / Japan West としてすでに記載されているようですね。

これにより、今までは海外のデータセンターに配置していた SQL Database のデータベースを国内に持ってきたい (データセンター / 地域 (リージョン間で移動)) というニーズが発生することがあるかと思います。

この時のどのような方法がとれるのか少し考えてみました。
基本的な情報については Windows Azure SQL データベースにおけるビジネス継続性 が参考になるかと。

■データベースの複製を作成する方法


SQL Database にはデータベースの複製を作成するための方法がいくつかあります。
それぞれのどの範囲で複製ができるかをまとめると以下のようになるのかなと。
# 間違っていたら教えてください…。

  サーバー内 サーバー間 データセンター間 サブスクリプション間
DATABASE COPY ×
DATA Sync
BacPac
SQL Database MW
スクリプトの生成

 

■DATABASE COPY

データベースの複製をするには DATABASE COPY が一番確実かと思います。
DATABASE COPY は内部で取得されているバックアップ + 以降のトランザクションをレプリケートする方式になっており、トランザクションの一貫性が保証された状態のデータの複製が作成できることになっているかと。
# 詳細は Windows Azure SQL データベースにおけるビジネス継続性 に書かれています。

ただし、同一のデータセンター間でないとコピーができないので、リージョン間の移行では使うことができないのですが…。
# 同一センター内の異なるサブスクリプション間はできるようなのですが。

■DATA Sync

Data Sync については同期に必要なテーブルやトリガーが作成されるため、既存のデータベースへの変更が入ります。
# トリガーベースで最少 5 分間隔だったはずですので、多少データもずれるのかなと。

また、Data Sync では同期できないデータ型がありますので、事前に全項目が同期可能なようにテーブルを設計する必要があります。

■BacPac / SQL Database MW

BacPac / MW については BCP を使用して、データをエクスポートしており、テーブルを上から順にエクスポートしているので、最初と最後のテーブルでは格納されている時系列にずれが発生することがあるかと思います。

BacPac を使用する場合には、Native 形式でデータがエクスポートされるようにするために、SQL Serve r2012 SP1 の DAC Fx を使用するとよいかと。
# それ以前のバージョンはデータを JSON 形式で出力していましたが SP1 以降は Native 形式の BCP でエクスポートしますので、効率が良くなっています。
sqlpackage と AzCopy を使用した SQL Database のデータ退避

■スクリプトの生成

スクリプトを生成する際にはスキーマのみ / スキーマとデータ / データのみが選択でき、データを含めた形でスクリプトを作成することができます。
データは INSERT 文になるはずですので、今回のような移行ですとあまり使わないかと。
image

 

■移行にはどの方法を使う??


トランザクションの一貫性を保った状態のデータベースを移行したい場合には、

  1. DATABASE COPY でデータベースのコピーを取得
  2. COPY したデータベースに対して、BacPac / MW を使用してデータベースを移行

がいいのかなと思います。
DATABASE COPY はバックアップをベースにコピーを作成し、そこからトランザクションの同期を行います。
バックアップはトランザクションの一貫性が保障された状態のものになりますの
で、データベースの静止点をベースにデータを移行することができます。

DB への更新が止められる場合には、

  1. BacPac / MW を使用してデータベースを移行
    # 自動エクスポートでエクスポートした BacPac を使用して移行してもよいかもしれません

を使うことができます。
データの更新が行われていなければ、すべてのテーブルを同時にエクスポートできなくてもテーブル間の一貫性が保障されますので、データベースのコピーで静止点を作らなくても移行が可能です。

また、BacPac や MW を使用した移行はデータベースが使用されている状態でも実施できますが、トランザクションの一貫性や既存 DB への負荷 (BCP でデータを抜くため、読み取り負荷がかかる) を考慮して選択する必要があるかと。

DataSync は既存 DB の変更が入ってしまいますので今回は使わない想定で。

今回は、

  1. DATABASE COPY でデータベースのコピーを取得
  2. COPY したデータベースに対して、BacPac を使用してデータベースを移行

でリージョン間を移行したいと思います。
この方法であれば、直接 BacPac を使用した場合も網羅できますので。

 

■リージョン間でデータベースを移行


今回は以下のような、異なるサブスクリプション / リージョンに SQL Database を作成しています。

image

現在は [dpwyfz8a9g] に AdventureWorks2012 を配置しており、これを異なるデータセンターにある [y9jhmc1o5i] に移行したいと思います。
# 米国東部 → 東アジア

image

まずはデータベースコピーでデータベースの静止点を作成します。

CREATE DATABASE AdventureWorks2012_20131208
AS COPY OF AdventureWorks2012

 

コピーが完了したかどうかは以下のクエリで確認ができます。

[COPYING] の状態はコピー中になりますので [ONLINE] になるまで待ちます。

SELECT name, state, state_desc
FROM sys.databases

image

以下のようなクエリで確認してもよいかもしれないですね。

SELECT database_id, start_date,modify_date,percent_complete, replication_state_desc
FROM sys.dm_database_copies

データベースのコピーが完了したらこれを移行します。

image

SSMS からデータベースを右クリックするとタスクから [SQL Azure へのデータベースの配置] を実行することができます。

image

これは、DACFx を使用して Bacpac を作成し、SQL Database へ配置するものになります。

これについては SQL Database 間でも実行できますので、この機能を使用することでリージョン間の移行が行えます。

移行先として東アジアのサーバーを選択して配置を実行します。

image

そうすると以下のような処理が行われます。

  1. ローカルに移行元のデータを BacPac として作成
  2. 作成した BacPac を移行先にインポート

正常に終了すればデータベースの移行が行われた状態になります。

image

データのサイズが大きい場合には、BacPac の作成とインポートは [データ層アプリケーションの抽出] と [データ層アプリケーションのインポート] に分けて、どれくらいの時間が必要となるかを計測してもよいかと思います。

これでデータセンター間の移動はできたので残りは後処理を実施します。

まずはデータベース名の変更をします。

コピーしたデータベースを移行していますので、データベースの名称がコピー後のものになってしまっています。

image

これを正規の名称に変更します。

ALTER DATABASE AdventureWorks2012_20131208
MODIFY NAME = AdventureWorks2012

 

次にログインのパスワードを再設定します。

BacPac では対象のデータベースで必要となるログインも移行してくれるのですが、パスワードがうまく連携されていないような雰囲気がありました。

# やり方が悪いだけかもしれませんが。

そこでパスワードを再設定します。

今回は [AWUser] というログインを事前に移行元に作成しており、それが移行先にも BacPac で作成されています。

このログインに対してパスワードを設定します。

ALTER LOGIN AWUser
WITH PASSWORD='<パスワード>'

 

必要に応じてログインとデータベースユーザーの再マップの方法も思えておくとよいかと。

BacPac からの移行では再マッピングは不要なはずですが。

# BacPac や MW で移行した場合は、ログインを新規に作成していますので、ログインにマッピングされていないユーザーはいないなずなので。

-- 対象のデータベースでクエリを実行
ALTER USER AWUser
WITH LOGIN = AWUser


これで移行は完了です。

今回はデータベースの部分のみについて書いていますが、実際にはこの後にアプリケーション側の接続文字列の変更が発生 (サーバー名が変わっているので) しますので、これについても効率的に設定を変更できる方法を考慮する必要が出てきます。

今回はローカルを BacPac の保存先として使用していますが、SSMS では Azure ストレージに直接接続できますので、 BacPac をインポート (移行) することも可能です。

image

トランザクションの一貫性のずれが多少発生していても問題ないまたは、更新が一切かからないようにすることができるのであれば、自動エクスポートによりストレージにエクスポートされた BacPac を使用して移行することも可能ですので、ケースに応じて最適な格納場所を使用するとよいかと思います。

# 自動エクスポートの場合は BacPac を作成する手間が省けますので移行時間の短縮ができるかと。

また、場所に応じてレイテンシーの差等が出てくるかと思いますので、どこにある BacPac をインポートするのが効率的かを検討するとよいかもしれないですね。

 


今回は BacPac を使用しましたが SQL Database Migration Wizard を使用しても同じことはできます。

BacPac の場合はデータベース全体ですが、MW の場合はテーブルを絞り込むことができますので、特定のテーブルのみを移行したいというような要件がある場合には MW を選択するとよいかと思います。

BacPac も MW もデータの移行には Native 形式の BCP が使用されていますので、データの基本的な移行方法に差はないかと。

# スキーマの移行についてはスクリプトベースが Dac Fx の形式かの違いはあります。

リトライ処理の実装等が違っているのでしょうがこの辺はデータベースのサイズにも応じてきますので、できるだけ本番に近いデータでこの手順が適用できるかを試すとよいのかもしれないですね。

SQL Database / SQL Server Management Studio の標準機能を使用してリージョン間の移行をすることができますので、本投稿が日本にデータセンターができた場合の方針の一助となれば幸いです。

 

それでは、8 日目の Windows Azure Advent Calendar 2013 の投稿はこの辺で。

明日は JAZUG コアメンバーの割と普通さんが Advent Calendar に投稿してくださいますのでお楽しみに!!

Written by Masayuki.Ozawa

12月 8th, 2013 at 12:03 am

Leave a Reply