Files
telegram-bot-workers/CLAUDE.md
kappa 4536a22003 docs: Deposit Agent 프롬프트 개선사항 문서화
- AI 시스템 프롬프트: 에이전트 응답 그대로 전달 규칙 추가
- Deposit Agent 핵심 규칙 확장:
  - 자연어 금액 인식 (만원, 5천원 등)
  - 즉시 실행 (확인 질문 없이)
  - 간편 취소 (최근 pending 자동 선택)
  - 동시 요청 허용
- Deposit Agent 응답 포맷 예시 추가

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-17 11:36:57 +09:00

16 KiB

CLAUDE.md

This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.

Auto-Read on Start

세션 시작 시 반드시 수행:

  1. README.md를 Read 도구로 읽어 프로젝트 전체 구조 파악
  2. 작업 대상 파일의 기존 코드 먼저 확인
필수 읽기: README.md → 작업 대상 파일

Critical Rules

절대 지켜야 할 규칙:

규칙 이유
배포 전 npm run dev 로컬 테스트 프로덕션 장애 방지
D1 스키마 변경 시 마이그레이션 SQL 별도 작성 기존 데이터 보존
Secrets(BOT_TOKEN, API_KEY 등) 코드에 하드코딩 금지 보안
wrangler.toml의 ID 값 변경 금지 리소스 연결 유지
Function Calling 도구 추가 시 tools 배열 + executeFunctionCall() 동시 수정 불일치 방지

위험한 작업:

  • wrangler d1 execute 직접 실행 (production) → 반드시 확인 요청
  • user_deposits, deposit_transactions 테이블 직접 수정 → 금전 관련, 주의

Documentation Rules

작업 완료 후 문서 자동 업데이트:

트리거 조건

