GPT-Live로 마이그레이션

GPT-Live로 마이그레이션 (Migrate to GPT-Live)

GPT-Live는 듣기와 말하기를 처리해요. 백엔드가 작업을 완료하는 방법과 어떤 도구를 호출할지 결정해요. 기존 도구 구현, 권한 검사, 저장된 작업 기록을 유지하세요. 마이그레이션 중에는 그 백엔드를 GPT-Live에 연결하고, 어떤 지시가 각 모델에 속하는지 결정하세요.

출처: 문서

본문

이 가이드는 예약 어시스턴트를 사용해요. 가용성을 확인하고, 사용자에게 슬롯 확인을 요청한 뒤 예약해요. Getting started의 연결된 세션으로 시작하고, 비교를 위해 기존 애플리케이션의 대표 대화를 보관하세요.

마이그레이션 전에

마이그레이션된 애플리케이션이 보존해야 할 요구사항을 기록하세요.

  • 도구와 비즈니스 규칙: 각 작업의 조건을 포함해 기존 프롬프트, 도구, 워크플로를 나열하세요.
  • 입력 유형: 오디오, 타입 텍스트, 이미지가 애플리케이션의 어디로 들어오는지, 어떤 백엔드가 필요로 하는지 식별하세요. 이미지·시각 컨텍스트 추가 참고.
  • 오디오에 의존하는 결정: 대본의 단어 너머, 원래 소리가 필요한 결정을 식별하세요. 오디오에 의존하는 결정 보존 참고.
  • 발화와 재생: 발화가 시작될 수 있는 시점, 멈춰야 하는 시점, 오디오가 재생되기 전에 끝나야 하는 검사를 지정하세요.
  • 권한과 가드레일: 권한 부여, 확인, 입력·출력 검사와 애플리케이션이 어디서 강제하는지 나열하세요. 가드레일 적응 참고.
  • 지속 상태: 연결 끊김과 새 세션에서도 애플리케이션이 유지해야 할 기록, 작업 진행, 보류 작업을 식별하세요.
  • 기준 대화: 현재 애플리케이션의 대표 대화와 시작 상태, 예상 도구 작업, 최종 애플리케이션 상태, 말한 응답을 저장하세요.

세션 설정은 Getting started, 비교 계획은 음성 에이전트 평가 Cookbook을 사용하세요.

위임 모드 선택하기

누가 백엔드를 실행할지 선택하세요.

  • Responses delegation: 호스팅된 Responses 모델을 구성해 작업을 추론하고 도구를 선택하게 하세요. 애플리케이션이 사용자 지정 함수를 실행하고 결과를 반환해요. 현재 Realtime 모델이 그 함수를 선택한다면 유용한 출발점이에요.
  • Client delegation: 기존 에이전트나 오케스트레이터를 유지하세요. 애플리케이션이 대화 컨텍스트를 제공하고, 작업을 시작하고, 어떤 결과를 GPT-Live로 보낼지 결정해요.

어느 모드든 두 마이그레이션 경로를 지원할 수 있어요. 예를 들어 별도 백엔드 에이전트가 있는 Realtime 애플리케이션은 client delegation으로 그 에이전트를 유지할 수 있어요. 전체 비교는 위임 모드 선택을 참고하세요.

마이그레이션 경로 선택

현재 음성 모델이 도구를 선택한다면 Realtime API에서로 시작하세요. 기존 에이전트를 유지하고 GPT-Live를 음성 인터페이스로 추가한다면 텍스트 에이전트나 체인 파이프라인에서로 시작하세요.

Realtime API에서

GPT-Live 프롬프팅 가이드로 시작하세요. 기존 프롬프트를 session.instructions에 그대로 복사하는 대신 음성 모델과 백엔드로 나눠 넣으세요. 대화 스타일과 위임 지침은 음성 프롬프트에, 상세 워크플로와 도구 사용 지시는 백엔드로 옮기세요.

이전: Realtime 모델이 발화를 처리하고 check_availability, book_appointment 같은 함수를 선택해요. 애플리케이션이 그 함수를 실행하고 결과를 반환해요.

이후: GPT-Live가 발화를 처리하고 작업을 위임해요. 백엔드가 같은 함수를 선택하고, 애플리케이션이 여전히 검증·실행해요. 여기 단계는 Responses delegation을 사용해요. 외부 에이전트를 유지한다면 client 어댑터를 대신 사용하세요.

Responses delegation 작동 방식

delegation.responses에서 백엔드 모델, 지시, 도구를 구성하세요. GPT-Live가 요청에 백엔드 작업이 필요하다고 판단하면 Live 서비스가 그 Responses 모델을 호출하고 관련 대화 컨텍스트를 제공해요. 백엔드가 작업을 추론하고 도구를 선택해요. 애플리케이션이 여전히 사용자 지정 함수를 실행하고, 권한을 강제하고, 결과를 반환해요.

예약 어시스턴트의 경우:

  1. 사용자가 금요일에 어떤 예약이 가능한지 묻고, GPT-Live가 요청을 위임해요.
  2. Responses 백엔드가 check_availability를 요청해요.
  3. 애플리케이션이 함수를 실행하고, 결과를 반환하고, 백엔드 응답을 계속해요.
  4. GPT-Live가 백엔드의 답으로 사용자와 가능한 슬롯을 논의해요.

GPT-Live는 백엔드가 작업하는 동안에도 계속 말할 수 있어요. 백엔드 작업과 오디오 재생을 따로 추적하세요. 작업 상태 업데이트에는 도구 결과를, 말하기 표시기에는 플레이어 상태를 사용해요. 구성과 전체 이벤트 흐름은 Delegation and tools을 참고하세요.

연결·오디오 라이프사이클 적응

Realtime 세션 설정을 GPT-Live 연결 절차로 바꾸세요. 전송의 시작과 오디오 형식을 다시 확인하세요. WebRTC는 미디어 트랙으로 오디오를, 데이터 채널로 JSON 이벤트를 전달해요. 기본 WebSocket은 JSON 이벤트로 오디오를 전달해요.

Realtime 애플리케이션이 호출을 모니터하거나 가드레일을 강제하는 서버 연결을 쓴다면 GPT-Live sideband 연결로 적응하세요. 대화 검사와 재생의 변경은 가드레일 적응을 따르세요.

기존 Realtime 동작 GPT-Live 적응
input_audio_buffer.append로 WebSocket 오디오 전송. session.input_audio.append 전송. 그 audio 필드에 base64 원시 오디오.
response.output_audio.delta의 delta 필드 재생. session.output_audio.delta의 delta 필드를 순서대로 재생.
수동 턴 제어 사용 시 턴을 시작하려면 오디오 커밋이나 응답 생성. 오디오를 연속 스트리밍. GPT-Live가 언제 말할지 결정. 수동 오디오 커밋·음성 턴 트리거 제거.
response.output_audio.done과 response.done으로 오디오 생성·응답 완료 추적. GPT-Live는 각 말한 응답의 끝을 표시하는 이벤트가 없음. 클라이언트에서 재생 추적.
입력 전사 이벤트로 사용자 캡션 표시. session.input_transcript.delta 텍스트를 사용자 캡션에 추가.
response.output_audio_transcript.delta로 어시스턴트 캡션 표시. session.output_transcript.delta 텍스트를 어시스턴트 캡션에 추가.

생성과 재생: 말하기 표시기를 오디오 플레이어에서 구동하세요. 서버가 생성을 끝내도 플레이어에 아직 1초의 오디오가 큐에 있을 수 있어요. Realtime에서 response.output_audio.done은 생성의 끝, response.done은 응답 스트림의 끝을 표시하고, 인터럽션·실패는 response.status로 확인해요. GPT-Live에는 각 말한 응답의 끝에 해당하는 이벤트가 없어요.

캡션: 입력 전사가 활성화되면 Realtime은 conversation.item.input_audio_transcription.delta로 텍스트 조각을, conversation.item.input_audio_transcription.completed로 최종 대본을 보내요. GPT-Live에서는 각 조각을 발신자나 어시스턴트 캡션에 추가하세요. 둘 다 동시에 바뀔 수 있어요. 텍스트를 어떻게 묶을지는 애플리케이션이 결정하고, 재생은 오디오 플레이어로 추적해요. 캡션 표시 참고.

위임된 Responses 작업을 시작·계속하려면 response.create를 쓰세요. GPT-Live는 대화를 들으며 언제 말할지 관리해요. 시작, 인사, 인터럽션, 세션 종료는 세션 관리를 참고하세요.

대화·백엔드 지시 분리

대화 스타일과 위임 지침은 session.instructions로, 비즈니스 규칙과 도구 사용 지시는 delegation.responses.instructions로 옮기세요. 직접 운영하는 백엔드라면 그 규칙을 기존 프롬프트에 두세요.

이전: 단일 Realtime 프롬프트

Help callers book appointments. Speak briefly. Check availability with the tool,
ask the caller to confirm a slot, then book it. Never claim an unverified booking.

이후: GPT-Live 대화 지시

Help callers book appointments. Keep spoken replies brief. Delegate availability
checks and booking requests. Ask the caller to confirm the proposed slot.
Only announce a booking when the backend reports that it succeeded.

이후: 백엔드 지시

Use the appointment tools to check current availability. Before booking, verify
that the caller confirmed the exact slot and still has permission to book it.
Apply the latest correction. Return verified availability, booking, or failure
status with the date, time, and time zone.

도구를 실행하기 전에 애플리케이션에서 확인·권한 검사를 강제하세요. 프롬프트 지시는 모델을 안내할 뿐 그 검사를 강제하지 않아요. 프롬프트 설계는 음성 모델 프롬프팅을 참고하세요.

함수 핸들러 적응

check_availability와 book_appointment의 구현을 유지하세요. 그 정의를 Realtime의 session.tools나 response.tools에서 delegation.responses.tools로 옮기고 Responses 함수 스키마를 사용하세요. 도구 선택 설정도 delegation.responses.tool_choice와 delegation.responses.parallel_tool_calls로 옮기세요. Responses delegation 구성 참고.

함수는 여전히 원래 call_id에 대한 결과를 반환해요. 변하는 것은 핸들러가 호출을 받고 결과를 보내는 위치예요.

단계 Realtime API Responses delegation이 있는 GPT-Live
완료된 함수 호출 수신 response.output_item.done 읽기 response.event 언랩 후 내부 response.output_item.done 읽기
작업 식별·실행 항목의 name, arguments, call_id 읽기, 승인된 핸들러 실행 그 핸들러와 검사 유지. 바깥 delegation_id와 백엔드 응답 ID 를 애플리케이션에 보존
각 함수 결과 반환 conversation.item.create 전송 response.item.create 전송
필요한 모든 결과 후 계속 response.create 전송 response.create로 백엔드 작업 계속

예를 들어 check_availability가 검증된 슬롯을 반환한 뒤 연결된 세션에 다음을 보내세요. call_availability를 받은 호출 ID로 바꾸세요.

이전: Realtime 결과

{
  "type": "conversation.item.create",
  "item": {
    "type": "function_call_output",
    "call_id": "call_availability",
    "output": "{\"available\":true,\"slot_id\":\"slot_friday_14\",\"booked\":false}"
  }
}

이후: GPT-Live 결과

export function sendUpdate(connection) {
  connection.send({
    type: "response.item.create",
    event_id: "availability_result_1",
    item: {
      type: "function_call_output",
      call_id: "call_availability",
      output: '{"available":true,"slot_id":"slot_friday_14","booked":false}',
    },
  });
}
from openai.resources.live.live import AsyncLiveConnection
from openai.resources.live.sideband import AsyncSidebandConnection
from openai.types.responses.response_input_item_param import ResponseInputItemParam


async def send_update(
    connection: AsyncLiveConnection | AsyncSidebandConnection,
) -> None:
    item: ResponseInputItemParam = {
        "type": "function_call_output",
        "call_id": "call_availability",
        "output": '{"available":true,"slot_id":"slot_friday_14","booked":false}',
    }
    await connection.response.item.create(
        event_id="availability_result_1",
        item=item,
    )

필요한 모든 함수 결과를 제출한 뒤 백엔드를 계속하세요.

export function sendUpdate(connection) {
  connection.send({
    type: "response.create",
    event_id: "continue_availability_1",
  });
}
from openai.resources.live.live import AsyncLiveConnection
from openai.resources.live.sideband import AsyncSidebandConnection


async def send_update(
    connection: AsyncLiveConnection | AsyncSidebandConnection,
) -> None:
    await connection.response.create(
        event_id="continue_availability_1",
    )

초기 마이그레이션에서는 parallel_tool_calls를 false로 설정해 한 번에 하나의 도구 호출을 처리하세요. 내부 response.output_item.done 이벤트에서 각 함수 호출을 수집하고 name, arguments, call_id를 유지하세요. 이후 완료 이벤트가 output: []를 포함해도 그 기록을 유지하세요. 완료된 항목을 기다렸다가 핸들러를 실행하세요. arguments-done 이벤트만으로는 함수 이름과 call_id가 없어요. 수집·출력 제출·오류는 완전한 함수 결과 절차를 따르세요.

컨텍스트 보존과 수정 적용

Responses delegation은 관련 음성 대화 컨텍스트를 백엔드에 제공해요. 권위 있는 예약 상태(선택된 슬롯, 확인된 슬롯, 권한, 활성 작업, 결과)는 애플리케이션에 유지하세요. Live 대화 히스토리는 압축될 수 있고, 예약 기록이 아니에요.

사용자가 "Actually, Friday instead"라고 말하면 금요일을 현재 요청으로 기록하고 목요일에 대한 확인을 지우세요. 작업에 revision 2 같은 새 버전 번호를 주어 애플리케이션이 이전 요청의 결과를 인식하게 하세요.

예약 전에 날짜, 슬롯, 확인이 현재 요청과 여전히 일치하는지 확인하세요. 사용자가 요청을 바꿔 보류 중인 함수 호출을 거절하면 실제 일어난 것과 일치하게 건너뛰었거나 취소됐다고 결과를 반환해요. 필요한 모든 호출에 대한 결과를 백엔드를 계속하기 전에 제출하세요.

목요일 예약이 이미 성공했다면 다른 예약을 시도하기 전에 현재 상태를 확인하고 요청된 변경을 처리하세요.

각 대본 조각을 화자, start_ms, end_ms와 함께 받은 그대로 정확히 유지하세요. 그 정보로 적절한 발신자·어시스턴트 캡션·채팅 버블을 업데이트하세요. 조각이 늦게 도착하거나 두 사람이 동시에 말해도요. 메시지 경계는 애플리케이션에서 선택하고, 재생은 플레이어에서 추적하세요. 대본 타임스탬프는 정확한 단어 재생 시간을 식별하지 않아요. 의도가 불확실하면 중요한 날짜·이름·숫자를 명확히 하세요. 대본·컨텍스트 처리는 세션 관리를 참고하세요.

이미지·화면 컨텍스트: Realtime 애플리케이션이 이미지를 받는다면 비전 지원 백엔드로 라우팅하고 관련 텍스트를 GPT-Live로 반환하세요. client·Responses delegation 모두 이 패턴을 지원해요. 이미지·시각 컨텍스트 추가 참고.

오디오에 의존하는 결정 보존

일부 결정은 소리 자체가 필요해요. 음성사서함 비프음 감지나 녹음된 인사를 그 타이밍으로 인식하는 것처럼요. GPT-Live는 호출을 듣지만 위임이 자동으로 백엔드에 오디오를 보내지는 않아요. Client 모드에서 session.delegation.created는 ID와 타이밍 정보를 포함하고, 애플리케이션이 요청 컨텍스트와 백엔드가 필요로 하는 오디오를 제공해요.

응답 기계 감지에는 수신 오디오를 오디오 감지기에 명시적으로 라우팅하세요. 평가할 수 있는 하나의 애플리케이션 관리 아키텍처는 호출 일부 동안 GPT-Live 옆에서 별도 Realtime 세션을 실행하는 거예요.

  1. 수신 호출 오디오의 사본을 두 세션 모두에 보내세요.
  2. 감지기가 구조화된 함수 호출로 분류를 보고하게 하세요. 각 결과를 스키마에 대해 확인하고, 낡은 결과는 거부하며, 증거가 불충분할 때는 unknown 상태를 유지하세요. 이후 증거가 결정을 수정하도록 허용하세요.
  3. 관련 신뢰 컨텍스트를 GPT-Live로 보내고, 나가는 오디오 재생에 애플리케이션 정책을 적용하세요.

사람과 대화 중인지 기계와 대화 중인지, 대상이 메시지를 기록할 준비가 됐는지 두 결정을 추적하세요. 감지기가 인사가 재생되는 동안 음성사서함을 인식할 수 있어요. 나가는 오디오를 허용하기 전에 애플리케이션이 요구하는 증거를 기다리세요. 컨텍스트 승인은 업데이트 수락을 기록할 뿐, 재생 결정은 애플리케이션이 해요. 가드레일 적응과 재생 컨트롤로 애플리케이션이 제어하는 오디오 경로에서 그 결정을 강제하세요.

음성사서함 인사로 발전하는 짧은 "hello", 호출 스크리닝 프롬프트, 음성사서함 중 사람이 받는 경우를 테스트하세요. 호출이 끝나기 전에 감지기를 멈출 계획이라면 이후 사람이 받을 때 무슨 일이 일어나는지 테스트하세요. 그 결과와 감지기의 추가 비용으로 얼마나 오래 실행할지 선택하세요. 더 많은 오디오가 도착하며 초기 "인간" 분류가 바뀌는 경우를 포함하세요.

텍스트 에이전트나 체인 파이프라인에서

이전: 텍스트 에이전트가 작성된 요청을 받고 도구와 저장된 상태를 사용해요. 체인(캐스케이드) 음성 파이프라인은 그 에이전트 앞에 speech-to-text, 뒤에 text-to-speech를 추가해요.

이후: GPT-Live가 음성 인터페이스를 제공하고 작업을 기존 에이전트에 위임해요. 체인 파이프라인에서는 별도의 speech-to-text·text-to-speech 단계를 대체해요. 작업에 여전히 맞는 모델, 지시, 도구, 워크플로, 지속 상태는 백엔드에 유지하세요.

기존 에이전트 연결

세션 설정 중에 delegation을 {"type":"client"}로 구성하세요. 애플리케이션이 이런 알림을 받아요.

{
  "type": "session.delegation.created",
  "offset_ms": 1000,
  "delegation": {
    "id": "item_appointment_1",
    "type": "delegation",
    "target": "client"
  }
}

이 알림으로 애플리케이션의 위임 핸들러를 시작하세요. 결과를 같은 요청에 붙일 수 있도록 delegation.id를 보존하세요. 핸들러는 발신자·어시스턴트 대본과 애플리케이션이 가진 작업 기록으로 에이전트 입력을 준비해요. 알림 자체에는 요청 텍스트나 도구 인자가 없어요.

예를 들어 예약 에이전트는 이런 입력을 받을 수 있어요.

Caller: "Actually, Friday instead."

Current request: Find an appointment on Friday in the caller's time zone.

Previous result: Thursday at 2 PM was offered.

Confirmation: No Friday slot has been confirmed.

Task revision: 2.

알림은 전체 문장이 전사되기 전에 도착할 수 있어요. 충분한 컨텍스트가 있을 때까지 유지하거나, 행동 전에 발신자에게 명확히 하라고 요청하세요.

텍스트 애플리케이션에서는 사용자의 최신 메시지를 에이전트에 직접 전달할 수 있어요. GPT-Live에서는 그 컨텍스트를 제공하고 간결한 검증된 결과를 반환하는 어댑터를 추가하세요.

어댑터를 호출하기 전에 delegation ID를 기록해서 하나의 핸들러만 그 작업을 시작하게 하세요. 요청이 불명확하면 컨텍스트가 준비됐을 때 어댑터를 다시 호출하세요.

백엔드는 권한 부여, 확인, operation ID, 재시도에 여전히 책임이 있어요. 예약을 변경하기 전에 작업의 현재 revision을 확인하세요. 어댑터의 이후 revision 검사는 낡은 결과가 발표되는 것만 막을 뿐, 이미 만들어진 예약을 되돌리지 못해요.

client delegation을 에이전트에 연결

async function handleDelegation(event, app) {
  if (
    event.type !== "session.delegation.created" ||
    event.delegation?.target !== "client"
  )
    return;

  const context = app.readContext();
  if (!context) return; // Retain the notice; resolve the request before acting.

  const summary = await app.runAgent({
    revision: context.revision,
    recentConversation: context.recentConversation,
    task: context.task,
  });

  if (app.currentRevision() !== context.revision) return;

  app.send({
    type: "session.commentary.append",
    event_id: crypto.randomUUID(),
    delegation_id: event.delegation.id,
    content: summary,
  });
}
from collections.abc import Awaitable, Callable
from dataclasses import dataclass
from uuid import uuid4

from openai.resources.live.live import AsyncLiveConnection
from openai.resources.live.sideband import AsyncSidebandConnection
from openai.types.live.server_event import ServerEvent


@dataclass(frozen=True)
class Context:
    revision: int
    recent_conversation: str
    task: str


