プライベートリポジトリにあるGitHub Workflowをほかのリポジトリで使う
この記事では、プライベートリポジトリにおいたReusable Workflowを、他のリポジトリで参照して使う方法を説明する。
プライベートリポジトリに置いたワークフローを参照して使えるようになった
処理内容が変わらないワークフローを、複数のリポジトリで実行させたいケースが多くある。
たとえばJavaScriptのプロジェクトの場合は、どのリポジトリでもESLintを実行したい。
GitHub Actionsでそれを実現するには、それぞれのリポジトリでワークフローファイルを持つ必要があり、それらのファイルをメンテナンスしていくのが手間である。
その解決手段のひとつとして、GitHubのReusable Workflowがある。
Reusable Workflowは、ひとつのワークフローを他のリポジトリで共有して使うことができる仕組みである。
ただし共有するワークフローファイルはパブリックなリポジトリに置く必要があり、公開したくないワークフローファイルに対しての運用ができなかった。
しかし、2022年12月14日に、プライベートリポジトリにあるActionやReusable Workflowを、ほかリポジトリから参照して使うことができるようになった。
GitHub Actions – Sharing actions and reusable workflows from private repositories is now GA
具体的には、プライベートリポジトリに置いたReusable Workflowを参照できる参照できる設定が追加された。
同じユーザーアカウントや組織内であれば、プライベートリポジトリに置いたワークフローを他のリポジトリと共有できるようになった。
Reusable Workflow を置くリポジトリのワークフロー
Reusable Workflow を作る
複数のリポジトリで共有して使うワークフローを定義する。
例としてESLintを実行するワークフローを作ることにする。
GitHubにプライベートリポジトリを作る。
このリポジトリを、複数のリポジトリ間で共有するワークフローの置き場所とする。
リポジトリ名は「github-actions-shared-workflows」とした。次の内容で、「.github/workflows」の下に共有するワークフローを作成する。 ファイル名は
eslint.yml
とした。
ワークフローをReusable Workflowにするには、on.workflow_call
を指定する。
name: eslint
on:
workflow_call:
jobs:
lint:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Use Node.js
uses: actions/setup-node@v3
with:
node-version: 16
cache: 'npm'
- name: Install dependencies
run: npm ci
- name: Run lint
run: npm run eslint
Actions のアクセス許可を有効にする
プライベートリポジトリに置いたReusable Workflowを共有するには、リポジトリの設定で、Actionsのアクセス許可を有効にする。
- Reusable Workflowを置いたリポジトリの[Settings]を開く。
- サイドメニューの[Actions]を展開し、[General]を選択する。
- 「Access」セクションで、「Accessible from repositories owned by the user 'USER_NAME'」を選択する。
- [Save]をクリックする。
Reusable Workflow を参照して使うワークフロー
Reusable Workflowを参照して使う側のワークフローを作成する。
このリポジトリには、すでにESLintが導入されているとする。そのため、ESLintの設定方法はこの記事に記載しない。
次の内容で、Reusable Workflowを参照するワークフローを「.github/workflows」の下に作成する。
他のリポジトリにあるReusable Workflowを参照するには、job.<job_name>.uses
で使うワークフローのパスを指定する。
name: eslint
on:
pull_request:
jobs:
lint:
uses: chick-p/github-actions-shared-workflows/.github/workflows/eslint.yml@main
動作確認
今回参照する側のワークフローでは、Pull Requestを作成したときに実行されるように設定した。
そのためPull Requestを作って動作を確認する。
プライベートリポジトリに置いたReusable Workflowが呼び出されて実行できている。
このリポジトリではESLintがエラーで落ちるような内容にしているため、CIとしては失敗することが期待値である。
リポジトリごとに個別の値を渡したい
実際の運用では、Reusable Workflowを参照するリポジトリごとに、ワークフローの微妙な違いが発生することもある。
たとえば、Node.jsのパッケージマネージャーがYarnである場合や、リポジトリごとに少し異なるコマンドを使いたい場合が考えられる。
Reusable Workflowでは、参照して使う側から入力値を渡すことができるため、このようなケースでも対応できる。
Reusable Workflow を置くリポジトリ側
参照するワークフロー側から入力値を渡すには、workflow_call.input
に変数名や型を定義する。
定義した変数は、${{ inputs.<variable_name
}}` で取り出せる。
参照:Using inputs and secrets in a reusable workflow
修正後のワークフローでは、次のことを対応することにした。
- パッケージマネージャーをnpmかyarnを選べる
- Lintのコマンドを渡せるようにする
name: eslint
on:
workflow_call:
+ inputs:
+ manager:
+ required: false
+ type: string
+ default: 'npm'
+ command:
+ required: false
+ type: string
+ default: 'npm run eslint'
jobs:
lint:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Use Node.js
uses: actions/setup-node@v3
+ with:
+ node-version: 16
+ cache: ${{ inputs.manager }}
- - name: Install dependencies
+ - name: Install dependencies (npm)
+ if: ${{ inputs.manager == 'npm' }}
run: npm ci
+ - name: Install dependencies (yarn)
+ if: ${{ inputs.manager == 'yarn' }}
+ run: yarn install
- name: Run lint
- run: npm run eslint
+ run: ${{ inputs.command }}
Reusable Workflow を参照して使う側
参照して使う側から入力値を設定するには、with.<variale_name>
を使う。
name: eslint
on:
pull_request:
jobs:
lint:
uses: chick-p/github-actions-workflow-provider/.github/workflows/eslint.yml@main
+ with:
+ manager: "yarn"
+ command: "yarn lint:eslint"
動作確認
参照して使う側のリポジトリで、パッケージマネージャーをYarnにして、Pull Requestを作成する。
無事、manager
とcommand
に設定した値が使われた。