Terraform
Terraform ↗は、標準化された構成構文を使用して異なるプロバイダーからサービスをデプロイすることを可能にするインフラストラクチャコードソフトウェアツールです。Terraform構成ファイルを作成する際には、手順を段階的に定義するのではなく、構成の最終状態を定義します。これにより、他のインフラストラクチャとともにトンネルを簡単にデプロイ、変更、管理できます。
このガイドでは、Terraformを使用して以下をデプロイします:
- HTTPテストサーバーを実行するGoogle Cloud Project (GCP)の仮想マシン
- インターネット上でサーバーを利用可能にするCloudflareトンネル
- サーバーに接続できるユーザーを定義するCloudflare Accessポリシー
以下の手順を完了するには、次のものが必要です:
お使いのオペレーティングシステムに応じたTerraformインストールガイド ↗を参照してください。
-
gcloud CLIをインストール ↗して、TerraformがGCPアカウントと対話できるようにします。
-
次のコマンドを実行してCLIで認証します:
Terminal window gcloud auth application-default login
TerraformがCloudflareアカウントと対話できるようにするためにAPIトークンを作成します。最低限、トークンには次の権限が含まれている必要があります:
| Permission type | Permission | Access level |
|---|---|---|
| Account | Cloudflare Tunnel | Edit |
| Account | Access: Apps and Policies | Edit |
| Zone | DNS | Edit |
Terraform functions through a working directory that contains configuration files. You can store your configuration in multiple files or just one — Terraform will evaluate all of the configuration files in the directory as if they were in a single document.
-
Create a folder for your Terraform configuration:
Terminal window mkdir cloudflare-tf -
Change into the directory:
Terminal window cd cloudflare-tf
The following variables will be passed into your GCP and Cloudflare configuration.
-
In your configuration directory, create a
.tffile:Terminal window touch variables.tf -
Open the file in a text editor and copy and paste the following:
# GCP variablesvariable "gcp_project_id" {description = "Google Cloud Platform (GCP) project ID"type = string}variable "zone" {description = "Geographical zone for the GCP VM instance"type = string}variable "machine_type" {description = "Machine type for the GCP VM instance"type = string}# Cloudflare variablesvariable "cloudflare_zone" {description = "Domain used to expose the GCP VM instance to the Internet"type = string}variable "cloudflare_zone_id" {description = "Zone ID for your domain"type = string}variable "cloudflare_account_id" {description = "Account ID for your Cloudflare account"type = stringsensitive = true}variable "cloudflare_email" {description = "Email address for your Cloudflare account"type = stringsensitive = true}variable "cloudflare_token" {description = "Cloudflare API token created at https://dash.cloudflare.com/profile/api-tokens"type = stringsensitive = true}
-
In your configuration directory, create a
.tfvarsfile:Terminal window touch terraform.tfvarsTerraform will automatically use these variables if the file is named
terraform.tfvars, otherwise the variable file will need to be manually passed in. -
Add the following variables to
terraform.tfvars. Be sure to modify the example with your own values.cloudflare_zone = "example.com"cloudflare_zone_id = "023e105f4ecef8ad9ca31a8372d0c353"cloudflare_account_id = "372e67954025e0ba6aaa6d586b9e0b59"cloudflare_email = "user@example.com"cloudflare_token = "y3AalHS_E7Vabk3c3lX950F90_Xl7YtjSlzyFn_X"gcp_project_id = "testvm-123"zone = "us-central1-a"machine_type = "e2-medium"
インフラストラクチャをプロビジョニングするために使用されるプロバイダー ↗を宣言する必要があります。
-
構成ディレクトリ内に
.tfファイルを作成します:Terminal window touch providers.tf -
providers.tfに次のプロバイダーを追加します。randomプロバイダーはトンネルの秘密を生成するために使用されます。terraform {required_providers {cloudflare = {source = "cloudflare/cloudflare"version = ">= 4.39.0"}google = {source = "hashicorp/google"}random = {source = "hashicorp/random"}}required_version = ">= 0.13"}# プロバイダーprovider "cloudflare" {api_token = var.cloudflare_token}provider "google" {project = var.gcp_project_id}provider "random" {}
次の構成は、Cloudflareアカウントの設定を変更します。
-
構成ディレクトリ内に
.tfファイルを作成します:Terminal window touch Cloudflare-config.tf -
Cloudflare-config.tfに次のリソースを追加します:# トンネルのための64文字の秘密を生成します。# `random_password`を使用することで、結果は機密として扱われ、コンソール出力には表示されません。参照:https://registry.terraform.io/providers/hashicorp/random/latest/docs/resources/passwordresource "random_password" "tunnel_secret" {length = 64}# GCP VMのための新しいローカル管理トンネルを作成します。resource "cloudflare_tunnel" "auto_tunnel" {account_id = var.cloudflare_account_idname = "Terraform GCP tunnel"secret = base64sha256(random_password.tunnel_secret.result)}# http_app.${var.cloudflare_zone}をトンネルにルーティングするCNAMEレコードを作成します。resource "cloudflare_record" "http_app" {zone_id = var.cloudflare_zone_idname = "http_app"content = "${cloudflare_tunnel.auto_tunnel.cname}"type = "CNAME"proxied = true}# トンネルの設定を作成します。resource "cloudflare_tunnel_config" "auto_tunnel" {tunnel_id = cloudflare_tunnel.auto_tunnel.idaccount_id = var.cloudflare_account_idconfig {ingress_rule {hostname = "${cloudflare_record.http_app.hostname}"service = "http://httpbin:8080"origin_request {connect_timeout = "2m0s"access {required = trueteam_name = "myteam"aud_tag = [cloudflare_access_application.http_app.aud]}}}ingress_rule {service = "http_status:404"}}}# 誰が接続できるかを制御するAccessアプリケーションを作成します。resource "cloudflare_access_application" "http_app" {zone_id = var.cloudflare_zone_idname = "Access application for http_app.${var.cloudflare_zone}"domain = "http_app.${var.cloudflare_zone}"session_duration = "1h"}# アプリケーションのためのAccessポリシーを作成します。resource "cloudflare_access_policy" "http_policy" {application_id = cloudflare_access_application.http_app.idzone_id = var.cloudflare_zone_idname = "Example policy for http_app.${var.cloudflare_zone}"precedence = "1"decision = "allow"include {email = [var.cloudflare_email]}}これらのリソースについて詳しく学ぶには、Cloudflareプロバイダーのドキュメント ↗を参照してください。
次の構成は、GCP仮想マシンの仕様を定義し、起動時に実行されるスタートアップスクリプトを作成します。
-
構成ディレクトリ内に
.tfファイルを作成します:Terminal window touch GCP-config.tf -
GCP-config.tfに次の内容を追加します:# GCP VMのOSを選択します。data "google_compute_image" "image" {family = "ubuntu-minimal-2004-lts"project = "ubuntu-os-cloud"}# GCP VMインスタンスをセットアップします。resource "google_compute_instance" "origin" {name = "test"machine_type = var.machine_typezone = var.zonetags = []boot_disk {initialize_params {image = data.google_compute_image.image.self_link}}network_interface {network = "default"access_config {// 一時的IP}}// インスタンスを一時的にするためのオプション設定scheduling {preemptible = trueautomatic_restart = false}// Terraform変数を受け取るスタートアップスクリプトを実行するようにVMを構成します。metadata_startup_script = templatefile("./install-tunnel.tpl",{tunnel_token = cloudflare_tunnel.auto_tunnel.tunnel_token})}
次のスクリプトは、cloudflaredをインストールし、トンネルのための権限と構成ファイルを作成し、サービスとしてトンネルを実行するように設定します。この例では、接続性をテストするために使用できる軽量HTTPアプリケーションもインストールします。
-
構成ディレクトリ内にTerraformテンプレートファイルを作成します:
Terminal window touch install-tunnel.tftpl -
テキストエディタでファイルを開き、次のbashスクリプトをコピーして貼り付けます:
Terminal window # CloudflareトンネルとDockerリソースをインストールするためのスクリプト# Docker構成cd /tmpsudo apt-get install software-properties-common# このOSのためのdockerリポジトリを取得curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add -sudo add-apt-repository "deb [arch=amd64] https://download.docker.com/linux/ubuntu bionic stable"# OSが更新され、dockerがインストールされますsudo apt update -y && sudo apt upgrade -ysudo apt install docker docker-compose -y# HTTPBinアプリケーションを追加し、localhost:8080で実行します。cat > /tmp/docker-compose.yml << "EOF"version: '3'services:httpbin:image: kennethreitz/httpbinrestart: alwayscontainer_name: httpbinports:- 8080:80cloudflared:image: cloudflare/cloudflared:latestrestart: alwayscontainer_name: cloudflaredcommand: tunnel run --token ${tunnel_token}EOFcd /tmpsudo docker-compose up -d
To deploy the configuration files:
-
Initialize your configuration directory:
Terminal window terraform init -
Preview everything that will be created:
Terminal window terraform plan -
Apply the configuration:
Terminal window terraform apply
GCPインスタンスとトンネルがオンラインになるまでに数分かかる場合があります。新しいトンネル、Accessアプリケーション、およびAccessポリシーはZero Trust ↗で確認できます。新しいDNSレコードはCloudflareダッシュボード ↗で利用可能です。
-
ネットワーク > トンネルで、トンネルがアクティブであることを確認します。
-
アクセス > アプリケーションで、CloudflareのメールがAccessポリシーによって許可されていることを確認します。
-
任意のデバイスからブラウザを開き、
http_app.<cloudflare_zone>(例:http_app.example.com)にアクセスします。最近ログインしていない場合、Accessログインページが表示されます。
-
Cloudflareのメールでログインします。
HTTPBin ↗のホームページが表示されるはずです。