Context variables
Context variables
Context variables let one agent serve many callers with personalized prompts. You write {placeholder} tokens in the agent's context (its system prompt and its greeting/opener), and supply a value for each one when a call starts — from a test call, the API, the public widget, or a campaign contact list. Both the prompt and the opener are rendered with the same value map before the agent speaks. See Building agents → Context for where these live in the builder.

The builder's Context step — write {placeholders} in the prompt or opener and they're detected automatically; mark each one required or optional.
You are calling {customer_name} about invoice {invoice_id}.
Their plan is {plan}. Be warm and concise.
With customer_name = "Alex", invoice_id = "INV-204", plan = "Pro", the agent's prompt becomes "You are calling Alex about invoice INV-204. Their plan is Pro."
Defining variables
Open the agent builder's Context step and type {name} tokens anywhere in the system prompt — or in the Opener text when "Speak opener when the call connects" is on. A Context variables panel lists every placeholder it detects in either field. For each one you choose:
- Optional (default) — if no value is supplied, the variable resolves to nothing (an empty value, stored as
null). - Required — a call is rejected if the value is missing or blank. Use this for variables the agent can't function without.
The list always tracks the placeholders in your prompt: add {city} and it appears; remove it and it drops off. Required flags are saved on the agent (under metadata.variables) and persist across edits.
Syntax rules
- Single braces only:
{name}. Double braces are an escape for a literal brace —{{renders as{and}}as}— so prompts containing JSON examples are left untouched. - Valid names start with a letter, digit, or underscore and may contain letters, digits,
_, spaces,.and-(up to 64 characters). An empty or malformed{ }is treated as plain text, not a variable. - The same
{name}may appear as many times as you like; every occurrence is substituted. - Substitution applies to the system prompt and the greeting/opener.
Supplying values
Where values come from depends on how the call starts.
Testing on the agent page
The agent page shows a Test variables card with one input per variable (required ones are marked). Fill them in, then use Test in browser or Place test call — the values are applied to that test conversation. Required variables must be filled before a test can start.
Over the API
Both call-start endpoints accept a variables object ({ "name": "value", … }):
POST /api/sessions/initiate-call— outbound phone calls.POST /api/sessions/init-web-call— browser/agent web calls.
curl -X POST https://api.telenow.ai/api/sessions/initiate-call \
-H "x-api-key: vai_live_…" -H "Content-Type: application/json" \
-d '{
"agentId": "…",
"mobileNumber": "+14155550123",
"variables": { "customer_name": "Alex", "invoice_id": "INV-204", "plan": "Pro" }
}'
If a required variable is missing or blank the request fails with 400 and the message lists the missing names. Optional variables you omit resolve to empty. See Sessions & calls.
Public widget & embed
When a published agent has variables, the public page and embedded widget ask the visitor for the required ones before connecting. You can also pre-fill values the embedding page already knows, via the script tag:
<!-- preferred: JSON, preserves capitalization -->
<script async src="https://telenow.ai/widget.js"
data-slug="YOUR_AGENT_SLUG"
data-vars='{"customer_name":"Alex","plan":"Pro"}'></script>
Pre-filled values are passed straight through; the visitor is only asked for required variables that weren't pre-filled. (HTML lowercases attribute names, so the data-var-<name> shorthand only works for all-lowercase variable names — use data-vars JSON otherwise.) The Publish panel generates a snippet listing your agent's variables.
Campaigns
For outbound campaigns, each contact supplies its own values. Upload a CSV or Excel file on the campaign page: the importer reads your columns and lets you map each one to a variable (it auto-matches columns whose names match). You can also add a single contact by hand, filling a field per variable. Each contact's values are substituted into that contact's call. See Campaigns API for the programmatic equivalent.
Built-in date & time variables
Some variable names are auto-filled by the platform at call time — you never need to supply them (the test panel marks them "Auto"). They resolve in the platform timezone (IST by default; operators can override with PLATFORM_UTC_OFFSET_MINUTES):
| Placeholder | Example value |
|---|---|
{current_ist_datetime} / {current_datetime} | Thursday, 11 June 2026, 12:15 PM |
{current_ist_weekday} / {current_weekday} | Thursday |
{today_date} | Thursday, 11 June 2026 |
{tomorrow_date} | Friday, 12 June 2026 |
{day_after_tomorrow_date} | Saturday, 13 June 2026 |
{current_date} | 2026-06-11 (ISO, for date arithmetic) |
{current_time} | 12:15 PM |
They work everywhere placeholders work — prompt, opener, every channel including inbound. Supplying your own value for one of these names overrides the auto-filled one.
Inbound calls
A call coming into a number has no caller to supply values, so every placeholder resolves to empty on inbound — except the built-in date/time variables above, which still auto-fill. Design prompts so they still read well when an optional variable is blank, and don't rely on required variables for inbound-only agents.
Tips
- Prefer optional variables with prompts that degrade gracefully ("…about your recent order{order_ref}") so a missing value never breaks the call.
- Keep variable names consistent with your CSV/Excel headers — the campaign importer auto-maps matching names.
- Variables are for values, not logic. Put behavior in the prompt; use variables to fill in the per-call specifics.