async def handle_delegation(
    event: ServerEvent,
    connection: AsyncLiveConnection | AsyncSidebandConnection,
    *,
    read_context: Callable[[], Context | None],
    run_agent: Callable[[Context], Awaitable[str]],
    current_revision: Callable[[], int],
) -> None:
    if (
        event.type != "session.delegation.created"
        or event.delegation.target != "client"
    ):
        return
    context = read_context()
    if context is None:
        return  # Retain the notice; resolve the request before acting.
    summary = await run_agent(context)
    if current_revision() != context.revision:
        return
    await connection.session.commentary.append(
        event_id=str(uuid4()),
        delegation_id=event.delegation.id,
        content=summary,
    )

컨텍스트와 에이전트 콜백을 애플리케이션에서 구현하세요. 컨텍스트 콜백은 최근 대화와 현재 작업을 반환하거나, 요청이 여전히 불명확한 동안 값을 반환하지 않아요. 에이전트 콜백은 기존 백엔드를 실행하고 최대 500 토큰의 검증된 요약을 반환해요. JavaScript에서는 애플리케이션이 제공한 send 콜백이 Live 연결에 JSON 이벤트를 보내요. Python에서는 어댑터가 SDK connection을 통해 직접 업데이트를 보내요.

예약 어시스턴트의 컨텍스트는 요청된 날짜·시간대, 이전에 제안된 슬롯, 확인된 슬롯, 최신 수정을 확립해야 해요. 가용성 결과는 슬롯이 가능하고 아직 예약되지 않았다고 말해야 해요. 예약 확인은 예약이 성공한 후에만 반환하세요. 전체 설정과 결과 흐름은 Client delegation을 참고하세요.

업데이트·수정 라우팅

구조화된 도구 출력과 워크플로 세부 사항은 백엔드에 두세요. GPT-Live에는 짧은 사실 업데이트를 반환하세요.

  • 백그라운드 진행(예: 아직 실행 중인 조회)은 session.thinking.append 사용.
  • 사용자가 들을 검증된 결과는 session.commentary.append 사용.
  • 애플리케이션이 작성한 행동 지침은 session.instructions.append 사용.

세 가지 모두 최대 500 토큰의 일반 문자열 content를 받고 delegation_id가 필요해요. 관련 작업에는 원래 client delegation ID를, 일반 세션 컨텍스트에는 null을 쓰세요. client_event_id로 각 승인을 보낸 명령과 일치시키세요. 이는 업데이트가 수락됐는지 확인해요. 생성된 발화를 관찰하려면 어시스턴트 대본 이벤트를, 재생 추적에는 플레이어 상태를 사용하세요. 올바른 종류의 업데이트 보내기 참고.

사용자가 "Actually, Friday instead"라고 말하면 금요일을 현재 요청으로 저장하고, 버전 번호를 올리고, 목요일 확인을 지우세요. 그 수정을 기존 에이전트로 보내세요. 목요일 조회를 취소 요청할지, 바꿀지, 끝내고 결과를 폐기할지 결정하세요.

취소로 보고하기 전에 조회 상태를 추적하세요. 사용자의 인터럽션이 어시스턴트 발화를 이미 멈췄어도 그 백엔드 결정을 처리하세요.

백엔드 작업은 음성 세션보다 오래 살 수 있어요. 애플리케이션에 그 상태를 지속하세요. 이후 음성 상호작용에서는 관련 저장 컨텍스트로 새 세션을 시작하세요. 세션 관리 참고.

타입 입력을 에이전트에 연결 유지

타입 입력을 기존 백엔드에 연결된 상태로 유지하세요. 타입 수정을 같은 작업에 대한 업데이트로 취급하고 관련 검증 컨텍스트를 음성 세션에 보내세요. 타입 입력 받기와 업데이트 정확하고 유용하게 유지를 참고하세요.

텍스트·발화 안전장치 적응

텍스트 에이전트나 체인 파이프라인은 표시·발화 전에 완전한 답변을 검증할 수 있어요. GPT-Live에서는 대화와 백엔드 작업이 동시에 실행돼요. 모든 말한 응답이 사용자가 듣기 전에 검사를 통과해야 한다면 그 검사를 애플리케이션이 제어하는 오디오 재생 경로에 넣으세요. 백엔드 결과를 붙잡는다고 모든 발화가 멈추지는 않아요.

