CloudSourceRepositoriesからGAEにデプロイしてみる

この記事は約14分で読めます。

公式Doc:CloudSourceRepositoriesからApp Engineへのデプロイを見ましたが、単にリポジトリにpushし、デプロイは別にやるという内容で、リポジトリへのpushからビルド、デプロイを自動化するというものではありませんでした。

ビルド、デプロイを自動化するにはCloud BuildをCloud Source Repositoriesに連携する必要があるので、やってみました。

スポンサーリンク

前提条件

当記事の手順を行うにあたり、

  • GAEのアプリケーションがデプロイ済であること
  • 上記アプリケーションリソースがCloud Source Repositoriesにpush済であること

以上を前提に進めます。

Cloud Source Repositoriesの利用方法については、こちらの記事をご覧下さい。

スポンサーリンク

事前準備

APIの有効化

  • GAE
  • Cloud Build

のAPIが有効となっている必要があります。

手順については下記公式Docを参照下さい。

クイックスタート: Cloud Build を使用して App Engine のデプロイを自動化する

Cloud BuildのサービスアカウントにGAEのアクセス権を付与する

手順については下記公式Docを参照下さい。

クイックスタート: Cloud Build を使用して App Engine のデプロイを自動化する

スポンサーリンク

cloudbuild.yamlを作成

Cloud Buildがビルドやデプロイといったタスクを行うには、手順や指示が必要になります。

この手順や指示の内容をcloudbuild.yamlに記述します。

記述したら、リポジトリ管理下、app.yamlが入っているフォルダに保存します。

公式Doc記載のcloudbuild.yaml

steps:
- name: "gcr.io/cloud-builders/gcloud"
  args: ["app", "deploy"]
timeout: "1600s"

当ブログのcloudbuild.yaml

当ブログの構成では、

  • app.yaml
  • cron.yaml

をデプロイしているので、cloudbuild.yamlを下記内容にカスタマイズしました。

リポジトリのルート階層にyamlファイルがある場合はパス指定は不要ですが、当ブログはリポジトリの2階層目にyamlファイルを置いているので、ファイル名の前にパス名を記述しています。

デプロイコマンドの後にgsutilコマンドを記述していますが、デプロイ時にGCSにasia.artifacts.{Project ID}.appspot.comというバケットが自動で作られ、都度その中にコンテナイメージが格納され、地味にストレージコストが課金されてしまうので、デプロイが完了したらgsutilコマンドで削除を行っています。

※このバケットに格納されるコンテナイメージはデプロイが完了したら不要となります。

こちらに関しては、GCSのオブジェクトライフサイクル管理で対応も出来ますが、今回はビルドトリガーで発行されるコマンドにて対応することにしました。

steps:
- name: gcr.io/cloud-builders/gcloud
  args: ['app', 'deploy', 'リポジトリのパス名/app.yaml', 'リポジトリのパス名/cron.yaml']
- name: gcr.io/cloud-builders/gsutil
  args: ['rm', '-r', 'gs://asia.artifacts.{Project ID}.appspot.com/*']
- name: gcr.io/cloud-builders/gsutil
  args: ['rb', 'gs://asia.artifacts.{Project ID}.appspot.com']
timeout: '1600s'

スポンサーリンク

Cloud Source Repositoriesにcloudbuild.yamlを追加

gitコマンドでCloud Source Repositoriesに作成したcloudbuild.yamlをpushします。

git add .
git commit -m "Add cloudbuild.yaml file"
git push origin master

スポンサーリンク

ビルドトリガーを作成

作成、pushしたcloudbuild.yamlを利用するCloud Buildのビルドトリガーを作成します。

[GCP Consoleのメニュー]->[Cloud Build]->[トリガー]でビルドトリガーの設定画面を開きます。

(Google Cloud プロジェクトが選択されていない場合は、[プロジェクトを選択] をクリックして、Google Cloud プロジェクトの名前をクリックします)

[トリガー作成]をクリックします。

ビルドトリガー作成画面で、

  • [名前]フィールドにビルドトリガー名を入力
  • [イベント][ブランチに push する]を選択
  • [ソース]-[リポジトリ]で対象となるリポジトリを選択
  • [ソース]-[ブランチ]に ^master$ を入力
  • [ビルド構成]で [Cloud Build 構成ファイル]を選択
  • [Cloud Build 構成ファイルの場所] フィールドで、/ の後に「cloudbuild.yaml」と入力(cloudbuild.yamlがリポジトリ直下にない場合はパス名も付与します)

以上の入力を行ったあと、[作成]をクリックします。

一覧に作成したビルドトリガーが追加されます。

スポンサーリンク

アプリケーションを変更しリポジトリにPush

ビルドトリガーが出来たので、アプリケーションに変更を加え、リポジトリにpushします。

前述で作成したビルドトリガーは、masterブランチにpushが通知されると動いてくれます。

git add .
git commit -m "Any comment"
git push origin master

スポンサーリンク

作成中のビルドを表示

サービスアカウントの権限まわりでハマる

Cloud Buildのダッシュボードを確認したところエラーになっていたので、確認したところ下記内容のエラーログが出力されていました。

ERROR: (gcloud.app.deploy) PERMISSION_DENIED: You do not have permission to act as 'xxx@appspot.gserviceaccount.com'
- '@type': type.googleapis.com/google.rpc.ResourceInfo
  description: You do not have permission to act as this service account.
  resourceName: xxx@appspot.gserviceaccount.com
  resourceType: serviceAccount
ERROR
ERROR: build step 0 "gcr.io/cloud-builders/gcloud" failed: step exited with non-zero status: 1

Cloud BuildのサービスアカウントにGAE関連のロール付与してなかったと思ったので[App Engineデプロイ担当者]を付与し、ビルドトリガーを再度実行したのですが、エラーは改善しませんでした。

