Inference API
Voice
POST /v1/realtime/client_secrets
为浏览器端实时 API 连接创建临时客户端密钥,用于身份验证。
请求体
expires_after(object)seconds(integer) — 客户端密钥过期前的秒数。最大值:3600(1小时)。省略时默认为 600(10分钟)。
session(object | null) — 可选的初始会话配置,绑定到客户端密钥。此 JSON 值与密钥一起存储,并在 WebSocket 连接打开时应用。model("grok-voice-latest" | "grok-voice-think-fast-2.0" | "grok-voice-think-fast-1.0") — 会话使用的模型。使用 grok-voice-latest 以获得最佳体验。reasoning(object) — 支持推理的模型的推理设置。effort("high" | "none") — 控制模型是否使用推理。默认为high。
响应体
value(string, required) — 临时令牌值。在 WebSocketAuthorization标头中用作 Bearer 令牌,或在sec-websocket-protocol标头中使用前缀xai-client-secret.。expires_at(integer, required) — 此客户端密钥过期的 Unix 时间戳(秒)。
代码示例
curl -s https://api.x.ai/v1/realtime/client_secrets \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $XAI_API_KEY" \
-d '{
"expires_after": {
"seconds": 300
}
}'const response = await fetch("https://api.x.ai/v1/realtime/client_secrets", {
method: "POST",
headers: {
Authorization: `Bearer ${process.env.XAI_API_KEY}`,
"Content-Type": "application/json",
},
body: JSON.stringify({
expires_after: {
seconds: 300,
},
}),
});
const data = await response.json();
console.log(JSON.stringify(data, null, 2));import json
import os
import requests
response = requests.post(
"https://api.x.ai/v1/realtime/client_secrets",
headers={
"Authorization": f"Bearer {os.environ['XAI_API_KEY']}",
"Content-Type": "application/json",
},
json={
"expires_after": {
"seconds": 300,
},
},
)
print(json.dumps(response.json(), indent=2))响应示例:
{
"value": "xai-realtime-client-secret-abc123...",
"expires_at": 1750000000
}POST /v2/phone-numbers
为 API 控制的 SIP 通话创建电话号码。
请求体
origin("xai_provisioned" | "byo_trunk", required) — 对于客户拥有的直接 SIP 号码,使用byo_trunk。name(string, required)agent_id(string) — 将通话路由到此代理。与webhook互斥。area_code(string) — 仅 xAI 分配:可选的 3 位美国区号过滤器。phone_number(string) — 仅 BYO 中继:客户拥有的 E.164 格式电话号码。sip_auth(object)auth_username(string) — SIP 摘要用户名。必须与auth_password一起提供。auth_password(string) — SIP 摘要密码。加密存储,读取端点永不返回。allowed_addresses(array<string>) — 允许发送 INVITE 的源 CIDR 范围。
webhook(object)name(string) — 可选显示名称。省略时默认为电话号码的名称。url(string, required) — xAI 向其发送签名的realtime.call.incoming事件的 URL。auth_url(string) — 可选的 OAuth 令牌交换 URL,与auth_token配对使用。auth_token(string) — 可选的 Bearer 凭据,或与auth_url配对使用的 OAuth 客户端凭据。
响应体
phone_number(object)phone_number_id(string)team_id(string)phone_number(string) — E.164 格式的电话号码。name(string)agent_id(string) — 此号码路由到的代理。webhook_id(string) — 此号码向其发送realtime.call.incoming事件的 Webhook 端点。origin("xai_provisioned" | "byo_trunk")sip_host(string) — 您的运营商或 PBX 应将呼叫路由到的 SIP 主机。inbound_trunk_id(string) — 只读 SIP 中继标识符。sip_auth(object)auth_username(string) — SIP 摘要用户名。仅在配置摘要身份验证时存在。allowed_addresses(array<string>) — 允许发送 INVITE 的源 CIDR 范围。
created_at(string)updated_at(string)agent_name(string)
webhook(object)webhook_id(string)dispatch_signing_secret(string) — 标准 Webhooks v1 HMAC-SHA256 签名密钥。仅返回一次,无法恢复。
响应示例:
{
"phone_number": {
"phone_number_id": "phone_abc123",
"team_id": "00000000-0000-0000-0000-000000000000",
"phone_number": "+18005550199",
"name": "Support SIP trunk",
"webhook_id": "webhook_abc123",
"origin": "byo_trunk",
"sip_host": "sip.voice.x.ai",
"sip_auth": {
"allowed_addresses": [
"203.0.113.0/24"
]
},
"created_at": "2026-06-19T00:00:00Z",
"updated_at": "2026-06-19T00:00:00Z"
},
"webhook": {
"webhook_id": "webhook_abc123",
"dispatch_signing_secret": "whsec_..."
}
}Realtime
WebSocket 端点:wss://api.x.ai/v1/realtime
通过 WebSocket 与 Grok 模型进行实时语音对话。连接以 HTTP GET 开始,然后升级为 WebSocket(状态 101)。连接后,客户端和服务器交换 JSON 消息以配置会话、流式传输音频和接收响应。对于 SIP 通话,使用来自 realtime.call.incoming webhook 的 call_id 进行连接。
完整模式和示例:/voice-realtime.ws.json
查询参数
call_id(string, optional) — 来自realtime.call.incomingwebhook 的 SIP 通话标识符。提供时,WebSocket 连接到该入站 SIP 通话。使用 xAI API 密钥进行身份验证;SIPcall_id会话不支持临时客户端密钥。model(string, optional, default: grok-voice-latest) — 会话使用的模型。提供call_id时被忽略,因为会话绑定到入站 SIP 通话。对于直接 WebSocket 会话,使用 grok-voice-latest 以获得最佳体验。reasoning.effort(string, optional, default: high) — 控制模型是否使用推理。默认为high。
客户端消息
session.update— 更新会话配置,如系统提示、语音、音频格式、轮次检测和工具。input_audio_buffer.append— 将 base64 编码的音频数据块追加到输入缓冲区。服务器不发送相应的消息。input_audio_buffer.commit— 将音频缓冲区提交为用户消息。仅在turn_detection类型为null时可用。由服务器的input_audio_buffer.committed确认。conversation.item.create— 创建新的对话项。可以是用户文本消息、用于历史记录种子的助手文本消息、用于工具使用历史记录种子的函数调用,或函数调用输出。input_audio_buffer.clear— 清除输入音频缓冲区。用于丢弃任何待处理的音频数据而不提交它。conversation.item.delete— 按 ID 删除对话项。服务器通过conversation.item.deleted事件确认删除。conversation.item.truncate— 截断之前的助手音频消息项。删除指定持续时间后的音频和转录内容,仅保留该点之前的内容。服务器通过conversation.item.truncated事件确认。response.create— 请求服务器创建新的助手响应。使用服务器端 VAD 时自动处理。response.cancel— 取消正在进行的响应。在 VAD 模式下,中断是自动的 — 在非 VAD 模式下使用此方法手动取消。
服务器消息
session.created— 在 WebSocket 连接时自动发送。包含会话配置。conversation.created— 连接上的第一条消息。通知客户端会话已创建。session.updated— 确认客户端的 session.update 消息,表示会话已配置。input_audio_buffer.speech_started— 通知服务器的 VAD 检测到语音开始。仅在 server_vad 轮次检测时可用。input_audio_buffer.speech_stopped— 通知服务器的 VAD 检测到语音结束。仅在 server_vad 轮次检测时可用。input_audio_buffer.committed— 输入音频缓冲区已作为用户消息提交。input_audio_buffer.timeout_triggered—turn_detection.idle_timeout_ms空闲计时器触发:助手响应完成后,在配置的持续时间内未检测到用户语音。服务器提交静音用户轮次并生成主动检查。input_audio_buffer.cleared— 确认输入音频缓冲区已清除。conversation.item.deleted— 确认对话项已删除。conversation.item.added— 新的用户或助手消息已添加到对话历史记录中。conversation.item.truncated— 确认对话项已被截断。作为对conversation.item.truncate客户端事件的响应发送。conversation.item.input_audio_transcription.completed— 用户输入的音频转录已完成。conversation.item.input_audio_transcription.updated— 用户音频输入的流式转录更新。在用户说话时发出,提供最终的completed事件之前的累积转录。注意,这是累积转录,可能对之前的更新转录有修正 — 这与转录增量不同。仅在会话配置中将audio.input.transcription.model设置为grok-transcribe时发出。对于显示实时字幕很有用。input_audio_buffer.dtmf_event_received— 在 SIP 会话上检测到 DTMF 音调(电话按键)。仅限 SIP — 在直接 WebSocket 连接上不发出。数字在服务器端缓冲,并在按下#键、2.5 秒空闲或用户开始说话时作为文本消息刷新到模型。response.created— 新的助手响应轮次正在进行中。此轮次的音频增量共享相同的 response_id。response.output_item.added— 新的助手响应项已添加到消息历史记录中。response.output_item.done— 输出项已完成。response.content_part.added— 内容部分在输出项内开始。response.content_part.done— 内容部分完成。response.output_audio_transcript.delta— 助手音频响应的流式文本转录增量。response.output_audio_transcript.done— 此助手轮次的音频转录生成完成。response.output_audio.delta— 助手响应的流式 base64 编码音频增量。response.output_audio.done— 此助手轮次的音频生成完成。response.text.delta— 文本模式输出增量(使用文本模态时)。response.output_text.delta— 使用 OpenAI GA 事件名称的文本模式输出增量。功能上与response.text.delta相同。客户端应处理两个事件名称以获得最大兼容性。response.function_call_arguments.delta— 流式函数调用参数。response.function_call_arguments.done— 已使用完整参数触发函数调用。您的代码应执行函数并通过conversation.item.create(类型为function_call_output)返回结果。mcp_list_tools.in_progress— MCP 工具发现已开始。mcp_list_tools.completed— MCP 工具发现成功。mcp_list_tools.failed— MCP 工具发现失败。response.mcp_call_arguments.delta— MCP 调用参数流式传输。response.mcp_call_arguments.done— MCP 调用参数已确定。response.mcp_call.in_progress— MCP 服务器 HTTP 调用开始。response.mcp_call.completed— MCP 工具执行成功。response.mcp_call.failed— MCP 工具执行失败。response.done— 助手的响应已完成。在所有音频和转录增量后发送。客户端可以添加新的对话项。error— 发生错误时发送。包含错误代码和消息。大多数错误是可恢复的,会话保持打开状态。
示例消息流
session.created(服务器)conversation.created(服务器)session.update(客户端)session.updated(服务器)conversation.item.create(客户端)conversation.item.added(服务器)response.create(客户端)response.created(服务器)response.output_item.added(服务器)response.content_part.added(服务器)response.output_audio.delta(服务器)response.output_audio_transcript.delta(服务器)response.output_audio.done(服务器)response.output_audio_transcript.done(服务器)response.content_part.done(服务器)response.output_item.done(服务器)response.done(服务器)
POST /v1/realtime/calls/{call_id}/refer
将活动的 SIP 通话转接到 PSTN 或 SIP 目的地。
路径参数
call_id(string, required) — 来自realtime.call.incomingwebhook 的 SIP 通话标识符。
请求体
target_uri(string, required) — SIPREFER 的目的地。对于 PSTN 目的地使用tel:+E.164,对于直接 SIP 路由使用sip:user@host。
请求示例:
{
"target_uri": "sip:agent@example.com"
}响应示例:
{
"audio": "<base64-encoded MP3>",
"content_type": "audio/mpeg",
"duration": 0.92,
"audio_timestamps": {
"graph_chars": [
"H",
"e",
"l",
"l",
"o",
" ",
"w",
"o",
"r",
"l",
"d",
"."
],
"graph_times": [
{
"start": 0,
"end": 0.06
},
{
"start": 0.06,
"end": 0.12
},
{
"start": 0.12,
"end": 0.18
},
{
"start": 0.18,
"end": 0.24
},
{
"start": 0.24,
"end": 0.34
},
{
"start": 0.34,
"end": 0.4
},
{
"start": 0.4,
"end": 0.48
},
{
"start": 0.48,
"end": 0.54
},
{
"start": 0.54,
"end": 0.62
},
{
"start": 0.62,
"end": 0.68
},
{
"start": 0.68,
"end": 0.78
},
{
"start": 0.78,
"end": 0.92
}
]
}
}POST /v1/realtime/calls/{call_id}/hangup
结束活动的 SIP 通话。
路径参数
call_id(string, required) — 来自realtime.call.incomingwebhook 的 SIP 通话标识符。
响应示例:
{}POST /v1/tts
将文本转换为语音音频。
请求体
text(string, required) — 要转换为语音的文本。最大 15,000 个字符。支持内联语音标签以实现富有表现力的输出:[pause]、[long-pause]、[hum-tune]、[laugh]、[chuckle]、[giggle]、[cry]、[tsk]、[tongue-click]、[lip-smack]、[breath]、[inhale]、[exhale]、[sigh]。还支持包装标签用于风格控制:<soft>、<whisper>、<loud>、<build-intensity>、<decrease-intensity>、<higher-pitch>、<lower-pitch>、<slow>、<fast>、<sing-song>、<singing>、<laugh-speak>、<emphasis>。voice_id(string) — 语音标识符。使用来自GET /v1/tts/voices的内置语音(如eve、ara)或自定义语音 ID。省略时默认为eve。output_format(object)codec("mp3" | "wav" | "pcm" | "mulaw" | "alaw", required) — 音频编解码器。sample_rate(integer | null) — 以 Hz 为单位的采样率。支持值:8000、16000、22050、24000、44100、48000。默认为 24000。bit_rate(integer | null) — 以 bps 为比特率。仅适用于 MP3 编解码器。支持值:32000、64000、96000、128000、192000。默认为 128000。
language(string, required) — BCP-47 语言代码(如en、zh、pt-BR)或auto自动语言检测。不区分大小写。支持值:auto、en、ar-EG、ar-SA、ar-AE、bn、zh、fr、de、hi、id、it、ja、ko、pt-BR、pt-PT、ru、es-MX、es-ES、tr、vi。其他语言可能以不同精度工作。optimize_streaming_latency("0" | "1") — 流式合成的延迟优化级别。0(默认):无优化 — 最佳音频质量。1:减少第一块大小以降低首次音频时间,在块边界处有轻微的质量权衡。text_normalization(boolean) — 在合成前启用文本规范化。启用后,模型将书面形式文本(如数字、缩写、符号)规范化为口语形式,然后再生成音频。with_timestamps(boolean) — 在音频旁返回每个字符的时间戳元数据。当true时,响应是application/json,包含 base64 编码的音频和audio_timestamps。speed(number) — 语音速度乘数。1.0是正常速度。低于1.0的值减慢语音,高于1.0的值加速语音。省略时默认为1.0。
响应体
audio(string, required) — 请求编解码器中的 base64 编码音频字节。content_type(string, required) — 解码音频的 MIME 类型(如audio/mpeg、audio/wav)。duration(number, required) — 总音频持续时间(秒)。audio_timestamps(object) — 当with_timestamps为true时生成的每个字符的时间戳。graph_chars(array<string>, required) — 原始输入文本的每个字符,按顺序排列。graph_times(array<object>, required) —graph_chars中每个条目的开始/结束秒数。start(number, required) — 开始时间(秒),从合成音频的开始测量。end(number, required) — 结束时间(秒),从合成音频的开始测量。
代码示例
tmpfile=$(mktemp /tmp/tts-output-XXXXXX.mp3)
trap 'rm -f "$tmpfile"' EXIT
http_code=$(curl -s -o "$tmpfile" -w "%{http_code}" \
https://api.x.ai/v1/tts \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $XAI_API_KEY" \
-d '{
"text": "Hello, this is a text-to-speech test from xAI.",
"voice_id": "eve",
"language": "en"
}')
if [ "$http_code" -ge 200 ] && [ "$http_code" -lt 300 ]; then
file_size=$(wc -c < "$tmpfile" | tr -d ' ')
echo "{\"status\": $http_code, \"audio_bytes\": $file_size}"
else
cat "$tmpfile"
exit 1
ficonst response = await fetch("https://api.x.ai/v1/tts", {
method: "POST",
headers: {
Authorization: `Bearer ${process.env.XAI_API_KEY}`,
"Content-Type": "application/json",
},
body: JSON.stringify({
text: "Hello, this is a text-to-speech test from xAI.",
voice_id: "eve",
language: "en",
}),
});
if (response.ok) {
const audioBuffer = await response.arrayBuffer();
console.log(
JSON.stringify(
{
status: response.status,
audio_bytes: audioBuffer.byteLength,
content_type: response.headers.get("content-type") || "",
},
null,
2,
),
);
} else {
const errorText = await response.text();
console.error(errorText);
process.exit(1);
}import json
import os
import requests
response = requests.post(
"https://api.x.ai/v1/tts",
headers={
"Authorization": f"Bearer {os.environ['XAI_API_KEY']}",
"Content-Type": "application/json",
},
json={
"text": "Hello, this is a text-to-speech test from xAI.",
"voice_id": "eve",
"language": "en",
},
)
if response.ok:
print(
json.dumps(
{
"status": response.status_code,
"audio_bytes": len(response.content),
"content_type": response.headers.get("Content-Type", ""),
},
indent=2,
)
)
else:
print(response.text)
raise SystemExit(1)响应示例:
{}curl -s https://api.x.ai/v1/tts/voices \
-H "Authorization: Bearer $XAI_API_KEY"const response = await fetch("https://api.x.ai/v1/tts/voices", {
headers: {
Authorization: `Bearer ${process.env.XAI_API_KEY}`,
},
});
const data = await response.json();
console.log(JSON.stringify(data, null, 2));import json
import os
import requests
response = requests.get(
"https://api.x.ai/v1/tts/voices",
headers={
"Authorization": f"Bearer {os.environ['XAI_API_KEY']}",
},
)
print(json.dumps(response.json(), indent=2))响应示例:
{
"voices": [
{
"voice_id": "carina",
"name": "Carina",
"language": "en"
},
{
"voice_id": "zagan",
"name": "Zagan",
"language": "en"
},
{
"voice_id": "helix",
"name": "Helix",
"language": "en"
},
{
"voice_id": "orion",
"name": "Orion",
"language": "en"
},
{
"voice_id": "luna",
"name": "Luna",
"language": "en"
},
{
"voice_id": "iris",
"name": "Iris",
"language": "en"
},
{
"voice_id": "altair",
"name": "Altair",
"language": "en"
},
{
"voice_id": "zenith",
"name": "Zenith",
"language": "en"
},
{
"voice_id": "perseus",
"name": "Perseus",
"language": "en"
},
{
"voice_id": "helios",
"name": "Helios",
"language": "en"
},
{
"voice_id": "lux",
"name": "Lux",
"language": "en"
},
{
"voice_id": "kepler",
"name": "Kepler",
"language": "en"
},
{
"voice_id": "rigel",
"name": "Rigel",
"language": "en"
},
{
"voice_id": "cosmo",
"name": "Cosmo",
"language": "en"
},
{
"voice_id": "celeste",
"name": "Celeste",
"language": "en"
},
{
"voice_id": "ursa",
"name": "Ursa",
"language": "en"
},
{
"voice_id": "sirius",
"name": "Sirius",
"language": "en"
},
{
"voice_id": "lumen",
"name": "Lumen",
"language": "en"
},
{
"voice_id": "castor",
"name": "Castor",
"language": "en"
},
{
"voice_id": "naksh",
"name": "Naksh",
"language": "en"
},
{
"voice_id": "atlas",
"name": "Atlas",
"language": "en"
},
{
"voice_id": "ara",
"name": "Ara",
"language": "en"
},
{
"voice_id": "eve",
"name": "Eve",
"language": "en"
},
{
"voice_id": "leo",
"name": "Leo",
"language": "en"
},
{
"voice_id": "rex",
"name": "Rex",
"language": "en"
},
{
"voice_id": "sal",
"name": "Sal",
"language": "en"
}
]
}GET /v1/tts/voices/
获取特定语音的详细信息。
路径参数
voice_id(string, 必需) — 语音的唯一标识符(例如eve、ara)。
响应体
voice_id(string, 必需) — 语音的唯一标识符(小写)。在 TTS 请求中作为voice_id传递,或在 Realtime API 会话配置中作为voice参数传递。name(string, 必需) — 语音的可读显示名称。language(string | null) — 语音的语言代码(例如en)。
代码示例
curl -s https://api.x.ai/v1/tts/voices/eve \
-H "Authorization: Bearer $XAI_API_KEY"const voiceId = "eve";
const response = await fetch(`https://api.x.ai/v1/tts/voices/${voiceId}`, {
headers: {
Authorization: `Bearer ${process.env.XAI_API_KEY}`,
},
});
const data = await response.json();
console.log(JSON.stringify(data, null, 2));import json
import os
import requests
voice_id = "eve"
response = requests.get(
f"https://api.x.ai/v1/tts/voices/{voice_id}",
headers={
"Authorization": f"Bearer {os.environ['XAI_API_KEY']}",
},
)
print(json.dumps(response.json(), indent=2))响应示例:
{
"voice_id": "eve",
"name": "Eve",
"language": "en"
}POST /v1/stt
将音频文件转录为文本。
请求体
file(string) — 要转录的音频文件。最大大小:500 MB。支持的容器格式(自动检测):wav、mp3、ogg、opus、flac、aac、mp4、m4a、mkv(仅限 MP3/AAC/FLAC 编解码器)。支持的原始格式(需要audio_format和sample_rate):pcm、mulaw、alaw。必须是多部分表单中的最后一个字段。url(string) — 要下载并转录的音频文件的 URL(服务器端)。必须提供file或url中的一个。audio_format("pcm" | "mulaw" | "alaw" | "wav" | "mp3" | "ogg" | "opus" | "flac" | "aac" | "mp4" | "m4a" | "mkv") — 音频格式提示。仅对原始/无头格式必需(pcm、mulaw、alaw)。对于容器格式(MP3、WAV、OGG 等),服务器会从文件头自动检测格式 — 请勿设置此字段。sample_rate("8000" | "16000" | "22050" | "24000" | "44100" | "48000") — 音频采样率(Hz)。当audio_format为原始格式时必需(pcm、mulaw、alaw)。对容器格式忽略。可以使用sample_rate或sample_rate_hertz。language(string) — 音频的语言代码(例如en、fr、de、ja)。当与format=true一起设置时,启用反向文本规范化 — 将口语形式的数字、货币和单位转换为书写形式。format("true" | "false") — 当为true时,启用文本格式化。需要设置language。multichannel("true" | "false") — 当为true时,启用每通道转录。每个音频通道独立转录,结果在channels数组中返回。channels(integer) — 音频通道数。多通道原始音频必需(最小 2,最大 8)。对于容器格式,通道数从文件头自动检测。diarize("true" | "false") — 当为true时,启用说话人分离。响应中的每个单词都包含一个speaker字段(整数),用于标识检测到的说话人。keyterm(array<string>) — 用于偏向转录的关键词(例如产品名称、专有名词)。对每个术语重复此字段(例如keyterm=Understand+The+Universe)。最多 100 个术语,每个最多 50 个字符。filler_words("true" | "false") — 当为true时,填充词(例如 "uh"、"um"、"er")包含在转录文本中。当为false(默认)时,填充词会自动从转录文本和words数组中移除。vad_threshold(number) — 语音活动检测的语音概率阈值(0.0–1.0)。得分低于阈值的音频段被视为非语音并跳过转录。较低的值可以转录 quieter 或更嘈杂的语音(例如窄带电话),但可能会为背景噪音产生虚假文本;0完全禁用门控。默认值:0.5。
响应体
text(string, 必需) — 完整的转录文本。对于多通道请求,这是所有通道的合并转录(按时间戳交错单词)。language(string, 必需) — 检测到的语言代码(ISO 639-1,例如en)。当前为空 — 尚未启用语言检测。duration(number, 必需) — 音频持续时间(秒,四舍五入到小数点后 2 位)。words(array<object>) — 带时间戳的词级分段。为空时省略。text(string, 必需) — 单词文本。start(number, 必需) — 单词开始时间(秒,2 位小数)。end(number, 必需) — 单词结束时间(秒,2 位小数)。confidence(number) — 置信度分数(0.0–1.0,基于熵)。为 0 时省略。speaker(integer) — 说话人索引(从 0 开始)。仅在diarize=true时存在。
channels(array<object>) — 每通道转录。仅在multichannel=true时存在。单通道音频时省略。index(integer, 必需) — 源音频中从 0 开始的通道索引。language(string) — 此通道的检测语言代码。当前为空。text(string, 必需) — 此通道的完整转录文本。words(array<object>) — 此通道的带时间戳的词级分段。text(string, 必需) — 单词文本。start(number, 必需) — 单词开始时间(秒,2 位小数)。end(number, 必需) — 单词结束时间(秒,2 位小数)。confidence(number) — 置信度分数(0.0–1.0,基于熵)。为 0 时省略。speaker(integer) — 说话人索引(从 0 开始)。仅在diarize=true时存在。
响应示例:
{
"text": "The balance is $167,983.15. That is $23.4 kilograms.",
"language": "",
"duration": 8.4,
"words": [
{
"text": "The",
"start": 0,
"end": 0.24,
"confidence": 0.33
},
{
"text": "balance",
"start": 0.24,
"end": 0.64,
"confidence": 0.67
},
{
"text": "is",
"start": 0.64,
"end": 0.88,
"confidence": 0.41
},
{
"text": "$167,983.15.",
"start": 0.88,
"end": 4.8,
"confidence": 0.07
},
{
"text": "That",
"start": 6.16,
"end": 6.48,
"confidence": 0.29
},
{
"text": "is",
"start": 6.48,
"end": 6.64,
"confidence": 0.4
},
{
"text": "$23.4",
"start": 6.64,
"end": 7.52,
"confidence": 0.07
},
{
"text": "kilograms.",
"start": 7.76,
"end": 8.4,
"confidence": 0.09
}
]
}语音转文本 - 流式传输
WebSocket 端点:wss://api.x.ai/v1/stt
通过 WebSocket 进行实时流式语音转文本。将原始音频作为二进制帧流式传输,并在音频处理时接收 JSON 转录事件。配置通过连接时的查询参数完成。
完整模式和示例:/stt-streaming.ws.json
查询参数
sample_rate(integer, 可选, 默认值: 16000) — 音频采样率(Hz)。支持值:8000、16000、22050、24000、44100、48000。encoding(string, 可选, 默认值: pcm) — 音频编码格式。pcm— 有符号 16 位小端序(2 字节/采样)。mulaw— G.711 µ-law(1 字节/采样)。alaw— G.711 A-law(1 字节/采样)。interim_results(boolean, 可选, 默认值: false) — 当为true时,服务器在处理音频时大约每 500 毫秒发出部分转录事件(is_final=false)。当为false(默认)时,仅发送最终结果。endpointing(integer, 可选, 默认值: 10) — 服务器触发speech_final=true事件之前的静音持续时间(毫秒),表示说话人已停止说话。范围:0–5000。设置为0表示无延迟(在任何 VAD 静音边界触发)。默认值:10ms。language(string, 可选, 默认值: ) — 语言代码(例如en、fr、de、ja)。设置时启用反向文本规范化 — 将口语形式的数字、货币和单位转换为书写形式。multichannel(boolean, 可选, 默认值: false) — 当为true时,为交错的多通道音频启用每通道转录。需要将channels设置为 ≥ 2。channels(integer, 可选, 默认值: 1) — 交错音频通道的数量。当multichannel=true时必需。最小值:2,最大值:8。diarize(boolean, 可选, 默认值: false) — 当为true时,启用说话人分离。transcript.partial和transcript.done事件中的单词包含一个speaker字段(整数),用于标识检测到的说话人。keyterm(string (可重复), 可选) — 用于偏向转录的关键词(例如产品名称、专有名词)。对每个术语重复参数(例如keyterm=Understand+The+Universe)。最多 100 个术语,每个最多 50 个字符。filler_words(boolean, 可选, 默认值: false) — 当为true时,填充词(例如uh、um、er)包含在转录文本中。当为false(默认)时,填充词会自动从转录文本和words数组中移除。smart_turn(number, 可选) — 启用智能轮次结束检测。设置为0.0到1.0之间的置信度阈值。当模型在 VAD 静音边界上的轮次结束概率超过此阈值时,立即触发speech_final。当置信度低于阈值时,speech_final被抑制,事件降级为chunk_final。启用智能轮次时,每个transcript.partial事件都包含一个end_of_turn_confidence字段(0.0–1.0)。示例:smart_turn=0.7。smart_turn_timeout(integer, 可选) — 强制触发speech_final之前的最大静音持续时间(毫秒),即使智能轮次模型预测说话人尚未结束。作为安全网,防止会话在长时间静音时挂起。仅在smart_turn启用时适用。范围:1–5000。示例:smart_turn_timeout=3000。vad_threshold(number, 可选, 默认值: 0.08) — 语音活动检测的语音概率阈值(0.0–1.0)。得分低于阈值的音频块被视为非语音并跳过转录。较低的值可以转录 quieter 或更嘈杂的语音(例如窄带电话),但可能会为背景噪音产生虚假文本;0完全禁用门控。不影响端点检测或speech_final计时。默认值:0.08。
客户端消息
二进制帧(音频)— 根据编码查询参数指定的编码,将原始音频作为二进制 WebSocket 帧发送。音频应以实时节奏的块流式传输(例如一次 100 毫秒)。不使用 base64 编码 — 直接发送原始字节。finalize— 强制当前语音立即作为speech_final完成,而不等待 VAD 端点检测或智能轮次。会话保持打开状态,以便您可以继续流式传输音频。接受finalize或Finalize作为类型值。当multichannel=true时,可选的channel(从 0 开始)将 finalize 限制在该通道;省略channel以 finalize 所有通道。audio.done— 表示所有音频已发送。服务器刷新任何剩余的缓冲音频,发出最终转录事件,并发送transcript.done事件。此事件后连接关闭。
服务器消息
transcript.created— 在 WebSocket 连接建立后立即发送,服务器准备接收音频。在发送音频之前等待此事件 — 服务器需要初始化其后端 ASR。transcript.partial— 音频流一部分的转录结果。两个布尔字段传达状态:临时结果(is_final=false)表示文本可能仍会更改,块最终结果(is_final=true、speech_final=false)表示该块已锁定,语音最终结果(is_final=true、speech_final=true)表示说话人已停止说话。transcript.done— 在audio.done之后的最终转录。duration始终存在。当multichannel=true时,每个通道一个。此事件后连接关闭。error— 会话期间发生错误。大多数错误(管道故障、流超时)会关闭连接。仅客户端消息解析错误保持连接打开。
示例消息流
transcript.created(服务器)二进制帧(音频)(客户端)二进制帧(音频)(客户端)transcript.partial(服务器)二进制帧(音频)(客户端)transcript.partial(服务器)二进制帧(音频)(客户端)transcript.partial(服务器)audio.done(客户端)transcript.done(服务器)
POST /v1/custom-voices
从参考音频片段创建自定义语音。
请求体
file(string, 必需) — 参考音频文件。最大持续时间:120 秒。支持的格式:WAV、MP3、FLAC、OGG、Opus、M4A、AAC、MKV、MP4(任何ffmpeg可以解码的格式)。name(string) — 语音的显示名称。显示在控制台中,并由GET /v1/custom-voices返回。description(string) — 语音的自由文本描述。gender("male" | "female" | "neutral") — 语音性别标签。accent(string) — 自由文本口音标签(例如British、American)。age("young" | "middle-aged" | "old") — 语音年龄标签。language(string) — ISO 639 语言代码(例如en)或 BCP-47 风格代码(例如en-US、zh-CN)。区域必须大写。use_case("conversational" | "narration" | "characters" | "educational" | "advertisement" | "social_media" | "entertainment") — 预期用例标签。tone("warm" | "casual" | "professional" | "friendly" | "authoritative" | "expressive" | "calm") — 语调标签。
响应体
voice_id(string, 必需) — 8 个字符的小写字母数字语音标识符。在POST /v1/tts中用作voice_id,在流式 TTS WebSocket 上用作voice查询参数,或在语音转语音session.update消息中用作voice。name(string | null) — 显示名称。description(string | null) — 自由文本描述。gender("male" | "female" | "neutral" | "null") — 语音性别标签。accent(string | null) — 自由文本口音标签。age("young" | "middle-aged" | "old" | "null") — 语音年龄标签。language(string | null) — ISO 639 / BCP-47 语言代码。use_case(string | null) — 预期用例标签。tone(string | null) — 语调标签。created_at(string, 必需) — RFC 3339 时间戳。
代码示例
curl -s https://api.x.ai/v1/custom-voices \
-H "Authorization: Bearer $XAI_API_KEY" \
-F "name=Friendly Narrator" \
-F "language=en" \
-F "gender=female" \
-F "tone=warm" \
-F "use_case=narration" \
-F "file=@reference.wav;type=audio/wav"import fs from 'fs';
const form = new FormData();
form.append('file', new Blob([fs.readFileSync('reference.wav')]), 'reference.wav');
form.append('name', 'Friendly Narrator');
form.append('language', 'en');
form.append('gender', 'female');
form.append('tone', 'warm');
form.append('use_case', 'narration');
const response = await fetch('https://api.x.ai/v1/custom-voices', {
method: 'POST',
headers: { Authorization: `Bearer ${process.env.XAI_API_KEY}` },
body: form,
});
console.log(JSON.stringify(await response.json(), null, 2));import json
import os
import requests
with open("reference.wav", "rb") as f:
response = requests.post(
"https://api.x.ai/v1/custom-voices",
headers={"Authorization": f"Bearer {os.environ['XAI_API_KEY']}"},
files={"file": ("reference.wav", f, "audio/wav")},
data={
"name": "Friendly Narrator",
"language": "en",
"gender": "female",
"tone": "warm",
"use_case": "narration",
},
)
print(json.dumps(response.json(), indent=2))响应示例:
{
"voice_id": "nlbqfwie",
"name": "Friendly Narrator",
"description": "Warm, conversational tone for narration.",
"gender": "female",
"accent": "American",
"age": "young",
"language": "en",
"use_case": "narration",
"tone": "warm",
"created_at": "2026-04-26T18:56:34.872993+00:00"
}GET /v1/custom-voices
列出您的团队拥有的自定义语音。
查询参数
limit(integer) — 每页返回的最大语音数。范围:1-1000。默认值:100。pagination_token(string) — 前一个响应中的pagination_token字段的令牌。传递以获取下一页。
响应体
voices(array<object>, 必需) — 调用团队拥有的自定义语音列表。voice_id(string, 必需) — 8 个字符的小写字母数字语音标识符。在POST /v1/tts中用作voice_id,在流式 TTS WebSocket 上用作voice查询参数,或在语音转语音session.update消息中用作voice。name(string | null) — 显示名称。description(string | null) — 自由文本描述。gender("male" | "female" | "neutral" | "null") — 语音性别标签。accent(string | null) — 自由文本口音标签。age("young" | "