case-kの備忘録

日々の備忘録です。データ分析とクラウドに興味があります。

Cloud BuildでGKEへのデプロイ作業を自動化させる

Cloud Buildを使いアプリのデプロイ作業を自動化してみました。Cloud Source RepositoriesへのpushをトリガーにDockerfileをビルド、イメージをContainer Registry に登録、登録したイメージをGKEのクラスタにデプロイさせます。

Cloud Buildの基本操作

マニフェストの定義

基本的には次のような形式でマニフェストを定義します。

steps:
- name: 'gcr.io/cloud-builders/docker'
  args: [ 'build', '-t', 'gcr.io/$PROJECT_ID/quickstart-image', '.' ]
images:
- 'gcr.io/$PROJECT_ID/quickstart-image'

この結果をdockerコマンドで実行する場合は次のようになります。

$ docker image build -t gcr.io/[PROJECT_ID]/quickstart-image .

YAMLファイルは次のようにして実行します。

$ gcloud builds submit --config cloudbuild.yaml .

cloud.google.com

サンプル

次のサンプルはDockerfileをContainer Registryに登録する名前でビルドし、Container RegistryにpushしてGKE上にデプロイするサンプルとなります。

steps:
- name: 'gcr.io/cloud-builders/docker'
  args: ['build', '-t', 'gcr.io/$PROJECT_ID/devops-handson:$SHORT_SHA', '.']
  dir: 'devops/'
- name: 'gcr.io/cloud-builders/docker'
  args: ['push', 'gcr.io/$PROJECT_ID/devops-handson:$SHORT_SHA']
- name: 'gcr.io/cloud-builders/kubectl'
  args:
  - 'set'
  - 'image'
  - 'deployment/devops-handson-deployment'
  - 'myapp=gcr.io/$PROJECT_ID/devops-handson:$SHORT_SHA'
  env:
  - 'CLOUDSDK_COMPUTE_ZONE=asia-northeast1-c'
  - 'CLOUDSDK_CONTAINER_CLUSTER=k8s-devops-handson'

#5 Cloud Soure Repository と Cloud Build をつかったコンテナイメージの自動ビルドとデプロイ | DevOps 編 | はじめてみよう Google Cloud Platform Online Handson

  • steps:ビルドのステップを定義
  • name:ビルダーを指定(docker, gcloud, npm等) 標準で提供されているビルダー コミュニティー提供のビルダー

クラウド ビルダー  |  Cloud Build のドキュメント  |  Google Cloud

  • env:実行時に使用される環境変数のリストを指定
  • args:nameフィールドで指定したビルダーに渡す引数を指定
  • images:レジストリにpushしたいimage名を配列で指定
  • dir:ステップ実行時に使用する作業ディレクト

cloud.google.com

株価アプリのデプロイを自動化させる

株価アプリのビルドからデプロイを自動化して行きたいと思います。
www.case-k.jp

事前準備

GKEクラスタ構築
$ gcloud container clusters create casek --machine-type=n1-standard-1 --num-nodes=3

www.case-k.jp

リポジトリ作成

コードをPUSHするリポジトリを準備しておきます。Cloud Source Repositoriyへのpushをトリガーにビルドからデプロイ処理を実行します。

認証鍵作成

ローカルホストからPUSHできるように認証鍵を作り、公開鍵をCloud Source Repositoriyに登録しておきます。

$ ssh-keygen -t rsa -C "user@example.com"

秘密鍵のパスを指定しクローンし、デプロイ対象のアプリを管理します。

$ GIT_SSH_COMMAND='ssh -i /Users/keisuke/.ssh/[秘密鍵]' git clone ・・・

cloud.google.com
https://source.cloud.google.com/user/ssh_keys?register=true&authuser=0

Cloud Buildの設定

Cloud Buildの実行ステップを定義したマニフェストとトリガーを定義します。

マニフェストを定義

次のようにしてCloud buildの実行ステップを定義したマニフェストを作ります。登録したリポジトリへのpushを検知しビルドとデプロイ処理を実行するように次のようにして定義します。10分を超える場合は「timeout」も定義します。
GCP CloudbuildでTimeoutエラーの対応 - Qiita
cloudbuild.yaml

steps:
# docker build & push
# react
- name: 'gcr.io/cloud-builders/docker'
  args: ['build','-f','Dockerfile-react-kube', '-t', 'gcr.io/[project id ]/react-app', '.']
  timeout: 500s
- name: 'gcr.io/cloud-builders/docker'
  args: ['push', 'gcr.io/[project id]/react-app']

# express
- name: 'gcr.io/cloud-builders/docker'
  args: ['build','-f','Dockerfile-express-kube', '-t', 'gcr.io/[project id]/express-app', '.']
- name: 'gcr.io/cloud-builders/docker'
  args: ['push', 'gcr.io/[project id]//express-app']
# nginx
- name: 'gcr.io/cloud-builders/docker'
  args: ['build','-f','Dockerfile-nginx-kube', '-t', 'gcr.io/[project id]/nginx-app', '.']
- name: 'gcr.io/cloud-builders/docker'
  args: ['push', 'gcr.io/[project id]//nginx-app']

# kubernets deploy
## deployment
- name: 'gcr.io/cloud-builders/kubectl'
  args: ['apply', '-f', 'express-app-deployment.yaml']
  env:
  - 'CLOUDSDK_COMPUTE_REGION=asia-northeast1-a'
  - 'CLOUDSDK_CONTAINER_CLUSTER=casek'
- name: 'gcr.io/cloud-builders/kubectl'
  args: ['apply', '-f', 'react-app-deployment.yaml']
  env:
  - 'CLOUDSDK_COMPUTE_REGION=asia-northeast1-a'
  - 'CLOUDSDK_CONTAINER_CLUSTER=casek'
## service
- name: 'gcr.io/cloud-builders/kubectl'
  args: ['apply', '-f', 'express-app-service.yaml']
  env:
  - 'CLOUDSDK_COMPUTE_REGION=asia-northeast1-a'
  - 'CLOUDSDK_CONTAINER_CLUSTER=casek'
- name: 'gcr.io/cloud-builders/kubectl'
  args: ['apply', '-f', 'react-app-service.yaml']
  env:
  - 'CLOUDSDK_COMPUTE_REGION=asia-northeast1-a'
  - 'CLOUDSDK_CONTAINER_CLUSTER=casek'
timeout: 3600s
トリガーを定義

Cloud buildよりトリガーを選び次の定義を行います。

動作確認

リポジトリにPUSHしDockerfileのビルドからデプロイうまく行っていることを確認します。

$ kubectl get pod
NAME                           READY   STATUS    RESTARTS   AGE
express-app-5b5956c4c9-dcc78   2/2     Running   0          105s
express-app-5b5956c4c9-vdpl9   2/2     Running   0          105s
react-app-5bb9c7f6b-575pc      2/2     Running   0          101s
react-app-5bb9c7f6b-hxgpg      2/2     Running   0          101s

その他

つまずいたところの備忘録。Cloud Buildはあまり関係ありませんが。

  • Reactプロジェクト

create-react-appコマンドで作ったプロジェクトをビルドできなくなった。
ディレクトリが影響しているよう。node_moduleの再インストールが必要

$ rm -r node_modules
$ yarn add react-scripts
  • 隠しファイル

隠しファイルがあり、node_moduleをContainer Registryにコミットできておらずデプロイ処理に失敗した。

.gitignore