4
3

More than 1 year has passed since last update.

GitHub Actionsの再利用可能なワークフローに別YAMLファイルで指定したmatrixを与えたい場合

Last updated at Posted at 2023-08-08

GitHub Actionsの再利用可能なワークフローに,入力として別YAMLファイルで指定したmatrixを与える方法について,苦心の末,ようやく実現できましたので,ご報告します.

ElixirとErlang/OTPのバージョンのmatrixを与える場合を例に書きます.

matrixの与え方

通常のmatrixだと次のように与える場合について,

matrix.yml
- otp-version: ['24.3.4.13', '25.3.2.3', '26.0.2']
  elixir-version: ['1.14.5', '1.15.4']

次のように展開し,さらにinclude:の下につけます.エラーにならないよう,.github/workflowsとは別のディレクトリに配置することもポイントです.

.github/actions/matrix.yml
include:
  - otp-version: '24.3.4.13'
    elixir-version: '1.14.5'
  - otp-version: '24.3.4.13'
    elixir-version: '1.15.4'
  - otp-version: '25.3.2.3'
    elixir-version: '1.14.5'
  - otp-version: '25.3.2.3'
    elixir-version: '1.15.4'
  - otp-version: '26.0.2'
    elixir-version: '1.14.5'
  - otp-version: '26.0.2'
    elixir-version: '1.15.4'

再利用可能なワークフローの書き方

次のようにします.

.github/workflows/reusable_ci.yml
name: Reusable workflow

on:
  workflow_call:
    inputs:
      matrix:
        required: true
        type: string
      
jobs:
  reusable_ci:

    name: On ${{ matrix.elixir-version }}, ${{ matrix.otp-version }}
    runs-on: ubuntu-latest
    strategy:
      matrix: ${{ fromJSON(inputs.matrix) }}
    steps:
    - run: echo "done."

fromJSONを用いることがポイントです.

呼び出し側

次のようにします.

name: Caller CI

on:
  pull_request:
    types: [opened, reopened, synchronize]
    branches: [ "main", "develop" ]
  push:
    branches: [ "main", "develop" ]    

jobs:
  constants:
    name: Constants
    runs-on: ubuntu-latest
    outputs:
      matrix: ${{ steps.set-matrix.outputs.matrix }}
    steps:
      - uses: actions/checkout@v3
      - id: set-matrix
        run: |
          json=$(cat ${{ github.workspace }}/.github/actions/matrix.yml| ruby -ryaml -rjson -e 'puts YAML.load(STDIN).to_json')
          echo "matrix=${json}" >> $GITHUB_OUTPUT
  call_reusable_workflows:
    name: Call Reusable Workflows
    needs: constants
    uses: ./.github/workflows/reusable_ci.yml
    with:
      matrix: ${{ needs.constants.outputs.matrix }}

あらかじめ,id: set-matrix としておきます.

YAMLからJSONへの変換のRubyワンライナーcat file.yml| ruby -ryaml -rjson -e 'puts YAML.load(STDIN).to_json' がポイントです.これで1行のJSONで出力されます. (Thanks! @zumin )

その値を環境変数jsonに一旦格納し,echo "matrix=${json}" >> $GITHUB_OUTPUTとすることで,matrix変数への出力として格納します.

それを matrix: ${{ steps.set-matrix.outputs.matrix }} として出力されたmatrixの値を参照したものを,matrixに入れます.

それをその後の呼び出しで,with: matrix: ${{ needs.constants.outputs.matrix }} として,再利用可能なワークフローに渡します.

4
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
3