コンテンツにスキップ

Cloudflareリソースのインポート

Terraformについて理解しておくべき重要な点は、Terraformは自ら作成した構成や、後から明示的に指示された構成のみを管理できるということです。この制限の理由は、Terraformが管理するリソースに対して権威を持つことを期待しているからです。Terraformは、どのリソースを制御しているか、またそれらがどのような状態にあるかを理解するために、2種類のファイルに依存しています。Terraformは以下の情報から、いつ、どのように変更を行うかを判断します。

  • Terraformが管理するリソースの構成を定義する構成ファイル.tfで終わるファイル)。これはチュートリアルのステップで扱ったものです。
  • あなたの構成ファイルで定義されたリソース名(例えば、cloudflare_load_balancer.www-lb)をCloudflareに存在するリソースにマッピングするローカル状態ファイル

Terraformがチュートリアルで説明されているようにCloudflareのAPIに新しいリソースを作成するために呼び出しを行うと、そのIDを状態ファイルに永続化します。デフォルトでは、Terraformはあなたのディレクトリ内のterraform.tfstateファイルを使用しますが、これもリモートロケーションにすることができます。これらのIDは、terraform planterraform applyを呼び出すときに後で参照され、更新されます。

他の手段(例えば、Cloudflareダッシュボードにログインするか、api.cloudflare.comcurlコールを行う)でCloudflareを構成した場合、Terraformはまだ状態ファイルにこれらのリソースIDを持っていません。この既存の構成を管理するには、まず構成をあなたの構成ファイルに再現し、その後、リソースIDとリソース名を提供して個別にリソースをインポートする必要があります。

cf-terraforming

cf-terraformingは、既存のCloudflare顧客がTerraformを使い始めるのを助けます。現在、cf-terraformingは、指定されたタイプのすべてのリソースをアカウントおよび/またはゾーンから取得することによって、Terraform構成状態を生成するのを助けます。

インストール

始める前に、cf-terraformingをインストールする必要があります。

macOSでHomebrewを使用している場合は、ターミナルを開いて以下のコマンドを実行します。

Terminal window
brew tap cloudflare/cloudflare
brew install cloudflare/cloudflare/cf-terraforming

別のOSを使用している場合は、cf-terraforming GitHubリポジトリから最新のリリースをダウンロードしてください。

ヘルプファイルを表示するには、cf-terraformingまたはcf-terraforming -hを実行します。

基本的な使用法

cf-terraformingを使用するには、以下の項目を指定します。

  1. 実行するコマンド(例えば、generateまたはimport)。
  2. あなたのCloudflareユーザーのメールアドレス - --emailまたは-e
  3. あなたのCloudflare APIトークン - --tokenまたは-t
  4. リソースを取得するアカウントおよび/またはゾーン - --account/--zoneまたは-a/-z
  5. 構成を生成するCloudflareリソース。

サポートされているリソースのリストは、Terraform READMEで確認できます。

既存のCloudflareリソースをインポート

Terraformで既存のCloudflareリソース(例えば、DNSレコード)を管理し始めるには、以下が必要です。

  • そのリソースのTerraform構成(.tfファイルで定義)
  • そのリソースの状態に関するTerraform状態ファイル(.tfstateファイルで定義)

cf-terraformingでTerraform構成を生成

Terraform構成ファイルが定義されていない場合は、以下のようにproviderブロックを定義する必要があります。

provider 'cloudflare' {
# Cloudflareのメールは$CLOUDFLARE_EMAILに保存
# CloudflareのAPIトークンは$CLOUDFLARE_API_TOKENに保存
}

資格情報は環境変数またはソースファイルにチェックインされていないterraform自動変数に保存しておくことを忘れないでください。

cf-terraforming generateを呼び出して、Terraformで管理したいゾーンのDNSレコードのTerraform構成を生成します。

Terminal window
cf-terraforming generate --email $CLOUDFLARE_EMAIL --token $CLOUDFLARE_API_TOKEN -z 1109d899a5ff5fd74bc01e581693685b --resource-type cloudflare_record > importing-example.tf

出力をimporting-example.tfファイルにリダイレクトしていなかった場合、標準出力(ターミナルウィンドウ)に表示される結果は以下のようになります。

resource "cloudflare_record" "terraform_managed_resource_3c0b456bc2aa443089c5f40f45f51b31" {
name = "@"
type = "A"
ttl = 1
proxied = true
value = "192.0.2.1"
zone_id = "1109d899a5ff5fd74bc01e581693685b"
}
resource "cloudflare_record" "terraform_managed_resource_5e10399a590a45279f09aa8fb1163354" {
name = "www"
type = "CNAME"
ttl = 1
proxied = true
value = "mitigateddos.net"
zone_id = "1109d899a5ff5fd74bc01e581693685b"
}
resource "cloudflare_record" "terraform_managed_resource_de1cb74bae184b569bb7f83fefe72248" {
name = "a123"
type = "NS"
ttl = 300
proxied = false
value = "rafe.ns.cloudflare.com"
zone_id = "1109d899a5ff5fd74bc01e581693685b"
}
resource "cloudflare_record" "terraform_managed_resource_5799bb01054843eea726758f935d2aa2" {
name = "a123"
type = "NS"
ttl = 300
proxied = false
value = "terin.ns.cloudflare.com"
zone_id = "1109d899a5ff5fd74bc01e581693685b"
}

