Your Web News in One Place

Help Webnuz

Referal links:

Sign up for GreenGeeks web hosting
April 23, 2022 10:49 am GMT

Jest Testing

When it comes to unit testing frameworks for JavaScript, Jest is certainly a serious contender for the #1 spot.

Initially, Jest was created by Facebook specifically for testing React applications. Its one of the most popular ways of testing React components. Since its introduction, the tool has gained a lot of popularity. This popularity has led to the use of Jest for testing both JavaScript front-end and back-end applications.

In this article, well talk about the ins and outs of Jest to help you get started with testing. Before we get there, though, well offer you a refresher on unit testing and its importance for software quality.

After that, well start covering Jest specifically, explaining:

  • its definition
  • what are its main advantages
  • and some of its most important characteristics

Well walk you through a 100% hands-on tutorial on how to get started with Jest. Youll learn more about the vocabulary associated with Jest testing, like mocks and spies. Also, well cover some of the basics of Jest testing, like using describe blocks and the keywords it and expect. Finally, well take a look at snapshot testing and why its particularly useful for front-end testing. Lets get started!

The What and Why of Unit Testing

The topic of software testing can often feel overwhelming. There are just too many types of testing, each operating on a different layer, verifying distinct aspects of the application and offering its unique type of feedback.

Among the myriad types of automated testing, unit testing is often cited as the most important onesee: test automation pyramid. Unit tests verify the smallest parts of your application in complete isolation, ensuring they work as expected. In unit testing, you arent allowed to interact with external dependenciese.g. make an HTTP callnor generate any kind of side-effect.

As a result of those properties, unit tests are usually:

  • very fast to execute
  • relatively easy to setup, not requiring any elaborate configuration
  • very precise in the feedback they provide

In the scale of automated tests, unit tests sit at the extreme opposite of end-to-end testing. The latter provide less-precise feedback, are generally slower, more fragile, though more realistic. The former are super precise in their feedback, are fast, and typically only fail due to the errors in the code.

However, they are in less realistic, because in real life users dont interact with units in complete isolation.

To sum it up: unit tests are far from being the only type of tests your application needs, but they should represent a significant portion of your testing strategy.

What Is Jest?

Jest is a popular test framework for JavaScript. It claims to provide delightful JavaScript testing and, after our tutorial, I bet you might agree with this claim! Jest prides itself in offering a complete and hassle-free experience.

The completeness comes from the fact that Jest doesnt rely on third-party tools for much of its functionality, like some competitors do. And the hassle-free part is due to Jests zero configuration setup. You can install it and start writing your first test in no time.

As mentioned in the introduction, Jest has gained a lot of popularity over recent years for both front-end and back-end testing. Many large companiesincluding Twitter, Instagram, Pinterest, and Airbnbuse Jest for React testing.

Jest itself is actually not a library but a framework. Theres even a CLI tool that you can use from the command line. To give an example, the CLI tool allows you to run only specific tests that match a pattern. Besides that, it hosts much more functionality, which you can find in the CLI documentation.

In summary, this means that Jest offers a test runner, assertion library, CLI tool, and great support for different mocking techniques. All of this makes it a framework and not just a library.

Lets take a quick look at the advantages of Jest.

Advantages of Jest

Heres a shortlist of Jest advantages.

  1. Offers a CLI tool to control your tests easily
  2. Comes with an interactive mode that automatically runs all affected tests for the code changes youve made in your last commit
  3. Provides syntax to test a single test or skip tests with .only and .skip. This feature is useful when debugging individual tests
  4. Provides excellent documentation with plenty of examples and a supportive community. You can join the Jest community via Discord or ask questions on Stack Overflow
  5. Brings easy mocking to developers as its one of the most painful things to do for testing engineers. We explain further in this post how Jest mocking works
  6. Jest offers code coverage out of the box through its CLIjust use the coverage option or the collectCoverage property in the Jest configuration file.

Jest Characteristics

From Jests website, we can find four main characteristics of Jest:

  • Zero config: Jest aims to work out of the box, config free, on most JavaScript projects. This means you can simply install Jest as a dependency for your project, and with no or minimal adjustments, you can start writing your first test.
  • Isolated: Isolation is a very important property when running tests. It ensures that different tests dont influence each others results. For Jest, tests are executed in parallel, each running in their own process. This means they cant interfere with other tests, and Jest acts as the orchestrator that collects the results from all the test processes.
  • Snapshots: Snapshots are a key feature for front-end testing because they allow you to verify the integrity of large objects. This means you dont have to write large tests full of assertions to check if every property is present on an object and has the right type. You can simply create a snapshot and Jest will do the magic. Later, well discuss in detail how snapshot testing works.
  • Rich API: Jest is known for having a rich API offering a lot of specific assertion types for very specific needs. Besides that, its great documentation should help you get started quickly.

