---
title: "List your originating numbers and the agent lines each one overrides"
method: GET
path: "/voice/bridge/numbers/instructions"
tags: ["voice"]
---

# List your originating numbers and the agent lines each one overrides

`GET /voice/bridge/numbers/instructions`

## Request

- Base URL: `https://corebee.ai/api/v1`
- URL: `https://corebee.ai/api/v1/voice/bridge/numbers/instructions`
- Auth: HTTP bearer

Every Telnyx DID your organization owns that can originate a bridge, with the spoken lines the conversational agent uses for calls placed from it. instructions is null when the number overrides nothing, which means it speaks every shipped template, that is the state of every number until you set one, and it is not an error. The value returned is the SCREENED value, i.e. exactly what will be spoken, not necessarily the bytes you sent: see the normalization note on PATCH. Requires the voice:bridge scope.

## Response `200`

OK

- object
  - `data` object, required
    - `numbers` BridgeNumberInstructions[], required
      - `from_number` string: The originating DID owned by your organization.
      - `instructions` SpeechOverrides: The spoken lines one DID overrides. Absent or null means the agent speaks every shipped template. templates keys are the lines themselves; variables are values interpolated into them and into the shipped templates. Both objects are optional but the document must set at least one entry, an empty document is a 400, and null (not {}) is how you clear a number. Total serialized size must be at most 8192 bytes. SLOTS. Any line may interpolate {businessName}, {consumerFirstName}, {dealership}, {department}, {prepLine}, {reasonForCall}. {prepLine} is the prep_line you sent when starting the bridge, its first 180 characters, unmodified. It is NOT unbounded: prep_line itself may be up to 500 characters and the closing line of a briefing call carries more of it than a {prepLine} slot does, so a long note is spoken in full at the close and shortened inside a line. Write lines that read correctly when the note is cut. {reasonForCall} is what the agent says the call is about; on a briefing-only call it is deliberately a neutral stand-in so your message is not delivered twice, which is why it is NOT the same value as {prepLine}. {dealership} and {department} come from `variables` below, falling back to the call's business name and to "sales". An unrecognised {slot} is removed from the line rather than read aloud. CHARACTERS. Lines are plain single-line text. Accents are folded to ASCII and whitespace collapses; a line containing a character outside the accepted set is REJECTED rather than stripped, so you are never given back mangled English you did not write. THE ACCEPTED SET IS EXACTLY: letters A-Z a-z, digits, space, apostrophe, comma, full stop, hyphen, exclamation mark, ampersand, percent, dollar, hash, at, slash, colon, semicolon, parentheses, question mark, and the braces of a {slot}. Everything else is refused, and the two that surprise people most are the DOUBLE QUOTE (so a quoted customer line must be written without quotation marks) and any emoji or non-Latin character that survives accent folding. SHAPES THAT ARE REFUSED, on every line AND on every variable. (a) A word followed by a colon in SPEAKER-LABEL POSITION, at the start of the line, or straight after a ".", "!" or "?", because that reads as a new speaker turn in the transcript the model reads. A colon LATER in a sentence is fine, so "Gunn Honda's sales & service: no-hassle pricing" is accepted and "Dana: yes I can help" is not. Note the rule is about POSITION, not about names: "Dana here, thanks so much." is accepted. (b) The reserved words "intent", "confidence" and "affirmative", which name the fields of the model output that decides whether a call is transferred. (c) An instruction aimed at the model ("ignore/disregard/forget/override/follow/obey" near "instructions/rules/previous/prior/above/earlier"). (d) An assertion that the person has already agreed ("has said yes", "already agreed", "has consented"), that is the exact fact the handoff question exists to establish. (e) Backticks and line breaks. These are NARROW, EXACT rules and not a general "no instructions to the model" filter: they close the phrasings that are known to move the transfer decision, and a sufficiently indirect sentence will still be accepted. What contains the risk is that the handoff question itself is code-owned and byte-identical on every call. ⛔ WHEN AN ACCEPTED LINE IS STILL NOT SPOKEN. A 200 means STORED. Three rules are re-checked at SPEAK time, once your {slots} are filled with that call's real values, and any of them returns the shipped wording FOR THAT CALL, never a truncation, never silence. (1) LENGTH AFTER FILLING: a preamble over 200 characters, or any other line over 500, is dropped whole. One filled slot contributes at most 180 characters. (2) A QUESTION ARRIVING THROUGH A SLOT: on the lines that are spoken while the agent is waiting for an answer to the handoff question (briefing_opening_greeting, briefing_opening_preamble, identify_self, opening_greeting, opening_preamble, reprompt_short, state_purpose), if the filled {prepLine} or {reasonForCall} contains a "?" or asks for a yes, the line is dropped for that call. A customer's note is usually a question, so a line like "…a note from a customer. {prepLine}" will speak your wording on some calls and the shipped wording on others. To have the prep line spoken EVERY time, put it in a free-text line (acknowledge_hold, apology_no_answer, clarify_once, consumer_ringing, consumer_ringing_with_reason, consumer_still_ringing, goodbye_confused, goodbye_polite, goodbye_unavailable) instead. (3) A slot value that would introduce one of the refused shapes above. PATCH tells you at write time which of your lines are exposed to (1) and (2): see the `warnings` array on the response. ⛔ STORED IS NOT THE SAME AS IN EFFECT. This API writes the configuration; the conversational voice service reads it, and it does so only when the operator has enabled the per-number-instructions feature on that service. While it is disabled, which is the default and the rollback, every PATCH still returns 200, every GET still shows your lines, and every call still speaks the shipped templates. There is no field on this API that can tell you which state the voice service is in, because the flag does not live here. Confirm activation with your Corebee contact before concluding from a call that your configuration is wrong. ⛔ HOW THE OPENING IS ASSEMBLED, AND WHAT IS STILL HELD BACK. (1) TWO KEYS, TWO DIFFERENT THINGS, ON EACH CALL TYPE. briefing_opening_preamble and opening_preamble PREPEND: your words, then the shipped introduction, then the question, so a preamble that also introduces the agent produces TWO self-introductions in a row, and you should write one that greets or frames instead. briefing_opening_greeting and opening_greeting REPLACE the shipped introduction outright: your words, then the question, and nothing in between. That is the key to use if you want the agent to introduce herself in your own words. Set BOTH on one call type and neither is used, the shipped opening is spoken, because "prepend to the introduction" and "replace the introduction" cannot both be honoured and guessing which you meant is not something this API does silently. (2) A GREETING MUST NAME THE CUSTOMER. It has to interpolate {consumerFirstName}, and a greeting that does not is a 400. The reason is grammatical: the question that follows a live-transfer greeting is "Are you able to help them right now?", and "them" has exactly one referent in the sentence, the customer, whom the shipped introduction names and your greeting replaced. A call that arrives with no customer name falls back to the shipped opening for that call. (2a) A GREETING MAY NOT CLAIM THE CALLER IS A PERSON. This is an artificial voice, so a greeting that asserts the caller is a PERSON is a 400: "a real person", "a live agent", "I'm a human", "not a bot", "this is not a recording" and the like. Introducing the agent by name is fine and is the point of the key, "Hey, it's Sam from Gunn Honda, here about {consumerFirstName}." is accepted. When a greeting is in use, the call opens with your greeting, then the handoff question. (3) There is no way to reword the handoff question, not even as a named variant, and no key, preamble or greeting, can reach it. It is the one sentence held back: it is the switch that dials the consumer and starts billing, and prompt.ts quotes it verbatim to the classifier that decides whether it was answered yes. It is taken as a substring of the shipped line at speak time, so it is byte-identical on every call and is always the last thing said. (4) The briefing script is three parts and you can write the first. briefing_opening_greeting replaces part one, or briefing_opening_preamble goes in front of it; the briefing handoff question is held back for the reason in (3); and briefing_close, the sentence that reads your message back to the dealership, is code-owned, because it is the pure carrier for the prep line you already send and overriding it would delete your own message.
        - `templates` object: Line id -> the words to speak. Any key outside the enum is a 400 that says whether the id is unknown or code-owned. FREE TEXT, QUESTIONS ALLOWED (acknowledge_hold, apology_no_answer, clarify_once, consumer_ringing, consumer_ringing_with_reason, consumer_still_ringing, goodbye_confused, goodbye_polite, goodbye_unavailable): spoken only when nothing is waiting on a yes/no answer. Up to 300 characters. DECLARATIVE ONLY (briefing_opening_greeting, briefing_opening_preamble, identify_self, opening_greeting, opening_preamble, reprompt_short, state_purpose): these are spoken while the agent is waiting for an answer to the handoff question, so they may not contain "?", may not end in a tag question ("..., right?"), and may not ask for a "yes" in any form ("just say yes and I'll connect you"). A line that does is a 400. Up to 300 characters, except the preambles which are capped at 120 to keep the opening inside one breath. identify_self REPLACES ONLY THE SENTENCE IN FRONT OF A QUESTION YOU CANNOT REMOVE. When the agent answers "who is calling?" while it is waiting for the handoff answer, your line is followed by the shipped handoff question: "Are you able to help them right now?" if your line names the customer with {consumerFirstName}, otherwise "Are you able to help this customer right now?", and on a briefing call "Can I read you the message now?". The published example is spoken as "I'm the assistant for Gunn Honda new car sales. Are you able to help this customer right now?". When a question was put in the last few seconds, or the agent is not waiting for that answer, your line is spoken alone. NEVER OVERRIDABLE (ask_for_sales, ask_handoff, ask_handoff_new_person, briefing_ask_handoff, briefing_ask_handoff_new_person, briefing_close, briefing_opening, opening): sending any of these is a 400.
          - `briefing_opening_preamble` string: Prepended to the shipped opening. Capped at 120 characters, shorter than the other lines, so the opening stays inside one breath.
          - `opening_preamble` string: Prepended to the shipped opening. Capped at 120 characters, shorter than the other lines, so the opening stays inside one breath.
          - `briefing_opening_greeting` string: REPLACES the shipped introduction on this call type, it does not prepend. A greeting that asserts the caller is a person ("a real person", "not a bot") is a 400. The code-owned handoff question that ends the shipped opening is kept and spoken immediately after your words, byte-identical, and nothing is ever said after it. MUST interpolate {consumerFirstName}: it replaces the only place the customer is named, and the question that follows refers back to that person. Capped at 120 characters, like the preambles, so the opening stays inside one breath. Setting this AND the matching *_preamble on the same call type is refused at speak time and the shipped opening is used, because the two mean different things.
          - `opening_greeting` string: REPLACES the shipped introduction on this call type, it does not prepend. A greeting that asserts the caller is a person ("a real person", "not a bot") is a 400. The code-owned handoff question that ends the shipped opening is kept and spoken immediately after your words, byte-identical, and nothing is ever said after it. MUST interpolate {consumerFirstName}: it replaces the only place the customer is named, and the question that follows refers back to that person. Capped at 120 characters, like the preambles, so the opening stays inside one breath. Setting this AND the matching *_preamble on the same call type is refused at speak time and the shipped opening is used, because the two mean different things.
        - `variables` object: Per-NUMBER values interpolated into both your lines and the shipped ones. One DID serves one dealership, so these are properties of the number, not of the call. At most 60 characters each, no question mark, and no slots of their own. A variable is interpolated into lines that are spoken while the agent is waiting for an answer to the handoff question, so it INHERITS THE STRICTEST RULES: the same character set and the same refused shapes as a line, including the speaker-label rule. "Gunn Honda: Service & Parts" is refused for that reason (the colon lands in label position after a short opening run); "Gunn Honda Service & Parts" is accepted.
      - `using_shipped_templates` boolean: True when instructions is null.
      - `corridors` BridgeCorridorCoverage[]: What each KIND OF CALL from this number will speak for its opening. Always one entry per corridor, including corridors you configured nothing for, that entry is the point of the array.
        - `corridor` 'live_transfer' | 'briefing': live_transfer = briefing_only absent or false, the calls that can bridge a consumer and bill. briefing = briefing_only true, message delivered and the call ends.
        - `template` 'opening' | 'briefing_opening': The shipped template this corridor speaks. Published so a support thread can name it.
        - `greeting_key` string: The key that REPLACES the shipped introduction on this corridor.
        - `preamble_key` string, nullable: The key that goes IN FRONT of the shipped introduction on this corridor.
        - `configured_by` string[]: Dotted paths this document sets for THIS corridor, sorted. Empty means this corridor is unconfigured and speaks the shipped wording however much the other corridor is configured.
        - `speaks` 'your_greeting' | 'your_preamble' | 'shipped_wording': What a call on this corridor actually opens with. NOT a synonym for "configured_by is empty": a corridor with BOTH its greeting and its preamble set speaks shipped_wording on every call, because the two mean opposite things and are not composed by guessing.
        - `note` string, nullable: Why shipped_wording, in one sentence. null when your own words are spoken.
      - `connection_status` string, nullable: Provisioning state of the number, informational only.
    - `has_more` boolean: True when your organization owns more DIDs than this response lists. There is no cursor yet: if you see this true, say so rather than treating the list as complete.

## Other responses

- `401`: Invalid or missing credential
- `403`: Forbidden (missing scope, or resource not owned by the credential org)
- `409`: Conflict (code conflict): the column backing this feature has not been added to the database yet. The message names the migration. Nothing was written and every number reads as unset.
- `500`: Error

---

[API](https://skmtc.dev/corebee/apis/corebee-api.md) · [All operations](https://skmtc.dev/corebee/apis/corebee-api/llms.txt) · [OpenAPI document](https://skmtc.dev/corebee/apis/corebee-api/revisions/a48ea543b4dc?raw)
