如何测试包含多个API请求和数组转换的redux-thunk操作?

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

我有一个redux-thunk动作,其中包含多个API请求,这些请求从一个端点获取数据以从另一个端点获取其他相关数据,并且我还进行了一些数组转换,以将某些数据合并在一起。

尽管我不确定这是否是最佳实践,但就目前而言,它满足了我的需求。但是,由于我不确定要测试的正确方法,因此很难进行测试。我搜寻了互联网并查看了“ thunk”测试的许多不同变体,但到目前为止,我的每种方法都失败了。

我将非常感谢一些有关如何测试重击动作(例如我的动作)的指南,或者可能有更好的实践,以帮助我简化测试。

我的重击动作...

export const fetchTopStreamsStartAsync = () => {
  return async dispatch => {
    try {
      const headers = {
        'Client-ID': process.env.CLIENT_ID
      };
      const url = 'https://api.twitch.tv/helix/streams?first=5';
      const userUrl = 'https://api.twitch.tv/helix/users?';
      let userIds = '';
      dispatch(fetchTopStreamsStart());

      const response = await axios.get(url, { headers });
      const topStreams = response.data.data;

      topStreams.forEach(stream => (userIds += `id=${stream.user_id}&`));
      userIds = userIds.slice(0, -1);

      const userResponse = await axios.get(userUrl + userIds, { headers });
      const users = userResponse.data.data;

      const completeStreams = topStreams.map(stream => {
        stream.avatar = users.find(
          user => user.id === stream.user_id
        ).profile_image_url;
        return stream;
      });

      const mappedStreams = completeStreams.map(
        ({ thumbnail_url, ...rest }) => ({
          ...rest,
          thumbnail: thumbnail_url.replace(/{width}x{height}/gi, '1280x720')
        })
      );

      dispatch(fetchTopStreamsSuccess(mappedStreams));
    } catch (error) {
      dispatch(fetchTopStreamsFail(error.message));
    }
  };
};

失败的许多测试方法之一...

import configureMockStore from 'redux-mock-store';
import thunk from 'redux-thunk';
import axios from 'axios';
import moxios from 'moxios';

import {
  fetchTopStreamsStart,
  fetchTopStreamsSuccess,
  fetchTopStreamsStartAsync
} from './streams.actions';

const mockStore = configureMockStore([thunk]);

describe('thunks', () => {
  describe('fetchTopStreamsStartAsync', () => {
    beforeEach(() => {
      moxios.install();
    });

    afterEach(() => {
      moxios.uninstall();
    });
    it('creates both fetchTopStreamsStart and fetchTopStreamsSuccess when api call succeeds', () => {
      const responsePayload = [{ id: 1 }, { id: 2 }, { id: 3 }];

      moxios.wait(() => {
        const request = moxios.requests.mostRecent();
        request.respondWith({
          status: 200,
          response: responsePayload
        });
      });

      const store = mockStore();

      const expectedActions = [
        fetchTopStreamsStart(),
        fetchTopStreamsSuccess(responsePayload)
      ];

      return store.dispatch(fetchTopStreamsStartAsync()).then(() => {
        // return of async actions
        expect(store.getActions()).toEqual(expectedActions);
      });
    });
  });
});

这是我在接收值的失败测试中遇到的错误...

+     "payload": "Cannot read property 'forEach' of undefined",
    +     "type": "FETCH_TOP_STREAMS_FAIL",

UPDATE:如@mgarcia所建议,我将responsePayload的格式从[{ id: 1 }, { id: 2 }, { id: 3 }]更改为{ data: [{ id: 1 }, { id: 2 }, { id: 3 }] },现在我没有收到初始错误,但是现在收到以下错误:] >

: Timeout - Async callback was not invoked within the 5000ms timeout specified by jest.setTimeout.Timeout - Async callback was not invoked within the 5000ms timeout specified by jest.setTimeout.Error:

我仍然不了解的是,测试是否必须复制多个API调用的确切结构,或者仅模拟一个响应就足够了?我仍在尝试找出Async callback...错误的原因。

我有一个redux-thunk动作,其中包含多个API请求,这些请求将从一个端点获取的数据从另一个端点获取其他相关数据,并且我也有几个数组...

reactjs redux react-redux jestjs redux-thunk
1个回答
0
投票

您正在通过moxios模拟axios请求,但似乎您没有以预期的格式返回数据。

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