이번 페어 과제는 redux를 이용해 저번에 진행하였던 cmarket의 기능을 구현하는 과제였습니다.
총 구현해야 할 기능은 3가지였습니다.
1. 상품리스트 화면에서 상품 화면아래 "장바구니 담기" 버튼을 클릭했을때 장바구니에 해당 상품이 추가되는 기능
2. 장바구니 화면에서 상품목록 옆에 "삭제"버튼을 클릭시 해당 상품이 리스트에서 삭제되는 기능
3. 장바구니 화면에서 상품목록 옆에 해당 상품의 갯수를 바꿀 때, 장바구니 안의 해당 상품의 수량이 변경되는 기능
action/index.js
에서
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
}
}
}
위의 내용을 추가해 action.payload로 불러와 사용할 값을 보내줍니다.
pages/ItemListContainer.js
에서
const handleClick = (item) => {
if (!cartItems.map((el) => el.itemId).includes(item.id)) {
dispatch(addToCart(item.id));
dispatch(notify(`장바구니에 ${item.name}이(가) 추가되었습니다.`))
}
위의 3번째 줄에 dispatch로 리듀서에 해당 함수와 변수를 보내주게 됩니다.
그리고 reducer/ItemReducer.js
파일에서
case ADD_TO_CART:
return Object.assign({}, state, {
cartItems: [...state.cartItems, action.payload]
});
해당 내용을 추가해주면 기능이 정상적으로 작동합니다.
Object.assign
를 사용해 기존의 상태인 state와 state.cartItems와 dispatch로 입력받은 값(action.payload)을 합쳐서 리턴해주게 됩니다.
pages/ShoppingCart.js
에서
const handleDelete = (itemId) => {
setCheckedItems(checkedItems.filter((el) => el !== itemId))
dispatch(removeFromCart(itemId));
}
해당 내용을 추가해 dispatch로 해당 함수와 변수를 보내준 후,
reducer/ItemReducer.js
파일에서
case REMOVE_FROM_CART:
let curItem = state.cartItems.filter(el => el.itemId !== action.payload.itemId)
return Object.assign({}, state, {
cartItems: curItem
})
해당 내용을 추가해주면 기능이 정상적으로 작동합니다.
cutItem이라는 변수 안에 state.cartitems에 저장된 전체 배열의 값 중 선택해서 지울 아이템만 filter로 지우고 남은 값들만 배열로 저장한 후, 리턴값에 해당 변수를 함께 포함하여 리턴합니다.
pages/ShoppingCart.js
에서
const handleQuantityChange = (quantity, itemId) => {
dispatch(setQuantity(itemId, quantity));
}
해당 내용을 추가해 dispatch로 해당 함수와 변수를 보내준 후,
reducer/ItemReducer.js
파일에서
case SET_QUANTITY:
let idx = state.cartItems.findIndex(el => el.itemId === action.payload.itemId);
let editQuantity = state.cartItems.map(function(el, index) {
if(idx === index){
return {itemId: action.payload.itemId, quantity: action.payload.quantity}
}else{
return el;
}
})
해당 내용을 추가해주면 기능이 정상적으로 작동합니다.
idx라는 변수 안에 수량을 바꿀 상품의 인덱스값이 저장되고,
해당 값을 사용해 장바구니에 저장된 값들을 모두 map으로 순회하며, 조건문을 사용해 해당 값에서만 dispatch로 받아온 아이템의 Id와 quantity값을 직접 입력해 변경해 주었습니다.
이후 해당 변경된 값을 포함해 리턴하여주었습니다.
이후 추가 advanced과제를 익일 도전 할 예정입니다.