refactor: 백엔드 배포 환경 파일 통합#120
Conversation
api-server/.env.{env} + ai-server/.{env}.env 2개 파일을
루트 .env.backend.{env} 1개로 통합하여 관리 포인트를 줄임.
- .env.backend.example 추가 (통합 템플릿)
- docker-compose 3개 (dev/staging/prod) env_file 경로 통합
- deploy-backend.sh env 파일 체크 단순화
- 충돌 키 LOG_FORMAT은 compose environment에서 서비스별 오버라이드
Closes #118
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
There was a problem hiding this comment.
Cursor Bugbot has reviewed your changes and found 2 potential issues.
❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.
Comment @cursor review or bugbot run to trigger another review on this PR
Reviewed by Cursor Bugbot for commit 6edc54c. Configure here.
| networks: | ||
| - decoded-backend-prod | ||
| env_file: | ||
| - ../../../ai-server/.prod.env |
There was a problem hiding this comment.
Stale env file path in Meilisearch error message
Medium Severity
The MEILISEARCH_MASTER_KEY required-variable error message on line 86 still references the old path packages/api-server/.env.prod, but this PR moved the env file to .env.backend.prod at the repo root. The comment at line 4 of the same file was correctly updated to .env.backend.prod, so this is an inconsistent omission. When MEILISEARCH_MASTER_KEY is missing in prod, the error will direct the operator to a file that no longer exists.
Reviewed by Cursor Bugbot for commit 6edc54c. Configure here.
| environment: | ||
| PORT: "8080" | ||
| HOST: "0.0.0.0" | ||
| LOG_FORMAT: text |
There was a problem hiding this comment.
Dev compose missing ENV override for api service
Medium Severity
The dev compose api service environment block doesn't override ENV, unlike staging (ENV: staging) and prod (ENV: production). Previously this was safe because the dev-specific env file had the correct value. Now the unified env file template sets ENV=production, so a dev api container created from a copy of .env.backend.example would run with ENV=production. The Rust config uses ENV to determine behavior like default log format and the reported environment mode.
Reviewed by Cursor Bugbot for commit 6edc54c. Configure here.
* docs(git): dev→main 브랜치 워크플로우 정립 (#127) (#128) * fix(web): solution 이미지 미표시 수정 (#97) (#98) * fix(web): use Supabase direct query for solutions instead of Rust proxy - Replace listSolutions (Orval REST → Rust backend) with direct Supabase query in useAllSolutionsForSpots hook - Make API_BASE_URL optional in server-env.ts to prevent module crash when Rust backend is not configured Fixes #97 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(web): enrich hero posts with spots/solutions data Hero posts were created with items: [] since the Supabase fallback was added. Now fetches spots+solutions for hero posts server-side so item overlay markers appear when a hero card is focused. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(web): Korean search fallback + published filter in search (#102) - Trigger Supabase fallback when backend returns empty results for non-empty query (enables synonym expansion for Korean→English) - Add post_magazines inner join + created_with_solutions filter to search fallback to match browse mode behavior Fixes #99 Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * docs(git): dev→main 브랜치 워크플로우 정립 (#127) - GIT-WORKFLOW.md에 브랜치 전략 섹션 추가 (feature→dev→main) - 긴급 hotfix 예외 플로우 문서화 - CLAUDE.md git workflow 요약 업데이트 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * refactor: 백엔드 배포 환경 파일을 단일 .env.backend.{env}로 통합 (#120) api-server/.env.{env} + ai-server/.{env}.env 2개 파일을 루트 .env.backend.{env} 1개로 통합하여 관리 포인트를 줄임. - .env.backend.example 추가 (통합 템플릿) - docker-compose 3개 (dev/staging/prod) env_file 경로 통합 - deploy-backend.sh env 파일 체크 단순화 - 충돌 키 LOG_FORMAT은 compose environment에서 서비스별 오버라이드 Closes #118 Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: env compose hotfix (Meilisearch 경로 + dev ENV) (#154) * fix: Meilisearch 에러 메시지 경로 수정 + dev compose ENV 오버라이드 추가 - docker-compose.prod.yml: MEILISEARCH_MASTER_KEY 에러 메시지에서 옛 경로(packages/api-server/.env.prod) → .env.backend.prod로 수정 - docker-compose.yml: dev api 서비스에 ENV=development 명시하여 .env.backend.example 복사 시 production 모드로 뜨는 문제 방지 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: staging Meilisearch MEILI_ENV를 production으로 변경 staging에서 MEILI_ENV=development로 되어있던 것을 production으로 수정. Meilisearch는 development/production 두 모드만 지원. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(ci): 백엔드 CD 파이프라인 — self-hosted runner 자동 배포 (#155) main 머지 시 Mac Mini self-hosted runner에서 자동 배포: - path filter: api-server, ai-server, deploy script 변경 시 트리거 - workflow_dispatch로 수동 배포 지원 - 롤백: 빌드 전 :prev 태깅, 실패 시 자동 복원 - health check: api(:8080) + ai(:10000) 최대 5분 대기 - Telegram 알림 (성공/실패) Closes #119 Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ci): CD workflow에서 .env.backend.prod 복사 스텝 추가 (#156) runner 작업 디렉토리에 env 파일이 없어 배포 실패. Mac Mini의 고정 경로에서 checkout 디렉토리로 복사. Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ci): ai health check를 docker exec로 변경 (#157) ai 컨테이너는 포트 10000을 호스트에 publish하지 않아 호스트에서 curl이 실패함. docker exec로 컨테이너 내부에서 체크. Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(api-server): Phase 2 백엔드 API 추가 (B1+B2) (#161) * refactor(web): Phase 1 — 클라이언트 Supabase 직접 호출을 백엔드 API로 전환 - authStore.ts: .from("users") select/update → getMyProfile()/updateMyProfile() - useImages.ts: Supabase 직접 쿼리 + fallback 제거 → listPosts() REST API - usePosts.ts: fetchPostWithSpotsAndSolutions → getPost() REST API - useSolutions.ts: fetchSolutionsFromSupabase fallback → listSolutions() REST API Part of #158 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * chore(web): 미사용 Supabase 파일 삭제 - lib/supabase/storage.ts — 정의만 있고 어디서도 import 안 됨 - lib/supabase/queries/debug/posts.ts — 개발용, production 미사용 Part of #158 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(api-server): UserResponse에 ink_credits/style_dna 추가 + social accounts 엔드포인트 B1: users 엔티티와 UserResponse에 ink_credits, style_dna 필드 추가 B2: GET /users/me/social-accounts 엔드포인트 신규 추가 - user_social_accounts 엔티티 추가 - SocialAccountResponse DTO - 서비스 + 핸들러 + OpenAPI 등록 Part of #160 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(api-server): B3 user stats 실제 구현 + B5 트렌딩 아티스트 엔드포인트 B3: GET /users/me/stats — stub(0) → 실제 posts/comments/likes count SQL 쿼리 B5: GET /rankings/artists — 트렌딩 아티스트 서버 사이드 SQL 집계 - period: weekly/monthly/all_time - limit: 최대 50 - artist_name별 post_count + 대표 이미지 Part of #160 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(api-server): B6 유저 Spots + B7 유저 Solutions 엔드포인트 추가 - GET /users/me/spots — 유저의 Spot 목록 (post image_url 포함, 페이지네이션) - GET /users/me/solutions — 유저의 Solution 목록 (active만, 페이지네이션) - UserSpotItem, UserSolutionItem DTO 추가 - OpenAPI 등록 Part of #160 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * test(web): Supabase→API 마이그레이션 E2E 테스트 추가 - 메인 피드 로딩 확인 - Explore 무한스크롤 확인 - 포스트 상세 페이지 확인 - 프로필 페이지 확인 - 백엔드 API health 확인 Part of #158 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * test(web): E2E 테스트 수정 — 비인증 환경 대응 + dotenv 로딩 - playwright.config.ts: dotenv 로딩 + api-migration을 chromium-no-auth에서 실행 - api-migration.spec.ts: 비인증 환경에 맞게 테스트 재작성 - 4/4 테스트 통과 확인 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * refactor(web): 클라이언트 Supabase 직접 호출 제거 (Phase 1+3) (#159) * refactor(web): Phase 1 — 클라이언트 Supabase 직접 호출을 백엔드 API로 전환 - authStore.ts: .from("users") select/update → getMyProfile()/updateMyProfile() - useImages.ts: Supabase 직접 쿼리 + fallback 제거 → listPosts() REST API - usePosts.ts: fetchPostWithSpotsAndSolutions → getPost() REST API - useSolutions.ts: fetchSolutionsFromSupabase fallback → listSolutions() REST API Part of #158 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * chore(web): 미사용 Supabase 파일 삭제 - lib/supabase/storage.ts — 정의만 있고 어디서도 import 안 됨 - lib/supabase/queries/debug/posts.ts — 개발용, production 미사용 Part of #158 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * docs: CLAUDE.md에 just hook 초기 설정 안내 추가 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * style: cargo fmt 적용 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * test(web): E2E 테스트 커버리지 확대 + pre-push 게이트 (#168) 핵심 사용자 플로우 E2E 테스트 12개 추가 (소비·생성·참여). API mock 헬퍼, Playwright config 정리, pre-push E2E 게이트, 테스트 문서 작성. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(web): ESLint + Prettier 에러 일괄 수정 기존 코드의 prettier formatting, no-explicit-any, no-empty, no-html-link-for-pages 에러 수정. pre-push hook 통과를 위해 필요. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(web): TypeScript 에러 수정 (debug/posts stub + image dimensions 타입) - debug/posts.ts 클라이언트 쿼리 파일 생성 (기존 import 에러) - image_width/image_height 타입 assertion 추가 (generated 타입 미반영) Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Kiyori <113906780+thxforall@users.noreply.github.com> Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* docs(git): dev→main 브랜치 워크플로우 정립 (#127) (#128) * fix(web): solution 이미지 미표시 수정 (#97) (#98) * fix(web): use Supabase direct query for solutions instead of Rust proxy - Replace listSolutions (Orval REST → Rust backend) with direct Supabase query in useAllSolutionsForSpots hook - Make API_BASE_URL optional in server-env.ts to prevent module crash when Rust backend is not configured Fixes #97 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(web): enrich hero posts with spots/solutions data Hero posts were created with items: [] since the Supabase fallback was added. Now fetches spots+solutions for hero posts server-side so item overlay markers appear when a hero card is focused. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(web): Korean search fallback + published filter in search (#102) - Trigger Supabase fallback when backend returns empty results for non-empty query (enables synonym expansion for Korean→English) - Add post_magazines inner join + created_with_solutions filter to search fallback to match browse mode behavior Fixes #99 Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * docs(git): dev→main 브랜치 워크플로우 정립 (#127) - GIT-WORKFLOW.md에 브랜치 전략 섹션 추가 (feature→dev→main) - 긴급 hotfix 예외 플로우 문서화 - CLAUDE.md git workflow 요약 업데이트 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * refactor: 백엔드 배포 환경 파일을 단일 .env.backend.{env}로 통합 (#120) api-server/.env.{env} + ai-server/.{env}.env 2개 파일을 루트 .env.backend.{env} 1개로 통합하여 관리 포인트를 줄임. - .env.backend.example 추가 (통합 템플릿) - docker-compose 3개 (dev/staging/prod) env_file 경로 통합 - deploy-backend.sh env 파일 체크 단순화 - 충돌 키 LOG_FORMAT은 compose environment에서 서비스별 오버라이드 Closes #118 Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: env compose hotfix (Meilisearch 경로 + dev ENV) (#154) * fix: Meilisearch 에러 메시지 경로 수정 + dev compose ENV 오버라이드 추가 - docker-compose.prod.yml: MEILISEARCH_MASTER_KEY 에러 메시지에서 옛 경로(packages/api-server/.env.prod) → .env.backend.prod로 수정 - docker-compose.yml: dev api 서비스에 ENV=development 명시하여 .env.backend.example 복사 시 production 모드로 뜨는 문제 방지 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: staging Meilisearch MEILI_ENV를 production으로 변경 staging에서 MEILI_ENV=development로 되어있던 것을 production으로 수정. Meilisearch는 development/production 두 모드만 지원. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(ci): 백엔드 CD 파이프라인 — self-hosted runner 자동 배포 (#155) main 머지 시 Mac Mini self-hosted runner에서 자동 배포: - path filter: api-server, ai-server, deploy script 변경 시 트리거 - workflow_dispatch로 수동 배포 지원 - 롤백: 빌드 전 :prev 태깅, 실패 시 자동 복원 - health check: api(:8080) + ai(:10000) 최대 5분 대기 - Telegram 알림 (성공/실패) Closes #119 Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ci): CD workflow에서 .env.backend.prod 복사 스텝 추가 (#156) runner 작업 디렉토리에 env 파일이 없어 배포 실패. Mac Mini의 고정 경로에서 checkout 디렉토리로 복사. Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ci): ai health check를 docker exec로 변경 (#157) ai 컨테이너는 포트 10000을 호스트에 publish하지 않아 호스트에서 curl이 실패함. docker exec로 컨테이너 내부에서 체크. Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * test(api): 백엔드 테스트 커버리지 10% → 65.64% 확대 - 985개 lib 테스트 (기존 378 → +607개) - tarpaulin 기준 65% 설정 (scripts/pre-push.sh) - SeaORM `mock` feature 활성화 + `AppState.db`를 `Arc<DatabaseConnection>`으로 전환 - 모든 `&state.db` → `state.db.as_ref()` 일괄 적용 (mock feature 호환) - 테스트 인프라 확장: `src/tests/fixtures.rs` (엔티티 팩토리), 확장된 `helpers.rs` - 도메인/서비스/핸들러/배치/미들웨어 전반에 MockDatabase 기반 단위 테스트 추가 - architecture::migration_no_duplicate_sequence: 기존 merge된 중복 prefix 허용 (KNOWN_DUPLICATES) - check-migration-sync.sh: 6자리 순번 없는 레거시 파일명도 수용하도록 regex 완화 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Kiyori <113906780+thxforall@users.noreply.github.com> Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>


Summary
.env.backend.{env}1개로 통합deploy-backend.shenv 체크 단순화LOG_FORMAT은 composeenvironment에서 서비스별 오버라이드 (api=text, ai=json)Test plan
docker compose config --services3개 환경 모두 정상 확인bash scripts/deploy-backend.sh prod up --build실행 검증Closes #118
🤖 Generated with Claude Code
Note
Medium Risk
Medium risk because it changes how dev/staging/prod Docker Compose loads environment variables; misnamed/missing keys or wrong paths could break deployments or alter runtime configuration.
Overview
Introduces a single unified backend env template (
.env.backend.example) and switches the Docker stack (dev/staging/prod compose files) to load env from repo-root.env.backend.{env}instead of separate api/ai env files.Updates
deploy-backend.shand the stack README to use the unified env file, simplifies env-file existence checks, and setsLOG_FORMATper-service via compose overrides (api=text,ai=json).Reviewed by Cursor Bugbot for commit 6edc54c. Configure here.