ロールを付与して解決

検証しましたが、App Enginデプロイ担当者ロールは不要でした。

(公式Docの手順でApp Engine管理者ロールを付与しているので不要ですね)

調べた結果、最終的に必要なロールは

  • App Engine管理者
  • ストレージ管理者(バケット:asia.artifacts.{Project ID}.appspot.comに作成されるコンテナイメージを削除するために必要なロール)
  • Cloud Buildサービスアカウント
  • サービスアカウントユーザー
  • Cloud Scheduler管理者(cron.yamlをデプロイする時になければエラーとなる。後述の補足を参考願います)

でした。

ロールを設定後ビルドトリガーを走らせると、GAEに無事デプロイしてくれました。

補足:cron.yamlをデプロイする場合

cron.yamlをデプロイする際、ロール:Cloud Scheduler管理者が必要になります。

付与していない場合は、下記エラーが表示されます。

ERROR: (gcloud.app.deploy) Server responded with code [403]:
  Forbidden Unexpected HTTP status 403.
  b"You do not have permission to modify this app (app_id=u'u~xxxx')."
ERROR
ERROR: build step 0 "gcr.io/cloud-builders/gcloud" failed: step exited with non-zero status: 1

スポンサーリンク

GAEで自動デプロイされたか確認

GAEのバージョン管理の画面で、新しいバージョンのインスタンスが出来ていれば、Cloud Buildによる自動デプロイが正しく動いたことになります。

スポンサーリンク

まとめ

案件に入った時、既にCI/CDの環境が構築済で、自分で作る機会は中々ないので、勉強になったなと思います。

ロールまわりの問題のところはハマりました(涙)

※参考にした公式Docに書いて欲しかったですね。

最後に、質問に答えて下さった社内の有識者の皆様、ありがとうございました。

スポンサーリンク

追記:GAEセキュリティ対策に伴うiam.serviceAccounts.actAs権限付与について

本件社内で質問した際、2021/1/27までにGAEにビルド・デプロイを行っているCloud Buildのサービスアカウントに対し、iam.serviceAccounts.actAs権限を付与しないとビルドやデプロイが出来なくなるという情報が共有されました。

iam.serviceAccounts.actAs権限はロール:サービスアカウントユーザーに含まれているので、期日までにCloud Buildのサービスアカウントへこのロールを付与しておく必要があります、ご注意下さい。

以下、Google Cloudから配信された案内メール(英文)を掲載します。

Dear Google App Engine Customer,

We are making a change to App Engine’s security posture. Going forward, developers who want to deploy App Engine applications, must have the iam.serviceAccounts.actAs permission on the App Engine default service account. These changes will come into effect on January 27, 2021. You need to take action to ensure your developers have the right service account permissions so that they can continue deploying App Engine applications. You can also opt-in to this change sooner than January 27, 2021 by following the steps described below.

What do I need to know?
Google Cloud projects have an App Engine default service account that is set up with the default role of project editor. To make onboarding easier, App Engine relied on product-level IAM permissions without requiring the iam.serviceAccounts.actAs permission on the App Engine default service account.

To improve App Engine’s security posture, we are making changes to require that any developer using the App Engine default service account has the iam.serviceAccounts.actAs permission. This is to reduce the risk that accidental IAM misconfigurations might make it possible for users of these services to gain elevated, non-obvious permissions.

You are being notified because you have projects (see attachment) with users who are using the App Engine default service account but do not have the iam.serviceAccounts.actAs permission. Starting on January 27, 2021, developers who don’t have the iam.serviceAccounts.actAs permission will not be able to deploy App Engine applications.

What do I need to do by January 27, 2021?
You must grant your developers the iam.serviceAccounts.actAs permission on the App Engine default service account by January 27, 2021 so that they can continue deploying App Engine applications.

Identify all developers who have the permissions to deploy App Engine applications.
Identify the App Engine default service account, which is usually of the format YOUR_PROJECT_ID@appspot.gserviceaccount.com
Grant each developer the Service Account User role (roles/iam.serviceAccountUser) on the App Engine default service account.
Repeat these steps for each of the projects listed below.
What can I do to improve my security posture today?
Instead of waiting for January 27, 2021, you can opt-in today to require that developers have the iam.serviceAccounts.actAs permission to deploy App Engine applications. To opt-in:

First, grant your developers the iam.serviceAccounts.actAs permission on the default App Engine service account before enabling the Organization Policy. See above.
Then, enable the Organization Policy constraints/appengine.enforceServiceAccountActAsCheck.
Need more information or assistance?
For more information, including links to tools to help you fix this issue, please review the Cloud IAM documentation.

If you have any questions or require assistance, please do not hesitate to reply to this email to contact Google Cloud Support.

スポンサーリンク

参考情報

クイックスタート: Cloud Build を使用して App Engine のデプロイを自動化する
ビルド構成の概要  |  Cloud Build のドキュメント  |  Google Cloud
[GAE] Cloud Buildからcron.yamlをデプロイする - Qiita
Google App Engine(GAE)でスケジュール実行したい場合、cron.yamlを書いてデプロイするわけですが、それをCloud Buildを使ってやりたい場合に軽くハマったことなど。 問題 まず、大前提として、Cl...
GAE/Go + Cloud Build でデプロイを自動化しよう - Qiita
こんにちは、今年も花粉症の季節でアレルギー症状に苦しんでる @wezardnet です🤧 最近は洗濯して再利用できるマスクが発売されてるとのことで試しに購入してみました。使用感はなかなか良いと思います。一度洗ってみましたが、あと2、3...
スポンサーリンク
GCP
ヤマログ
タイトルとURLをコピーしました