# 📚 Todo Project 종합 개발 가이드

> **"Simple Todo, Smart Integration"**  
> 간결한 할일 관리 + 시놀로지 생태계 연동으로 완벽한 개인 생산성 도구

---

## 🎯 프로젝트 개요

### 목표
사진과 메모를 기반으로 한 간단한 일정관리 시스템 구축

### 핵심 기능
- **입력**: 사진(선택) + 텍스트 메모
- **분류**: GTD형 / 캘린더형 / 체크리스트형
- **플랫폼**: iOS + Apple Watch + 웹

### 시스템 환경
- **배포 서버**: Synology DS1525+ 
- **개발 환경**: Mac mini M4 Pro (macOS)
- **네트워크**: LG U+ 2.5G + Synology Router

### 핵심 가치
- ⚡ **즉시 접근**: 바로 켜서 바로 쓸 수 있는 간편함
- 🎯 **간결함**: 복잡하지 않은 직관적인 인터페이스  
- 🔗 **스마트 연동**: 시놀로지 캘린더/메일과 자동 동기화
- 📱 **어디서나**: 폰, 컴퓨터에서 동일한 경험

---

## 🏗 시스템 아키텍처

### 볼륨 매핑 구조
```
Synology NAS:
/volume3/docker/todo-app/     # 시스템/컨테이너
├── docker-compose.yml
├── app/                      # 애플리케이션 코드
└── config/                   # 설정 파일

/volume1/todo-data/           # 데이터 저장
├── database/                 # DB 파일
├── uploads/images/           # 업로드 이미지
└── backups/                  # 백업
```

### 기술 스택
```
Backend:  FastAPI (Python) / PostgreSQL
Frontend: Vanilla JS + Alpine.js + Tailwind CSS
Database: PostgreSQL (포트: 5434)
Deployment: Docker + Docker Compose
Integration: CalDAV, SMTP, DSM API
```

### 전체 구조
```
┌─────────────────┐    ┌─────────────────┐    ┌─────────────────┐
│   Frontend      │    │    Backend      │    │   Synology      │
│   (4000)        │◄──►│    (9000)       │◄──►│   Services      │
│                 │    │                 │    │                 │
│ • PWA Support   │    │ • FastAPI       │    │ • Calendar      │
│ • Offline Mode  │    │ • SQLAlchemy    │    │ • MailPlus      │
│ • Auto Login    │    │ • PostgreSQL    │    │ • DSM API       │
└─────────────────┘    └─────────────────┘    └─────────────────┘
```

### API 구조
```
POST   /api/items              # 생성
GET    /api/items?type={type}  # 조회
PUT    /api/items/{id}         # 수정
DELETE /api/items/{id}         # 삭제
POST   /api/upload/image       # 이미지
```

---

## 📁 프로젝트 구조

```
Todo-Project/
├── README.md
├── DESIGN.md                    # 설계 문서
├── SYNOLOGY_INTEGRATION.md      # 시놀로지 연동 가이드
├── docker-compose.yml
├── .env.example
├── backend/
│   ├── Dockerfile
│   ├── pyproject.toml
│   ├── src/
│   │   ├── main.py
│   │   ├── core/
│   │   │   ├── config.py
│   │   │   ├── database.py
│   │   │   └── security.py
│   │   ├── models/
│   │   │   ├── user.py
│   │   │   └── todo.py
│   │   ├── schemas/
│   │   │   ├── auth.py
│   │   │   └── todo.py
│   │   ├── api/
│   │   │   ├── dependencies.py
│   │   │   └── routes/
│   │   │       ├── auth.py
│   │   │       ├── users.py
│   │   │       └── todos.py
│   │   └── integrations/
│   │       ├── synology/
│   │       │   ├── dsm_auth.py
│   │       │   ├── calendar_sync.py
│   │       │   └── mail_service.py
│   │       └── device_auth.py
│   └── migrations/
├── frontend/
│   ├── index.html
│   ├── login.html
│   ├── static/
│   │   ├── css/
│   │   │   └── main.css
│   │   ├── js/
│   │   │   ├── api.js
│   │   │   ├── auth.js
│   │   │   ├── todos.js
│   │   │   └── synology-sync.js
│   │   └── icons/
│   ├── components/
│   └── manifest.json            # PWA 설정
├── docs/
│   ├── API.md                   # API 문서
│   ├── DEPLOYMENT.md            # 배포 가이드
│   └── SECURITY.md              # 보안 가이드
└── database/
    └── init/
        └── 01_init.sql
```

