如何在每个 vitest 测试中重新模拟 json 文件导入

问题描述 投票:0回答:1

我有一个名为

validateData()
的函数,它导入 json 文件 (data.json),并验证数据是否缺少任何字段。 我想编写多个
vitest
测试来测试该函数,并且我希望每个测试以不同的方式模拟 json 文件。

我尝试使用

vi.mock
进行模拟并确保提升默认导入,如下所示:

const mocks = vi.hoisted(() => {
  return {
    default: vi.fn(),
  };
});

vi.mock('data/data.json', () => {
  return {
    default: mocks.default,
  };
});

const obj1 = {
  id: 1,
  name: "obj1"
}

describe('validateData', () => {
  test('with valid data', () => {
    mocks.default.mockReturnValueOnce({ obj1 });
    expect(validateData()).toStrictEqual([]);
  });
  test('with missing field', () => {
    mocks.default.mockReturnValue({ obj1: { ...obj1, name: undefined } });
    expect(validateData()).toStrictEqual(['Missing name for obj1']);
  });
});

而数据 json 文件如下所示:

{
 obj1: {
   id: 1,
   name: "obj1"
 }
}

这仍然不起作用,

validateData
函数仍然使用实际的json而不是模拟。

javascript unit-testing vite vitest
1个回答
0
投票

我也遇到了这个问题,并设法通过使用

vi.doMock
await import(...)
vi.resetModules()
解决了它:

const obj1 = {
  id: 1,
  name: 'obj1'
}

describe('validateData', () => {
  afterEach(() => vi.resetModules());

  test('with valid data', async () => {
    vi.doMock('data/data.json', () => ({ default: { obj1 } }));
    const { validateData } = await import('./validator.js');
    expect(validateData()).toStrictEqual([]);
  });

  test('with missing field', async() => {
    vi.doMock('data/data.json', () => ({ default: { obj1: { ...obj1, name: undefined } } }));
    const { validateData } = await import('./validator.js');
    expect(validateData()).toStrictEqual(['Missing name for obj1']);
  });
});

在您给定的代码中,

validateData
和JSON在开始时仅导入一次。 所以后面模拟的返回值就不再起作用了。

使用

doMock
和动态导入时,每个测试中都会导入模拟的 JSON。每次测试后不要忘记重置模块。

© www.soinside.com 2019 - 2024. All rights reserved.