콘텐츠로 이동

실시간 대화 흐름

연결과 정상 턴

아래 흐름은 일반 클라이언트가 WebRTC Gateway에 직접 연결하는 기본 경로입니다. EPD가 STT까지 수행하므로 Socket Backend가 별도 STT 서비스를 다시 호출하지 않습니다.

sequenceDiagram
    autonumber
    participant C as 일반 클라이언트
    participant W as WebRTC Gateway
    participant S as Socket Backend
    participant E as EPD + STT
    participant DB as PostgreSQL
    participant G as Graph Builder
    participant R as Sohri Skill Runtime
    participant K as Skill Engine / 외부 API
    participant T as TTS Provider

    C->>W: WebRTC 연결 + Opus 마이크 오디오
    W->>S: 세션 전용 WSS + PCM 16 kHz
    S->>E: PCM + 재생/입력 제어 상태
    E-->>S: candidate / confirmed
    S-->>W: speech_candidate / speech_started
    W-->>C: 실시간 대화 이벤트
    E-->>S: END + STT + confidence + 음성 참조

    S->>S: 발화 세대·텍스트·처리권 검증
    S->>S: 입력 gate 닫기
    par EPD 기록
        S->>DB: EPD·STT 메타데이터 저장
    and 대화 턴
        S->>DB: USER 메시지 저장
        S-->>W: stt_result / dm_processing
        S->>G: 세션 ID + 사용자 텍스트 + confidence
        G->>G: DialogueState 로드
        par NLU
            G->>G: 규칙 또는 LLM NLU
        and 선택적 Skill
            opt 현재 시나리오 노드에 skill 선언
                G->>R: skill_id + arguments + 제한된 context
                R->>K: 공통 Engine 실행 요청
                K-->>R: 도메인 결과 또는 오류
                R-->>G: 정규화된 skill 결과
            end
        end
        G->>G: NLU·skill 결과 → Policy → NLG
        G-->>S: 응답 텍스트 + 상태/완료 정보
        S->>DB: BOT 메시지·DM 응답 저장
        S->>T: 응답 텍스트 + 음성 설정
        T-->>S: WAV 또는 PCM 스트림
        S-->>W: TTS 오디오 + dialog_response
        W-->>C: Opus 오디오 + 응답 이벤트
    end
    S->>S: 입력 gate 열기 + 처리권 반납

유효한 END는 현재 발화 세대에 속하고 STT 텍스트가 비어 있지 않으며 턴 처리권을 획득해야 합니다. Socket Backend는 유효한 END를 수락한 뒤 다음 PCM 입력을 막고, 현재 응답 출력이 끝난 뒤 gate를 다시 엽니다. 오류나 취소 경로도 finally 성격의 정리에서 gate와 lease를 반납합니다.

Graph Builder 내부

flowchart LR
    I["STT 텍스트·confidence"] --> L["DialogueState 로드"]
    L --> N["규칙 또는 LLM NLU"]
    L --> SK["선택적 Node Skill"]
    N --> P["공통 Policy"]
    P --> X["Executor / NLG"]
    SK --> X
    X --> U["slot·context update"]
    U --> TR["Transition 결정"]
    TR --> H["history 기록"]
    H --> SV["DialogueState 저장"]
    SV --> O["응답·완료 정보"]

같은 세션의 턴은 직렬화되고 서로 다른 세션은 병렬 처리할 수 있습니다. Skill은 일반 대화 executor를 대체하지 않는 pre-NLG 단계이며, 시나리오가 선택한 입력만 전달하고 허용한 결과만 상태에 반영합니다.

영속화와 최종화

sequenceDiagram
    participant X as 종료 트리거
    participant S as Socket Backend
    participant Q as 대기 중 기록
    participant V as Vocal Biomarkers
    participant M as 요약 모델
    participant DB as PostgreSQL

    X->>S: 대화 종료 / DM 완료 / 연결 제거
    S->>S: dialog 단위 single-flight 최종화
    S->>Q: USER/BOT 기록 완료 대기
    par 발화 분석
        S->>V: 확정 발화 오디오/참조
        V-->>S: 분석 결과
        S->>DB: 발화별 지표 저장
    and 일반 대화 요약
        S->>M: 확정 USER/BOT 메시지
        M-->>S: 요약·키워드·대표 정보
        S->>DB: 대화 요약 upsert
    end
    S->>M: 분석과 일반 요약을 반영한 바이오마커 요약
    M-->>S: 대화 단위 요약
    S->>DB: 바이오마커 요약 저장
    S-->>X: 최종화 완료(best effort)
  • USER 메시지는 Graph Builder 호출 전에 저장되고 BOT 메시지는 응답 후 저장됩니다.
  • 출력 취소는 이미 확정된 USER/BOT 기록과 Graph Builder 호출을 롤백하지 않습니다.
  • 분석은 턴 직후 또는 대화 최종화 시점에 실행하도록 배포별로 구성할 수 있습니다.
  • 요약과 분석 입력은 확정 발화를 화이트리스트로 선택해 취소·잔류 오디오가 섞이지 않게 합니다.
  • 최종화와 연결 제거는 멱등이어야 하며, 연결이 닫혀도 DB 후처리는 계속될 수 있습니다.

실패 의미

  • Graph Builder 실패: 현재 턴 오류로 끝내되 입력 gate와 처리권은 반드시 반납합니다.
  • TTS 실패: 텍스트 대화와 저장된 턴은 유지하고 음성 출력만 soft-fail할 수 있습니다.
  • Skill 실패: 오류를 NLG에 전달하고 시나리오 fallback으로 대화를 계속할 수 있습니다.
  • 분석·오디오 보관 실패: 핵심 대화 성공 여부와 분리해 관측 가능한 부가 실패로 기록합니다.

관련 문서