Редукционный редуктор запускается несколько раз при первой отправке неиспользованного действия - PullRequest
0 голосов
/ 07 марта 2019

Обновление: я использую React-Boilerplate, не измененный от оригинала, за исключением контейнеров / компонентов. Редукторы запускаются несколько раз, иногда более двух раз, когда новое действие отправляется впервые, но не тогда, когда одно и то же действие отправляется впоследствии. Сами действия не выполняются при повторных вызовах редуктора, но состояние обновляется и повторно выполняет визуализацию компонента.

Например: если я отправлю action1, который обновляет reducerCase1, а не action2, который обновляет reducerCase2, action1 будет выполняться один раз, а reducerCase1 будет выполняться дважды. action2 и reducerCase2 не будут работать. Если я затем отправлю action3, который обновляет reducerCase3, reducerCase1 будет вызываться несколько раз, но не будут вызваны action1, action2 и reducerCase2.

Если я отправлю action2 таким же образом, как action1, он будет обрабатываться так же, как action1 и reducerCase1, многократно запуская редуктор без запуска действия.

Если после всего этого я отправлю action3 во второй раз, reducerCase1 вообще не будет запущен (как и должно быть).

Здесь меня интересуют действия GET_CATEGORIES и GET_CATS_COMPLETED:

enter image description here

вот журнал консоли внутри редуктора:

export default function Categories(state = initialState, action) {
  switch (action.type) {
    case GET_CATEGORIES:
      debugger;
      console.log('getting categories...');
      return state.set('isLoading', true);
    case GET_CATEGORIES_COMPLETED:
      debugger;
      console.log('setting categories...');
      return state
        .set('categories', fromJS(action.cats))
        .set('isLoading', false);

enter image description here

Поскольку это происходит со всеми моими редукторами, я предполагаю, что это как-то связано с mapDispatchToProps:

const mapStateToProps = createStructuredSelector({
  categories: makeSelectCategories(),
  ownerId: makeSelectProfileId(),
  selectedCategoryId: makeSelectSelectedCategoryId(),
  isLoading: makeSelectIsLoading(),
});

const mapDispatchToProps = {
  getCategories,
  setCategory,
};

const withConnect = connect(
  mapStateToProps,
  mapDispatchToProps
);

const withReducer = injectReducer({ key: 'CategoryContainer', reducer });
const withSaga = injectSaga({ key: 'CategoryContainer', saga });

export default compose(
  withSaga,
  withReducer,
  withConnect
)(CategoryContainer);

и вот мои действия:

export function getCategories() {
  console.log('inside getCategories()');
  return {
    type: GET_CATEGORIES,
  };
}

export function getCategoriesCompleted(cats) {
  return {
    type: GET_CATEGORIES_COMPLETED,
    cats,
  };
}

и, наконец, сага:

export default function* CategoryContainerSaga() {
  yield takeLatest(GET_CATEGORIES, getCategories);
}

function* getCategories() {
  try {
    const plidParam = yield call(getPlParam);
    const profileId = yield call(getProfileId);
    const url = getUrl();
    const { categories2, playlist } = yield call(
      getCatsRequest,
      url,
      profileId,
      plidParam
    );
    yield put(getCategoriesCompleted(categories2));
    if (playlist) yield put(setPlaylist(playlist));
  } catch (error) {
    yield put(getCategoriesCompleted([]));
    yield put(setError(error.message));
  }
}

1 Ответ

0 голосов
/ 07 марта 2019

Благодаря комментарию lecstor, я смог определить, что это ожидаемое поведение Redux devtools.

...