Maskierte Anrufe

Dieser Anwendungsfall zeigt Ihnen, wie Sie die Idee, die in Anwendungsfall private Sprachkommunikation. Es zeigt Ihnen, wie Sie einen Sprach-Proxy mit der Vonage-Software erstellen. Node Server SDKmit virtuellen Numbers, um die echten Telefonnummern der Teilnehmer zu verbergen. Der vollständige Quellcode ist auch in unserem Voice Proxy unter Verwendung des Voice API GitHub Repo. Alternativ können Sie sich auch an Code Hub zum Ausprobieren der Masked Calling API.

Übersicht

Manchmal möchte man, dass sich zwei Benutzer gegenseitig anrufen können, ohne ihre privaten Nummern preiszugeben.

Wenn Sie zum Beispiel einen Mitfahrdienst betreiben, möchten Sie, dass Ihre Nutzer miteinander sprechen können, um Abholzeiten und -orte zu koordinieren. Aber Sie wollen die Telefonnummern Ihrer Kunden nicht herausgeben - schließlich haben Sie die Pflicht, deren Privatsphäre zu schützen. Und Sie wollen auch nicht, dass sie direkt Mitfahrgelegenheiten arrangieren können, ohne Ihren Dienst zu nutzen, denn das bedeutet Umsatzeinbußen für Ihr Unternehmen.

Mithilfe der APIs von Vonage können Sie jedem Teilnehmer eines Anrufs eine temporäre Nummer zuweisen, hinter der sich seine echte Nummer verbirgt. Jeder Anrufer sieht nur die temporäre Nummer für die Dauer des Anrufs. Wenn kein weiterer Gesprächsbedarf mehr besteht, wird die temporäre Nummer wieder aufgehoben.

Sie können den Quellcode von unserer Website herunterladen GitHub-Repositorium.

Voraussetzungen

Um diesen Anwendungsfall bearbeiten zu können, benötigen Sie:

Code-Speicher

Es gibt eine GitHub-Repository, das den Code enthält.

Schritte

Um die Anwendung zu erstellen, führen Sie die folgenden Schritte durch:

Konfiguration

Sie müssen eine .env Datei mit der Konfiguration. Anweisungen dazu finden Sie im Abschnitt GitHub README. Während Sie diesen Anwendungsfall durcharbeiten, können Sie Ihre Konfigurationsdatei mit den erforderlichen Werten für Variablen wie API-Schlüssel, API-Geheimnis, Anwendungs-ID, Debug-Modus und bereitgestellte Numbers auffüllen.

Erstellen einer Voice API-Anwendung

Eine Voice API Application ist ein Konstrukt von Vonage und sollte nicht mit der Anwendung, die Sie schreiben werden, verwechselt werden. Es handelt sich vielmehr um einen "Container" für die Authentifizierungs- und Konfigurationseinstellungen, die Sie für die Arbeit mit der API benötigen.

Sie können eine Voice API Application mit der Vonage CLI erstellen. Sie müssen einen Namen für die Anwendung und die URLs von zwei Webhook-Endpunkten angeben: Der erste ist derjenige, an den die APIs von Vonage eine Anfrage stellen, wenn Sie einen eingehenden Anruf auf Ihrer virtuellen Nummer erhalten, und der zweite ist derjenige, an den die API Ereignisdaten senden kann.

Ersetzen Sie den Domänennamen in dem folgenden Vonage CLI-Befehl durch Ihren ngrok-Domänennamen (Wie man ngrok ausführt) und führen Sie es im Stammverzeichnis Ihres Projekts aus:

vonage apps:create "Voice Proxy" --voice_answer_url=https://example.com/proxy-call --voice_event_url=https://example.com/event

Dieser Befehl erstellt eine Datei namens voice_proxy.key die Authentifizierungsinformationen enthält und eine eindeutige Anwendungs-ID zurückgibt. Notieren Sie sich diese ID, da Sie sie in den folgenden Schritten benötigen werden.

Erstellen Sie die Webanwendung

Diese Anwendung verwendet die Express Rahmen für das Routing und die Vonage Node Server SDK für die Arbeit mit der Voice API. dotenv wird verwendet, damit die Anwendung mit einem .env Textdatei.

Unter server.js initialisiert der Code die Abhängigkeiten der Anwendung und startet den Webserver. Für die Homepage der Anwendung wird ein Route-Handler implementiert (/), so dass Sie testen können, ob der Server läuft, indem Sie node server.js und Besuch http://localhost:3000 in Ihrem Browser:

"use strict";

const express = require('express');
const bodyParser = require('body-parser');

const app = express();
app.set('port', (process.env.PORT || 3000));
app.use(bodyParser.urlencoded({ extended: false }));

const config = require(__dirname + '/../config');

const VoiceProxy = require('./VoiceProxy');
const voiceProxy = new VoiceProxy(config);

