Member Junction
    Preparing search index...

    Real-time, full-duplex driver for the AssemblyAI Voice Agent API (launched April 2026), implementing the Core BaseRealtimeModel primitive. Registers as AssemblyAIRealtime and is resolved for MJ: AI Models typed Realtime (API-key env alias: AI_VENDOR_API_KEY__AssemblyAIRealtime).

    What the provider is: a single-websocket speech-to-speech stack — Universal-3 Pro streaming ASR, server-side turn detection / barge-in, LLM reasoning, JSON-Schema tool calling, and conversational TTS — billed flat per session-hour. Unlike ElevenLabs there is no server-side agent object to manage: the ENTIRE session config (prompt, tools, voice, turn detection) is supplied per-session via the first session.update frame, so MJ's prompt/tool authority is native here, with no managed-agent ensure flow.

    Model resolution: the Voice Agent API exposes ONE endpoint and no model selection; params.Model is carried through to ClientRealtimeSessionConfig.Model for bookkeeping but plays no wire role.

    Topologies:

    • Server-bridged (StartSession): the driver opens the websocket itself (?token=<api key>), sends the session config, and resolves only after session.ready.
    • Client-direct (CreateClientSession): the driver mints a ONE-TIME, short-lived client token (GET /v1/token) — the browser opens its own socket with it (no API key ever leaves the server) and applies the server-built session object from the SessionConfig pact.

    No usage events: billing is a flat hourly session rate; the websocket reports no token usage, so sessions never emit IRealtimeSession.OnUsage. (The terminal session.ended frame carries duration seconds, but by then the consumer has typically closed — duration accounting lives in the provider dashboard.)

    Hierarchy (View Summary)

    Index

    Constructors

    Properties

    SupportsDynamicToolSet?: boolean

    Whether this driver subclass supports dynamic, multi-tool sets projected into the realtime session (e.g. direct action invocation on realtime co-agents).

    Static capability descriptor read before a session instance exists. Default: absent / false. Subclasses that support dynamic toolsets declare public static readonly SupportsDynamicToolSet = true;.

    Accessors

    • get apiKey(): string

      Only sub-classes can access the API key

      Returns string

    • get SupportsClientDirect(): boolean

      AssemblyAI supports the client-direct topology natively: a one-time temp token minted server-side authenticates the browser's own websocket.

      Returns boolean

    Methods

    • Optional WebRTC SDP exchange seam for drivers that support server-brokered WebRTC topologies.

      Parameters

      • _offerSdp: string

        The local SDP offer generated by the browser.

      • Optional_sessionConfig: Record<string, unknown>

        The session configuration to initialize the session with.

      Returns Promise<{ answerSdp: string; prebillSeconds: number; sessionId: string }>

      The answer SDP, provider session ID, and any prebill accounting.

    • REST seam: mints a ONE-TIME client token for a browser-direct session (GET /v1/token?expires_in_seconds=… with Authorization: Bearer <api key>).

      Parameters

      • expiresInSeconds: number

      Returns Promise<string>

    • Whether this driver's sessions can render a live avatar for the model, on the endpoint the driver serves.

      Defaults to false: a driver whose models render no avatar says nothing more, and may ignore an avatar request. A driver that renders one for some models (Gemini Enterprise) overrides it. The client-session service reads it to tell a call or a meeting that asked for an avatar "this voice model can't show an avatar" (RealtimeAvatarUnavailableReason 'endpoint'), whichever driver serves it.

      Parameters

      • _model: string

        The provider's API name for the model.

      Returns boolean

      true when sessions on this model can render a live avatar; false otherwise.

    • Builds the session object for the session.update frame from the Core params:

      • system_prompt: the session system prompt, with InitialContext folded in under a "Prior context" heading — the protocol has no history-seeding channel, so prior conversation context rides the prompt.
      • tools: the Core tool set mapped to the provider's { type: 'function', … } schema.
      • Recognized params.Config keys pass through to their wire slots: voice → output.voice, firstMessage (or the legacy greeting) → greeting (spoken on connect; omitted = no auto-greeting), turn_detection → input.turn_detection, keyterms → input.keyterms.

      Parameters

      Returns JSONObject

    • Folds optional prior context into the system prompt (no history channel exists).

      Parameters

      • systemPrompt: string
      • OptionalinitialContext: string

      Returns string

    • Reads the session's opening utterance out of the config bag — this driver's greeting wire slot, fed from the driver-NEUTRAL firstMessage key (issue #3557) that a persona authors without knowing which vendor will run. greeting predates the neutral name and is still accepted so existing configs keep working.

      Both keys go through the SAME trim-and-drop-blank rule the ElevenLabs driver applies, so one authored value means the same thing on either provider. That rule is also why the neutral key only wins when it carries something: a blank firstMessage must not suppress a valid legacy greeting — it is an absent opening utterance, not an empty one.

      Parameters

      Returns string

      The trimmed opening utterance, or undefined when neither key carries one.