본문 바로가기
웹 프론트엔드/React 리액트 (기초)

[React] 리덕스(redux) 기능으로 데이터 관리하기 ① 기초

by 지구인한군 2020. 10. 16.

 지난 시간에는 컨텍스트(context) 기능으로 데이터 관리하는 법을 배웠습니다. 컨텍스트가 작은 편의점 같은 존재라면 리덕스는 대형마트 같은 느낌입니다. 즉 리덕스는 강력한 기능만큼 복잡하고 까다로운 절차를 거쳐야 사용 가능합니다. 하지만 리덕스를 사용하면 통합적인 데이터 관리가 가능하기 때문에 꼭 알고 가야 하는 기능입니다. 그럼 설치부터 ㄱㄱ

 

명령 프롬프트에서 리덕스 관련 라이브러리 설치

> yarn add redux react-redux

 

 첫 시간인 만큼 가볍게 접근해 보겠습니다. 컨텍스트가 공급자(provider)와 소비자(consumer) 개념으로 나뉘었다면 리덕스는 스토어(store), 리듀서(reducer), 액션(action)이 있습니다. 쉽게 설명하자면 스토어는 데이터 저장소이고 리듀서는 데이터 저장 형태이며 액션은 데이터를 저장하는 행위입니다. 그럼 직접 간단한 코딩을 해보겠습니다.

 

// ..\test_project\src\components\CountUpRedux.jsx

import React, { PureComponent } from "react";
import { createStore } from "redux";
import { Provider } from "react-redux";
import Text from "./Text";
import Button from "./Button";

class CountUpRedux extends PureComponent {
  constructor(props) {
    super(props);

    // 리듀서(데이터 저장 형태) 정의
    const reducer = (state, action) => {
      const { type, data } = action;
      // 액션 타입
      switch (type) {
        // 카운트 업
        case "SET_COUNT": {
          return {
            ...state,
            ...data,
          };
        }
        // 리셋 카운트
        case "RESET_COUNT": {
          return {
            ...state,
            ...data,
          };
        }
        // 디폴트 변경 없음
        default:
          return state;
      }
    };

    // 콜백 함수 바인딩
    this.countUp = this.countUp.bind(this);
    this.resetCount = this.resetCount.bind(this);

    // 정의한 리듀서로 스토어 생성
    this.store = createStore(reducer, {
      // 데이터 초기화
      count: 1,
      isTen: false,
      // 콜백 함수 연결
      countUp: this.countUp,
      resetCount: this.resetCount,
    });
  }

  countUp() {
    // 스토어 데이터
    const data = this.store.getState();

    // 숫자 증가
    const countTemp = data.count + 1;
    let isTenTemp = data.isTen;

    // 10이상이면 true
    if (countTemp >= 10) isTenTemp = true;

    // 액션 타입으로 데이터 저장
    this.store.dispatch({
      type: "SET_COUNT",
      data: { count: countTemp, isTen: isTenTemp },
    });

    // 강제 갱신 (state 변경이 없어서)
    this.forceUpdate();
  }

  resetCount() {
    this.store.dispatch({
      type: "RESET_COUNT",
      data: { count: 1, isTen: false },
    });

    this.forceUpdate();
  }

  render() {
    // 프로바이더를 사용하여 자식에게 데이터 전달
    const data = this.store.getState();
    return (
      <Provider store={this.store}>
        <React.Fragment>
          <Text>숫자값 : {data.count}</Text>
          <br />
          <Text>10이상 : {String(data.isTen)}</Text>
          <Button name="countUp" onClick={data.countUp}>
            카운트
          </Button>
          <Button name="resetCount" onClick={data.resetCount}>
            리셋
          </Button>
        </React.Fragment>
      </Provider>
    );
  }
}

export default CountUpRedux;

 

 지난 컨텍스트에서 했던 카운드 업 기능을 그대로 사용했습니다. 비교해 보시면 로직은 변함없고 데이터 사용 방법만 바뀌었습니다. 또한 프로퍼티나 스테이트 기능을 전혀 사용하지 않고 오직 리덕스만 사용해서 구현해 봤습니다.

 

중요한 부분은 생성자에서 createStore()을 하는 곳입니다. 첫 번째 인자는 데이터 저장 형태인 리듀서이고 두 번째 인자는 초기 데이터를 넣습니다. dispatch() 메서드로 액션 타입을 나눠 데이터를 저장합니다.

 

스토리북에서 동작 확인

 

 스토리북에 넣는 코드는 너무 간단해서 생략했습니다. 그냥 <CountUpRedux> 컴포넌트 하나입니다. 생각보다 간단? 하다고 생각할 수 있는데, 사실은 첫 시간이라 모든 것을 하나에 넣어서 그런 것입니다. 앞으로 몇 번에 걸쳐 포스팅을 더 할 예정이니 오늘은 개념만 파악하셔도 충분합니다.

 

마지막으로 중요한 부분을 한번 더 설명하자면, 데이터 저장 액션을 리듀서에 타입 별로 나누고, 형태도 정의한 다음에 스토어 생성, dispatch()로 변경, getState()로 취득입니다.

 

오늘은 여기까지 입니다.

 

지금은 참 쉽죠? 


2020/10/22 - [Web프론트엔드/리액트] - [React] 리덕스(redux) 기능으로 데이터 관리하기 ② 디버깅

댓글