app.listen(app.get('port'), function() {
  console.log('Voice Proxy App listening on port', app.get('port'));
});

Beachten Sie, dass der Code ein Objekt des Typs VoiceProxy Klasse, um die Weiterleitung von Nachrichten, die an Ihre virtuelle Nummer gesendet werden, an die reale Nummer des Empfängers zu gewährleisten. Der Proxying-Prozess wird beschrieben in den Anruf bevollmächtigenDiese Klasse initialisiert das Vonage Server SDK mit dem API-Schlüssel und dem Geheimnis, die Sie im nächsten Schritt konfigurieren. Dadurch kann Ihre Anwendung Sprachanrufe tätigen und empfangen:

const VoiceProxy = function(config) {
  this.config = config;
  
  this.nexmo = new Nexmo({
      apiKey: this.config.VONAGE_API_KEY,
      apiSecret: this.config.VONAGE_API_SECRET
    },{
      debug: this.config.VONAGE_DEBUG
    });
  
  // Virtual Numbers to be assigned to UserA and UserB
  this.provisionedNumbers = [].concat(this.config.PROVISIONED_NUMBERS);
  
  // In progress conversations
  this.conversations = [];
};

Bereitstellung virtueller Numbers

Virtuelle Numbers werden verwendet, um echte Telefonnummern vor den Nutzern Ihrer Anwendungen zu verbergen.

Das folgende Workflow-Diagramm zeigt den Prozess der Bereitstellung und Konfiguration einer virtuellen Nummer:

UserBUserAVonageAppUserBUserAVonageAppInitializationSearch NumbersNumbers FoundProvision NumbersNumbers ProvisionedConfigure NumbersNumbers Configured

Um eine virtuelle Nummer einzurichten, durchsuchen Sie die verfügbaren Nummern, die Ihren Kriterien entsprechen. Zum Beispiel eine Rufnummer in einem bestimmten Land mit Sprachfunktion:

const Nexmo = require('nexmo');

/**
 * Create a new VoiceProxy
 */
const VoiceProxy = function(config) {
  this.config = config;

  this.nexmo = new Nexmo({
    apiKey: this.config.NEXMO_API_KEY,
    apiSecret: this.config.NEXMO_API_SECRET
  },{
    debug: this.config.NEXMO_DEBUG
  });

  // Virtual Numbers to be assigned to UserA and UserB
  this.provisionedNumbers = [].concat(this.config.PROVISIONED_NUMBERS);

  // In progress conversations
  this.conversations = [];
};

/**
 * Provision two virtual numbers. Would provision more in a real app.
 */
VoiceProxy.prototype.provisionVirtualNumbers = function() {
  // Buy a UK number with VOICE capabilities.
  // For this example we'll also get SMS so we can send them a text notification
  this.nexmo.number.search('GB', {features: 'VOICE,SMS'}, function(err, res) {
    if(err) {
      console.error(err);
    }
    else {
      const numbers = res.numbers;

      // For demo purposes:
      // - Assume that at least two numbers will be available
      // - Rent just two virtual numbers: one for each conversation participant
      this.rentNumber(numbers[0]);
      this.rentNumber(numbers[1]);
    }
  }.bind(this));
};

Mieten Sie dann die gewünschten Numbers und verknüpfen Sie sie mit Ihrer Bewerbung.

HINWEIS: Für einige Numbers ist eine Postanschrift erforderlich, um sie mieten zu können. Wenn Sie nicht in der Lage sind, eine Nummer programmgesteuert zu erhalten, besuchen Sie die Dashboard wo Sie Numbers nach Bedarf mieten können.

Wenn ein Ereignis in Bezug auf jede mit einer Applikation verbundene Nummer eintritt, sendet Vonage eine Anfrage an Ihren Webhook-Endpunkt mit Informationen über das Ereignis. Nach der Konfiguration speichern Sie die Rufnummer für die spätere Verwendung:

/**
 * Rent the given numbers
 */
VoiceProxy.prototype.rentNumber = function(number) {
  this.nexmo.number.buy(number.country, number.msisdn, function(err, res) {
    if(err) {
      console.error(err);
    }
    else {
      this.configureNumber(number);
    }
  }.bind(this));
};

/**
 * Configure the number to be associated with the Voice Proxy application.
 */
VoiceProxy.prototype.configureNumber = function(number) {
  const options = {
    voiceCallbackType: 'app',
    voiceCallbackValue: this.config.NEXMO_APP_ID,
  };
  this.nexmo.number.update(number.country, number.msisdn, options, function(err, res) {
    if(err) {
      console.error(err);
    }
    else {
      this.provisionedNumbers.push(number);
    }
  }.bind(this));
};

Um virtuelle Numbers bereitzustellen, besuchen Sie http://localhost:3000/numbers/provision in Ihrem Browser.