---

## 📊 데이터베이스 설계

### ERD (Entity Relationship Diagram)
```
┌─────────────┐         ┌─────────────┐         ┌─────────────┐
│    Users    │         │ TodoItems   │         │TodoComments │
├─────────────┤         ├─────────────┤         ├─────────────┤
│ id (PK)     │◄────────│ user_id(FK) │◄────────│todo_item_id │
│ email       │         │ content     │         │ content     │
│ password    │         │ status      │         │ created_at  │
│ full_name   │         │ start_date  │         └─────────────┘
│ is_active   │         │ estimated   │
│ created_at  │         │ completed   │
└─────────────┘         │ parent_id   │ ◄─┐
                        └─────────────┘   │
                               │          │
                               └──────────┘
                            (Self Reference)
```

### 상태 관리
```python
TODO_STATES = {
    "draft": "검토 필요 - 아직 일정 미설정",
    "scheduled": "예정됨 - 일정 설정 완료", 
    "active": "진행중 - 현재 작업 중",
    "completed": "완료됨 - 작업 완료",
    "delayed": "지연됨 - 새로운 날짜로 연기"
}
```

### 데이터 플로우
```
1. 할일 생성 → 2. 일정 설정 → 3. 캘린더 동기화 → 4. 메일 알림
     ↓              ↓              ↓              ↓
   Draft         Scheduled      Calendar       Email
                                  Event        Sent
```

---

## 🔐 보안 설계

### 개인용 최적화 보안 모델

#### 기기 등록 방식
```python
class DeviceAuth:
    """개인 기기 인증 시스템"""
    
    def register_device(self, user_id, device_info):
        """신뢰할 수 있는 기기 등록"""
        # 기기 고유 ID 생성 (브라우저 fingerprint + 사용자 입력)
        device_id = self.generate_device_id(device_info)
        
        # 장기간 유효한 토큰 생성 (30일)
        device_token = self.create_device_token(user_id, device_id)
        
        return device_token
    
    def quick_login(self, device_token):
        """기기 토큰으로 빠른 로그인"""
        if self.is_valid_device_token(device_token):
            return self.create_session_token()
        return None
```

#### 보안 레벨
- **Minimal**: 기기 등록 후 비밀번호 불필요 (개인용 권장)
- **Balanced**: 주기적 비밀번호 확인
- **Secure**: 매번 인증 + 생체 인증

---

## 🔗 시놀로지 연동 설계

### 연동 개요

Todo-Project는 시놀로지 생태계와 **양방향 연동**되어 **간결한 할일 관리**와 **전체 일정 조망**을 동시에 제공합니다.

#### 핵심 철학
- **Todo-Project**: 빠른 할일 추가 및 관리 (간결함)
- **시놀로지 캘린더**: 전체 일정 조망 및 통합 관리 (완전성)
- **MailPlus**: 외부 요청을 Todo로 자동 변환 (자동화)

### 🔄 간소화된 연동 플로우 ⭐ 새로운 접근

#### 핵심 아이디어: **메일 중심 워크플로우**
```
📧 MailPlus 메일 수신 
    ↓
📅 시놀로지 캘린더 이벤트 생성 (수동/자동)
    ↓  
📋 Todo 자동 추가 (메일 내용 + 첨부파일 포함)
    ↓
🔄 캘린더 ↔ Todo 양방향 동기화
```

#### 장점
- **단순함**: 복잡한 API 연동 최소화
- **자연스러움**: 기존 메일 워크플로우 활용
- **유연성**: 다양한 메일 클라이언트에서 작동
- **안정성**: 시놀로지 기본 기능 활용

### 간소화된 구현 방법

#### 1. 메일 모니터링 (핵심 기능)
```python
class SimpleMailMonitor:
    """간단한 메일 모니터링 서비스"""
    
    def __init__(self, imap_server, username, password):
        self.imap_server = imap_server
        self.username = username
        self.password = password
    
    async def check_new_emails(self):
        """새 메일 확인 (IMAP)"""
        import imaplib
        import email
        
        mail = imaplib.IMAP4_SSL(self.imap_server, 993)
        mail.login(self.username, self.password)
        mail.select('inbox')
        
        # 읽지 않은 메일 검색
        status, messages = mail.search(None, 'UNSEEN')
        
        new_emails = []
        for msg_id in messages[0].split():
            status, msg_data = mail.fetch(msg_id, '(RFC822)')
            email_body = msg_data[0][1]
            email_message = email.message_from_bytes(email_body)
            
            new_emails.append({
                'id': msg_id,
                'subject': email_message['Subject'],
                'from': email_message['From'],
                'body': self._extract_body(email_message),
                'attachments': self._extract_attachments(email_message)
            })
        
        mail.close()
        mail.logout()
        return new_emails
```

