You are on page 1of 7

JS201 - Class-16 [Live]

Importance of automated Testing

If tests are not automated, then we end up manually inspecting every feature in every release. The manual approach is
unscalable & its easier to make mistakes

In Automated tests, we have a piece of code that does the verification for us. Automated tests interface with our application to
perform actions and compare the actual result with the expected output we have previously defined.

By making our test reproduce the steps that may cause the bug to happen, we can be assured that the specific bug does not
happen any more

If we are working on a new feature or fixing an existing bug, passing tests for the existing features, makes us more confident
that our code is not causing any regressions

The more tests we have and the closer these tests resemble what real users do, the more reliable they become.

Tests decreases the time it takes to get feedback on the code we write, and, therefore make it quicker to fix mistakes. Not
having automated tests will cause us to write too much code before checking whether the feature works. Most of the time, by
the time we do realise that the code is buggy, its too late. We have already written too much code and there are more places
for bugs to hide.

Even if we maintain a checklist of test cases for manual testing, we will have the overhead of keeping that documentation
always up to date. Humans are bad at performing repetitive tasks. Machines are good at it.

Tests are excellent for collaborative development. When a programmer adds automated tests for their features, everyone else
benefits. The other developers dont need to ask them how to test their changes. Even if our changes builds on top of theirs,
we can be assured that we are not breaking any of their work.

Initially, writing tests may be time consuming, but more we run it, the more value we extract from it. As time passes and the
number of features increases in our application, the efforts involved in manual tests grows much quicker than automated
tests. The longer the lifecycle of a project, the more critical tests become.

Type of tests

Consider a bicycle:

JS201 - Class-16 [Live] 1


Unit tests: When building a bi-cycle, its crucial to test if a chain, paddle, tyre & chain-rings are individually working as expected.
In the same way, testing tiny pieces (like functions) of a software is the first step.

Integration tests: It’s also vital to ensure that they work together. for example a chain must fit properly into the chain rings. The
pedals must fit into the chain ring in an expected way. Similarly, the next step is to test larger components which are a combination
of several functions.

E2E Tests: Its equally important to test whether people can drive the bi-cycle once all parts are in place. In the same way, the final
step is to test the application itself.

Tools
Unit & Integration tests: Jest

E2E: Cypress

Unit tests
Unit tests helps us ensure that the smallest units of our software, functions, behave as we expect them to. We write unit tests to
test the functionality of our code, i.e. Whether our code is working as expected or not. A unit in a unit test can be a function, an
object or a few lines of code that is capable of either consumed or executing independently.

Documentation
https://jestjs.io/docs/getting-started

Examples
https://codesandbox.io/s/javascript-testing-class-8q0y87?file=/src/matchers.test.js:564-778

JS201 - Class-16 [Live] 2


https://codesandbox.io/s/asynchronousjavascriptclass-ng2cl4?file=/src/asyncAwait.test.js:617-622

https://codesandbox.io/s/jest-mocking-0uwg8v?file=/src/localBank.test.js:2125-2148

https://stackblitz.com/edit/jest-example-kfagfy?file=playground.test.js

Format

Live examples

export function add(a, b) {


return a + b;
}

export function subtract(a, b) {


return a - b;
}

import { add, subtract } from "./functions";

describe("add tests", function () {


test("calling add with 2 and 3", function () {
expect(add(2, 3)).toBe(5);
});

test("calling add with 2 and 0", function () {


expect(add(2, 0)).toBe(2);
});

test("calling add with 2 and -2", function () {


expect(add(2, -2)).toBe(0);
});
});

describe("subtract tests", function () {


test("calling subtract with 5,2", function () {
expect(subtract(5, 2)).toBe(3);
});

JS201 - Class-16 [Live] 3


test("calling subtract with 5, 7", function () {
expect(subtract(5, 7)).toBe(-2);
});
});

// matchers:
// toBe strict equality
// range
// null, undefined or NaN
// truthy or falsey
// object properties
// collections
// errors
// custom mathcers

expect(add(2, 3)).toBe(5); is called an assertion

toBe is a matcher

Matchers
toBe() vs toEqual()

toBe() → for non-primitives matches identity

toEqual()

const book1 = {
id: 5,
title: "Book 5",
price: 49
};

const book2 = {
id: 5,
title: "Book 5",
price: 99
};

const book3 = book1;

const myDesiredBook = {
title: "Book 5"
};

test("understanding toBe() and toEqual() matcher", () => {


// expect(book1).toEqual(book2);
// expect(book1).not.toBe(book2);
// expect(book1).toBe(book2);
});

use case - write a function that returns an object.

toMatch

test("understanding toMatch() matcher", () => {


let bookTitle = "Lord of the Rings";

expect(bookTitle).toMatch("Rings");
expect(bookTitle).toMatch(/rin../i);
// expect(bookTitle).not.toMatch("Potter");
});

test("understanding toMatchObject() matcher", () => {


expect(book1).toMatchObject(myDesiredBook);
});

JS201 - Class-16 [Live] 4


toMatchObject

kind of subset

test("understanding toMatchObject() matcher", () => {


expect(book1).toMatchObject(myDesiredBook);
});

toBeLessThan()

// toBeLessThan(), toBeLessThanOrEqual works with numbers & BigInt


