w3resource

Jest Globals


In this tutorial we will introduce you to the global methods of jest, these methods do not need to be required or imported for them to be used in our tests. This is because Jest has already put them in the global environment.

Methods

  • afterAll(fn, timeout)
  • afterEach(fn, timeout)
  • beforeAll(fn, timeout)
  • beforeEach(fn, timeout)
  • describe(name, fn)
  • describe.each(table)(name, fn, timeout)
  • describe.only(name, fn)
  • describe.only.each(table)(name, fn)
  • describe.skip(name, fn)
  • describe.skip.each(table)(name, fn)
  • test(name, fn, timeout)
  • test.each(table)(name, fn, timeout)
  • test.only(name, fn, timeout)
  • test.only.each(table)(name, fn)
  • test.skip(name, fn)
  • test.skip.each(table)(name, fn)
  • test.todo(name)

Reference

afterAll(fn, timeout)

This will run a function after all the tests in this file have completed. In the case where the function returns a promise or is a generator, Jest will wait for that promise to resolve before continuing.

You can optionally provide a timeout (in milliseconds) for specifying how long to wait before aborting. Note: 5 seconds is the default timeout.

This is mostly useful if you want to clean up some global setup state that is shared across tests.

For instance:

const globalDatabase = makeGlobalDatabase();

function cleanUpDatabase(db) {
  db.cleanUp();
}

afterAll(() => {
  cleanUpDatabase(globalDatabase);
});

test('can find things', () => {
  return globalDatabase.find('thing', {}, results => {
    expect(results.length).toBeGreaterThan(0);
  });
});

test('can insert a thing', () => {
  return globalDatabase.insert('thing', makeThing(), response => {
    expect(response.success).toBeTruthy();
  });
});

In this case the afterAll ensures that cleanUpDatabase is called after all tests run.

whenever afterAll is inside a describe block, it will run at the end of the describe block.

If you would like to run some cleanup after every test instead of after all tests, you should use afterEach instead.

afterEach(fn, timeout)

This Runs a function after each one of the tests in this file completes. In the case where the function returns a promise or is a generator, Jest will wait for that promise to resolve before continuing.

You can optionally provide a timeout (in milliseconds) for specifying how long to wait before aborting. Note: 5 seconds is the default timeout.

afterEach is often useful if you want to clean up some temporary state that is created by each test.

For instance:

const globalDatabase = makeGlobalDatabase();

function cleanUpDatabase(db) {
  db.cleanUp();
}

afterEach(() => {
  cleanUpDatabase(globalDatabase);
});

test('can find things', () => {
  return globalDatabase.find('thing', {}, results => {
    expect(results.length).toBeGreaterThan(0);
  });
});

test('can insert a thing', () => {
  return globalDatabase.insert('thing', makeThing(), response => {
    expect(response.success).toBeTruthy();
  });
});

In this case the afterEach ensures that cleanUpDatabase is called after each test runs.

In the case where afterEach is inside a describe block, it will only run after the tests that are inside this describe block.

If you would like to run some cleanup just once, once all of the tests run, you should use afterAll instead.

beforeAll(fn, timeout)

This runs a function before any of the tests in this file run. In the case where the function returns a promise or is a generator, Jest will wait for that promise to resolve before running tests.

You can optionally provide a timeout (in milliseconds) for specifying how long to wait before aborting. Note: 5 seconds is the default timeout.

This is often useful if you want to set up some global state that will be used by many tests.

For instance:

const globalDatabase = makeGlobalDatabase();

beforeAll(() => {
  // this clears the database and adds some testing data.
  // Jest waits for this promise to resolve before running tests.
  return globalDatabase.clear().then(() => {
    return globalDatabase.insert({testData: 'foo'});
  });
});

// Since the database was set up once in this example, it's important
// that our tests do not modify it.
test('can find things', () => {
  return globalDatabase.find('thing', {}, results => {
    expect(results.length).toBeGreaterThan(0);
  });
});

Here the beforeAll will ensure that the database is set up before tests run. In the case where the setup was synchronous, you could do this without beforeAll. The key is that Jest waits for a promise to resolve, Hence, you can have asynchronous setup as well.

