1. 개요

이번 예약 시스템 고도화(Feature)에서 구현 및 개선된 주요 비즈니스 로직들의 E2E(End-to-End) 흐름을 한눈에 파악할 수 있도록 시퀀스 다이어그램으로 정리했습니다. 클라이언트(Frontend) 요청부터 컨트롤러, 서비스(비즈니스 로직 및 락 획득), 데이터베이스 상태 변경까지의 전체 생명주기를 시각화했습니다.


2. 수강 예약 (Class Booking) E2E 흐름도

회원이 특정 스케줄에 수강 예약을 요청할 때의 흐름입니다. **비관적 락(Pessimistic Lock)**을 통해 스케줄 정원 및 수강권 잔여 횟수를 안전하게 차감합니다.

sequenceDiagram
    autonumber
    actor User as Client (회원)
    participant API as ClassBookingApiController
    participant Service as ClassBookingService
    participant DB as PostgreSQL (DB)

    User->>API: POST /bookings (스케줄 예약 요청)
    API->>Service: bookClass(userId, scheduleId, ticketId)
    
    rect rgb(240, 248, 255)
        Note over Service,DB: [Transaction 시작]
        Service->>DB: 1. SELECT ClassSchedule FOR UPDATE (비관적 락 획득)
        DB-->>Service: 스케줄 정보 반환
        Service->>Service: 정원 초과 여부 검증 (Capacity Check)
        
        Service->>DB: 2. SELECT Ticket FOR UPDATE (비관적 락 획득)
        DB-->>Service: 수강권 정보 반환
        Service->>Service: 잔여 횟수 및 유효기간 검증
        
        Service->>DB: UPDATE Ticket (잔여 횟수 -1 차감)
        Service->>DB: UPDATE ClassSchedule (예약 인원 +1 증가)
        Service->>DB: INSERT ClassBooking (상태: CONFIRMED)
        Note over Service,DB: [Transaction 커밋 및 락 해제]
    end
    
    Service-->>API: 예약 성공 응답 DTO
    API-->>User: 200 OK (예약 완료)

3. 예약 취소 (Booking Cancellation) E2E 흐름도

회원이 예약을 취소할 때의 흐름입니다. 데드락 방지를 위해 예약 생성 시와 **동일한 순서(ClassSchedule Ticket)**로 락을 획득하며, 멱등성 보장 로직이 포함되어 있습니다.

sequenceDiagram
    autonumber
    actor User as Client (회원)
    participant API as ClassBookingApiController
    participant Service as ClassBookingService
    participant DB as PostgreSQL (DB)

    User->>API: POST /bookings/{bookingId}/cancel (예약 취소 요청)
    API->>Service: cancelBooking(userId, bookingId)
    
    rect rgb(255, 240, 245)
        Note over Service,DB: [Transaction 시작]
        Service->>DB: 예약 정보(Booking) 조회
        DB-->>Service: Booking Entity
        Service->>Service: 멱등성 검증 (이미 CANCELLED 상태인지 확인)
        
        Service->>DB: 1. SELECT ClassSchedule FOR UPDATE (비관적 락)
        Service->>DB: 2. SELECT Ticket FOR UPDATE (비관적 락)
        
        Service->>DB: UPDATE ClassSchedule (예약 인원 -1 감소)
        Service->>DB: UPDATE Ticket (잔여 횟수 +1 복구)
        Service->>DB: UPDATE ClassBooking (상태: CANCELLED)
        Note over Service,DB: [Transaction 커밋 및 락 해제]
    end
    
    Service-->>API: 취소 완료 응답 DTO
    API-->>User: 200 OK (취소 완료)

4. 백그라운드 스케줄러 (No-Show 자동 처리) E2E 흐름도

수업 시작 시간이 지났음에도 출석(ATTENDED) 처리가 되지 않은 CONFIRMED 예약들을 찾아 자동으로 NO_SHOW 상태로 변경하는 백그라운드 스케줄러의 흐름입니다.

sequenceDiagram
    autonumber
    participant Cron as Spring Scheduler (주기적 실행)
    participant Sched as BookingScheduler
    participant DB as PostgreSQL (DB)

    Cron->>Sched: processNoShows() 호출 (예: 매 10분마다)
    
    rect rgb(240, 255, 240)
        Note over Sched,DB: 노쇼 후보 조회 대상: <br/> 수업 시작 후 30분이 지난 CONFIRMED 예약
        Sched->>DB: SELECT ClassBooking WHERE status='CONFIRMED' AND startTime < (NOW - 30분)
        DB-->>Sched: 대상 Booking 리스트 반환
        
        loop 대상 예약 리스트 반복
            Note over Sched,DB: [Transaction 시작]
            Sched->>DB: 대상 Booking 상태 업데이트 (NO_SHOW)
            Note over Sched,DB: (추후 센터 정책에 따른 패널티 차감 로직 연계 예정)
            Note over Sched,DB: [Transaction 커밋]
        end
    end
    
    Sched-->>Cron: 스케줄러 작업 완료