You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用Twilio Task Router处理非电话任务时出现'Failed to issue Dequeue'错误

注意:以下代码片段可正常运行。本文提及的"dequeue"错误源于这些脚本之外的现有Assignment Callback。移除该URL并将reservation.dequeue移至本代码后,错误已解决。

我们正在开发一款基于Twilio Conversations的双人聊天应用,当前用户发起聊天的流程如下:

  • 创建Conversation
  • 创建User
  • 将用户添加至对话
  • 创建Task,并在属性中携带对话元数据

(后续为另一方用户会话接受预约等步骤)

这些步骤可正常执行,但由于该任务并非来电,会触发错误:"40140 - Failed to issue Dequeue instruction due to missing 'call_sid' property"。我尝试将任务放入"SMS"任务通道,但未能阻止错误。

我未找到创建非电话任务的具体文档,因此任务路由设置可能存在问题。

以下是创建对话、用户和任务的.NET代码片段,以及使用TaskRouter.js接受预约的代码片段:

/***********************************************************************************************************
This code is server-side in .NET
***********************************************************************************************************/
public ConversationCredentials CreateConversation( string program, string name )
{
  var memberId = DateTime.Now.ToString( "yyyyMMdd" );  // Temporary
  TwilioClient.Init( _twilioAccountSid,_twilioAuthToken );

  // If we decide to keep conversations on Twilio, we should replace the memberid with phiid, since member id might change

  var conversation = ConversationResource.Create(
    friendlyName: memberId + "_" + DateTime.Now.ToString( "HHmmss" )
  );

  var conversationCredentials = JoinConversation( conversation.Sid, name );
  var taskSid = CreateTask( program, conversation.Sid, memberId );

  conversationCredentials.taskSid = taskSid;
  
  return conversationCredentials;
}

public ConversationCredentials JoinConversation( string conversationSid, string name )
{
  var identity = name + "_" + DateTime.Now.ToString( "HHmmss" ); // Makes sure the user is unique, in case it's an employee joining more than one chat session)
  TwilioClient.Init( _twilioAccountSid,_twilioAuthToken );

  var participant = ParticipantResource.Create(
    pathConversationSid: conversationSid,
    identity: identity
  );

  var user = UserResource.Update(
    pathSid: identity,
    friendlyName: name
  );

  var token = GetJWT( _twilioConversationServiceSid, name );  // Conversation Service Sid

  var conversationCredentials = new ConversationCredentials();
  
  conversationCredentials.token = token;
  conversationCredentials.conversationSid = conversationSid;
  conversationCredentials.participantSid = participant.Sid;
  conversationCredentials.participantName = name;
  conversationCredentials.participantIdentity = participant.Identity;

  return conversationCredentials;
}

public string CreateTask( string program, string conversationSid, string memberId )
{

  TwilioClient.Init( _twilioAccountSid, _twilioAuthToken );

  var attributes = JsonConvert.SerializeObject( new Dictionary<string,Object>()
  {
    {"conversationSid", conversationSid },
    {"memberId",        memberId        },
    {"program",         program         },
    {"call_sid",        "CHAT"          }
  }, Formatting.Indented);

  var task = TaskResource.Create(
    attributes: attributes,
    workflowSid: _twilioWorkflowSid,
    pathWorkspaceSid: _twilioWorkspaceSid_Nurses,
    taskChannel: "Default"
  );

  return task.Sid;

}
/***********************************************************************************************************
This code is browser-side using TaskRouter.js
NOTE: This handles both voice (works fine) and conversations (the part in question)
***********************************************************************************************************/
registerTaskRouterCallbacks( _this ) : void {
this.worker.on('ready', function(worker) {
  _this.updateButton( worker.activityName, "" );
});

this.worker.on("reservation.created", function(reservation) {
  if ( reservation.task.attributes.type != "CHAT" )
  {
    _this.updateButton( "Call", reservation.task.attributes.from.replace( "+1", "" ) );
    reservation.dequeue();
  } else {
    _this.updateButton( "Chat", reservation.task.attributes.memberId );
    confirm("You have an incoming chat!");
    reservation.accept();
    // This is where the chat window would pop-up
  }
});

this.worker.on("reservation.accepted", function(reservation) {
  _this.worker.update({"ActivitySid": _this.activitySids["Busy"][0].sid});
  _this.updateButton( "Busy", "" );
});

内容的提问来源于stack exchange,提问作者tcbeaton

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.22 08:54:16