In the case where beforeAll is inside a describe block, it will run at the beginning of the describe block.

If you want to run something before every test rather than before any test runs, you should use beforeEach.

beforeEach(fn, timeout)

This will run a function before each of the tests in this file runs. Where the function returns a promise or is a generator, Jest will wait for that promise to resolve before running the test.

You can optionally provide a timeout (in milliseconds) for specifying how long to wait before aborting. Note: 5 seconds is the default timeout.

This is often useful when you want to reset some global state that will be used by many tests.

For instance:

const globalDatabase = makeGlobalDatabase();

beforeEach(() => {
  // this will clear the database and adds some testing data.
  // Jest waits for this promise to resolve before running tests.
  return globalDatabase.clear().then(() => {
    return globalDatabase.insert({testData: 'foo'});
  });
});

test('can find things', () => {
  return globalDatabase.find('thing', {}, results => {
    expect(results.length).toBeGreaterThan(0);
  });
});

test('can insert a thing', () => {
  return globalDatabase.insert('thing', makeThing(), response => {
    expect(response.success).toBeTruthy();
  });
});

Here the beforeEach will ensure that the database is reset for each test.

In the case where beforeEach is inside a describe block, it will run for each test in the describe block.

In the case where you only need to run some setup code once, before any tests run, you should use beforeAll instead.

describe(name, fn)

describe(name, fn) will create a block that groups together several related tests. For instance, if you have a myBeverage object that is supposed to be sour but not delicious, you could test it using:

const myBeverage = {
  delicious: false,
  sour: true,
};

describe('my beverage', () => {
  test('is sour', () => {
    expect(myBeverage.sour).toBeTruthy();
  });

  test('is not delicious', () => {
    expect(myBeverage.delicious).toBeFalsy();
  });
});

This is not required - you could just write the test blocks directly at the top level. However, this can be handy if you prefer your tests to be organized into groups.

You can equally nest describe blocks if you have a hierarchy of tests:

const binaryStringToNumber = binString => {
  if (!/^[01]+$/.test(binString)) {
    throw new CustomError('Not a binary number.');
  }

  return parseInt(binString, 2);
};



describe('binaryStringToNumber', () => {
  describe('given an invalid binary string', () => {
    test('composed of non-numbers throws CustomError', () => {
      expect(() => binaryStringToNumber('abc')).toThrowError(CustomError);
    });

    test('with extra whitespace throws CustomError', () => {
      expect(() => binaryStringToNumber('  100')).toThrowError(CustomError);
    });
  });

  describe('given a valid binary string', () => {
    test('returns the correct number', () => {
      expect(binaryStringToNumber('100')).toBe(4);
    });
  });
});

describe.each(table)(name, fn, timeout)

You should use describe.each if you keep duplicating the same test suites with different data. describe.each will allow you to write the test suite once and pass data in.

there are two APIs available for describe.each:

1. describe.each(table)(name, fn, timeout)

  • table: Array of Arrays with the arguments which are passed into the fn for each row.
    • Note: In the case where you pass in a 1D array of primitives, internally it is mapped to a table i.e. [1, 2, 3] -> [[1], [2], [3]]
  • name: String the title of our test suite.
    • Generate unique test titles by positionally injecting parameters using printf formatting:
      • %p - pretty-format.
      • %s- String.
      • %d- Number.
      • %i - Integer.
      • %f - Floating point value.
      • %j - JSON.
      • %o - Object.
      • %# - Index of the test case.
      • %% - single percent sign ('%'). This does not consume an argument.
  • fn: Function the suite of tests that is to be ran, this is the function that receives the parameters in each row as function arguments.
  • You can optionally provide a timeout (in milliseconds) for specifying how long to wait for each row before aborting. Note: 5 seconds is the default timeout.

Here is an example:

