プロジェクト間でデータを移動する

このページでは、マネージド インポート機能とマネージド エクスポート機能を使用して Firestore のデータをプロジェクト間で移動する方法を説明します。これは、開発環境を設定する場合やアプリを他のプロジェクトに永久的に移行する場合に役立ちます。このページの例では、ソース プロジェクトからデータをエクスポートし、そのデータを宛先プロジェクトにインポートする方法を示します。プロジェクト間でデータを移動する手順は次のとおりです。

  1. ソース プロジェクトのデータを保持する Cloud Storage バケットを作成します。
  2. ソース プロジェクトのデータをバケットにエクスポートします。
  3. 宛先プロジェクトにバケットから読み取りを許可する権限を付与します。
  4. バケットのデータを宛先プロジェクトにインポートします。

準備

マネージド エクスポート / インポート サービスを使用するには、事前に次のタスクを完了する必要があります。

  1. ソース プロジェクトと宛先プロジェクトの両方で課金を有効にします。エクスポート機能とインポート機能を使用できるのは、課金が有効になっている Google Cloud プロジェクトのみです。
  2. ソース プロジェクトと宛先プロジェクトで必要な IAM の権限がアカウントに付与されていることを確認します。両方のプロジェクトのプロジェクト オーナーである場合は、アカウントに必要な権限が付与されています。それ以外の場合は、次の IAM ロールで Firestore のエクスポートとインポート オペレーションに必要な権限を付与します。

    OwnerCloud Datastore Owner、または Cloud Datastore Import Export Admin

    プロジェクト オーナーがアクセスの許可の手順に従ってこれらの役割のいずれかを付与します。

  3. 次のいずれかの方法で gcloud コマンドライン ツールを設定し、プロジェクトに接続します。

  4. 新しいプロジェクトのインデックスを設定します。複合インデックスは、ソース プロジェクトと宛先プロジェクト間で一致する必要があります。各ドキュメントを何度も処理する必要がないように、まずインデックスを設定する必要があります。

ソース プロジェクトからデータをエクスポートする

データをエクスポートするには、Firestore エクスポート ファイル用の Cloud Storage バケットを作成し、エクスポート オペレーションを開始します。

Cloud Storage バケットの作成

Firestore データベースと同じロケーションに Cloud Storage バケットを作成します。データベースのロケーションを確認するには、プロジェクトのロケーションの設定をご覧ください。エクスポート / インポート オペレーションには、リクエスト元による支払いバケットは使用できません。

Cloud Storage バケットがソース プロジェクト内に存在しない場合、ソース プロジェクトのデフォルトのサービス アカウントに、バケットへのアクセス権を付与する必要があります。各 Google Cloud プロジェクトには、PROJECT_ID@appspot.gserviceaccount.com という名前のデフォルトのサービス アカウントが自動的に作成されています。Firestore のエクスポート オペレーションでは、Cloud Storage バケット オペレーションの承認にこのデフォルトのサービス アカウントが使用されます。デフォルトのサービス アカウントにソースバケットへのアクセス権を付与するには、Storage Admin 役割を付与します。

Cloud Shell で利用可能な gsutil ツールを使用すると、このロールを付与できます。

Cloud Shell の起動

gsutil iam ch serviceAccount:[service-PROJECT_NUMBER]@gcp-sa-firestore.iam.gserviceaccount.com :roles/storage.admin\
gs://[BUCKET_NAME]@

Google Cloud Console でこのロールを付与することもできます。

書き込みオペレーションを無効にする(省略可)

エクスポート オペレーションの実行中にアプリがデータベースへの書き込みを続けている場合、それらの書き込みのすべてをエクスポート ファイルにキャプチャできるわけではありません。一貫した状態からデータをエクスポートするには、セキュリティ ルールを更新し、Admin SDK 操作を停止することにより、データベースへの書き込みを無効にします。

  1. セキュリティ ルールを更新する

    Firestore コンソールの [ルール] タブで、すべての書き込みを拒否するようにソース プロジェクトのセキュリティ ルールを更新します。例:

      // Deny write access to all users under any conditions
      service cloud.firestore {
        match /databases/{database}/documents {
          match /{document=**} {
            allow write: if false;
          }
          // Reads do not affect export operations
          // Add your read rules here
        }
      }
    
  2. Admin SDK からの書き込みを停止する

    セキュリティ ルールでは、Firebase Admin SDK または Google Cloud サーバー クライアント ライブラリを使用して作成された特権サーバー環境からの書き込みは阻止されません。必ず、サーバーをシャットダウンまたは更新して、管理サーバーからの書き込みオペレーションを停止してください。

