or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

docs

index.md
tile.json

tessl/npm-jest-date-mock

Mock Date when run unit test cases with jest to make tests of Date easier.

Workspace
tessl
Visibility
Public
Created
Last updated
Describes
npmpkg:npm/jest-date-mock@1.0.x

To install, run

npx @tessl/cli install tessl/npm-jest-date-mock@1.0.0

index.mddocs/

Jest Date Mock

Jest Date Mock is a Jest testing utility that enables developers to mock the Date class for consistent and predictable unit tests. It provides simple controls to advance, set, or reset mocked time, supporting both browser and Node.js environments with automatic environment detection.

Package Information

  • Package Name: jest-date-mock
  • Package Type: npm
  • Language: JavaScript
  • Installation: npm install --save-dev jest-date-mock

Core Imports

import { advanceBy, advanceTo, clear } from "jest-date-mock";

For CommonJS:

const { advanceBy, advanceTo, clear } = require("jest-date-mock");

Basic Usage

import { advanceBy, advanceTo, clear } from "jest-date-mock";

describe("Date mocking tests", () => {
  beforeEach(() => {
    // Set a fixed date for consistent testing
    advanceTo(new Date("2023-01-01T00:00:00.000Z"));
  });

  afterEach(() => {
    // Reset to real time after each test
    clear();
  });

  test("should mock Date constructor", () => {
    const now = new Date();
    expect(now.toISOString()).toBe("2023-01-01T00:00:00.000Z");
  });

  test("should advance time", () => {
    advanceBy(1000); // Advance by 1 second
    const now = new Date();
    expect(now.toISOString()).toBe("2023-01-01T00:00:01.000Z");
  });
});

Architecture

Jest Date Mock uses a sophisticated approach to provide seamless Date mocking across different JavaScript environments:

Environment Detection: The package automatically detects the runtime environment on import and applies the appropriate mocking strategy:

  • Node.js environment: Replaces global.Date with the mocked implementation
  • Browser environment: Replaces global.window.Date with the mocked implementation

Date Class Replacement: The core mocking mechanism creates a new Date class that inherits from the original Date class while intercepting constructor calls and static methods. This ensures full API compatibility while enabling time control.

State Management: Internal state tracks the current mocked timestamp, with three states:

  • Unmocked (undefined): Uses real system time
  • Fixed time: Returns the set timestamp
  • Advanced time: Calculates time based on initial timestamp plus accumulated advances

Prototype Chain Preservation: The mocked Date class maintains the complete prototype chain and constructor relationships, ensuring instanceof checks and method availability work correctly.

Jest Configuration

Add to your package.json:

{
  "jest": {
    "setupFiles": ["jest-date-mock"]
  }
}

Or if you already have setupFiles:

{
  "jest": {
    "setupFiles": ["./__setups__/other.js", "jest-date-mock"]
  }
}

Capabilities

Advance Time by Offset

Advances the current mocked date by specified milliseconds.

/**
 * Advances the current mocked date by specified milliseconds
 * @param {number} ms - Milliseconds to advance the date by (defaults to 0 if falsy)
 * @returns {number} The new timestamp after advancing
 */
function advanceBy(ms?: number): number;

Usage:

import { advanceBy } from "jest-date-mock";

// Start from current time if no mock is active
advanceBy(5000); // Advance by 5 seconds

// Or advance from existing mock time
advanceTo(new Date("2023-01-01T00:00:00.000Z"));
advanceBy(60000); // Now at 2023-01-01T00:01:00.000Z

Set Specific Time

Sets the mocked date to a specific timestamp.

/**
 * Sets the mocked date to a specific timestamp
 * @param {number|Date|string} ms - Timestamp, Date object, or date string to set mock to; if falsy, sets to epoch (0)
 * @returns {number} The timestamp that was set
 */
function advanceTo(ms?: number | Date | string): number;

Usage:

import { advanceTo } from "jest-date-mock";

// Set to specific date
advanceTo(new Date("2023-06-15T12:30:00.000Z"));

// Set to timestamp
advanceTo(1687094200000);

// Set to epoch (if falsy value provided)
advanceTo(0);
advanceTo(null);
advanceTo(undefined);

Clear Date Mock

Clears the date mock, returning to real-time Date behavior.

/**
 * Clears the date mock, returning to real-time Date behavior
 * @returns {undefined}
 */
function clear(): undefined;

Usage:

import { clear } from "jest-date-mock";

// After setting up mocks
advanceTo(new Date("2023-01-01"));

// Clear the mock to return to real time
clear();

// Now Date will return actual current time
const realNow = new Date();

Version

Package version string constant.

const version: string;

Types

/**
 * The Date constructor interface
 */
interface DateConstructor {
  new (): Date;
  new (value: number | string): Date;
  new (year: number, month: number, date?: number, hours?: number, minutes?: number, seconds?: number, ms?: number): Date;
  (): string;
  readonly prototype: Date;
  now(): number;
  parse(s: string): number;
  UTC(year: number, month: number, date?: number, hours?: number, minutes?: number, seconds?: number, ms?: number): number;
}

Environment Support

jest-date-mock automatically detects the runtime environment and applies the appropriate mocking:

  • Node.js environment: Mocks global.Date
  • Browser environment: Mocks global.window.Date

The package works seamlessly in both environments without any additional configuration.

Mocked Date Class Features

When active, the mocked Date class provides:

  • Full Date API compatibility: All standard Date methods and properties work normally
  • Constructor mocking: new Date() returns the mocked time
  • Static method mocking: Date.now() returns the mocked timestamp
  • Original Date access: Date.__OriginalDate__ provides access to the original Date class
  • Real-time access: Date.current() returns the actual current time regardless of mock state

Enhanced Date Class API

When jest-date-mock is active, the global Date class is enhanced with additional methods:

/**
 * Returns the mocked timestamp, or real time if no mock is active
 * @returns {number} Current timestamp in milliseconds
 */
Date.now(): number;

/**
 * Reference to the original, unmocked Date class
 * @type {DateConstructor}
 */
Date.__OriginalDate__: DateConstructor;

/**
 * Returns the actual current system time, ignoring any active mock
 * @returns {number} Real system timestamp in milliseconds
 */
Date.current(): number;

Testing Patterns

Setup and Teardown

import { advanceTo, clear } from "jest-date-mock";

describe("Time-dependent functionality", () => {
  beforeEach(() => {
    // Set consistent starting point
    advanceTo(new Date("2023-01-01T00:00:00.000Z"));
  });

  afterEach(() => {
    // Clean up after each test
    clear();
  });

  // Your tests here
});

Testing Time Progression

import { advanceBy, advanceTo } from "jest-date-mock";

test("should handle time progression", () => {
  advanceTo(new Date("2023-01-01T00:00:00.000Z"));
  
  const start = new Date();
  advanceBy(60000); // Advance 1 minute
  const end = new Date();
  
  expect(end.getTime() - start.getTime()).toBe(60000);
});