#### 2. 메일 → Todo 자동 변환 서비스
```python
class MailToTodoService:
    """메일을 Todo로 자동 변환하는 간단한 서비스"""
    
    def __init__(self, mail_monitor, todo_service):
        self.mail_monitor = mail_monitor
        self.todo_service = todo_service
        
    async def monitor_emails(self):
        """메일 모니터링 및 자동 변환"""
        while True:
            try:
                new_emails = await self.mail_auth.check_new_emails()
                
                for email in new_emails:
                    if self._is_todo_email(email):
                        todo_item = await self._convert_email_to_todo(email)
                        await self.todo_service.create_todo(todo_item)
                        
                        # 캘린더에도 동기화
                        await self.calendar_sync.sync_todo_to_calendar(todo_item)
                        
            except Exception as e:
                logger.error(f"메일 모니터링 오류: {e}")
            
            await asyncio.sleep(60)  # 1분마다 체크
    
    def _is_todo_email(self, email):
        """Todo 변환 대상 메일인지 판단"""
        # 제목에 특정 키워드 포함
        todo_keywords = ['할일', 'TODO', 'Task', '작업', '요청']
        subject = email['subject'].lower()
        
        return any(keyword.lower() in subject for keyword in todo_keywords)
    
    async def _convert_email_to_todo(self, email):
        """메일을 Todo 항목으로 변환"""
        # 제목에서 할일 내용 추출
        content = self._extract_todo_content(email['subject'])
        
        # 본문에서 날짜/시간 추출
        due_date = self._extract_date_from_body(email['body'])
        
        # 첨부파일 처리
        attachments = await self._save_attachments(email['attachments'])
        
        todo_data = {
            'content': content,
            'description': email['body'],
            'due_date': due_date,
            'attachments': attachments,
            'source': 'email',
            'source_id': email['id'],
            'sender': email['from']
        }
        
        return todo_data
    
    def _extract_todo_content(self, subject):
        """제목에서 할일 내용 추출"""
        # "할일: 문서 검토" → "문서 검토"
        # "TODO: Review document" → "Review document"
        import re
        
        patterns = [
            r'할일:\s*(.+)',
            r'TODO:\s*(.+)',
            r'Task:\s*(.+)',
            r'작업:\s*(.+)',
            r'요청:\s*(.+)'
        ]
        
        for pattern in patterns:
            match = re.search(pattern, subject, re.IGNORECASE)
            if match:
                return match.group(1).strip()
        
        return subject  # 패턴이 없으면 전체 제목 사용
    
    def _extract_date_from_body(self, body):
        """본문에서 날짜 추출"""
        import re
        from datetime import datetime, timedelta
        
        # 날짜 패턴들
        date_patterns = [
            r'(\d{4}-\d{2}-\d{2})',  # 2024-01-15
            r'(\d{2}/\d{2}/\d{4})',  # 01/15/2024
            r'(\d{1,2}월\s*\d{1,2}일)',  # 1월 15일
            r'(내일|tomorrow)',
            r'(다음주|next week)',
            r'(이번주|this week)'
        ]
        
        for pattern in date_patterns:
            match = re.search(pattern, body, re.IGNORECASE)
            if match:
                date_str = match.group(1)
                return self._parse_date_string(date_str)
        
        # 기본값: 3일 후
        return datetime.now() + timedelta(days=3)
    
    async def _save_attachments(self, attachments):
        """첨부파일을 NAS에 저장"""
        saved_files = []
        
        for attachment in attachments:
            # /volume1/todo-data/attachments/ 에 저장
            file_path = f"/data/attachments/{attachment['filename']}"
            
            with open(file_path, 'wb') as f:
                f.write(attachment['content'])
            
            saved_files.append({
                'filename': attachment['filename'],
                'path': file_path,
                'size': len(attachment['content'])
            })
        
        return saved_files
```

