[오하영] Sprint6#151
Hidden character warning
Conversation
reach0908
left a comment
There was a problem hiding this comment.
미션하시느라 고생많으셨습니다!
백엔드는 별도의 레포지터리로 옮기시면 좋을 것 같습니다!
추가로 이렇게 폴더를 옮기는 경우 변경사항들이 기록되지 않는 경우가 있는데, 폴더 옮기기만 진행한 후 커밋을 한번하고 그 뒤에 파일들을 수정하시면 파일 diff가 잘 기록됩니다!
모바일에서 상단 헤더때문에 레이아웃이 깨지는 문제가 발생하고 있습니다!
| export const handleError = async (url, options = {}) => { | ||
| try { | ||
| const res = await fetch(url, options); | ||
| if (!res.ok) { | ||
| throw new Error(`HTTP error: ${res.status}`); | ||
| } | ||
| const body = await res.json(); | ||
| return body; | ||
| } catch (e) { | ||
| console.error("Failed to fetch products:", e); | ||
| throw e; | ||
| } | ||
| }; |
There was a problem hiding this comment.
[P1]
공통되는 로직을 분리한 것은 좋았으나 네이밍을 변경하면 좋을 것 같습니다.
해당 로직에서 에러만 핸들링하는 것이 아닌 fetch의 기능도 포함하고 있어 오해할 수도 있을 것 같습니다!
| }; | ||
|
|
||
| return ( | ||
| <form onSubmit={handleAddItem}> |
| <input | ||
| type="text" | ||
| value={name} | ||
| onChange={(e) => setName(e.target.value)} | ||
| placeholder="상품명을 입력해주세요" | ||
| /> |
There was a problem hiding this comment.
[P2]
input 태그의 속성을 활용한 validation 방법에 대해서 알아보시면 좋을 것 같습니다!
| useEffect(() => { | ||
| const updatePageSize = () => { | ||
| if (window.matchMedia("(max-width: 743px)").matches) { | ||
| setPageSize(BEST_PAGE_SIZE.mobile); | ||
| } else if (window.matchMedia("(max-width: 1199px)").matches) { | ||
| setPageSize(BEST_PAGE_SIZE.tablet); | ||
| } else { | ||
| setPageSize(BEST_PAGE_SIZE.desktop); | ||
| } | ||
| }; | ||
|
|
||
| updatePageSize(); | ||
|
|
||
| window.addEventListener("resize", updatePageSize); | ||
| return () => { | ||
| window.removeEventListener("resize", updatePageSize); | ||
| }; | ||
| }, []); |
| {bestItems.map((item) => ( | ||
| <div key={item.id}> | ||
| <img className={styles.img} src={defaultImg} alt={item.name} /> | ||
| <div className={styles.description}> | ||
| <div className={styles.name}>{item.name}</div> | ||
| <div className={styles.price}>{item.price}원</div> | ||
| <div className={styles.favoriteCount}> | ||
| <img src={unheartIcon} alt="좋아요 아이콘" />{" "} | ||
| {item.favoriteCount} | ||
| </div> | ||
| </div> | ||
| </div> | ||
| ))} |
There was a problem hiding this comment.
[P0]
bestItems의 배열의 길이가 0일때의 처리를 해주면 좋을 것 같습니다.
| @@ -0,0 +1,79 @@ | |||
| import { useEffect, useState } from "react"; | |||
| import { getProducts } from "../../api/index"; | |||
| import { PAGE_SIZE, ORDER } from "../../constants"; | |||
| useEffect(() => { | ||
| updatePageSize(); | ||
| fetchSortedData({ page, pageSize, order, keyword }); | ||
|
|
||
| window.addEventListener("resize", updatePageSize); | ||
| return () => { | ||
| window.removeEventListener("resize", updatePageSize); | ||
| }; | ||
| }, [page, pageSize, order, keyword]); | ||
|
|
||
| const onPageChange = (pageNum) => { | ||
| setPage(pageNum); | ||
| fetchSortedData({ page: pageNum, pageSize, order, keyword }); | ||
| }; |
There was a problem hiding this comment.
[P0]
이 부분이 어차피 page가 바뀌면서 useEffect로 인해 fetchSortedData 한번 요청이 될 것 같은데, 그 과정에서 onPageChage 하는 부분에서도 또 fetch를 하고 있어 중복으로 요청이 되지 않는지 확인이 필요합니다!
| @@ -0,0 +1,16 @@ | |||
| export const PAGE_SIZE = { | |||
There was a problem hiding this comment.
[P2]
별도의 파일로 분리 잘하신 것 같습니다. 다만 도메인 단위로 constants/page.constant.js 등과 같이 별도의 파일로 관리해보는 것도 좋을 것 같아요!
backend/server.js
Outdated
|
|
||
| const app = express(); | ||
| app.use(express.json()); | ||
| app.use(cors()); |
There was a problem hiding this comment.
[P0]
이렇게 설정하면 모든 URL에 대해 허용을 해주게 됩니다. 자신이 사용하는 프론트엔드 레포만 허용해줄 수 있도록 설정해주세요!
요구사항
기본
공통프론트엔드 구현 요구사항랜딩 페이지
중고마켓 페이지
상품 등록 페이지
백엔드 구현 요구사항중고마켓
id,name,description,price,tags,createdAt,updatedAt필드를 가집니다.name,description,price,tags를 입력하여 상품을 등록합니다.id,name,description,price,tags,createdAt를 조회합니다.id,name,price,createdAt를 조회합니다.name,description에 포함된 단어로 검색할 수 있습니다..env파일에 환경 변수를 설정해 주세요.심화
프론트엔드 구현 요구사항상품 등록 페이지
주요 변경사항
스크린샷
멘토에게