Sie verfügen nun über die virtuellen Numbers, die Sie benötigen, um die Kommunikation zwischen Ihren Benutzern zu verschleiern.

HINWEIS: In einer Produktionsanwendung wählen Sie aus einem Pool von virtuellen Numbers. Sie sollten diese Funktion jedoch beibehalten, um bei Bedarf zusätzliche Nummern zu mieten.

Einen Aufruf erstellen

Der Arbeitsablauf zum Erstellen eines Anrufs ist folgender:

UserBUserAVonageAppUserBUserAVonageAppConversation StartsBasic Number InsightNumber Insight responseMap Real/Virtual Numbersfor Each ParticipantSMS to UserASMSSMS to UserBSMS

Der folgende Aufruf:

/**
 * Create a new tracked conversation so there is a real/virtual mapping of numbers.
 */
VoiceProxy.prototype.createConversation = function(userANumber, userBNumber, cb) {
  this.checkNumbers(userANumber, userBNumber)
    .then(this.saveConversation.bind(this))
    .then(this.sendSMS.bind(this))
    .then(function(conversation) {
      cb(null, conversation);
    })
    .catch(function(err) {
      cb(err);
    });
};

Überprüfen Sie die Telefonnummern

Wenn die Benutzer Ihrer Anwendung ihre Telefonnummern angeben, können Sie mit Number Insight sicherstellen, dass sie gültig sind. Sie können auch sehen, in welchem Land die Telefonnummern registriert sind:

/**
 * Ensure the given numbers are valid and which country they are associated with.
 */
VoiceProxy.prototype.checkNumbers = function(userANumber, userBNumber) {
  const niGetPromise = (number) => new Promise ((resolve) => {
    this.nexmo.numberInsight.get(number, (error, result) => {
      if(error) {
        console.error('error',error);
      }
      else {
        return resolve(result);
      }
    })
  });

  const userAGet = niGetPromise({level: 'basic', number: userANumber});
  const userBGet = niGetPromise({level: 'basic', number: userBNumber});

  return Promise.all([userAGet, userBGet]);
};

Zuordnung von Telefonnummern zu echten Nummern

Sobald Sie sich vergewissert haben, dass die Telefonnummern gültig sind, ordnen Sie jede echte Nummer einem virtuelle Nummer und speichern Sie den Anruf:

/**
 * Store the conversation information.
 */
VoiceProxy.prototype.saveConversation = function(results) {
  let userAResult = results[0];
  let userANumber = {
    msisdn: userAResult.international_format_number,
    country: userAResult.country_code
  };

  let userBResult = results[1];
  let userBNumber = {
    msisdn: userBResult.international_format_number,
    country: userBResult.country_code
  };

  // Create conversation object - for demo purposes:
  // - Use first indexed LVN for user A
  // - Use second indexed LVN for user B
  let conversation = {
    userA: {
      realNumber: userANumber,
      virtualNumber: this.provisionedNumbers[0]
    },
    userB: {
      realNumber: userBNumber,
      virtualNumber: this.provisionedNumbers[1]
    }
  };

  this.conversations.push(conversation);

  return conversation;
};

Senden Sie eine Bestätigungs-SMS

Wenn in einem privaten Kommunikationssystem ein Nutzer einen anderen kontaktiert, ruft der Anrufer eine virtuelle Nummer von seinem Telefon aus an.

Senden Sie eine SMS, um jedem Gesprächsteilnehmer die virtuelle Nummer mitzuteilen, die er anrufen soll:

/**
 * Send an SMS to each conversation participant so they know each other's
 * virtual number and can call either other via the proxy.
 */
VoiceProxy.prototype.sendSMS = function(conversation) {
  // Send UserA conversation information
  // From the UserB virtual number
  // To the UserA real number
  this.nexmo.message.sendSms(conversation.userB.virtualNumber.msisdn,
                             conversation.userA.realNumber.msisdn,
                             'Call this number to talk to UserB');

  // Send UserB conversation information
  // From the UserA virtual number
  // To the UserB real number
  this.nexmo.message.sendSms(conversation.userA.virtualNumber.msisdn,
                             conversation.userB.realNumber.msisdn,
                             'Call this number to talk to UserB');

  return conversation;
};

Die Benutzer können sich nicht gegenseitig SMS schicken. Um diese Funktion zu aktivieren, müssen Sie Folgendes einrichten Private SMS-Kommunikation.

In diesem Anwendungsfall hat jeder Nutzer die virtuelle Nummer in einer SMS erhalten. In anderen Systemen könnte dies über E-Mail, In-App-Benachrichtigungen oder eine vordefinierte Nummer erfolgen.

Eingehende Anrufe bearbeiten

Wenn Vonage einen eingehenden Anruf an Ihre virtuelle Nummer empfängt, stellt es eine Anfrage an den Webhook-Endpunkt, den Sie bei der Einrichtung der eine Sprachanwendung erstellt:

