Как инициализировать состояние Redux с помощью ответа асинхронного запроса - PullRequest
0 голосов
/ 06 ноября 2019

Я создаю React-Redux приложение, которое должно загружать список из API с самого начала. Мне удалось заставить его работать, инициализируя состояние с помощью жестко закодированного списка, пока:

reducers/Catalogs.js

import {
  GET_CATALOGS,
  SHOW_MESSAGE,
  HIDE_MESSAGE,
  GET_CATALOGS_SUCCESS
} from 'constants/ActionTypes';

const INIT_STATE = {
  loader: false,
  alertMessage: '',
  showMessage: false,
  catalogsList: ['uno', 'dos'] /// Hard coded initialization that must be from an api
};

export default (state=INIT_STATE, action) => {
  switch (action.type) {
    case GET_CATALOGS_SUCCESS: {
      return {
        ...state,
        loader: false,
        catalogsList: action.payload
      }
    }
    case SHOW_MESSAGE: {
      return {
        ...state,
        alertMessage: action.payload,
        showMessage: true,
        loader: false
      }
    }
    case HIDE_MESSAGE: {
      return {
        ...state,
        alertMessage: '',
        showMessage: false,
        loader: false
      }
    }
    case GET_CATALOGS: {
      return {
        ...state
      }
    }
    default:
      return state;
  }
}

Я знаю из показаний, что редукторы не должны делать асинхронные вызовыили отправлять действия, например, поэтому я использую redux-sagas для управления асинхронными вызовами.

sagas/Catalogs.js

import {all, call, fork, put, takeEvery} from "redux-saga/effects";
import {catalogs} from 'backend/Catalogs';
import {GET_CATALOGS} from "constants/ActionTypes";
import {getCatalogs, getCatalogsSuccess, showCatalogsMessage} from 'actions/Catalogs';

const getCatalogsRequest = async (group) =>
  await catalogs.getCatalogs(group)
    .then(catalogsList => catalogsList)
    .catch(error => error);

function* getCatalogsListFromRequest({payload}) {
  const {group} = payload;
  try {
    const catalogsList = yield call(getCatalogsRequest, group);
    if (catalogsList.message) {
      yield put(showCatalogsMessage(catalogsList.Message));
    } else {
      yield put(getCatalogsSuccess(catalogsList))
    }
  } catch (error) {
    yield put(showCatalogsMessage(error));
  }
}

export function* getCatalogsList() {
  yield takeEvery(GET_CATALOGS, getCatalogsListFromRequest);
}

export default function* rootSaga() {
  yield all([
    fork(getCatalogsList)
  ]);
}

Проблема в том, что я не надеваюне знаю, как использовать его для инициализации состояния, поскольку такая инициализация не является частью действия.

1 Ответ

0 голосов
/ 06 ноября 2019

В основном вам нужно создать componentDidMount() для вашего основного App компонента и отправить в него действие GET_CATALOGS, которое должно запрашивать данные о монтировании вашего приложения (при инициализации) и обновлении хранилища.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...