Skip to content

About

SignalWire AI Agents Typescript SDK, Relay and REST

Resources

Code of conduct

Contributing

Security policy

Stars

3 stars

Watchers

1 watching

Forks

Latest commit

 

History

709 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

SignalWire SDK for TypeScript

Build AI voice agents, control live calls over WebSocket, and manage every SignalWire resource over REST, all from one package.

Documentation · Report an Issue · npm

Discord MIT License GitHub Stars


export {}; // treat each example as a module (top-level await)
declare global {
  const callId: string;
  const signingKey: string;
  const signatureHeader: string;
  const fullUrl: string;
  const rawBodyString: string;
  const requestParams: Record<string, string>;
}

What's in this SDK

Capability What it does Quick link
AI Agents Build voice agents that handle calls on their own. The platform runs the AI pipeline, and your code defines the persona, tools, and call flow. Agent Guide
RELAY Client Control live calls and SMS/MMS in real time over WebSocket: answer, play, record, collect DTMF, conference, transfer, and more RELAY docs
REST Client Manage SignalWire resources over HTTP: phone numbers, SIP endpoints, Fabric AI agents, video rooms, messaging, and the other REST API namespaces REST docs

Install the SDK from npm:

npm install @signalwire/sdk

The package installs its own documentation. npx sw-tsdocs prints a map of the SDK for the installed version, with the docs and examples on disk, and npx sw-tsdocs api <name> reads signatures and JSDoc from the installed declarations. If you're a coding agent working with the SDK, start there:

npx sw-tsdocs                 # the map: what the SDK does and where to start
npx sw-tsdocs agents          # one topic: concepts, files to read, examples, API
npx sw-tsdocs api AgentBase   # a signature, JSDoc and members

AI Agents

Each agent is a self-contained microservice that generates SWML (SignalWire Markup Language) and handles SWAIG (SignalWire AI Gateway) tool calls. The SignalWire platform runs the entire AI pipeline (STT, LLM, TTS), and your agent defines the behavior.

import { AgentBase, FunctionResult } from '@signalwire/sdk';

const agent = new AgentBase({
  name: 'my-agent',
  route: '/agent',
});

agent.addLanguage({ name: 'English', code: 'en-US', voice: 'inworld.Mark' });
agent.promptAddSection('Role', { body: 'You are a helpful assistant.' });

agent.defineTool({
  name: 'get_time',
  description: 'Get the current time',
  parameters: {},
  handler: () => new FunctionResult(`The time is ${new Date().toLocaleTimeString()}`),
});

agent.run(); // Starts HTTP server on port 3000

In a clone of this repository, swaig-test checks an agent without running a server. These commands list the example agent's tools, print its SWML, and call its get_time tool:

npx tsx src/cli/swaig-test.ts examples/simple-agent.ts --list-tools
npx tsx src/cli/swaig-test.ts examples/simple-agent.ts --dump-swml
npx tsx src/cli/swaig-test.ts examples/simple-agent.ts --exec get_time

Agent Features

An agent built on AgentBase gets these features:

  • Prompt Object Model (POM): structured prompt composition with promptAddSection()
  • SWAIG tools: functions defined with defineTool() that the AI calls mid-conversation. A tool's result is context for the model, and its actions can control the call.
  • Skills system: capabilities added in one line, such as await agent.addSkill(new DateTimeSkill())
  • Contexts and steps: structured multi-step workflows with navigation control
  • DataMap tools: tools that run on SignalWire's servers, calling REST APIs without your own webhook
  • Dynamic configuration: a per-request copy of the agent, configured for each call, for multi-tenant deployments
  • Call flow control: pre-answer, post-answer, and post-AI verb insertion
  • Prefab agents: ready-to-use archetypes (InfoGatherer, Survey, FAQ, Receptionist, Concierge)
  • Multi-agent hosting: multiple agents on a single server with AgentServer
  • SIP routing: SIP calls routed to agents by username
  • Session state: global data for the call, and post-prompt summaries when it ends
  • Security: auto-generated basic auth, per-call tool tokens, webhook signature validation, and TLS support
  • Serverless: automatic detection of Lambda, CGI, Google Cloud Functions, and Azure Functions

