# 51124 서버 주요 이슈 - ChromaDB 격리 및 OAuth 토큰 갱신 ## 문제 발생일 2025-08-27 ## 작성자 Claude Code ## 문제 1: ChromaDB 사용자 대화 격리 문제 ### 문제 설명 rb8001 서비스에서 ChromaDB 컬렉션 구조와 사용자 데이터 분리 방식 검토 필요 ### 현재 구조 1. **rb8001 방식** - 컬렉션명: `robeing_rb8001_memories` - 모든 사용자 대화가 하나의 컬렉션에 저장 - metadata의 user_id 필드로 구분 2. **기술적 특성** - 메모리 검색 시 필터링 의존 - 벡터 검색 후 메타데이터 필터 적용 - 사용자 간 데이터 논리적 분리 ### 원인 분석 #### rb8001 코드 분석 ```python # /home/admin/ivada_project/rb8001/app/memory/manager.py:40 self.collection_name = f"robeing_{robeing_id}_memories" # /home/admin/ivada_project/rb8001/app/router/router.py:327-336 await self.memory_manager.store_memory( content=f"User: {message}\nAssistant: {response}", metadata={ "user_id": user_id, # metadata에만 저장 "channel_id": channel, "intent": intent, "confidence": confidence }, memory_type="conversation" ) ``` #### rb10508_micro 구조 (비교) ```python # /home/admin/ivada_project/rb10508_micro/app/core/memory/storage.py:88 collection_name = f"{settings.ROBEING_ID}_{username if username else 'default'}_{memory_type}" # 예: rb10508_test_김종태_episodic ``` ### 해결 방안 #### 1. 즉시 적용 가능한 임시 조치 - 메모리 검색 시 user_id 필터링 강화 - `where` 조건에 user_id 필수 포함 #### 2. 근본적 해결책 (권장) rb8001의 MemoryManager 클래스를 rb10508 방식으로 수정: ```python # 수정 전 self.collection_name = f"robeing_{robeing_id}_memories" # 수정 후 def get_collection_name(self, user_id: str, memory_type: str = "conversation"): """사용자별 컬렉션명 생성""" return f"robeing_{self.robeing_id}_{user_id}_{memory_type}" ``` #### 3. 구현 시 고려사항 - 기존 데이터 마이그레이션 필요 - 컬렉션 생성 시점 조정 (사용자별 동적 생성) - 메모리 검색 로직 수정 ### 영향 범위 - **관련 서비스**: rb8001, rb10508_micro - **처리 우선순위**: HIGH - **데이터 구조**: 서비스별 차이 존재 ### 테스트 방법 ```bash # 1. 현재 컬렉션 구조 확인 docker exec -it rb8001 python -c " import chromadb client = chromadb.PersistentClient(path='/app/chroma_db') print(client.list_collections()) " # 2. 특정 사용자 대화만 조회 테스트 curl -X POST http://localhost:8001/api/memory/search \ -H "Content-Type: application/json" \ -d '{ "query": "test", "user_id": "U0925SXQFDK", "limit": 5 }' ``` --- ## 문제 2: ~~skill-email OAuth 토큰 자동 갱신 부재~~ ✅ 해결완료 (2025-08-27) ### 문제 설명 ~~skill-email 서비스의 Gmail OAuth 토큰 자동 갱신 기능 미구현 상태~~ → **2025-08-27 배포 완료**: OAuth 토큰 자동 갱신 구현 및 배포 완료 ### 현상 (해결 전) 1. **토큰 갱신 미구현** - `/skill_email/services/gmail_service.py:62` TODO 주석 확인 - refresh_credentials 함수가 실제 갱신 없이 그대로 반환 2. **auth-server 연동 부재** - auth-server API 호출 코드 전혀 없음 - 파일 시스템에서 토큰 읽기만 수행 (`/auth-server/tokens`) - 토큰 만료 체크 로직 없음 ### 원인 분석 (해결됨) #### ~~현재~~ 해결 전 상태 (2025-08-27 이전) 1. **auth-server (51123)**: ✅ 토큰 갱신 API 구현 완료 - `/api/gmail/refresh/{user_id}` - 토큰 자동 갱신 - `/api/gmail/check/{user_id}` - 토큰 상태 확인 - 2025-08-23 문서에서 구현 확인됨 2. **skill-email (51124)**: ~~❌ auth-server API 미연동~~ → ✅ 자체 갱신 구현 완료 - 2025-08-25 commit `2d175c1`: "이메일 보내기 전 refresh" 구현 - 2025-08-27 배포 완료 #### 해결 방법 (구현됨) - Google OAuth 라이브러리(`google.auth`) 직접 사용 - `creds.refresh(Request())` 호출로 자동 갱신 - 갱신된 토큰은 DB에 자동 저장 - auth-server API 연동 없이 독립적으로 처리 ### ✅ 구현 완료 (2025-08-27) #### 구현된 솔루션 (`/skill_email/services/gmail_service.py:95-108`) ```python # 토큰이 만료되었거나 곧 만료될 경우 자동 refresh if creds and creds.expired and creds.refresh_token: logger.info(f"Refreshing expired token for user: {user_id}") from google.auth.transport.requests import Request creds.refresh(Request()) # Google OAuth 라이브러리가 자동 갱신 # 갱신된 토큰 저장 if hasattr(self.creds_provider, 'save_credentials'): self.creds_provider.save_credentials(user_id, creds) logger.info(f"Refreshed token saved for user: {user_id}") ``` #### 추가 구현 사항 - 401 에러 발생 시 토큰 재갱신 후 재시도 로직 추가 - DBCredentialsProvider에 `save_credentials()` 메서드 구현 완료 - 토큰 갱신 실패 시에도 서비스 계속 진행 (graceful degradation) ### 영향 범위 - **영향받는 서비스**: skill-email - **관련 서비스**: auth-server (51123 서버) - **긴급도**: ~~MEDIUM~~ → ✅ RESOLVED (2025-08-27 해결) ### 테스트 방법 ```bash # 1. 현재 토큰 상태 확인 (skill-email에서) docker exec -it skill-email python -c " from services.db_credentials_provider import DBCredentialsProvider provider = DBCredentialsProvider() creds = provider.get_credentials('U0925SXQFDK') print(f'Token expiry: {creds.expiry if creds else None}') " # 2. auth-server의 토큰 상태 확인 API (이미 구현됨) curl http://192.168.219.45:3000/api/gmail/check/U0925SXQFDK # 3. auth-server의 토큰 갱신 API 테스트 (이미 구현됨) curl -X POST http://192.168.219.45:3000/api/gmail/refresh/U0925SXQFDK ``` ## 개선 방향 1. **데이터 구조**: 사용자별 컬렉션 분리 검토 2. **서비스 표준화**: rb8001과 rb10508 구조 통일 검토 3. **코드 관리**: TODO 항목 추적 및 구현 4. **토큰 관리**: OAuth 토큰 자동 갱신 체계 구축 ## 참고 문서 - rb10508_micro 메모리 구조: `/home/admin/ivada_project/rb10508_micro/app/core/memory/storage.py` - rb8001 메모리 관리자: `/home/admin/ivada_project/rb8001/app/memory/manager.py` - skill-email Gmail 서비스: `/home/admin/ivada_project/skill_email/services/gmail_service.py` - auth-server 토큰 디렉토리: `/home/admin/auth-server/tokens` ## 업데이트 이력 - 2025-08-27: 초기 문서 작성 - ChromaDB 격리 문제 (Claude Code) - 2025-08-27: skill-email OAuth 토큰 자동 갱신 문제 추가 (Claude Code) - 2025-08-27: skill-email OAuth 토큰 자동 갱신 해결 완료 및 배포 (Claude Code)