2

Let's say I have a function that returns an id (integer) that increments every time.

let nextId = 0;

const getId = () => nextId++;

export default  getId;

I will have multiple tests for this function. Normally, in each test, I expect the id to be reset, meaning that the first time i call the function in each test, the returned value should be 0, but that's not the case. The value is persisted cross tests.

import getId  from './getId'

describe('getId()', () => {
  it('test1', () => {
    expect(getId()).toEqual(0); //passes
    expect(getId()).toEqual(1); //passes
  })
  it('test2', () => {
    expect(getId()).toEqual(0); //fails
  })
})

How to address this problem? Is having a global variable nextId a bad idea?

Abdou Ouahib
  • 821
  • 5
  • 14
  • 2
    You can use `beforeEach` function according to [the docs](https://jestjs.io/docs/en/setup-teardown) – luckongas Jan 06 '21 at 23:19
  • 3
    Adding to what @luckongas said, you probably want to call [`jest.resetModules()`](https://jestjs.io/docs/en/jest-object#jestresetmodules) in `beforeEach`. – rickdenhaan Jan 06 '21 at 23:22

2 Answers2

1

I think that this should do the job.

let nextId = 0;

const getId = () => nextId++;

export default getId;
import getId from './getId'

describe('getId()', () => {
  beforeEach(() => jest.resetModules());
  it('test1', () => {
    expect(getId()).toEqual(0); //passes
    expect(getId()).toEqual(1); //passes
  })
  it('test2', () => {
    expect(getId()).toEqual(0); //fails
  })
})

Any issue, please, let me know

luckongas
  • 1,651
  • 8
  • 17
0

Yes, having a global variable for this is a bad idea. Global variables are more difficult to control because anything can alter them. I would just use a simple class.

class IdManager() {
    constructor() {
        this.last_id = 0;
    }

    getId() {
        this.last_id++;
        return this.last_id;
    }

}

Then create a new Id manager every time you start a new test.

let id_man = new IdManager();
let id = id_man.getId();
J.F.
  • 13,927
  • 9
  • 27
  • 65