Skip to content

👷 How to integrate Github Checks with Google Cloud Build and Python Tests

Posted on:May 10, 2019 at 03:57 PM

Written by Alejandro Barone and Matias Vergara.

At Kunder, we use Jenkins and Github Checks to make sure our code meets certain standards (unit tests, code coverage and coverage differential). Google Cloud Build recently released a Github Checks integration and since the project we were working on was built entirely on Google Cloud, we wanted to try out it’s CI/CD products.

Our dev team was wondering if we could do the same with Cloud Build, so we set three goals, show a green Github check if :

  1. All unit tests are executed correctly.
  2. Code coverage is greater than 90%.
  3. No problems found by python linter (in this project we use flake8).

These are the steps we took:

Connect Github with Cloud Build

To connect Github Checks with Cloud Build, first go to the Cloud Build App on the Github Marketplace and then select a plan:

Setup with Google Cloud Build

You will then be presented with an option to connect all repositories or only one. We recommend only connecting your current project’s repository. After installing the app, you will be redirected to Google Cloud Platform to finalize the process. After two more steps, the integration process is complete.

Cloud Build Steps

Now, every push to Github on any branch will trigger a build on Cloud Build. The Cloud Build looks for a file called cloudbuild.yaml or Dockerfile in the root of your repository (hopefully in the future, the location and name of this file will be configurable). In this case, we used the following cloudbuild.yaml file:

steps:
 - name: python:3.7
  id: INSTALL
  entrypoint: python3
  args:
  - '-m'
  - 'pip'
  - 'install'
  - '-t'
  - '.'
  - '-r'
  - 'functions/requirements.txt'
 - name: python:3.7
  entrypoint: python3
  id: RUN-UNIT-TESTS
  args:
  - '-m'
  - 'nose2'
  - '-s'
  - 'functions'
  - '-c'
  - 'functions/nose2.cfg'
  waitFor:
  - INSTALL
 - name: python:3.7
  entrypoint: python3
  id: RUN-COVERAGE-TESTS
  args:
  - '-c'
  - 'import sys; from pycobertura import Cobertura, TextReporter; cobertura = Cobertura("functions/coverage.xml"); tr = TextReporter(cobertura); coverage = tr.generate().split(" ")\[-1\].strip("%"); print("Coverage OK:",coverage + "% > 90%") if float(coverage) > 90 else sys.exit("Coverage is less than 90%")'
  waitFor:
  - RUN-UNIT-TESTS
 - name: python:3.7
  entrypoint: python3
  id: RUN-LINTER-CHECK
  args:
  - '-m'
  - 'flake8'
  - '--ignore=E501'
  - 'functions/'
  waitFor:
  - INSTALL

This YAML file tells Cloud Build what to do. It’s divided in steps and each step represents a task.

  1. The first step uses the python container to install all of our requirements (the requirements file is inside a functions folder and contains nose2, pycobertura and flake8 which are the python packages needed in the build steps). The first argument -m is for running a python module.
  2. Next, we run our test command. In this project we used nose2, but most testing libraries should work similarly. The command is nose2 -s functions/ -c functions/nose2.cfg and the step needs the additional -m argument. If a single test fails, the build fails.
  3. Now we check if the coverage is greater than 90%. Cloud Build will run a python command that uses pycobertura. It loads the coverage.xml file, finds the coverage and makes sure it’s greater than 90. If it isn’t, we call sys.exit() and the build fails.
  4. Lastly, we run our flake8 linter (ignoring line length, we don’t care much about that). If flake finds any problem, the build fails.

If the build fails, the Cloud Build notifies Github and the red check of terror is shown. Else, we get a beautiful green check:

Github check with Cloud Build

Cloud Build Github App wishlist:

Show steps as separate checks on Github. It would also be nice if a step could be omitted from showing on Github (no need to show the INSTALL step for example).

Show custom information on the Github check. For now, if anything went wrong, you have to enter the Cloud Build console. Furthermore, the Github Check detail page doesn’t show any useful information:

Detail page doesn’t show any useful information.

It could show how many tests failed, what the current coverage is etc.

Filter steps by branch name. It would be nice to be able to execute certain steps only if a certain branch triggered the build. For example, deploy the code if the branch is called staging. There is a workaround, but it would be better if it were supported natively.

Trigger when a pull request is opened or has a new commit, not on any commit. Running a build for every commit might end up being costly, triggering on pull requests would be enough.

Conclusions:

Cloud Build is great at running builds: it’s fast, easy to use and easy to set up. Creating a trigger for deploying our code when a pushing to our master branch was also very easy and it only took us a few minutes. It’s also awesome having everything in the same GCP project, no need to use external services and only one billing at the end of the month! Our team was pleased with the results we achieved.

But in our opinion the integration with Github is still in its early stages. There isn’t much to configure and hopefully Google will continue developing the Cloud Build Github App to show more information and be more helpful to developers.