[GitHub]Workflowでバージョン番号管理とrelease作成に大変便利なGitHub Tagsの使い方を出力図例込でまとめてみた

ActionsのWorkflow内でtagを作成するのに便利な「GitHub Tag」について、具体的な利用例がなかなか見つからなかったこともあり、動作確認した結果を備忘録兼ねて書いてみました。
2020.11.27

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

はじめに

Deployする際のバージョン番号更新について色々とやり方を検討していたものの、権限や手間の問題で悩ましいところでした。

社内にて相談した結果、GitHub Tagが無難ではないかということに。試してみたものの実際の動作例の掲載が少なく、ソースコードと照らし合わせながらの作業となりました。

便利な機能が多いことは確かなので、確認の手間が元で躊躇するケースが減らせればと動作確認の例をまとめてみました。

GitHub Tagの使い方

利用の多いと思われるバージョンのインクリメントと変更履歴の本文掲載を中心にしています。

バージョンのインクリメント

初期設定でのdefault_dumpによるインクリメント先は以下の位置になります。

type increment reset
major 1.0.0 minor & patch
minor 0.1.0 patch
patch 0.0.1 -
false - -
major.minor.patch

majorアップデートにした場合に、3.4.1なら4.0.0へ更新されます。

これ以外にもインクリメントのルールが存在します。これについては次項にて触れます。

キーワードを元にしたバージョンインクリメント

Conventional Commitsを利用して、最後のタグ以降に積まれたコミットメッセージから特定のキーワードを含むコミットを元にインクリメントを行えます。

リポジトリのREADMEに利用できるキーワードが記載されていますが、実際に本文として扱われる場合は以下のようになります。

キーワード type 本文 screen shot
fix patch Bug Fixes
feat minor Features
perf
BREAKING CHANGE
major Performance Improvements

キーワードが存在する場合、default_bumpによるインクリメント指定は無視されます。 キーワードによるインクリメントは、含まれる中で一番大きなものが1つ加算されます(major > minor > patch)。その他はdefault_bumpと同じ扱いになります。

本文として取得されるフォーマットは以下の構成になっています。:(コロン)の後に半角スペースを入れることで認識されます。

fix: XXXXX

BREAKING CHANGEのみ末尾に必要です。

ドキュメントによる説明 記述例 実出力
<type>[optional scope]: <description>

[optional body]

[optional footer(s)]
fix: test

aaaaaa

BREAKING CHANGE: test

キーワードを含む修正をリリース本文に追加する

以下のようなコミットを積むとします。
Author: haoyayoi <xxxxxxxxx@xxxxxxxx>
Date:   Thu Nov 26 18:53:39 2020 +0900

    feat: add

commit dfef7bdee663669f71c097c01d74b2ba696a75e7
Author: haoyayoi <xxxxxxxxx@xxxxxxxx>
Date:   Thu Nov 26 18:53:13 2020 +0900

    fix: test

以下のstepが含まれるActionを実行すると、

    - name: Bump version and push tag
      id: tag_version
      uses: mathieudutour/github-tag-action@v5
      with:
        github_token: ${{ secrets.GITHUB_TOKEN }}
        default_bump: "minor"
    - name: Publish release
      uses: actions/create-release@v1
      env:
        GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
      with:
        tag_name: ${{ steps.tag_version.outputs.new_tag }}
        release_name: Release ${{ steps.tag_version.outputs.new_tag }}
        body: ${{ steps.tag_version.outputs.changelog }}

スクリーンショットのような内容がreleaseの本文に出力されます。changelogが反映された結果です。

ポイントは実際の修正内容問わず、前回のタグ以降に積まれたコミットのうち、メッセージにキーワードが含まれているものを全て拾うところです。一つのissueに対して細かいcommitを積んだ場合には、rebaseで一つにまとめる等の工夫が必要です。

独自tagを設定する

custom_tagに指定します。

    - name: Bump version and push tag
      id: tag_version
      uses: mathieudutour/github-tag-action@v5
      with:
        github_token: ${{ secrets.GITHUB_TOKEN }}
        default_bump: "minor"
        custom_tag: "test"

ポイントとしてActionのインクリメント動作を完全に上書きするところです。実装が分岐になっています。

    if (customTag) {
      newVersion = customTag;
    } else {
      let previousTag: SemVer | null;
      if (!latestPrereleaseTag) {
        previousTag = parse(latestTag.name);
      } else {
        previousTag = parse(
          gte(latestTag.name, latestPrereleaseTag.name)
            ? latestTag.name
            : latestPrereleaseTag.name
        );
      }

tagのプレフィックス

tag_prefixに指定します。

    - name: Bump version and push tag
      id: tag_version
      uses: mathieudutour/github-tag-action@v5
      with:
        github_token: ${{ secrets.GITHUB_TOKEN }}
        default_bump: "minor"
        tag_prefix: "test"

初期値はvとなり、1.0.0ならv1.0.0となります。スタンダードな初期設定だと思われるため、要件として設定が必要な場合を除いてはそのままでも問題ないと思われます。

あとがき

キーワードベースのバージョンインクリメントについてはコミット時のルール付を行っていれば利便性は高そうです。changelogのrelease本文出力については、rebase操作への慣れや、releaseに載せる基準をある程度決めておく必要があると感じました。

使い方について迷っている場合の参考になると幸いです。

参考リンク