この時点でterraform planを呼び出すと、これらのリソースが存在しないかのように作成しようとします。なぜなら、ローカル状態ファイルには存在しないからです。

Terminal window
terraform plan
Terraform used the selected providers to generate the following execution plan.
Resource actions are indicated with the following symbols:
+ create
Terraform will perform the following actions:
# cloudflare_record.terraform_managed_resource_3c0b456bc2aa443089c5f40f45f51b31 will be created
+ resource "cloudflare_record" "terraform_managed_resource_3c0b456bc2aa443089c5f40f45f51b31" {
+ id = (known after apply)>
+ created_on = (known after apply)
+ domain = "mitigateddos.net"
+ hostname = (known after apply)
+ metadata = (known after apply)
+ modified_on = (known after apply)
+ name = "mitigateddos.net"
+ proxiable = (known after apply)
+ proxied = true
+ ttl = 1
+ type = "A"
+ value = "192.0.2.1"
+ zone_id = "1109d899a5ff5fd74bc01e581693685b"
}
# cloudflare_record.terraform_managed_resource_5e10399a590a45279f09aa8fb1163354 will be created
+ resource "cloudflare_record" "terraform_managed_resource_5e10399a590a45279f09aa8fb1163354" {
+ id = (known after apply)
+ created_on = (known after apply)
+ domain = "mitigateddos.net"
+ hostname = (known after apply)
+ metadata = (known after apply)
+ modified_on = (known after apply)
+ name = "www.mitigateddos.net"
+ proxiable = (known after apply)
+ proxied = true
+ ttl = 1
+ type = "CNAME"
+ value = "mitigateddos.net"
+ zone_id = "1109d899a5ff5fd74bc01e581693685b"
}
# cloudflare_record.terraform_managed_resource_de1cb74bae184b569bb7f83fefe72248 will be created
+ resource "cloudflare_record" "terraform_managed_resource_de1cb74bae184b569bb7f83fefe72248" {
+ id = (known after apply)
+ created_on = (known after apply)
+ domain = "mitigateddos.net"
+ hostname = (known after apply)
+ metadata = (known after apply)
+ modified_on = (known after apply)
+ name = "a123.mitigateddos.net"
+ proxiable = (known after apply)
+ proxied = false
+ ttl = 300
+ type = "NS"
+ value = "rafe.ns.cloudflare.com"
+ zone_id = "1109d899a5ff5fd74bc01e581693685b"
}
# cloudflare_record.terraform_managed_resource_5799bb01054843eea726758f935d2aa2 will be created
+ resource "cloudflare_record" "terraform_managed_resource_5799bb01054843eea726758f935d2aa2" {
+ id = (known after apply)
+ created_on = (known after apply)
+ domain = "mitigateddos.net"
+ hostname = (known after apply)
+ metadata = (known after apply)
+ modified_on = (known after apply)
+ name = "a123.mitigateddos.net"
+ proxiable = (known after apply)
+ proxied = false
+ ttl = 300
+ type = "NS"
+ value = "terin.ns.cloudflare.com"
+ zone_id = "1109d899a5ff5fd74bc01e581693685b"
}
Plan: 4 to add, 0 to change, 0 to destroy.
------------------------------------------------------------------------
Note: You didn't use the -out option to save this plan, so Terraform can't
guarantee to take exactly these actions if you run "terraform apply" now.

これを修正するには、Cloudflareからこれらのリソースの実際の状態をTerraform状態ファイル(.tfstate)にインポートする必要があります。

Terraform状態にリソースをインポート

cf-terraformingを使用すると、構成中にインポートしたのと同じリソースのローカル状態(.tfstateファイル)をインポートできます。

cf-terraforming import ...を実行すると、手動で実行する必要があるterraform import ...コマンドのリストが得られます。これは現在手動のプロセスですが、将来的には自動化される可能性があります。

  1. 以下のコマンドを実行します。

    Terminal window
    cf-terraforming import --resource-type "cloudflare_record" --email $CLOUDFLARE_EMAIL --key $CLOUDFLARE_API_KEY --zone $CLOUDFLARE_ZONE_ID
  2. 出力に含まれる各terraform import ...コマンドをコピーして実行します。Terraformは各リソースを個別にTerraform状態にインポートします。

例えば、最初のコマンド(cf-terraforming import ...)の出力に以下のterraformコマンドが含まれていた場合:

