Gerenciar a gravação de chamadas no cliente

Importante

A funcionalidade descrita neste artigo está atualmente em versão prévia pública. Essa versão prévia é fornecida sem um contrato de nível de serviço e não é recomendada para cargas de trabalho de produção. Alguns recursos podem não ter suporte ou podem ter restrição de recursos. Para obter mais informações, consulte Termos de Uso Complementares de Versões Prévias do Microsoft Azure.

A gravação de chamadas permite que os usuários gravem chamadas feitas com os Serviços de Comunicação do Azure. Neste artigo, você aprenderá a gerenciar a gravação no lado do cliente. Antes de começar, você precisa configurar a gravação no lado do servidor.

Pré-requisitos

Instalar o SDK

Use o comando npm install para instalar o SDK Comum e de Chamada dos Serviços de Comunicação do Azure para JavaScript:

npm install @azure/communication-common --save
npm install @azure/communication-calling --save

Inicializar objetos necessários

Uma instância CallClient é necessária para a maioria das operações de chamada. Ao criar uma instância de CallClient, você pode configurá-la com opções personalizadas, como uma instância de Logger.

Com a instância de CallClient, você pode criar uma instância de CallAgent chamando o createCallAgent. Esse método retorna de modo assíncrono um objeto de instância CallAgent.

O método createCallAgent usa CommunicationTokenCredential como um argumento. Ele aceita um token de acesso do usuário.

Você pode usar o método getDeviceManager na instância CallClient para acessar o deviceManager.

const { CallClient } = require('@azure/communication-calling');
const { AzureCommunicationTokenCredential} = require('@azure/communication-common');
const { AzureLogger, setLogLevel } = require("@azure/logger");

// Set the logger's log level
setLogLevel('verbose');

// Redirect log output to console, file, buffer, REST API, or whatever location you want
AzureLogger.log = (...args) => {
    console.log(...args); // Redirect log output to console
};

const userToken = '<USER_TOKEN>';
callClient = new CallClient(options);
const tokenCredential = new AzureCommunicationTokenCredential(userToken);
const callAgent = await callClient.createCallAgent(tokenCredential, {displayName: 'optional Azure Communication Services user name'});
const deviceManager = await callClient.getDeviceManager()

Como gerenciar melhor a conectividade do SDK com a infraestrutura da Microsoft

A instância Call Agent ajuda você a gerenciar chamadas (para ingressar ou iniciar chamadas). Para trabalhar, o SDK de chamada precisa se conectar à infraestrutura da Microsoft para receber notificações de chamadas de entrada e coordenar outros detalhes da chamada. O seu Call Agent tem dois estados possíveis:

Conectado: um valor connectionStatue Call Agent de Connected significa que o SDK do cliente está conectado e capaz de receber notificações da infraestrutura da Microsoft.

Desconectado: um valor connectionStatue Call Agent de Disconnected declara que há um problema que está impedindo o SDK de se conectar corretamente. Call Agent deve ser recriado.

  • invalidToken: se um token tiver expirado ou for inválido, a instância Call Agent se desconecta com este erro.
  • connectionIssue: se houver um problema com o cliente se conectando à infraestrutura da Microsoft, depois de muitas tentativas Call Agent expõe o erro connectionIssue.

Você pode verificar se o local Call Agent está conectado à infraestrutura da Microsoft inspecionando o valor atual da propriedade connectionState. Durante uma chamada ativa, você pode ouvir o evento connectionStateChanged para determinar se Call Agent é alterado do estado Conectado ao Desconectado.

const connectionState = callAgentInstance.connectionState;
console.log(connectionState); // it may return either of 'Connected' | 'Disconnected'

const connectionStateCallback = (args) => {
    console.log(args); // it will return an object with oldState and newState, each of having a value of either of 'Connected' | 'Disconnected'
    // it will also return reason, either of 'invalidToken' | 'connectionIssue'
}
callAgentInstance.on('connectionStateChanged', connectionStateCallback);

Observação

Esta API é fornecida como uma versão prévia para desenvolvedores e pode ser alterada com base nos comentários que recebemos. Não use essa API em um ambiente de produção. Para usar essa API, use a versão beta do SDK da Web de Chamadas dos Serviços de Comunicação do Azure.

