本記事では、手動で作成したGCP環境を簡単にTerraformコード化したい!
という方に便利なツール、terraformit-gcpをご紹介します。
目次
既存環境のTerraformコード化は面倒
最近Infrastructure as Codeの考え方が浸透してきました。
そんな中、手動で管理していた環境をコードで管理できるようにしたい!
と思っている方も多いはず。
ただ、既存環境をTerraformコード化するのはなかなか大変な作業です。
具体的には以下の手順が必要になります。
- 作成した既存のGCPリソースを把握
- リソースをインポートするためのTerraformコードを記述
- リソースごとにterraform importコマンドをひたすら打ってtfstateを作成
- コードを書いて、ひたすらterraform planでコードが正しいか確認
GCP環境の規模が大きくなればなるほど、手間のかかる作業となります。
辛い作業をなんとかしたい、、、という思いから開発されたのがterraformit-gcpです。
terraformit-gcp
terraformit-gcpはオープンソースとして公開されていますので、どなたでも利用できます。
terraformit-gcpバージョン0.9が対応しているTerraformのバージョンはv0.11.13または14です。
Terraformのv0.12は今後対応予定です。
類似オープンソースとの違い
既存環境をterraform化するオープンソースとしては、
他にterraformerやterraformingがあります。
このうちGCPに対応しているのはterraformerです。
terraformerとterraformit-gcpの違いは、
既存リソースをCloud Asset APIを利用して取得するかどうかです。
terraformit-gcpはCloud Asset APIを利用して既存GCPリソースを取得します。
CloudAssetAPIの設定が必要になりますが、どのリソースをインポートするかを指定する必要はありません。
terraformerは以下のように既存リソースを指定して、コマンドを実行します。
terraformer import google --resources=gcs,forwardingRules,httpHealthChecks --filter=google_compute_firewall=rule1:rule2:rule3 --zone=europe-west1-a --projects=aaa,fff
また、対応しているリソースはterraformerの方が多いです。
terraformit-gcpはCloud Asset APIで取得できるリソースに制限されます。
対応リソースはgithubを参照してください。
コマンド一発でコード化してみる
それではさっそく、実際に手動で作成したGCP環境を、terraformit-gcpを使ってコード化してみます。
PCはMacを想定しています。
プロジェクトを作成
デモ用のプロジェクトを作成します。
今回は手動でNetwork、SubNetwork、サービスアカウント、GCEインスタンスを作成しました。
terraformit-gcp準備
terraformをインストール
terraformまたはtfenv(Terraformバージョン管理ツール)をインストールします。
オススメはtfenvです。簡単にterraformのバージョンを切り替えられます。
brew install tfenv
tfenv install 0.11.14
tfenv use 0.11.14
terraform version
goインストール
goをインストールします。
brew install go
go version
Path設定
Pathを通します。
echo 'export GOPATH=$HOME/go' >> ~/.bash_profile
echo 'export PATH=$PATH:$GOPATH/bin' >> ~/.bash_profile
source ~/.bash_profile
gcloudインストール
gcloudをリンク先の手順に従いインストールします。
gcloudはGCPを管理するためのコマンドラインツールです。
gcloud初期設定
gcloudを使って、ローカル環境から、GCPリソースにアクセスするために使用する認証情報を生成します。
gcloud init
または
gcloud auth login
terraformit-gcpインストール
terraformit-gcpをインストールします。
export GO111MODULE=on
git clone https://github.com/cloud-ace/terraformit-gcp.git -b v0.9.1 ~/go/src/github.com/cloud-ace/terraformit-gcp
cd ~/go/src/github.com/cloud-ace/terraformit-gcp
go install
goのバージョンv1.13を使用している場合、上記のインストールが失敗する可能性があります。その場合は以下を実行して再度go installしてください。
go get -u golang.org/x/xerrors
Cloud Asset APIを有効化
Cloud Asset APIを使って、GCP既存リソースの情報を取得します。
ConsoleからCloud Asset APIを有効化します。
bucket作成
Cloud Asset APIは2019年6月時点ではGCSに出力する必要があります。
Cloud Asset APIの出力を保存するためのBucketを作成します。
gsutil mb gs://バケット名
OauthClientIDを生成してダウンロード
CloudAssetAPIを呼び出すための、認証情報を生成します。
まず、Oauth画面を作成します。
OAuth同意画面を選択して、アプリケーション名を選択して、OKを選択します。
次に、認証情報からOauth Client IDを生成します。
アプリケーションの種類はその他を選択します。
最後に、ダウンロードボタンからjsonファイルをダウンロードします。
この認証情報には有効期限があります。有効期限がきれた場合は、もう一度生成します。
コードを生成するディレクトリに移動
コードを生成するディレクトリに移動します。
cd yourpath
構成ファイルを作成
自分の環境に応じた、.terraformit-gcp.yamlファイルを生成します。
CloudAsset:
# GCP プロジェクトナンバー
project-number: "1234456788"
# 先ほど作成したCloudAssetAPIの出力先のバケット名
bucket: "your-terraformit-test-bucket"
# 先ほどダウンロードした認証情報のパス
credential: "/Users/yourname/Downloads/xxxxxxxxxxxx.json"
Terraform:
# provider名"google" または "google-beta"
provider: "google"
# ワークスペース
workspace: "default"
# バックエンド"local" または "gcs"
backend-type: "local"
# バックエンドが"local"なら
# backend-location: ""
# バックエンドが"gcs"なら
# backend-location: "your bucket name"
backend-location: ""
# デフォルトのリージョン
gcp-provider-default-region: "asia-northeast1"
# デフォルトで作成されるリソースをTerraformで管理するかどうか
resource-default-network: false
resource-default-subnetwork: false
resource-default-route: false
resource-default-firewall: false
terraformit-gcp planコマンドでコードを生成
いよいよ、terraformit-gcpコマンドを実行します。
terraformit-gcp plan
Go to the following link in your browser:
が最初に表示されます。
記述されたリンクにいき、verification codeを取得します。
取得したコードを入力し、Enterキーを押します。
以下の結果が表示されたら成功です。
################## terraform plan start ##################
plan sccess
################## terraform plan end ##################
かかる時間は、terraformコマンドとCloud Asset API取得の時間がメインです。
この環境ですと、90秒くらいで完了しました。
ディレクトリに、tfstateとコードが出力されています。
ls
terraform.tfstate terraformit-gcp-import.sh* terraformit-gcp-resource.tf*
terraform.tfstate.backup terraformit-gcp-provider.tf*
terraformit-gcpで生成されるファイル
出力されたファイルの中身を見てみましょう。
terraformit-gcp-import.sh
既存環境をimportするためのコマンドです。
terraform importコマンドが羅列してあります。
terraform import -provider=google google_project.xxxxxx xxxxxxxx
terraform import -provider=google google_compute_disk.terraformit-gcp-instance xxxxxxxxx/asia-northeast1-b/terraformit-gcp-instance
terraform import -provider=google google_compute_network.terraformit-gcp-network terraformit-gcp-network
terraform import -provider=google google_compute_instance.terraformit-gcp-instance xxxxxxxxx/asia-northeast1-b/terraformit-gcp-instance
terraform import -provider=google google_compute_subnetwork.terraformit-gcp-subnet asia-northeast1/terraformit-gcp-subnet
terraform import -provider=google google_service_account.terraformit-gcp-gce-instance-xxxxxxxxx-iam-gserviceaccount-com projects/xxxxxxxxx/serviceAccounts/terraformit-gcp-gce-instance@xxxxxxxxx.iam.gserviceaccount.com
terraform import -provider=google google_storage_bucket.xxxxxxxxx xxxxxxxxx
terraformit-gcp-provider.tf
providerの情報が記述されているファイルです。
provider "google" {
project = "xxxxxxxxx"
region = "asia-northeast1"
}
provider "google-beta" {
project = "xxxxxxxxx”
region = "asia-northeast1"
}
terraformit-gcp-backend.tf
バックエンドの情報が記述されているファイルです。
バックエンドにGCSを指定した場合は出力されます。
terraformit-gcp-resource.tf
gcpリソースの情報が記述されているファイルです。
resource "google_project" "terraformit-gcp" {xxxxxx}
resource "google_compute_disk" "terraformit-gcp-instance" {xxxxxx}
resource "google_compute_network" "terraformit-gcp-network" {xxxxxx}
resource "google_compute_instance" "terraformit-gcp-instance" {xxxxxx}
resource "google_compute_subnetwork" "terraformit-gcp-subnet" {xxxxxx}
resource "google_service_account" "terraformit-gcp-gce-instance-xxxxxx-iam-gserviceaccount-com" {xxxxxx}
resource "google_storage_bucket" "terraformit-gcp-demo" {xxxxxx}
よくあるエラー
- Oauthの認証情報の有効期限が切れていると、Cloud Asset APIの取得に失敗します。
もう一度認証情報を生成してダウンロードしてください。
Error: Failed to create CloudAssetAPI
{
"error": {
"code": 401,
"message": "Request had invalid authentication credentials. Expected OAuth 2 access token, login cookie or other valid authentication credential. See https://developers.google.com/identity/sign-in/web/devconsole-project.",
"status": "UNAUTHENTICATED"
}
}:github.com/cloud-ace/terraformit-gcp/cloudasset.CreateCloudAsset
- 生成したtfファイルが正しくなく、エラーが発生する場合もあります。
現在、startup-scriptなどの設定は、うまく取り込めない場合があります。
その場合、tfファイルのエラー部分を修正し、terraform planで正しく修正されていることを確認してください。 -
その他、ソースコードのバグを発見した場合は、issueまたはpull requestをあげていただければ幸いです。
terraformit-gcpはどんなことをしているのか
terraformit-gcpは、以下の手順で既存環境をTerraformコード化しています。
- CloudAssetAPIを呼び出してアセットデータをGCSに出力
- GCS上のアセットデータをローカルに取得
- terraform importをするために必要なファイルを生成
- terraform init
- terraform workspace new
- terraform import
- tfstateからTerraformコードを生成
- terraform plan
terraformit-gcp planコマンドはこの手順を一発で実行します。
terraform importするためのファイルだけ生成したい、など任意の手順だけを実行したい場合は、terraformit-gcp createコマンドを使用します。
詳細はREADMEをご覧ください。
注意点
・現在Cloud Asset APIが対応しているリソースにのみ対応しています。
対応しているリソースはGithubを確認してください。(まだ開発中のリソースもあります。)
・Terraformで管理したくないリソースがある場合は、createコマンドで1つずつ手順を実行します。
現在、マネージドインスタンスグループのインスタンスなど、Terrafromで管理したくないリソースもコード化されます。
その場合、createコマンドで作成したimportファイルとresourceファイルにあるリソースの定義を削除して、terraform importしてください。
まとめ
初期設定は少し手間がかかるかもしれませんが、簡単にTerraformコード化できたと思います。
terraformit-gcpは、2019年6月に公開したできたてのオープンソースです。
まだまだ発展途上ですので、是非イシューやプルリクいただければと思います!