How to create filter on both tag and branch

Hello everyone!

We’ve spent quite some time trying to figure out how to create a workflow that will only be run for commits that are both on master and tagged with v* in order to identify release commits.

The workflow we have in mind for creating releases is as follows:

  1. Checkout branch release-prep

  2. Merge the current master branch into it

  3. Bump the version within the code

  4. Update the CHANGELOG.md file

  5. Commit the changes

  6. Add a tag containing the version number (prefixed with v)

  7. Push and open pull request to master

  8. Go through normal review workflow keeping the tag at the branch head

Once everything is fine, the branch (along with the tag) will be merged into master which is then supposed to trigger publishing a release both to github and pypi.

If you’re interested, our project is:
https://github.com/real-digital/esque/

The filter variants we’ve tried are:

on:
push:
branches:
- master
tags:
- v*

on:
push:
tags:
- v*
branches-ignore:
- "*"
- "!master"

on:
  push:
    tags:
      - v*
    branches-ignore:
      - "!master"

on:
push:
branches:
- master
-"refs/tags/v\*"

Based on https://github.community/t5/GitHub-Actions/How-to-restrict-execution-of-GitHub-Actions-workflow-on-tags/td-p/29567

We’re now falling back to a solution where the workflow itself fails when the conditions are not met. How do other people do this? I know there is a release draft option but there is so much you can miss in a release code wise that we’d like to enforce reviews and tests on it before it’s actually published.

1 Like

Based on current paths/tags filter for on: push event, it doesn’t supported to filter a commit which are included in a release tag meanwhile in master branch.

There is a way to trigger a workflow when a new release published , using

on:

  release:

    types: [published]

Please refer to this document: https://help.github.com/en/actions/automating-your-workflow-with-github-actions/events-that-trigger-workflows#release-event-release

Hey, thanks for your answer!

That is actually what we do now. So once the release PR gets merged, we create a release manually. Once that release is published, it creates the tag and the corresponding pipeline pushes the package to pypi.

Guess there isn’t really a way to do it fully automated.

Though I am replying to an old message, this is how I found the workaround.

Create a filter on both tag and branch is to compare the hash commit of the tag and master.

We can create a job that will check the hash commit. If the hash commit match than run another job to perform your desired actions. Else, if the hash commit don’t match you can make the workflow fail so that your next job doesn’t run.

This is how I do it.

name: Check Deployment and versions

on:
  push:
    tags:
      - v1.*

jobs:
  check-tag-branch:
    runs-on: ubuntu-latest
    steps:
    - name: get tag commit hash
      id: tag-commit-hash
      run: |
        hash=${{ GITHUB.SHA }}
        echo "::set-output name=tag-hash::${hash}"
        echo $hash
    - name: checkout master
      uses: actions/checkout@v2
      with:
        ref: master
    - name: get latest master commit hash
      id: master-commit-hash
      run: |
        hash=$(git log -n1 --format=format:"%H")
        echo "::set-output name=master-hash::${hash}"
        echo $hash
    - name: exit if tag commit hash don't match master commit hash
      if: steps.tag-commit-hash.outputs.tag-hash != steps.master-commit-hash.outputs.master-hash
      run: exit 1

  build-base:
    needs: [check-tag-branch]
    runs-on: ubuntu-latest
    steps:
    - name: setup python
      uses: actions/setup-python@v1
    - name: echo something
      run: echo "This steps run successfully"
1 Like

Based on the answer of @khatiwadanilav I created an action which currently using in my workflows to only trigger jobs when a tag was pushed to a specific branch:

name: Github tag test
on:
  push:
    tags:
      - "v*.*.*"
jobs:
  on-main-branch-check:
    runs-on: ubuntu-latest
    outputs:
      on_main: ${{ steps.contains_tag.outputs.retval }}
    steps:
      - uses: actions/checkout@v2
        with:
          fetch-depth: 0
      - uses: rickstaa/action-contains-tag@v1
        id: contains_tag
        with:
          reference: "main"
          tag: "${{ github.ref }}"
  tag-on-main-job:
    runs-on: ubuntu-latest
    needs: on-main-branch-check
    if: ${{ needs.on-main-branch-check.outputs.on_main == 'true' }}
    steps:
      - run: echo "Tag was pushed to main."
      - run: echo ${{needs.on-main-branch-check.outputs.on_main}}
  tag-not-on-main-job:
    runs-on: ubuntu-latest
    needs: on-main-branch-check
    if: ${{ needs.on-main-branch-check.outputs.on_main != 'true' }}
    steps:
      - run: echo "Tag was not pushed to main."
      - run: echo ${{needs.on-main-branch-check.outputs.on_main}}

You can see this workflow in action here. I also send a feature request to the GitHub support to support this without using a workaround. Hope GitHub adds this feature soon. In the meantime, feel free to create an issue or a pull request onto my workaround if something is missing.