### ⚙️ 환경 설정

#### 환경 변수 설정
```bash
# .env 파일
# 시놀로지 메일 설정 (필수)
SYNOLOGY_MAIL_SERVER=your-nas.synology.me
SYNOLOGY_MAIL_USERNAME=todo_user
SYNOLOGY_MAIL_PASSWORD=your_secure_password

# 메일 모니터링 설정
ENABLE_MAIL_MONITORING=true
MAIL_CHECK_INTERVAL=60  # 초 단위
TODO_KEYWORDS=할일,TODO,Task,작업,요청

# 첨부파일 저장 경로
ATTACHMENTS_PATH=/data/attachments
```

#### 시놀로지 NAS 설정

##### 1. MailPlus 설정
```bash
# MailPlus 패키지에서:
1. IMAP 활성화: 설정 → IMAP/POP3 → IMAP 활성화
2. 포트: 993 (SSL) 또는 143 (일반)
3. 전용 계정 생성: todo_mail_user
4. 권한: MailPlus 접근만 허용
```

##### 2. 캘린더 설정 (선택사항)
```bash
# Calendar 패키지에서:
1. 새 캘린더 생성: "Todo Tasks"
2. 색상: 보라색 (#6366f1)
3. 메일에서 일정 추가 기능 활성화
```

### 🔧 사용 방법

#### 1. 메일로 할일 추가
```
제목: 할일: 프로젝트 문서 검토
본문: 
- 마감일: 2024-01-20
- 예상 소요시간: 2시간
- 첨부파일: project_spec.pdf

→ Todo 앱에 자동으로 추가됨
```

#### 2. 캘린더 연동 (선택)
```
MailPlus → 캘린더 이벤트 생성 → Todo 동기화
캘린더에서 완료 처리 → Todo 상태 자동 업데이트
```

#### 3. 첨부파일 관리
```
메일 첨부파일 → NAS 저장 (/data/attachments/)
Todo에서 파일 링크로 접근 가능
```

---

## 📱 프론트엔드 설계

### PWA (Progressive Web App) 구조
```javascript
// manifest.json
{
    "name": "Todo Project",
    "short_name": "Todo",
    "start_url": "/",
    "display": "standalone",
    "theme_color": "#6366f1",
    "shortcuts": [
        {
            "name": "빠른 할일 추가",
            "url": "/quick-add"
        }
    ]
}
```

### 오프라인 지원
```javascript
// Service Worker
self.addEventListener('fetch', event => {
    if (event.request.url.includes('/api/todos')) {
        event.respondWith(
            // 온라인: API 호출
            // 오프라인: 로컬 캐시 사용
            caches.match(event.request) || fetch(event.request)
        );
    }
});
```

### 상태 관리
```javascript
class TodoState {
    constructor() {
        this.todos = [];
        this.syncQueue = []; // 오프라인 시 동기화 대기열
        this.isOnline = navigator.onLine;
    }
    
    async addTodo(content) {
        const todo = this.createTodo(content);
        
        if (this.isOnline) {
            await this.syncToServer(todo);
        } else {
            this.syncQueue.push({action: 'create', todo});
        }
        
        return todo;
    }
}
```

### 간결한 인터페이스 원칙

#### 메인 화면
```html
<!-- 최소한의 요소만 표시 -->
<div class="todo-app">
    <!-- 빠른 입력 -->
    <input class="quick-add" placeholder="할일을 입력하세요..." />
    
    <!-- 간단한 탭 -->
    <div class="tabs">
        <button class="tab active">진행중</button>
        <button class="tab">완료</button>
    </div>
    
    <!-- 할일 목록 -->
    <div class="todo-list">
        <!-- 할일 아이템들 -->
    </div>
</div>
```

#### 모바일 최적화
- **터치 친화적**: 44px 이상 터치 영역
- **햅틱 피드백**: 액션 시 진동 피드백
- **풀투리프레시**: 아래로 당겨서 새로고침
- **오프라인 표시**: 네트워크 상태 표시

### 색상 시스템
```css
:root {
    --primary: #6366f1;      /* 보라색 - 메인 컬러 */
    --success: #10b981;      /* 초록색 - 완료 */
    --warning: #f59e0b;      /* 주황색 - 진행중 */
    --danger: #ef4444;       /* 빨간색 - 지연 */
    --gray: #6b7280;         /* 회색 - 대기 */
}
```

---

## 🎯 코딩 표준 및 규칙

### 핵심 원칙: "간결함 (Simplicity)"

> **"복잡함은 버그의 온상이다. 간결함이 최고의 아름다움이다."**

### 파일 크기 제한

#### 핵심 로직 파일 (엄격)
- **모델 파일 (models/)**: 최대 200줄
- **스키마 파일 (schemas/)**: 최대 150줄
- **설정 파일 (config.py)**: 최대 100줄

#### 서비스 파일 (보통)
- **API 라우터**: 최대 400줄
- **서비스 클래스**: 최대 350줄
- **통합 서비스**: 최대 500줄

#### 프론트엔드 파일 (유연)
- **JavaScript 파일**: 최대 300줄
- **HTML 파일**: 최대 250줄
- **CSS 파일**: 최대 200줄

### 함수/메서드 크기 제한
- **단순 함수**: 최대 20줄
- **비즈니스 로직 함수**: 최대 40줄
- **통합/조합 함수**: 최대 60줄
- **초기화 함수**: 최대 30줄

### 간결성 규칙

#### 1. 한 가지 일만 하기
```python
# ❌ 나쁜 예 - 여러 일을 함
def process_todo_and_send_email_and_update_calendar(todo):
    # 할일 처리
    # 이메일 발송
    # 캘린더 업데이트
    pass

# ✅ 좋은 예 - 각각 분리
def process_todo(todo): pass
def send_notification_email(todo): pass  
def update_calendar(todo): pass
```

#### 2. 명확한 이름 사용
```python
# ❌ 나쁜 예
def calc(x, y, z): pass
def proc_data(d): pass

# ✅ 좋은 예
def calculate_estimated_time(start, duration, buffer): pass
def process_todo_item(todo_data): pass
```

#### 3. 중복 제거
```python
# ❌ 나쁜 예 - 중복 코드
def create_synology_event(todo):
    event = CalendarEvent()
    event.title = f"📋 {todo.content}"
    event.start_time = todo.start_date
    # ... 공통 로직

# ✅ 좋은 예 - 공통 로직 분리
def create_base_event(todo):
    return CalendarEvent(
        title=f"📋 {todo.content}",
        start_time=todo.start_date
    )

def create_synology_event(todo):
    event = create_base_event(todo)
    # 시놀로지 특화 로직만
    return event
```

---

## 🐳 Docker 설정

### docker-compose.yml (Production - NAS)
```yaml
version: '3.8'

services:
  frontend:
    build: ./frontend
    container_name: todo-web
    ports:
      - "4000:80"
    depends_on:
      - backend
    restart: unless-stopped

  backend:
    build: ./backend
    container_name: todo-api
    ports:
      - "9000:9000"
    volumes:
      - /volume3/docker/todo-app/app:/app
      - /volume1/todo-data:/data
    environment:
      - DATABASE_URL=postgresql://todouser:${DB_PASSWORD}@database:5432/todo
      - UPLOAD_PATH=/data/uploads/images
      - TZ=Asia/Seoul
    depends_on:
      - database
    restart: unless-stopped

  database:
    image: postgres:15-alpine
    container_name: todo-db
    ports:
      - "5434:5432"
    volumes:
      - /volume1/todo-data/database:/var/lib/postgresql/data
    environment:
      - POSTGRES_DB=todo
      - POSTGRES_USER=todouser
      - POSTGRES_PASSWORD=${DB_PASSWORD}
    restart: unless-stopped
```

---

## 🔄 개발 워크플로우

### Mac 로컬 개발 구조
```bash
~/Developer/todo-app/
├── backend/
│   ├── main.py
│   ├── requirements.txt
│   ├── Dockerfile
│   └── docker-compose.dev.yml
├── frontend/
│   └── (React/Vue 파일)
├── ios/
│   └── TodoApp.xcodeproj
└── README.md
```

### 1단계: 로컬 개발 (Mac)
```bash
# 프로젝트 시작
cd ~/Developer/todo-app
docker-compose -f docker-compose.dev.yml up

# API 테스트
curl http://localhost:9000/api/items

# 프론트엔드 개발
npm run dev  # http://localhost:4000
```

### 2단계: NAS 배포
```bash
# Mac에서 푸시
git add .
git commit -m "기능 추가"
git push gitea main

# NAS SSH 접속
ssh admin@nas-ip

# 배포
cd /volume3/docker/todo-app
git pull
docker-compose down
docker-compose up -d --build
```