Agent Examples

The examples/ directory contains more than 50 working examples. These show the main features:

Example What it demonstrates
simple-agent.ts POM prompts, SWAIG tools, multilingual support, LLM tuning
contexts-steps.ts Multi-step workflow with context switching and step navigation
datamap-tools.ts Server-side API tools without webhooks
skills-demo.ts Loading built-in skills (datetime, math)
call-flow.ts Call flow verbs, debug events, FunctionResult actions
session-state.ts onSummary, global data, post-prompt summaries
multi-agent.ts Multiple agents on one server
serverless-lambda.ts AWS Lambda deployment
dynamic-config.ts Per-request dynamic configuration, multi-tenant routing

See examples/README.md for the full list organized by category.


RELAY Client

Real-time call control and messaging over WebSocket. The RELAY client connects to SignalWire via the Blade protocol and gives you imperative, async control over live phone calls and SMS/MMS.

The RELAY client connects with SIGNALWIRE_PROJECT_ID, SIGNALWIRE_API_TOKEN and SIGNALWIRE_SPACE from the environment. This client answers each call on the default context, plays a greeting, and hangs up:

import { RelayClient, Call } from '@signalwire/sdk';

const client = new RelayClient({
  contexts: ['default'],
});

client.onCall(async (call: Call) => {
  await call.answer();
  const action = await call.play([{ type: 'tts', text: 'Welcome to SignalWire!' }]);
  await action.wait();
  await call.hangup();
});

client.run();

The RELAY client provides:

  • Calling methods for play, record, collect, detect, tap, stream, AI, conferencing, and more
  • SMS/MMS messaging with delivery tracking
  • Action objects with wait(), stop(), pause(), resume()
  • Auto-reconnect with exponential backoff

See the RELAY documentation for the full guide, API reference, and examples.


REST Client

Typed HTTP client for managing SignalWire resources and controlling calls over HTTP. It sends standard fetch requests, with no WebSocket.

This client creates a Fabric AI agent, plays text on a live call, searches for phone numbers and searches Datasphere documents:

import { RestClient } from '@signalwire/sdk';

const client = new RestClient({
  project: '...',
  token: '...',
  host: 'example.signalwire.com',
});

await client.fabric.aiAgents.create({ name: 'Support Bot', prompt: { text: 'You are helpful.' } });
await client.calling.play(callId, [{ type: 'tts', params: { text: 'Hello!' } }]);
await client.phoneNumbers.search({ areacode: '512' });
await client.datasphere.documents.search('billing policy');

The REST client provides:

  • Namespaced API surfaces: Fabric, Calling, Video, Datasphere, Phone Numbers, SIP, Queues, Recordings, and more
  • Node's built-in fetch, with no HTTP client dependency
  • Plain object returns: the raw JSON, with no wrapper objects

See the REST documentation for the full guide, API reference, and examples.


Webhook Verification

Your Signing Key verifies that an inbound webhook (a status callback, a messaging callback, or a SWML or SWAIG request) came from SignalWire. validateRequest replaces the Compatibility API's RestClient.validateRequest() and validateRequestWithBody(). It's a top-level export of @signalwire/sdk, so you don't need the separate @signalwire/compatibility-api package.

This fragment checks a form-encoded webhook, then a JSON one:

import { validateRequest } from '@signalwire/sdk';

// Parsed form params, from a cXML (Compatibility API) webhook.
const ok = validateRequest(signingKey, signatureHeader, fullUrl, requestParams);

// The raw request body, for JSON and SWML webhooks, or a cXML body that
// carries bodySHA256.
const okBody = validateRequest(signingKey, signatureHeader, fullUrl, rawBodyString);