// toBeGreaterThan(), toBeGreaterThanOrEqual
// toBeCloseTo() - param-1 the number, param-2 number of digits after decimal point (defaults to 2)
test("understanding toBeLessThan, toBeGreaterThan & toBeCloseTo", () => {
expect(book1.price).toBeGreaterThan(40);
let price = 5.12345;

expect(price).toBeCloseTo(5.1234, 4);
});

// toBeNull(), toBeDefined(), toBeUnderfined(), toBeNaN()


test("understanding toBeNull, Defined, Underfined and NaN", () => {
let a;
let b = null;
let c = Math.sqrt(-25);
let d = "Vivek";

expect(a).toBeUndefined();
expect(b).toBeNull();
expect(c).toBeNaN();
expect(d).toBeDefined();
});

// toBeTruthy(), toBeFalsy()
// falsey values - false, 0, "", null, underfined, NaN
// more falsey values - -0, -0n, Objects are falsy if and only if they have the [[IsHTMLDDA]] internal slot.
test("understanding toBeTruthy and toBeFalsy", () => {
let a = 0;
let b = 1;

expect(a).toBeFalsy();
expect(b).toBeTruthy();
});

// toHaveLength() array/string
// toHaveProperty() can use the dot syntax (or array syntax) to drill into nested objects;
// "one.two.three" or ["one","two","three"]
// 2nd argument if we care about the value
test("understanding matchers for object properties", () => {
let str = "Vivek";
let arr1 = ["one", "two", "three"];
let arr2 = ["four", "five", "six"];
let obj = {
name: "Vivek",
arr1: ["one", "two", "three"],
obj1: {
a: "a",
b: "b"
}
};

expect(obj).toHaveProperty("obj1.a", "a");

JS201 - Class-16 [Live] 5


expect(obj).toHaveProperty(["obj1", "a"], "a");
expect(obj).toHaveProperty("arr1.2", "three");

expect(str).toHaveLength(5);
expect(arr1).toHaveLength(3);
});

// toContain() - compares item of an array by reference


// toContainEqual() - compares item of an array by property value
// Map/Set.has("key").toBeTruthy()
// Map.get("key").toBe("some value")
test("understand matchers for collections", () => {
let obj1 = { name: "Vivek" };
let obj2 = { name: "Abhay" };
let obj3 = obj1;
let arr = [obj1, obj2, obj3];

expect(arr).toContainEqual({ name: "Vivek" });

const fruits = new Map([


["apples", 500],
["bananas", 300],
["oranges", 200]
]);

fruits.set("mangoes", 700);

expect(fruits.has("bananas")).toBeTruthy();
expect(fruits.get("mangoes")).toBe(700);

const letters = new Set(["a", "b", "c"]);

letters.add("d");
letters.add("e");
letters.add("f");

expect(letters.has("e")).toBeTruthy();
letters.delete("e");

expect(letters.has("e")).not.toBeTruthy();
});

Pre-recorded Lectures in Hindi


Maybe watch in 1.5x speed (100% optional)

Javascript
Class - 1 Video Hinglish https://www.loom.com/share/189401b30d724e0b81aa00a9ba8ef249
Testing Course

Javascript https://codesandbox.io/s/javascript-testing-class-8q0y87?
Class - 1 Codesandbox English
Testing Course file=/src/matchers.test.js:2953-2959
Javascript
Class - 2 Video Hinglish https://www.loom.com/share/f7ddf66dab8443858cf2651edacb5a25
Testing Course

Javascript
Class - 3 Video Hinglish https://www.loom.com/share/66108fc73e8049c389f995d2042e42b4
Testing Course
Javascript
Class - 4 Video Hinglish https://www.loom.com/share/a8ff801ac55a45bfb2d89a45f89143e5
Testing Course

Javascript
Class - 5 Video Hinglish https://www.loom.com/share/bc7c793afcdb42b781051829a516192f
Testing Course
Javascript Class - 5 Codesandbox English https://codesandbox.io/s/asynchronousjavascriptclass-ng2cl4?
Testing Course file=/src/asyncAwait.test.js:617-622

JS201 - Class-16 [Live] 6


Javascript
Class - 6 Video Hinglish https://www.loom.com/share/6c55695f691641469f1fe8d8165b03ae
Testing Course
Javascript https://codesandbox.io/s/jest-mocking-0uwg8v?
Class - 6 Codesandbox English
Testing Course file=/src/localBank.test.js:2125-2148

Javascript
Class - 7 Video Hinglish https://www.loom.com/share/d3f8d0db695f46e19a1e46001413da8e
Testing Course
Javascript https://stackblitz.com/edit/jest-example-kfagfy?
Class - 7 StackBlitz English
Testing Course file=playground.test.js

Javascript
Class - 8 Video Hinglish https://www.loom.com/share/9dfa5817120c43fb897f4ec16a12177e
Testing Course
Javascript https://stackblitz.com/edit/jest-example-kfagfy?
Class - 8 StackBlitz English
Testing Course file=playground.test.js

Part-2 (if time permits) - Road to React


https://www.notion.so/vivmagarwal/JS211-Road-to-React-2699fda285a5446b8868a648c8e50586

Part-3 (student task) - after evaluation


The concept of debouncing:
https://steadfast-shark-012.notion.site/Debouncing-ef9be2ad121f4e0e90a7da6149575b83

JS201 - Class-16 [Live] 7

You might also like