Gravação na nuvem

A gravação de chamadas é um recurso estendido da API de Chamada principal. Primeiro, você precisa importar recursos de chamada do SDK de Chamadas:

import { Features} from "@azure/communication-calling";

Em seguida, é possível obter o objeto da API dos recursos de gravação da instância de chamada:

const callRecordingApi = call.feature(Features.Recording);

Para verificar se a chamada está sendo gravada, inspecione a propriedade isRecordingActive de callRecordingApi. Ele retorna Boolean.

const isRecordingActive = callRecordingApi.isRecordingActive;

Você também pode assinar as alterações de gravação:

const isRecordingActiveChangedHandler = () => {
    console.log(callRecordingApi.isRecordingActive);
};

callRecordingApi.on('isRecordingActiveChanged', isRecordingActiveChangedHandler);

Você pode obter uma lista de gravações usando a propriedade recordings de callRecordingApi. Ela retorna RecordingInfo[], que tem o nome de exibição do usuário e o estado atual da gravação na nuvem.

const recordings = callRecordingApi.recordings;

recordings.forEach(r => {
    console.log("State: ${r.state}");

Você também pode assinar recordingsUpdated e obter uma coleção de gravações atualizadas. Esse evento é disparado sempre que há uma atualização de gravação.

const cloudRecordingsUpdatedHandler = (args: { added: SDK.RecordingInfo[], removed: SDK.RecordingInfo[]}) => {
                        console.log('Recording started by: ');
                        args.added?.forEach(a => {
                            console.log('State: ${a.state}');
                        });

                        console.log('Recording stopped by: ');
                        args.removed?.forEach(r => {
                            console.log('State: ${r.state}');
                        });
                    };
callRecordingApi.on('recordingsUpdated', cloudRecordingsUpdatedHandler );

Instalar o SDK

Localize seu arquivo build.gradle no nível do projeto e adicione mavenCentral() à lista de repositórios em buildscript e allprojects:

buildscript {
    repositories {
    ...
        mavenCentral()
    ...
    }
}
allprojects {
    repositories {
    ...
        mavenCentral()
    ...
    }
}

Em seguida, no seu arquivo build.gradle no nível do módulo, adicione as seguintes linhas à seção de dependencies:

dependencies {
    ...
    implementation 'com.azure.android:azure-communication-calling:1.0.0'
    ...
}

Inicializar objetos necessários

Para criar uma instância CallAgent, você precisa chamar o método createCallAgent em uma instância CallClient. Essa chamada retorna de forma assíncrona um objeto de instância CallAgent.

O método createCallAgent usa CommunicationUserCredential como argumento, que encapsula um token de acesso.

Para acessar DeviceManager, você deverá criar uma instância callAgent primeiro. Em seguida, você poderá usar o método CallClient.getDeviceManager para obter DeviceManager.

String userToken = '<user token>';
CallClient callClient = new CallClient();
CommunicationTokenCredential tokenCredential = new CommunicationTokenCredential(userToken);
android.content.Context appContext = this.getApplicationContext(); // From within an activity, for instance
CallAgent callAgent = callClient.createCallAgent(appContext, tokenCredential).get();
DeviceManager deviceManager = callClient.getDeviceManager(appContext).get();

Para definir um nome de exibição para o chamador, use este método alternativo:

String userToken = '<user token>';
CallClient callClient = new CallClient();
CommunicationTokenCredential tokenCredential = new CommunicationTokenCredential(userToken);
android.content.Context appContext = this.getApplicationContext(); // From within an activity, for instance
CallAgentOptions callAgentOptions = new CallAgentOptions();
callAgentOptions.setDisplayName("Alice Bob");
DeviceManager deviceManager = callClient.getDeviceManager(appContext).get();
CallAgent callAgent = callClient.createCallAgent(appContext, tokenCredential, callAgentOptions).get();

Chamadas de registro

Observação

Esta API é fornecida como uma versão prévia para desenvolvedores e pode ser alterada com base nos comentários que recebemos. Não use essa API em um ambiente de produção. Para usar essa API, use a versão beta do SDK do Android de Chamadas dos Serviços de Comunicação do Azure.

A gravação de chamada é um recurso estendido do objeto Call principal.

Aviso

Até a versão 1.1.0 e versão beta 1.1.0-beta.1 do SDK do Android de Chamadas dos Serviços de Comunicação do Azure, isRecordingActive e addOnIsRecordingActiveChangedListener faziam parte do objeto Call. Para novas versões beta, essas APIs foram movidas como um recurso estendido de Call.

Primeiro, você precisa obter o objeto do recurso de gravação:

RecordingCallFeature callRecordingFeature = call.feature(Features.RECORDING);

Em seguida, para verificar se a chamada está sendo gravada, inspecione a isRecordingActive de propriedadecallRecordingFeature. Ele retorna boolean.

boolean isRecordingActive = callRecordingFeature.isRecordingActive();

Você também pode assinar as alterações de gravação:

private void handleCallOnIsRecordingChanged(PropertyChangedEvent args) {
  boolean isRecordingActive = callRecordingFeature.isRecordingActive();
}

callRecordingFeature.addOnIsRecordingActiveChangedListener(handleCallOnIsRecordingChanged);

Se quiser iniciar a gravação do seu aplicativo, primeiro siga a Visão geral da Gravação de chamada para ver as etapas para configurar a gravação de chamada.

Depois de configurar a gravação de chamada no servidor, no aplicativo Android, você precisará obter o valor ServerCallId da chamada e enviá-lo ao servidor para iniciar o processo de gravação. Você pode encontrar o valor ServerCallId usando getServerCallId() da classe CallInfo. Você pode encontrar a classe CallInfo no objeto de classe usando getInfo().

try {
    String serverCallId = call.getInfo().getServerCallId().get();
    // Send serverCallId to your recording server to start the call recording.
} catch (ExecutionException | InterruptedException e) {

} catch (UnsupportedOperationException unsupportedOperationException) {

}

Quando você inicia a gravação do servidor, o evento handleCallOnIsRecordingChanged é disparado e o valor de callRecordingFeature.isRecordingActive() é true.

Assim como para iniciar a gravação de chamada, se você quiser interromper a gravação de chamada, será necessário obter ServerCallId e enviá-lo ao servidor de gravação para que ele possa interromper a gravação:

try {
    String serverCallId = call.getInfo().getServerCallId().get();
    // Send serverCallId to your recording server to stop the call recording.
} catch (ExecutionException | InterruptedException e) {

} catch (UnsupportedOperationException unsupportedOperationException) {

}

Quando você interrompe a gravação do servidor, o evento handleCallOnIsRecordingChanged é disparado e o valor de callRecordingFeature.isRecordingActive() é false.

Configurar o backup do sistema

Siga essas etapas para configurar seu sistema.

Criar o projeto do Xcode

No Xcode, crie um projeto do iOS e selecione o modelo Aplicativo de Modo de Exibição Único. Este artigo usa a estrutura SwiftUI e, portanto, você deve definir a Linguagem como Swift e a Interface como SwiftUI.

Você não vai criar testes neste artigo. Fique à vontade para limpar a caixa de seleção Incluir Testes.

Captura de tela que mostra a janela para a criação de um projeto no Xcode.

Instalar o pacote e as dependências usando o CocoaPods

  1. Crie um Podfile para seu aplicativo, como este exemplo:

    platform :ios, '13.0'
    use_frameworks!
    target 'AzureCommunicationCallingSample' do
        pod 'AzureCommunicationCalling', '~> 1.0.0'
    end
    
  2. Execute pod install.

  3. Abra o .xcworkspace usando o Xcode.

Solicitar acesso ao microfone

Para acessar o microfone do dispositivo, você precisa atualizar a lista de propriedades de informações do aplicativo usando NSMicrophoneUsageDescription. Defina o valor associado como uma cadeia de caracteres incluída na caixa de diálogo que o sistema usa para solicitar acesso ao usuário.

Clique com o botão direito do mouse na entrada Info.plist da árvore de projeto e selecione Abrir Como>Código-Fonte. Adicione as linhas a seguir na seção do nível superior<dict>e, em seguida, salve o arquivo.

<key>NSMicrophoneUsageDescription</key>
<string>Need microphone access for VOIP calling.</string>

Configurar o framework de aplicativos

Abra o arquivo ContentView.swift do seu projeto. Adicione uma declaração import à parte superior do arquivo para importar a biblioteca AzureCommunicationCalling. Além disso, importeAVFoundation. Você vai precisar dele para as solicitações de permissão de áudio no código.

import AzureCommunicationCalling
import AVFoundation

Inicialização do CallAgent

Para criar umaCallAgentinstânciaCallClient,você precisa usar um método callClient.createCallAgentque retorne de modo assíncrono um objetoCallAgentdepois que ele for inicializado.

Para criar um cliente de chamada, passe um objeto CommunicationTokenCredential:

import AzureCommunication

let tokenString = "token_string"
var userCredential: CommunicationTokenCredential?
do {
    let options = CommunicationTokenRefreshOptions(initialToken: token, refreshProactively: true, tokenRefresher: self.fetchTokenSync)
    userCredential = try CommunicationTokenCredential(withOptions: options)
} catch {
    updates("Couldn't created Credential object", false)
    initializationDispatchGroup!.leave()
    return
}

// tokenProvider needs to be implemented by Contoso, which fetches a new token
public func fetchTokenSync(then onCompletion: TokenRefreshOnCompletion) {
    let newToken = self.tokenProvider!.fetchNewToken()
    onCompletion(newToken, nil)
}

Passe o objeto CommunicationTokenCredential que você criou para CallClient e defina o nome de exibição:

self.callClient = CallClient()
let callAgentOptions = CallAgentOptions()
options.displayName = " iOS Azure Communication Services User"

self.callClient!.createCallAgent(userCredential: userCredential!,
    options: callAgentOptions) { (callAgent, error) in
        if error == nil {
            print("Create agent succeeded")
            self.callAgent = callAgent
        } else {
            print("Create agent failed")
        }
})

Chamadas de registro

Observação

Esta API é fornecida como uma versão prévia para desenvolvedores e pode ser alterada com base nos comentários que recebemos. Não use essa API em um ambiente de produção. Para usar essa API, use a versão beta do SDK do iOS de Chamadas dos Serviços de Comunicação do Azure.

A gravação de chamada é um recurso estendido do objeto Call principal.

Aviso

Até a versão 1.1.0 e a versão beta 1.1.0-beta.1 do SDK do iOS de Chamadas dos Serviços de Comunicação do Azure, isRecordingActive fazia parte do objeto Call e didChangeRecordingState fazia parte do delegado CallDelegate. Para novas versões beta, essas APIs foram movidas como um recurso estendido de Call.

Primeiro, você precisa obter o objeto do recurso de gravação:

let callRecordingFeature = call.feature(Features.recording)

Em seguida, para verificar se a chamada está sendo gravada, inspecione a isRecordingActive de propriedadecallRecordingFeature. Ele retorna Bool.

let isRecordingActive = callRecordingFeature.isRecordingActive;

Você também pode assinar as alterações de gravação implementando o delegado RecordingCallFeatureDelegate em sua classe com o evento didChangeRecordingState:

callRecordingFeature.delegate = self

// didChangeRecordingState is a member of RecordingCallFeatureDelegate
public func recordingCallFeature(_ recordingCallFeature: RecordingCallFeature, didChangeRecordingState args: PropertyChangedEventArgs) {
    let isRecordingActive = recordingFeature.isRecordingActive
}

Se quiser iniciar a gravação do seu aplicativo, primeiro siga a Visão geral da Gravação de chamada para ver as etapas para configurar a gravação de chamada.

Depois de configurar a gravação de chamada no servidor, no aplicativo iOS, você precisará obter o valor ServerCallId da chamada e enviá-lo ao servidor para iniciar o processo de gravação. Você pode encontrar o valor ServerCallId usando getServerCallId() da classe CallInfo. Você pode encontrar a classe CallInfo no objeto de classe usando getInfo().

// Send serverCallId to your recording server to start the call recording.
let serverCallId = call.info.getServerCallId(){ (serverId, error) in }

Quando você inicia a gravação do servidor, o evento didChangeRecordingState é disparado e o valor de recordingFeature.isRecordingActive é true.

Assim como para iniciar a gravação de chamada, se você quiser interromper a gravação de chamada, será necessário obter ServerCallId e enviá-lo ao servidor de gravação para que ele possa interromper a gravação:

// Send serverCallId to your recording server to stop the call recording.
let serverCallId = call.info.getServerCallId(){ (serverId, error) in }

Quando você interrompe a gravação do servidor, o evento didChangeRecordingState é disparado e o valor de recordingFeature.isRecordingActive é false.

Configurar o backup do sistema

Siga essas etapas para configurar seu sistema.

Criar o projeto do Visual Studio

Para um aplicativo da Plataforma Universal do Windows, crie um novo projeto de Aplicativo em Branco (Windows Universal) no Visual Studio 2022. Depois de inserir o nome do projeto, fique à vontade para escolher qualquer SDK do Windows posterior a 10.0.17763.0.

Para um aplicativo WinUI 3, crie um novo projeto com o modelo Aplicativo em Branco, Empacotado (WinUI 3 na Área de Trabalho) para configurar um aplicativo WinUI 3 de página única. O SDK do Aplicativo do Windows versão 1.3 ou posterior é necessário.

Instalar o pacote e as dependências usando o Gerenciador de Pacotes do NuGet

As bibliotecas e as APIs do SDK de Chamada estão disponíveis publicamente por meio de um pacote NuGet.

Para localizar, baixar e instalar o pacote NuGet do SDK de Chamada:

  1. Abra o Gerenciador de Pacotes do NuGet selecionando Ferramentas>Gerenciador de Pacotes do NuGet>Gerenciar de Pacotes do NuGet para Solução.
  2. Selecione Procurar e, em seguida, insira Azure.Communication.Calling.WindowsClient na caixa de pesquisa.
  3. Certifique-se de que a caixa de seleção Incluir pré-lançamento esteja marcada.
  4. Selecione o pacote Azure.Communication.Calling.WindowsClient e, a seguir, selecione Azure.Communication.Calling.WindowsClient 1.4.0-beta.1 ou uma versão mais recente.
  5. Marque a caixa de seleção que corresponde ao projeto dos Serviços de Comunicação do Azure no painel do lado direito.
  6. Selecione Instalar.

Chamadas de registro

A gravação de chamada é um recurso estendido do objeto Call principal. Primeiro, você precisa obter o objeto do recurso de gravação:

RecordingCallFeature recordingFeature = call.Features.Recording;

Em seguida, para verificar se a chamada está sendo gravada, inspecione a IsRecordingActive de propriedaderecordingFeature. Ele retorna boolean.

boolean isRecordingActive = recordingFeature.IsRecordingActive;

Você também pode assinar as alterações de gravação:

private async void Call__OnIsRecordingActiveChanged(object sender, PropertyChangedEventArgs args)
  boolean isRecordingActive = recordingFeature.IsRecordingActive;
}

recordingFeature.IsRecordingActiveChanged += Call__OnIsRecordingActiveChanged;

Gravação de conformidade

A gravação de conformidade é uma gravação baseada na política do Microsoft Teams. Você pode habilitá-la usando este tutorial: Introdução à gravação baseada em política do Teams para chamadas.

A gravação baseada em política é iniciada automaticamente quando um usuário que tem a política ingressa em uma chamada. Para receber uma notificação dos Serviços de Comunicação do Azure sobre a gravação, use o código a seguir:

const callRecordingApi = call.feature(Features.Recording);

const isComplianceRecordingActive = callRecordingApi.isRecordingActive;

const isComplianceRecordingActiveChangedHandler = () => {
    console.log(callRecordingApi.isRecordingActive);
};

callRecordingApi.on('isRecordingActiveChanged', isComplianceRecordingActiveChangedHandler);

Você também pode implementar a gravação de conformidade usando um bot de gravação personalizado. Confira o exemplo do GitHub.

Próximas etapas