validateRequest folds both Compatibility API methods into one call: pass a parsed params object / Map / array of tuples for form-encoded webhooks, or the raw body string to additionally verify the bodySHA256 the platform includes for JSON/SWML payloads. It returns true on a match, false otherwise, and throws if the Signing Key is missing.

validateWebhookSignature(signingKey, signature, url, rawBody) is the lower-level check of one signature over a raw body.

SignalWire also sends an HMAC-SHA256 signature in the X-SignalWire-Sha256-Signature header on JSON and SWML webhooks. It signs the same message, the URL followed by the raw body, and you can check it with validateWebhookSignatureSha256(signingKey, signature, url, rawBody). An agent's built-in validation, and webhookValidationMiddleware, check that header first when it's present and fall back to X-SignalWire-Signature.


Installation

One package covers agents, RELAY and REST. It requires Node.js 22 or later:

npm install @signalwire/sdk

Documentation

The reference documentation is at developer.signalwire.com/sdks/agents-sdk.

The docs/ directory has these guides. They're installed with the package, with the examples: npx sw-tsdocs path prints where.

Getting Started

Core Features

Skills and Extensions

Deployment

Reference

Environment Variables

Variable Used by Description
SIGNALWIRE_PROJECT_ID RELAY, REST Project identifier
SIGNALWIRE_API_TOKEN RELAY, REST API token
SIGNALWIRE_SPACE RELAY, REST Space hostname (e.g. example.signalwire.com)
SIGNALWIRE_REST_BASE_URL REST Override the REST base URL with a full http(s):// URL (local mock / private space / proxy). Precedence: host option > SIGNALWIRE_REST_BASE_URL > SIGNALWIRE_SPACE.
SIGNALWIRE_REST_CA_FILE REST Path to a PEM CA bundle to trust for HTTPS REST requests (private/self-signed certificates).
SIGNALWIRE_RELAY_HOST RELAY Override the RELAY WebSocket host (advanced/testing). Precedence: host option > SIGNALWIRE_RELAY_HOST > SIGNALWIRE_SPACE > built-in default.
SIGNALWIRE_RELAY_SCHEME RELAY Override the RELAY WebSocket scheme (ws/wss; default wss). Precedence: scheme option > SIGNALWIRE_RELAY_SCHEME > wss; any value other than ws/wss falls back to wss.
SWML_BASIC_AUTH_USER Agents Basic auth username (default: auto-generated)
SWML_BASIC_AUTH_PASSWORD Agents Basic auth password (default: auto-generated)
SWML_PROXY_URL_BASE Agents Base URL when behind a reverse proxy
SWML_SSL_ENABLED Agents Enable HTTPS (true, 1, yes)
SWML_SSL_CERT_PATH Agents Path to SSL certificate
SWML_SSL_KEY_PATH Agents Path to SSL private key
SIGNALWIRE_LOG_LEVEL All Logging level (debug, info, warn, error)
SIGNALWIRE_LOG_MODE All Set to off to suppress all logging

Testing

The scripts under scripts/ lint, format and test the SDK. They install their dependencies on first run and work from any directory:

# Run the test suite (optional filter passed through to vitest)
bash scripts/run-tests.sh
bash scripts/run-tests.sh AgentBase

# Format the tree (or --check to verify without writing)
bash scripts/run-format.sh
bash scripts/run-format.sh --check

# Lint (tsc + eslint; --fix to autofix)
bash scripts/run-lint.sh

These npm scripts build the SDK and watch for changes:

# Build
npm run build

# Dev mode (watch + rebuild)
npm run dev

# Watch-mode tests
npm run test:watch

License

MIT. See LICENSE for details.

About

SignalWire AI Agents Typescript SDK, Relay and REST

Resources

Code of conduct

Contributing

Security policy

Stars

3 stars

Watchers

1 watching

Forks

Releases

Packages

Contributors

Languages