0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Dependabotでの自動PRを自動マージさせる

0
Posted at

GitHub Actionsなどの依存関係を最新に保つために便利な Dependabot
自動でプルリクエスト(PR)を作成してくれるのは非常に強力ですが、アップデート頻度が高いと「毎回PRを開いて、レビューして、マージする」という作業が意外と面倒になってきますよね。

運用コストが高いと感じることもしばしば...
でもセキュリティ的には、最新版にしておかないといけない

意外と面倒な「日々のアプデ対応」を自動化する

すべてを自動マージしてしまうと、破壊的変更(Breaking Changes)が含まれるメジャーアップデートによってワークフローが壊れてしまうリスクがあります。
動かなくなったり、必須パラメータが変わったりして、予期せぬエラーに繋がりかねません。

一方で、マイナーアップデートやパッチアップデートは、バグ修正やセキュリティパッチが含まれることが多く、できるだけ早く適用したいものです。

そこで、以下のような運用ポリシーを構築します。

  • メジャーアップデート:影響が大きいため、人間が手動でレビュー・マージする。
  • マイナー/パッチアップデート:安全性が高いため(信用して)、自動でApproveしてマージ**する。

これにより、運用リスクを最小限に抑えつつ、日常的なアップデートの運用コストを大幅に削減できます。

実装:自動マージ用のGitHub Actions

リポジトリの .github/workflows/dependabot-auto-merge.yml として以下のワークフローを作成します。

name: Dependabot auto-merge
on: pull_request

permissions:
  pull-requests: write
  contents: write

jobs:
  dependabot:
    runs-on: ubuntu-latest
    # Dependabotが作成したPRのみを対象にする
    if: github.event.pull_request.user.login == 'dependabot[bot]'
    steps:
      # Dependabotのメタデータを取得する公式アクション
      - name: Dependabot metadata
        id: metadata
        uses: dependabot/fetch-metadata@25dd0e34f4fe68f24cc83900b1fe3fe149efef98 # v3.1.0
        with:
          github-token: "${{ secrets.GITHUB_TOKEN }}"

      # メジャーアップデート「以外」であれば自動でApproveする
      - name: Auto-approve Dependabot PRs
        if: steps.metadata.outputs.package-ecosystem == 'github_actions' && steps.metadata.outputs.update-type != 'version-update:semver-major'
        run: gh pr review --approve "$PR_URL"
        env:
          PR_URL: ${{ github.event.pull_request.html_url }}
          GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

      # メジャーアップデート「以外」であればオートマージを有効化する
      - name: Enable auto-merge for Dependabot PRs
        if: steps.metadata.outputs.package-ecosystem == 'github_actions' && steps.metadata.outputs.update-type != 'version-update:semver-major'
        run: gh pr merge --auto --merge "$PR_URL"
        env:
          PR_URL: ${{ github.event.pull_request.html_url }}
          GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

技術的な解説

1. dependabot/fetch-metadata でバージョン変化を検知

このアクションを使うことで、Dependabotが検知したアップデートのメタデータ(パッケージマネージャーの種類や、アップデートの度合い)を取得できます。

steps.metadata.outputs.update-type には以下のいずれかが格納されるため、これを利用して条件分岐を行います。

  • version-update:semver-major(メジャー)
  • version-update:semver-minor(マイナー)
  • version-update:semver-patch(パッチ)

今回は update-type != 'version-update:semver-major' と指定することで、マイナーとパッチのみを対象にしています。

2. GitHub CLI (gh) による自動化

GitHub Actionsランナーには標準で GitHub CLI がインストールされています。これを利用して、以下の2ステップを実行しています。

  • gh pr review --approve: PRを自動承認
  • gh pr merge --auto --merge: 自動マージ

3. 必要最小限の permissions 設定

GitHub Actionsでデフォルトで生成される secrets.GITHUB_TOKEN を使用します。PRのApproveやマージを行う権限が必要なため、ワークフローの冒頭で明示的に以下の権限を付与しています。

permissions:
  pull-requests: write
  contents: write

💡 ちょっとした注意点:エコシステム名の「表記ゆれ」

Dependabotの設定ファイル(dependabot.yml)では、GitHub Actionsを対象にする際、以下のようにハイフン繋ぎで指定します。

# dependabot.yml の設定
updates:
  - package-ecosystem: "github-actions" # ハイフン繋ぎ

しかし、メタデータ取得アクションから返ってくる steps.metadata.outputs.package-ecosystem の値は、アンダースコア繋ぎgithub_actions になります。

ワークフロー側の条件分岐で "github-actions" と書くと、条件に合致せず自動マージが動かなくなってしまうため注意してください。

ルールの設定

自動マージを行えるようにするのと合わせて、リポジトリのルールを設定するのが重要です。
マイナー・パッチアップデートのPRは自動マージされるようになりますが、それでもワークフローが壊れる可能性はゼロではありません。
そのため、特定のテストが通らない場合はマージできないように、ブランチ保護ルールを設定しておくことをおすすめします。

まとめ

依存関係を常に最新に保つことはセキュリティ上とても重要ですが、すべてを人間の手でレビューするのは現実的ではありません。

今回紹介した「メジャーアップデート以外は自動マージ」というハイブリッドな運用を取り入れることで、以下のメリットが得られます。

  • 開発効率の向上: 日常的なマイナー/パッチアップデートは完全自動で処理される。
  • 安全性の担保: 破壊的変更リスクのあるメジャーアップデートだけを人間がじっくりレビューできる。

ぜひ自分に合った安全な自動化運用の構築の参考にしてみてください!

参考資料

0
0
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
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?