변경 유형 업데이트 대상
src/*.ts 파일 수정 CLAUDE.md (Core Services, Key Patterns)
새 Function Calling 도구 추가 양쪽 (README: 지원 기능 테이블, CLAUDE: tools 목록)
schema.sql 변경 양쪽 (Data Layer 섹션)
wrangler.toml 환경변수 추가 양쪽 (Configuration 섹션)
외부 API 연동 추가/변경 양쪽 (External Integrations)
봇 명령어 추가 양쪽 (Commands 섹션)

업데이트 체크리스트

[ ] CLAUDE.md - 기술 상세 (개발자용)
[ ] README.md - 사용자 가이드 (배포/운영자용)
[ ] 다이어그램/플로우 수정 필요 여부
[ ] wrangler.toml 주석 업데이트

Commands

npm run dev           # 로컬 개발 (wrangler dev)
npm run deploy        # Cloudflare Workers 배포
npm run db:init       # D1 스키마 초기화 (production) ⚠️ 주의
npm run db:init:local # D1 스키마 초기화 (local)
npm run tail          # Workers 로그 스트리밍

Secrets 설정:

wrangler secret put BOT_TOKEN        # Telegram Bot Token
wrangler secret put WEBHOOK_SECRET   # Webhook 검증용
wrangler secret put OPENAI_API_KEY   # OpenAI API 키

Webhook 설정:

curl https://telegram-summary-bot.kappa-d8e.workers.dev/setup-webhook
curl https://telegram-summary-bot.kappa-d8e.workers.dev/webhook-info

Code Style & Conventions

TypeScript

  • Strict mode: tsconfig.json에서 strict 활성화
  • 타입 정의: types.ts에 인터페이스 집중 관리
  • any 사용 금지: 불가피한 경우 주석으로 이유 명시

에러 핸들링

// 패턴: try-catch + 사용자 친화적 메시지
try {
  // 작업
} catch (error) {
  console.error('[ServiceName] 작업 실패:', error);
  return '죄송합니다. 일시적인 오류가 발생했습니다.';
}

로깅 규칙

console.log('[ServiceName] 동작 설명');      // 정상 동작
console.error('[ServiceName] 에러 설명:', error);  // 에러
// wrangler tail로 확인 가능

네이밍

  • 파일: kebab-case.ts (예: openai-service.ts)
  • 함수: camelCase (예: executeFunctionCall)
  • 상수: UPPER_SNAKE_CASE (예: SUMMARY_THRESHOLD)
  • 타입/인터페이스: PascalCase (예: TelegramUpdate)

Testing

현재 테스트 스크립트 없음 - 수동 테스트 필수

로컬 테스트 절차

# 1. 로컬 D1 초기화 (최초 1회)
npm run db:init:local

# 2. 로컬 서버 실행
npm run dev

# 3. 다른 터미널에서 테스트 요청
curl -X POST http://localhost:8787/webhook \
  -H "Content-Type: application/json" \
  -H "X-Telegram-Bot-Api-Secret-Token: test-secret" \
  -d '{"message":{"chat":{"id":123},"text":"테스트"}}'

배포 후 확인

# 로그 스트리밍
npm run tail

# Webhook 상태 확인
curl https://telegram-summary-bot.kappa-d8e.workers.dev/webhook-info

Troubleshooting

자주 발생하는 에러

증상 원인 해결
D1_ERROR: no such table 스키마 미적용 npm run db:init 실행
401 Unauthorized (OpenAI) API 키 만료/잘못됨 wrangler secret put OPENAI_API_KEY
Webhook 응답 없음 Secret Token 불일치 WEBHOOK_SECRET 재설정 후 /setup-webhook
Function Calling 무한 루프 tool_choice 설정 오류 tool_choice: "auto" 확인
프로필 업데이트 안됨 메시지 20개 미만 /context로 버퍼 수 확인
Email Worker 파싱 실패 SMS 형식 변경 index.ts의 정규식 패턴 확인
AI가 도구 호출 안 함 키워드 미인식 시스템 프롬프트 + 도구 description에 키워드 추가
예치금 최소 금액 제한 Agent 프롬프트 문제 Deposit Agent 프롬프트 수정 (OpenAI API)

디버깅 명령어

# D1 데이터 직접 조회 (로컬)
wrangler d1 execute telegram-conversations --local --command "SELECT * FROM users LIMIT 5"

# D1 데이터 직접 조회 (production) ⚠️ 주의
wrangler d1 execute telegram-conversations --command "SELECT * FROM users LIMIT 5"

Architecture

Message Flow:

Telegram Webhook → Security Validation → Command/Message Router
                                              ↓
                   ┌──────────────────────────┴──────────────────────────┐
                   ↓                                                      ↓
            Command Handler                                    AI Response Generator
            (commands.ts)                                      (openai-service.ts)
                                                                      ↓
                                                              Function Calling
                                                    (weather, search, time, calc, docs)
                                                                      ↓
                                                              Profile System
                                                            (summary-service.ts)

Core Services:

파일 역할 주요 함수
index.ts Worker 진입점, Email Handler fetch(), email()
openai-service.ts AI 응답 + Function Calling generateResponse(), executeFunctionCall()
summary-service.ts 프로필 시스템 updateSummary(), getConversationContext()
deposit-agent.ts 예치금 에이전트 (Assistants API) callDepositAgent(), executeDepositFunction()
security.ts Webhook 보안 validateWebhook(), checkRateLimit()
commands.ts 봇 명령어 handleCommand()
telegram.ts Telegram API sendMessage(), sendTypingAction()

Function Calling Tools (7개):

도구 함수명 외부 API 트리거 키워드
날씨 get_weather wttr.in 날씨
검색 web_search Brave Search ~란, ~뭐야
시간 get_current_time 내장 몇 시, 시간
계산 calculate 내장 계산, +, -, *, /
문서 lookup_docs Context7 문서, 사용법, API
도메인 manage_domain Domain Agent → Namecheap 도메인, 네임서버, WHOIS
예치금 manage_deposit Deposit Agent → D1 입금, 충전, 잔액, 계좌, 송금

Data Layer (D1 SQLite):

테이블 용도 주요 컬럼
users 사용자 telegram_id, username
message_buffer 대화 기록 user_id, role, content
summaries 프로필 user_id, generation, summary
user_deposits 예치금 계정 user_id, balance
deposit_transactions 거래 내역 user_id, amount, status
bank_notifications SMS 파싱 depositor_name, amount, bank

AI Fallback: OpenAI 미설정 시 Workers AI (Llama 3.1 8B) 자동 전환


Key Patterns

Function Calling 추가 방법

// 1. openai-service.ts의 tools 배열에 추가
const tools = [
  // ... 기존 도구들
  {
    type: "function",
    function: {
      name: "new_tool",
      description: "도구 설명",
      parameters: { /* JSON Schema */ }
    }
  }
];

