Vitest Module Mock Unit Test
Isolate a module under test with Vitest vi.mock hoisting, typed mock functions, and restore between tests so suites stay order-independent.
Code
import { describe, it, expect, vi, beforeEach } from 'vitest';
const rateClient = {
async getRate(currency: string): Promise<number> {
throw new Error('real network call in unit test');
},
};
vi.mock('./rate-client', () => ({
rateClient: { getRate: vi.fn() },
}));
import { priceInUsd } from './pricing';
import { rateClient } from './rate-client';
vi.mocked(rateClient.getRate).mockResolvedValue(7.2);
describe('priceInUsd', () => {
beforeEach(() => {
vi.clearAllMocks();
vi.mocked(rateClient.getRate).mockResolvedValue(7.2);
});
it('converts amounts using the fetched rate', async () => {
vi.mocked(rateClient.getRate).mockResolvedValue(7.2);
const result = await priceInUsd(100, 'eur');
expect(result).toBeCloseTo(720);
expect(rateClient.getRate).toHaveBeenCalledWith('eur');
});
it('rejects when the rate service fails', async () => {
vi.mocked(rateClient.getRate).mockRejectedValue(new Error('fx down'));
await expect(priceInUsd(100, 'eur')).rejects.toThrow('fx down');
});
it('caches repeat lookups within one call', async () => {
await priceInUsd(50, 'eur');
await priceInUsd(60, 'eur');
expect(rateClient.getRate).toHaveBeenCalledTimes(2);
});
});Report a problem with this exampleOpens a pre-filled issue on GitHub.