Before we dive a bit further into the Jest vocabulary, lets show you how you can get started with this tool in practice.

Get Started With Jest: A Practical, Hands-On Tutorial in 5 Steps

Well now walk you through our five step tutorial on how to get started with testing using Jest.

1. Install Jest Globally
The first step will be to install Jest globally. That way, you gain access to Jests CLI. Make sure you have Node.js installed, because youll use npm.

Go to your terminal and run the following command:

npm install -g jest

Once the installation is complete, execute jest version to see the version installed.

2. Create a Sample Project

Youll now create a npm-based project to house our production code and test code.

Start by creating a folder and accessing it:

mkdir learning-jestcd learning-jest

Then, run npm init -y to create a project. As a result, you should have a package.json file inside your folder, with this content:

{  "name": "learning-jest",  "version": "1.0.0",  "description": "",  "main": "index.js",  "scripts": {    "test": "echo \"Error: no test specified\" && exit 1"  },  "keywords": [],  "author": "",  "license": "ISC"}

Now, create a file called index.js and paste the following content on it:

function fizz_buzz(numbers) {    let result = []    for (number of numbers) {        if (number % 15 === 0) {            result.push('fizzbuzz')        } else if (number % 3 === 0) {            result.push('fizz')        } else if (number % 5 === 0) {            result.push('buzz')        } else {            result.push(number)        }    }    return result.join(', ')}module.exports = fizz_buzz;

The code above contains a function that solves the famous FizzBuzz programming interview question.

3. Add Jest to the Project

Youll now add Jest as a dev dependency to the project. Run the following command:

npm install --save-dev jest

Then, go to your package.json file and change this part:

"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},

To this:

"scripts": {
"test": "jest"
},

4. Write Your First Test

Now, create a new file called index.test.js. Paste the following content on it:

const fizz_buzz = require('./index');describe("FizzBuzz", () => {    test('[3] should result in "fizz"', () => {      expect(fizz_buzz([3])).toBe('fizz');    });    test('[5] should result in "buzz"', () => {      expect(fizz_buzz([5])).toBe('buzz');    });    test('[15] should result in "fizzbuzz"', () => {      expect(fizz_buzz([15])).toBe('fizzbuzz');    });    test('[1,2,3] should result in "1, 2, fizz"', () => {      expect(fizz_buzz([3])).toBe('fizz');    });});

Well explain Jests syntax in more detail later. For now, understand were verifying that:

  • passing an array containing 3 should result in fizz
  • an array containing 5 should result in buzz
  • an array containing 15 should result in fizzbuzz
  • passing an array with 1, 2, and 3 should result in 1, 2, fizz

5. Run Your First Test

Youre now ready to run your first test. Back to your terminal, simply run npm test. You should see a result like the following:

Image description

As you can see, all four tests passed. All test suites were executedwhich makes sense, since we only have one. The total time for execution was 0.616 seconds.

Now that you had a test of Jest, lets take a step back and understand, in more detail, its syntax and vocabulary.

Jest Vocabulary

Lets take a look at two of the most commonly used Jest terms that are also used in other testing tools: mock and spy.

Jest Vocabulary: Mock

From the Jest documentation, we can find the following description for a Jest mock: Mock functions make it easy to test the links between code by erasing the actual implementation of a function, capturing calls to the function (and the parameters passed in those calls).

In addition, we can use a mock to return whatever we want it to return. This is very useful to test all the paths in our logic because we can control if a function returns a correct value, wrong value, or even throws an error.

In short, a mock can be created by assigning the following snippet of code to a function or dependency:

jest.fn()

Heres an example of a simple mock, where we just check whether a mock has been called. We mock mockFn and call it. Thereafter, we check if the mock has been called:

const mockFn = jest.fn();mockFn();expect(mockFn).toHaveBeenCalled();

The following example also mocks a return value for checking specific business logic. We mock the returnsTrue function and let it return false:

const returnsTrue = jest.fn(() => false);console.log(returnsTrue()); // false;

Next up, lets explore what a spy is.

Jest Vocabulary: Spy

A spy has a slightly different behavior but is still comparable with a mock. Again, from the official docs, we read, Creates a mock function similar to jest.fn() but also tracks calls to object[methodName]. Returns a Jest mock function.

