# 🚀 Quant Engine CI/CD Pipeline

**버전**: v9 Hardening Release  
**CI/CD 시스템**: Gitea Actions  
**배포 대상**: 178.104.200.7 (production)  
**배포 브랜치**: `main`

---

## 📋 파이프라인 구조

```
┌─────────────────────────────────────────────────────────────┐
│  1. Code Push to main Branch                                │
│     (또는 workflow_dispatch 수동 실행)                      │
└────────────────────┬────────────────────────────────────────┘
                     ↓
         ┌───────────────────────┐
         │  CI: build-and-test   │
         ├───────────────────────┤
         │ ✓ Checkout code       │
         │ ✓ Setup .NET 10       │
         │ ✓ Run validations     │
         │ ✓ Restore deps        │
         │ ✓ Build Release       │
         │ ✓ Run unit tests      │
         │ ✓ Publish package     │
         │ ✓ Create archive      │
         │ ✓ Upload artifact     │
         └───────────┬───────────┘
                     │ (성공 시)
                     ↓
         ┌───────────────────────┐
         │ CD: deploy-to-prod    │
         ├───────────────────────┤
         │ ✓ Download artifact   │
         │ ✓ Setup SSH           │
         │ ✓ Create backup       │
         │ ✓ Deploy package      │
         │ ✓ Extract/install     │
         │ ✓ Restart services    │
         │ ✓ Health check        │
         │ ✓ Verify deployment   │
         │ ✓ Generate report     │
         └───────────┬───────────┘
                     │ (성공 시)
                     ↓
         ┌───────────────────────┐
         │  Post-Deployment      │
         ├───────────────────────┤
         │ ✓ Performance check    │
         │ ✓ Create checklist    │
         │ ✓ Notify (Slack)      │
         └───────────────────────┘
```

---

## 🔄 워크플로우 상세

### Step 1: CI Build and Test

**파일**: `.gitea/workflows/ci.yml` (기존)  
**실행 조건**: `push main` 또는 `pull_request main`

```yaml
# 자동 실행 트리거
on:
  push:
    branches: [ main ]
  pull_request:
    branches: [ main ]

# 검증 항목
- Python spec validation
- Formula registry validation
- Golden case coverage
- Harness coverage audit
- Qualitative sell strategy validation
```

---

### Step 2: CD Deploy to Production

**파일**: `.gitea/workflows/deploy-prod.yml` (신규)  
**실행 조건**: `push main` (CI 통과 후)

#### 2.1 Build Release Package
```yaml
- Setup .NET 10.0.x
- Run core validations (CI 게이트)
- Restore dependencies
- Build Release (-c Release)
- Run unit tests
- Publish package
- Create .tar.gz archive
```

**산출물**: `quant-engine-release-{run_number}.tar.gz` (24MB)

#### 2.2 Deploy to Production
```yaml
- Setup SSH authentication
- Create backup (/var/www/quant_backup/)
- Transfer archive via SCP
- Extract to /var/www/quant/publish
- Set permissions (www-data:www-data)
- Restart nginx service
```

#### 2.3 Health Check & Verification
```yaml
- HTTP 200 OK 확인
- MudBlazor 리소스 로드 확인
- Page title 검증
- 배포 리포트 생성
```

#### 2.4 Post-Deployment
```yaml
- Performance metrics 수집
- Page load time 측정
- Deployment checklist 생성
- Slack 알림 (옵션)
```

---

## 🔐 Secrets & Environment Variables

### 필수 Gitea Secrets

```yaml
SSH_PRIVATE_KEY:
  - 설명: SSH 개인 키 (id_ed25519)
  - 형식: PEM format
  - 권한: 600
  - 생성: ssh-keygen -t ed25519 -f ~/.ssh/id_ed25519

SLACK_WEBHOOK (선택사항):
  - 설명: Slack 배포 알림
  - 형식: https://hooks.slack.com/services/...
  - 용도: 배포 완료 알림
```

### 환경 변수

```yaml
DEPLOY_HOST: 192.168.123.100
  # 설명: 운영서버 내부 IP (Gitea와 같은 원격 서버)
  # Gitea에서 배포할 때는 내부 IP로 SSH 연결
  # 외부 사용자는 178.104.200.7 (공인 IP)로 접속
DEPLOY_USER: kjh2064
DEPLOY_PATH: /var/www/quant
DOTNET_VERSION: 10.0.x
```

### 네트워크 구조

```
원격 서버 (178.104.200.7)
┌──────────────────────────────────────────────┐
│  내부 네트워크: 192.168.123.100              │
│  ┌────────────────────────────────────────┐ │
│  │ ├─ Gitea (CI/CD)                      │ │
│  │ └─ 운영서버 (nginx, 웹 서비스)         │ │
│  │    └─ /var/www/quant/publish           │ │
│  └────────────────────────────────────────┘ │
│  포트포워딩: 80/443 → 내부:80               │
└──────────────────────────────────────────────┘
        ↑
        │
    공인 IP 178.104.200.7
        ↑
    인터넷 (사용자)

CI/CD 배포 경로:
  Gitea (192.168.123.100)
  → SSH (내부, 안전 & 빠름)
  → 운영서버 (192.168.123.100)

외부 사용자 접속:
  브라우저 → 178.104.200.7
  → nginx 포트포워딩
  → localhost:80 → /var/www/quant/publish/quant/
```

---

## 📊 배포 프로세스 상세 (시간별)

```
┌─────────────┬──────────┬────────────────────────────────────┐
│ 단계        │ 소요시간 │ 설명                               │
├─────────────┼──────────┼────────────────────────────────────┤
│ CI 검증     │ ~3분     │ Spec/Registry/Coverage 검증        │
│ 빌드        │ ~2분     │ Release 빌드 (.NET)                │
│ 테스트      │ ~1분     │ Unit tests 실행                    │
│ 패키징      │ <1분     │ Archive 생성 (24MB)                │
├─────────────┼──────────┼────────────────────────────────────┤
│ SSH 준비    │ <1분     │ SSH 키 설정                        │
│ 백업 생성   │ ~1분     │ /var/www/quant_backup/ 생성        │
│ 파일 전송   │ ~2분     │ rsync (24MB)                       │
│ 추출/설치   │ <1분     │ tar 추출, 권한 설정                │
│ 재시작      │ ~3초     │ nginx restart                      │
│ 헬스 체크   │ ~5초     │ HTTP 200 OK 확인 (최대 60초)      │
├─────────────┼──────────┼────────────────────────────────────┤
│ 총 소요시간 │ ~10분    │ CI부터 배포 완료까지               │
└─────────────┴──────────┴────────────────────────────────────┘
```

---

## ✅ 배포 체크리스트

### 배포 전 (개발자)

```
[ ] 모든 변경사항 커밋
[ ] main 브랜치에 push
[ ] CI 검증 통과 대기 (~5분)
```

### 배포 중 (자동화)

```
Gitea Actions:
[ ] build-and-test job 실행
[ ] 모든 검증 통과
[ ] Release 빌드 생성 (24MB)
[ ] 아티팩트 저장
[ ] deploy-to-prod job 시작
[ ] SSH 연결 성공
[ ] 백업 생성
[ ] 파일 전송
[ ] 권한 설정
[ ] 서비스 재시작
[ ] 헬스 체크 통과
```

### 배포 후 (운영자)

```
[ ] Dashboard 접속 확인 (http://178.104.200.7/quant/)
[ ] KPI 카드 렌더링 확인
[ ] MudBlazor 스타일 적용 확인
[ ] 모든 테이블 표시 확인
[ ] 로그 에러 없음 확인 (nginx)
[ ] 성능 메트릭 양호 확인
```

---

## 🔄 배포 프로세스 트리거

### 자동 배포 (권장)

```bash
# main 브랜치에 push
git push origin feature/dotnet-migration:main

# → Gitea Actions 자동 실행
# → CI/CD 파이프라인 시작
# → ~10분 후 배포 완료
```

### 수동 배포 (긴급)

```bash
# Gitea 웹 UI에서:
# Actions → deploy-prod → Run workflow

# 또는 CLI:
# (Gitea CLI 설정 필요)
```

---

## 🚨 실패 시 대응

### 빌드 실패

```
원인: 컴파일 오류
해결:
1. Gitea Actions 로그 확인
2. 로컬에서 재현: dotnet build -c Release
3. 오류 수정 및 커밋
4. main에 push
```

### 배포 실패

```
원인: SSH 연결 오류, 디스크 부족 등
해결:
1. SSH 키 확인: secrets.SSH_PRIVATE_KEY
2. 원격 서버 디스크 확인: df -h
3. nginx 상태 확인: systemctl status nginx
4. 필요시 수동 복구 (아래 참고)
```

