state & props로 데이터를 전달했던 이전의 쇼핑몰 코드를 Redux로 변경하여 연습했다. state & props로 데이터를 전달할때는 전달 흐름이 꼬여서 고치는데 시간을 많이 쏟았는데, redux로 변경하니 편하고 좋았다.
그래도 "react로 사고"한다면 20개가 넘는 state도 redux 없이 관리가 가능하다고 하니 연습차원에서 데이터 흐름을 많이 만들어봐야겠다.
const store = createStore(rootReducer);
rootReducer
// src/reducers/index.js
const rootReducer = combineReducers({
itemReducer,
notificationReducer
});
itemReducer
// src/reducers/itemReducer.js
const itemReducer = (state = initialState, action) => {
// action은 객체 형태이다.
switch (action.type) {
case ADD_TO_CART:
return Object.assign({}, state, {
cartItems: [...state.cartItems, action.payload]
})
// 모든 case 내부에서 return을 하고 있어서 break 필요 없다.
// break;
case REMOVE_FROM_CART:
let currentItem = state.cartItems.filter((el => el.itemId !== action.payload.itemId))
return Object.assign({}, state, {
cartItems: [...currentItem]
})
case SET_QUANTITY:
let idx = state.cartItems.findIndex(el => el.itemId === action.payload.itemId)
let newCart = [...state.cartItems]
newCart.splice(idx, 1, action.payload);
return {
...state,
cartItems: [...newCart]
}
default:
return state;
}
}
export default itemReducer;
// action types
export const ADD_TO_CART = "ADD_TO_CART";
export const REMOVE_FROM_CART = "REMOVE_FROM_CART";
export const SET_QUANTITY = "SET_QUANTITY";
// actions creator functions
export const addToCart = (itemId) => {
return {
type: ADD_TO_CART,
payload: {
quantity: 1,
itemId
}
}
}
export const removeFromCart = (itemId) => {
return {
type: REMOVE_FROM_CART,
payload: {
itemId
}
}
}
export const setQuantity = (itemId, quantity) => {
return {
type: SET_QUANTITY,
payload: {
itemId,
quantity
}
}
}
addToCart
import { useSelector, useDispatch } from 'react-redux';
const state = useSelector(state => state.itemReducer);
const { items, cartItems } = state;
const dispatch = useDispatch();
const handleClick = (item) => {
dispatch(addToCart(item.id))
}
removeFromCart, setQuantity
import { useDispatch, useSelector } from 'react-redux'const;
const state = useSelector(state => state.itemReducer);
const { cartItems, items } = state
dispatch = useDispatch();
const handleDelete = (itemId) => {
setCheckedItems(checkedItems.filter((el) => el !== itemId))
dispatch(removeFromCart(itemId))
}
const handleQuantityChange = (quantity, itemId) => {
dispatch(setQuantity(itemId, quantity))
}
학습자료에서는 순서대로 Redux를 만들라고 했지만, 직접 구현을 해보니 action 객체를 만든 후에 reducer 함수를 만드는 것이 흐름 이해가 잘 되었다.
지금까지 이해한 흐름
action 객체 생성 -> reducer 만들기 -> dispatch로 reducer에 전달인자 주기.
그나저나 이번에 실습한 createStore, legacy_createStore 보다는 Redux Toolkit이 더 권장되는 방식이라고 한다. (Redux Toolkit을 사용하면 전역상태관리를 좀 더 쉽고 효율적으로 할 수 있다.)
그래서 다음 번에는 Redux Toolkit을 이용하여 상태관리를 연습해볼까 한다.