Skip to content

Instantly share code, notes, and snippets.

@mottaquikarim
Created January 1, 2021 14:30
Show Gist options
  • Save mottaquikarim/ff363d7a83b2b6870e72f8bd52490e30 to your computer and use it in GitHub Desktop.
Save mottaquikarim/ff363d7a83b2b6870e72f8bd52490e30 to your computer and use it in GitHub Desktop.

TL; DR: When integrating golang code coverage with Code Climate, be sure to set the --prefix arg (set it to your pkg github prefix, ie: "github.com/mottaquikarim/esquerydsl") in the after-build stage in order for your src code to be recognized by the test reporter.

If ^^ that didn't make sense, read on below for the full background 👍


I've recently published a golang pkg, called esquerydsl, which facillitates safe construction of elasticsearch queries in golang.

In order to ensure future stability, I wanted to integrate Code Climate for tracking maintainability and test coverage.

I've used CC before on python projects but never for go and while integrating, I ran into a gotcha that I thought I ought to document / share.

Step 0: Write and run some tests!

I won't expound on the actual source code and instead focus on how to run and export test + results to code climate.

Running tests in go is super easy:

https://gist.github.com/f212801106c5bb41a8867cec18f183b4

I prefer to work in docker so I usually run the above as:

https://gist.github.com/eaaff5ef3f985a84a066e7b4fb017d66

(All examples here on out will be run in docker)

Let's break this down before continuing:

  • docker run: within a docker container, let's run some stuff
  • -w /app: our "working directory" will be the app folder
  • -v ${PWD}:/app: we volume mount our current working directory into the "working directory" in the container. This is a nice trick for quickly running tests on source code you are writing during dev
  • golang:1.15: the image we want to run - in this case, golang v1.15
  • go test ./...: finally, the command we want to run in our docker container - which is of course our go test command

Track code coverage

Tracking code coverage in golang is also super easy. We just need to add a single arg to your go test command:

https://gist.github.com/407d216ca5b7ecd989dedef3b733fcc8

The -coverprofile arg tells go where to publish the test coverage results, which can be parsed later on to help visualize your source code's coverage results.

Putting it all together: https://gist.github.com/07fb2ddc32dcc1ab7860443dd0d54718

Now, there is a file called c.out which is available in your current working directory that encodes your line-by-line test coverage data. Great! All we have to do now is upload this to code climate and we are golden.

Sidebar: generating code coverage results as HTML

This is a proper tangent, so feel free to ignore.


I find it super useful to understand/view which lines I missed in my unit tests. While line by line test coverage does not necessarily guarantee stability, I find it to be a useful benchmark for knowing when to stop writing unit tests (somewhere around 90+% is my 👍 point)

To visualize this in go, run the following after your tests:

https://gist.github.com/6bff8eda27c67c9179265d3c03bb4f20

coverage.html can be opened in your browser to walk through your src code and it will visually indicate which lines have been covered by your tests and which lines have been missed.

Getting started with CodeClimate

I'm going to skip this because otherwise this post will get long. My assumption is folks reading this already have a CC Quality account and have a (golang!) repo set up for usage.

Step 1: Downloading the test reporter

Download and run the Code Climate test reporter. Of course, we want to do this in our docker container (there are plenty of examples available on how to do this "bare" around the internet). For me, this entailed:

https://gist.github.com/2c8f036b5126d4c3bb9c93f0e3decb8a

The three main parts here:

  1. We need to download the test reporter, which is available to curl via the CC_URL. I run this in two steps in a single docker run command which is why I have the /bin/bash -c "...steps to run..." line (you can do it in two lines if needed as well)
  2. Update perms to make this download executable. Notice that I run chmod on the renamed file cc-test-reporter (you can call this whatever you want) within the container itself.
  3. Finally, run before-build which sets up the test reporter to send the coverage data. The CC_TEST_REPORTER_ID is significant - this is how CC authenticates your repo's code coverage as really from you. I have it as an envvar since it should not be committed to code anywhere

Step 2: Running the tests with code coverage

This step is easy, basically Step 0:

https://gist.github.com/a8f8361926af1a59d156c4da94460db1

Step 3: Running the after build

This is where I ran into my issue. The easy / documented step is this:

https://gist.github.com/55a7ad4df292a262cbc344c290cef5e3

This is pretty standard at this point: we run the cc-test-reporter with the after-build arg as directed by CodeClimate. And, we pass along the CC_TEST_REPORTER_ID to property identify ourselves. However, the kicker is the command above alone will not work!

When I ran the line above for my esquerydsl package (heads up, I temporarily added the --debug flag too), I ended up with the following output:

https://gist.github.com/37016ccf4d2d2ccd4d93bcdd0abe1c07

To fix, it looks like the --prefix is required, as follows:

https://gist.github.com/664cc18e2e4da2a86d78951ca0742d1d

Note the --prefix=github.com/mottaquikarim/esquerydsl. The full package prefix url is needed for this to work. Once I added this arg, I was able to upload code coverage stats for my pkg just fine. (Check it out here).

The Code

I have this thing tied up in a neat bow at this point and thought I'd share. I use make targets to handle running this in Github Actions. I'll share the recipes below in the hopes maybe it can help someone else in the future.

Makefile

https://gist.github.com/7df431a81298c968ceb53fe26bc4777b

Github Action

I saved this file in: .github/workflows/run-build.yml and in my repo secrets, I saved my CC_TEST_REPORTER_ID so that I can export it as envvar on build time.

https://gist.github.com/245d88507ec22ff7dc2fabdc6c8146a9

Note that running make test-ci will run tests with the codeclimate reporter running and make test just runs normal unit tests for dev/debugging.

The results of the configs above should be viewable in the following:

Happy coding!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment