리덕스 모듈이란 위 항목들을 포함하는 파일을 의미한다.
Ducks 구조는 리듀서와 액션 관련 코드들을 하나의 파일에 모두 작성하는 구조이다.
const INCREASE = 'counter/increase';
const DECREASE = 'counter/decrease';
위처럼 접두사를 넣어주는 이유는 다른 모듈과 액션 이름이 중복되는 것을 방지하기 위함이다.
export const increase = () => ({ type: INCREASE });
export const decrease = () => ({ type: DECREASE });
export default function counterReducer(state = initialState, action) {
switch (action.type) {
case INCREASE:
return {
...state,
number: state.number + state.diff,
};
case DECREASE:
return {
...state,
number: state.number - state.diff,
};
default:
return state;
useReducer 에선 일반적으로 default 부분에 error를 발생시켰지만 리덕스에서는 state를 반환하는데 이는 여러개의 서브 리듀서를 루트 리듀서로 합쳐서 하나로 만들기 때문이다. (루트 리듀서 안의 작은 리듀서들은 서브 리듀서라고 부른다.)
아래는 여러개의 서브 리듀서를 하나로 합쳐 root 리듀서를 만드는 과정이다.
import { combineReducers } from "redux";
import counterReducer from "./counter";
import todoReducer from "./todo";
const rootReducer = combineReducers({
counterReducer,
todoReducer,
});
export default rootReducer;
redux에서 combineReducers
를 불러와 하나로 합칠 수 있다.
참고로 modules 내부에 있는 index.js를 불러올 때는 아래처럼 modules/index.js 경로를 생략하고 modules만 불러와도 자동으로 index 파일을 읽는다.
rootReducer from modules
우선 아래와 같이 react에서 redux를 사용하기 위해 react-redux를 설치해야한다.
yarn add react-redux
리덕스에서는 보통 프리젠테이셔널 컴포넌트와 컨테이너 컴포넌트로 나눈다.
프리젠테이셔널 컴포넌트란, 리덕스 스토어에 직접적으로 접근하지 않고 필요한 값 또는 함수를 props로 만 받아와서 사용하는 컴포넌트이다. 보통 components
디렉터리 안에 생성한다.
컨테이너 컴포넌트란, 리덕스 스토어의 상태를 조회하거나, 액션을 디스패치 할 수 있는 컴포넌트를 의미한다. 그리고, HTML 태그들을 사용하지 않고 다른 프리젠테이셔널 컴포넌트들을 불러와서 사용한다.
보통 containers
디렉터리 안에 생성한다.
유지보수가 쉽다.
각 컴포넌트가 자신의 역할이 명확하기 때문에 어떤 에러가 발생했을 시 어떤 컴포넌트를 고쳐야하는 지 확인하기 쉽다.
예) container는 리덕스로부터 데이터를 받고 action을 실행하는 역할만을 전담하고, component는 리덕스의 state가 어떻든 상관하지 않고 그저 사용자와 상호작용한 후 정보를 받아서 Container로 넘겨준다.
성능이 좋아진다.
컴포넌트가 복잡해짐에 따라 여러 개로 나누게 된다면, 업데이트가 컴포넌트 별로 일어나기 때문에 잘게 쪼갤수록 불필요한 컴포넌트의 업데이트를 방지할 수 있다.
예) Container는 앱의 상태가 자주 바뀔수록 그에 따라 업데이트가 일어난다. 그래서 필요없는 부분에 업데이트가 일어나지 않게 하려면 Container과 Component를 구분해주어야 한다. Container가 업데이트되어도 그 아래 Component와 상관이 없다면 업데이트가 일어나지 않는다.
코드가 분리되어 용량이 조금 증가되고 코드의 양이 많아지는 만큼 추적이 어려워질 수 있다. 또한 Container에서 Component로 데이터를 보내는 부분이 중복의 느낌이 있습니다. (props를 전달하는 과정에서 생기는 중복)
참고
https://www.zerocho.com/category/React/post/57e1428c11a9b10015e803aa
https://react.vlpt.us/redux/05-counter.html