Coding Planet

[React] redux-persist 설치 및 환경설정 (store.js 예시) 본문

front

[React] redux-persist 설치 및 환경설정 (store.js 예시)

jhj.sharon 2024. 7. 10. 10:43
반응형
redux-persist 상태를 유지함으로써 페이지를 새로고침하거나 탐색할 때도 사용자 설정이나 임시 데이터(예: 폼 입력 내용)를 유지할 수 있다. 또한 백엔드 서버와의 통신을 줄여주어 사용자 경험을 크게 향상시킨다.
보통 로컬스토리지에 저장하게 된다. 다만 이런 클라이언트상의 저장은 문제가 있으므로 보안이 요구되는 데이터 보다는 임시데이터 위주로 저장한다.

 

 

 

설치

yarn add redux-persist

 

 

환경설정

  • store.js는 Redux 스토어를 생성하고 설정하는 파일이다. 여기에 persistConfig를 포함시켜 저장소와 관련된 모든 설정을 한 곳에서 관리하는 것이 좋.
  • 스토어 생성 과정에서 persistReducer와 함께 persistConfig를 사용하여 일관된 상태 저장 및 복원을 보장한다.
  • 기본적으로 로컬 저장소를 사용하지만, redux-persist는 localStorage, sessionStorage, AsyncStorage(React Native) 등 다양한 저장소를 지원한다. 아래 예제에서는 로컬 저장소(store)를 사용한다.
// redux/store.js
import { useMemo } from 'react';
import { createStore, applyMiddleware } from 'redux';
import createSagaMiddleware from 'redux-saga';
import { composeWithDevTools } from 'redux-devtools-extension';
import { persistStore, persistReducer } from 'redux-persist';
import storage from 'redux-persist/lib/storage';
import rootReducer from './rootReducer';
import rootSaga from './saga';

// persistConfig 정의
const persistConfig = {
    key: 'root', //로컬 저장소에 저장될 때의 상태 키, 일반적으로 루트 리듀서
    storage, //태를 저장할 저장소 엔진을 정의
    whitelist: ['auth'], // 예시로 'auth' 리듀서만 저장
    blacklist: ['temporaryData'], // 저장하지 않을 리듀서
    version: 1, // 상태 구조가 변경될 때 사용하여 이전 버전과 호환되지 않는 상태를 무효화
        migrate: (state) => {
        // 상태 변환 로직 :상태 구조가 변경될 때 상태를 변환하는 함수
        return Promise.resolve(newState);
    },
      timeout: 10000, //복원 시간 제한(밀리초 단위)입니다.

};

const persistedReducer = persistReducer(persistConfig, rootReducer);

let store;

function initStore(initialState) {
    const sagaMiddleware = createSagaMiddleware();
    const store = createStore(
        persistedReducer,
        initialState,
        composeWithDevTools(applyMiddleware(sagaMiddleware))
    );

    store.sagaTask = sagaMiddleware.run(rootSaga);

    return store;
}

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

    if (preloadedState && store) {
        _store = initStore({
            ...store.getState(),
            ...preloadedState,
        });
        store = undefined;
    }

    if (typeof window === 'undefined') return _store;
    if (!store) store = _store;

    return _store;
};

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

// persistStore를 사용하여 스토어를 지속적으로 유지
export const persistor = persistStore(store);

 

 

사용예시

import React from 'react';
import { Provider } from 'react-redux';
import { useStore, persistor } from '../redux/store';
import { PersistGate } from 'redux-persist/integration/react';
import Header from '../src/app/components/layout/Header';
import BottomNavBar from '../src/app/components/layout/BottomNavBar';
import '../src/app/assets/styles/global.css';

const GreenScreen = ({ Component, pageProps }) => (
    <div className="green-border">
        <Header />
        <Component {...pageProps} />
        <BottomNavBar />
    </div>
);

const MyApp = ({ Component, pageProps }) => {
    const store = useStore(pageProps.initialReduxState);

    return (
        <Provider store={store}>
            <PersistGate loading={null} persistor={persistor}>
            <GreenScreen Component={Component} pageProps={pageProps} />
            </PersistGate>
        </Provider>
    );
};

export default MyApp;
반응형
Comments