# CLAUDE.md ## Commands ```bash npm run dev # 개발 서버 (HMR) npm run build # 프로덕션 빌드 → dist/ npm run preview # 빌드 결과 미리보기 npm run lint # ESLint ``` ## Tech Stack - **React 19** — plain JavaScript (no TypeScript) - **Vite 7** — `@vitejs/plugin-react` (Babel / Fast Refresh) - **React Router v7** - **ESLint** — flat config, `no-unused-vars` ignores `^[A-Z_]` ## Project Purpose Unity 3D 멀티플레이어 게임 "One of the plans" 웹 플랫폼. 유저 인증 → 게임 런처 다운로드 → `a301://` 프로토콜로 런처 실행. ## Project Structure ``` src/ ├── api/ # 백엔드 호출 (client.js: fetch 래퍼 + JWT + 401 처리) ├── context/ # AuthContext — 3파일 분리 (react-refresh 규칙) │ ├── authContextValue.js │ ├── AuthContext.jsx │ └── useAuth.js ├── pages/ # HomePage, LoginPage, RegisterPage, AdminPage └── components/ ├── DownloadSection.jsx # a301:// URI 호출, 미설치 시 launcher.exe 다운로드 ├── AnnouncementBoard.jsx └── admin/ # AnnouncementAdmin, DownloadAdmin, UserAdmin ``` ## Key Patterns - `src/api/client.js` — 모든 API 호출은 이 래퍼를 통해 처리. 401 응답 시 자동으로 localStorage 토큰 삭제 후 `/login` 리다이렉트. - AuthContext는 `react-refresh` 린트 규칙(컴포넌트와 hook 혼재 금지) 때문에 3개 파일로 분리. - 환경변수 `VITE_API_BASE_URL` — 빌드 시 주입. 개발 시 빈 문자열(상대경로 사용). - 게임 이름 표기: **"One of the plans"** (기술 식별자 `a301`, `A301.exe` 등은 변경하지 않음) ## API Base URL 프론트엔드 nginx는 `/api/` 프록시 없음. 런처·백엔드 직접 통신은 `https://a301.api.tolelom.xyz` 사용.