### 3단계: iOS 앱 연동
```swift
// Development
let API_BASE = "http://192.168.1.100:9000"

// Production  
let API_BASE = "https://your.synology.me:9000"
```

---

## 🚀 빠른 시작

### 포트 설정
- **Frontend**: http://localhost:4000
- **Backend API**: http://localhost:9000  
- **Database**: localhost:5434

### 개발 환경 설정

1. **환경 변수 설정**
```bash
cp .env.example .env
# .env 파일에서 시놀로지 연동 정보 설정 (선택사항)
```

2. **Docker로 실행**
```bash
docker-compose up -d
```

3. **브라우저에서 접속**
```
http://localhost:4000
```

4. **개인용 설정 (권장)**
- 첫 접속 시 "개인용으로 설정" 선택
- 내 기기 등록으로 자동 로그인 활성화

### 초기 설정 명령어
```bash
# Mac: 프로젝트 생성
mkdir -p ~/Developer/todo-app/{backend,frontend,ios}
cd ~/Developer/todo-app

# NAS: 폴더 생성
ssh admin@nas-ip
sudo mkdir -p /volume3/docker/todo-app
sudo mkdir -p /volume1/todo-data/{database,uploads/images,backups}

# Git 초기화
git init
git remote add origin http://nas-ip:3000/username/todo-app.git
```

### 첫 배포 테스트
```bash
# 1. 간단한 API 작성
echo "from fastapi import FastAPI
app = FastAPI()
@app.get('/')
def read_root():
    return {'status': 'ok'}" > backend/main.py

# 2. Dockerfile 생성
echo "FROM python:3.11-slim
WORKDIR /app
RUN pip install fastapi uvicorn
COPY . .
CMD ['uvicorn', 'main:app', '--host', '0.0.0.0', '--port', '9000']" > backend/Dockerfile

# 3. 배포 및 테스트
docker build -t todo-api backend/
docker run -p 9000:9000 todo-api
curl http://localhost:9000
```

---

## 📝 구현 로드맵

### Phase 1: 백엔드 (Week 1)
- [ ] Docker 환경 구성
- [ ] FastAPI 기본 CRUD
- [ ] PostgreSQL 스키마
- [ ] 이미지 업로드 처리
- [ ] JWT 인증

### Phase 2: 웹 프론트엔드 (Week 1)
- [ ] React/Vue 프로젝트 설정
- [ ] 3가지 분류 UI
- [ ] 이미지 업로드 컴포넌트
- [ ] PWA 설정
- [ ] 반응형 디자인

### Phase 3: iOS 앱 (Week 2-3)
- [ ] SwiftUI 기본 구조
- [ ] API Service 클래스
- [ ] 카메라/갤러리 연동
- [ ] 오프라인 캐싱
- [ ] 푸시 알림

### Phase 4: Apple Watch (Week 1)
- [ ] WatchOS 타겟 추가
- [ ] 오늘 할일 뷰
- [ ] 체크 기능
- [ ] 컴플리케이션

### 시놀로지 연동 (1단계)
- [ ] 시놀로지 인증 시스템
- [ ] 시놀로지 캘린더 연동
- [ ] PWA 모바일 지원
- [ ] 브라우저 확장 프로그램
- [ ] 오프라인 기능

---

## 🔧 NAS 설정 체크리스트

### Container Manager
```
1. 프로젝트 생성
   - 이름: todo-app
   - 경로: /volume3/docker/todo-app
   
2. 포트 설정
   - Frontend: 4000
   - Backend: 9000
   - Database: 5434
   
3. 볼륨 마운트
   - 소스: /volume1/todo-data
   - 타겟: /data
```

### 리버스 프록시 (선택)
```
제어판 > 로그인 포털 > 고급 > 리버스 프록시
- 소스: https://todo.your-domain.me
- 대상: http://localhost:4000
- HSTS, HTTP/2 활성화
```

---

## 🧪 테스트 전략

### 테스트 피라미드
```
    ┌─────────────┐
    │   E2E Tests │  ← 사용자 시나리오
    ├─────────────┤
    │ Integration │  ← API + DB 통합
    │    Tests    │
    ├─────────────┤
    │  Unit Tests │  ← 개별 함수/클래스
    └─────────────┘
```