describe.each([[1, 1, 2], [1, 2, 3], [2, 1, 3]])(
  '.add(%i, %i)',
  (x, y, expected) => {
    test(`returns ${expected}`, () => {
      expect(x + y).toBe(expected);
    });

    test(`returned value is not be greater than ${expected}`, () => {
      expect(x + y).not.toBeGreaterThan(expected);
    });

    test(`returned value is not be less than ${expected}`, () => {
      expect(x + y).not.toBeLessThan(expected);
    });
  },
);

2. describe.each`table`(name, fn, timeout)

  • table: Tagged Template Literal
    • First row of variable name column headings is separated with |
    • One or more subsequent rows of data supplied as template literal expressions with ${value} syntax.
  • name: String the title of our test suite, you should use $variable to inject test data into the suite title from the tagged template expressions.
    • If you want to inject nested object values use you can supply a keyPath i.e. $variable.path.to.value
  • fn: Function the suite of tests that is to be ran, this is the function that receives the test data object.
  • you can optionally provide a timeout (in milliseconds) for specifying how long to wait for each row before aborting. Note: 5 seconds is the default timeout.

Example:

describe.each`
  x    | y    | expected
  ${1} | ${1} | ${2}
  ${1} | ${2} | ${3}
  ${2} | ${1} | ${3}
`('$x + $y', ({x, y, expected}) => {
  test(`returns ${expected}`, () => {
    expect(x + y).toBe(expected);
  });

  test(`returned value is not be greater than ${expected}`, () => {
    expect(x + y).not.toBeGreaterThan(expected);
  });

  test(`returned value is not be less than ${expected}`, () => {
    expect(x + y).not.toBeLessThan(expected);
  });
});

describe.only(name, fn)

This is also under the alias: fdescribe(name, fn)

You can use describe.only if you would like to run only one describe block:

describe.only('my beverage', () => {
  test('is sour', () => {
    expect(myBeverage.sour).toBeTruthy();
  });

  test('is not delicious', () => {
    expect(myBeverage.delicious).toBeFalsy();
  });
});

describe('my other beverage', () => {
  // ... this will be skipped
});

describe.only.each(table)(name, fn)

This is also under the aliases: fdescribe.each(table)(name, fn) and fdescribe.each`table`(name, fn)

You should use describe.only.each if you want to only run specific tests suites of data driven tests.

There are two APIs available to describe.only.each:

  • describe.only.each(table)(name, fn)
  • describe.only.each([[1, 1, 2], [1, 2, 3], [2, 1, 3]])(
      '.add(%i, %i)',
      (x, y, expected) => {
        test(`returns ${expected}`, () => {
          expect(x + y).toBe(expected);
        });
      },
    );
    
    test(' this will not be ran', () => {
      expect(1 / 0).toBe(Infinity);
    });
  • describe.only.each`table`(name, fn)
  • describe.only.each`
      b   | c    | expected
      ${1} | ${1} | ${2}
      ${1} | ${2} | ${3}
      ${2} | ${1} | ${3}
    `('this will return $expected when $b is added $c', ({b, c, expected}) => {
      test('passes', () => {
        expect(b + c).toBe(expected);
      });
    });
    
    test('this will not be ran', () => {
      expect(1 / 0).toBe(Infinity);
    });

    describe.skip(name, fn)

    This is also under the alias: xdescribe(name, fn)

    You can use describe.skip in the case where you do not want to run a particular describe block:

    describe('my beverage', () => {
      test('is sour', () => {
        expect(myBeverage.sour).toBeTruthy();
      });
    
      test('is not delicious', () => {
        expect(myBeverage.delicious).toBeFalsy();
      });
    });
    
    describe.skip('my other beverage', () => {
      // ... this will be skipped
    });

    Often using describe.skip is just an easier alternative to temporarily commenting out a chunk of tests.

    describe.skip.each(table)(name, fn)

    This is also under the aliases: xdescribe.each(table)(name, fn) and xdescribe.each`table`(name, fn)

    You should use describe.skip.each if you want to stop running a suite of data driven tests.

    There are two APIs available to describe.skip.each:

  • describe.skip.each(table)(name, fn)
describe.skip.each([[1, 1, 2], [1, 2, 3], [2, 1, 3]])(
  '.add(%i, %i)',
  (x, y, expected) => {
    test(`returns ${expected}`, () => {
      expect(x + y).toBe(expected); // will not be ran
    });
  },
);

