Skip to content

Conversation

@holdn2
Copy link
Collaborator

@holdn2 holdn2 commented Dec 23, 2025

📌 Related Issues

  • close #

✅ 체크 리스트

  • PR 제목의 형식을 잘 작성했나요? e.g. [Feat/#이슈번호] PR 템플릿 작성
  • 빌드가 성공했나요? (pnpm build)
  • 컨벤션을 지켰나요?
  • 이슈는 등록했나요?
  • 리뷰어와 라벨을 지정했나요?

📄 Tasks

⭐ PR Point (To Reviewer)

  • 아직 리뷰하지 말아주세요. 연동 전입니다ㅠㅠ

📷 Screenshot

🔔 ETC

Summary by CodeRabbit

릴리스 노트

  • 새로운 기능

    • 푸드트럭 정보 수정 기능 추가
    • 잘못된 접근 시 알림 메시지 표시
  • 개선사항

    • 운영 가능 날짜 최대 개수를 2일에서 4일로 증대
    • 폼 검증 및 초기화 로직 개선
  • 기타

    • 전기 필요 여부 및 결제 수단 표시 텍스트 업데이트

✏️ Tip: You can customize this high-level summary in your review settings.

@coderabbitai
Copy link

coderabbitai bot commented Dec 23, 2025

Walkthrough

음식 트럭 폼의 편집 모드를 API 기반으로 구현하는 변경입니다. useFoodTruckForm 훅이 음식 트럭 ID를 받아 상세 정보와 메뉴 데이터를 조회한 후 폼을 초기화하도록 리팩토링되었습니다. 동시에 상수값 업데이트, 스키마 검증 개선, 날짜 형식화 유틸리티 이름 변경이 포함되어 있습니다.

Changes

응집 / 파일 변경 요약
폼 훅 및 로직
src/pages/@owner/food-truck-form/hooks/use-food-truck-form.ts, src/pages/@owner/food-truck-form/FoodTruckForm.tsx
훅 시그니처 변경: prevDatafoodTruckIdNumber. 편집 모드에서 useFoodTruckDetailuseMenusQuery를 통해 데이터 자동 조회 및 폼 초기화. 폼 컴포넌트에 토스트 기반 유효성 검사 추가 (잘못된 ID 시 에러 표시 및 FOOD_TRUCK_MANAGEMENT로 네비게이션). RegionSection에 foodTruckId prop 전달.
폼 스키마 검증
src/pages/@owner/food-truck-form/schemas/food-truck-form.schema.ts
Enum 기반 검증에서 문자열 검증으로 변경: availableQuantity, needElectricity, paymentMethod, menuCategories 필드 업데이트. 관련 Enum import 제거.
폼 상수
src/pages/@owner/food-truck-form/constants/food-truck.ts
FOOD_TRUCK_MAX_LENGTHavailableDates 최대 개수를 2에서 4로 증가.
공유 상수 업데이트
src/shared/constant/need-electricity.ts, src/shared/constant/payment-method.ts
NEED_ELECTRICITY.NOT_REQUIRED: '필요 없음' → '불필요'. PAYMENT_METHOD: 'BANK_TRANSFER' 및 'ANY' 텍스트 값 변경 ('계좌 이체' → '계좌이체', '아무거나' → '무관').
날짜 포맷팅 유틸리티
src/shared/utils/date/date-formatter.ts, src/pages/@owner/estimate/hooks/use-estimate-form.ts
함수명 변경: formatEstimateDatesToAvailableDatesformatStringDatesToAvailableDates. 용도를 더 명확하게 반영하는 이름으로 업데이트.
상세 조회 훅 최적화
src/pages/food-truck-detail/hooks/use-food-truck-detail.ts
쿼리 설정에 enabled: !!foodTruckId 추가하여 유효한 ID가 있을 때만 쿼리 실행.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related issues

Possibly related PRs

Suggested reviewers

  • junghyungo
  • Glyph8
  • hamxxn

Poem

🐰 편집 모드 깔끔하게, 데이터는 술술 흘러가고,
상수들은 옷을 갈아입고, 스키마는 문자로 단정하고,
폼은 ID 받아 반짝반짝, 케이크 구웠어요! 🥕✨

Pre-merge checks and finishing touches

❌ Failed checks (2 warnings, 1 inconclusive)
Check name Status Explanation Resolution
Description check ⚠️ Warning PR 설명이 템플릿 구조를 따르지만, 핵심 섹션들이 미완성 상태입니다. Tasks는 비어있고, PR Point에는 '아직 리뷰하지 말아주세요'라는 메시지만 있으며, 관련 이슈도 지정되지 않았습니다. Tasks 섹션에 작업 내용을 상세히 작성하고, Related Issues에 이슈 번호를 지정하며, PR Point에 리뷰어가 확인해야 할 주요 변경 사항을 구체적으로 설명하세요.
Docstring Coverage ⚠️ Warning Docstring coverage is 50.00% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
Title check ❓ Inconclusive PR 제목이 기능 변경과 관련이 있지만, '리뷰 XXXX'라는 불완전한 텍스트로 인해 주요 변경 사항이 명확하지 않고 마지막 부분이 미완성 상태입니다. PR 제목을 완성하고 명확하게 수정하세요. 예: '[Feature/#199] 푸드트럭 등록/수정 폼 API 연동' 또는 구체적인 작업 내용을 반영한 제목으로 변경하세요.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch feature/#199/food-truck-form-api

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@github-actions
Copy link

빌드 및 린트 결과

모든 검사 통과 🎉

  • 린트 통과 ✅
  • 빌드 성공 🎊

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

🧹 Nitpick comments (2)
src/pages/food-truck-detail/hooks/use-food-truck-detail.ts (1)

13-13: ID 검증 로직을 더 명확하게 개선하세요.

enabled: !!foodTruckId는 0을 허용합니다. 푸드트럭 ID가 1부터 시작한다면 enabled: foodTruckId > 0이 더 명확합니다.

🔎 제안하는 수정
-  enabled: !!foodTruckId,
+  enabled: foodTruckId > 0,
src/pages/@owner/food-truck-form/hooks/use-food-truck-form.ts (1)

56-80: 여러 번의 리렌더링 가능성을 고려해주세요.

foodTruckDetailDatamenuData가 서로 다른 시점에 로드되면 폼이 여러 번 리셋될 수 있습니다. 또한 API 호출 실패 시 에러 처리가 없습니다.

💡 한 번만 리셋하도록 개선하는 제안

두 데이터가 모두 준비된 후 한 번만 리셋하도록 수정할 수 있습니다:

  useEffect(() => {
-    if (foodTruckDetailData) {
+    if (foodTruckDetailData && menuData !== undefined) {
      setIsEdit(true);
      reset({
        // ... 기존 코드
      });
    }
  }, [foodTruckDetailData, menuData, reset]);

또는 두 API 호출이 모두 완료될 때까지 대기하는 로딩 상태를 추가할 수 있습니다.

📜 Review details

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between e57813d and 35eb0e1.

📒 Files selected for processing (9)
  • src/pages/@owner/estimate/hooks/use-estimate-form.ts
  • src/pages/@owner/food-truck-form/FoodTruckForm.tsx
  • src/pages/@owner/food-truck-form/constants/food-truck.ts
  • src/pages/@owner/food-truck-form/hooks/use-food-truck-form.ts
  • src/pages/@owner/food-truck-form/schemas/food-truck-form.schema.ts
  • src/pages/food-truck-detail/hooks/use-food-truck-detail.ts
  • src/shared/constant/need-electricity.ts
  • src/shared/constant/payment-method.ts
  • src/shared/utils/date/date-formatter.ts
🧰 Additional context used
🧬 Code graph analysis (4)
src/pages/@owner/estimate/hooks/use-estimate-form.ts (1)
src/shared/utils/date/date-formatter.ts (1)
  • formatStringDatesToAvailableDates (73-102)
src/pages/@owner/food-truck-form/hooks/use-food-truck-form.ts (4)
src/pages/@owner/food-truck-form/schemas/food-truck-form.schema.ts (1)
  • foodTruckSchema (12-65)
src/pages/food-truck-detail/hooks/use-food-truck-detail.ts (1)
  • useFoodTruckDetail (16-46)
src/pages/@owner/menu/hooks/use-menus-query.ts (1)
  • useMenusQuery (6-25)
src/shared/utils/date/date-formatter.ts (1)
  • formatStringDatesToAvailableDates (73-102)
src/pages/food-truck-detail/hooks/use-food-truck-detail.ts (1)
apis/data-contracts.ts (1)
  • FoodTruckDetailResponse (1427-1517)
src/pages/@owner/food-truck-form/FoodTruckForm.tsx (3)
src/pages/@owner/food-truck-form/hooks/use-food-truck-form.ts (1)
  • useFoodTruckForm (33-103)
src/router/constant/routes.ts (1)
  • ROUTES (1-33)
src/pages/@owner/food-truck-form/@section/region-section/RegionSection.tsx (1)
  • RegionSection (15-46)
🔇 Additional comments (10)
src/pages/@owner/estimate/hooks/use-estimate-form.ts (1)

9-9: LGTM!

함수 이름 변경에 맞춰 import와 사용처가 올바르게 업데이트되었습니다.

Also applies to: 70-72

src/pages/@owner/food-truck-form/FoodTruckForm.tsx (2)

82-82: LGTM!

isEdit 플래그에 따라 제목을 동적으로 표시하는 로직이 적절합니다.


97-97: LGTM!

RegionSectionfoodTruckId를 전달하여 지역 데이터를 로드할 수 있도록 개선되었습니다.

src/pages/@owner/food-truck-form/constants/food-truck.ts (1)

26-26: 백엔드 API와의 호환성 확인됨 - 추가 검증 불필요

변경사항이 다음 항목들과 호환되는 것으로 확인되었습니다:

  • 백엔드 API: apis/data-contracts.ts 라인 269에서 이미 @maxItems 4로 정의되어 있음
  • UI 처리: ActiveDate.tsx, ScheduleCalendar.tsx 등의 컴포넌트가 날짜 범위를 동적으로 처리하므로 4개 제한 수용 가능
  • 폼 검증: food-truck-form.schema.ts에서 FOOD_TRUCK_MAX_LENGTH.availableDates.max를 참조하므로 자동으로 새로운 값 적용됨
  • 에러 메시지: 템플릿 기반이므로 상수값 변경 시 자동 반영됨
src/shared/utils/date/date-formatter.ts (1)

68-75: 함수 이름 변경이 적절하게 완료되었습니다.

formatEstimateDatesToAvailableDatesformatStringDatesToAvailableDates로 변경하여 함수의 범용성을 더 잘 표현하고 있으며, JSDoc도 적절히 업데이트되었습니다. 모든 호출처(use-food-truck-form.ts, use-estimate-form.ts)가 정상적으로 업데이트되었고, 이전 함수명의 남은 참조는 없습니다.

src/pages/@owner/food-truck-form/hooks/use-food-truck-form.ts (5)

1-12: LGTM!

새로운 기능에 필요한 import들이 올바르게 추가되었습니다.


95-103: LGTM!

isEdit 상태를 반환값에 추가하여 컴포넌트에서 편집 모드를 판단할 수 있도록 한 것이 적절합니다.


50-54: 두 훅 모두 이미 유효하지 않은 ID로부터 보호되어 있습니다.

useFoodTruckDetailuseMenusQuery 모두 enabled: !!foodTruckId 조건부 실행 로직을 포함하고 있으므로, 무효한 ID가 전달될 경우 API 호출이 실행되지 않습니다. 현재 구현이 이미 적절한 보호를 제공하고 있어 추가 수정이 필요하지 않습니다.

Likely an incorrect or invalid review comment.


33-48: 문제 없습니다. useFoodTruckDetailuseMenusQuery 훅 모두 enabled: !!foodTruckId 조건을 통해 유효하지 않은 ID로 인한 불필요한 API 호출을 이미 방지하고 있습니다. 새로운 푸드트럭 등록 시 foodTruckIdNumber가 NaN이 되면 쿼리가 실행되지 않으므로 추가 검증이 필요하지 않습니다.


69-69: 이 코드는 타입 오류가 없습니다. FoodTruckDetailResponse.photoUrl은 이미 string[] 배열로 정의되어 있으며, 폼 필드 photoUrlsstring[]을 기대합니다.

Comment on lines +69 to +73
if (!foodTruckId || isNaN(foodTruckIdNumber)) {
toast.error('잘못된 접근입니다.');
navigate(ROUTES.FOOD_TRUCK_MANAGEMENT);
return null;
}
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🔴 Critical

Hooks 규칙 위반 및 로직 흐름 문제를 수정해주세요.

현재 구조는 다음 문제들이 있습니다:

  1. Hooks 규칙 위반: 유효성 검증(line 69-73)이 hooks 호출(line 43-61) 이후에 위치하여, 조건부로 hooks를 건너뛰게 됩니다. Hooks는 항상 동일한 순서로 호출되어야 합니다.

  2. 로직 흐름 문제: navigate()는 비동기적으로 작동하므로 return null 전에 컴포넌트가 잠깐 렌더링될 수 있으며, 토스트 메시지가 표시되지 않을 수 있습니다.

  3. 사용자 경험: 잘못된 접근 시 빈 화면이 깜빡일 수 있습니다.

🔎 제안하는 수정

방법 1: Early return을 hooks 전에 배치

 export default function FoodTruckForm() {
   const { foodTruckId } = useParams();
-  const foodTruckIdNumber = Number(foodTruckId);
-
   const navigate = useNavigate();
   const location = useLocation();
   const toast = useToast();

+  // Hooks 호출 전에 early return
+  if (!foodTruckId || isNaN(Number(foodTruckId))) {
+    useEffect(() => {
+      toast.error('잘못된 접근입니다.');
+      navigate(ROUTES.FOOD_TRUCK_MANAGEMENT);
+    }, [navigate, toast]);
+    return null;
+  }
+
+  const foodTruckIdNumber = Number(foodTruckId);
+
   const { isEdit, methods, reset, isFormValid, handleSubmit } =
     useFoodTruckForm(foodTruckIdNumber);

   // ... rest of hooks

-  if (!foodTruckId || isNaN(foodTruckIdNumber)) {
-    toast.error('잘못된 접근입니다.');
-    navigate(ROUTES.FOOD_TRUCK_MANAGEMENT);
-    return null;
-  }

방법 2: useEffect로 검증 처리 (더 권장)

 export default function FoodTruckForm() {
   const { foodTruckId } = useParams();
   const foodTruckIdNumber = Number(foodTruckId);
   const navigate = useNavigate();
   const location = useLocation();
   const toast = useToast();

+  // 유효성 검증을 useEffect로 처리
+  useEffect(() => {
+    if (!foodTruckId || isNaN(foodTruckIdNumber)) {
+      toast.error('잘못된 접근입니다.');
+      navigate(ROUTES.FOOD_TRUCK_MANAGEMENT);
+    }
+  }, [foodTruckId, foodTruckIdNumber, navigate, toast]);
+
+  // 잘못된 접근인 경우 로딩 상태 표시
+  if (!foodTruckId || isNaN(foodTruckIdNumber)) {
+    return null; // 또는 <LoadingSpinner /> 등
+  }

   const { isEdit, methods, reset, isFormValid, handleSubmit } =
     useFoodTruckForm(foodTruckIdNumber);

   // ... rest of the component

-  if (!foodTruckId || isNaN(foodTruckIdNumber)) {
-    toast.error('잘못된 접근입니다.');
-    navigate(ROUTES.FOOD_TRUCK_MANAGEMENT);
-    return null;
-  }

),
activeTime: foodTruckDetailData.activeTime,
timeDiscussRequired: foodTruckDetailData.timeDiscussRequired,
menus: menuData !== undefined,
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

메뉴 존재 여부 체크 로직을 개선해주세요.

menuData !== undefineduseMenusQuery의 반환값이 존재하는지만 체크합니다. useInfiniteQuerydata.pages 배열을 반환하므로, 실제 메뉴 항목이 있는지 확인하려면 페이지 내용을 체크해야 합니다.

🔎 메뉴 존재 여부를 정확히 체크하는 수정 제안
-        menus: menuData !== undefined,
+        menus: menuData?.pages?.[0]?.content?.length > 0,

또는 더 안전하게:

-        menus: menuData?.pages.some(page => page.content?.length > 0) ?? false,
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
menus: menuData !== undefined,
menus: menuData?.pages?.[0]?.content?.length > 0,
🤖 Prompt for AI Agents
In src/pages/@owner/food-truck-form/hooks/use-food-truck-form.ts around line 77,
the current menus check uses `menuData !== undefined`, which only verifies the
query returned something but not whether any menu items exist; update it to
inspect `menuData.pages` (e.g., check `menuData?.pages?.some(page => page.items
&& page.items.length > 0)` or `menuData?.pages?.flatMap(p => p.items ??
[]).length > 0`) so the flag truly reflects presence of menu entries and safely
handles undefined/null pages/items.

Comment on lines +34 to +37
availableQuantity: z.string(),
needElectricity: z.string(),
paymentMethod: z.string(),
menuCategories: z.array(z.string()),
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

타입 안정성 손실을 해결해주세요.

availableQuantity, needElectricity, paymentMethod, menuCategoriesz.nativeEnum()에서 z.string()으로 변경되어 다음 문제가 발생합니다:

  1. 컴파일 타임 타입 체크 손실: 잘못된 값이 런타임까지 발견되지 않음
  2. 허용값 검증 없음: 오타나 잘못된 문자열도 통과
  3. API 계약 불일치 가능성: 백엔드가 예상하지 못한 값 수신 가능

의도적인 변경이라면 다음 중 하나를 권장합니다:

  • z.enum([...]) 사용하여 허용값 명시
  • .refine() 추가로 런타임 검증
  • 백엔드 스키마와 동기화된 공유 타입 정의
🔎 제안하는 개선안 (예시: needElectricity)
+import { NEED_ELECTRICITY } from '@shared/constant/need-electricity';
+
+const needElectricityValues = Object.values(NEED_ELECTRICITY) as [string, ...string[]];
+
 export const foodTruckSchema = z.object({
   // ... other fields
-  needElectricity: z.string(),
+  needElectricity: z.enum(needElectricityValues, {
+    error: () => ({ code: 'custom', message: '올바른 전기 사용 옵션을 선택해주세요.' }),
+  }),

다른 필드들도 유사하게 처리할 수 있습니다.

Committable suggestion skipped: line range outside the PR's diff.

export const NEED_ELECTRICITY = {
REQUIRED: '필요',
NOT_REQUIRED: '필요 없음',
NOT_REQUIRED: '불필요',
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Search for needElectricity usage across the codebase
rg -nP --type=ts --type=tsx -C3 'needElectricity|NEED_ELECTRICITY|need-electricity' -g '!node_modules'

Repository: CHA-CALL/ChaCall-FE

Length of output: 90


🏁 Script executed:

#!/bin/bash
# Search for needElectricity usage across the codebase
# Using glob pattern to include .ts and .tsx files
rg 'needElectricity|NEED_ELECTRICITY|need-electricity' -g '*.ts' -g '*.tsx' -C3

Repository: CHA-CALL/ChaCall-FE

Length of output: 23723


Zod 스키마에서 needElectricity 유효성 검증 누락

food-truck-form.schema.ts에서 needElectricityz.string()으로 정의되어 있어 허용되는 값에 대한 검증이 없습니다. 백엔드 API는 "필요" | "불필요" | "논의 필요" 중 하나만 받아들이므로, 다음과 같이 수정이 필요합니다:

needElectricity: z.enum(['필요', '불필요', '논의 필요'])

또한 예상과 다르게 src/pages/@owner/estimate/@section/basic-info-section/NeedElectricity.tsx에서는 같은 필드가 boolean 타입으로 처리되고 있습니다. 데이터 타입 일관성을 확인해주세요.

🤖 Prompt for AI Agents
src/shared/constant/need-electricity.ts (around line 3) and related files: the
current constant and form/schema usage are inconsistent with the backend enum;
update food-truck-form.schema.ts to validate needElectricity as
z.enum(['필요','불필요','논의 필요']) instead of z.string(), ensure
src/pages/@owner/estimate/@section/basic-info-section/NeedElectricity.tsx stops
treating the field as boolean and instead reads/writes one of the three string
values, and sync the constant file to export exactly those three string values
so all places use the same type/labels.

Comment on lines +3 to +4
BANK_TRANSFER: '계좌이체',
ANY: '무관',
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Find usages of paymentMethod and PAYMENT_METHOD across the codebase
rg -nP --type=ts --type=tsx -C3 'paymentMethod|PAYMENT_METHOD' -g '!node_modules'

Repository: CHA-CALL/ChaCall-FE

Length of output: 90


🏁 Script executed:

#!/bin/bash
# Search for paymentMethod and PAYMENT_METHOD usage without tsx type
rg -nP 'paymentMethod|PAYMENT_METHOD' -C3 -g '!node_modules'

Repository: CHA-CALL/ChaCall-FE

Length of output: 16300


🏁 Script executed:

#!/bin/bash
# Search for old payment method values that may have changed
rg '계좌 이체|아무거나' -g '!node_modules'

Repository: CHA-CALL/ChaCall-FE

Length of output: 45


🏁 Script executed:

#!/bin/bash
# Read the food-truck-form.schema.ts file
head -100 src/pages/@owner/food-truck-form/schemas/food-truck-form.schema.ts

Repository: CHA-CALL/ChaCall-FE

Length of output: 2146


🏁 Script executed:

#!/bin/bash
# Search for any hardcoded payment method comparisons or mappings
rg 'BANK_TRANSFER|CARD|ANY' -C2 src/shared/constant/payment-method.ts

Repository: CHA-CALL/ChaCall-FE

Length of output: 159


기존 데이터와의 호환성을 확인해주세요.

BANK_TRANSFERANY의 문자열 값이 변경되었습니다:

  • '계좌 이체' → '계좌이체' (공백 제거)
  • '아무거나' → '무관' (더 공식적인 표현)

백엔드 API 계약서에는 이미 새로운 값('무관', '계좌이체', '카드')이 정의되어 있어 새 값을 수신하는 데는 문제가 없습니다. 그러나 데이터베이스에 존재하는 기존 푸드트럭 데이터가 여전히 이전 문자열 값을 가지고 있을 수 있으므로 다음을 확인해주세요:

  • 기존 데이터를 조회할 때 이전 값이 반환되는 경우 UI에서 제대로 처리되는지
  • 기존 푸드트럭 수정 시 백엔드에서 반환된 이전 값이 폼에 올바르게 로드되는지
  • 필요한 경우 데이터 마이그레이션 계획

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants