Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,12 @@ await HookEmitter.Emit<ITwilioCallStatusHook>(_services,
response.Redirect(new Uri($"{_settings.CallbackHost}/twilio/voice/reply/{seqNum}?agent-id={request.AgentId}&conversation-id={request.ConversationId}&{twilio.GenerateStatesParameter(request.States)}"), HttpMethod.Post);
}
}

_ = Task.Run(async () =>
{
await Task.Delay(1500);
await twilio.StartRecording(request.CallSid, request.AgentId, request.ConversationId);
});
}

await HookEmitter.Emit<ITwilioSessionHook>(_services, async hook =>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,10 @@ public async Task<ActionResult> PhoneRecordingStatus(ConversationalVoiceRequest
// recording completed
await HookEmitter.Emit<ITwilioCallStatusHook>(_services, x => x.OnRecordingCompleted(request));
}
else
{
_logger.LogError($"Unknown record status: {request.CallStatus}, {request.CallSid}");
}

return Ok();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -214,7 +214,7 @@ public async Task<TwiMLResult> ReplyCallerMessage(ConversationalVoiceRequest req

var reply = await sessionManager.GetAssistantReplyAsync(request.ConversationId, request.SeqNum);
VoiceResponse response;

if (request.AIResponseWaitTime > 10)
{
// Wait AI Response Timeout
Expand Down Expand Up @@ -381,19 +381,23 @@ await HookEmitter.Emit<ITwilioCallStatusHook>(_services,
else if (request.CallStatus == "canceled")
{
await HookEmitter.Emit<ITwilioCallStatusHook>(_services,
async hook =>
{
if (hook.IsMatch(request)) await hook.OnCallCanceledStatus(request);
async hook =>
{
if (hook.IsMatch(request)) await hook.OnCallCanceledStatus(request);
});
}
else if (request.CallStatus == "failed")
{
await HookEmitter.Emit<ITwilioCallStatusHook>(_services,
async hook =>
{
if (hook.IsMatch(request)) await hook.OnCallFailedStatus(request);
async hook =>
{
if (hook.IsMatch(request)) await hook.OnCallFailedStatus(request);
});
}
else
{
_logger.LogError($"Unknown call status: {request.CallStatus}, {request.CallSid}");
}

return Ok();
}
Expand Down
18 changes: 18 additions & 0 deletions src/Plugins/BotSharp.Plugin.Twilio/Services/TwilioService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@
using BotSharp.Plugin.Twilio.Interfaces;
using BotSharp.Plugin.Twilio.Models;
using Twilio.Jwt.AccessToken;
using Twilio.Rest.Api.V2010.Account.Call;
using Task = System.Threading.Tasks.Task;
using Token = Twilio.Jwt.AccessToken.Token;

namespace BotSharp.Plugin.Twilio.Services;
Expand Down Expand Up @@ -122,6 +124,22 @@ public VoiceResponse ReturnNoninterruptedInstructions(ConversationalVoiceRespons
return response;
}

public async Task StartRecording(string callSid, string agentId, string conversationId)
{
if (_settings.RecordingEnabled)
{
// https://help.twilio.com/articles/360010317333-Recording-Incoming-Twilio-Voice-Calls
var recordStatusUrl = $"{_settings.CallbackHost}/twilio/record/status?agent-id={agentId}&conversation-id={conversationId}";
var recording = await RecordingResource.CreateAsync(pathCallSid: callSid,
recordingStatusCallback: new Uri(recordStatusUrl),
trim: "trim-silence",
recordingChannels: "dual",
recordingTrack: "both");

_logger.LogInformation($"Recording started: {recording.CallSid} {recording.Sid}");
}
}

public VoiceResponse HangUp(string speechPath)
{
var response = new VoiceResponse();
Expand Down
Loading