Testing Promise.all with Jest / Vuex

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

我正在尝试测试使用Promise.all从API提取数据的Vuex动作,然后根据响应进行更改。但是,我的断言测试(expect.assertions(1))和查看是否调用了提交的测试都失败了。

我的动作是:

fetchUserProfile ({ dispatch, commit}) {
      const userAccountFetch = api.get('/user/account');
      const userProfileFetch = api.get('/user/profile');
      const userItemsFetch = api.get(`/user/purchases`);
      Promise.all([
        userAccountFetch.catch((error) => {
          console.error(error);
          return { error, };
        }), 
        userProfileFetch.catch((error) => { 
          console.error(error); 
          return { error, };
        }),
        userItemsFetch.catch((error) => {
          console.error(error);
          return { error, };
        }),
      ]).then((responses) => {
          commit('setUserAccount', {responses});
        }
      });
  }

我的测试如下:

jest.mock('@api/api.js', () => ({ get: jest.fn(), }));
const mockApi = require('@api/api.js');

test('fetchUserProfile performs commit on successful fetch', () => {
    const mockResponse = [{userAccount: ....}, {userProfile: ...}, {userItems: ....}];
    mockApi.get.mockReturnValueOnce(Promise.resolve(mockResponse[0]));
    mockApi.get.mockReturnValueOnce(Promise.resolve(mockResponse[1]));
    mockApi.get.mockReturnValueOnce(Promise.resolve(mockResponse[2]));
    expect.assertions(1);
    fetchUserProfile({ commit, state, }).then(() => expect(commit).toHaveBeenCalledTimes(1));
  });

我在整个操作过程中都放置了console.logs,并且测试将其降至执行提交的那一行,但是由于某种原因,测试未通过。我不确定这是怎么回事。任何帮助将不胜感激。

mocking jestjs vuex es6-promise
1个回答
0
投票

这是一个非常常见的反模式,使用诺言的函数不会返回可以链接的诺言。这阻止了它的有效使用和测试。

应该是:

return Promise.all(...)

另一个问题是Jest异步测试没有返回承诺。这会导致未捕获的拒绝,不会影响测试结果。

async..await是维护执行顺序的有效方法; async函数总是返回一个Promise:

test('fetchUserProfile performs commit on successful fetch', async () => {
    ....
    await fetchUserProfile({ commit, state });
    expect(commit).toHaveBeenCalledTimes(1);
});
© www.soinside.com 2019 - 2024. All rights reserved.