43 lines
1.8 KiB
Python
43 lines
1.8 KiB
Python
from __future__ import annotations
|
|
|
|
import os
|
|
import sys
|
|
from dataclasses import dataclass, field
|
|
|
|
sys.path.append(os.path.dirname(os.path.abspath(__file__)))
|
|
|
|
from hotel_db import HotelDB, RoomBooking
|
|
|
|
from livekit.agents import llm
|
|
|
|
|
|
@dataclass
|
|
class Userdata:
|
|
db: HotelDB
|
|
# Departments already transferred to this call - guards against a duplicate transfer
|
|
# row when the agent re-calls transfer_call after the caller's reaction.
|
|
transferred_to: set[str] = field(default_factory=set)
|
|
# The refund outcome from the last room cancellation, and the caller-turn count when it
|
|
# happened - so a re-invoked cancel (no caller input since) re-surfaces that answer
|
|
# instead of re-verifying into a confusing "already cancelled" dead end.
|
|
last_cancel_message: str = ""
|
|
caller_turns_at_last_cancel: int = -1
|
|
verified_booking: RoomBooking | None = None
|
|
# The most recent completed room booking, and the caller-turn count at the moment
|
|
# it completed - together they catch a model that re-runs the booking flow with no
|
|
# caller input since, which would silently double-book the guest.
|
|
last_room_booking: RoomBooking | None = None
|
|
caller_turns_at_last_booking: int = 0
|
|
|
|
|
|
def _speak_code(code: str) -> str:
|
|
# Spell character by character, with "-" spoken as the single word "dash" -
|
|
# NOT spelled D, A, S, H (that reads as four more code characters).
|
|
return ", ".join("dash" if c == "-" else c for c in code.upper())
|
|
|
|
|
|
def _count_caller_turns(chat_ctx: llm.ChatContext) -> int:
|
|
"""How many times the caller has spoken so far - the signal for whether a
|
|
booking flow was actually driven by the caller or silently re-run by the model."""
|
|
return sum(1 for it in chat_ctx.items if it.type == "message" and it.role == "user")
|