test('this will be ran', () => {
  expect(1 / 0).toBe(Infinity);
});

describe.skip.each`table`(name, fn)

describe.skip.each`
  b    | c    | expected
  ${1} | ${1} | ${2}
  ${1} | ${2} | ${3}
  ${2} | ${1} | ${3}
`('returns $expected when $b is added $c', ({b, c, expected}) => {
  test('will not be ran', () => {
    expect(b + c).toBe(expected); // this will not be ran
  });
});

test('this will be ran', () => {
  expect(1 / 0).toBe(Infinity);
});

test(name, fn, timeout)

This is also under the alias: it(name, fn, timeout)

The only thing you need in a test file is the test method which will run a test. For instance, let's say there is a function inchesOfRain() that should be zero. This could be your whole test:

test('it did not rain', () => {
  expect(inchesOfRain()).toBe(0);
});

The test name is the first argument; a function that contains the expectations to test is the second argument. The third argument (which is optional) is timeout (in milliseconds) for specifying how long to wait before aborting. Note: 5 seconds is the default timeout.

Note: In the case where a promise is returned from test, Jest waits for the promise to resolve before letting the test complete. Jest also waits if you provide an argument to the test function, usually called done. This can be handy when you want to test callbacks.

For instance, let's say fetchBeverageList() will return a promise that is supposed to resolve to a list that has lime in it. You can test this with:

test('has lime in it', () => {
  return fetchBeverageList().then(list => {
    expect(list).toContain('lime');
  });
});

Even though the call to test returns right away, the test does not complete until the promise resolves as well.

test.each(table)(name, fn, timeout)

This is also under the alias: it.each(table)(name, fn) and it.each`table`(name, fn)

You should use test.each if you keep duplicating the same test with different data. test.each will allow you to write the test once and pass data in.

There are two APIs available for test.each:

1. test.each(table)(name, fn, timeout)

  • table: Array of Arrays with the arguments that will be passed into the test fn for each row.
    • Note in the case where you pass in a 1D array of primitives, it will be mapped internally to a table i.e. [1, 2, 3] -> [[1], [2], [3]]
  • name: String the title of the test block.
    • Generate unique test titles by positionally injecting parameters using printf formatting:
      • %p - pretty-format.
      • %s- String.
      • %d- Number.
      • %i - Integer.
      • %f - Floating point value.
      • %j - JSON.
      • %o - Object.
      • %# - Index of the test case.
      • %% - single percent sign ('%'). This does not consume an argument.
  • fn: Function the test that is to be ran, this is the function that receives the parameters in each row as function arguments.
  • You can optionally provide a timeout (in milliseconds) for specifying how long to wait for each row before aborting. Note:5 seconds is the default timeout.

Example:

test.each([[1, 1, 2], [1, 2, 3], [2, 1, 3]])(
  '.add(%i, %i)',
  (x, y, expected) => {
    expect(x + y).toBe(expected);
  },
);

2. test.each`table`(name, fn, timeout)

  • table: Tagged Template Literal
    • First row of variable name column headings separated by |
    • One or more subsequent rows of data supplied as template literal expressions using the ${value} syntax.
  • name: String the title of the test, you should use $variable to inject test data into the test title from the tagged template expressions.
    • If you want to inject nested object values use you can supply a keyPath i.e. $variable.path.to.value
  • fn: Function the test that is to be ran, this is the function that receives the test data object.
  • You can optionally provide a timeout (in milliseconds) for specifying how long to wait for each row before aborting. Note:5 seconds is the default timeout.

Example:

test.each`
  x   | y    | expected
  ${1} | ${1} | ${2}
  ${1} | ${2} | ${3}
  ${2} | ${1} | ${3}
`('will return $expected when $x is added $y', ({x, y, expected}) => {
  expect(x + y).toBe(expected);
});

test.only(name, fn, timeout)

This is also under the aliases: it.only(name, fn, timeout) or fit(name, fn, timeout)

