원래 weinvite는 모바일 청첩장만 만들어주는 서비스였다. 오늘은 여기에
돌잔치 초대장 카테고리를 새로 얹는 작업을 했다. 단순히 폼 하나 더
만드는 걸로 끝나지 않고, 라우팅 구조 개편 · 관리자 대시보드 · D1 마이그레이션 ·
운영 중이던 버그 수정까지 하루 만에 꽤 많은 일이 있었다. 기록해둔다.
청첩장을 만든 고객이 나중에 아이를 낳으면 돌잔치도 우리 서비스로 다시
찾아오게 만들고 싶었다. 그러려면 "청첩장 전용 사이트"가 아니라 "모바일
초대장 플랫폼"으로 방향을 넓혀야 했고, 첫 확장 대상으로 돌잔치 초대장을
골랐다.
가장 먼저 부딪힌 문제는 이거였다. 청첩장 커버 디자인이 34종이나 있는데,
전부 groom.name/bride.name을 하드코딩해서 렌더링하고 있었다. 게다가
5개 언어 i18n 스키마, wedding-admin의 D1 스키마에도 신랑/신부 개념이
깊게 박혀 있었다.
여기서 전면 리팩터(필드명 전부 중립화)로 가면 기존 청첩장 상품 전체가
회귀 위험에 노출된다. 그래서 택한 방향은:
WeddingContext + 34개 커버는 그대로 유지 (한 줄도 안 건드림)FirstBirthdayContext 신규 생성SharedInvitationContext라는 최소 공통 필드 컨텍스트로이렇게 하면 "새 기능 추가"가 "기존 기능 수정"이 되지 않는다. 대신 대가는
있다 — 완전히 새로운 타입/컨텍스트/섹션 컴포넌트를 병행해서 만들어야 해서
작업량 자체는 늘어난다.
FirstBirthdayConfig, 아기/보호자 정보 타입/ 진입 시 청첩장/돌잔치 중 고르는 카테고리 선택 화면 신규category 필드 추가, 운영 DB에 마이그레이션1. tsc 검증이 사실 아무것도 안 하고 있었다
세션 내내 npx tsc --noEmit -p .로 타입 체크를 돌리고 "클린"이라고
확인했는데, 나중에 알고 보니 이 프로젝트의 tsconfig.json은 references만
있는 솔루션 파일이라 이 명령으로는 실질적으로 아무것도 체크가 안 되고
있었다. 진짜 빌드(tsc -b && vite build)를 돌려보고서야 실제 타입 에러
2건을 발견했다. 이후로는 항상 실제 빌드 명령으로 검증하기로 했다.
2. 리팩터 과정에서 생긴 사진 탭 크래시 — 그리고 이미 배포돼 있었다
공용 컴포넌트들을 SharedInvitationContext를 구독하도록 옮기면서, 정작
편집 폼(왼쪽 패널)에는 그 Provider를 안 씌워놨다는 걸 나중에 발견했다.
결과: 사진 탭에 들어가면 즉시 크래시. 문제는 이게 돌잔치뿐 아니라
이미 운영 중이던 청첩장 에디터에도 동일하게 적용되고 있었다는 것.
새 기능을 얹다가 기존 기능을 몰래 부순 전형적인 케이스였다.
다행히 바로 발견해서 수정했다.