ํตํฉ ํ ์คํธ๋?
๋ ๊ฐ ์ด์์ ๋ชจ๋์ด ์ฐ๊ฒฐ๋ ์ํ๋ฅผ ๊ฒ์ฆ. ๋จ์ํ ์คํธ์ ๋นํด ๋ชจํน์ ๋น์ค์ด ์ ๋ค. ๋ชจ๋๋ค์ด ์ํธ ์์ฉํ์ฌ ๋ฐ์ํ๋ ์ํ๋ฅผ ๊ฒ์ฆ. ๊ทธ๋์ ์ค์ ์ฑ์ด ๋์ํ๋ ๋น์ฆ๋์ค ๋ก์ง์ ๊ฐ๊น๊ฒ ๊ธฐ๋ฅ์ ๊ฒ์ฆํ ์ ์๋ค.
ํตํฉ ํ ์คํธ ํญ๋ชฉ
- ํน์ ์ํ๋ฅผ ๊ธฐ์ค์ผ๋ก ๋์ํ๋ ์ปดํฌ๋ํธ ์กฐํฉ
- API์ ํจ๊ป ์ํธ์์ฉ ํ๋ ์ปดํฌ๋ํธ ์กฐํฉ
- ๋จ์ UI ๋ ๋๋ง ๋ฐ ๊ฐ๋จํ ๋ก์ง์ ์คํํ๋ ์ปดํฌ๋ํธ(๋จ์ ํ ์คํธ๋ฅผ ํ์ง ์์๋) ๊ฐ ์ ๋๋ก ๋ ๋๋ง ๋๋์ง ํ๋ฒ์ ๊ฒ์ฆ
์์
์์
์๋ฃ์ ProductList์ ProductCard ์ปดํฌ๋ํธ๋ฅผ ๋ณด์.
const ProductCard = ({
product,
onClickAddCartButton,
onClickPurchaseButton,
}) => {
const navigate = useNavigate();
if (!product) {
return null;
}
const { title, images, price, category, id } = product;
const handleClickItem = () => {
navigate(pathToUrl(pageRoutes.productDetail, { productId: id }));
};
const handleClickAddCartButton = ev => {
onClickAddCartButton(ev, product);
};
const handleClickPurchaseButton = ev => {
onClickPurchaseButton(ev, product);
};
return (.....);
};
ํ๋ก๋ํธ ์นด๋๋ ์์ ์ ํธ์ถํ๋ ํ๋ก๋ํธ๋ฆฌ์คํธ ์ปดํฌ๋ํธ์์ ์ ๋ฌ๋ฐ์ prop๋ค(product ๊ฐ์ฒด, ์ด๋ฒคํธ ํธ๋ค๋ฌ๋ค)์ ๊ทธ๋๋ก ์ฌ์ฉํ๋ค.
- ๋จ์ํ ์คํธ์์๋ ๊ฐ ์ด๋ฒคํธ ํธ๋ค๋ฌ๋ค์ด ์ฌ๋ฐ๋ฅธ ๊ฐ์ ๊ฐ์ง๊ณ ํธ์ถ ๋๋์ง ์ฌ๋ถ๋ง ๊ฒ์ฆ ๊ฐ๋ฅํ๋ค.
- ์ค์ ๋ฒํผ์ ๋๋ ์ ๋์ ๋์์ ๊ฒ์ฆ ๋ถ๊ฐ๋ฅํ๋ค.
- ์ฌ๊ธฐ์ ๋งํ๋ ๋์์ด๋ ์ ๋ง ์ฅ๋ฐ๊ตฌ๋์ ์ซ์๊ฐ ๋์ด๋๋์ง ๋ฑ์ ์๋ฏธ
const ProductList = ({ limit = PRODUCT_PAGE_LIMIT }) => {
...
...
const products =
data?.pages.reduce((acc, cur) => [...acc, ...cur.products], []) ?? [];
const handleClickCart = (ev, product) => {
ev.stopPropagation();
if (isLogin) {
addCartItem(product, user.id, 1);
toast.success(`${product.title} ์ฅ๋ฐ๊ตฌ๋ ์ถ๊ฐ ์๋ฃ!`, { id: TOAST_ID });
} else {
navigate(pageRoutes.login);
}
};
const handleClickPurchase = (ev, product) => {
ev.stopPropagation();
if (isLogin) {
addCartItem(product, user.id, 1);
navigate(pageRoutes.cart);
} else {
navigate(pageRoutes.login);
}
};
return (
<Grid container spacing={1} rowSpacing={1} justifyContent="center">
{products.map((product, index) => (
<ProductCard
key={`${product.id}_${index}`}
product={product}
onClickAddCartButton={handleClickCart}
onClickPurchaseButton={handleClickPurchase}
/>
))}
...
...
);
};
๋จผ์ ProductCard๋ฅผ ๋จ์ํ
์คํธ ํ์ ๋ ๊ฒ์ฆํ ์ ์๋ ํญ๋ชฉ๋ค์ ๋ค์๊ณผ ๊ฐ๋ค :
- prop ๊ธฐ์ค์ผ๋ก ์ ํ ์ ๋ณด๊ฐ(price, name ..) ์ ๋๋ก ๋ ๋๋ง ๋๋์ง
- ์ํ์ ํด๋ฆญ ํ์ ๋(
handleClickItem) navigate ๋ชจํน์ ํตํด ์์ธํ๋ฉด์ผ๋ก ์ด๋ํ๋์ง - ์ฅ๋ฐ๊ตฌ๋, ๊ตฌ๋งค ๋ฒํผ์ ๋๋ ์ ๋ spy ํจ์๋ฅผ ํตํด ๊ฐ ํธ๋ค๋ฌ๊ฐ ํธ์ถ๋๋์ง
- ํธ์ถ์ด ๋๋์ง๋ ๊ฒ์ฆํ ์ ์์ง๋ง ์๋ํ๋์ง ๊ฒ์ฆํ ์ ์๋ค.
๋ฐ๋ฉด ProductList๋ฅผ ํตํฉํ
์คํธ ํ์ ๋ ๊ฒ์ฆํ ์ ์๋ ํญ๋ชฉ๋ค์ ๋ค์๊ณผ ๊ฐ๋ค :
- ์ํ ๋ฆฌ์คํธ ์กฐํ api์ ๋ง๊ฒ ์ํ ์ ๋ณด ๊ฐ ์ ๋๋ก ๋ ๋๋ง ๋๋์ง
- ์ํ์ ํด๋ฆญ ํ์ ๋ navigate ๋ชจํน์ ํตํด ์์ธํ๋ฉด์ผ๋ก ์ด๋ํ๋์ง
- ์ฅ๋ฐ๊ตฌ๋ ํน์ ๊ตฌ๋งค ๋ฒํผ์ ๋๋ ์ ๋ ๋ค์๊ณผ ๊ฐ์ด ์๋ ํ๋์ง
- ๋ก๊ทธ์ธ : ์ํ ์ถ๊ฐ ํ ์ฅ๋ฐ๊ตฌ๋๋ก ์ด๋
- ๋น๋ก๊ทธ์ธ : ๋ก๊ทธ์ธ ํ์ด์ง๋ก ์ด๋
- ์ํ ๋ฆฌ์คํธ๊ฐ ๋ ์๋ ๊ฒฝ์ฐ show more ๋ฒํผ์ด ๋ ธ์ถ๋๊ณ , ์ด๋ฅผ ํตํด ๋ฐ์ดํฐ๋ฅผ ๋ ๊ฐ์ ธ์ฌ ์ ์๋์ง
์์ ๋ ํญ๋ชฉ๋ค์ ๋น๊ตํด๋ณด๋ฉด 1,2,3๋ฒ์ ์ค๋ณต๋๋ค๊ณ ๋ณผ ์ ์๋ค. (ํต1,2,3 ์ด ์ฑ๊ณตํ๋ค๋๊ฒ์ ๋จ1,2,3 ์ด ์ฑ๊ณตํจ์ ํจ์ํ๋ค) ๊ทธ๋์ ํ๋ก๋ํธ ์นด๋์ ๋ํ ๋จ์ํ ์คํธ๋ฅผ ํ์ง ์๊ณ ํ๋ก๋ํธ๋ฆฌ์คํธ์ ํตํฉํ ์คํธ์์ ํ๋ฒ์ ๊ฒ์ฆํ๋๊ฒ์ด ๋ ํจ์จ์ ์ด๋ค.
