首页 文章

jest mocking promise方法被称为错误的次数

提问于
浏览
2

作为我的redux操作的一部分,它会发出几个连续的api请求 . apiCall 方法返回带有某个值的Promise,后续 apiCall 使用该值来发出另一个请求,依此类推 . 我正在使用Jest来测试这些api调用 .

const myAPI = {
  apiCall(param: any): Promise<any> {
    return new Promise((resolve, reject) => {
      resolve('result');
    });
  },
};

const serialAPIRequests = () => {
  myAPI.apiCall('first_param')
    .then((result) => {
      console.log(result);
      return myAPI.apiCall(result);
    })
    .then((result) => {
      console.log(result);
      return myAPI.apiCall(result);
    })
    .then((result) => {
      console.log(result);
      return Promise.resolve(result);
    });
};

我正在尝试编写一个测试,以确保 apiCall 被称为正确的次数和正确的参数 .

describe.only('my test', () => {
  it('should test api stuff', () => {
    myAPI.apiCall = jest.fn()
      .mockReturnValueOnce(Promise.resolve('result1'))
      .mockReturnValueOnce(Promise.resolve('result2'))
      .mockReturnValueOnce(Promise.resolve('result3'));
    serialAPIRequests();
    expect(myAPI.apiCall).toHaveBeenCalledTimes(3);
  });
});

会发生什么是Jest报告 Expected mock function to have been called three times, but it was called one time.

Jest测试结果显示

● Console

console.log 
  result1
console.log 
  result2
console.log 
  result3

 ● my test › should test api stuff

expect(jest.fn()).toHaveBeenCalledTimes(3)

Expected mock function to have been called three times, but it was called one time.

console.log显示不同值的事实意味着模拟返回正确地通过mock函数传递,并且它被调用了3次 .

可能导致此问题的原因以及如何正确测试此功能?

2 回答

  • 3

    使用async / await测试异步代码 . 在这里阅读更多:https://facebook.github.io/jest/docs/en/tutorial-async.html

    describe.only('my test', () => {
          it('should test api stuff', async () => {
            myAPI.apiCall = jest.fn()
              .mockReturnValueOnce(Promise.resolve('result1'))
              .mockReturnValueOnce(Promise.resolve('result2'))
              .mockReturnValueOnce(Promise.resolve('result3'));
            await serialAPIRequests();
            expect(myAPI.apiCall).toHaveBeenCalledTimes(3);
          });
        });
    
  • 2

    Promise是异步的,所以当你检查mock实际上被调用一次 .

    你可以这样做 . 等待所有调用完成并返回一个promise以指示测试是异步的 .

    return serialAPIRequests().then(() => {
        expect(myAPI.apiCall).toHaveBeenCalledTimes(3);
    })
    

相关问题