React-Redux Process정리

생강🖤·2021년 6월 6일
0
출처: https://velog.io/@jeffyoun/React-Redux-%ED%94%84%EB%A1%9C%EC%84%B8%EC%8A%A4-%EC%A0%95%EB%A6%AC

Reducer함수 만들기

State와 정의한 Action Type으로 Reducer함수를 만들면 된다.
이때 Reducer는 꼭 순수 함수로 만들어야 한다.
아래 4가지 조건을 만족하면 된다.

  1. Reducer함수는 이전상태와 액션객체를 파라미터로 받는다.
  2. 파라미터 값 외에는 의존하면 안된다.
  3. 이전 상태는 절대 건들이지 않고, 변화를 준 새로운 상태 객체를 만들어 반환한다.
  4. 똑같은 파라미터로 호출된 리듀서 함수는 언제나 똑같은 결과 값을 반환해야한다.
function counter(state = initialState, action) {
  switch (action.type) {
    case INCREASE : 
      return {
      	number: state.number +1
      };
    case DECREASE : 
      return {
      	number: state.number -1 
      };
    default : 
      return state;
  }

}
export default counter;

Action type에 따라 state를 변형한 새로운 state를 반환해주면 된다.
절대로 기존 state수정해서는 안됨.

createAction메소드를 사용해 action타입을 반환하는 함수를 만들어준다.

export const increase = createAction(INCREASE);
export const decrease = createAction(DECREASE);
//만약 파라미터를 전달해줘야 한다면 payload를 사용하면 됨.
export const changeInput = createAction(CHANGE_INPUT, input => input);

코드가 길어질때
redux-actions라이브러리를 사용해 switch-case에서 벗어 날 수 있다.

const counter = handleActions (
  {
  	[INCREASE] : (state,action) => (
      {
      	number:state.number +1
      }
    ),
    [DECREASE] : (state,action)=>(
      {
    	number: state.number -1
      }
    ),
    initialState
  
  }

);

createAction에서 payload를 넣어줬다면?

const counter = handleActions (
  {
  	[INCREASE] : (state,action) => (
      {
      	number:state.number +1
      }
    ),
    [DECREASE] : (state,action)=>(
      {
    	number: state.number -1
      }
    ),
    
    [CHANGE_INPUT] : (state,action) => (
      {
      	...state,
        input : action.payload
      }
    )
    
    initialState
  
  }

);

위와 같이 작성하면 payload에 어떤 값을 넣었는지 헷갈리므로

handleActions (
  {
  	[CHANGE_INPUT] : (state,{payload:input})=>(
      {
      	...state,
        input: input
      }
    )
  },
  initialState

);

이런식으로 작성하면 가독성이 좋아진다.

ReduxStore에는 하나의 Reducer만 연결되어야 하므로 reducer를 통합해야한다.
redux는 combineReducers 라는 함수를 사용한다.

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

const rootReducer = combineReducers({
	counter
});

export default rootReducer;

combineReducers메소드 안에 객체 형태로 우리가 만든 Reducer를 넣어주면 됨.

const rootReducer = combineReducers ({
	counter1,
  	counter2,
  	counter3
});

Hook을 이용해 Redux이용하기

useSelector사용

useSelector를 이용하면 connect 함수 없이 redux를 조회할 수 있다.

const result = useSelector(상태 선택 함수);
import {useSelector} from 'react-redux';
const CounterContainer = ()=>{
	const counterNum = useSelector(state=> state.counter.number)
    return (
    	<Counter number = {counterNume}/>
    );
};

useDispatch를 사용해서 action dispatch하기

const dispatch = useDispatch();

를 이용해 dispatch를 얻은 후에 modules에서 얻은 함수를 넣어준다.

import {useSelector} from 'react-redux';
const CounterContainer = ()=>{
	const counterNum = useSelector(state=> state.counter.number);
    const dispatch = useDispatch();
    return (
    	<Counter 
      		number = {counterNume}
			onIncrease = {()=>dispatch(increase())}
            onDecrease = {()}
		/>
    );
};

이렇게 작성하면 숫자가 바뀔때마다 컴포넌트가 리렌더링 됨
-> 매번 함수를 새로 만드므로 useCallback으로 감싸준다.

import React, {useCallback} from 'react';
const CounterContainer = () => {
	const CounterNum = useSelector(state=>state.counter.number);
  	const dispatch = useDispatch();
  	const onIncrease = useCallback(()=>dispatch(increase(),[dispatch]));
  	const onDecrease = useCallback(()=>dispatch(decrease(),[dispatch]));
  
  return (
  	<Counter
    	number = {counterNum}
		onIncrese = {onIncrease}
		onDerease = {onDecrease}
    />
  );

};
profile
Slow but steady

0개의 댓글