0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Cloudflare PagesのTerraform Moduleを作った

Posted at

Cloudflare Pagesを簡単にセットアップしたい

Cloudflare Pagesは、簡単に静的ファイルをホスティングできるので便利で、いろいろなテスト的な使い方をしているのですが、毎回コンソールでセットアップするのが手間に感じたので、Terraformの勉強も兼ねて、TerraformでCloudflare Pagesプロジェクトとその関連リソースを管理するようにしました。

最終的な構成

$ tree .
.
├── README.md
└── cloudflare
    ├── main.tf
    ├── modules
    │   └── pages
    │       ├── README.md
    │       ├── main.tf
    │       ├── outputs.tf
    │       └── variables.tf
    ├── terraform.tfstate
    ├── terraform.tfstate.backup
    ├── terraform.tfvars
    └── variables.tf

3 directories, 10 files

上記が最終的なディレクトリ構造です。

将来的にはcloudflare以外のリソースも管理することを考えて、プロジェクトルートにcloudflareディレクトリを作成し、その中にCloudflare関連のmoduleを配置するようにしました。

Pages Moduleについて

普段Cloudflare Pagesを使うときに、GitHub連携をさせないパターンが多いので、今回はとてもシンプルに空のプロジェクトと、カスタムドメインの設定とそれに伴うDNSの設定ができるようなModuleにしました。

完成形としては以下のとおりです。

modules/pages/main.tf
terraform {
  required_providers {
    cloudflare = {
      source = "cloudflare/cloudflare"
      version = "~> 4.0"
    }
  }
}

resource "cloudflare_pages_project" "cloudflare_pages" {
  account_id = var.cloudflare_account_id
  name = var.project_name
  production_branch = var.production_branch
}

resource "cloudflare_pages_domain" "cloudflare_pages" {
  account_id = var.cloudflare_account_id
  project_name = cloudflare_pages_project.cloudflare_pages.name
  domain = var.custom_domain
}

resource "cloudflare_record" "cloudflare_pages" {
  zone_id = var.cloudflare_zone_id
  name = var.custom_domain
  value = cloudflare_pages_project.cloudflare_pages.subdomain
  type = "CNAME"
  proxied = true
}
modules/pages/variables.tf
variable "cloudflare_account_id" {
  description = "Cloudflare account ID"
  type = string
  nullable = false
}

variable "project_name" {
  description = "Cloudflare pages project"
  type = string
  nullable = false
}

variable "production_branch" {
  description = "Production branch for Cloudflare pages project"
  type = string
  default = "main"
  nullable = true
}

variable "custom_domain" {
  description = "Custom subdomain for Cloudflare pages project"
  type = string
  nullable = false
}

variable "cloudflare_zone_id" {
  description = "Cloudflare zone ID"
  type = string
  nullable = false
}
modules/pages/outputs.tf
output "name" {
  description = "Cloudflare pages project name"
  value = cloudflare_pages_project.cloudflare_pages.name
}

output "default_url" {
  description = "Cloudflare pages project default URL"
  value = cloudflare_pages_project.cloudflare_pages.subdomain
}

output "custom_url" {
  description = "Cloudflare pages project custom URL"
  value = cloudflare_record.cloudflare_pages.name
}

躓いたところ

terraform applyに失敗する

最初は、terraform applyを実行すると、Cloudflare Pagesにカスタムドメインを設定するためには、Cloudflare Pagesのプロジェクトが必要だというエラーが出てきてしまいました。

これは、はじめは以下のように各リソースに対して値を与えてそれぞれのリソースを作成するようにしていたため、Cloudflare Pagesのプロジェクトが作成される前に、カスタムドメインの設定が行われてしまっていたためです。

resource "cloudflare_pages_project" "cloudflare_pages" {
  account_id = var.cloudflare_account_id
  name = var.project_name
  production_branch = var.production_branch
}

resource "cloudflare_pages_domain" "cloudflare_pages" {
  account_id = var.cloudflare_account_id
  project_name = var.project_name
  domain = var.custom_domain
}

resource "cloudflare_record" "cloudflare_pages" {
  zone_id = var.cloudflare_zone_id
  name = var.custom_domain
  value = cloudflare_pages_project.cloudflare_pages.subdomain
  type = "CNAME"
  proxied = true
}

これを修正して、Cloudflare Pagesのプロジェクトリソースのoutputを参照するようにしたところ依存関係が解決し、正常に適用できるようになりました。

ちなみにこれ以外にもdepends_onを使う方法もあるようですが、今回はoutputを使う方法で解決しました。

Inconsistent dependency lock fileエラー

最初は、terraform planを実行すると、以下のエラーが出てしまいました。

Error: Inconsistent dependency lock file
│
│ The following dependency selections recorded in the lock file are inconsistent with the current configuration:
│   - provider registry.terraform.io/hashicorp/cloudflare: required by this configuration but no version is selected
│
│ To update the locked dependency selections to match a changed configuration, run:
│   terraform init -upgrade

hashcorp/cloudflareのバージョンが指定されていないというエラーですが、terraform init -upgradeを実行しても解決しませんでした。

実際に使用しているのはcloudflare/cloudflareなので、その旨をmoduleのmain.tfに記載して解決しました。

terraform {
  required_providers {
    cloudflare = {
      source = "cloudflare/cloudflare"
      version = "~> 4.0"
    }
  }
}

まとめ

とりあえずTerraformでリソース管理デビューを果たすことができました。今後は、他のリソースも管理できるようにしていきたいと思います。

多分、Terraformのベストプラクティスとかもあると思うので、それも勉強していきたいですね。

ありがとうございました。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?