# Event Service 클래스 설계서 ## 1. 개요 ### 1.1 목적 Event Service의 Clean Architecture 기반 클래스 설계를 정의합니다. ### 1.2 설계 원칙 - **아키텍처 패턴**: Clean Architecture - **패키지 그룹**: com.kt.event - **의존성 방향**: Presentation → Application → Domain ← Infrastructure ### 1.3 핵심 특징 - 복잡한 이벤트 생명주기 관리 (DRAFT → PUBLISHED → ENDED) - 상태 머신 패턴 적용 - AI 서비스 비동기 연동 (Kafka) - Content Service 동기 연동 (Feign) - Redis 캐시 활용 --- ## 2. 계층별 구조 ### 2.1 Domain Layer (핵심 비즈니스 로직) #### 2.1.1 Entity **Event (이벤트 집합 루트)** ```java - 책임: 이벤트 전체 생명주기 관리 - 상태: DRAFT, PUBLISHED, ENDED - 비즈니스 규칙: * DRAFT 상태에서만 수정 가능 * 배포 시 필수 데이터 검증 (이벤트명, 기간, 이미지, 채널) * 상태 전이 제약 (DRAFT → PUBLISHED → ENDED) - 관계: * 1:N GeneratedImage (생성된 이미지) * 1:N AiRecommendation (AI 추천안) ``` **AiRecommendation (AI 추천 엔티티)** ```java - 책임: AI가 생성한 이벤트 기획안 관리 - 속성: 이벤트명, 설명, 프로모션 유형, 타겟 고객 - 선택 상태: isSelected (단일 선택) ``` **GeneratedImage (생성 이미지 엔티티)** ```java - 책임: 이벤트별 생성된 이미지 관리 - 속성: 이미지 URL, 스타일, 플랫폼 - 선택 상태: isSelected (단일 선택) ``` **Job (비동기 작업 엔티티)** ```java - 책임: AI 추천, 이미지 생성 등 비동기 작업 상태 관리 - 상태: PENDING, PROCESSING, COMPLETED, FAILED - 진행률: 0~100 (progress) - 결과: Redis 키 (resultKey) 또는 에러 메시지 ``` #### 2.1.2 Enums - **EventStatus**: DRAFT, PUBLISHED, ENDED - **JobStatus**: PENDING, PROCESSING, COMPLETED, FAILED - **JobType**: AI_RECOMMENDATION, IMAGE_GENERATION #### 2.1.3 Repository Interfaces - **EventRepository**: 이벤트 조회, 필터링, 페이징 - **AiRecommendationRepository**: AI 추천 관리 - **GeneratedImageRepository**: 이미지 관리 - **JobRepository**: 작업 상태 관리 --- ### 2.2 Application Layer (유스케이스) #### 2.2.1 Services **EventService (핵심 오케스트레이터)** ```java 책임: - 이벤트 전체 생명주기 조율 - AI 서비스 연동 (Kafka 비동기) - Content 서비스 연동 (Feign 동기) - 트랜잭션 경계 관리 주요 유스케이스: 1. createEvent(): 이벤트 생성 (Step 1: 목적 선택) 2. requestAiRecommendations(): AI 추천 요청 (Step 2) 3. selectRecommendation(): AI 추천 선택 4. requestImageGeneration(): 이미지 생성 요청 (Step 3) 5. selectImage(): 이미지 선택 6. selectChannels(): 배포 채널 선택 (Step 4) 7. publishEvent(): 이벤트 배포 (Step 5) 8. endEvent(): 이벤트 종료 ``` **JobService (작업 관리)** ```java 책임: - 비동기 작업 상태 조회 - 작업 진행률 업데이트 - 작업 완료/실패 처리 주요 유스케이스: 1. createJob(): 작업 생성 2. getJobStatus(): 작업 상태 조회 3. updateJobProgress(): 진행률 업데이트 4. completeJob(): 작업 완료 처리 5. failJob(): 작업 실패 처리 ``` #### 2.2.2 DTOs **Request DTOs** - SelectObjectiveRequest: 목적 선택 - AiRecommendationRequest: AI 추천 요청 (매장 정보 포함) - SelectRecommendationRequest: AI 추천 선택 + 커스터마이징 - ImageGenerationRequest: 이미지 생성 요청 (스타일, 플랫폼) - SelectImageRequest: 이미지 선택 - ImageEditRequest: 이미지 편집 - SelectChannelsRequest: 배포 채널 선택 - UpdateEventRequest: 이벤트 수정 **Response DTOs** - EventCreatedResponse: 이벤트 생성 응답 - EventDetailResponse: 이벤트 상세 (이미지, 추천 포함) - JobAcceptedResponse: 작업 접수 응답 - JobStatusResponse: 작업 상태 응답 - ImageGenerationResponse: 이미지 생성 응답 **Kafka Message DTOs** - AIEventGenerationJobMessage: AI 작업 메시지 - ImageGenerationJobMessage: 이미지 생성 작업 메시지 - EventCreatedMessage: 이벤트 생성 이벤트 --- ### 2.3 Infrastructure Layer (기술 구현) #### 2.3.1 Kafka (비동기 메시징) **AIJobKafkaProducer** ```java 책임: AI 추천 생성 작업 발행 토픽: ai-event-generation-job 메시지: AIEventGenerationJobMessage ``` **AIJobKafkaConsumer** ```java 책임: AI 작업 결과 수신 및 처리 처리: COMPLETED, FAILED, PROCESSING 상태별 분기 수동 커밋: Acknowledgment 사용 ``` **ImageJobKafkaConsumer** ```java 책임: 이미지 생성 작업 결과 수신 처리: 생성된 이미지 DB 저장 ``` **EventKafkaProducer** ```java 책임: 이벤트 생성 이벤트 발행 토픽: event-created 용도: Distribution Service 연동 ``` #### 2.3.2 Client (외부 서비스 연동) **ContentServiceClient (Feign)** ```java 대상: Content Service (포트 8082) API: POST /api/v1/content/images/generate 요청: ContentImageGenerationRequest 응답: ContentJobResponse (Job ID 반환) ``` #### 2.3.3 Config **RedisConfig** ```java 책임: Redis 연결 설정 용도: - AI 추천 결과 임시 저장 - 이미지 생성 결과 임시 저장 - Job 결과 캐싱 ``` --- ### 2.4 Presentation Layer (API) #### 2.4.1 Controllers **EventController** ```java Base Path: /api/v1/events 주요 엔드포인트: 1. POST /objectives - 이벤트 목적 선택 (생성) 2. GET /events - 이벤트 목록 조회 (페이징, 필터링) 3. GET /events/{id} - 이벤트 상세 조회 4. DELETE /events/{id} - 이벤트 삭제 5. POST /events/{id}/publish - 이벤트 배포 6. POST /events/{id}/end - 이벤트 종료 7. POST /events/{id}/ai-recommendations - AI 추천 요청 8. PUT /events/{id}/recommendations - AI 추천 선택 9. POST /events/{id}/images - 이미지 생성 요청 10. PUT /events/{id}/images/{imageId}/select - 이미지 선택 11. PUT /events/{id}/images/{imageId}/edit - 이미지 편집 12. PUT /events/{id}/channels - 배포 채널 선택 13. PUT /events/{id} - 이벤트 수정 ``` **JobController** ```java Base Path: /api/v1/jobs 엔드포인트: 1. GET /jobs/{id} - 작업 상태 조회 ``` --- ## 3. 핵심 플로우 ### 3.1 이벤트 생성 플로우 ``` 1. 목적 선택 (POST /objectives) → Event 생성 (DRAFT 상태) 2. AI 추천 요청 (POST /events/{id}/ai-recommendations) → Job 생성 (AI_RECOMMENDATION) → Kafka 메시지 발행 (ai-event-generation-job) → AI Service 처리 → Kafka 메시지 수신 (결과) → Redis 캐시 저장 → Job 완료 처리 3. AI 추천 선택 (PUT /events/{id}/recommendations) → Redis에서 추천 목록 조회 → 선택 + 커스터마이징 적용 → Event 업데이트 (eventName, description, period) 4. 이미지 생성 요청 (POST /events/{id}/images) → Content Service 호출 (Feign) → Job ID 반환 → 폴링으로 상태 확인 5. 이미지 선택 (PUT /events/{id}/images/{imageId}/select) → Event.selectedImageId 업데이트 → GeneratedImage.isSelected = true 6. 배포 채널 선택 (PUT /events/{id}/channels) → Event.channels 업데이트 7. 이벤트 배포 (POST /events/{id}/publish) → 필수 데이터 검증 → 상태 변경 (DRAFT → PUBLISHED) → Kafka 메시지 발행 (event-created) ``` ### 3.2 상태 머신 다이어그램 ``` DRAFT → publish() → PUBLISHED → end() → ENDED ↑ | | ↓ └─────── (수정 불가) ─────┘ ``` **상태별 제약:** - DRAFT: 모든 수정 가능, 삭제 가능 - PUBLISHED: 수정 불가, 삭제 불가, 종료만 가능 - ENDED: 모든 변경 불가 (읽기 전용) --- ## 4. 비동기 작업 처리 ### 4.1 Job 생명주기 ``` PENDING → start() → PROCESSING → complete() → COMPLETED ↓ fail() → FAILED ``` ### 4.2 작업 유형별 처리 **AI_RECOMMENDATION (AI 추천 생성)** - 발행: AIJobKafkaProducer - 수신: AIJobKafkaConsumer - 결과: Redis 캐시 (추천 목록) - 시간: 10~30초 **IMAGE_GENERATION (이미지 생성)** - 발행: EventService → ContentServiceClient - 수신: ImageJobKafkaConsumer (Content Service에서 발행) - 결과: GeneratedImage 엔티티 (DB 저장) - 시간: 30~60초 --- ## 5. 패키지 구조 ``` com.kt.event.eventservice ├── domain/ │ ├── entity/ │ │ ├── Event.java │ │ ├── AiRecommendation.java │ │ ├── GeneratedImage.java │ │ └── Job.java │ ├── enums/ │ │ ├── EventStatus.java │ │ ├── JobStatus.java │ │ └── JobType.java │ └── repository/ │ ├── EventRepository.java │ ├── AiRecommendationRepository.java │ ├── GeneratedImageRepository.java │ └── JobRepository.java ├── application/ │ ├── service/ │ │ ├── EventService.java │ │ └── JobService.java │ └── dto/ │ ├── request/ │ │ ├── SelectObjectiveRequest.java │ │ ├── AiRecommendationRequest.java │ │ ├── SelectRecommendationRequest.java │ │ ├── ImageGenerationRequest.java │ │ ├── SelectImageRequest.java │ │ ├── ImageEditRequest.java │ │ ├── SelectChannelsRequest.java │ │ └── UpdateEventRequest.java │ ├── response/ │ │ ├── EventCreatedResponse.java │ │ ├── EventDetailResponse.java │ │ ├── JobAcceptedResponse.java │ │ ├── JobStatusResponse.java │ │ ├── ImageGenerationResponse.java │ │ └── ImageEditResponse.java │ └── kafka/ │ ├── AIEventGenerationJobMessage.java │ ├── ImageGenerationJobMessage.java │ └── EventCreatedMessage.java ├── infrastructure/ │ ├── kafka/ │ │ ├── AIJobKafkaProducer.java │ │ ├── AIJobKafkaConsumer.java │ │ ├── ImageJobKafkaConsumer.java │ │ └── EventKafkaProducer.java │ ├── client/ │ │ └── ContentServiceClient.java (Feign) │ ├── client.dto/ │ │ ├── ContentImageGenerationRequest.java │ │ └── ContentJobResponse.java │ └── config/ │ └── RedisConfig.java ├── presentation/ │ └── controller/ │ ├── EventController.java │ └── JobController.java └── config/ ├── SecurityConfig.java ├── KafkaConfig.java └── DevAuthenticationFilter.java ``` --- ## 6. 의존성 방향 ### 6.1 Clean Architecture 계층 ``` Presentation Layer (EventController) ↓ depends on Application Layer (EventService) ↓ depends on Domain Layer (Event, EventRepository) ↑ implements Infrastructure Layer (EventRepositoryImpl, Kafka, Feign) ``` ### 6.2 핵심 원칙 1. **Domain Layer는 외부 의존성 없음** (순수 비즈니스 로직) 2. **Application Layer는 Domain을 조율** (유스케이스) 3. **Infrastructure Layer는 Domain 인터페이스 구현** (기술 세부사항) 4. **Presentation Layer는 Application 호출** (API 엔드포인트) --- ## 7. 주요 설계 패턴 ### 7.1 Domain 패턴 - **Aggregate Root**: Event (경계 내 일관성 보장) - **State Machine**: EventStatus, JobStatus (상태 전이 제약) - **Value Object**: StoreInfo, Customizations (불변 값) ### 7.2 Application 패턴 - **Service Layer**: EventService, JobService (유스케이스 조율) - **DTO Pattern**: Request/Response 분리 (계층 간 데이터 전송) - **Repository Pattern**: EventRepository (영속성 추상화) ### 7.3 Infrastructure 패턴 - **Adapter Pattern**: ContentServiceClient (외부 서비스 연동) - **Producer/Consumer**: Kafka 메시징 (비동기 통신) - **Cache-Aside**: Redis 캐싱 (성능 최적화) --- ## 8. 트랜잭션 경계 ### 8.1 @Transactional 적용 위치 ```java EventService: - createEvent() - 쓰기 - deleteEvent() - 쓰기 - publishEvent() - 쓰기 - endEvent() - 쓰기 - updateEvent() - 쓰기 - requestAiRecommendations() - 쓰기 (Job 생성) - selectRecommendation() - 쓰기 - selectImage() - 쓰기 - selectChannels() - 쓰기 JobService: - createJob() - 쓰기 - updateJobProgress() - 쓰기 - completeJob() - 쓰기 - failJob() - 쓰기 ``` ### 8.2 읽기 전용 트랜잭션 ```java @Transactional(readOnly = true): - getEvent() - getEvents() - getJobStatus() ``` --- ## 9. 보안 및 인증 ### 9.1 인증 방식 - **개발 환경**: DevAuthenticationFilter (Header 기반) - **운영 환경**: JWT 인증 (JwtAuthenticationFilter) ### 9.2 인가 처리 ```java @AuthenticationPrincipal UserPrincipal - userId: 요청자 ID - storeId: 매장 ID 검증: - Event는 userId로 소유권 확인 - EventRepository.findByEventIdAndUserId() 사용 ``` --- ## 10. 에러 처리 ### 10.1 공통 에러 코드 ```java ErrorCode: - EVENT_001: 이벤트를 찾을 수 없음 - EVENT_002: 이벤트 수정/삭제 불가 (상태 제약) - EVENT_003: 선택한 리소스를 찾을 수 없음 - JOB_001: 작업을 찾을 수 없음 - JOB_002: 작업 상태 변경 불가 ``` ### 10.2 예외 처리 ```java Domain Layer: - IllegalStateException (상태 전이 제약 위반) - IllegalArgumentException (비즈니스 규칙 위반) Application Layer: - BusinessException (비즈니스 로직 에러) Infrastructure Layer: - InfraException (외부 시스템 에러) ``` --- ## 11. 테스트 전략 ### 11.1 단위 테스트 ```java Domain Layer: - Event 상태 전이 로직 - 비즈니스 규칙 검증 Application Layer: - EventService 유스케이스 - DTO 변환 로직 ``` ### 11.2 통합 테스트 ```java Infrastructure Layer: - Kafka Producer/Consumer - Feign Client - Redis 캐싱 Presentation Layer: - REST API 엔드포인트 - 인증/인가 ``` --- ## 12. 파일 정보 ### 12.1 다이어그램 파일 - **상세 다이어그램**: `design/backend/class/event-service.puml` - **요약 다이어그램**: `design/backend/class/event-service-simple.puml` ### 12.2 참조 문서 - 공통 컴포넌트: `design/backend/class/common-base.puml` - API 설계서: `design/backend/api/spec/event-service-api.yaml` - 데이터 설계서: `design/backend/database/event-service-schema.sql` --- **작성일**: 2025-10-29 **작성자**: Backend Architect (Claude Code) **버전**: 1.0.0