GitHub Actionsで複数のworkflowを連携する時にハマったあれこれ
GitHub Actionsで或るworkflowが終わったら別のworkflowを動かす、みたいなことをやりたくなった時にちまちまハマったのでメモとして残します。
workflow_run
で呼び出されたworkflowで前workflowのステータスを取る
これはハマったことというか「こうやれば良い」という話なんですが、
on: workflow_run: workflows: - check types: - completed jobs: ...
みたいに書いておくと check
workflowが完了した時にこのworkflowが呼び出されるのですが、この時 check
の成否は関係無く呼び出されます。
従って、check
が完了した時にのみ実行したい時には以下のようにステータスチェックを入れる必要があります。
on: workflow_run: workflows: - check types: - completed jobs: do_something: if: ${{ github.event.workflow_run.conclusion == 'success' }} steps: ...
ref: Events that trigger workflows - GitHub Docs
それはそうとして completed
typeだけじゃなくて succeeded
や failed
みたいなtypeを workflow_run
で指定できると嬉しいような気はするのですが......
workflow_run
はdefault branchに存在していないと動かない
Events that trigger workflows - GitHub Docs
Note: This event will only trigger a workflow run if the workflow file is on the default branch.
公式ドキュメントにめっちゃ目立つように書いてある!!
workflowを整備するブランチで作業してて「おかしいな〜動かないな〜」と思っていたらこういう話だったというオチ。default branchに workflow_run
を使うworkflowをpushしておかなければ駄目。
workflow_run
で呼び出されるworkflow中では github.ref_type
は常に branch
になる
1つ前の話題にも通ずるところですが、
Events that trigger workflows - GitHub Docs
このドキュメントにもあるように `GITHUB_REF` はdefault branchとなっているため github.ref_type
は常に branch
となります。
on: workflow_run: workflows: - check types: - completed jobs: do_something: if: ${{ github.ref_type == 'tag' }} steps: ...
上のように書いていると、仮に元のworkflow (この場合は check
) がtagのpushによってトリガーされていたとしても github.ref_type
は branch
となるため絶対に do_something
は実行されません。これはちょっとハマった......
workflow_call
で呼び出されたworkflowからはrepositoryに登録されているsecretsを直接参照できない
on: workflow_call: jobs: do_something: runs-on: "ubuntu-latest" steps: - env: PASSWORD: ${{ secrets.PASSWORD }} run: | echo ${{ env.PASSWORD }} ...
今度は workflow_run
ではなく workflow_call
の話題。なぜなら workflow_run
では「tagがpushされた時だけなんかやる」が実現できなかったため......
workflow_call
により、他のworkflowから明示的に呼び出されたworkflowはrepositoryに登録されているsecretsを直接参照することができないため、上記のechoは何も表示しません。
on: workflow_call: secrets: PASSWORD: required: true jobs: do_something: runs-on: "ubuntu-latest" steps: - env: PASSWORD: ${{ secrets.PASSWORD }} run: | echo ${{ env.PASSWORD }} ...
上記のように workflow_call.secrets
で受け取る変数を明示しておいて、
call-workflow: uses: ./.github/workflows/next.yml secrets: PASSWORD: ${{ secrets.PASSWORD }}
のような感じで呼び元のworkflowから適切に渡してあげる必要があります。
ref: Reusing workflows - GitHub Enterprise Cloud Docs
というわけで、これらを総合した「tagがpushされ、なおかつ元のworkflow (この場合は check
job) が成功した時にrepoに登録されたsecretsを渡しながら別のworkflowを呼び出す」という定義を書きたい時は元のworkflowでは
on: push: jobs: check: ... call-workflow: needs: [check] if: ${{ github.ref_type == 'tag' }} uses: ./.github/workflows/next.yml secrets: PASSWORD: ${{ secrets.PASSWORD }}
と書いておきつつ、呼ばれるworkflowでは
on: workflow_call: secrets: PASSWORD: required: true jobs: do_something: ...
というふうに書いておけば目的を満足できることがわかりました。これがやりたかった......