GitHub Actionsで特定フォルダの変更時のみワークフローを実行する方法
問題
GitHubリポジトリに複数のフォルダがある場合、特定のフォルダ(例:folder1
)内のファイルが変更されたときだけGitHub Actionsのワークフローを実行したいというニーズがあります。これにより、不要なワークフローの実行を回避し、CI/CDプロセスを効率化できます。
基本的な解決策
パスフィルターの使用
GitHub Actionsでは、on.push.paths
またはon.pull_request.paths
を使用して、特定のパターンに一致するファイルが変更されたときのみワークフローをトリガーできます。
on:
push:
paths:
- 'folder1/**'
この設定により、folder1
ディレクトリ内のいずれかのファイルが変更された場合にのみ、ワークフローが実行されます。
パターンの詳細
**
: 任意の数のディレクトリとサブディレクトリにマッチ*
: 任意の数の文字にマッチ(パス区切り文字を除く)?
: 任意の1文字にマッチ(パス区切り文字を除く)
高度な設定例
ブランチとの組み合わせ
特定のブランチでのみパスフィルターを適用する場合:
on:
push:
branches: ['main', 'development']
paths: ['folder1/**']
複数のイベントタイプに対応
pushとpull_requestの両方でパスフィルターを適用する場合:
on:
push:
paths:
- 'folder1/**'
pull_request:
paths:
- 'folder1/**'
除外パターンの使用
特定のパスを除外したい場合は、否定パターン(!
プレフィックス)を使用できます。ただし、少なくとも1つの肯定パターンを含める必要があります。
on:
push:
paths:
- 'sub-project/**'
- '!sub-project/docs/**'
この例では、sub-project
ディレクトリ内の変更でワークフローが実行されますが、sub-project/docs
ディレクトリの変更は無視されます。
ワークフローファイル自体の変更に対応
ワークフローファイル(通常は.github/workflows/
内)が変更された場合もワークフローを実行したい場合は、明示的にパスを追加する必要があります。
on:
push:
paths:
- 'folder1/**'
- '.github/workflows/**'
ジョブレベルでのフィルタリング
パスフィルターはワークフロー全体に適用されますが、ジョブごとに条件を設定したい場合は、changed-files
アクションを使用できます。
jobs:
my-job:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Get changed files
id: changed-files
uses: tj-actions/changed-files@v40
- name: Run if folder1 changed
if: contains(steps.changed-files.outputs.all_changed_files, 'folder1/')
run: echo "folder1 was changed!"
注意点
重要
paths
とpaths-ignore
を同じイベントで同時に使用することはできません- パターンの評価順序は重要です(上から順に評価されます)
- 否定パターンだけを使用することはできません(少なくとも1つの肯定パターンが必要)
まとめ
GitHub Actionsのパスフィルター機能を使用することで、特定のディレクトリ内のファイル変更時のみワークフローを実行するように設定できます。これにより、CI/CDプロセスの効率化とリソースの最適化が可能になります。複雑な条件が必要な場合は、サードパーティのアクションを組み合わせることで柔軟な対応ができます。