AI電話通話API:AIエージェントで実際の電話をかけ、受ける
Wixzel Voiceは、自社のSIPトランク経由で実際の電話を発信・着信するAIエージェントや、Webアプリやモバイルアプリの中で人と話すAIエージェントを構築するための音声AI APIです。1つのAPIキーと1つの前払い残高ですべての音声エンジンを利用でき、実際の使用量に応じて秒単位で課金されます。
最終更新日:
AI電話通話のためのWixzel Voice APIとは?
Wixzel Voice APIを使うと、定義したAIエージェントが自社のSIPトランクで実際の電話をかけたり受けたりします。電話番号とエージェントIDを指定してPOST /v1/callsを呼ぶだけで、実際の使用量に応じて秒単位で課金されます。
ひと言でいえば、Wixzel VoiceはAI電話エージェントを構築するための音声AI APIです。エージェントを定義するのはお客様で、通話を動かすのはWixzel VoiceというAI通話APIです。発信では、POST /v1/callsが番号に電話をかけてエージェントにつなぎます。着信では、inbound_agent_idを設定した電話番号が、その番号へのすべての電話に応答します。同じエージェントが、リアルタイムAPIを通じて電話回線なしでWebページやアプリの中で人と話すことも、MCPサーバーを通じてAIアシスタントから操作されることもできます。
Wixzel Voiceは「1つのAPIキー、1つの残高、すべての音声エンジン」です。音声認識、言語、音声のプロバイダーのアカウントはプラットフォームのものなので、Deepgram、ElevenLabs、OpenRouterのキーを用意する必要はありません。持ち込むのは電話回線だけで、「SIPトランクは持ち込み」です。Twilio、Telnyx、Plivo、または任意のSIPプロバイダーのトランクを使えます。
Wixzel VoiceでAI電話をかけるには?
APIキーとクレジットを用意したら、4つのリクエストで完了します。各レスポンスには次のリクエストに必要なIDが含まれ、スニペットではそれをシェル変数から読み込みます。
- 01
SIPトランクを接続する
通信事業者のホストと認証情報を指定します。パスワードは保存時に暗号化され、二度と返されません。レスポンスには、通信事業者が許可リストに登録する必要がある
platform_ip(現在は187.126.120.231)と、通信事業者が着信を送る先のorigination_uri(現在はsip:187.126.120.231:5090)が含まれます。cURLcurl https://api.voice.wixzel.com/v1/sip-trunks \ -H "Authorization: Bearer $WIXZEL_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "name": "My carrier", "host": "sip.carrier.example", "username": "acct123", "password": "..." }' - 02
電話番号を登録する
その通信事業者ですでに持っている番号を、E.164形式で指定します。Wixzel Voiceは電話番号の販売も移転(ポーティング)も行いません。トランクが自社のTwilio、Telnyx、Plivo、Vobiz、Vonageのアカウントに接続されている場合は、代わりに
POST /v1/phone-numbers/purchaseでそのアカウント上に新しい番号を購入できます。番号の料金は通信事業者が請求します。cURLcurl https://api.voice.wixzel.com/v1/phone-numbers \ -H "Authorization: Bearer $WIXZEL_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "phone_number": "+14155550100", "sip_trunk_id": "'"$TRUNK_ID"'" }' - 03
エージェントを作成する
話し言葉で書いた短いプロンプト、最初に話す言葉、音声(3つのモデル、または1つのリアルタイムモデル)を指定します。
opening_messageは必須です。これがないエージェントは無言で応答してしまうためです。outbound_phone_number_idを指定すると、手順2の番号が発信者番号になります。cURLcurl https://api.voice.wixzel.com/v1/agents \ -H "Authorization: Bearer $WIXZEL_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "name": "Support", "system_prompt": "You are a concise support agent.", "opening_message": "Hi, how can I help?", "voice": { "stt": { "model": "deepgram/nova-3" }, "llm": { "model": "openrouter/gpt-4o-mini" }, "tts": { "model": "elevenlabs/eleven_flash_v2_5" } }, "outbound_phone_number_id": "'"$NUMBER_ID"'" }' - 04
電話をかける
発信先とエージェントを指定します。
Idempotency-Keyは必須です。ネットワークのタイムアウトでは、通話が発信されたかどうかがわからないためです。同じキーで再試行すると、二重に発信せずに元の通話が返ります。レスポンスは201で、通話はstatus: "queued"です。cURLcurl https://api.voice.wixzel.com/v1/calls \ -H "Authorization: Bearer $WIXZEL_API_KEY" \ -H "Idempotency-Key: $(uuidgen)" \ -H "Content-Type: application/json" \ -d '{ "to": "+14155551234", "agent_id": "'"$AGENT_ID"'" }'
最初の通話がつながる前に、通信事業者でplatform_ipを許可リストに登録する必要があります。Twilio, Telnyx, Plivo, Vonage, Bandwidth, Exotel, Vobiz, Mobilyでその設定がどこにあるかは、通信事業者のガイドで説明しています。
TypeScriptやDartからAI電話をかけるには?
公式SDKは、Node、ブラウザ、エッジランタイムでTypeScriptとJavaScriptに使えるnpmのwixzel-voiceと、DartとFlutterに使えるpub.devのwixzel_voiceです。どちらもすべてのエンドポイントに対応し、レート制限時に再試行し、費用が発生するパスではIdempotency-Keyを自動で生成します。その他の言語では、通常のHTTP APIとOpenAPIドキュメントを使います。
import { WixzelVoice } from 'wixzel-voice';
const client = new WixzelVoice({ apiKey: process.env.WIXZEL_API_KEY! });
// 1. Connect your SIP trunk.
const trunk = await client.sipTrunks.create({
name: 'My carrier',
host: 'sip.carrier.example',
username: 'acct123',
password: process.env.CARRIER_PASSWORD!,
});
console.log('Allowlist', trunk.platform_ip, 'and send inbound calls to', trunk.origination_uri);
// 2. Register a number you own on it.
const number = await client.phoneNumbers.create({
phone_number: '+14155550100',
sip_trunk_id: trunk.id,
});
// 3. Create the agent, with that number as its caller ID.
const agent = await client.agents.create({
name: 'Support',
system_prompt: 'You are a concise support agent.',
opening_message: 'Hi, how can I help?',
voice: {
stt: { model: 'deepgram/nova-3' },
llm: { model: 'openrouter/gpt-4o-mini' },
tts: { model: 'elevenlabs/eleven_flash_v2_5' },
},
outbound_phone_number_id: number.id,
});
// 4. Place the call. The SDK sends the Idempotency-Key for you.
const call = await client.calls.create({ to: '+14155551234', agent_id: agent.id });
// Inbound: calls to the number are answered by the same agent.
await client.phoneNumbers.update(number.id, { inbound_agent_id: agent.id });
// Later: what happened, what it cost, what was said.
const detail = await client.calls.retrieve(call.id);
console.log(detail.status, detail.cost_micros, detail.failure_code, detail.failure_reason);
for (const line of detail.transcript) console.log(line.role, line.content);import 'dart:io';
import 'package:wixzel_voice/wixzel_voice.dart';
Future<void> main() async {
final client = WixzelVoice(apiKey: Platform.environment['WIXZEL_API_KEY']!);
// 1. Connect your SIP trunk.
final trunk = await client.sipTrunks.create(CreateSipTrunk(
name: 'My carrier',
host: 'sip.carrier.example',
username: 'acct123',
password: Platform.environment['CARRIER_PASSWORD']!,
));
print('Allowlist ${trunk.platformIp}; send inbound calls to ${trunk.originationUri}');
// 2. Register a number you own on it.
final number = await client.phoneNumbers.create(CreatePhoneNumber(
phoneNumber: '+14155550100',
sipTrunkId: trunk.id,
));
// 3. Create the agent, with that number as its caller ID.
final agent = await client.agents.create(CreateAgent(
name: 'Support',
systemPrompt: 'You are a concise support agent.',
openingMessage: 'Hi, how can I help?',
voice: VoiceConfig.composed(
stt: const SttConfig(model: 'deepgram/nova-3'),
llm: const LlmConfig(model: 'openrouter/gpt-4o-mini'),
tts: const TtsConfig(model: 'elevenlabs/eleven_flash_v2_5'),
),
outboundPhoneNumberId: number.id,
));
// 4. Place the call. The SDK sends the Idempotency-Key for you.
final call = await client.calls.create(CreateCall(
to: '+14155551234',
agentId: agent.id,
));
// Inbound: calls to the number are answered by the same agent.
await client.phoneNumbers.update(
number.id, UpdatePhoneNumber(inboundAgentId: agent.id));
// Later: what happened, what it cost, what was said.
final detail = await client.calls.retrieve(call.id);
print('${detail.status} ${detail.costMicros} ${detail.failureCode}');
for (final line in detail.transcript) {
print('${line.role}: ${line.content}');
}
client.close();
}Wixzel VoiceでAIエージェントが着信に応答するには?
電話番号にinbound_agent_idを設定すると、その番号へのすべての電話にそのエージェントが応答します。設定しない場合、その番号への着信は拒否されます。
curl -X PATCH https://api.voice.wixzel.com/v1/phone-numbers/$NUMBER_ID \
-H "Authorization: Bearer $WIXZEL_API_KEY" \
-H "Content-Type: application/json" \
-d '{ "inbound_agent_id": "'"$AGENT_ID"'" }'もう半分は通信事業者側の設定です。着信をトランクのorigination_uri(現在はsip:187.126.120.231:5090)に届ける必要があります。これは許可リストとは別の設定で、通信事業者のコンソールの別の場所にあります。これが設定されていないと、番号はまったく鳴りません。通信事業者に電話の送り先がないため、どのログにも何も記録されません。すべての着信はdirection: "inbound"と双方の番号とともに記録され、inboundCall webhookが送信されます。
Wixzel Voiceの通話記録は何を返しますか?
POST /v1/callsはすぐに通話を返します(status: "queued")。GET /v1/calls/{id}は通話中も終了後も完全な記録を返します。また、X-Wixzel-Signatureで署名されたcallCompleted webhookが通話の終了をサーバーに知らせるため、ポーリングは不要です。
| フィールド | 内容 |
|---|---|
| status | queued、ringing、in-progress、completed、failed、busy、no-answer、canceledのいずれか。 |
| direction / channel | outboundまたはinbound。トランク経由の通話はphone、ブラウザやアプリからのリアルタイムセッションはweb。 |
| duration_seconds | 通話が終了した後の、通話の長さ。 |
| engine | エージェントが使った音声エンジン。 |
| cost_micros | 通話の費用(micro-USD、1,000,000 = $1.00)。通話の精算時に記録されます。つながらなかった通話はnullで、費用はかかりません。 |
| transcript | すべての発話のターン。role(user、assistant、system)、content、UTCのタイムスタンプを含みます。GET /v1/calls/{id}/transcriptでも取得できます。 |
| summary / recording_url | 通話を録音した場合はその録音。APIで発信した通話ではsummaryは空なので、文字起こしを読んでください。 |
| failure_code / failure_reason | つながらなかった通話の場合:通信事業者からのQ.850の原因コード(分岐の判定に使える安定した値)と、その対処法をわかりやすく説明した文。 |
| transfers | 発信者を人につなごうとした試行ごとに1件。それぞれの状態、呼び出し時間、SIPの原因コードを含みます。 |
| metadata | POST /v1/callsに付けたフラットな文字列のマップを、そのまま返します。モデルには送られません。 |
cost_microsの1マイクロドル単位まで、GET /v1/usage/eventsの使用量の行で内訳がわかります。認識した音声の秒数、モデルの入力と出力のトークン数、合成した文字数、1分あたりのオーケストレーション料金です。
AI電話がつながらなかった場合はどうなりますか?
通信事業者が拒否した通話はstatus: "failed"(またはbusy、no-answer)となり、failure_codeとfailure_reasonが付き、cost_micros: nullになります。費用はかからず、その通話のために確保したクレジットは解放されます。failure_codeは通信事業者からのQ.850の原因コードで、分岐の判定に使える安定した値です。failure_reasonは、その対処法をわかりやすく説明します。
発信前に拒否され、費用がかからないリクエストもあります。最初の15秒をまかなえない残高は402 insufficient_credits、Idempotency-Keyのない直接のリクエストは400 missing_idempotency_key、同時通話数の上限を超える通話は503で拒否されます。 すべての失敗コードと拒否、それぞれの対処法は通信事業者のページにあります。
Wixzel VoiceでのAI電話の費用は?
1回の通話のエンジン費用を、一般的な発話速度で、メーターが課金に使う価格表から計算しています。各価格には1分あたり$0.012のオーケストレーション料金が含まれます。通話は実際の使用量に応じて秒単位で課金されるため、90秒の通話は3分の通話の約半分の費用です。通信は自社のトランクを通信事業者の料金で使うため含まれません。
| エンジン | パイプライン | 1分の通話 | 3分の通話 | 5分の通話 |
|---|---|---|---|---|
| classic | Deepgram + GPT-4o-mini + ElevenLabs | $0.0867 | $0.2601 | $0.4335 |
| sarvam | Sarvam、インドの言語をエンドツーエンドで処理 | $0.0617 | $0.1851 | $0.3085 |
| gemini-live | Gemini Live、ネイティブ音声 | $0.0491 | $0.1473 | $0.2455 |
| deepgram-agent | Deepgram Voice Agent | $0.1851 | $0.5553 | $0.9255 |
プリペイド制で、$5からクレジットをチャージします。サブスクリプションも無料プランもありません。現在最も安いエンジンはgemini-liveで、1分あたり$0.0491です。自分の使い方で見積もる。
AI電話通話のためのWixzel Voice APIの制限は?
- Wixzel Voiceは稼働中で、実際の通話を処理しています。挙動の変更は日付付きの
Wixzel-Versionヘッダーのもとで提供され、既存のキーは作成時の挙動を維持します。 - 同時通話数はデフォルトで1アカウントあたり5件で、依頼に応じて引き上げます。Webやアプリのセッションも同じ上限に数えます。
- 人への転送はブラインド転送のみで、発信者は登録した番号にそのままつながれます。アテンデッド転送は実装しておらず、テスト通話やWeb・アプリのセッションでは転送を使えません。
- Wixzel Voiceは電話番号の販売も移転(ポーティング)も行わず、電話の通話には自社のSIPトランクが必要です。自社のTwilio、Telnyx、Plivo、Vobiz、Vonageのアカウント上で番号を購入することはでき、請求は通信事業者から届きます。
- Webやアプリのセッションの音声はG.711 µ-law、8 kHzで、広帯域ではなく電話と同じ品質です。
- APIリクエストはキーごとに1秒あたり10件、バースト20件まで。レート制限されたリクエストは課金されません。
- APIと保存データはインドのムンバイにあります。通話中は米国とインドの音声・言語プロバイダーが音声とテキストを処理し、sarvamエンジンの音声はインドで処理されます。
- 無料プランもトライアルクレジットもありません。最低チャージ額は$5です。無料で使えるのは、コンソールから自分のエージェントと話す1アカウントあたり5分だけです。
よくある質問
AI電話通話APIとは何ですか?
POST /v1/callsが自社のSIPトランクで電話をかけ、inbound_agent_idを設定した電話番号は同じ方法で着信に応答します。Wixzel VoiceはAI通話APIですか、それとも完成した通話エージェントですか?
AI電話の通話料金はいくらですか?
AIエージェントは発信だけでなく着信にも応答できますか?
PATCH /v1/phone-numbers/{id}で電話番号にinbound_agent_idを設定すると、その番号への電話にそのエージェントが応答します。通信事業者は、トランクが返すorigination_uriに着信を送る必要があります。inbound_agent_idがない場合、その番号への着信は拒否されます。AIエージェントは発信者を人に転送できますか?
human_transferでエージェントに登録した転送先の1つに、自社のSIPトランク経由で通話中の電話を渡します。エージェントが先に相手と話すアテンデッド転送は実装しておらず、テスト通話やWeb・アプリのセッションでは転送を使えません。同時にいくつのAI通話を処理できますか?
無料トライアルはありますか?
402 insufficient_creditsで拒否されます。次に読むもの
最初の音声エージェントを構築

