대화 경로 선택¶
ConversationEngineRouter는 세션마다 sohri 또는 openai_realtime 하나를 선택합니다. 선택
전 조회의 기본값과 PCM 선착 경로는 모두 sohri입니다.
코드의 ConversationEngine과 Sohri Skill Engine은 다른 개념입니다
여기서 ConversationEngine은 Socket Backend 내부의 경로 선택 인터페이스입니다.
SohriConversationEngine은 기본 EPD·DM·TTS 오케스트레이션 어댑터이고, 실제 Sohri Skill
Engine은 Graph Builder가 Skill Runtime을 거쳐 호출합니다.
기본 대화 경로 (sohri)¶
기본 경로는 기존 서비스 조합을 오케스트레이션합니다.
flowchart LR
PCM["PCM 16 kHz s16le"] --> G["AudioInputGate"]
G --> E["EPD 연결/송신"]
E -->|"candidate · confirmed · END+STT"| P["END 처리"]
P --> DB["USER/BOT 저장"]
P --> DM["Graph Builder"]
DM --> SR["Skill Runtime"]
SR --> SE["Sohri Skill Engine"]
DM --> TTS["선택된 TTS"]
TTS --> OUT["오디오 → dialog_response"]
- EPD 연결은 WebSocket 연결 시 만들지 않고 첫 PCM에서 생성합니다.
- EPD가 STT까지 수행합니다. Socket Backend는 END의 텍스트·confidence·음성 경로를 받아 저장·분석·DM 요청에 사용합니다.
- DM 응답은 BOT 메시지와 원본 응답으로 저장된 뒤 TTS와
dialog_response로 전달됩니다. - TTS는 CLOVA, Fish Audio, Inworld, Gemini 어댑터 중 세션 확정값을 사용합니다.
OpenAI Realtime 엔진¶
OpenAI 엔진은 upstream WebSocket을 열고 다음 기능을 한 연결에서 사용합니다.
- 입력 PCM 16 kHz를 24 kHz로 리샘플해
input_audio_buffer.append로 전송 - semantic VAD,
gpt-live-transcribe, 자동 응답 생성과 interrupt realtime_event로 provider 이벤트 전달- 24 kHz raw PCM을
tts_stream_start→ binary PCM →tts_stream_end로 전달 - 완료된 USER/BOT 기록과 오디오·분석을 공통 영속화 경계로 전달
취소 시 활성 응답이 있으면 upstream에 response.cancel을 전송합니다. Gateway가 실제 재생한
길이를 보고하는 realtime_playback_truncated는 upstream
conversation.item.truncate(item_id, content_index=0, audio_end_ms)로 변환됩니다.
WebSocket 경로 선택 계약¶
연결이 수립되면 클라이언트는 첫 PCM을 보내기 전에
conversation_session_update 텍스트 메시지로 대화 경로를 선택할 수 있습니다.
sequenceDiagram
participant C as Client/Gateway
participant W as /sohri WebSocket
participant R as ConversationEngineRouter
C->>W: conversation_session_update(conversationEngine)
W->>R: 경로 설정
R-->>W: 설정 완료
W-->>C: conversation_session_updated
C->>W: Binary PCM
W->>R: 선택된 경로로 PCM 전달
- 선택값은
sohri또는openai_realtime입니다. - 설정 메시지 없이 Binary PCM이 먼저 오면 기본 경로
sohri가 확정됩니다. - 경로는 세션에서 한 번 확정되면 바꿀 수 없습니다.
- OpenAI Realtime 경로는 upstream 준비가 끝난 뒤에만
conversation_session_updated를 반환합니다. - 설정 실패는 WebSocket 오류 응답으로 전달되며 기존 경로로 조용히 폴백하지 않습니다.
비교¶
| 항목 | 기본 경로 (sohri) |
openai_realtime |
|---|---|---|
| VAD/STT | 외부 EPD가 통합 수행 | OpenAI Realtime |
| 대화 생성 | Graph Builder DM; Skill은 Runtime을 거쳐 Sohri Skill Engine 호출 | OpenAI Realtime |
| 음성 생성 | 별도 TTS 프로바이더 | OpenAI native audio |
| 입력 레이트 | 16 kHz PCM | 16 kHz 수신 후 24 kHz 변환 |
| 바지인 | response generation으로 출력 억제 | provider interrupt + response.cancel |
| 재생 절단 | generation으로 잔여 송신 억제 | conversation.item.truncate upstream 전송 |