HIPAA, PCI DSS, TCPA consent tracking, SOC 2 Type II, STIR/SHAKEN attestation. The requirements document lists them all. None are AI problems.
Call control is table stakes
Warm transfers with context, hold music, conference bridging, IVR fallback, call recording with consent management. Enterprise buyers expect these on day one.
Audit trails are non-negotiable
Who accessed what, when, and why. Every call, every agent action, every data access must produce a reviewable record for regulated industries.
Building these features takes quarters, not sprints
HIPAA compliance alone requires encryption, access controls, audit logging, BAA coverage, retention policies, and breach notification procedures. Each is months of engineering.
Build a Voice AI Agent
fromsignalwire_agentsimportAgentBasefromsignalwire_agents.core.function_resultimportSwaigFunctionResultclassSupportAgent(AgentBase):def__init__(self):super().__init__(name="Support Agent",route="/support")self.prompt_add_section("Instructions",body="You are a customer support agent. ""Greet the caller and resolve their issue.")self.add_language("English","en-US","rime.spore:mistv2")@AgentBase.tool(name="check_order")defcheck_order(self,order_id:str):"""Check the status of a customer order. Args: order_id: The order ID to look up """returnSwaigFunctionResult(f"Order {order_id}: shipped, ETA April 2nd")agent=SupportAgent()agent.run()
import{AgentBase,FunctionResult}from'@signalwire/sdk';constagent=newAgentBase({name:'Support Agent',route:'/support',});agent.promptAddSection('Instructions','You are a customer support agent. Greet the caller and resolve their issue.');agent.addLanguage({name:'English',code:'en-US',voice:'rime.spore:mistv2'});agent.defineTool({name:'check_order',description:'Check the status of a customer order',parameters:{type:'object',properties:{order_id:{type:'string',description:'The order ID to look up'},},required:['order_id'],},handler:(args)=>{returnnewFunctionResult(`Order ${args.order_id}: shipped, ETA April 2nd`);},});agent.run();
packagemainimport("fmt""github.com/signalwire/signalwire-go/pkg/agent""github.com/signalwire/signalwire-go/pkg/swaig")funcmain(){a:=agent.NewAgentBase(agent.WithName("Support Agent"),agent.WithRoute("/support"),)a.PromptAddSection("Instructions","You are a customer support agent. Greet the caller and resolve their issue.")a.AddLanguage(map[string]any{"name":"English","code":"en-US","voice":"rime.spore:mistv2",})a.DefineTool(agent.ToolDefinition{Name:"check_order",Description:"Check the status of a customer order",Parameters:map[string]any{"type":"object","properties":map[string]any{"order_id":map[string]any{"type":"string","description":"The order ID to look up",},},"required":[]string{"order_id"},},Handler:func(argsmap[string]any,rawDatamap[string]any)*swaig.FunctionResult{orderID:=args["order_id"]returnswaig.NewFunctionResult(fmt.Sprintf("Order %v: shipped, ETA April 2nd",orderID),)},})a.Run()}
importcom.signalwire.sdk.agent.AgentBase;importcom.signalwire.sdk.swaig.FunctionResult;importjava.util.List;importjava.util.Map;publicclassSupportAgent{publicstaticvoidmain(String[]args)throwsException{varagent=AgentBase.builder().name("Support Agent").route("/support").build();agent.promptAddSection("Instructions","You are a customer support agent. "+"Greet the caller and resolve their issue.");agent.addLanguage("English","en-US","rime.spore:mistv2");agent.defineTool("check_order","Check the status of a customer order",Map.of("type","object","properties",Map.of("order_id",Map.of("type","string","description","The order ID to look up")),"required",List.of("order_id")),(toolArgs,rawData)->{varorderId=toolArgs.get("order_id");returnnewFunctionResult("Order "+orderId+": shipped, ETA April 2nd");});agent.run();}}
# frozen_string_literal: truerequire'signalwire'agent=SignalWire::AgentBase.new(name:'Support Agent',route:'/support')agent.prompt_add_section('Instructions','You are a customer support agent. Greet the caller and resolve their issue.')agent.add_language(name:'English',code:'en-US',voice:'rime.spore:mistv2')agent.define_tool(name:'check_order',description:'Check the status of a customer order',parameters:{'order_id'=>{'type'=>'string','description'=>'The order ID to look up'}})do|args,_raw|SignalWire::Swaig::FunctionResult.new("Order #{args['order_id']}: shipped, ETA April 2nd")endagent.run
<?phprequire'vendor/autoload.php';useSignalWire\Agent\AgentBase;useSignalWire\SWAIG\FunctionResult;$agent=newAgentBase(['name'=>'Support Agent','route'=>'/support']);$agent->promptAddSection('Instructions','You are a customer support agent. Greet the caller and resolve their issue.');$agent->addLanguage('English','en-US','rime.spore:mistv2');$agent->defineTool(name:'check_order',description:'Check the status of a customer order',parameters:['order_id'=>['type'=>'string','description'=>'The order ID to look up'],],handler:function(array$args):FunctionResult{returnnewFunctionResult("Order {$args['order_id']}: shipped, ETA April 2nd");});$agent->run();
#!/usr/bin/env perlusestrict;usewarnings;uselib'lib';useSignalWire::Agent::AgentBase;useSignalWire::SWAIG::FunctionResult;my$agent=SignalWire::Agent::AgentBase->new(name=>'Support Agent',route=>'/support',);$agent->prompt_add_section('Instructions','You are a customer support agent. Greet the caller and resolve their issue.');$agent->add_language(name=>'English',code=>'en-US',voice=>'rime.spore:mistv2');$agent->define_tool(name=>'check_order',description=>'Check the status of a customer order',parameters=>{order_id=>{type=>'string',description=>'The order ID to look up'},},handler=>sub{my($args,$raw)=@_;returnSignalWire::SWAIG::FunctionResult->new(response=>"Order $args->{order_id}: shipped, ETA April 2nd");},);$agent->run;
#include<signalwire/agent/agent_base.hpp>usingnamespacesignalwire;usingjson=nlohmann::json;classSupportAgent:publicagent::AgentBase{public:SupportAgent():AgentBase("Support Agent","/support"){prompt_add_section("Instructions","You are a customer support agent. ""Greet the caller and resolve their issue.");add_language({"English","en-US","rime.spore:mistv2"});define_tool({.name="check_order",.description="Check the status of a customer order",.parameters={{"order_id",{{"type","string"},{"description","The order ID to look up"}}}},.handler=[](constjson&args,constjson&){autoorder_id=args.value("order_id","unknown");returnswaig::FunctionResult("Order "+order_id+": shipped, ETA April 2nd");}});}};intmain(){SupportAgent().run();}
usingSignalWire.Agent;usingSignalWire.SWAIG;varagent=newAgentBase(newAgentOptions{Name="Support Agent",Route="/support"});agent.PromptAddSection("Instructions","You are a customer support agent. Greet the caller and resolve their issue.");agent.AddLanguage("English","en-US","rime.spore:mistv2");agent.DefineTool("check_order","Check the status of a customer order",new{type="object",properties=new{order_id=new{type="string",description="The order ID to look up"}},required=new[]{"order_id"}},(args,rawData)=>{varorderId=args.TryGetValue("order_id",outvarid)?id:"unknown";returnnewFunctionResult($"Order {orderId}: shipped, ETA April 2nd");});agent.Run();
usesignalwire::agent::AgentBase;usesignalwire::swaig::FunctionResult;useserde_json::json;fnmain(){letmutagent=AgentBase::builder().name("Support Agent").route("/support").build();agent.prompt_add_section("Instructions","You are a customer support agent. Greet the caller and resolve their issue.",&[]).add_language("English","en-US","rime.spore:mistv2");agent.define_tool("check_order","Check the status of a customer order",json!({"type":"object","properties":{"order_id":{"type":"string","description":"The order ID to look up"}},"required":["order_id"]}),Box::new(|args,_raw|{letorder_id=args.get("order_id").and_then(|v|v.as_str()).unwrap_or("unknown");FunctionResult::with_response(&format!("Order {order_id}: shipped, ETA April 2nd"))}),);agent.run();}
Build for Quarters or Ship on Day One
DIY Enterprise Features
HIPAA compliance: 3 to 6 months of engineering
Call recording with consent: 1 to 2 months
Warm transfers with SIP re-INVITEs: 2 to 4 weeks
Audit trail infrastructure: 1 to 2 months
PCI scope reduction: 2 to 3 months
SOC 2 Type II readiness: 6 to 12 months
Total: 2+ quarters before your first enterprise deal
SignalWire Platform
HIPAA: single BAA, AES-256 encryption, access controls
Recording: native consent management and retention policies
Transfers: warm and blind with conversation context
Audit: automatic compliance-ready records per call
PCI: architectural governance via hidden data layer
SOC 2: inherited from platform certification
Available from day one, no engineering required
Enterprise Readiness Checklist
Requirement
SignalWire
DIY Timeline
HIPAA compliance
Built in (single BAA)
3 to 6 months
Call recording + consent
Native platform feature
1 to 2 months
Warm transfers with context
Native platform feature
2 to 4 weeks
Audit trails
Automatic per call
1 to 2 months
PCI scope reduction
Hidden data layer
2 to 3 months
TCPA consent tracking
Platform-enforced
1 to 2 months
SOC 2 Type II
Inherited from platform
6 to 12 months
IVR fallback
Declarative routing
2 to 4 weeks
DTMF handling
Native (FreeSWITCH heritage)
1 to 2 weeks
Enterprise-Grade in Under 10 Minutes
1
Install the SDK
pip install signalwire-agents. Enterprise features are infrastructure, not add-ons.
2
Define your agent with the hidden data layer
PII lives in the hidden data layer, accessible to tool functions but invisible to the LLM context window.
3
Configure compliance and recording policies
Consent management, encrypted storage, retention policies, and audit logging from the platform.
4
Ship to your enterprise customer
HIPAA, PCI, TCPA, and SOC 2 controls are active from the first call. No retrofit required.
The FCC confirmed in February 2024 that AI-generated voice calls are subject to TCPA. Consent tracking, opt-out handling, and call disposition logging are not optional features.
FAQ
Can I use my own LLM with enterprise compliance features?
Yes. Enterprise features are infrastructure. Your AI handles conversations. SignalWire handles encryption, recording, consent, audit trails, and access controls regardless of your AI provider.
How do warm transfers preserve conversation context?
Calls carry session state, conversation summary, and authentication status through transfers. The receiving agent inherits the full context without the caller repeating information.
What does the hidden data layer protect?
Sensitive data (SSNs, payment details, medical records) lives in the hidden data layer. Tool functions access it. The LLM context window never receives it. The model cannot leak what it cannot see.
How does IVR fallback work?
When the AI cannot handle a request, the platform routes to a human with full call history and context. Fallback rules are defined declaratively per conversation step.
Is there a separate enterprise pricing tier?
Enterprise features are available on every plan. No enterprise-only pricing gates. Usage-based pricing with no minimum commitments.
Trusted by 2,000+ companies
Ship Enterprise-Grade Voice AI Today
Every feature your enterprise customer requires, available from the first call.