// 2. executeFunctionCall()에 케이스 추가
case 'new_tool':
  return await executeNewTool(args);

프로필 시스템 흐름

메시지 수신 → message_buffer 저장 (최대 19개)
                    ↓ 20개 도달
            사용자 발언만 추출 → OpenAI 분석
                    ↓
            summaries 테이블 저장 (generation++)
                    ↓
            구버전 삭제 (최근 3개만 유지)

Context Enrichment

// getConversationContext() 반환값 구조
{
  profile: "이전 프로필 요약",
  recentMessages: [ /* 최근 10개 */ ]
}
// → AI 프롬프트의 system 메시지에 포함

AI 시스템 프롬프트 (summary-service.ts)

- 날씨, 시간, 계산, 검색 등의 요청은 제공된 도구를 사용하세요.
- 예치금, 입금, 충전, 잔액, 계좌 관련 요청은 반드시 manage_deposit 도구를 사용하세요.
  금액 제한이나 규칙을 직접 판단하지 마세요.
- 도메인 관련 요청은 반드시 manage_domain 도구를 사용하세요.
- manage_deposit, manage_domain 도구 결과는 그대로 전달하세요.
  추가 질문이나 "도움이 필요하시면~" 같은 멘트를 붙이지 마세요.

중요: 메인 AI가 도구를 호출하지 않고 직접 답변하는 경우:

  1. 시스템 프롬프트에 해당 키워드 추가 (summary-service.ts:252-254)
  2. 도구 description에 키워드 명시 (openai-service.ts tools 배열)

Deposit Agent 프롬프트 수정 방법

# Vault에서 API 키 조회
curl -s -H "X-Vault-Token: hvs.xxx" https://vault.anvil.it.com/v1/secret/data/openai

# Assistant 프롬프트 업데이트
curl -X POST 'https://api.openai.com/v1/assistants/asst_XMoVGU7ZwRpUPI6PHGvRNm8E' \
  -H 'Authorization: Bearer sk-xxx' \
  -H 'OpenAI-Beta: assistants=v2' \
  -d @update-agent.json

Configuration

wrangler.toml 환경변수:

변수 기본값 설명
SUMMARY_THRESHOLD 20 프로필 업데이트 주기 (메시지 수)
MAX_SUMMARIES_PER_USER 3 유지할 프로필 버전 수
DOMAIN_AGENT_ID - 도메인 관리 Assistant ID
DOMAIN_OWNER_ID - 도메인 관리 권한 Telegram ID
DEPOSIT_AGENT_ID - 예치금 관리 Assistant ID
DEPOSIT_ADMIN_ID - 예치금 관리 권한 Telegram ID
BANK_API_SECRET - 입금 알림 API 인증 키 (wrangler secret)
BRAVE_API_KEY - Brave Search API 키 (wrangler secret)

External Integrations

서비스 용도 엔드포인트 주의사항
Context7 문서 조회 context7.com API -
Domain Agent 도메인 관리 OpenAI Assistants asst_MzPFKoqt7V4w6bc0UwcXU4ob
Deposit Agent 예치금 관리 OpenAI Assistants asst_XMoVGU7ZwRpUPI6PHGvRNm8E
Namecheap API 도메인 백엔드 namecheap-api.anvil.it.com 날짜: MM/DD/YYYY → ISO 변환
WHOIS API WHOIS 조회 whois-api-eight.vercel.app ccSLD 미지원
wttr.in 날씨 wttr.in -
Brave Search 검색 api.search.brave.com Free AI 플랜 (2,000/월)
Vault API 키 관리 vault.anvil.it.com -
Gmail 입금 SMS 수신 deposit.anvil@gmail.com Apps Script 연동
Apps Script Gmail → Worker 연동 script.google.com 1분마다 실행, message_id 중복 방지

