如何用玩笑模拟nestjs-redis

时间:2020-08-28 18:30:37

标签: redis jestjs nestjs

我正在尝试模拟和监视Nestjs设置中的redis set方法,但我认为它没有按预期方式工作。

    const mockRedis = {
      set: jest.fn().mockResolvedValue(undefined),
    };

    const mockRedisService = {
      getClient: jest.fn(() => mockRedis),
    };

    beforeEach(async () => {
      const moduleRef = await Test.createTestingModule({
        providers: [
          { provide: RedisService, useValue: mockRedisService },
        ],
      }).compile();
    });

    it('...',() => {
      const redisSetSpy = jest.spyOn(mockRedis, 'set');

      myTestedMethod();

      expect(redisSetSpy).toBeCalledWith(/* args here */);
    })

我怀疑在这种情况下无法将spyOn与嵌套方法一起用作set吗?我应该如何模拟Redis以便能够在set上使用spyOn?在这种情况下,用于redis的库为nestjs-redis

1 个答案:

答案 0 :(得分:2)

您不必使用spyOn来检查已传递给函数的争论。您可以简单地创建一个jest.fn()

let mockRedisSet;

// Function that creates the testing app.
const createApp = () => {
  const mockRedis = {
    set: mockRedisSet,
  };

  const mockRedisService = {
    getClient: jest.fn(() => mockRedis),
  };

  const moduleRef = await Test.createTestingModule({
    providers: [{ provide: RedisService, useValue: mockRedisService }],
  }).compile();
};

// For each test, set default mock and create testing app.
beforeEach(async () => {
  mockRedisSet = jest.fn().mockResolvedValue(undefined);
  createApp();
});

describe("...", () => {
  // For each sub tests, set default mock and create testing app.
  beforeEach(async () => {
    mockRedisSet = jest.fn().mockResolvedValue(/* Specific value for sub tests */);
    createApp();
  });

  it("...", () => {
    myTestedMethod();

    // Check which arguments was passed to the mock function.
    expect(mockRedisSet).toHaveBeenCalledWith(/* args here */);
  });
});

以这种方式创建模拟程序要简单得多,因为您只需创建模拟对象并测试功能的使用即可。

这里的间谍是mockRedisSet,并且我重新组织了您的测试文件,因此间谍功能具有默认值,可以为特定测试覆盖。您可以更好地控制测试值,并为每个测试重置默认值,以使测试不会相互干扰。