javascript 如何使用redux-toolkit在nextjs 13.4应用程序目录中获得redux-persist?

yzckvree  于 12个月前  发布在  Java
关注(0)|答案(2)|浏览(130)

我准备使用nextjs使用新的app router来设置一个新的项目,我可以使用基于nextjs仓库中的官方示例的提供程序来设置redux工具包:https://github.com/vercel/next.js/tree/canary/examples/with-redux但问题是当我添加redux-persistent时:

"use client";

import { PersistGate } from "redux-persist/integration/react";
/* Core */
import { Provider } from "react-redux";

/* Instruments */
import { persistor, reduxStore } from "@/lib/redux";

export const Providers = ({ children }) => {
  return (
    <Provider store={reduxStore}>
      <PersistGate persistor={persistor}>
        {children}
      </PersistGate>
    </Provider>
  );
};

我也尝试使用动态导入导入PersistGate:

"use client";

import dynamic from "next/dynamic";

const PersistGateComponent = dynamic(
  () =>
    import("redux-persist/integration/react").then((mod) => mod.PersistGate),
  {
    ssr: false,
  }
);

const SSROutset = ({ children, persistor }) => {
  if (typeof window !== "undefined") {
    return (
      <PersistGateComponent persistor={persistor}>
        {children}
      </PersistGateComponent>
    );
  }

  // You can create a visually hidden component to avoid layout flashes and also maintain SEO content
  // see Chakra for an example of one https://chakra-ui.com/docs/components/visually-hidden
  return (
    <span
      style={{
        border: "0",
        clip: "rect(0, 0, 0, 0)",
        height: "1px",
        width: "1px",
        margin: "-1px",
        padding: "0",
        overflow: "hidden",
        whiteSpace: "nowrap",
        position: "absolute",
      }}
    >
      {children}
    </span>
  );
};

export default SSROutset

以及:

"use client";

/* Core */
import { Provider } from "react-redux";

/* Instruments */
import { persistor, reduxStore } from "@/lib/redux";
import SSROutset from "./redux/SSROutset";

export const Providers = ({ children }) => {
  return (
    <Provider store={reduxStore}>
      <SSROutset persistor={persistor}>
        {children}
      </SSROutset>
    </Provider>
  );
};

仍然出现以下错误:
Hydration failed because the initial UI does not match what was rendered on the server.

zhte4eai

zhte4eai1#

我用useEffect解决了这个问题

const { list } = useAppSelector(state => state.example);

const [isMounted, setIsMounted] = useState(false);

useEffect(() => {
  setIsMounted(true);
}, []);

return (
  <div>
     {isMounted && list.length > 0 && ( ... )}
  </div>
)
z6psavjg

z6psavjg2#

我已经解决了这个问题,商店的初始

import {
  addToCartMiddleware,
  updateCartMiddleware,
  deleteCartMiddleware,
} from "./slices/checkout/middleware";
import CheckoutLineReducer from "./slices/checkout/Line.Slice";

let store;

const rootReducer = combineReducers({
  notification: NotificationReducer,

});

const middlewares = [
  addToCartMiddleware,
  updateCartMiddleware,
  deleteCartMiddleware,
  thunk,
];

const persistConfig = {
  key: "primary",
  storage,
  whitelist: ["auth", "checkout"],
};

const persistedReducer = persistReducer(persistConfig, rootReducer);

function makeStore() {
  return configureStore({
    reducer: persistedReducer,
    devTools: process.env.NODE_ENV !== "production",
    middleware: middlewares,
  });
}

export const initializeStore = (preloadedState) => {
  let _store = store ?? makeStore();

  // For SSG and SSR always create a new store
  if (typeof window === "undefined") return _store;

  // Create the store once in the client
  if (!store) store = _store;

  return _store;
};

export function useStore() {
  const store = useMemo(() => initializeStore(), []);
  return store;
}

export default makeStore;

然后制作Provider组件,将项目 Package 在Layout中

"use client";
import { Provider } from "react-redux";
import { PersistGate } from "redux-persist/integration/react";
import { persistStore } from "redux-persist";
import { useStore } from "@/lib/redux/store";

const ProviderWrapper = ({ children }) => {
  const store = useStore();
  let persistor;

  if (store) {
    persistor = persistStore(store, {}, function () {
      persistor.persist();
    });
  }

  return (
    <Provider store={store}>
      <PersistGate loading={<p>loading</p>} persistor={persistor} />
      {children}
    </Provider>
  );
};

export default ProviderWrapper;

persist存储工作,但它在persist/PERSIST persist/REYHIDRATION中执行了很多操作
注意:在Provider中,我把孩子放在PersistCate之外,因为当你在persistgate中添加它时,所有的应用程序都将是客户端的

相关问题