> For the complete documentation index, see [llms.txt](https://angoor-ai.gitbook.io/angoor-ai/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://angoor-ai.gitbook.io/angoor-ai/tutorials/setup-a-simple-voice-agent/building-voice-agent-flows.md).

# Building Voice Agent Flows

#### Overview

A Flow is the orchestration layer of Angoor AI — the visual workflow where every component you configured in Steps 1–3 is finally wired together. Agents generate responses and Tools perform specialized tasks, but the Flow decides **what happens next** at each moment of the call. It is built on a canvas as a series of connected **paths**, each containing one or more **steps** that run from top to bottom.

This is the most important step: the Plivo channel, the Agent, and the Tools only become a working voice agent once the Flow connects them.

**Navigation:** `Configuration → Flows → Edit Flow`

#### 4.1 Flow Settings

Before building the canvas, the flow's Settings tab defines how the flow is identified and triggered.

#### Flow Name

**Description:** The identifier for this flow. **Example value:** `Customer Support Flow`

#### Description / Tags

**Description:** Optional fields to summarize the flow's purpose and categorize it for easier management.

#### Select Form

**Description:** Optionally attaches a Form to the flow, so data collected during the conversation can be captured in a structured way.

#### Add Channels

**Description:** Binds the flow to one or more channels (phone numbers). This is the link between the telephony layer from Step 1 and this flow. **Why it matters:** A call to a bound number runs this flow. Without a channel binding, the flow can never be triggered by a real call. **Example value:** the voice channel (phone number) you configured in Step 1

#### Add User Groups

**Description:** Restricts or targets the flow to a defined set of users. **Example value:** `All Users`

#### Expiration Time

**Description:** How long a flow session remains active before it expires, set in Hours and Minutes. **Example value:** Hours `Never`, Minutes `00` (sessions do not auto-expire)

#### Flow Type

Defines the execution model of the flow.

**Values:**

* **`Agentic`** — The flow is driven by the AI agent's reasoning. The agent interprets the conversation and decides how to move through the flow dynamically. This is the model used for conversational voice agents.
* **`Action`** — The flow runs as a fixed, predefined sequence of actions rather than being driven by agent reasoning. Suited to deterministic, rule-based workflows where each step follows the previous one in a set order.

#### Test Mode

**Description:** Lets you run the flow against specific test identifiers before going live. Includes **Test Mode Identifiers** (who the test applies to), **Ignore Past Sessions**, and **Restrict Send If Multiple Inputs**. **Why it matters:** Lets you validate the flow safely without affecting real callers.

<figure><img src="/files/rIWV99CxxGLCPScKtuSU" alt=""><figcaption></figcaption></figure>

***

#### 4.2 The Flow Canvas — Paths and Steps

The flow is built as a chain of **paths** on a visual canvas. Each path is a card containing one or more **steps**, and paths connect left to right to form the conversation's journey. You add steps with **+ Add Step** and new branches with **+ Add Path**.

Every step shares the same **Additional Settings**, which control how often it runs:

* **Retry on Error** — re-attempt the step if it fails
* **Run Once Per Session** — execute at most once per call session
* **Run Once Per Execution** — execute at most once per flow run
* **Run Post Async** — run the next steps connected to it asynchronously (content steps)

#### Reference Flow Structure

A complete production flow runs as follows:

`Start (All Users) → Path A: System Prompt + Agent → Path B: Call Orchestrator Tool → Decision Routing (state Equals cut_call) → Path C: Wait Time (When the timer expires) → Path D: End Call (Path E: Text — supporting branch)`

<figure><img src="/files/8C1uq20PurMeHEgbPSX1" alt=""><figcaption></figcaption></figure>

***

#### 4.3 Node-by-Node Configuration

#### Start Node — "All Users"

**Description:** The entry point of every flow. It defines the channel the flow listens on and the events that trigger it.

**Channel:** the voice channel (phone number) bound to this flow

**Triggers:**

* **`INBOUND_CALL_RECEIVED`** — fires the moment an inbound call connects
* **`INBOUND`** — fires on an inbound interaction
* **`RECORDING_COMPLETED`** — fires when a call recording finishes processing

**Why it matters:** These triggers are what make the flow start automatically when a real call arrives — no manual intervention.

#### System Prompt + Agent

**Description:** The first action path. It applies a **System Prompt** (the voice-agent instructions defining identity, behavior, conversation rules, and restrictions) and then attaches the **Agent**, which handles the actual conversation.

**Steps in this path:**

* **Add System Prompt** — the core voice-agent prompt
* **Agent** — the configured agent from Step 2

**Why it matters:** This is where the caller actually talks to your AI. Everything from the Agent configuration in Step 2 comes into play here.

#### Call Orchestrator Tool

**Description:** The Tool from Step 3 that analyzes the live conversation and determines its current state. It is wired into the flow with explicit input and output variables.

**Input Variables:**

* **`conversation_history`** ← `History` (the live conversation transcript)
* **`current_state`** ← `state` (the current workflow state)

**Output Variables:**

* **`state`** — the classified result (`welcome_message`, `conversation`, or `cut_call`)

**Why it matters:** This is the bridge between the conversation and the decision logic. The Tool reads what's happening and writes a single state value that the next step acts on.

#### Decision Routing

**Description:** A routing step that creates branches in the flow based on objective decision and variable checks. It evaluates the `state` value produced by the Call Orchestrator.

**Condition (LOGIC 1):**

| Field   | Operator | Value      |
| ------- | -------- | ---------- |
| `state` | `Equals` | `cut_call` |

**Options:**

* **Block Path** — stops the path when the condition is not met
* **+ Add Decision** — add further conditions to the same logic block

**Behavior:**

* **Condition TRUE** (`state = cut_call`) → proceed to the termination sequence (Wait Time → End Call)
* **Condition FALSE** (`state = conversation` or `welcome_message`) → the call continues normally

**Why it matters:** This single check is what decides, on every turn, whether the call should keep going or wind down — the heart of the call-termination workflow.

#### Wait Time

**Description:** Introduces a short, deliberate delay before the call disconnects, so the ending doesn't feel abrupt. Its logic triggers the next step **when the timer expires**.

**Input Variables:**

* **`waitTimeHrs`** — hours (left unset)
* **`waitTimeMins`** — minutes (left unset)
* **`waitTimeSec`** — seconds

**Why it matters:** A short pause after the closing message makes the goodbye feel natural and human rather than a hard cut.

#### End Call

**Description:** The final step. It terminates the active call session — stopping audio streaming, transcription, and speech generation, finalizing logs, and updating analytics.

**Variables:** None required.

**Why it matters:** This cleanly closes the call once the conversation has genuinely concluded, completing the workflow.

#### Text (Supporting Branch)

**Description:** A supporting content branch containing a **Text** step, used to send a text message within the flow.

***

#### 4.4 Available Step Types

When you click **+ Add Step**, the "Search for Step" palette opens, organized into categories. This is the full toolkit available when extending the flow:

**Content (Send Content)** — Image, Nudge, Text, Video, Document, Template, Collect Payment, Instagram Comment, Product, Comment, Slack, Email, Email Template

**Routing** — Quick Replies, Logic Routing, Decision Routing

**Agents** — the workspace's configured agents

**Tools** — the workspace's configured tools

**Actions** — Get Shopify Order List, Update Shopify Order, Add Tag To Shopify Order, Cancel Shopify Order, Get User From Identifier, Check User In Group, Check User By Data, Transform With Regex, Match With Regex, Audio Analysis, Add Plugin Event, Has A New Session, Close Session, Close All Controlled Sessions, Control Session, Format Date, Parse Json, Apply Metabase Filter, Process Knowledge Base, Generate Random Number, Create Round Robin, Add To Array

**Why it matters:** These categories show what a flow can do beyond this example — integrate with Shopify, run regex extraction, manage sessions, analyze audio, process knowledge bases, and more — all without code.

***

#### 4.5 How the Pieces Connect — End-to-End

**1.Inbound call to the bound voice channel** &#x20;

**2.Start (All Users) fires on INBOUND\_CALL\_RECEIVED** &#x20;

**3.System Prompt + Agent (the conversation happens)** &#x20;

**4.Call Orchestrator Tool (reads History + state → outputs state)**&#x20;

**5.Decision Routing (state Equals cut\_call ?) FALSE**&#x20;

**6.Conversation continues TRUE → Wait Time (short delay)**&#x20;

**7.End Call (session terminated, logs finalized)**

***

#### 4.6 Complete Workflow Example

The following demonstrates the full termination process end-to-end.

\`Conversation Agent: "Is there anything else I can help you with today?" Caller: "No, thank you." Agent: "Thank you for calling. Have a wonderful day." Caller: "Thank you."

Tool Analysis -> Call Orchestrator returns: cut\_call Decision -> state Equals cut\_call => TRUE Wait Timer -> delay 2 seconds End Call -> call disconnected, analytics updated, conversation archived, workflow completed\`

***

#### 4.7 Best Practices for Voice Flows

**Use dedicated Tools for state management.** Do not hardcode call-termination logic inside Agent prompts; use specialized Tools such as the Call Orchestrator. This improves maintainability and scalability.

**Keep decision logic simple.** Decision Nodes should evaluate clearly defined outputs (good: `state = cut_call`; poor: complex multi-condition expressions without clear outputs).

**Always add a Wait Timer** (2–3 seconds) for better caller experience, and test every branch —

* ✓ welcome\_message
* ✓ conversation
* ✓ cut\_call

This ensures the workflow behaves correctly under all conditions.
