portal-backend 포트폴리오 노트
메인 인덱스 | CCG-Platform | 오버뷰 | GitHub
이 문서는 제가
portal-backend레포를 조금 더 길게 설명하려고 남긴 심층 메모입니다. 빠르게 훑어보실 때는 오버뷰부터 보시고, 구현 판단이나 한계까지 보고 싶으실 때 이 문서로 내려오시면 됩니다.
왜 이 레포를 먼저 설명하는가
portal-backend는 프로덕션 백엔드를 어떤 시각으로 읽고 설명하는지 보여드리기 좋은 레포입니다. 인증, 결제, 워크스페이스 라이프사이클, 관리자 패널, 비동기 작업이 한 곳에 모여 있어서 운영 백엔드의 구조를 정리하기에 적합합니다.
제가 맡은 범위
- CCGP 팀장 역할
- Front와 DB 설계를 제외한 대부분의 구현
- 운영 백엔드, Pod 관리 흐름, 인프라 연결부 중심 구현
이 레포에서 드러나는 점
- 단순 CRUD 서버가 아니라 운영 백엔드 전체를 설계하고 구현하는 관점을 갖고 있다는 점
- Kubernetes 기반 워크스페이스 플랫폼에서 백엔드가 어떤 책임을 가져야 하는지 설명할 수 있다는 점
- 구현 결과뿐 아니라 남은 제약의 원인도 함께 추적했다는 점
프로젝트 개요
이 문서는 제가 portal-backend를 포트폴리오에서 설명할 때 쓰는 기준 정리입니다. portal-backend는 CCGP (Cloud Container Gaming Platform)의 핵심 백엔드 시스템으로, FastAPI 기반으로 구축되었고 컨테이너 게이밍 워크스페이스 관리, 결제 처리, 사용자 인증 같은 주요 기능을 맡고 있습니다.
1. 기능 (Functions)
1.1 자동-발견 기반 API 라우트 시스템
-
동적 라우트 마운팅:
src/server.py의get_sub_applications_mount()함수는 파일 시스템을 스캔하여 자동으로 API 버전(v1, v2 등)과 서비스 라우트를 탐색하고 마운트합니다. 새로운 API 모듈을 추가할 때__init__.py에router만 정의하면 별도의 서버 재시작 없이 자동으로 인식됩니다. -
서비스 자동 등록:
src/application/api/v1/__init__.py는service폴터의 각 모듈에서 라우터를 자동으로 수집하여 메인 라우터에 포함시킵니다. 이를 통해 auth, workspace, transaction, product 등의 서비스를 선언적으로 등록할 수 있습니다. -
환경별 라우트 제어:
__EXCLUDING_ROUTE__플래그를 통해 특정 환경(예: production)에서는 특정 라우트를 제외할 수 있는 유연한 구조를 제공합니다. 이는 개발 환경에서만 필요한 디버그 엔드포인트를 관리하는 데 유용합니다.
1.2 사용자 인증 및 권한 관리 시스템
-
fastapi-users 통합 인증:
src/application/api/v1/service/auth/auth_service.py는 fastapi-users 라이브러리를 확장하여 JWT 기반 인증, OAuth2, 이메일 검증, 비밀번호 재설정 등의 기능을 제공합니다. UserManager 클래스는 각 사용자 액션(등록, 로그인, 검증 등)에 대한 후처리 로직을 커스터마이징할 수 있는 8개의 라이프사이클 메서드를 구현했습니다. -
Redis 기반 세션 관리:
src/application/api/dependencies.py는 Redis를 활용한 세션 전략(RedisStrategy)을 구현하여 토큰 블랙리스팅, 세션 만료, 분산 환경에서의 세션 공유를 지원합니다. 토큰의 유효 기간은 환경설정에서 동적으로 조정 가능합니다. -
역할 기반 접근 제어:
current_active_user,current_superuser등의 FastAPI 의존성 주입 함수를 통해 엔드포인트별로 세분화된 권한 체크를 수행할 수 있습니다. 검증된 사용자, 활성 사용자, 관리자 등 다양한 권한 레벨을 지원합니다.
1.3 컨테이너 워크스페이스 라이프사이클 관리
-
Pod Controller 연동:
src/application/api/v1/service/workspace/workspace_service.py는 Pod Controller 서비스(POD_CONTROLLER_SERVICE)와 HTTP 통신하여 컨테이너 워크스페이스의 생성, 조회, 삭제를 관리합니다. aiohttp를 사용한 비동기 HTTP 클라이언트로 외부 서비스 호출의 성능을 최적화했습니다. -
워크스페이스 메타데이터 관리: 데이터베이스에는 워크스페이스의 대여 정보(
ContainerRentals)를 저장하고, 실제 컨테이너 실행은 Pod Controller에 위임하는 하이브리드 아키텍처를 채택했습니다. 이를 통해 비즈니스 로직과 인프라 관리를 분리했습니다. -
에러 처리 및 복구:
_handle_response()헬퍼 함수를 통해 Pod Controller의 응답을 일관되게 처리하며, 2xx 응답과 에러 응답을 구분하여 적절한 예외를 발생시킵니다. 이는 API의 안정성과 클라이언트에게 명확한 에러 메시지를 제공합니다.
1.4 분당 과금 기반 결제 시스템
-
실시간 과금 처리:
src/infrastructure/celery/tasks/process_rental_billing_task.py는 1분마다 실행되는 Celery 태스크로, 활성화된 대여 건의 과금을 자동으로 처리합니다. 사용자 잔액에서 분당 요금(price_per_min)을 차감하고, 잔액 부족 시 자동으로 워크스페이스를 종료합니다. -
트랜잭션 이력 관리: 모든 과금 내역은
Transactions테이블에 기록되어 투명한 결제 이력을 제공합니다. 과금(charge), 충전(deposit) 등 다양한 트랜잭션 타입을 지원하며, 특정 대여 건과 연결된 과금 내역을 추적할 수 있습니다. -
비동기 알림 시스템:
send_mail_taskCelery 태스크를 통해 비밀번호 변경, 이메일 검증, 환영 메일 등의 이메일 알림을 비동기로 발송합니다. 이는 메인 API 응답 시간에 영향을 주지 않으면서도 사용자 경험을 향상시킵니다.
1.5 제품 카탈로그 관리
-
유연한 리소스 정의:
ContainerResources모델은 JSON 타입의resource필드를 통해 CPU, GPU, 메모리 등의 사양을 유연하게 정의할 수 있습니다. 이는 다양한 컨테이너 스펙을 하나의 테이블에서 관리할 수 있게 해줍니다. -
소프트 삭제 지원:
delete_product()는 실제 레코드를 삭제하는 대신deleted_at필드를 업데이트하는 소프트 삭제를 수행합니다. 이는 실수로 삭제된 데이터를 복구하거나, 삭제 이력을 유지해야 하는 감사 요구사항을 충족합니다. -
페이징 및 필터링:
get_list_products()는 offset/limit 기반 페이징과 다중 필터링을 지원하여 대용량 제품 목록을 효율적으로 조회할 수 있습니다.
1.6 관리자 패널 (Starlette Admin)
-
자동 관리 인터페이스:
src/utils/starlette_admin/admin_panel.py는 Starlette Admin을 활용하여 데이터베이스 모델(User, ContainerResources, ContainerRentals, Transactions)에 대한 CRUD 인터페이스를 자동으로 생성합니다. 커스텀 뷰(UserView,ProductView등)를 통해 특정 모델의 표시 방식을 조정할 수 있습니다. -
통합 인증: CustomAuthProvider를 통해 관리자 패널에 대한 접근을 제어하며, 일반 사용자 인증 시스템과 통합되어 있습니다.
-
외부 링크 통합: Swagger UI, ReDoc 등의 API 문서 링크를 관리자 패널에 직접 포함하여 개발자 경험을 향상시킵니다.
2. 특징 (Characteristics)
2.1 계층형 아키텍처 및 관심사 분리
-
명확한 레이어 구분:
- Presentation Layer:
application/api/- FastAPI 라우트와 스키마 정의 - Service Layer:
application/api/v1/service/*/*_service.py` - 비즈니스 로직 - Repository Layer:
crud/base_crud.py- 데이터 접근 로직 - Infrastructure Layer:
infrastructure/- 데이터베이스, Celery, Redis, 외부 API 연동
- Presentation Layer:
-
제네릭 CRUD 구현:
BaseRepository클래스는 Python 제네릭(Generic[ModelType])을 활용하여 모든 모델에 대해 동일한 CRUD 인터페이스를 제공합니다.async_get_list(),async_create(),async_update()등의 메서드는 타입 안전성을 보장하면서 코드 중복을 제거했습니다. -
동기/비동기 듀얼 지원:
BaseRepository는 동기 메서드(get_list,create,update)와 비동기 메서드(async_get_list,async_create,async_update)를 모두 제공하여, Celery 워커(동기)와 FastAPI 엔드포인트(비동기) 모두에서 재사용할 수 있습니다.
2.2 고급 로깅 및 모니터링 시스템
-
Loguru 기반 구조화 로깅:
src/core/logger.py는 표준 logging 모듈을 Loguru로 인터셉트하여 일관된 로그 형식과 색상화된 콘솔 출력을 제공합니다.InterceptHandler를 통해 기존 라이브러리들의 로그도 Loguru로 통합합니다. -
파일 기반 로그 관리: 로거 이름별로 별도의 로그 파일을 생성하며, 파일 크기 기반 로테이션(10MB)과 백업 개수 제한(5개)을 통해 디스크 공간을 효율적으로 관리합니다. 로그 파일은 gzip으로 압축되어 저장됩니다.
-
Apprise 통합 알림: ERROR 레벨 이상의 로그는 자동으로 Apprise를 통해 외부 알림 채널(Discord, Slack, Telegram 등)로 전송될 수 있습니다. 이는 운영 환경에서 치명적인 문제를 즉시 인지할 수 있게 해줍니다.
-
요청/응답 로깅 미들웨어:
LoggingMiddleware는 모든 HTTP 요청의 메서드, 경로, 상태 코드, 실행 시간을 자동으로 로깅하여 성능 모니터링과 디버깅을 용이하게 합니다. -
선택적 프로파일링: YappiProfileMiddleware는 환경변수(
YAPPI_PROFILE_ENABLE)에 따라 조건부로 활성화되어, 성능 병목 지점을 식별할 수 있는 상세한 프로파일링 데이터를 수집합니다.
2.3 환경별 설정 관리
-
Pydantic Settings 기반 구성:
src/core/config/app_config.py는 Pydantic BaseSettings를 활용하여 환경변수에서 설정을 로드하며, 타입 검증과 기본값 제공을 통해 설정 오류를 런타임에 방지합니다. -
pyproject.toml 연동: 애플리케이션 메타데이터(이름, 버전, 설명)는
pyproject.toml에서 동적으로 로드하여 단일 소스 원칙을 준수합니다. 환경변수로 오버라이드 가능하여 유연한 배포를 지원합니다. -
데이터베이스 Read/Write 분리:
dependencies.py에서 writer와 reader 데이터베이스 엔진을 분리하여 향후 읽기/쓰기 분리 아키텍처로의 확장을 준비했습니다. -
환경별 문서 노출 제어: Production 환경에서는 Swagger UI, ReDoc, OpenAPI JSON 엔드포인트를 비활성화하여 API 스키마 노출을 방지하고 보안을 강화합니다.
2.4 Celery 기반 비동기 작업 처리
-
주기적 과금 작업:
schedule_billing_checks_task는 60초 간격으로 실행되는 Celery Beat 스케줄러를 통해 모든 활성 대여 건에 대한 과금을 체크하고 필요 시process_rental_billing태스크를 큐에 추가합니다. -
데이터베이스 트랜잭션 관리:
create_sync_session_context컨텍스트 매니저는 Celery 태스크에서 데이터베이스 세션의 생명주기를 관리하며, 자동 커밋/롤백을 보장하여 데이터 일관성을 유지합니다. -
SELECT FOR UPDATE 락: 과금 처리 시
with_for_update()를 사용하여 동시성 문제를 방지하고, 동일한 대여 건에 대한 중복 과금을 막습니다.
2.5 타입 안전성 및 코드 품질
-
Pydantic V2 스키마: 모든 API 요청/응답은 Pydantic V2 기반의 스키마로 정의되어 런타임 타입 검증과 자동 문서화를 제공합니다.
model_validate()와model_dump()메서드를 통해 일관된 직렬화/역직렬화를 수행합니다. -
SQLAlchemy 2.0 ORM:
Mapped타입 힌트와mapped_column을 사용하여 모델 정의에 타입 안전성을 적용했습니다. 관계 설정(relationship)도 타입 힌트를 통해 IDE 자동완성을 지원합니다. -
Pre-commit 훅:
pyproject.toml에 정의된 개발 의존성(isort, ruff, bandit, pylint)과 pre-commit 훅을 통해 코드 포맷팅, 보안 검사, 린팅을 자동화하여 코드 품질을 유지합니다.
2.6 예외 처리 및 에러 응답 표준화
-
커스텀 예외 계층:
APIClientError예외 클래스는 외부 API 호출 실패 시 일관된 에러 정보(status_code, detail)를 포함하여 상위 레이어에서 적절한 HTTP 응답으로 변환할 수 있게 합니다. -
전역 예외 핸들러: FastAPI 앱 레벨의
@app.exception_handler(Exception)는 처리되지 않은 모든 예외를 잡아 500 응답으로 변환하고 로깅하여 서버 크래시를 방지합니다. -
HTTP 상태 코드 활용:
_handle_response()는 FastAPI의status모듈 상수(HTTP_204_NO_CONTENT, HTTP_500_INTERNAL_SERVER_ERROR 등)를 사용하여 의미 있는 HTTP 응답을 생성합니다.
3. 부족한 점 (Limitations)
3.1 테스트 인프라 부재
-
테스트 코드 미존재: 프로젝트 전체에 pytest나 unittest 기반의 테스트 코드가 없습니다.
tests/디렉토리가 존재하지 않으며, 단위 테스트, 통합 테스트, E2E 테스트 모두 부재합니다. 이는 리팩토링 시 회귀 버그 발생 위험을 높이고, CI/CD 파이프라인에서 품질 게이트를 설정할 수 없습니다. -
테스트용 DB/Redis 설정 없음: 테스트 환경을 위한 격리된 데이터베이스나 mock Redis 설정이 없어, 로컬 개발 환경의 데이터를 오염시킬 위험이 있습니다.
-
의존성 주입 테스트 미흡: FastAPI의
Depends를 사용하는 의존성 주입 로직을 테스트하기 위한 fixture나 override 메커니즘이 구축되지 않았습니다.
3.2 API 문서화 및 버전 관리 미흡
-
OpenAPI 스키마 불완전: Pydantic 스키마는 정의되어 있으나, 엔드포인트별로
summary,description,response_model등의 FastAPI 문서화 데코레이터가 일관되게 적용되지 않았습니다. 일부 라우트에는 태그만 있고 상세 설명이 부족합니다. -
API 버전 관리 전략 부재: 현재 v1 API만 존재하지만, 향후 v2로의 마이그레이션을 위한 전략(URI versioning vs Header versioning, deprecation 정책 등)이 문서화되지 않았습니다.
-
스키마 문서화 누락: Pydantic 스키마의 필드별
Field(description=...)정의가 거의 없어, Swagger UI에서 필드의 의미를 파악하기 어렵습니다.
3.3 에러 처리 및 복구 메커니즘 취약점
-
세분화된 예외 부재: 현재는
APIClientError하나의 예외 클래스로 대부분의 에러를 처리하고 있어, 클라이언트가 에러 유형에 따라 다른 처리를 하기 어렵습니다. 예: ValidationError, NotFoundError, ConflictError 등의 세분화가 필요합니다. -
재시도 로직 없음: Pod Controller나 SMTP 서버 등 외부 서비스 호출 시 네트워크 일시 장애에 대응하는 exponential backoff 재시도 로직이 없습니다.
requests.delete()호출이 실패하면 해당 워크스페이스는 과금은 멈췄지만 실제로는 종료되지 않는 불일치 상태가 발생할 수 있습니다. -
트랜잭션 롤백 검증 부족: Celery 태스크에서 예외 발생 시 롤백은 수행되지만, 이미 외부 서비스에 호출한 작업(Pod 삭제 등)은 되돌릴 수 없는 eventual consistency 문제가 있습니다.
3.4 보안 강화 필요
-
Rate Limiting 부재: API 엔드포인트에 대한 요청 빈도 제한(rate limiting)이 구현되어 있지 않아, brute-force 공격이나 DDoS에 취약합니다. 로그인 엔드포인트에 대한 보호가 특히 필요합니다.
-
CORS 설정 완화: 현재 CORS 설정(
allow_origin_regex=r"https?://(.+\.)?ccgp\.dev")은 서브도메인을 허용하지만,allow_credentials=True와 함께 사용될 때 보안 위험이 있습니다. 정확한 origin 목록을 명시하는 것이 더 안전합니다. -
SQL Injection 가능성:
_apply_filters()메서드에서 사용자 입력을 직접 getattr로 변환하여 사용하는데, 이는 모델 속성만 허용하는 화이트리스트 검증이 없어 잠재적인 보안 위험이 있을 수 있습니다. -
비밀번호 정책 미흡: fastapi-users의 기본 설정을 사용하므로, 최소 길이, 복잡도 요구사항, 이전 비밀번호 재사용 방지 등의 정책이 없습니다.
3.5 확장성 및 운영 한계
-
단일 데이터베이스 의존: 현재는 단일 PostgreSQL 인스턴스를 사용하며, read replica나 샤딩 전략이 없어 데이터베이스가 병목이 될 수 있습니다.
-
Celery Worker 모니터링 제한: Flower가 의존성에 포함되어 있으나, 프로덕션 환경에서의 worker health check, dead letter queue, 태스크 재처리 전략 등이 구현되지 않았습니다.
-
로그 집계 부재: 파일 기반 로깅만 제공하며, ELK 스택이나 CloudWatch 같은 중앙 집계 시스템으로의 연동을 위한 구조화된 로그(JSON 포맷) 출력이 없습니다.
3.6 실시간 기능 부재
-
WebSocket 미지원: 현재 모든 통신은 HTTP 요청/응답 기반으로, 실시간 알림(워크스페이스 상태 변경, 잔액 부족 경고 등)을 위한 WebSocket이나 Server-Sent Events(SSE)가 구현되어 있지 않습니다.
-
웹훅 시스템 없음: 외부 시스템(Pod Controller, 결제 게이트웨이)으로부터의 이벤트 수신을 위한 웹훅 엔드포인트가 없어, 폴링 방식으로 상태를 확인해야 합니다.
4. 개선 방향 (Improvements)
4.1 테스트 인프라 구축
-
단위 테스트 스위트 도입: pytest와 pytest-asyncio를 사용하여 서비스 레이어와 CRUD 레이어에 대한 단위 테스트를 작성합니다.
pytest-mock으로 외부 의존성(Pod Controller, SMTP)을 모킹하고,pytest-cov로 80% 이상의 커버리지를 목표로 합니다. -
통합 테스트 환경:
testcontainers라이브러리를 사용하여 테스트용 PostgreSQL과 Redis 컨테이너를 자동으로 생성하는 fixture를 구축합니다.conftest.py에 공통 설정을 정의하여 모든 테스트에서 재사용합니다. -
API 엔드포인트 테스트: FastAPI의
TestClient와AsyncClient를 사용하여 각 엔드포인트의 성공/실패 시나리오를 테스트합니다. 인증이 필요한 엔드포인트는dependency_overrides를 사용하여 테스트용 사용자로 주입합니다. -
Celery 태스크 테스트:
celery.contrib.testing을 사용하여 Celery 태스크의 비즈니스 로직을 테스트하고, 모킹을 통해 데이터베이스와 외부 API 호출을 검증합니다.
4.2 API 문서화 및 버전 관리 개선
-
OpenAPI 스키마 강화: 모든 Pydantic 스키마에
Field(description=..., example=...)를 추가하여 Swagger UI에서 필드의 의미와 예시 값을 명확히 표시합니다. 엔드포인트 데코레이터에summary,description,response_description을 추가합니다. -
API 버전 관리 전략 수립: URI 기반 버전 관리(
/api/v1/,/api/v2/)를 유지하되, 하위 호환성을 깨는 변경 시 명확한 deprecation 정책을 문서화합니다.X-API-Version헤더를 통한 클라이언트 버전 협상도 고려합니다. -
API 변경 로그 관리:
CHANGELOG.md나API_CHANGES.md를 유지하여 버전 간 변경 사항을 문서화하고, 마이그레이션 가이드를 제공합니다.
4.3 에러 처리 및 복구 메커니즘 강화
-
예외 계층 구조화:
src/core/exceptions.py에 다음과 같은 예외 클래스를 추가합니다:NotFoundError(404)ValidationError(422)ConflictError(409)ExternalServiceError(503)InsufficientBalanceError(402)
-
재시도 로직 구현:
tenacity라이브러리를 사용하여 Pod Controller 호출과 SMTP 발송에 exponential backoff 재시도 로직을 추가합니다. 일시적인 네트워크 오류에 대한 복원력을 높입니다. -
Dead Letter Queue: Celery 태스크 실패 시 자동 재시도 횟수를 제한하고, 최종 실패한 태스크는 dead letter queue에 저장하여 수동 조사가 가능하게 합니다.
-
Saga 패턴 적용: 워크스페이스 생성 → 과금 시작의 분산 트랜잭션에 Saga 패턴을 적용하여, 각 단계별 보상 작업(compensating action)을 정의하고 eventual consistency를 관리합니다.
4.4 보안 강화
-
Rate Limiting 구현:
slowapi라이브러리를 사용하여 IP 기반 및 사용자 기반 rate limiting을 구현합니다. 특히 로그인, 비밀번호 재설정 엔드포인트에 strict limit(5회/분)을 적용합니다. -
CORS 설정 강화: 정확한 origin 목록을
config.ALLOWED_ORIGINS로 관리하고, production 환경에서는 와일드카드나 정규식 대신 명시적인 origin을 사용합니다. -
입력 검증 강화:
_apply_filters()에 허용된 필드 목록(화이트리스트)을 추가하여, 존재하지 않는 모델 속성에 대한 접근을 방지합니다. Pydantic 스키마에서도constr(),conint()등으로 더 엄격한 검증을 적용합니다. -
보안 헤더 추가:
secure.py미들웨어를 추가하여 HSTS, CSP, X-Frame-Options, X-Content-Type-Options 등의 보안 헤더를 모든 응답에 포함시킵니다. -
비밀번호 정책 강화: fastapi-users의
password_helper를 커스터마이징하여 최소 12자, 대소문자+숫자+특수문자 포함, 이전 5개 비밀번호 재사용 방지 정책을 적용합니다.
4.5 확장성 및 성능 개선
-
데이터베이스 Read Replica 활용:
dependencies.py의 reader 엔진을 활성화하여 읽기 쿼리를 read replica로 분산시킵니다. 읽기 작업이 많은 엔드포인트(get_list_products,get_my_rentals)에서get_read_async_session을 사용합니다. -
캐싱 레이어 도입: Redis를 활용하여 제품 목록, 사용자 세션 등의 데이터를 캐싱합니다.
fastapi-cache나cashews라이브러리를 사용하여 데코레이터 기반 캐싱을 적용합니다. -
구조화된 로깅: JSON 포맷의 로그 출력을 지원하여 ELK 스택이나 Datadog으로의 연동을 용이하게 합니다.
structlog나 Loguru의 JSON 포맷터를 사용합니다. -
Health Check 엔드포인트 강화: 현재는 단순히
{"status": "OK"}를 반환하지만, 데이터베이스 연결, Redis 연결, Pod Controller 연결 상태를 포함한 상세한 health check를 구현합니다. Kubernetes 환경에서 readiness/liveness probe에 활용할 수 있습니다.
4.6 실시간 기능 추가
-
WebSocket 구현: FastAPI의 WebSocket 기능을 사용하여 실시간 알림 시스템을 구축합니다. 사용자별 웹소켓 연결을 관리하고, 워크스페이스 상태 변경, 잔액 부족 경고, 과금 알림 등을 실시간으로 푸시합니다.
-
웹훅 시스템: 외부 시스템(Pod Controller)으로부터의 이벤트를 수신하는 웹훅 엔드포인트를 구현합니다. 워크스페이스 종료, 리소스 변경 등의 이벤트를 받아 실시간으로 데이터베이스를 업데이트합니다.
-
Server-Sent Events(SSE): 대체로 WebSocket이 더 유연하지만, 단방향 알림(서버→클라이언트)만 필요한 경우 SSE를 고려할 수 있습니다. HTTP 기반이므로 방화벽 친화적입니다.
4.7 운영 및 모니터링 개선
-
메트릭 수집:
prometheus-fastapi-instrumentator를 도입하여 요청 지연 시간, 에러율, 처리량 등의 메트릭을 Prometheus 형식으로 노출합니다. Grafana 대시보드와 연동하여 시각화합니다. -
분산 추적: OpenTelemetry를 사용하여 요청이 여러 서비스(Portal Backend → Pod Controller → Database)를 거치는 과정을 추적합니다. 성능 병목 지점과 에러 발생 지점을 시각적으로 파악할 수 있습니다.
-
Circuit Breaker 패턴: Pod Controller 같은 외부 서비스에 Circuit Breaker를 적용하여, 해당 서비스가 다운되었을 때 빠른 실패(fail-fast)하고, 복구되었을 때 자동으로 재시도하도록 합니다.
-
Graceful Shutdown: Uvicorn의 graceful shutdown을 활용하여, 진행 중인 요청을 완료한 후 프로세스를 종료하도록 합니다. Kubernetes 환경에서 rolling update 시 요청 손실을 방지합니다.
4.8 마이크로서비스 아키텍처 검토
-
도메인 분리 평가: 현재는 모놀리식 구조이지만, 사용자 인증, 과금, 워크스페이스 관리를 별도 서비스로 분리하는 것을 장기적으로 검토합니다. 특히 과금 시스템은 독립적인 배포 주기와 확장이 필요할 수 있습니다.
-
API Gateway 도입: 마이크로서비스로 전환 시 Kong, Ambassador 등의 API Gateway를 도입하여 인증, rate limiting, 라우팅을 중앙에서 관리합니다.
-
이벤트 기반 아키텍처: Apache Kafka나 AWS SNS/SQS를 사용하여 서비스 간 느슨한 결합을 구현합니다. 예: “워크스페이스 생성됨” 이벤트를 발행하면 과금 서비스가 이를 구독하여 과금을 시작합니다.
결론
portal-backend는 FastAPI와 SQLAlchemy 2.0을 기반으로 한 현재 사용한 Python 백엔드 아키텍처를 잘 다루는 프로젝트입니다. 자동 라우트 디스커버리, 계층형 아키텍처, 제네릭 CRUD, Celery 기반 비동기 처리 등 다양한 고급 패턴을 적절히 활용하고 있습니다.
그러나 테스트 부재, API 문서화 미흡, rate limiting 부재 등 프로덕션 환경에서 필수적인 요소들이 누락되어 있습니다. 특히 테스트 인프라 구축과 보안 강화는 즉시 진행해야 할 우선순위 높은 작업입니다.
향후 WebSocket 기반 실시간 기능, 구조화된 로깅, 메트릭 수집 등을 추가하면 더욱 완성도 높은 클라우드 게이밍 플랫폼 백엔드를 구축할 수 있을 것입니다.