GitHub actions: how to push a GitHub status in addition of GitHub checks

Bertrand Paquet - Aug 27 '21 - - Dev Community

GitHub actions are incredibly efficient to quickly deploy a CI on a project, especially because of the native parallelism system.

But we found some downsides along the way. One downside is the result of a GitHub actions is a Check, not a Status.
There are identical in the UI, but are not in the API. In the image below, the last line is a status in the API, but all the lines above are checks at API Level.

image

What is wrong with that? At Doctolib, we have a lot of automation relying on statuses, not on checks. To onboard some of our projects on Github action, we were looking for an elegant solution.

The first idea is to add a step at the end of the workflows, which push a status from here.
Something like:

      - name: Create status
        run: |
          curl --request POST \
          --url https://api.github.com/repos/${{ github.repository }}/statuses/${{ github.event.workflow_run.head_commit.id }} \
          --header 'authorization: Bearer ${{ secrets.GITHUB_TOKEN }}' \
          --header 'content-type: application/json' \
          --data '{
            "state": "${{ github.event.workflow_run.conclusion }}",
            "context": "unit test (kube)",
            "target_url": "${{ github.event.workflow_run.html_url }}"
            }' \
          --fail
Enter fullscreen mode Exit fullscreen mode

This solution is working, but only for green build (successful build). For red build (failed build), we can use a failure condition. If we have workflows with multiple jobs, we have to put this failure condition in every job. This can be painful, and add code duplication.

So we found a simpler solution: have an independent GitHub workflow which listen to the CI workflow (success AND failure), and set a status accordingly.

name: Set test status

on:
  workflow_run:
    workflows: ["Run tests"]
    types:
      - completed

jobs:
  set_status:
    runs-on: ubuntu-latest
    permissions:
      statuses: write 
    steps:
      - name: Create status
        run: |
          curl --request POST \
          --url https://api.github.com/repos/${{ github.repository }}/statuses/${{ github.event.workflow_run.head_commit.id }} \
          --header 'authorization: Bearer ${{ secrets.GITHUB_TOKEN }}' \
          --header 'content-type: application/json' \
          --data '{
            "state": "${{ github.event.workflow_run.conclusion }}",
            "context": "unit test (kube)",
            "target_url": "${{ github.event.workflow_run.html_url }}"
            }' \
          --fail
Enter fullscreen mode Exit fullscreen mode

Feel free to reuse it, you just have to change:

  • The name of your CI workflow in the on clause.
  • The name of the status you want to push on GitHub in the context params.
. . . . . . . . . . . . . . . . . . . . . . . . . . . .