How To Level Up Your Angular Unit Testing Game (2/3)
Tags: testing, angular, tips, webdev
Published: 2019-01-21 20:41:40

---
title: How To Level Up Your Angular Unit Testing Game (2/3)
published: true
description: Tips to run Angular unit tests and customize your test tooling
tags: testing,angular,tips,webdev
cover_image: https://github.com/alisaduncan/tutorial-angular-httpclient/blob/test-configuration/post-images/level-up-mario.jpg?raw=true
series: level-up-angular-unit-testing 
---

_This is the second post in the series about Angular unit testing. If you are unfamiliar with using Angular CLI, please read the first post in the series._

In [the previous post](https://dev.to/alisaduncan/how-to-level-up-your-angular-unit-testing-game-13-7a1), we learned how to pass parameters into Angular CLI to run unit tests. In this post, we'll dive into Karma configuration and make the test runner more snazzy by configuring it for our unique needs. It's time to level up your testing game and get pumped up to unit test!

![](https://media.giphy.com/media/bdpIDWZFkI67S/giphy.gif)


# Follow Along

We're using Angular CLI to test the application and using code from a previous post I wrote. 

{% link https://dev.to/alisaduncan/intercepting-http-requests---using-and-testing-angulars-httpclient %}

You can clone the [tutorial-angular-httpclient](https://github.com/alisaduncan/tutorial-angular-httpclient) and run tests too. All the level ups discussed in the posts are found in "test-configuration" branch.


# Karma Configuration

In your Angular app, find `$/src/karma.config.js`. This is the config file Karma uses to run tests. Let's start editing it!

## Reporters
Out of the box, Angular CLI enables 'progress' and 'kjhtml' reporters. In v7 and v5, you can configure reporters via commandline but sadly, that option was removed in v6. We can still make changes via the config file for v6 though!

If you are using Angular v5 or v7, pass in a comma separated list of reporters using the `reporters` flag.

To change _karma.config.js_, in the `reporters` array, remove 'progress' and replace it with 'dots'. Now when you run tests, the output to the console uses the dot reporter instead of the progress reporter.

![](https://cdn.someecards.com/someecards/usercards/MjAxMy04Zjg3NGFhZDE1NTI2Mjg2.png)


## Add A New Reporter
But our test output could be way better. It's nothing to write home about yet. Let's try adding a reporter. 

Add the 'karma-spec-reporter' npm package 

``` bash
npm install karma-spec-reporter --save-dev
```

Require the reporter in _karma.conf.js_ by adding the require statement to the `plugins` array

```js
plugins: [
      require('karma-jasmine'),
      require('karma-chrome-launcher'),
      require('karma-jasmine-html-reporter'),
      require('karma-coverage-istanbul-reporter'),
      require('@angular-devkit/build-angular/plugins/karma'),
      require('karma-spec-reporter')
    ],
```

Add to the `reporters` array
```js
reporters: ['kjhtml', 'spec']
```

Now when you run tests, you'll see an output like this
![](https://github.com/alisaduncan/tutorial-angular-httpclient/blob/test-configuration/post-images/spec.png?raw=true)


![](https://media.giphy.com/media/WuGSL4LFUMQU/giphy.gif)

There's all sorts of reporters available for Karma. If you want unit test output available in your CI environment, you can add a reporter for JUnit output and configure Jenkins to consume JUnit reports as an example. If you need some more flair in your life, add the nyan cat progress reporter.

![](https://raw.githubusercontent.com/dgarlitt/image-repo/master/karma-nyan-reporter/v0.2.2/karma-nyan-reporter.gif)

## Code Coverage

Now that you know how to run tests and set it up to get the output format you like, it's time to measure coverage. 

Keep in mind test coverage metrics can't determine if an application is working as intended or if the tests you have are "good" by testing the important things. 


{% twitter 912487170371284994 %}

Angular CLI automatically adds and configures Istanbul as a coverage reporter. In _karma.conf.js_ there's a section for `coverageIstanbulReporter` and it's already set up to generate reports. Prior to v7 of Angular, it only had 'html' and 'lcov' enabled out of the box. Add 'text-summary' to the array if it's not already there.

Run test with the coverage flag enabled. In v6, use `--code-coverage`.
```bash
ng test --watch false --browsers ChromeHeadless --codeCoverage
```

Now you have nice output in the console for coverage summary.

![](https://github.com/alisaduncan/tutorial-angular-httpclient/blob/test-configuration/post-images/ng-cc-text-summary.png?raw=true)

Running coverage with 'html' report creates a visual overview of coverage in html format. You can view coverage results for the entire app broken down per file.

![](https://github.com/alisaduncan/tutorial-angular-httpclient/blob/test-configuration/post-images/ng-test-cc-overview.png?raw=true)

And step into coverage report for a single file and see the number of times each line of code was executed. 

![](https://github.com/alisaduncan/tutorial-angular-httpclient/blob/test-configuration/post-images/ng-test-cc-view.png?raw=true)

Add native report formats such as 'text', 'json', 'Cobertura', 'TeamCity', or use the 'lcov' report as part of your CI process so you can show test coverage trend lines per build.

## Maintaining Thresholds

![](http://s2.quickmeme.com/img/03/0347c3efdc17cc1959d089f60b8b2fc267d9093caa8e8cb483bf476b58e63e45.jpg)

If you want to ensure a certain level of coverage, you can configure `coverageIstanbulReporter` object in _karma.conf.js_ to add `thresholds`.

To the `thresholds` object, fill in keys for `statements`, `lines`, `branches`, and `functions`. 

```js
coverageIstanbulReporter: {
      dir: require('path').join(__dirname, '../coverage'),
      reports: ['html', 'lcovonly', 'text-summary'],
      fixWebpackSourcePaths: true,
      thresholds: {
            statements: 80,
            lines: 80,
            branches: 80,
            functions: 80
      }
},
```

Now when you run tests with code coverage, your tests will complete with failure if your project doesn't meet the thresholds of coverage.

![](https://github.com/alisaduncan/tutorial-angular-httpclient/blob/test-configuration/post-images/ng-cc-threshold-fail.png?raw=true)


# Setting Up _angular.json_ For Defaults
Sure, we can create npm scripts to wrap all the parameters we send in while running unit tests, but there's cases where we always want a certain configuration set. An example might be code coverage. Despite `watch` or `browsers` configurations, we always want to run coverage. We can set that up in _angular.json_.

In `$/angular.json` file, find the configuration for "test". It has an "options" property. Add a new property for "codeCoverage" and set the value to true.

You can set more properties than just coverage. All parameters that you pass in to Angular CLI can be configured. Check out the [schema for angular.json for more details](https://github.com/angular/angular-cli/blob/master/packages/angular/cli/lib/config/schema.json).


# Add A Git Hook
Want to make sure every push to the repo has passing unit tests and adequate coverage? Add the npm package 'husky' and add the `pre-push` step that runs unit tests [following their instructions](https://github.com/typicode/husky).

Now people can't push code into the repo without passing unit tests that meet code coverage. Applied to all branches, this requirement might make it difficult for teams to collaborate so you might want to target only master branch following a method posted in this GitHub issue.

{% github https://github.com/typicode/husky/issues/186 %}


![](https://media.giphy.com/media/8fen5LSZcHQ5O/giphy.gif)


In the next post, we'll learn about ways to target tests to run and dive a little deeper into custom solutions.