From 6ec083787e995b1ea7bc66c955668c4a13c63612 Mon Sep 17 00:00:00 2001 From: joungmin Date: Fri, 27 Feb 2026 19:22:03 +0900 Subject: [PATCH] docs: expand CLAUDE.md with team workflow and role guides - Add issue-to-code workflow (branch naming, commit message format) - Add code quality standards and PR rules with template - Add test strategy (pyramid, tools, naming conventions) - Add Jenkins CI pipeline example with AI code review stage - Add role-specific guides (PM, Planner, Developer, QA) - Add common workflow diagram and automation prompts - Add Makefile targets (start-issue, pr-ready, draft-pr) Co-Authored-By: Claude Sonnet 4.6 --- CLAUDE.md | 307 ++++++++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 300 insertions(+), 7 deletions(-) diff --git a/CLAUDE.md b/CLAUDE.md index d147fc4..cb322df 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -19,8 +19,29 @@ ## 디렉터리 구조 +### 프로젝트 저장 위치 + +모든 개발 프로젝트는 **건별로** 아래 경로에 저장합니다. + ``` -. +/Users/joungmin/workspaces/ +├── {프로젝트명-A}/ ← 프로젝트 단위로 디렉터리 생성 +├── {프로젝트명-B}/ +└── ... +``` + +> 새 프로젝트 시작 시: +> ```bash +> cd /Users/joungmin/workspaces +> git clone https://gitea.cloud-handson.com/{org}/{repo} +> # 또는 +> mkdir {프로젝트명} && cd {프로젝트명} +> ``` + +### 프로젝트 내부 구조 (표준) + +``` +/Users/joungmin/workspaces/{프로젝트명}/ ├── backend/ │ ├── api/ # FastAPI 라우터 (엔드포인트 정의) │ ├── models/ # SQLAlchemy DB 모델 @@ -139,6 +160,254 @@ API 호출 대신 MCP 툴을 우선 사용하세요. - 테스트 커버리지 목표: **unit 80%+**, integration 60%+ - PR 머지 전 최소 1명의 코드 리뷰 승인 필요 +### 이슈 → 코드 워크플로우 +1. 작업 시작 시 반드시 Redmine 이슈 번호 확인 +2. 브랜치명 형식: `feature/RM-{이슈번호}-{간단설명}` + 예: `feature/RM-342-user-auth-refactor` +3. 커밋 메시지: `RM-{번호}: {Conventional Commit 메시지}` + 예: `RM-342: feat: add JWT refresh token logic` + +### 코드 품질 기준 +- 새 함수는 반드시 docstring + type hints +- 비즈니스 로직에 주석 필수 +- 복잡도(cyclomatic complexity) 10 이하 유지 +- 함수 길이 50줄 이하 권장 + +### PR 규칙 +- PR 제목: `[RM-{번호}] {작업 내용}` +- 최소 1명 리뷰어 승인 필요 +- Jenkins CI 통과 후 머지 가능 + +### PR 본문 템플릿 +``` +## 변경 사항 +- + +## 테스트 방법 +- + +## 스크린샷 (UI 변경 시) + +## 관련 이슈 +RM-{번호} +``` + +--- + +## 테스트 전략 + +### 테스트 피라미드 +- **Unit Tests (70%)**: 순수 함수, 비즈니스 로직 +- **Integration Tests (20%)**: API 엔드포인트, DB 연동 +- **E2E Tests (10%)**: 핵심 사용자 시나리오 + +### 도구 +| 종류 | Python | JavaScript | +|------|--------|------------| +| Unit | pytest | Jest | +| Integration | pytest + httpx | Supertest | +| E2E | — | Playwright | +| 커버리지 | pytest-cov (80% 목표) | Istanbul (80% 목표) | + +### 테스트 명명 규칙 +``` +test_{대상}_{조건}_{기대결과} +예: test_user_login_with_invalid_password_returns_401 +``` + +### 테스트 작성 지침 +- **AAA 패턴** (Arrange, Act, Assert) + Given/When/Then 주석 +- Mocking은 외부 의존성(API, DB)만 +- 경계값, 엣지 케이스 반드시 포함 +- 테스트당 assert 최소화 (SRP 원칙) + +### Jenkins CI 파이프라인 +```groovy +pipeline { + agent any + stages { + stage('Lint') { + steps { + sh 'ruff check . --output-format=github' + sh 'mypy src/' + } + } + stage('Unit Tests') { + steps { + sh 'pytest tests/unit/ -v --cov=src --cov-fail-under=80 --junitxml=test-results/unit.xml' + } + post { + always { + junit 'test-results/unit.xml' + publishCoverage adapters: [coberturaAdapter('coverage.xml')] + } + } + } + stage('Integration Tests') { + steps { + sh 'pytest tests/integration/ -v --junitxml=test-results/integration.xml' + } + } + stage('AI Code Review') { + when { changeRequest() } + steps { + sh ''' + git diff origin/develop...HEAD | \ + claude -p "이 코드 변경사항을 리뷰해줘. 보안, 성능, 코딩 컨벤션 관점에서 문제점만 JSON으로 출력" \ + > review_output.json + ''' + archiveArtifacts 'review_output.json' + } + } + } +} +``` + +--- + +## 팀 역할별 운영 가이드 + +> 모든 역할은 동일한 MCP 설정을 공유하되, 역할별 주요 도구와 프롬프트 패턴을 달리 사용합니다. + +### PM (프로젝트 매니저) +**주요 도구**: Redmine MCP, Obsidian MCP + +**지침** +- 이슈 생성 시: 제목, 담당자, 마감일, 우선순위, 예상 시간(h), 수락 기준(체크리스트) 필수 입력 +- 스프린트 리뷰 리포트는 Obsidian `Sprints/` 폴더에 저장 +- 에픽-스토리-태스크 계층 구조 유지 + +**주요 프롬프트 패턴** +```bash +# 스프린트 현황 정리 +"Redmine에서 이번 스프린트 이슈들의 상태를 가져와서 완료/진행중/대기/블로커로 분류하고 Obsidian Sprints/2026-W09.md에 정리해줘" + +# 스프린트 계획 보조 +"Redmine 백로그 상위 20개 이슈를 가져오고 예상 시간을 합산해서 2주 스프린트(팀원 4명, 주 40시간) 기준 소화 가능한 범위를 계획해줘" + +# 회의록 → 이슈 자동 생성 +"오늘 기획 회의 내용이야: [회의록] / 액션아이템을 추출해서 Redmine 이슈로 생성해줘. 담당자는 미정으로." +``` + +--- + +### 기획자 / 시스템 분석가 +**주요 도구**: Obsidian MCP, Redmine MCP + +**지침** +- 요구사항 문서: Obsidian `Requirements/{기능명}.md`에 저장 +- 사용자 스토리 형식: "나는 {역할}로서 {기능}을 원한다. 왜냐하면 {이유} 때문이다." +- 화면 정의서: Mermaid 다이어그램 또는 ASCII 와이어프레임 사용 +- 용어집(`Glossary.md`) 업데이트 필수 + +**주요 프롬프트 패턴** +```bash +# 요구사항 → 사용자 스토리 분해 +"다음 기능 요구사항을 INVEST 원칙에 따라 사용자 스토리로 분해하고 수락 기준을 추가해서 Obsidian Requirements/기능명.md에 저장해줘: [요구사항]" + +# API 명세 초안 +"Obsidian Requirements/user-auth.md를 읽고 OpenAPI 3.0 명세 초안을 작성해줘. 엔드포인트, 요청/응답 스키마 포함." + +# 시퀀스 다이어그램 +"로그인 플로우를 Mermaid 시퀀스 다이어그램으로 그리고 Obsidian Diagrams/login-flow.md에 저장해줘" +``` + +--- + +### 개발자 (백엔드 / 프론트엔드) +**주요 도구**: Gitea MCP, Redmine MCP, Jenkins MCP + +**지침** +- 새 작업 시작: Redmine 이슈 확인 → 브랜치 생성 → CLAUDE.md 읽기 +- 코드 생성 시 기존 코드 스타일 분석 후 일관성 유지 +- 외부 라이브러리 추가 시 보안 취약점 먼저 확인 +- 레거시 코드 수정 시 회귀 테스트 먼저 작성 + +**주요 프롬프트 패턴** +```bash +# 이슈 기반 개발 시작 +"Redmine 이슈 #342의 내용을 읽고 구현 계획을 세워줘. 필요한 파일 목록, 예상 작업 시간, 잠재적 위험 요소 포함." + +# 코드 리뷰 요청 +"feature/RM-342-user-auth 브랜치의 변경사항을 리뷰해줘. OWASP Top 10 보안 관점과 팀 컨벤션 준수 여부 중심으로." + +# 빌드 실패 분석 +"Jenkins 빌드 #123의 실패 로그를 가져와서 root cause를 분석하고 수정 방법을 제시해줘." + +# 새 기능 구현 +"Obsidian Requirements/payment-gateway.md의 명세를 읽고 FastAPI 엔드포인트와 서비스 레이어를 구현해줘. 기존 auth_service.py 패턴을 따라서." +``` + +--- + +### QA 엔지니어 +**주요 도구**: Jenkins MCP, Gitea MCP, Redmine MCP + +**지침** +- 테스트 케이스는 Redmine 이슈의 수락 기준에서 도출 +- 버그 이슈: 즉시 Blocker / Critical / Major / Minor 분류 +- 버그 리포트 필수 항목: 재현 단계, 기대 결과, 실제 결과, 환경 정보 +- 머지 전 Jenkins 회귀 테스트 자동 실행 확인 + +**테스트 환경** +| 환경 | URL | +|------|-----| +| DEV | http://dev.company.com | +| STG | http://staging.company.com | +| PRD | http://app.company.com | + +**주요 프롬프트 패턴** +```bash +# 테스트 계획 수립 +"Redmine 이슈 #342의 수락 기준을 읽고 테스트 케이스를 작성해줘. Happy Path, Negative Case, 경계값, 보안 케이스 모두 포함." + +# 빌드 품질 분석 +"Jenkins에서 최근 5개 빌드의 테스트 결과를 가져와서 flaky 테스트를 찾고 실패 트렌드를 분석해줘." + +# 회귀 테스트 커버리지 확인 +"이번 스프린트에서 변경된 Gitea PR 목록을 가져와서 테스트가 없는 PR 목록을 알려줘." + +# E2E 테스트 시나리오 작성 +"Obsidian Requirements/checkout-flow.md를 읽고 Playwright E2E 테스트 스크립트를 작성해줘. Page Object Model 패턴 사용." +``` + +--- + +## 공통 워크플로우: 이슈 → 개발 → 배포 + +``` +[PM] Redmine 이슈 생성 (수락 기준 포함) + ↓ +[개발자] 이슈 확인 → 브랜치 생성 (feature/RM-{번호}-{설명}) + ↓ +[개발자] 구현 + 단위 테스트 작성 (커버리지 80%+) + ↓ +[개발자] PR 생성 → PR 본문 템플릿 작성 → 리뷰어 지정 + ↓ +[QA / 개발자] 코드 리뷰 + Jenkins CI 자동 실행 (lint → unit → integration) + ↓ +[QA] STG 환경에서 수락 기준 기반 테스트 + ↓ +[개발자] 승인 후 develop 머지 + ↓ +[PM] Redmine 이슈 상태 → 완료 처리 +``` + +### Claude Code 자동화 프롬프트 (전체 사이클) +```bash +# 이슈 기반 브랜치 자동 생성 (Makefile) +make start-issue # Redmine 이슈 번호 입력 → 브랜치 자동 생성 + +# PR 전 체크 +make pr-ready # lint + test 자동 실행 + +# PR 설명 초안 생성 +claude -p "현재 브랜치의 git diff를 분석해서 PR 본문 초안을 한국어로 작성해줘. Conventional Commit 형식 준수." + +# 배포 후 이슈 완료 처리 +"Redmine 이슈 #342 상태를 완료로 변경하고 실제 소요 시간을 기록해줘." +``` + --- ## 금기 사항 (AI 포함 모든 기여자 준수) @@ -157,25 +426,49 @@ API 호출 대신 MCP 툴을 우선 사용하세요. # 개발 서버 시작 (backend + frontend 동시 실행) make dev +# 이슈 기반 브랜치 자동 생성 +make start-issue # Redmine 이슈 번호 + 브랜치 설명 입력 → 브랜치 생성 + +# PR 전 체크 (lint + test) +make pr-ready + # 테스트 실행 make test # 특정 테스트만 실행 pytest tests/unit/ -v -# 린트 검사 +# 린트 검사 / 자동 수정 make lint - -# 린트 자동 수정 make lint-fix -# DB 마이그레이션 생성 +# DB 마이그레이션 생성 / 적용 alembic revision --autogenerate -m "description" - -# DB 마이그레이션 적용 alembic upgrade head ``` +### Makefile +```makefile +.PHONY: dev test lint lint-fix pr-ready start-issue draft-pr + +start-issue: + @read -p "프로젝트명 (/Users/joungmin/workspaces/ 내): " PROJ; \ + read -p "Redmine 이슈 번호: " RM_NUM; \ + read -p "브랜치 설명 (영어 kebab-case): " DESC; \ + cd /Users/joungmin/workspaces/$$PROJ; \ + git checkout develop; \ + git pull origin develop; \ + git checkout -b "feature/RM-$$RM_NUM-$$DESC" + +pr-ready: + make lint + make test + @echo "✅ 린트 & 테스트 완료. PR 생성 준비됨." + +draft-pr: + claude -p "현재 브랜치의 git diff를 분석해서 PR 본문 초안을 한국어로 작성해줘. Conventional Commit 형식 준수." +``` + --- ## 참조 문서