Skip to navigation

addPerCallConfig

View as MarkdownOpen in Claude

Register a per-request configuration callback, keeping any already registered. Same signature and contract as setDynamicConfigCallback(), except that callbacks accumulate instead of replacing each other. They run in registration order on the same per-request copy of the agent, so a later callback sees what an earlier one configured.

Prefer this form when composing. A base class and a subclass, or an agent and a helper, can each register what they own without knowing about the other. Calling setDynamicConfigCallback() afterwards replaces every callback registered so far.

Callbacks run for every request of a call: the SWML fetch, each SWAIG function call, and the summary delivery. Only the SWML fetch carries the caller’s data, such as user variables, so verify the caller there, remember the call_id, and check it on later requests.

Parameters

cb
DynamicConfigCallbackRequired

A function with the signature (queryParams: Record<string, string>, bodyParams: SwmlRequestData, headers: Record<string, string>, agent: AgentBase) => void | Promise<void>. agent is the per-request copy. Configure that object, never the agent itself, or the configuration leaks across callers.

Returns

AgentBase — Returns this for method chaining.

Rejecting a call

A callback can’t refuse the request, but it can decide what the call does. Build the agent to fail closed: add a goodbye with addPostAnswerVerb('play', …) and addPostAnswerVerb('hangup', {}), and no tools, so a call hears the message and hangs up before the ai verb runs. For a call the callback accepts, add the tools to the copy and call clearPostAnswerVerbs() last.

A callback that throws is logged, and the copy is rendered as it stands, so a failure before that last step leaves the goodbye in place. A throwing callback also stops the ones after it without restoring verbs an earlier one cleared, so the callback that clears them must be registered last.

Example

import { AgentBase } from '@signalwire/sdk';
const agent = new AgentBase({ name: 'dispatch', route: '/dispatch' });
agent.setPromptText('You are Ada, the dispatcher for Bayview Taxi.');
agent.addPerCallConfig((queryParams, bodyParams, headers, copy) => {
if (queryParams.lang === 'es') {
copy.addLanguage({ name: 'Spanish', code: 'es-MX', voice: 'rime.marsh' });
}
});
agent.addPerCallConfig((queryParams, bodyParams, headers, copy) => {
copy.setGlobalData({ tenant: queryParams.tenant ?? 'default' });
});
await agent.serve();