검사를 유지하고 연속 발화를 고려하려면 가드레일 적응을 따르세요.

가드레일 적응

어느 아키텍처에서 마이그레이션하든 기존 애플리케이션의 입력·출력 안전장치를 유지하세요. GPT-Live는 백엔드 작업과 정책 검사가 실행되는 동안에도 계속 말할 수 있으므로, 대화와 백엔드가 취하는 작업 모두에 검사를 적용하세요.

서버가 브라우저의 WebRTC 세션을 모니터·제어해야 한다면 sideband WebSocket을 붙여 대본을 받고 교정 지시를 보내세요. 오디오는 WebRTC로 계속 흘러요. 서버가 이미 기본 WebSocket으로 오디오를 스트리밍한다면 그 연결의 이벤트 스트림을 이 검사에 쓰세요. Responses delegation을 선택한다고 해서 sideband가 필요한 건 아니에요.

  1. 사용자·어시스턴트 대본 이벤트를 모니터하고 대화와 함께 검사를 실행하세요.
  2. 영향을 받는 도구와 외부 작업을 애플리케이션 코드에서 차단하세요. 지원되는 곳에서 애플리케이션 소유 작업을 취소하고, 늦은 결과가 차단된 요청을 계속하지 못하게 하세요.
  3. session.instructions.append로 어시스턴트를 리다이렉트하고 결정을 애플리케이션에 기록하세요.

예를 들어 발신자가 예약 어시스턴트에 권한 없이 다른 사람의 예약을 바꾸라고 하면, 예약 작업을 실행 전에 차단하세요. 그런 다음 어시스턴트에게 그 변경을 할 수 없다고 설명하라고 지시하세요. 변하지 않은 예약 기록과 말한 응답을 모두 검증하세요. 거절만으로는 권한 부여를 강제하지 않아요.

교정 지시는 이미 들린 오디오를 되돌릴 수 없어요. 재생 전에 어시스턴트 발화를 검사해야 한다면 재생 전 발화 검사의 버퍼링·승인·인터럽션·복구 처리를 따르세요. 작업 제어와 교정 지시 예시는 대화 가드레일 적용, 필수 개시 표현은 고지 사항 전달을 참고하세요.

마이그레이션 검증

마이그레이션된 어시스턴트를 현재 애플리케이션의 대표 대화와 비교하세요. 시나리오, 백엔드 도구, 성공 기준을 일관되게 유지하고, 각 시나리오를 반복하며 회귀와 함께 의도적 동작 변경을 기록하세요.

  • 작업과 말한 확인: 가용성 확인, 확인 요청, 확인된 슬롯만 예약. 백엔드 결과, 말한 답, 클라이언트 재생을 따로 검증.
  • 수정과 중복 방지: 보류 요청 중 목요일을 금요일로 변경. 낡은 결과 폐기, 재시도가 두 번째 예약을 만들지 않게.
  • 권한: 권한 없는 작업과 확인 없는 예약 시도. 애플리케이션 정책이 실행을 차단하는지 확인.
  • 가드레일 개입: 발화·도구 실행 중 검사 트리거. 어시스턴트가 교정을 받고, 도구 결과가 늦게 도착해도 영향을 받는 작업이 차단된 채 유지되며, 재생이 의도대로 재개되는지 확인. 실행 중인 작업이 실제로 멈췄는지 확인. 느린 검사와 오탐(false positives) 포함.
  • 인터럽션: 어시스턴트가 말하거나 작업하는 동안 말하기. 대화, 오디오 재생, 백엔드 작업 상태를 독립적으로 검증.
  • 실패와 재연결: 도구 오류, 잃은 결과, 연결 끊김 테스트. 예약 요청이 응답을 잃으면 재시도 전에 예약이 성공했는지 확인. 저장된 작업 컨텍스트로 다음 음성 세션을 시작하고 확립된 결과에서 계속되는지 검증.

마이그레이션된 백엔드 조정에는 백엔드 지연 줄이기를, 유용한 말한 응답 시간과 작업 성공 비교에는 음성 에이전트 평가 Cookbook을, 사용·비용 비교에는 비용 최적화를 사용하세요.

더 알아보기 (Learn more)

관련 문서: GPT-Live 시작하기, Delegation and tools, GPT-Live 프롬프팅, 세션 관리 가이드를 함께 보면 좋아요.