When is this relevant?
Ok, here's the situation. You are maintaining a NodeJS application that depends on Luxon and you practice test-driven development. Along comes a requirement that is dependent on the current date and time.
If you tried to use Luxon's default DateTime.now() function in your tests, you will quickly find that it's difficult to set up proper test data and assertions. This is due to the coupling between the tests and the actual current time.
What's the solution?
As TDD practitioners, we know it's always a good thing to fake integration points. This is true for network calls, database read/writes, and even the system clock!
Let's dive deeper into how you can leverage Jest to fake Luxon's default DateTime.now() function so we can assert on an expected current time.
First, let's take a look at a very simple system under test (SUT).
import { DateTime } from 'luxon';
export const doSomethingThatDependsOnDateTimeNow = () => DateTime.now();
Nothing special here, just a simple function that returns Luxon's DateTime.now()
result.
Now let's dive into the unit test.
import { DateTime, Settings } from 'luxon';
import { doSomethingThatDependsOnDateTimeNow } from './doSomethingThatDependsOnDateTimeNow';
describe('Mocking DateTime.now with Luxon', () => {
it('should return the mock DateTime', () => {
// Arrange
const expectedNow = DateTime.local(2021, 6, 1, 23, 0, 0);
Settings.now = () => expectedNow.toMillis();
// Act
const actual = doSomethingThatDependsOnDateTimeNow();
// Assert
expect(actual).toEqual(expectedNow);
});
});
A lot going on here, so let's break it down.
First, we need to import Settings
from Luxon, which is used to configure Luxon. We also import DateTime and our system under test (SUT), doSomethingThatDependsOnDateTimeNow
.
Next, in the arrange section of the test, we create a new DateTime for the date 6/1/2021 at 11 pm EST. Then we override the DateTime.Now()
function by assigning a new function Settings.now
that returns our DateTime instead of the current time.
Finally, we invoke our SUT, capture the actual result, and assert that it is equal to our DateTime value.
Wrapping things up
Using TDD and integrating with Luxon's DateTime.now() can be a bit complex at first, but I hope this guide helps you red-green-refactor your way through your next time-based application feature.
If you found this useful, please consider following me on Twitter https://twitter.com/thealexkates
Top comments (2)
Thank you for this post!
Very helpful post! Thanks a lot!