GitHub Actions(v2)からgcloud/gsutilを扱う際のスマートな方法

自分の忘備録用に書く。

### 注意事項
本投稿は2019年8月にリリースされたGitHub Actions v2(bate)版の話です。
2019/9/12時点ではまだBeta版なので書いてある記述は古くなるなる可能性があります。最新情報は適宜公式ドキュメントを参照してください。

また、GitHub Actionsの何が良いのか、他との違いとかは、検索すれば出てくるので他の方にお任せします。
僕自身はGitHub Actions何が良いのかを確かめるために検証している段階で、どのCIも一長一短なので早く収束してほしいなと思ってます。

# はじめに
最初に完成版のコードはこちらです。これをやる背景をつらつら書きます。

```
name: CI
on: [push]
jobs:
  build:
    runs-on: ubuntu-latest
    steps:
    - uses: actions/checkout@v1

    - name: Setup Google Cloud
      uses: actions/gcloud/auth@master
      env:
        GCLOUD_AUTH: ${{ secrets.GCLOUD_AUTH }}

    - name: GCP List Clusters
      uses: actions/gcloud/cli@master
      with:
        args: container clusters list
      env:
        CLOUDSDK_CORE_PROJECT: < project id >

    - name: GCS List Bucket
      uses: docker://gcr.io/cloud-builders/gsutil
      with:
        args: ls
      env:
        CLOUDSDK_CORE_PROJECT: < project id >

    - name: Terraform version
      uses: docker://hashicorp/terraform
      with:
        args: version

    - name: kubectl version
      uses: docker://gcr.io/cloud-builders/kubectl
      with:
        args: version
      env:
        CLOUDSDK_CORE_PROJECT: < project id >
        CLOUDSDK_COMPUTE_ZONE: < zone name >
        CLOUDSDK_CONTAINER_CLUSTER: < cluster name >
```

# やりたかったこと
- GitHub Actionsを利用してCI/CDを行いたい
- GCRに登録したり、GKEにpushしたい

# 課題だったこと
- クレデンシャルの取り回し方法を探してもアナログな方法しか見当たらなかった
    - 冗長的で長い
    - 同じことの繰り返しなのでスマートな方法は無いか

```:アナログな方法
      run: |
        echo "deb [signed-by=/usr/share/keyrings/cloud.google.gpg] https://packages.cloud.google.com/apt cloud-sdk main" > google-cloud-sdk.list
        sudo cp google-cloud-sdk.list /etc/apt/sources.list.d
        curl https://packages.cloud.google.com/apt/doc/apt-key.gpg > apt-key.gpg
        sudo apt-key --keyring /usr/share/keyrings/cloud.google.gpg add apt-key.gpg
        sudo apt-get update
        sudo apt-get install google-cloud-sdk kubectl
        echo $GCLOUD_AUTH > gcp_key.json
        gcloud auth activate-service-account --project=<project id> --key-file=gcp_key.json
        gcloud container clusters list
```

# 解決方法はあった。 がしかし
解決方法はあった。GitHub公式のActionsリストに[gcloud](https://github.com/actions/gcloud)はあった。
だがしかし、記載されている記法はv1。頑張るか。

まずは、サービスアカウントを発行してJsonをダウンロード。base64でエンコードしてGitHubのSecretsに **GCLOUD_AUTH** として登録してください。[この辺り](https://github.com/actions/gcloud/tree/master/auth#secrets)を参考に。

そしてコードを読みながら（と言ってもSecretの扱い見ただけ）書き換えた

```
    steps:
      - uses: actions/checkout@v1
      - name: Setup Google Cloud
        uses: actions/gcloud/auth@master
        env:
          GCLOUD_AUTH: ${{ secrets.GCLOUD_AUTH }}

      - name: GCP List Clusters
        uses: actions/gcloud/cli@master
        with:
          args: container clusters list
        env:
          CLOUDSDK_CORE_PROJECT: < project id >
```

内部的な動作はアナログな手法と同じだった。base64された **GCLOUD_AUTH** を受け取り、エンコードし、アクティベートする。まぁこれで冗長的なコードは減ったな。

ちなみに actions/gcloud/cli の EntryPoint は gcloud になっている。そのため、argsでコマンドの引数を渡す手法がオススメ。

# よしよし。これでgcloudはできた。あれ？gutilsは？？
と思ったら公式のActionsにはなかった。
ということで、CloudBuildの手法を拝借することにした。

```
      - name: GCS List Bucket
        uses: docker://gcr.io/cloud-builders/gsutil
        with:
          args: ls
        env:
          CLOUDSDK_CORE_PROJECT: < project id >
```
usesはdockerも扱えるため、似たような実装になっているCloudBuildの手法も使えるかなと思ったら案の定使えた。
しかも基本書き方は同じようになる。これでOK。

参考までに、 Terraform も docker image が公開されているし、kubectlも同じように書ける

```
      - name: Terraform version
        uses: docker://hashicorp/terraform
        with:
          args: version
      - name: kubectl version
        uses: docker://gcr.io/cloud-builders/kubectl
        with:
          args: version
        env:
          CLOUDSDK_CORE_PROJECT: < project id >
          CLOUDSDK_COMPUTE_ZONE: < zone name >
          CLOUDSDK_CONTAINER_CLUSTER: < cluster name >
```

これで冗長的な部分は公式の手法で隠蔽されているので、良い感じにはなったかと。
強いて言うなら env を各処理でとりまわせなくて、書き回る必要があるのをその内なんとかしてほしい。