Ошибка: Предупреждение: ПО промежуточного слоя для RTK-Query API по адресу reducerPath «api» не было добавлено в магазин, но оно было добавлено

Итак, я переношу свое приложение на NextJS, и у меня есть следующая конфигурация магазина. Сейчас это немного грязно, так как я буду все очищать/уменьшать дублированный код, как только все заработает.

import { configureStore } from '@reduxjs/toolkit';
import AsyncStorage from '@react-native-async-storage/async-storage';
import {
  FLUSH,
  REHYDRATE,
  PAUSE,
  PERSIST,
  PURGE,
  REGISTER,
} from 'redux-persist';
import expireReducer from 'redux-persist-expire';
import { API } from 'utils/RTKAPI';
import createSagaMiddleware from 'redux-saga';
import { createOrSyncSettings } from 'controllers/SettingsController';
import { syncWords } from 'controllers/WordController';
import { syncSentences } from 'controllers/SentenceController';
import { syncBookmarks } from 'controllers/BookmarkController';
import { syncReadArticles } from 'controllers/ReadArticleController';
import rootSaga from 'reducers/sagas/index';
import moment from 'moment';
import { createWrapper, HYDRATE } from 'next-redux-wrapper';
import rootReducer from 'reducers/rootReducer';


const makeStore = () => {
  const SSR = typeof window === 'undefined';
  if (SSR) {

    const sagaMiddleware = createSagaMiddleware();

    const store = configureStore({
      middleware: (getDefaultMiddleware) =>
        getDefaultMiddleware({
          serializableCheck: {
            ignoredActions: [FLUSH, REHYDRATE, PAUSE, PERSIST, PURGE, REGISTER],
          },
        }).concat(
          loggerMiddleware,
          promiseMiddleware,
          sagaMiddleware,
          syncMiddleware,
          API.middleware
        ),
      reducer: rootReducer(),
    });
    sagaMiddleware.run(rootSaga);
    return store;
  } else {
    const { persistStore, persistReducer } = require('redux-persist');
    const sagaMiddleware = createSagaMiddleware();

    const persistConfig = {
      key: 'root',
      storage: AsyncStorage,
      blacklist: [API.reducerPath, 'router', 'sidebar', 'currentchar'],
      transforms: [
        expireReducer('date', {
          expireSeconds: 86400,
          expiredState: {
            end_date: moment().format('YYYY-MM-DD'),
            start_date: '2021-07-04',
          },
          autoExpire: true,
        }),
      ],
    };

    const persistedReducer = persistReducer(persistConfig, rootReducer());
    const store = configureStore({
      middleware: (getDefaultMiddleware) =>
        getDefaultMiddleware({
          serializableCheck: {
            ignoredActions: [FLUSH, REHYDRATE, PAUSE, PERSIST, PURGE, REGISTER],
          },
        }).concat(
          loggerMiddleware,
          promiseMiddleware,
          sagaMiddleware,
          syncMiddleware,
          API.middleware
        ),
      reducer: persistedReducer,
    });

    sagaMiddleware.run(rootSaga);

    store.__persistor = persistStore(store); // Necessary hack

    return store;
  }
};

export const wrapper = createWrapper(makeStore);

async function callSync(store) {
  const storeState = await store.getState();
  const profile = storeState.profile;
  if (profile !== null) {
    createOrSyncSettings(profile.id);
    syncWords(profile);
    syncSentences(profile);
    syncBookmarks(profile);
    syncReadArticles(profile);
  }
}

const loggerMiddleware = (store) => (next) => (action) => {
  next(action);
};

function promiseMiddleware({ dispatch }) {
  function isPromise(val) {
    return val && typeof val.then === 'function';
  }

  return (next) => (action) => {
    return isPromise(action.payload)
      ? action.payload.then(
          (result) => dispatch({ ...action, payload: result }),
          (error) => dispatch({ ...action, payload: error, error: true })
        )
      : next(action);
  };
}

const syncMiddleware = (store) => (next) => (action) => {
  next(action);
  if (action.type === 'persist/REHYDRATE') {
    callSync(store);
  }
};

Мой rootReducer тоже довольно стандартный:

export default () =>
  combineReducers({
    [API.reducerPath]: API.reducer,
    categories,
    profile,
    ...

Тем не менее, несмотря на мою конфигурацию, я продолжаю получать эту ошибку:

Error: Warning: Middleware for RTK-Query API at reducerPath "api" has not been added to the store.
You must add the middleware for RTK-Query to function correctly!

Что именно я делаю неправильно? Насколько я могу судить, мой reducerPath был добавлен в магазин.

Аналогичная конфигурация магазина отлично работала в предыдущей итерации моего приложения, в котором не использовался NextJS, поэтому мне интересно, что вызывает проблему сейчас.

Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
В настоящее время производительность загрузки веб-сайта имеет решающее значение не только для удобства пользователей, но и для ранжирования в...
Безумие обратных вызовов в javascript [JS]
Безумие обратных вызовов в javascript [JS]
Здравствуйте! Юный падаван 🚀. Присоединяйся ко мне, чтобы разобраться в одной из самых запутанных концепций, когда вы начинаете изучать мир...
Система управления парковками с использованием HTML, CSS и JavaScript
Система управления парковками с использованием HTML, CSS и JavaScript
Веб-сайт по управлению парковками был создан с использованием HTML, CSS и JavaScript. Это простой сайт, ничего вычурного. Основная цель -...
JavaScript Вопросы с множественным выбором и ответы
JavaScript Вопросы с множественным выбором и ответы
Если вы ищете платформу, которая предоставляет вам бесплатный тест JavaScript MCQ (Multiple Choice Questions With Answers) для оценки ваших знаний,...
1
0
115
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Ваш рукописный Redux syncMiddleware не работает. Он не возвращает результат next(action). Это означает, что если более позднее промежуточное ПО попытается вернуть значение, этот более поздний возвращаемый результат будет отброшен и никогда не будет возвращен из dispatch.

Проверка конфигурации RTKQ основана на отправке специального действия, которое перехватывается промежуточным программным обеспечением RTKQ и возвращает соответствующий результат. Поскольку ваше промежуточное ПО отбрасывает этот результат, уровень пользовательского интерфейса делает вывод, что промежуточное ПО RTKQ на самом деле было добавлено неправильно. (И в каком-то смысле это было не так!)

Так что мне просто нужно вернуть следующее (действие), и все будет хорошо?

Steven Matthews 03.01.2023 05:52

Попытался добавить это в конец моего syncMiddleware: return next(action); Все еще вижу ту же ошибку

Steven Matthews 03.01.2023 06:33

Похоже, у loggerMiddleware та же проблема. Если вы убедитесь, что каждое промежуточное ПО обновлено, чтобы в какой-то момент вернуть результат next(action), это все еще происходит?

markerikson 05.01.2023 03:19

Да, похоже, проблема устранена. Странный. У меня было одно и то же промежуточное ПО на протяжении всей жизни моего приложения, и раньше оно никогда не вызывало эту проблему, только при переходе на Next. Я собираюсь прочитать документы о том, как написать лучшее промежуточное программное обеспечение. Спасибо.

Steven Matthews 05.01.2023 18:19

Другие вопросы по теме