I have a method which depends on new Date
to create a date object and then manipulates it. I'm testing that the manipulation works as expected, so I need to compare the returned date with expected date. In order to do that I need to make sure that new Date
returns the same value in the test and in the method being tested. How can I do that?
Is there a way to actually mock the return value of a constructor function?
I could create a module that can be required with a function that provides a date object and can be mocked. But that seems like an unnecessary abstraction in my code.
an example function to be tested...
module.exports = {
sameTimeTomorrow: function(){
var dt = new Date();
dt.setDate(dt + 1);
return dt;
}
};
how do I mock the return value of new Date()
?
You can mock a constructor like new Date() using jest.spyOn
as below:
test('mocks a constructor like new Date()', () => {
console.log('Normal: ', new Date().getTime())
const mockDate = new Date(1466424490000)
const spy = jest
.spyOn(global, 'Date')
.mockImplementation(() => mockDate)
console.log('Mocked: ', new Date().getTime())
spy.mockRestore()
console.log('Restored: ', new Date().getTime())
})
And the output looks like:
Normal: 1566424897579
Mocked: 1466424490000
Restored: 1566424897608
See the reference project on GitHub.
Note: If you are using TypeScript and you would encounter a compilation error, Argument of type '() => Date' is not assignable to parameter of type '() => string'. Type 'Date' is not assignable to type 'string'
. In this case, a workaround is to use the mockdate library, which can be used to change when "now" is. See this question for more details.