OpenAI und Twilio in Echtzeit: So rekonstruieren Sie das korrekte Gesprächsprotokoll, wenn die Sprachausgabe unterbrochePython

Python-Programme
Anonymous
 OpenAI und Twilio in Echtzeit: So rekonstruieren Sie das korrekte Gesprächsprotokoll, wenn die Sprachausgabe unterbroche

Post by Anonymous »

Ich integriere Twilio Media Streams mit einem Sprachgenerierungs- und Transkriptionsdienst in Echtzeit, um eingehende Telefonanrufe zu bearbeiten (z. B. ein Bäckerei-Bestellsystem).
Die größte Herausforderung für mich besteht darin, den korrekten Gesprächsverlauf zu rekonstruieren, insbesondere das, was der Anrufer tatsächlich gehört hat, wenn Unterbrechungen (Barge-In) auftreten.
Problem:
Bei einem Echtzeitanruf wird die Der Sprachdienst gibt kontinuierlich Folgendes aus:
  • Audioausgabeblöcke
  • Transkriptdeltas für dieses Audio
Transkriptdeltas werden jedoch auch dann ausgegeben, wenn das Audio nie vollständig abgespielt wird oder wenn die Wiedergabe auf der Twilio-Seite unterbrochen und gelöscht wird.
Wenn der Anrufer unterbricht, erkenne ich dies anhand eines Sprachstartsignals (z. B. input_audio_buffer.speech_started) und gehe sofort wie folgt vor:
  • Aktuell wiedergegebene Ausgabe abschneiden
  • Löschen Sie den Twilio-Audiostream
  • Setzen Sie das Hören fort Anrufer
Trotzdem gibt der Transkript-Stream weiterhin Deltas für Inhalte aus, die generiert, aber nie gehört wurden.
Infolgedessen wird der Transkriptverlauf falsch und spiegelt nicht mehr das wider, was der Anrufer tatsächlich erlebt hat.
Beispiel
Konversationsablauf:
System: Ja, ich kann Ihnen bei der Bestellung helfen. Was möchten Sie?

Kunde: Ich möchte Bagels und eine Limonade.

System: Das kostet 9,05 $. Bargeld oder Kredit?

(Der Kunde unterbricht hier)

(Der Kunde hört den Rest des Satzes nie)

Kunde: Entschuldigen Sie die Unterbrechung – trinken Sie auch Kaffee?

System: Sicher. Was möchten Sie bestellen?
Was tatsächlich intern generiert wird (unerwünscht)
System: Das sind 9,05 $. Bargeld oder Kredit? Wir haben auch einen Store-Rabatt, den Sie jetzt anwenden können.
Der letzte Satz wird generiert und transkribiert, aber dem Anrufer nie vorgespielt, da der Stream gelöscht wurde.
Was ich tatsächlich erhalten möchte:
Ich versuche nicht, alle generierten Transkript-Deltas zu sammeln.
Ich muss insbesondere Folgendes rekonstruieren: Nur den Text, der der Audiodatei entspricht, die dem Anrufer tatsächlich vorgespielt wurde Twilio
Dies umfasst die Behandlung von Fällen, in denen:
  • Ausgabe teilweise abgespielt wird
  • Ausgabe mitten im Satz abgeschnitten wird
  • Der Anrufer unterbricht, während Audio abgespielt wird
Aktueller Code
Wenn der Anrufer zu sprechen beginnt (Barge-In)
Die Audioausgabe wird wie folgt an Twilio gesendet:

Code: Select all

---------------------------------------------

AGENT AUDIO → TWILIO

---------------------------------------------

if rtype in (“response.output_audio.delta”, “response.audio.delta”):
agent_cutoff = False

delta = response.get("delta")
if not delta or not stream_sid:
continue

await websocket.send_json({
"event": "media",
"streamSid": stream_sid,
"media": {"payload": delta},
})

last_audio_ts = time.monotonic()

if response_start_timestamp_twilio is None:
response_start_timestamp_twilio = latest_media_timestamp

item_id = response.get("item_id")
if item_id:
last_assistant_item = item_id

await send_mark(websocket, stream_sid)
continue

Auf jeden an Twilio gesendeten Audioblock folgt eine Markierung, damit die Wiedergabe später bestätigt werden kann.
Unterbrechungsbehandlung
Wenn der Anrufer anfängt zu sprechen, erkenne ich es und schneide die Ausgabe sofort ab und lösche die Twilio-Wiedergabe:

Code: Select all

await openai_ws.send(json.dumps({
“type”: “conversation.item.truncate”,
“item_id”: last_assistant_item,
“content_index”: 0,
“audio_end_ms”: elapsed_ms,
}))

await websocket.send_json({
“event”: “clear”,
“streamSid”: stream_sid,
})

Code: Select all

elapsed_ms
wird mithilfe von Twilio-Medienzeitstempeln berechnet.
Transkriptverarbeitung
Transkriptdeltas kommen kontinuierlich an, auch wenn Audio später abgeschnitten oder gelöscht wird.

Um zu vermeiden, dass Text protokolliert wird, der nie abgespielt wurde, füge ich Transkriptdeltas derzeit der neuesten unbestätigten Markierung hinzu:

Code: Select all


---------------------------------------------

OUTPUT TRANSCRIPT DELTA

---------------------------------------------

if rtype == “response.output_audio_transcript.delta”:
if agent_cutoff or not mark_queue:
continue

delta = response.get("delta")
if not delta:
continue

active_mark_id = mark_queue[-1]
pending_agent_transcripts.setdefault(active_mark_id, []).append(delta)
continue

Trotzdem treffen weiterhin Transkriptdeltas für Audiodaten ein, die nie abgespielt wurden.

Frage
Was ist in diesem Szenario die richtige oder empfohlene Methode zur Rekonstruktion eines zuverlässigen Gesprächstranskripts? Wie kann ich zuverlässig feststellen, welche Transkriptsegmente dem tatsächlich abgespielten Audio entsprechen?
Ich folge einem offiziellen Twilio-Beispiel, das Wiedergabemarkierungen und Unterbrechungserkennung verwendet, aber das Problem besteht weiterhin in dieser PR: Anfängliche KI-Unterbrechung/Konversationskürzung hinzufügen. KI spricht zuerst. von pkamp3 · Pull Request #13 · twilio-samples/speech-assistant-openai-realtime-api-python · GitHub
Vielen Dank

Quick Reply

Change Text Case: 
   
  • Similar Topics
    Replies
    Views
    Last post