Documentation Index
Fetch the complete documentation index at: https://patter-06b046ce-feat-observability-otel-attrs-0-6-1.mintlify.app/llms.txt
Use this file to discover all available pages before exploring further.
Test Mode
Test mode lets you interact with your agent in the terminal using pure text — no phone calls, no STT/TTS, no external services required. It simulates a phone conversation for rapid development.
Quick Start
import { Patter, Twilio, OpenAIRealtime } from "getpatter";
const phone = new Patter({ carrier: new Twilio(), phoneNumber: "+15550001234" });
const agent = phone.agent({
engine: new OpenAIRealtime(), // OPENAI_API_KEY from env
systemPrompt: "You are a helpful customer service agent for Acme Corp.",
firstMessage: "Hello! Welcome to Acme Corp. How can I help you today?",
});
await phone.test({ agent });
This opens an interactive REPL:
============================================================
PATTER TEST MODE
============================================================
Agent: gpt-4o-mini-realtime-preview / alloy
Provider: openai_realtime
Call ID: test_a1b2c3d4e5f6
Caller: +15550000001 → Callee: +15550000002
------------------------------------------------------------
Commands: /quit /transfer <number> /hangup /history
============================================================
Agent: Hello! Welcome to Acme Corp. How can I help you today?
You: I need to return an item
Agent: I'd be happy to help with your return...
Commands
| Command | Description |
|---|
/quit | End the test session. |
/hangup | Simulate hanging up the call. |
/transfer <number> | Simulate a call transfer. |
/history | Print the full conversation history. |
Using with onMessage
Test mode works with custom message handlers, exactly as they would work in production:
async function onMessage(data: Record<string, unknown>) {
const userText = data.text as string;
if (userText.toLowerCase().includes("cancel")) {
return "Let me transfer you to our cancellation team.";
}
return `You said: ${userText}`;
}
await phone.test({ agent, onMessage });
The onMessage handler receives a single data object with text, call_id, caller, and history fields.
Using with Built-in LLM Loop
When no onMessage handler is provided and OPENAI_API_KEY is available (either from new OpenAIRealtime({ apiKey }) or the env var), test mode uses the built-in LLM loop with streaming responses:
const agent = phone.agent({
systemPrompt: "You are a restaurant booking assistant.",
tools: [
{
name: "check_availability",
description: "Check table availability",
parameters: {
type: "object",
properties: {
date: { type: "string" },
partySize: { type: "number" },
},
},
webhookUrl: "https://api.example.com/availability",
},
],
});
await phone.test({ agent });
The LLM loop supports tool calling — tools are executed via their configured webhooks just like in production.
Event Callbacks
Test mode fires the same lifecycle callbacks as serve():
await phone.test({
agent,
onCallStart: async (event) => {
console.log(`Test call started: ${event.call_id}`);
},
onCallEnd: async (event) => {
console.log(`Test call ended: ${event.call_id}`);
const transcript = event.transcript as Array<unknown>;
console.log(`Transcript: ${transcript.length} messages`);
},
});
Test mode is designed for development only. It does not use any external APIs (except OpenAI for the LLM loop when no onMessage is provided).