### 중요 테스트 케이스
- **할일 CRUD**: 생성, 조회, 수정, 삭제
- **상태 전환**: Draft → Active → Completed
- **시놀로지 연동**: 캘린더 동기화, 메일 발송
- **오프라인 모드**: 네트워크 없이 기본 기능
- **기기 인증**: 등록, 로그인, 토큰 갱신

---

## 🛠 도구 및 자동화

### 코드 품질 도구
```bash
# Python
pip install flake8 black isort

# 라인 수 체크
find . -name "*.py" -exec wc -l {} + | sort -n

# 복잡도 체크
pip install mccabe
flake8 --max-complexity=5 .
```

### pre-commit 훅
```yaml
# .pre-commit-config.yaml
repos:
  - repo: local
    hooks:
      - id: check-file-size
        name: Check file size
        entry: bash -c 'find . -name "*.py" -exec wc -l {} + | awk "$1 > 300 {print $2 " exceeds 300 lines (" $1 ")"; exit 1}"'
        language: system
```

---

## 📈 성능 최적화

### 프론트엔드 최적화
- **지연 로딩**: 필요한 컴포넌트만 로드
- **가상 스크롤**: 많은 할일 목록 처리
- **캐싱**: 자주 사용하는 데이터 캐시
- **압축**: 정적 파일 gzip 압축

### 백엔드 최적화
- **데이터베이스 인덱스**: 자주 조회하는 컬럼
- **연결 풀링**: 데이터베이스 연결 재사용
- **캐싱**: Redis를 통한 세션 캐시
- **비동기 처리**: FastAPI async/await 활용

---

## 🔄 동기화 전략

### 실시간 동기화
```python
class SyncManager:
    """동기화 관리자"""
    
    async def sync_todo_change(self, todo_id, action):
        """할일 변경 시 동기화"""
        
        # 1. 로컬 상태 업데이트
        await self.update_local_state(todo_id, action)
        
        # 2. 시놀로지 캘린더 동기화
        if self.synology_enabled:
            await self.sync_to_calendar(todo_id, action)
        
        # 3. 다른 기기에 알림 (WebSocket)
        await self.notify_other_devices(todo_id, action)
```

### 충돌 해결
- **Last Write Wins**: 마지막 수정이 우선
- **사용자 선택**: 충돌 시 사용자가 선택
- **자동 병합**: 단순한 변경사항은 자동 병합

---

## 📌 참고사항

### 보안
- JWT 토큰 구현 필수
- HTTPS 설정 (Let's Encrypt)
- 환경변수로 민감정보 관리

### 백업
- Hyper Backup으로 자동 백업 설정
- `/volume1/todo-data` 전체 백업
- Git으로 코드 버전 관리

### 모니터링
- Synology Resource Monitor 활용
- Docker 로그: `docker logs todo-api`
- 에러 추적: Sentry 고려

---

## 📋 체크리스트

### 코드 작성 전
- [ ] 이 기능이 정말 필요한가?
- [ ] 더 간단한 방법은 없는가?
- [ ] 기존 코드를 재사용할 수 있는가?

### 코드 작성 중
- [ ] 함수가 30줄을 넘지 않는가?
- [ ] 하나의 함수가 한 가지 일만 하는가?
- [ ] 변수명이 명확한가?

### 코드 작성 후
- [ ] 파일이 300줄을 넘지 않는가?
- [ ] 중복 코드가 있는가?
- [ ] 다른 개발자가 쉽게 이해할 수 있는가?

---

## 🎯 1단계 목표 (시놀로지 연동)

1. **할일 → 캘린더**: 일정 설정 시 시놀로지 캘린더에 'todo' 태그로 등록
2. **메일 알림**: MailPlus를 통한 검토 정보 발송  
3. **상태 동기화**: 완료 시 '완료' 태그로 변경
4. **지연 처리**: 지연 시 캘린더 날짜 자동 수정

---

## 🤝 기여 방법

이 프로젝트는 개인용으로 시작되었지만, 유용한 기능이나 개선사항이 있다면 언제든 기여해주세요!

---

## 📄 라이선스

이 프로젝트는 기존 Document Server 프로젝트에서 분리되어 독립적으로 개발되고 있습니다.

---

**이 종합 가이드를 따라가면 체계적이고 간결한 Todo 앱을 개발할 수 있습니다! 🚀**
