Skip to main content
This example shows how to use Guava to call patients and remind them of upcoming appointments. If a patient needs to reschedule, the agent checks your Amazon Connect queue in real time — and either transfers them directly to a live scheduling agent (if one is free) or captures their callback preference and creates a Connect task (if the queue is busy).

What Happens on the Call

Prerequisites

  • Python 3.10 or later
  • A Guava account with an API key and a phone number — sign up at app.goguava.ai
  • An AWS account with an Amazon Connect instance

Step 1: Install Guava

Choose whichever package manager you prefer:
You also need boto3 for the Amazon Connect API:

Step 2: Set Up Amazon Connect

If you already have a Connect instance configured, skip to the parts you haven’t done yet.

2a. Create a Connect Instance

  1. Open the Amazon Connect console.
  2. Click Create instance and follow the setup wizard.
  3. Once the instance is created, open it and copy the Instance ID from the ARN shown in the overview — it’s the UUID at the end:

2b. Create a Contact Flow for Task Routing

Amazon Connect tasks need a dedicated contact flow — the default queue flow does not support tasks.
  1. In your Connect instance, go to Routing → Contact flows → Create contact flow.
  2. Name it something like Guava Task Routing Flow.
  3. Add a Set working queue block and connect it to your scheduling queue.
  4. Add a Transfer to queue block after that.
  5. Add a Disconnect / hang up block at the end of the error branch.
  6. Save and publish the flow.
  7. Open the flow, click Show additional flow information, and copy the Contact flow ID (the UUID at the end of the ARN).
Tip: For a minimal test flow, you can also use any existing inbound contact flow — tasks will be routed to whatever queue the flow sets.

2c. Set Up a Scheduling Queue

  1. Go to Routing → Queues → Add new queue.
  2. Name it (e.g., Scheduling) and assign it to the hours of operation and outbound caller ID of your choice.
  3. Copy the Queue ID from the queue’s ARN (the UUID at the end).

2d. Get a Transfer Number

This is the phone number Guava will transfer rescheduling patients to — typically your scheduling desk or the Amazon Connect direct dial number for your scheduling queue.
  • In Connect, go to Channels → Phone numbers to see claimed numbers.
  • Or use any external scheduling desk number in E.164 format (e.g., +15551234567).

Step 3: Configure AWS Credentials

The example uses boto3, which reads credentials from the standard AWS credential chain. The easiest way for local development:
The IAM user or role you use needs the following permissions:
  • connect:GetCurrentMetricData — to check queue availability
  • connect:StartTaskContact — to create callback tasks
A minimal IAM policy:

Step 4: Set Environment Variables

Step 5: Run the Example

Replace +15559876543 with the phone number to call and adjust --name and --appointment as needed. What to expect:
  • Guava calls the patient and verifies they’re the right person
  • If they confirm: you’ll see a confirmation logged and an SMS is sent
  • If they need to reschedule: the example checks your Connect queue in real time
    • If agents are free: Guava transfers the patient to CONNECT_TRANSFER_NUMBER
    • If the queue is busy: Guava collects a callback preference and creates a task in your Connect instance — visible to agents in the Contact Control Panel (CCP)
  • If no one picks up: Guava leaves a voicemail

How It Works

1. Defining the Agent and Kicking Off the Call

Agent is the top-level handle for the AI persona. call_phone places the call and binds the agent to that single conversation. The variables dict is passed into the call and made available throughout — handlers can read each value with call.get_variable(key).

2. Reaching the Right Person (reach_person)

reach_person handles the gatekeeper problem — it has the agent confirm they’re speaking with the intended patient before proceeding. If a family member answers, the agent politely asks for the patient by name. The reach result is delivered to the handler registered with @agent.on_reach_person.

3. Collecting the Appointment Response

set_task gives the agent a named objective and a checklist of items to work through. guava.Field tells the agent what information to collect — the patient might say “Yes, I’ll be there” or “Actually, I have a conflict that day” — and the agent normalizes that into a structured value you can inspect via call.get_field(...).

4. Classifying the Patient’s Response

When the remind task completes, the registered @agent.on_task_complete("remind") handler runs. Rather than matching against a list of keywords, IntentRecognizer uses an LLM to classify what the patient actually meant — natural phrasing like “I actually have a conflict that day” or “Can we move it?” still maps to needs to reschedule without enumerating every variant. The recognizer is instantiated once at module level and reused across calls.

5. Checking the Connect Queue in Real Time

GetCurrentMetricData returns a real-time snapshot of the queue — how many agents are available and how many contacts are already waiting. This snapshot updates every ~15 seconds.

6. Routing Decision: Transfer vs. Task

If a scheduler is free, Guava transfers the call live. If not, the agent collects the patient’s preferred callback time in a follow-up callback task; its completion handler creates a Connect task via StartTaskContact — complete with the patient’s name, original appointment, and preferred callback window. The task appears in your agents’ Contact Control Panel (CCP) just like any other contact.

7. SMS Confirmation

After call_phone() returns, if the patient confirmed, we send an SMS reminder via the Guava client. This runs after the call ends, so it never blocks the voice interaction.

Customization Ideas

Pull patient data from a database or CRM Replace the hardcoded --name and --appointment CLI args with a database query or CRM API call, and call patients in a loop:
Set a queue depth threshold Instead of transferring whenever any agent is free, add a threshold — e.g., only transfer if fewer than 3 contacts are already waiting:
Route by appointment type Different appointment types may need different queues or transfer numbers. Pass the appointment type into the call as a variable and route accordingly:
Add multi-language support Guava supports English, Spanish, French, German, and Italian. The agent’s voice can be set per call using the persona configuration on the underlying Call object.

Complete Example