UserBUserAVonageAppUserBUserAVonageAppUserA calls UserB'sVonage NumberCalls virtual numberInbound Call(from, to)

Auszug to und from aus dem eingehenden Webhook und leiten sie an die Geschäftslogik des Sprachproxys weiter:

app.get('/proxy-call', function(req, res) {
  const from = req.query.from;
  const to = req.query.to;

  const ncco = voiceProxy.getProxyNCCO(from, to);
  res.json(ncco);
});

Umkehrung der Zuordnung von realen Telefonnummern zu virtuellen Nummern

Da Sie nun die Telefonnummer des Anrufers und die virtuelle Nummer des Empfängers kennen, können Sie die eingehende virtuelle Nummer der ausgehenden realen Telefonnummer zuordnen:

UserBUserAVonageAppUserBUserAVonageAppFind the real number for UserBNumber mapping lookup

Die Rufrichtung kann wie folgt identifiziert werden:

  • Die from Zahl ist UserA reelle Zahl und die to Nummer ist UserB Vonage-Nummer
  • Die from Zahl ist eine reelle UserB-Zahl und die to Nummer ist UserA Vonage-Nummer
const fromUserAToUserB = function(from, to, conversation) {
  return (from === conversation.userA.realNumber.msisdn &&
          to === conversation.userB.virtualNumber.msisdn);
};
const fromUserBToUserA = function(from, to, conversation) {
  return (from === conversation.userB.realNumber.msisdn &&
          to === conversation.userA.virtualNumber.msisdn);
};

/**
 * Work out real number to virtual number mapping between users.
 */
VoiceProxy.prototype.getProxyRoute = function(from, to) {
  let proxyRoute = null;
  let conversation;
  for(let i = 0, l = this.conversations.length; i < l; ++i) {
    conversation = this.conversations[i];

    // Use to and from to determine the conversation
    const fromUserA = fromUserAToUserB(from, to, conversation);
    const fromUserB = fromUserBToUserA(from, to, conversation);

    if(fromUserA || fromUserB) {
      proxyRoute = {
        conversation: conversation,
        to: fromUserA? conversation.userB : conversation.userA,
        from: fromUserA? conversation.userA : conversation.userB
      };
      break;
    }
  }

  return proxyRoute;
};

Nachdem die Nummernsuche durchgeführt wurde, müssen Sie nur noch die Vollmacht für den Anruf erteilen.

Bevollmächtigung des Anrufs

Vermitteln Sie den Anruf an die Telefonnummer, mit der die virtuelle Nummer verknüpft ist. Die Website from Nummer ist immer die virtuelle Nummer, die to ist eine echte Telefonnummer.

UserBUserAVonageAppUserBUserAVonageAppProxy Inboundcall to UserB'sreal numberUserA has calledUserB. But UserAdoes not have the real numberof UserB, nor vice versa.Connect (proxy)Call

Erstellen Sie dazu eine NCCO (Nexmo Call Control Objekt). Dieser NCCO verwendet eine talk Aktion, um einen Text vorzulesen. Wenn die talk abgeschlossen ist, eine connect Aktion leitet den Anruf an eine echte Nummer weiter.

/**
 * Build the NCCO response to instruct Nexmo how to handle the inbound call.
 */
VoiceProxy.prototype.getProxyNCCO = function(from, to) {
  // Determine how the call should be routed
  const proxyRoute = this.getProxyRoute(from, to);

  if(proxyRoute === null) {
    const errorText = 'No conversation found' +
                    ' from: ' + from +
                    ' to: ' + to;
    throw new Error(errorText);
  }

  // Build the NCCO
  let ncco = [];

  const textAction = {
    action: 'talk',
    text: 'Please wait whilst we connect your call'
  };
  ncco.push(textAction);

  const connectAction = {
    action: 'connect',
    from: proxyRoute.from.virtualNumber.msisdn,
    endpoint: [{
      type: 'phone',
      number: proxyRoute.to.realNumber.msisdn
    }]
  };
  ncco.push(connectAction);

  return ncco;
};

Der NCCO wird vom Webserver an Vonage zurückgegeben.

app.get('/proxy-call', function(req, res) {
  const from = req.query.from;
  const to = req.query.to;

  const ncco = voiceProxy.getProxyNCCO(from, to);
  res.json(ncco);
});

Schlussfolgerung

Sie haben gelernt, wie man einen Voice-Proxy für die private Kommunikation einrichtet. Sie haben Telefonnummern eingerichtet und konfiguriert, Nummerneinblicke durchgeführt, reale Nummern virtuellen Nummern zugeordnet, um Anonymität zu gewährleisten, einen eingehenden Anruf bearbeitet und den Anruf an einen anderen Benutzer weitergeleitet.

Weitere Informationen