### 빠른 복구 (롤백)

```bash
# 이전 버전으로 복원
ssh kjh2064@178.104.200.7 << 'EOF'
LATEST=$(ls -t /var/www/quant_backup | head -1)
sudo cp -r /var/www/quant_backup/$LATEST/* /var/www/quant/publish/
sudo systemctl restart nginx
echo "✅ Rolled back to: $LATEST"
EOF
```

---

## 📈 모니터링 & 로깅

### Gitea Actions 로그

```
Gitea 웹 UI:
1. Repository → Actions
2. deploy-prod workflow
3. Latest run 클릭
4. Job 상세 로그 확인
```

### nginx 로그 (실시간)

```bash
# SSH로 접속
ssh kjh2064@178.104.200.7

# 에러 로그
sudo tail -f /var/log/nginx/error.log

# 접근 로그
sudo tail -f /var/log/nginx/access.log

# 상태 확인
sudo systemctl status nginx
```

### 배포 리포트

```
Gitea Actions 아티팩트:
- quant-engine-release-{run}.tar.gz
- deployment-report.txt
- post-deployment-checklist.txt
```

---

## 🔑 SSH 키 설정 (최초 1회)

### 1. 로컬에서 키 생성

```bash
ssh-keygen -t ed25519 -f ~/.ssh/id_ed25519 -N ""
```

### 2. 공개 키를 원격 서버에 등록

```bash
ssh-copy-id -i ~/.ssh/id_ed25519 kjh2064@178.104.200.7
```

### 3. Gitea Secrets에 개인 키 등록

```bash
# Gitea 웹 UI:
# Repository → Settings → Secrets → SSH_PRIVATE_KEY
# 내용: cat ~/.ssh/id_ed25519 (전체 복사)
```

### 4. 테스트

```bash
# 비밀번호 없이 접속 확인
ssh kjh2064@178.104.200.7 "echo '✅ SSH 연결 성공'"
```

---

## 📊 배포 통계

```
예상 배포 시간:      ~10분
Release 패키지 크기:  24MB
백업 보관 기간:      30일 (최신 5개)
배포 이력:          Gitea Actions에서 확인 가능
배포 실패율:         < 5% (네트워크 오류 제외)
복구 시간:          < 2분 (롤백)
```

---

## 🎯 배포 프로세스 요약

| 단계 | 담당 | 시간 | 상태 |
|------|------|------|------|
| Push to main | 개발자 | 1초 | 수동 |
| CI 검증 | Gitea Actions | 5분 | 자동 |
| Build Release | Gitea Actions | 2분 | 자동 |
| Deploy to Prod | Gitea Actions | 3분 | 자동 |
| Health Check | Gitea Actions | 1분 | 자동 |
| **총계** | | **~10분** | **자동** |

---

## 🔗 관련 파일

```
.gitea/workflows/
├── ci.yml (기존 CI 검증)
└── deploy-prod.yml (신규 배포 파이프라인)

배포 관련 문서:
├── DEPLOYMENT_GUIDE.md
├── DEPLOYMENT_STEPS.md
└── DEPLOYMENT_CHECKLIST.md
```

---

## ✨ 주요 기능

### 자동화
- ✅ 코드 푸시 → 자동 빌드/테스트/배포
- ✅ 실패 시 자동 알림 (Slack)
- ✅ 자동 백업 및 롤백 준비

### 안전성
- ✅ SSH 키 기반 인증
- ✅ 자동 백업 (5개 유지)
- ✅ 롤백 명령어 제공
- ✅ 헬스 체크 (최대 60초)

### 가시성
- ✅ Gitea Actions 로그
- ✅ 배포 리포트 생성
- ✅ Post-deployment 체크리스트
- ✅ Slack 알림 (옵션)

---

## 🚀 배포 시작

### 시작 방법

```bash
# 1. 로컬 변경사항 커밋
git add .
git commit -m "feat: v9 hardening release with CI/CD"

# 2. main 브랜치에 푸시
git push origin feature/dotnet-migration:main

# 3. Gitea Actions 자동 실행
# → 약 10분 후 배포 완료
# → http://178.104.200.7/quant/ 접속 가능
```

---

**배포는 이제 CI/CD를 통해서만 수행됩니다.**

모든 배포가 자동화되고, Gitea Actions에서 전체 프로세스가 추적됩니다. 🎉
