id:pokutuna
Web Developer

Cloud Build の waitFor の挙動

Google Cloud Buildにおいて、

ビルドステップの順序の構成  |  Cloud Build のドキュメント  |  Google Cloud

waitFor の値が指定されない場合、ビルドステップは、ビルド リクエスト内の先行するすべてのビルドステップが正常に完了するまで待機した後に実行されます。

"先行する" とは

  • yaml 上で先に定義されている
  • 既に実行されているタスク

のどちらやねん、と使ってて思ったので調べた

以下のような cloudbuild.yaml を用意して
$ gcloud builds submit --config ./cloudbuild.yaml . する。

waitFor のない task2-2 がどのタイミングで実行されるかを見たい。

f:id:pokutuna:20200105043154p:plain:w300

steps:
   - id: prepare
     name: alpine:latest
     entrypoint: /bin/echo
     args: ["prepare"]
 
   - id: task1
     name: alpine:latest
     entrypoint: /bin/ash
     args: ["-c", "sleep 20s"]
     waitFor: ["prepare"]
 
   - id: task2-1
     name: alpine:latest
     entrypoint: /bin/ash
     args: ["-c", "sleep 10s"]
     waitFor: ["prepare"]
 
   - id: task2-2
     name: alpine:latest
     entrypoint: /bin/ash
     args: ["-c", "sleep 10s"]
 
   - id: task3
     name: alpine:latest
     entrypoint: /bin/ash
     args: ["-c", "sleep 30s"]
     waitFor: ["prepare"]
 
   - id: last
     name: alpine:latest
     entrypoint: /bin/ash
     args: ["-c", "sleep 10s"]
 BUILD
 Starting Step #0 - "prepare"
 Step #0 - "prepare": Pulling image: alpine:latest
 Step #0 - "prepare": latest: Pulling from library/alpine
 Step #0 - "prepare": e6b0cf9c0882: Pulling fs layer
 Step #0 - "prepare": e6b0cf9c0882: Verifying Checksum
 Step #0 - "prepare": e6b0cf9c0882: Download complete
 Step #0 - "prepare": e6b0cf9c0882: Pull complete
 Step #0 - "prepare": Digest: sha256:3983cc12fb9dc20a009340149e382a18de6a8261b0ac0e8f5fcdf11f8dd5937e
 Step #0 - "prepare": Status: Downloaded newer image for alpine:latest
 Step #0 - "prepare": docker.io/library/alpine:latest
 Step #0 - "prepare": prepare
 Finished Step #0 - "prepare"
 Starting Step #4 - "task3"
 Starting Step #2 - "task2-1"
 Starting Step #1 - "task1"
 Step #1 - "task1": Already have image: alpine:latest
 Step #4 - "task3": Already have image: alpine:latest
 Step #2 - "task2-1": Already have image: alpine:latest
 Finished Step #2 - "task2-1"
 Finished Step #1 - "task1"
 Starting Step #3 - "task2-2"
 Step #3 - "task2-2": Already have image: alpine:latest
 Finished Step #4 - "task3"
 Finished Step #3 - "task2-2"
 Starting Step #5 - "last"
 Step #5 - "last": Already have image: alpine:latest
 Finished Step #5 - "last"
 PUSH
 DONE

結果

  • task3, task2-1 , task1 は同時に起動する
    • waitForLIFO なのか、毎回 yaml 上で後の記述のものがログの上では先に start されている気がする(未確認)
  • task2-2
    • task1task2-1 を待つ
      • task1 を待つので先に定義しているものを待つ
    • task3 を待たない
      • 先に開始されているが yaml 上では後に定義されているものは待ってない

ということで、"先行する" は yaml のステップ定義上で先行しているもの、先に開始されているステップではない、という挙動とおもわれる。

Cloud Build、分岐して合流するステップを書きたい場合、分岐内のステップが多いと id 振ったり waitFor したりはやや記述がめんどいのだけれど、/workspace を volume として引き継いで各ステップは docker run していくだけというのがなかなかおもしろい。