terraform import cloudflare_record.terraform_managed_resource_3c0b456bc2aa443089c5f40f45f51b31 1109d899a5ff5fd74bc01e581693685b/3c0b456bc2aa443089c5f40f45f51b31
terraform import cloudflare_record.terraform_managed_resource_5e10399a590a45279f09aa8fb1163354 1109d899a5ff5fd74bc01e581693685b/d09d916d059aa9fc8cb54bdd49deea5f
terraform import cloudflare_record.terraform_managed_resource_de1cb74bae184b569bb7f83fefe72248 1109d899a5ff5fd74bc01e581693685b/8d6ec0d02c5b22212ff673782c816ef8
terraform import cloudflare_record.terraform_managed_resource_5799bb01054843eea726758f935d2aa2 1109d899a5ff5fd74bc01e581693685b/3766b952a2dda4c47e71952aeef33c77

各コマンドをターミナルで個別に実行します。

Terminal window
terraform import cloudflare_record.terraform_managed_resource_3c0b456bc2aa443089c5f40f45f51b31 1109d899a5ff5fd74bc01e581693685b/3c0b456bc2aa443089c5f40f45f51b31
cloudflare_record.terraform_managed_resource_3c0b456bc2aa443089c5f40f45f51b31: Importing from ID "1109d899a5ff5fd74bc01e581693685b/3c0b456bc2aa443089c5f40f45f51b31"...
cloudflare_record.terraform_managed_resource_3c0b456bc2aa443089c5f40f45f51b31: Import complete!
Imported cloudflare_record [id=3c0b456bc2aa443089c5f40f45f51b31]
cloudflare_record.terraform_managed_resource_3c0b456bc2aa443089c5f40f45f51b31: Refreshing state... [id=3c0b456bc2aa443089c5f40f45f51b31]
Import successful!
The resources that were imported are shown above. These resources are now in
your Terraform state and will henceforth be managed by Terraform.
Terminal window
terraform import cloudflare_record.terraform_managed_resource_5e10399a590a45279f09aa8fb1163354 1109d899a5ff5fd74bc01e581693685b/d09d916d059aa9fc8cb54bdd49deea5f
cloudflare_record.terraform_managed_resource_5e10399a590a45279f09aa8fb1163354: Importing from ID "1109d899a5ff5fd74bc01e581693685b/d09d916d059aa9fc8cb54bdd49deea5f"...
cloudflare_record.terraform_managed_resource_5e10399a590a45279f09aa8fb1163354: Import complete!
Imported cloudflare_record [id=d09d916d059aa9fc8cb54bdd49deea5f]
cloudflare_record.terraform_managed_resource_5e10399a590a45279f09aa8fb1163354: Refreshing state... [id=d09d916d059aa9fc8cb54bdd49deea5f]
Import successful!
The resources that were imported are shown above. These resources are now in
your Terraform state and will henceforth be managed by Terraform.
Terminal window
terraform import cloudflare_record.terraform_managed_resource_de1cb74bae184b569bb7f83fefe72248 1109d899a5ff5fd74bc01e581693685b/8d6ec0d02c5b22212ff673782c816ef8
cloudflare_record.terraform_managed_resource_de1cb74bae184b569bb7f83fefe72248: Importing from ID "1109d899a5ff5fd74bc01e581693685b/8d6ec0d02c5b22212ff673782c816ef8"...
cloudflare_record.terraform_managed_resource_de1cb74bae184b569bb7f83fefe72248: Import complete!
Imported cloudflare_record [id=8d6ec0d02c5b22212ff673782c816ef8]
cloudflare_record.terraform_managed_resource_de1cb74bae184b569bb7f83fefe72248: Refreshing state... [id=8d6ec0d02c5b22212ff673782c816ef8]
Import successful!
The resources that were imported are shown above. These resources are now in
your Terraform state and will henceforth be managed by Terraform.
Terminal window
terraform import cloudflare_record.terraform_managed_resource_5799bb01054843eea726758f935d2aa2 1109d899a5ff5fd74bc01e581693685b/3766b952a2dda4c47e71952aeef33c77
cloudflare_record.terraform_managed_resource_5799bb01054843eea726758f935d2aa2: ID "1109d899a5ff5fd74bc01e581693685b/3766b952a2dda4c47e71952aeef33c77" からインポート中...
cloudflare_record.terraform_managed_resource_5799bb01054843eea726758f935d2aa2: インポート完了!
インポートされた cloudflare_record [id=3766b952a2dda4c47e71952aeef33c77]
cloudflare_record.terraform_managed_resource_5799bb01054843eea726758f935d2aa2: 状態を更新中... [id=3766b952a2dda4c47e71952aeef33c77]
インポート成功!
インポートされたリソースは上記に示されています。これらのリソースは現在
あなたの Terraform ステートにあり、以後 Terraform によって管理されます。

terraform plan を実行すると、Terraform が cloudflare_record リソースを再作成しようとしなくなることに気付くでしょう:

Terminal window
terraform plan | grep changes
変更はありません。インフラは最新の状態です。