Skip to main content

Escalate a live voice call into a video room

A voice call sometimes wants to be more than voice — a screen share to walk through a proposal, a facial read on a negotiation, a whiteboard with the customer’s engineering team. Escalation to video takes the call you’re on and opens a video room for both parties, without asking the customer to hang up and dial into anything. This guide covers the POST /voice/call-escalation/video endpoint: what it does on the softphone, the request and response contract, how the created room is stamped back to the originating call, the optional remote-party SMS notification, and how to clean the room up when the video session ends.

1. What “Move to video” does in the softphone

While a call is live on the Browser Softphone, the active-call HUD offers a Move to video action. One click calls the escalation endpoint with the live call SID, and both parties end up in the same video room: the agent joins directly on a host token, and the remote party (the customer) joins through a public guest link — delivered by SMS if requested, or share by hand over the call itself. The voice leg stays up until both sides are on video; the client hangs up the phone leg once the remote party has joined, so there is no simultaneous voice-and-video double media. Escalation is a tenant-owned convenience — Orbit does not block or gate it beyond the standard voice-write role guard (owner, admin, developer, or agent). Whether and when to invite a customer onto video is your routing, tone, and consent decision.

2. The endpoint

POST /api/v1/voice/call-escalation/video requires voice:write scope. The only required field is the live callSid.
A successful call returns 201 with the room identifiers, the agent’s host join material, the guest invite, and the notification outcome:
The agent’s browser connects the host.ws_url with host.token directly — no second round-trip. A malformed body returns 400 with per-field validation details; an unconfigured media service returns 503.

3. The created room and its call-SID stamp

The room is created with these properties:
  • Name — roomName if supplied, otherwise Call with <remote party name or number>.
  • Participant cap — 8 seats by default (agent, remote party, and room for a supervisor or warm-transfer target), clamped down to your plan’s video participant tier so an escalation can never exceed the plan’s video allowance.
  • Empty timeout — 300 seconds of inactivity ends the room.
  • Call traceability — the originating identifiers are stamped into the room’s settings.escalation block: source: "voice_call_escalation", call_sid, call_log_id, plus the remote party’s number and name when known. When you read the room later (GET /api/v1/video/rooms/{roomId}), that block ties the meeting back to the exact call it came from, so analytics and QA see one continuous interaction across voice and video.
The guest payload is a classic video invite: join_url opens the room as an unauthenticated guest (the opaque invite token is the credential), and expires_at is 4 hours out — short, since the escalation is happening now. There is no use cap, so a dropped or refreshed remote party can rejoin through the same link. For the invite mechanics in general, see Video room access tokens.

4. Remote-party notification

remote_party_notification in the response is one of:
  • sent — the guest link was delivered to remotePartyNumber by SMS.
  • failed — the SMS could not be sent (the extension is missing, disabled, lacks outbound messaging, has no direct caller ID, or the sender number is no longer owned). The failure is non-blocking — the agent still has the guest link and can read it out over the call.
  • not_requested — notifyRemoteParty was omitted or false; sharing the link is up to the agent.
The SMS is best-effort by design: an escalation must succeed even when notification cannot. The message the remote party receives is a single line with the join link:
The send goes through the same gated messaging pipeline every outbound SMS surface uses; sipCredentialId only selects which of your extensions (and therefore which caller ID) the message is sent from.

5. Resolve the room and tear it down

Read the room back when you need status:
When the video conversation ends, end the room explicitly rather than waiting out the empty timeout:
The client hangs up the voice leg once both parties are in the room, the agent ends the video room at the end of the meeting, and an unused room self-cleans after its 300-second empty timeout.

6. Workflow example — voice call to video meeting

  1. Agent answers an inbound call on the Browser Softphone and winds up talking to a customer who wants to see the product screen.
  2. Escalate. The agent taps Move to video (or your own integration posts callSid + notifyRemoteParty: true). The response returns the host token and guest link.
  3. Customer joins. The SMS lands on the customer’s phone; they tap the join URL and enter the room as a guest. The agent joined directly on the host token.
  4. Voice leg ends. Once the customer is visibly in the room, the client hangs up the phone leg — the conversation continues on video.
  5. Close. At the end of the meeting the agent ends the room (POST /api/v1/video/rooms/{roomId}/end); the call record and the room stay linked by the call_sid stamp for QA and reporting.

See also