If you are debugging a large test file, you often will only want to run a subset of tests. You can use .only to specify the tests are the only ones you want to run in that test file.

You can optionally provide a timeout (in milliseconds) for specifying how long to wait before aborting. Note: 5 seconds is the default timeout.

For instance, let us say that you had these tests:

test.only('it is snowing', () => {
  expect(inchesOfSnow()).toBeGreaterThan(0);
});

test('it is not raining', () => {
  expect(inchesOfRain()).toBe(0);
});

Only the "it is snowing" test will run in that test file, because it is run with test.only.

Usually you don?t check code using test.only into source control - you should use it just for debugging, and then remove it once you have fixed the broken tests.

test.only.each(table)(name, fn)

This is also under the aliases: it.only.each(table)(name, fn), fit.each(table)(name, fn), it.only.each`table`(name, fn) and fit.each`table`(name, fn)

You should use test.only.each if you want to only run specific tests with different test data.

There are two APIs available for test.only.each:

  • test.only.each(table)(name, fn)
test.only.each([[1, 1, 2], [1, 2, 3], [2, 1, 3]])(
  '.add(%i, %i)',
  (x, y, expected) => {
    expect(x + y).toBe(expected);
  },
);

test('this will not be ran', () => {
  expect(1 / 0).toBe(Infinity);
});
  • test.only.each`table`(name, fn)
test.only.each`
  x    | y    | expected
  ${1} | ${1} | ${2}
  ${1} | ${2} | ${3}
  ${2} | ${1} | ${3}
`('returns $expected when $x is added $y', ({x, y, expected}) => {
  expect(x + y).toBe(expected);
});

test('this will not be ran', () => {
  expect(1 / 0).toBe(Infinity);
});

test.skip(name, fn)

this is also under the aliases: it.skip(name, fn) or xit(name, fn) or xtest(name, fn)

If you are maintaining a large codebase, you may find that sometimes a test is temporarily broken for some reason. If you want to skip running the broken test, but you don't want to delete the code, you should use test.skip to specify some tests to skip.

For instance, let us say you had these tests:

test('it is snowing', () => {
  expect(inchesOfSnow()).toBeGreaterThan(0);
});

test.skip('it is not raining', () => {
  expect(inchesOfRain()).toBe(0);
});

Only the "it is snowing" test will run, this is because the other test is run with test.skip.

You can simply comment the test out, but most times it is a bit nicer to use test.skip because it will maintain indentation and syntax highlighting.

test.skip.each(table)(name, fn)

This is also under the aliases: it.skip.each(table)(name, fn), xit.each(table)(name, fn), xtest.each(table)(name, fn), it.skip.each`table`(name, fn), xit.each`table`(name, fn) and xtest.each`table`(name, fn)

You should use test.skip.each if you want to stop running a collection of data driven tests.

The test.skip.each is available with two APIs:

  • test.skip.each(table)(name, fn)
test.skip.each([[1, 1, 2], [1, 2, 3], [2, 1, 3]])(
  '.add(%i, %i)',
  (x, y, expected) => {
    expect(x + y).toBe(expected); // this will not be ran
  },
);

test('this will be ran', () => {
  expect(1 / 0).toBe(Infinity);
});
  • test.skip.each`table`(name, fn)
test.skip.each`
  x    | y    | expected
  ${1} | ${1} | ${2}
  ${1} | ${2} | ${3}
  ${2} | ${1} | ${3}
`('returns $expected when $x is added $y', ({x, y, expected}) => {
  expect(x + y).toBe(expected); //this will not be ran
});

test('this will be ran', () => {
  expect(1 / 0).toBe(Infinity);
});

test.todo(name)

You should use test.todo when you are planning on writing tests. These are highlighted in the summary output at the end so you know how many tests you still need todo.

Note: when you supply a test callback function then the test.todo throws an error. In the case where you have already implemented the test and the test is broken and you don?t want it to run, then you can use test.skip instead.

API

  • name: String the title of the test plan.

Example:

const add = (x, y) => x + y;

test.todo('add should be associative');


Inviting useful, relevant, well-written and unique guest posts