Java调用Twilio实现双通道实时录制报错求助(无需Dial Verb)
解决Twilio双通道实时录制的21220错误(无需Twiml Dial verb)
首先咱们把问题拆解清楚:你碰到的SEVERE: Servlet.service()...错误,根源是Twilio返回的Error - 21220 Invalid call state——你尝试对一个已经结束(或不在活跃状态)的调用发起录制操作,而Twilio只允许对in-progress状态的调用执行实时录制操作。
你的当前代码是直接通过Recording.creator(callSid).create()触发录制,但如果此时调用已经挂断或者还没接通,就会触发这个错误。下面给你两种无需使用Twiml Dial verb的解决方案:
方案1:调用创建时直接启用双通道录制(最可靠)
如果你的场景允许在发起调用时就启动录制,这是最稳妥的方式——因为调用创建后进入in-progress状态时,录制会自动启动,完全避开状态不匹配的问题。
Java代码示例:
Twilio.init(account, auth); // 创建调用时直接配置双通道录制 Call call = Call.creator( new PhoneNumber("+1234567890"), // 目标被叫号码 new PhoneNumber("+0987654321"), // 你的Twilio号码(主叫方) new URI("https://your-public-server.com/basic-twiml") // 基础Twiml,比如返回<Response><Say>Connected</Say></Response>即可,无需Dial ) .setRecord(true) // 启用录制 .setRecordingChannels("dual") // 设置双通道录制 .setRecordingStatusCallback(URI.create("https://your-public-server.com/recording-callback")) // 录制状态回调地址 .create(); System.out.println("Call initiated with SID: " + call.getSid());
这种方式下,调用一接通就会开始双通道录制,不需要额外的后续操作,也不会出现状态错误。
方案2:动态启动录制(需确保调用处于活跃状态)
如果必须在调用接通后根据某些条件动态启动录制,那你必须先校验调用的当前状态,确保它处于in-progress:
Java代码示例:
Twilio.init(account, auth); // 先获取调用当前状态 Call call = Call.fetcher(callSid).fetch(); if ("in-progress".equals(call.getStatus())) { // 状态合法,启动双通道录制 Recording recording = Recording.creator(callSid) .setRecordingChannels("dual") .setRecordingStatusCallback(URI.create("https://your-public-server.com/recording-callback")) .create(); System.out.println("Dual-channel recording started, SID: " + recording.getSid()); } else { System.out.println("Cannot start recording: Call is not in progress. Current status: " + call.getStatus()); }
⚠️ 注意:动态启动录制的时机非常关键,必须在调用接通后、挂断前发起请求。如果调用已经进入completed或busy等状态,这个操作还是会失败。
额外注意事项
- 确保你的Twilio账号有权限使用双通道录制:部分地区或基础套餐可能需要联系客服开通该功能
- 录制状态回调URL必须是公网可访问的HTTPS地址,Twilio才能正常推送录制状态通知
- 避免在调用状态切换的边缘节点发起录制请求(比如刚接通或刚挂断的瞬间),建议预留1-2秒的缓冲时间
内容的提问来源于stack exchange,提问作者Anvesha Chaudhary
相关产品推荐
相关产品推荐