エクスポート オペレーションを開始する

ソース プロジェクトからデータをエクスポートするには、gcloud firestore export コマンドを使用します。すべてのデータをエクスポートすることも、特定のコレクションのみをエクスポートすることもできます。[SOURCE_BUCKET] を該当する Cloud Storage バケットの名前に置き換えます。

すべてのデータをエクスポートする
gcloud firestore export gs://[SOURCE_BUCKET] --async
特定のコレクションをエクスポートする
gcloud firestore export gs://[SOURCE_BUCKET] --collection-ids=[COLLECTION_ID_1],[COLLECTION_ID_2] --async

エクスポート オペレーションの outputURIPrefix は後で使用するため、メモしておきます。デフォルトでは、Firestore はタイムスタンプに基づいてエクスポート ファイルにプレフィックスを追加します。

outputUriPrefix: gs://[SOURCE_BUCKET]/2019-03-05T20:58:23_56418

エクスポート オペレーション実行時に、firestore operations list コマンドでオペレーションの進行状況を表示できます。

gcloud firestore operations list

宛先プロジェクトにデータをインポートする

次に、宛先プロジェクトに Firestore のデータファイルへのアクセス権を付与し、インポート オペレーションを開始します。

宛先プロジェクトにデータファイルへのアクセス権を付与する

インポート オペレーションを開始する前に、宛先プロジェクトが Firestore のデータファイルにアクセスできることを確認する必要があります。

データファイルをローカル バケットに移動する

ソースバケットのロケーションが宛先プロジェクトの Firestore のロケーションと異なる場合は、データファイルを宛先プロジェクトと同じロケーションに存在する Cloud Storage バケットに移動する必要があります。

バケットの移動と名前変更の手順に従ってデータファイルを他の Cloud Storage バケットに移動します。以下のすべての手順で、新しいバケットを [SOURCE_BUCKET] として使用します。

プロジェクトのサービス アカウントにソースバケットへのアクセス権を付与する

ソースバケットが宛先プロジェクト内に存在しない場合、宛先プロジェクトのデフォルトのサービス アカウントに、ソースバケットへのアクセス権を付与する必要があります。デフォルトのサービス アカウントの名前は、[DESTINATION_PROJECT_ID]@appspot.gserviceaccount.com です。デフォルトのサービス アカウントにソースバケットへのアクセス権を付与するには、バケットにアクセスするための適切な権限を付与します。

Cloud Shell で入手可能な gsutil ツールを使用して必要なロールを付与できます。

Cloud Shell を起動

gsutil iam ch serviceAccount:[DESTINATION_PROJECT_ID]@appspot.gserviceaccount.com:legacyBucketReader,legacyObjectReader \
gs://[SOURCE_BUCKET]

Google Cloud Console でこのロールを付与することもできます。

インポート オペレーションを開始する

インポート オペレーションを開始する前に、gcloud が正しいプロジェクトに構成されていることを確認します。

gcloud config set project [DESTINATION_PROJECT_ID]

gcloud firestore import コマンドを使用して、ソースバケットのデータを宛先プロジェクトにインポートします。

gcloud firestore import gs://[SOURCE_BUCKET]/[EXPORT_PREFIX] --async

[EXPORT_PREFIX] は、エクスポート オペレーションの outputUriPrefix のプレフィックスと一致します。例:

gcloud firestore import gs://[SOURCE_BUCKET]/2019-03-05T20:58:23_56418 --async

エクスポート オペレーション実行時に、firestore operations list コマンドでオペレーションの進行状況を表示できます。

gcloud firestore operations list