Início Rápido: como fazer uma chamada de saída por meio da Automação de Chamadas
As APIS de Automação de Chamada dos Serviços de Comunicação do Azure APIs são uma maneira poderosa de criar experiências interativas de chamada. Nesse início rápido, abordamos uma maneira de fazer uma chamada de saída e reconhecer vários eventos na chamada.
Pré-requisitos
- Uma conta do Azure com uma assinatura ativa. Crie uma conta gratuitamente.
- Um recurso dos Serviços de Comunicação implantado. Crie um recurso dos Serviços de Comunicação.
- Um número de telefone em seu recurso dos Serviços de Comunicação do Azure que pode fazer chamadas de saída. Caso você não tenha uma assinatura, você pode obter um número de telefone de avaliação gratuita.
- Crie e hospede um Azure Dev Tunnel. Instruções aqui.
- Crie e conecte serviços de IA do Azure de vários serviços ao recurso dos Serviços de Comunicação do Azure.
- Crie um subdomínio personalizado para seu recurso de serviços de IA do Azure.
- (Opcional) Um usuário do Microsoft Teams com uma licença de telefone
voice
habilitada. A licença de telefonia do Teams é necessária para adicionar usuários do Teams à chamada. Saiba mais sobre as licenças do Teams aqui. Saiba mais sobre como ativar o sistema telefônico comvoice
aqui.
Código de exemplo
Baixe ou clone o código de exemplo de início rápido do GitHub.
Navegue até a pasta CallAutomation_OutboundCalling
e abra a solução em um editor de código.
Configurar e hospedar seu Azure DevTunnel
OAzure DevTunnels é um serviço do Azure que permite compartilhar serviços Web locais hospedados na Internet. Execute os comandos para conectar seu ambiente de desenvolvimento local à Internet pública. O DevTunnels cria uma URL de ponto de extremidade persistente e que permite acesso anônimo. Usamos esse ponto de extremidade para notificar seu aplicativo de eventos de chamada do serviço Automação de Chamadas dos Serviços de Comunicação do Azure.
devtunnel create --allow-anonymous
devtunnel port create -p 8080
devtunnel host
Como alternativa, siga as instruções para configurar seu Azure DevTunnel no Visual Studio
Atualize a configuração do aplicativo
Em seguida, atualize o arquivo Program.cs
com os seguintes valores:
acsConnectionString
: a cadeia de conexão do recurso dos Serviços de Comunicação do Azure. Encontre a cadeia de conexão dos Serviços de Comunicação do Azure usando as instruções descritas aqui.callbackUriHost
: depois de inicializar o host do DevTunnel, atualize esse campo com a URI.acsPhonenumber
: atualize esse campo com o número de telefone dos Serviços de Comunicação do Azure que você adquiriu. Esse número de telefone deve usar o formato de número de telefone E164 (por exemplo, +18881234567)targetPhonenumber
: atualize o campo com o número de telefone que você gostaria que seu aplicativo chamasse. Esse número de telefone deve usar o formato de número de telefone E164 (por exemplo, +18881234567)cognitiveServiceEndpoint
: atualize o campo com o ponto de extremidade dos serviços de IA do Azure.targetTeamsUserId
: (Opcional) atualize o campo com a ID de usuário do Microsoft Teams que você deseja adicionar à chamada. Consulte Usar a API do Graph para obter a ID de usuário do Teams.
// Your ACS resource connection string
var acsConnectionString = "<ACS_CONNECTION_STRING>";
// Your ACS resource phone number will act as source number to start outbound call
var acsPhonenumber = "<ACS_PHONE_NUMBER>";
// Target phone number you want to receive the call.
var targetPhonenumber = "<TARGET_PHONE_NUMBER>";
// Base url of the app
var callbackUriHost = "<CALLBACK_URI_HOST_WITH_PROTOCOL>";
// Your cognitive service endpoint
var cognitiveServiceEndpoint = "<COGNITIVE_SERVICE_ENDPOINT>";
// (Optional) User Id of the target teams user you want to receive the call.
var targetTeamsUserId = "<TARGET_TEAMS_USER_ID>";
Fazer uma chamada de saída
Para fazer a chamada de saída dos Serviços de Comunicação do Azure, este exemplo usa o targetPhonenumber
que você definiu anteriormente no aplicativo para criar a chamada usando a API CreateCallAsync
. Esse código fará uma chamada de saída usando o número de telefone de destino.
PhoneNumberIdentifier target = new PhoneNumberIdentifier(targetPhonenumber);
PhoneNumberIdentifier caller = new PhoneNumberIdentifier(acsPhonenumber);
var callbackUri = new Uri(callbackUriHost + "/api/callbacks");
CallInvite callInvite = new CallInvite(target, caller);
var createCallOptions = new CreateCallOptions(callInvite, callbackUri) {
CallIntelligenceOptions = new CallIntelligenceOptions() {
CognitiveServicesEndpoint = new Uri(cognitiveServiceEndpoint)
}
};
CreateCallResult createCallResult = await callAutomationClient.CreateCallAsync(createCallOptions);
Lidar com eventos de automação de chamadas
Anteriormente em nosso aplicativo, registramos o callbackUriHost
no Serviço de Automação de Chamadas. O host indica o ponto de extremidade que o serviço exige para nos notificar sobre a chamada de eventos que acontecem. Em seguida, podemos iterar pelos eventos e detectar eventos específicos que nosso aplicativo deseja entender. No código abaixo respondemos ao evento CallConnected
.
app.MapPost("/api/callbacks", async (CloudEvent[] cloudEvents, ILogger < Program > logger) => {
foreach(var cloudEvent in cloudEvents) {
logger.LogInformation($"Event received: {JsonConvert.SerializeObject(cloudEvent)}");
CallAutomationEventBase parsedEvent = CallAutomationEventParser.Parse(cloudEvent);
logger.LogInformation($"{parsedEvent?.GetType().Name} parsedEvent received for call connection id: {parsedEvent?.CallConnectionId}");
var callConnection = callAutomationClient.GetCallConnection(parsedEvent.CallConnectionId);
var callMedia = callConnection.GetCallMedia();
if (parsedEvent is CallConnected) {
//Handle Call Connected Event
}
}
});
(Opcional) Adicionar um usuário do Microsoft Teams à chamada
Você pode adicionar um usuário do Microsoft Teams à chamada usando o AddParticipantAsync
método com a MicrosoftTeamsUserIdentifier
ID do usuário e do Teams. Primeiro, você precisa concluir a etapa de pré-requisito Autorização para o recurso dos Serviços de Comunicação do Azure para habilitar a chamada aos usuários do Microsoft Teams. Opcionalmente, você também pode passar um SourceDisplayName
para controlar o texto exibido na notificação do sistema para o usuário do Teams.
await callConnection.AddParticipantAsync(
new CallInvite(new MicrosoftTeamsUserIdentifier(targetTeamsUserId))
{
SourceDisplayName = "Jack (Contoso Tech Support)"
});
Iniciar a gravação de uma chamada
O serviço de Automação de Chamadas também permite a capacidade de iniciar a gravação e armazenar gravações de chamadas de voz e vídeo. Você pode aprender mais sobre os vários recursos das APIs de gravação de chamadas aqui.
CallLocator callLocator = new ServerCallLocator(parsedEvent.ServerCallId);
var recordingResult = await callAutomationClient.GetCallRecording().StartAsync(new StartRecordingOptions(callLocator));
recordingId = recordingResult.Value.RecordingId;
Reproduza mensagem de boas-vindas e reconheça
Usando o TextSource
, você pode fornecer ao serviço o texto que deseja sintetizar e usado para sua mensagem de boas-vindas. O serviço Automação de Chamadas dos Serviços de Comunicação do Azure reproduz essa mensagem após o evento CallConnected
.
Em seguida, passamos o texto para o CallMediaRecognizeChoiceOptions
e, em seguida, chamamos StartRecognizingAsync
. Isso permite que seu aplicativo reconheça a opção escolhida pelo chamador.
if (parsedEvent is CallConnected callConnected) {
logger.LogInformation($"Start Recording...");
CallLocator callLocator = new ServerCallLocator(parsedEvent.ServerCallId);
var recordingResult = await callAutomationClient.GetCallRecording().StartAsync(new StartRecordingOptions(callLocator));
recordingId = recordingResult.Value.RecordingId;
var choices = GetChoices();
// prepare recognize tones
var recognizeOptions = GetMediaRecognizeChoiceOptions(mainMenu, targetPhonenumber, choices);
// Send request to recognize tones
await callMedia.StartRecognizingAsync(recognizeOptions);
}
CallMediaRecognizeChoiceOptions GetMediaRecognizeChoiceOptions(string content, string targetParticipant, List < RecognitionChoice > choices, string context = "") {
var playSource = new TextSource(content) {
VoiceName = SpeechToTextVoice
};
var recognizeOptions = new CallMediaRecognizeChoiceOptions(targetParticipant: new PhoneNumberIdentifier(targetParticipant), choices) {
InterruptCallMediaOperation = false,
InterruptPrompt = false,
InitialSilenceTimeout = TimeSpan.FromSeconds(10),
Prompt = playSource,
OperationContext = context
};
return recognizeOptions;
}
List < RecognitionChoice > GetChoices() {
return new List < RecognitionChoice > {
new RecognitionChoice("Confirm", new List < string > {
"Confirm",
"First",
"One"
}) {
Tone = DtmfTone.One
},
new RecognitionChoice("Cancel", new List < string > {
"Cancel",
"Second",
"Two"
}) {
Tone = DtmfTone.Two
}
};
}
Manipular eventos de escolha
A Automação de Chamadas dos Serviços de Comunicação do Azure dispara o api/callbacks
para o webhook que configuramos e nos notificará com o evento RecognizeCompleted
. O evento nos dá a capacidade de responder à entrada recebida e disparar uma ação. Em seguida, o aplicativo reproduz uma mensagem para o chamador com base na entrada específica recebida.
if (parsedEvent is RecognizeCompleted recognizeCompleted) {
var choiceResult = recognizeCompleted.RecognizeResult as ChoiceResult;
var labelDetected = choiceResult?.Label;
var phraseDetected = choiceResult?.RecognizedPhrase;
// If choice is detected by phrase, choiceResult.RecognizedPhrase will have the phrase detected,
// If choice is detected using dtmf tone, phrase will be null
logger.LogInformation("Recognize completed successfully, labelDetected={labelDetected}, phraseDetected={phraseDetected}", labelDetected, phraseDetected);
var textToPlay = labelDetected.Equals(ConfirmChoiceLabel, StringComparison.OrdinalIgnoreCase) ? ConfirmedText : CancelText;
await HandlePlayAsync(callMedia, textToPlay);
}
async Task HandlePlayAsync(CallMedia callConnectionMedia, string text) {
// Play goodbye message
var GoodbyePlaySource = new TextSource(text) {
VoiceName = "en-US-NancyNeural"
};
await callConnectionMedia.PlayToAllAsync(GoodbyePlaySource);
}
Desligar e parar a gravação
Por fim, quando detectamos uma condição que faz sentido para encerrarmos a chamada, podemos usar o método HangUpAsync
para desligar a chamada.
if ((parsedEvent is PlayCompleted) || (parsedEvent is PlayFailed))
{
logger.LogInformation($"Stop recording and terminating call.");
callAutomationClient.GetCallRecording().Stop(recordingId);
await callConnection.HangUpAsync(true);
}
Executar o código
Para executar o aplicativo com o VS Code, abra uma janela do Terminal e execute o comando a seguir
dotnet run
Abra http://localhost:8080/swagger/index.html
ou a URL do túnel de desenvolvimento no navegador. A URL do túnel é semelhante a: <YOUR DEV TUNNEL ENDPOINT>/swagger/index.html
Pré-requisitos
- Uma conta do Azure com uma assinatura ativa. Crie uma conta gratuitamente.
- Um recurso dos Serviços de Comunicação implantado. Crie um recurso dos Serviços de Comunicação.
- Um número de telefone em seu recurso dos Serviços de Comunicação do Azure que pode fazer chamadas de saída. Caso você não tenha uma assinatura, você pode obter um número de telefone de avaliação gratuita.
- Crie e hospede um Azure Dev Tunnel. Instruções aqui.
- Crie e conecte serviços de IA do Azure de vários serviços ao recurso dos Serviços de Comunicação do Azure.
- Crie um subdomínio personalizado para seu recurso de serviços de IA do Azure.
- JDK (Java Development Kit) versão 11 ou posterior.
- Apache Maven.
- (Opcional) Um usuário do Microsoft Teams com uma licença de telefone
voice
habilitada. A licença de telefonia do Teams é necessária para adicionar usuários do Teams à chamada. Saiba mais sobre as licenças do Teams aqui. Para obter mais informações sobre como habilitar avoice
no seu sistema de telefonia, confira como configurar seu sistema de telefonia.
Código de exemplo
Baixe ou clone o código de exemplo de início rápido do GitHub.
Navegue até a pasta CallAutomation_OutboundCalling
e abra a solução em um editor de código.
Configurar e hospedar seu Azure DevTunnel
OAzure DevTunnels é um serviço do Azure que permite compartilhar serviços Web locais hospedados na Internet. Execute os comandos do DevTunnel para conectar seu ambiente de desenvolvimento local à Internet pública. Em seguida, o DevTunnels cria um túnel com uma URL de ponto de extremidade persistente e que permite acesso anônimo. Os Serviços de Comunicação do Azure usa esse ponto de extremidade para notificar seu aplicativo de eventos de chamada do serviço Automação de Chamadas dos Serviços de Comunicação do Azure.
devtunnel create --allow-anonymous
devtunnel port create -p MY_SPRINGAPP_PORT
devtunnel host
Atualize a configuração do aplicativo
Em seguida, abra o arquivo application.yml
na pasta /resources
para configurar os seguintes valores:
connectionstring
: a cadeia de conexão do recurso dos Serviços de Comunicação do Azure. Encontre a cadeia de conexão dos Serviços de Comunicação do Azure usando as instruções descritas aqui.basecallbackuri
: depois de inicializar o host do DevTunnel, atualize esse campo com a URI.callerphonenumber
: atualize esse campo com o número de telefone dos Serviços de Comunicação do Azure que você adquiriu. Esse número de telefone deve usar o formato de número de telefone E164 (por exemplo, +18881234567)targetphonenumber
: atualize o campo com o número de telefone que você gostaria que seu aplicativo chamasse. Esse número de telefone deve usar o formato de número de telefone E164 (por exemplo, +18881234567)cognitiveServiceEndpoint
: atualize o campo com o ponto de extremidade dos serviços de IA do Azure.targetTeamsUserId
: (Opcional) atualize o campo com a ID de usuário do Microsoft Teams que você deseja adicionar à chamada. Consulte Usar a API do Graph para obter a ID de usuário do Teams.
acs:
connectionstring: <YOUR ACS CONNECTION STRING>
basecallbackuri: <YOUR DEV TUNNEL ENDPOINT>
callerphonenumber: <YOUR ACS PHONE NUMBER ex. "+1425XXXAAAA">
targetphonenumber: <YOUR TARGET PHONE NUMBER ex. "+1425XXXAAAA">
cognitiveServiceEndpoint: <YOUR COGNITIVE SERVICE ENDPOINT>
targetTeamsUserId: <(OPTIONAL) YOUR TARGET TEAMS USER ID ex. "00aa00aa-bb11-cc22-dd33-44ee44ee44ee">
Fazer uma chamada de saída e reproduzir mídia
Para fazer a chamada de saída dos Serviços de Comunicação do Azure, este exemplo usa o targetphonenumber
que você definiu no arquivo application.yml
para criar a chamada usando a API createCallWithResponse
.
PhoneNumberIdentifier caller = new PhoneNumberIdentifier(appConfig.getCallerphonenumber());
PhoneNumberIdentifier target = new PhoneNumberIdentifier(appConfig.getTargetphonenumber());
CallInvite callInvite = new CallInvite(target, caller);
CreateCallOptions createCallOptions = new CreateCallOptions(callInvite, appConfig.getCallBackUri());
CallIntelligenceOptions callIntelligenceOptions = new CallIntelligenceOptions().setCognitiveServicesEndpoint(appConfig.getCognitiveServiceEndpoint());
createCallOptions = createCallOptions.setCallIntelligenceOptions(callIntelligenceOptions);
Response<CreateCallResult> result = client.createCallWithResponse(createCallOptions, Context.NONE);
(Opcional) Adicionar um usuário do Microsoft Teams à chamada
Você pode adicionar um usuário do Microsoft Teams à chamada usando o addParticipant
método com a MicrosoftTeamsUserIdentifier
ID do usuário e do Teams. Primeiro, você precisa concluir a etapa de pré-requisito Autorização para o recurso dos Serviços de Comunicação do Azure para habilitar a chamada aos usuários do Microsoft Teams. Opcionalmente, você também pode passar um SourceDisplayName
para controlar o texto exibido na notificação do sistema para o usuário do Teams.
client.getCallConnection(callConnectionId).addParticipant(
new CallInvite(new MicrosoftTeamsUserIdentifier(targetTeamsUserId))
.setSourceDisplayName("Jack (Contoso Tech Support)"));
Iniciar a gravação de uma chamada
O serviço de Automação de Chamadas também permite a capacidade de iniciar a gravação e armazenar gravações de chamadas de voz e vídeo. Você pode aprender mais sobre os vários recursos das APIs de gravação de chamadas aqui.
ServerCallLocator serverCallLocator = new ServerCallLocator(
client.getCallConnection(callConnectionId)
.getCallProperties()
.getServerCallId());
StartRecordingOptions startRecordingOptions = new StartRecordingOptions(serverCallLocator);
Response<RecordingStateResult> response = client.getCallRecording()
.startWithResponse(startRecordingOptions, Context.NONE);
recordingId = response.getValue().getRecordingId();
Responder a eventos de chamada
Anteriormente em nosso aplicativo, registramos o basecallbackuri
no Serviço de Automação de Chamadas. O URI indica o ponto de extremidade que o serviço usará para nos notificar sobre a chamada de eventos que acontecem. Em seguida, podemos iterar pelos eventos e detectar eventos específicos que nosso aplicativo deseja entender. No código abaixo respondemos ao evento CallConnected
.
List<CallAutomationEventBase> events = CallAutomationEventParser.parseEvents(reqBody);
for (CallAutomationEventBase event : events) {
String callConnectionId = event.getCallConnectionId();
if (event instanceof CallConnected) {
log.info("CallConnected event received");
}
else if (event instanceof RecognizeCompleted) {
log.info("Recognize Completed event received");
}
}
Reproduza mensagem de boas-vindas e reconheça
Usando o TextSource
, você pode fornecer ao serviço o texto que deseja sintetizar e usado para sua mensagem de boas-vindas. O serviço Automação de Chamadas dos Serviços de Comunicação do Azure reproduz essa mensagem após o evento CallConnected
.
Em seguida, passamos o texto para o CallMediaRecognizeChoiceOptions
e, em seguida, chamamos StartRecognizingAsync
. Isso permite que seu aplicativo reconheça a opção escolhida pelo chamador.
var playSource = new TextSource().setText(content).setVoiceName("en-US-NancyNeural");
var recognizeOptions = new CallMediaRecognizeChoiceOptions(new PhoneNumberIdentifier(targetParticipant), getChoices())
.setInterruptCallMediaOperation(false)
.setInterruptPrompt(false)
.setInitialSilenceTimeout(Duration.ofSeconds(10))
.setPlayPrompt(playSource)
.setOperationContext(context);
client.getCallConnection(callConnectionId)
.getCallMedia()
.startRecognizing(recognizeOptions);
private List < RecognitionChoice > getChoices() {
var choices = Arrays.asList(
new RecognitionChoice().setLabel(confirmLabel).setPhrases(Arrays.asList("Confirm", "First", "One")).setTone(DtmfTone.ONE),
new RecognitionChoice().setLabel(cancelLabel).setPhrases(Arrays.asList("Cancel", "Second", "Two")).setTone(DtmfTone.TWO)
);
return choices;
}
Manipular eventos de escolha
A Automação de Chamadas dos Serviços de Comunicação do Azure dispara o api/callbacks
para o webhook que configuramos e nos notificará com o evento RecognizeCompleted
. O evento nos dá a capacidade de responder à entrada recebida e disparar uma ação. Em seguida, o aplicativo reproduz uma mensagem para o chamador com base na entrada específica recebida.
else if (event instanceof RecognizeCompleted) {
log.info("Recognize Completed event received");
RecognizeCompleted acsEvent = (RecognizeCompleted) event;
var choiceResult = (ChoiceResult) acsEvent.getRecognizeResult().get();
String labelDetected = choiceResult.getLabel();
String phraseDetected = choiceResult.getRecognizedPhrase();
log.info("Recognition completed, labelDetected=" + labelDetected + ", phraseDetected=" + phraseDetected + ", context=" + event.getOperationContext());
String textToPlay = labelDetected.equals(confirmLabel) ? confirmedText : cancelText;
handlePlay(callConnectionId, textToPlay);
}
private void handlePlay(final String callConnectionId, String textToPlay) {
var textPlay = new TextSource()
.setText(textToPlay)
.setVoiceName("en-US-NancyNeural");
client.getCallConnection(callConnectionId)
.getCallMedia()
.playToAll(textPlay);
}
Desligar a chamada
Por fim, quando detectamos uma condição que faz sentido para encerrarmos a chamada, podemos usar o método hangUp
para desligar a chamada.
client.getCallConnection(callConnectionId).hangUp(true);
Executar o código
Acesse o diretório que contém o arquivo pom.xml e use os seguintes comandos mvn:
- Compilar o aplicativo:
mvn compile
- Criar o pacote:
mvn package
- Executar o aplicativo:
mvn exec:java
Pré-requisitos
- Uma conta do Azure com uma assinatura ativa. Crie uma conta gratuitamente.
- Um recurso dos Serviços de Comunicação implantado. Crie um recurso dos Serviços de Comunicação.
- Um número de telefone em seu recurso dos Serviços de Comunicação do Azure que pode fazer chamadas de saída. Caso você não tenha uma assinatura, você pode obter um número de telefone de avaliação gratuita.
- Crie e hospede um Azure Dev Tunnel. Instruções aqui.
- Crie um subdomínio personalizado para seu recurso de serviços de IA do Azure.
- Instalação do LTS do Node.js.
- O Visual Studio Code instalado.
- (Opcional) Um usuário do Microsoft Teams com uma licença de telefone
voice
habilitada. A licença de telefonia do Teams é necessária para adicionar usuários do Teams à chamada. Saiba mais sobre as licenças do Teams aqui. Para obter mais informações sobre como habilitar avoice
no seu sistema de telefonia, confira como configurar seu sistema de telefonia.
Código de exemplo
Baixe ou clone o código de exemplo de início rápido do GitHub.
Navegue até a pasta CallAutomation_OutboundCalling
e abra a solução em um editor de código.
Configurar o ambiente
Baixe o código de exemplo e navegue até o diretório do projeto e execute o comando npm
, que instala as dependências necessárias e configure seu ambiente de desenvolvedor.
npm install
Configurar e hospedar seu Azure DevTunnel
OAzure DevTunnels é um serviço do Azure que permite compartilhar serviços Web locais hospedados na Internet. Use os comandos da CLI do DevTunnel para conectar seu ambiente de desenvolvimento local à Internet pública. Usamos esse ponto de extremidade para notificar seu aplicativo de eventos de chamada do serviço Automação de Chamadas dos Serviços de Comunicação do Azure.
devtunnel create --allow-anonymous
devtunnel port create -p 8080
devtunnel host
Atualize a configuração do aplicativo
Em seguida, atualize o arquivo .env
com os seguintes valores:
CONNECTION_STRING
: a cadeia de conexão do recurso dos Serviços de Comunicação do Azure. Encontre a cadeia de conexão dos Serviços de Comunicação do Azure usando as instruções descritas aqui.CALLBACK_URI
: depois de inicializar o host do DevTunnel, atualize esse campo com a URI.TARGET_PHONE_NUMBER
: atualize o campo com o número de telefone que você gostaria que seu aplicativo chamasse. Esse número de telefone deve usar o formato de número de telefone E164 (por exemplo, +18881234567)ACS_RESOURCE_PHONE_NUMBER
: atualize esse campo com o número de telefone dos Serviços de Comunicação do Azure que você adquiriu. Esse número de telefone deve usar o formato de número de telefone E164 (por exemplo, +18881234567)COGNITIVE_SERVICES_ENDPOINT
: atualize o campo com o ponto de extremidade dos serviços de IA do Azure.TARGET_TEAMS_USER_ID
: (Opcional) atualize o campo com a ID de usuário do Microsoft Teams que você deseja adicionar à chamada. Consulte Usar a API do Graph para obter a ID de usuário do Teams.
CONNECTION_STRING="<YOUR_CONNECTION_STRING>"
ACS_RESOURCE_PHONE_NUMBER ="<YOUR_ACS_NUMBER>"
TARGET_PHONE_NUMBER="<+1XXXXXXXXXX>"
CALLBACK_URI="<VS_TUNNEL_URL>"
COGNITIVE_SERVICES_ENDPOINT="<COGNITIVE_SERVICES_ENDPOINT>"
TARGET_TEAMS_USER_ID="<TARGET_TEAMS_USER_ID>"
Fazer uma chamada de saída e reproduzir mídia
Para fazer a chamada de saída dos Serviços de Comunicação do Azure, use o número de telefone fornecido para o ambiente. Verifique se o número de telefone está no formato de número de telefone E164 (por exemplo, +18881234567)
O código faz uma chamada de saída por meio do target_phone_number que você forneceu e faz uma chamada de saída para esse número:
const callInvite: CallInvite = {
targetParticipant: callee,
sourceCallIdNumber: {
phoneNumber: process.env.ACS_RESOURCE_PHONE_NUMBER || "",
},
};
const options: CreateCallOptions = {
cognitiveServicesEndpoint: process.env.COGNITIVE_SERVICES_ENDPOINT
};
console.log("Placing outbound call...");
acsClient.createCall(callInvite, process.env.CALLBACK_URI + "/api/callbacks", options);
(Opcional) Adicionar um usuário do Microsoft Teams à chamada
Você pode adicionar um usuário do Microsoft Teams à chamada usando o método addParticipant
com a propriedade microsoftTeamsUserId
. Primeiro, você precisa concluir a etapa de pré-requisito Autorização para o recurso dos Serviços de Comunicação do Azure para habilitar a chamada aos usuários do Microsoft Teams. Opcionalmente, você também pode passar um sourceDisplayName
para controlar o texto exibido na notificação do sistema para o usuário do Teams.
await acsClient.getCallConnection(callConnectionId).addParticipant({
targetParticipant: { microsoftTeamsUserId: process.env.TARGET_TEAMS_USER_ID },
sourceDisplayName: "Jack (Contoso Tech Support)"
});
Iniciar a gravação de uma chamada
O serviço de Automação de Chamadas também permite a capacidade de iniciar a gravação e armazenar gravações de chamadas de voz e vídeo. Você pode aprender mais sobre os vários recursos das APIs de gravação de chamadas aqui.
const callLocator: CallLocator = {
id: serverCallId,
kind: "serverCallLocator",
};
const recordingOptions: StartRecordingOptions = {
callLocator: callLocator,
};
const response = await acsClient.getCallRecording().start(recordingOptions);
recordingId = response.recordingId;
Responder a eventos de chamada
Anteriormente em nosso aplicativo, registramos o CALLBACK_URI
no Serviço de Automação de Chamadas. O URI indica o ponto de extremidade que o serviço usa para nos notificar sobre a chamada de eventos que ocorrem. Em seguida, podemos iterar pelos eventos e detectar eventos específicos que nosso aplicativo deseja entender. Respondemos ao evento CallConnected
para ser notificado e iniciar operações de downstream. Usando o TextSource
, você pode fornecer ao serviço o texto que deseja sintetizar e usado para sua mensagem de boas-vindas. O serviço Automação de Chamadas dos Serviços de Comunicação do Azure reproduz essa mensagem após o evento CallConnected
.
Em seguida, passamos o texto para o CallMediaRecognizeChoiceOptions
e, em seguida, chamamos StartRecognizingAsync
. Isso permite que seu aplicativo reconheça a opção escolhida pelo chamador.
callConnectionId = eventData.callConnectionId;
serverCallId = eventData.serverCallId;
console.log("Call back event received, callConnectionId=%s, serverCallId=%s, eventType=%s", callConnectionId, serverCallId, event.type);
callConnection = acsClient.getCallConnection(callConnectionId);
const callMedia = callConnection.getCallMedia();
if (event.type === "Microsoft.Communication.CallConnected") {
console.log("Received CallConnected event");
await startRecording();
await startRecognizing(callMedia, mainMenu, "");
}
async function startRecognizing(callMedia: CallMedia, textToPlay: string, context: string) {
const playSource: TextSource = {
text: textToPlay,
voiceName: "en-US-NancyNeural",
kind: "textSource"
};
const recognizeOptions: CallMediaRecognizeChoiceOptions = {
choices: await getChoices(),
interruptPrompt: false,
initialSilenceTimeoutInSeconds: 10,
playPrompt: playSource,
operationContext: context,
kind: "callMediaRecognizeChoiceOptions"
};
await callMedia.startRecognizing(callee, recognizeOptions)
}
Manipular eventos de escolha
A Automação de Chamadas dos Serviços de Comunicação do Azure dispara o api/callbacks
para o webhook que configuramos e nos notificará com o evento RecognizeCompleted
. O evento nos dá a capacidade de responder à entrada recebida e disparar uma ação. Em seguida, o aplicativo reproduz uma mensagem para o chamador com base na entrada específica recebida.
else if (event.type === "Microsoft.Communication.RecognizeCompleted") {
if(eventData.recognitionType === "choices"){
console.log("Recognition completed, event=%s, resultInformation=%s",eventData, eventData.resultInformation);
var context = eventData.operationContext;
const labelDetected = eventData.choiceResult.label;
const phraseDetected = eventData.choiceResult.recognizedPhrase;
console.log("Recognition completed, labelDetected=%s, phraseDetected=%s, context=%s", labelDetected, phraseDetected, eventData.operationContext);
const textToPlay = labelDetected === confirmLabel ? confirmText : cancelText;
await handlePlay(callMedia, textToPlay);
}
}
async function handlePlay(callConnectionMedia:CallMedia, textContent:string){
const play : TextSource = { text:textContent , voiceName: "en-US-NancyNeural", kind: "textSource"}
await callConnectionMedia.playToAll([play]);
}
Desligar a chamada
Por fim, quando detectamos uma condição que faz sentido para encerrarmos a chamada, podemos usar o método hangUp()
para desligar a chamada.
await acsClient.getCallRecording().stop(recordingId);
callConnection.hangUp(true);
Executar o código
Para executar o aplicativo, abra uma janela terminal e execute o seguinte comando:
npm run dev
Pré-requisitos
- Uma conta do Azure com uma assinatura ativa. Crie uma conta gratuitamente.
- Um recurso dos Serviços de Comunicação implantado. Crie um recurso dos Serviços de Comunicação.
- Um número de telefone em seu recurso dos Serviços de Comunicação do Azure que pode fazer chamadas de saída. Caso você não tenha uma assinatura, você pode obter um número de telefone de avaliação gratuita.
- Crie e hospede um Azure Dev Tunnel. Instruções aqui.
- Crie e conecte serviços de IA do Azure de vários serviços ao recurso dos Serviços de Comunicação do Azure.
- Crie um subdomínio personalizado para seu recurso de serviços de IA do Azure.
- Python 3.7+.
- (Opcional) Um usuário do Microsoft Teams com uma licença de telefone
voice
habilitada. A licença de telefonia do Teams é necessária para adicionar usuários do Teams à chamada. Saiba mais sobre as licenças do Teams aqui. Para obter mais informações sobre como habilitar avoice
no seu sistema de telefonia, confira como configurar seu sistema de telefonia.
Código de exemplo
Baixe ou clone o código de exemplo de início rápido do GitHub.
Navegue até a pasta CallAutomation_OutboundCalling
e abra a solução em um editor de código.
Configurar o ambiente do Python
Crie e ative o ambiente do Python e instale os pacotes necessários usando o comando a seguir. Você pode aprender mais sobre como gerenciar pacotes aqui
pip install -r requirements.txt
Configurar e hospedar seu Azure DevTunnel
OAzure DevTunnels é um serviço do Azure que permite compartilhar serviços Web locais hospedados na Internet. Use os comandos para conectar seu ambiente de desenvolvimento local à Internet pública. O DevTunnels cria um túnel com uma URL de ponto de extremidade persistente e que permite acesso anônimo. Usamos esse ponto de extremidade para notificar seu aplicativo de eventos de chamada do serviço Automação de Chamadas dos Serviços de Comunicação do Azure.
devtunnel create --allow-anonymous
devtunnel port create -p 8080
devtunnel host
Atualize a configuração do aplicativo
Em seguida, atualize o arquivo main.py
com os seguintes valores:
ACS_CONNECTION_STRING
: a cadeia de conexão do recurso dos Serviços de Comunicação do Azure. Encontre a cadeia de conexão dos Serviços de Comunicação do Azure usando as instruções descritas aqui.CALLBACK_URI_HOST
: depois de inicializar o host do DevTunnel, atualize esse campo com a URI.TARGET_PHONE_NUMBER
: atualize o campo com o número de telefone que você gostaria que seu aplicativo chamasse. Esse número de telefone deve usar o formato de número de telefone E164 (por exemplo, +18881234567)ACS_PHONE_NUMBER
: atualize esse campo com o número de telefone dos Serviços de Comunicação do Azure que você adquiriu. Esse número de telefone deve usar o formato de número de telefone E164 (por exemplo, +18881234567)COGNITIVE_SERVICES_ENDPOINT
: atualize o campo com o ponto de extremidade dos serviços de IA do Azure.TARGET_TEAMS_USER_ID
: (Opcional) atualize o campo com a ID de usuário do Microsoft Teams que você deseja adicionar à chamada. Consulte Usar a API do Graph para obter a ID de usuário do Teams.
# Your ACS resource connection string
ACS_CONNECTION_STRING = "<ACS_CONNECTION_STRING>"
# Your ACS resource phone number will act as source number to start outbound call
ACS_PHONE_NUMBER = "<ACS_PHONE_NUMBER>"
# Target phone number you want to receive the call.
TARGET_PHONE_NUMBER = "<TARGET_PHONE_NUMBER>"
# Callback events URI to handle callback events.
CALLBACK_URI_HOST = "<CALLBACK_URI_HOST_WITH_PROTOCOL>"
CALLBACK_EVENTS_URI = CALLBACK_URI_HOST + "/api/callbacks"
#Your Cognitive service endpoint
COGNITIVE_SERVICES_ENDPOINT = "<COGNITIVE_SERVICES_ENDPOINT>"
#(OPTIONAL) Your target Microsoft Teams user Id ex. "00aa00aa-bb11-cc22-dd33-44ee44ee44ee"
TARGET_TEAMS_USER_ID = "<TARGET_TEAMS_USER_ID>"
Fazer uma chamada de saída
Para fazer a chamada de saída dos Serviços de Comunicação do Azure, primeiro forneça o número de telefone que deseja receber a chamada. Para simplificar, você pode atualizar o target_phone_number
com um número de telefone no formato de número de telefone E164 (por exemplo, +18881234567)
Faça uma chamada de saída por meio do target_phone_number que você forneceu:
target_participant = PhoneNumberIdentifier(TARGET_PHONE_NUMBER)
source_caller = PhoneNumberIdentifier(ACS_PHONE_NUMBER)
call_invite = CallInvite(target=target_participant, source_caller_id_number=source_caller)
call_connection_properties = call_automation_client.create_call(call_invite, CALLBACK_EVENTS_URI,
cognitive_services_endpoint=COGNITIVE_SERVICES_ENDPOINT)
app.logger.info("Created call with connection id: %s",
call_connection_properties.call_connection_id)
return redirect("/")
(Opcional) Adicionar um usuário do Microsoft Teams à chamada
Você pode adicionar um usuário do Microsoft Teams à chamada usando o add_participant
método com a MicrosoftTeamsUserIdentifier
ID do usuário e do Teams. Primeiro, você precisa concluir a etapa de pré-requisito Autorização para o recurso dos Serviços de Comunicação do Azure para habilitar a chamada aos usuários do Microsoft Teams. Opcionalmente, você também pode passar um source_display_name
para controlar o texto exibido na notificação do sistema para o usuário do Teams.
call_connection_client.add_participant(target_participant = CallInvite(
target = MicrosoftTeamsUserIdentifier(user_id=TARGET_TEAMS_USER_ID),
source_display_name = "Jack (Contoso Tech Support)"))
Iniciar a gravação de uma chamada
O serviço de Automação de Chamadas também permite a capacidade de iniciar a gravação e armazenar gravações de chamadas de voz e vídeo. Você pode aprender mais sobre os vários recursos das APIs de gravação de chamadas aqui.
recording_properties = call_automation_client.start_recording(ServerCallLocator(event.data['serverCallId']))
recording_id = recording_properties.recording_id
Responder a eventos de chamada
Anteriormente em nosso aplicativo, registramos o CALLBACK_URI_HOST
no Serviço de Automação de Chamadas. O URI indica o ponto de extremidade que o serviço usa para nos notificar sobre a chamada de eventos que ocorrem. Em seguida, podemos iterar pelos eventos e detectar eventos específicos que nosso aplicativo deseja entender. No código abaixo respondemos ao evento CallConnected
.
@app.route('/api/callbacks', methods=['POST'])
def callback_events_handler():
for event_dict in request.json:
event = CloudEvent.from_dict(event_dict)
if event.type == "Microsoft.Communication.CallConnected":
# Handle Call Connected Event
...
return Response(status=200)
Reproduza mensagem de boas-vindas e reconheça
Usando o TextSource
, você pode fornecer ao serviço o texto que deseja sintetizar e usado para sua mensagem de boas-vindas. O serviço Automação de Chamadas dos Serviços de Comunicação do Azure reproduz essa mensagem após o evento CallConnected
.
Em seguida, passamos o texto para o CallMediaRecognizeChoiceOptions
e, em seguida, chamamos StartRecognizingAsync
. Isso permite que seu aplicativo reconheça a opção escolhida pelo chamador.
get_media_recognize_choice_options(
call_connection_client=call_connection_client,
text_to_play=MainMenu,
target_participant=target_participant,
choices=get_choices(),context="")
def get_media_recognize_choice_options(call_connection_client: CallConnectionClient, text_to_play: str, target_participant:str, choices: any, context: str):
play_source = TextSource (text= text_to_play, voice_name= SpeechToTextVoice)
call_connection_client.start_recognizing_media(
input_type=RecognizeInputType.CHOICES,
target_participant=target_participant,
choices=choices,
play_prompt=play_source,
interrupt_prompt=False,
initial_silence_timeout=10,
operation_context=context
)
def get_choices():
choices = [
RecognitionChoice(label = ConfirmChoiceLabel, phrases= ["Confirm", "First", "One"], tone = DtmfTone.ONE),
RecognitionChoice(label = CancelChoiceLabel, phrases= ["Cancel", "Second", "Two"], tone = DtmfTone.TWO)
]
return choices
Manipular eventos de escolha
A Automação de Chamadas dos Serviços de Comunicação do Azure dispara o api/callbacks
para o webhook que configuramos e nos notificará com o evento RecognizeCompleted
. O evento nos dá a capacidade de responder à entrada recebida e disparar uma ação. Em seguida, o aplicativo reproduz uma mensagem para o chamador com base na entrada específica recebida.
elif event.type == "Microsoft.Communication.RecognizeCompleted":
app.logger.info("Recognize completed: data=%s", event.data)
if event.data['recognitionType'] == "choices":
labelDetected = event.data['choiceResult']['label'];
phraseDetected = event.data['choiceResult']['recognizedPhrase'];
app.logger.info("Recognition completed, labelDetected=%s, phraseDetected=%s, context=%s", labelDetected, phraseDetected, event.data.get('operationContext'))
if labelDetected == ConfirmChoiceLabel:
textToPlay = ConfirmedText
else:
textToPlay = CancelText
handle_play(call_connection_client = call_connection_client, text_to_play = textToPlay)
def handle_play(call_connection_client: CallConnectionClient, text_to_play: str):
play_source = TextSource(text = text_to_play, voice_name = SpeechToTextVoice)
call_connection_client.play_media_to_all(play_source)
Desligar a chamada
Por fim, quando detectamos uma condição que faz sentido para encerrarmos a chamada, podemos usar o método hang_up()
para desligar a chamada. Por fim, também podemos interromper com segurança a operação de gravação de chamadas.
call_automation_client.stop_recording(recording_id)
call_connection_client.hang_up(is_for_everyone=True)
Executar o código
Para executar o aplicativo com o VS Code, abra uma janela do Terminal e execute o comando a seguir
python main.py