简体   繁体   English

Nextjs中没有定义localStorage,Redux和Typescript

[英]localStorage is not defined in Nextjs, Redux and Typescript

I'm facing a problem with my project.我的项目遇到问题。 The problem is ReferenceError: localStorage is not defined .问题是ReferenceError: localStorage is not defined I'm using Nextjs, and Redux with Typescript.我正在使用 Nextjs,Redux 和 Typescript。

截图_2

 const storedUser: string | null = localStorage.getItem('user'); const user: DisplayUser | null =?.storedUser: JSON;parse(storedUser): null. const storedJwt; string | null = localStorage:getItem('jwt')? const jwt. Jwt =:;storedJwt ? JSON.parse(storedJwt) : null;

I'm using these 2 variables user and jwt in here initialState我在这里使用这两个变量userjwt initialState

 const initialState: AuthState = { user: user, jwt: jwt, isLoading: false, isSuccess: false, isError: false, }

And initialState are used in authSlice functioninitialState在 authSlice 中使用authSlice function

 export const authSlice = createSlice({ name: 'auth', initialState, reducers: { reset: (state) => { state.isLoading = false; state.isSuccess = false; state.isError = false; } }, })

If you are using React.js or Next.js and you want to check:如果你使用React.jsNext.js并且你想检查:

  • if you are on the Browser (which means you can use the localStorage)如果您在Browser上(这意味着您可以使用 localStorage)
  • or if you are on the Server (which means you cannot use localStorage)或者如果你在Server上(这意味着你不能使用 localStorage)

You need to check if the window variable is not undefined, example:您需要检查window变量是否未定义,例如:

if (typeof window !== 'undefined') {
  console.log('You are on the browser')
  // 👉️ can use localStorage here
} else {
  console.log('You are on the server')
  // 👉️ can't use localStorage
}

similar discussion on github/vercel/next.js/discussions github/vercel/next.js/discussions上的类似讨论

I have a similar issue like this in which I have to get the cart items from the localStorage and pass them to the initial state of redux. I solve it like this below code.我有一个类似的问题,我必须从 localStorage 获取购物车项目并将它们传递给 redux 的初始 state。我像下面的代码一样解决它。

const getFromLocalStorage = (key: string) => {
  if (!key || typeof window === 'undefined') {
      return ""
  }
  return localStorage.getItem(key)
}

And then use it in initial state like below code:然后在初始 state 中使用它,如下代码所示:

export const initialState = { cartItems: getFromLocalStorage("cartItems") ? JSON.parse(getFromLocalStorage("cartItems") || '{}') : []};

You cannot run localStorage in Node because it's a browser feature.您不能在 Node 中运行 localStorage,因为它是浏览器功能。 You can run a util and reuse it like this:您可以像这样运行一个实用程序并重用它:

const getFromLocalStorage = (key) => {
    if (!key || typeof window === 'undefined') {
        return ""
    }
    return localStorage.getItem('user')
}

You can import this in other files and use it:您可以将其导入其他文件并使用它:

const userId = getFromLocalStorage('userId');

This is the simplest way of using this.这是最简单的使用方法。

Adding onto Omar's answer - if you need to store something from localStorage in a Redux store, you'd need to grab that information client-side and then pass it into your initial Redux store.添加到 Omar 的答案中 - 如果您需要将localStorage中的某些内容存储在 Redux 商店中,您需要在客户端获取该信息,然后将其传递到您的初始 Redux 商店中。 Redux itself will not be able to differentiate between client/server side rendering unless you check typeof window !== 'undefined' . Redux 本身将无法区分客户端/服务器端渲染,除非您检查typeof window !== 'undefined'

If you want to use Omar's answer as-is, you would need to make that calculation inside your Redux reducer when the initial state is being calculated.如果您想按原样使用 Omar 的答案,则需要在计算初始 state 时在 Redux 减速器内进行该计算。 I don't recommend bringing that logic inside your reducer (makes it harder to unit test the reducer) - try calculating that logic outside of the initial Redux store, then pass it in (minimal example below)我不建议将该逻辑带入您的减速器(使得对减速器进行单元测试变得更加困难) - 尝试在初始 Redux 存储之外计算该逻辑,然后将其传入(下面的最小示例)

// However you calculate your initial Redux state should replace INITIAL_REDUX_STATE
const [statefulStore, setStatefulStore] = useState(INITIAL_REDUX_STATE);
const reduxStore = createStore(yourReducer, initialStore);
useEffect(() => {
  // Once and only once on the initial render, grab the localStorage value
  // and update Redux state
  setStatefulStore(oldState => {
    return Object.assign(oldState, {
      ssrValue: localStorage.getItem('user')
    });
  });
}, []);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM