Develop/React

[Redux] redux-persist

ParkJava 2021. 10. 9. 19:23

 

React나 React Native 혹은 JavaScript 생태계에서 쓰일 수 있는 Redux라는 상태 관리 라이브러리가 널리 쓰이고 있습니다. 하지만 사용해보진 분들은 아시겠지만, Redux의 Store는 앱을 종료하거나 브라우저를 새로고침 하게 되면 저장되어있던 모든 상태가 제거됩니다. 
그래서 캐시 기능을 하는 여러가지의 방법 중 LocalStorage, SessionStorage등을 보편적으로 사용하는데, 

Redux-Persist는 이런 작업들을 굉장히 편리하게 제공하는 라이브러리입니다.

 

설치방법 

$ npm install redux-persist

 

사용해보기

 

환경

  • WebApp
  • React
  • Redux
  • Redux-Persist

프로젝트 세팅

 

1. 새로운 리액트 프로젝트를 생합니다.

$ npx create-react-app persisted-counter
$ cd persisted-counter

2. 프로젝트에 필요한 라이브러리들을 설치합니다.

$ npm i --save redux react-redux redux-persist

3. 불필요한 파일들 및 코드를 제거한 뒤 아래와 같은 구조를 만들어줍니다.

리듀서 및 스토어

1. src/modules/couner.js 파일에서 Counter Reducer를 생성합니다.

const INCREMENT = "counter/INCREMENT";
const DECREMENT = "counter/DECREMENT";

export const increment = () => ({ type: INCREMENT });
export const decrement = () => ({ type: DECREMENT });

const inititialState = 0;

const counter = (state = inititialState, action) => {
  switch (action.type) {
    case INCREMENT:
      return state + 1;
    case DECREMENT:
      return state - 1;
    default:
      return state;
  }
};

export default counter;

2. src/modules/index.js 파일에서 Root Reducer를 생성합니다.

import { combineReducers } from "redux";
import counter from "./counter";

const rootReducer = combineReducers({
  counter,
});

export default rootReducer;

3. 리듀서가 완성되면 store/index.js 파일에서 스토어를 생성합니다. 

import { createStore } from 'redux';
import rootReducer from '../modules';
import { persistStore, persistReducer } from 'redux-persist';
import storage from 'redux-persist/lib/storage';

const persistConfig = {
  key: 'root',
  storage
};

const enhancedReducer = persistReducer(persistConfig, rootReducer);

export default function configureStore() {
  const store = createStore(enhancedReducer);
  const persistor = persistStore(store);
  return { store, persistor };
};

컴포넌트 및 컨테이너

차례대로 Counter 컴포넌트, ConterContainer 컨테이너를 생성합니다.

import React from "react";

const Counter = ({ onIncrease, onDecrese, number }) => {
  return (
    <div>
      <h1>꼬박로그</h1>
      <span>{number}</span>
      <div>
        <button onClick={onIncrease}>+1</button>
        <button onClick={onDecrese}>-1</button>
      </div>
    </div>
  );
};

export default Counter;
import React from "react";
import { useSelector, useDispatch, shallowEqual } from "react-redux";
import Counter from "../components/Counter";
import { increment, decrement } from "../modules/counter";

const CounterContainer = () => {
  const counter = useSelector((state) => state.counter, shallowEqual);
  const dispatch = useDispatch();

  const onIncrease = () => dispatch(increment());
  const onDecrese = () => dispatch(decrement());

  return (
    <Counter number={counter} onIncrease={onIncrease} onDecrese={onDecrese} />
  );
};

export default CounterContainer;

 

마지막으로 index.js와 App.js를 세팅합니다.

import React from 'react';
import ReactDOM from 'react-dom';
import App from './App';

import { Provider } from 'react-redux';
import { PersistGate } from 'redux-persist/integration/react';

import configureStore from './store';

const { store, persistor } = configureStore();

const Root = () => (
  <Provider store={store}>
    <PersistGate loading={null} persistor={persistor}>
      <App />
    </PersistGate>
  </Provider>
);

ReactDOM.render(<Root />, document.getElementById('root'));

프로젝트를 실행해보면  스토어의 state값이 변하게 되면 로컬 스토리지에 데이터가 갱신되는 것을 확인할 수 있고, 새로고침을 하거나 브라우저를 닫아도 값이 유지가 되는 것을 확인할 수 있습니다.