Friday, 19 April 2019

Is there a way to properly mock Reselect selectors for unit testing?

I'm having a pretty complex selectors structure in my project (some selectors may have up to 5 levels of nesting) so some of them are very hard to test with passing input state and I would like to mock input selectors instead. However I found that this is not really possible.

Here is the most simple example:

// selectors1.js
export const baseSelector = createSelector(...);

-

// selectors2.js
export const targetSelector = createSelector([selectors1.baseSelector], () => {...});

What I would like to have in my test suite:

beforeEach(() => {
  jest.spyOn(selectors1, 'baseSelector').mockReturnValue('some value');
});

test('My test', () => {
  expect(selectors2.targetSelector()).toEqual('some value');
});

But, this approach won't work as targetSelector is getting reference to selectors1.baseSelector during initialization of selectors2.js and mock is assigned to selectors1.baseSelector after it.

There are 2 working solutions I see now:

  1. Mock entire selectors1.js module with jest.mock, however, it won't work if I'll need to change selectors1.baseSelector output for some specific cases
  2. Wrap every dependency selectors like this:

export const targetSelector = createSelector([(state) => selectors1.baseSelector(state)], () => {...});

But I don't like this approach a lot for obvious reasons.

So, the question is next: is there any chance to mock Reselect selectors properly for unit testing?



from Is there a way to properly mock Reselect selectors for unit testing?

No comments:

Post a Comment