What this means is that the function acts as it normally wouldhowever, all calls are being tracked. This allows you to verify if a function has been called the right number of times and held the right input parameters.

Below, youll find an example where we want to check if the play method of a video returns the correct result but also gets called with the right parameters. We spy on the play method of the video object.

Next, we call the play method and check if the spy has been called and if the returned result is correct. Pretty straightforward! In the end, we must call the mockRestore method to reset a mock to its original implementation.

const video = require('./video');test('plays video', () => {const spy = jest.spyOn(video, 'play');const isPlaying = video.play();expect(spy).toHaveBeenCalled();expect(isPlaying).toBe(true);spy.mockRestore();});

OK, now that we know about the two most used technical terms, lets explore the basic structure.

Jest Basics

Lets take a look at some basics on writing tests with Jest.

Jest Basics: Describe Blocks

A describe block is used for organizing test cases in logical groups of tests. For example, we want to group all the tests for a specific class. We can further nest new describe blocks in an existing describe block.

To continue with the example, you can add a describe block that encapsulates all the tests for a specific function of this class.

Jest Basics: It or Test Tests

Furthermore, we use the test keyword to start a new test case definition. The it keyword is an alias for the test keyword. Personally, I like to use it, which allows for more natural language flow of writing tests. To give an example:

describe('Beverage()', () => {
it('should be delicious', () => {
expect(myBeverage.delicious).toBeTruthy();
});
});

Jest Basics: Matchers

Next, lets look at the matchers Jest exposes. A matcher is used for creating assertions in combination with the expect keyword. We want to compare the output of our test with a value we expect the function to return.

Again, lets look at a simple example where we want to check if an instance of a class is the correct class we expect. We place the test value in the expect keyword and call the exposed matcher function toBeInstanceOf() to compare the values. The test results in the following code:

it('should be instance of Car', () => {   expect(newTruck()).toBeInstanceOf(Car);});

The complete list of exposed matchers can be found in the Jest API reference.

Jest Basics: Setup and Teardown

Its important we understand how to prepare and clean up a test. For example, a particular test relies on a mocked database. We dont want to call a function to set up and clean up the mocked database for each test.

To solve this problem, we can use the beforeEach and afterEach functions to avoid code duplication. Both functions allow you to execute logic before or after each test.

Heres an example of mocking a database before each test and tear it down when each test has finished.

describe('tests with database', () => {  beforeEach(() => {    initDB()  })  afterEach(() => {    removeDB()  })  test('if country exists in database', () => {    expect(isValidCountry('Belgium')).toBe(true)  })})

Moreover, you can also make use of beforeAll and afterAll functions. Both functions will run before or after all tests, but only once. You can use these functions to create a new database connection object and destroy it when youve completed the tests.

beforeAll(() => {  return createDBConnection()})afterAll(() => {  return destroyDBConnection()})

Lastly, lets take a look at snapshot testing.

Jest Basics: Snapshot Testing for React Front Ends

At last, the Jest documentation suggests using snapshot tests to detect UI changes. As I mentioned earlier, snapshot testing can also be applied for checking larger objects, or even the JSON response for API endpoints.

Lets take a look at an example for React where we simply want to create a snapshot for a link object. The snapshot itself will be stored with the tests and should be committed alongside code changes.

it('renders correctly', () => {   const tree = renderer      .create(<Link page="http://www.facebook.com">Facebook</Link>)      .toJSON();   expect(tree).toMatchSnapshot();});

Following, the above code renders the following snapshot:

exports[`renders correctly 1`] = `<a  className="normal"  href="http://www.facebook.com"  onMouseEnter={[Function]}  onMouseLeave={[Function]}>  Facebook</a>`;

If the link object changes, this test will fail in the future. If the changes to the UI elements are correct, you should update the snapshots by storing the results in the snapshot file. You can automatically update snapshots using the Jest CLI tool by adding a -u flag when executing the tests.

Getting Started With Jest Testing

Finally, weve covered all the basic elements for you to get started with Jest testing. When youre writing your first test cases, it can feel a bit uncomfortable writing mocks. However, mocks are especially useful in unit testing because they allow you to test the business logic of your function without worrying about its dependencies.


Original Link: https://dev.to/mokadevlight/jest-testing-2ckd

Share this article:    Share on Facebook
View Full Article

Dev To

An online community for sharing and discovering great ideas, having debates, and making friends

More About this Source Visit Dev To