Deposit System

자동 매칭 흐름:

[시나리오 1: 사용자 먼저]
"홍길동 50000원 입금" → bank_notifications 검색
                              ↓
              매칭 O → confirmed + 잔액↑ | 매칭 X → pending

[시나리오 2: SMS 먼저 - Gmail → Apps Script → Worker]
은행 SMS → Gmail(deposit.anvil@gmail.com) → Apps Script (1분마다)
                                                    ↓
                                    POST /api/bank-notification
                                                    ↓
                                    파싱 → bank_notifications 저장
                                                    ↓
                                    deposit_transactions 검색 (pending)
                                                    ↓
                                    매칭 O → confirmed + 잔액↑ + 사용자/관리자 알림
                                    매칭 X → 저장만 + 관리자 알림

알림 시스템:

이벤트 사용자 알림 관리자 알림
자동 매칭 성공 입금액 + 현재 잔액 입금 정보 + 매칭 완료
매칭 대기 (SMS만) - 입금 정보 + 대기 상태

Gmail → Worker 연동:

  • Gmail 계정: deposit.anvil@gmail.com
  • Apps Script: 1분마다 is:unread 입금 검색 → Worker API 호출
  • 중복 방지: Gmail message_id 기반

API 엔드포인트:

POST /api/bank-notification
Content-Type: application/json

{
  "content": "[Web발신]\n하나,01/16, 23:30\n427******27104\n입금5원\n황병하",
  "messageId": "19bc737b3415596a",
  "secret": "BANK_API_SECRET 값"
}

입금 계좌: 하나은행 427-910018-27104 (주식회사 아이언클래드)

  • Vault 경로: secret/companies/ironclad-corp

Deposit Agent 핵심 규칙:

1. 금액 제한 없음: 1원도 입금 가능
2. 입금 신고 시 반드시 입금자명 + 금액 확인 (빠지면 물어보기)
3. "계좌번호 주세요" → get_account_info 호출
4. 자연어 금액 인식: "만원"→10000, "5천원"→5000, "삼만오천원"→35000
5. 즉시 실행: 입금자명+금액 있으면 확인 없이 바로 request_deposit 호출
6. 간편 취소: "취소해줘" → 최근 pending 자동 선택
7. 동시 요청 허용: 기존 pending 있어도 새 입금 신고 가능

Deposit Agent 응답 포맷:

잔액 조회: "현재 잔액: 10,000원"
입금 성공: "입금 확인! 5,000원 충전. 잔액: 15,000원"
입금 대기: "입금 요청 등록! 은행 확인 후 자동 충전됩니다."
거래 내역: "#5: 입금 10원 ✓ (01/17)" (✓확인, ⏳대기, ✗취소)

Deposit Agent 도구:

함수 설명 권한
get_balance 잔액 조회 모든 사용자
get_account_info 입금 계좌 안내 모든 사용자
request_deposit 입금 신고 모든 사용자
get_transactions 거래 내역 모든 사용자
cancel_transaction 입금 취소 모든 사용자
get_pending_list 대기 목록 관리자
confirm_deposit 입금 확인 관리자
reject_deposit 입금 거절 관리자

Domain System

도구 목록:

도구 권한 설명
list_domains 소유자 도메인 목록
get_domain_info 소유자 상세 정보 (만료일 등)
get_nameservers 공개 네임서버 조회
set_nameservers 소유자 네임서버 변경
get_price 공개 TLD 가격 (원화)
check_domains 공개 가용성 확인
whois_lookup 공개 WHOIS 조회

가격 정책: Namecheap 원가 + 13%, 매일 환율 업데이트

권한 체크: user_domains 테이블 verified=1