Erstellen eines Chatbots mit PubNub und ChatGPT / OpenAI

pubnubdevrel

PubNub Developer Relations

Posted on March 11, 2024

Erstellen eines Chatbots mit PubNub und ChatGPT / OpenAI

Wenn man bis vor kurzem einen Chatbot entwickeln wollte, musste man die "natürliche Sprachverarbeitung" (NLP) nutzen, um die Fragen des Benutzers zu verstehen und zu interpretieren, und dann versuchen, diese Anfrage mit Hilfe einer Backend-Logik zu erfüllen, die möglicherweise in einen proprietären Dienst integriert war. Lösungen wie Dialogflow oder das Bot-Framework von Microsoft bieten Konversations-KI auf der Grundlage von maschinellem Lernen und sind bei Entwicklern, die Chatbots erstellen, traditionell beliebt.

OpenAI und ChatGPT von OpenAI machen es einfacher denn je, einen KI-Chatbot zu erstellen, der auf künstlicher Intelligenz basiert. Da das große Sprachmodell (LLM), das OpenAI antreibt, auf einem öffentlichen Datensatz basiert, können Sie die Benutzererfahrung Ihrer App ganz einfach verbessern, indem Sie alle Informationen bereitstellen, von denen Sie erwarten, dass sie in einer öffentlichen Wissensdatenbank vorhanden sind.

PubNub ermöglicht Echtzeit-Erlebnisse für ein breites Spektrum von Branchen und Anwendungsfällen, darunter Kundensupport und In-App-ChatAll diese Echtzeit-Erlebnisse werden durch Daten angetrieben, entweder durch vom Benutzer lesbare Nachrichten oder durch Metadaten über Ihre Lösung - wäre es nicht großartig, diese vorhandenen Daten zu nutzen, um einen Chatbot zu betreiben?

Einige Anwendungsbeispiele aus der Praxis:

  • Antworten auf häufig gestellte Fragen des Kundensupports bereitstellen

  • Anreicherung Ihrer vorhandenen Daten mit zusätzlichen Inhalten, z. B. mit Vorschlägen für Restaurants in der Nähe eines angegebenen Standorts

  • Erstellen Sie Zusammenfassungen von Unterhaltungen auf der Grundlage des Nachrichtenverlaufs.

Wir veröffentlichten einen Artikel zu diesem Thema veröffentlicht, und obwohl dieser ältere Artikel immer noch richtig ist, entwickelt sich die Branche sehr schnell, und ein paar Monate sind eine lange Zeit.

In diesem Artikel geht es darum, wie man einen Chatbot auf Basis von OpenAI erstellt, ähnlich dem, den Sie in unserem PubNub Schaufenster Anwendung läuft, wie unten gezeigt.

The showcase's AI model has been primed to mention PubNub, where appropriate

High-Level Architektur

Um einen Chatbot wie ChatGPT zu erstellen, müssen Sie die OpenAI-Chat-API verwenden und sich für ein Konto anmelden, um einen API-Schlüssel zu erstellen. Die OpenAI-API ist als REST-Endpunkt zugänglich, so dass sie von so ziemlich jeder Programmiersprache aus aufgerufen werden kann, obwohl die meisten der bereitgestellten Beispiele in Python geschrieben sind.

Der beste Weg, Daten aus PubNub zu extrahieren, um eine Konversation mit dem Chatbot zu beginnen oder fortzusetzen, ist die Verwendung von Funktionen. Funktionen bieten einen serverlosen JavaScript-Container, der in Node.JS läuft und es Ihnen ermöglicht, Geschäftslogik auszuführen, sobald ein Ereignis im PubNub-Netzwerk eintritt, wie z. B. der Empfang einer Chat-Nachricht. PubNub-Funktionen werden häufig für Echtzeit-Sprachübersetzung, Profanity-Filterung oder zum Aufrufen eines Drittanbieterdienstes wie OpenAI verwendet.

Dieses Beispiel wird wie folgt funktionieren:

  • Die bestehende Chat-Anwendung nutzt PubNub, um Nachrichten in Echtzeit zu senden und zu empfangen.

  • Eine PubNub-Funktion wartet auf Nachrichten, die an einen bestimmten Kanal gesendet werden.

  • Eine einzelne Nachricht allein bietet keinen Kontext für ChatGPT, daher wird auch ein Teil des Gesprächsverlaufs zwischengespeichert, um einen fortlaufenden Dialog zu ermöglichen.

  • Die PubNub-Funktion ruft die OpenAI-API auf und holt die Antwort ab

  • Die Antwort wird auf dem PubNub-Kanal veröffentlicht, der mit Ihrem eigenen Chatbot verbunden ist.

Sie können dies in dem folgenden Sequenzdiagramm sehen:

Example sequence diagram for implementing a ChatGPT-like chatbot with PubNub and OpenAI

  1. Der Benutzer tippt eine Nachricht in Ihrer Chat-App. Mit über 50 SDKs kann PubNub die meisten Anwendungen unterstützen, und die Nachricht wird in dem Kanal veröffentlicht, der den Chatbot im PubNub-Netzwerk repräsentiert.

  2. Eine PubNub-Funktion wird so konfiguriert, dass sie nach einem Veröffentlichungsereignis auf einem Kanal aufgerufen wird. Wenn eine Nachricht empfangen wird, wird der Kanalverlauf abgerufen, um einen Kontext für die Konversation zu liefern, und dieser Verlauf wird zusammen mit den Benutzereingaben und zusätzlichem Kontext über die Chat Completion API an ChatGPT übermittelt.

  3. Die ChatGPT-API generiert Antworten, die an den Gesprächsverlauf angepasst sind

  4. Innerhalb der PubNub-Funktion wird eine Antwort von ChatGPT empfangen, die geparst und wieder im PubNub-Netzwerk veröffentlicht wird.

  5. Die Anwendung, die zuvor den Empfang von Nachrichten von PubNub abonniert hat, wird die Antwort des Chatbots anzeigen.

Konfigurieren Ihrer PubNub-Funktion

Erstellen Sie Ihre PubNub-Funktion wie folgt:

Voraussetzungen: Wenn Sie neu bei PubNub sind, folgen Sie unserer Dokumentation, um Ihr Konto einzurichten oder besuchen Sie unsere Tour, um zu verstehen, worum es bei PubNub geht.

  1. Navigieren Sie zum Admin-Dashboard

  2. Wählen Sie Funktionen aus dem linken Menü und wählen Sie das entsprechende Keyset, in dem Sie die Funktion erstellen möchten.

  3. Wählen Sie + Neues Modul erstellen.

  4. Geben Sie einen Modulnamen und eine Modulbeschreibung ein, wählen Sie ein Keyset aus und klicken Sie dann auf Erstellen

  5. Wählen Sie das soeben erstellte Modul aus

  6. Wählen Sie + Neue Funktion erstellen

  7. Geben Sie der Funktion einen Namen und wählen Sie den Ereignistyp After Publish oder Fire. Diese Funktion wird aufgerufen, NACHDEM eine Nachricht an PubNub übermittelt wurde. Funktionen können synchron oder asynchron sein. In diesem Fall erfassen wir nur eine Kopie der Nachricht, um sie an OpenAI zu senden. Weitere Einzelheiten zu den verschiedenen Arten von Funktionen finden Sie in unserer Dokumentation

  8. Der Funktionskanal sollte mit dem Kanal übereinstimmen, in dem Sie Nachrichten veröffentlichen, die Sie an OpenAI senden wollen. Sie können hier einen Platzhalter verwenden, so dass z.B. chatgpt. * mit jedem Kanal übereinstimmt, der mit chatgpt beginnt. Da wir mit dieser Funktion mit mehreren Personen gleichzeitig sprechen wollen, ermöglicht uns ein Platzhalter zu unterscheiden, welcher Benutzer an der aktiven Konversation beteiligt ist, so dass wir auf dem entsprechenden Kanal antworten können.Wenn mehrere Personen gleichzeitig mit OpenAI sprechen, kümmert sich PubNub um die Erstellung mehrerer Instanzen Ihrer Funktion. chatgpt.dave und chatgpt.simon sind zum Beispiel zwei verschiedene Kanäle, aber beide rufen die PubNub-Funktion auf, die auf chatgpt.* hört. Wie PubNub mit Channel-Wildcards umgeht, wird in unserer Dokumentation genauer erklärt.

  9. Wählen Sie My Secrets und erstellen Sie ein neues Geheimnis für den OpenAI-API-Schlüssel; der folgende Code setzt voraus, dass dieses Geheimnis OPENAI_API_KEY heißt.

Hier ist ein Beispiel für eine PubNub-Funktion, die OpenAI / ChatGPT aufruft

const pubnub = require('pubnub');
const xhr = require('xhr');
const vault = require('vault');

// Process all messages posted to the private ChatGPT channel
// This will be unique for each user, so chat is 1:1 with ChatGPT
export default request => {
  const inboundChannel = request.channels[0];
  if (request.message.content.type == "text" && request.message.sender != "OpenAI")
  {
    //  user’s query
    let naturalCommand = request.message.content.text;
   // Always provide OpenAI with some context of how you want questions answered
    let historicalMsgs = 
      [{"role": "system", "content": "You are a helpful assistant, expert in PubNub"}];
    return getOpenaiApiKey().then(apikey => {
      // Read the last messages from the conversation to provide conversation context
      return pubnub.history({
        channel: inboundChannel,
        count: 10
        }).then((response) => {
          response['messages'].forEach((value, index) => {
            // The message role will vary depending on whether it was sent or received 
            if (value.entry.sender && value.entry.sender == "OpenAI")
              historicalMsgs.push({"role": "assistant", 
                "content": value.entry.content.text})
            else
              historicalMsgs.push({"role": "user", 
                "content": value.entry.content.text})
          });

          // Depending on timing, last published message may or may not yet be stored
          if (historicalMsgs[historicalMsgs.length - 1].content != naturalCommand)
          {
            historicalMsgs.push({"role": "user", 
              "content": naturalCommand});
          }
          return openAI(naturalCommand, historicalMsgs).then(aiResponse => {
            // Respond back by publishing the message to PubNub
            pubnub.publish({
              channel: inboundChannel,  //  In the showcase, this is unique per user
              message: {
                content: {
                  type: "text",
                  text: aiResponse
                },
                sender: "OpenAI",
              },
            });
            return request.ok();
          });
        })
      });
    }
    return request.ok();
  };


  // Get API Key for OpenAI
  // Key is populated via Vault Secret Manager  
  let OPENAI_API_KEY = null;
  function getOpenaiApiKey() {
    // Use cached key
    if (OPENAI_API_KEY) {
      return new Promise(resolve => resolve(OPENAI_API_KEY));
    }
    // Fetch key from vault
    return vault.get("OPENAI_API_KEY").then(apikey => {
      OPENAI_API_KEY = apikey;
      return new Promise(resolve => resolve(OPENAI_API_KEY));
    });  
  }

  // API Call to OpenAI asking the AI to run functions if it thinks it needs to
  function openAI(naturalCommand, msgs) {
    // Generate Function Instructions for the AI
    const url = 'https://api.openai.com/v1/chat/completions';
    const http_options = {
      'method': 'POST',
      'headers': {
        "Content-Type": "application/json",
        "Authorization": `Bearer ${OPENAI_API_KEY}`,
      },
    'body': JSON.stringify({
      "model": "gpt-3.5-turbo",
      "messages": msgs,
      "max_tokens": 300
    }),
    timeout: 9500, // PubNub functions timeout limit can be raised if needed
    retries: 0
  };

  return xhr.fetch(url, http_options).then((resp) => {
    const body = JSON.parse(resp.body);
    return body.choices[0].message.content;
  })
  .catch((err) => {
    console.log(err);
    return "Timed out. Please try again or ask a simpler question";
  });
}
Enter fullscreen mode Exit fullscreen mode

Praktische Überlegungen beim Aufrufen der OpenAI API

Eigenschaften der Chat Completion API

Der in diesem Artikel vorgestellte Code verwendet die OpenAI Chat Completion API, aber sie ist besser konfigurierbar als oben gezeigt.

Wenn Sie stream als true angeben, wird die OpenAI-Antwort als Datenstrom über vom Server gesendete Ereignisse zurückgegeben. In der Praxis kann dies die wahrgenommene Latenz verringern, da der Benutzer eine unmittelbarere Antwort sieht, ähnlich wie die ChatGPT-Webschnittstelle funktioniert.

model ermöglicht die Angabe des Sprachmodells, das zur Generierung der Antwort verwendet wird. Die API wird von einer Familie von Modellen mit unterschiedlichen Fähigkeiten und Preispunkten angetrieben, wobei die Modelle regelmäßig aktualisiert und neue Modelle hinzugefügt werden.

max_tokens schränkt die Anzahl der Token ein, die die API zur Generierung der Ausgabe verwendet. Im Allgemeinen gilt: Je geringer die Anzahl der Token, desto weniger komplex ist die Ausgabe und desto weniger Kontext wird verfolgt, aber die Antworten werden schneller geliefert.

Das Beispiel in diesem Artikel verwendet system, um einige Anweisungen an OpenAPI zu übermitteln, user für Nachrichten, die vom Endbenutzer gesendet werden, und assistant für Antworten, die zuvor von OpenAI geliefert wurden.

Das Modell kann durch die Angabe von temperature / top_p, frequency_penality und presence_penalty weiter angepasst werden. Weitere Informationen hierzu finden Sie in der OpenAPI-Dokumentation.

Die API erlaubt es Ihnen auch, benutzerdefinierte Funktionen zu definieren und zu spezifizieren, die die Fähigkeiten des Modells erweitern, was aber außerhalb des Rahmens dieses Blogs liegt. Wenn Sie mehr darüber erfahren möchten, haben wir einen separaten Beitrag, der zeigt, wie Sie ChatGPT erlauben können, in Ihrem Namen auf PubNub zu veröffentlichen, was es Ihnen ermöglicht, etwas zu sagen wie: "Sende eine Nachricht an den Hauptkanal, die besagt, dass ich in 5 Minuten bereit bin."Sie können ChatGPT auch erlauben, Ihre eigene Geschäfts-API aufzurufen, um z.B. Produktinformationen oder Informationen zum Bestellstatus direkt an den Kunden zu übermitteln.

Kontext für den Chat bereitstellen

HTTP-Anfragen sind zustandslos. Um also eine lang andauernde Konversation mit OpenAI zu führen, muss es eine Möglichkeit geben, der API einen gewissen Kontext zu geben, die bisherige Konversation zu beschreiben und Metadaten zu dieser Konversation bereitzustellen.

Die Chat Completion API akzeptiert ein Array von Nachrichten, die es dem KI-Modell ermöglichen, aus einer ansonsten mehrdeutigen Frage eine Bedeutung abzuleiten. Betrachten Sie dieses Beispiel:

> [Benutzer] Wie groß ist die Erde?

> [OpenAI] Die Erde hat einen Durchmesser von etwa 12.742 Kilometern

> [Benutzer] Ich meinte, wie schwer ist sie?

> [OpenAI] Die Erde hat eine Masse von etwa 5,97x10^24 kg

Um die Frage "Wie schwer ist sie?" zu beantworten, musste die KI natürlich wissen, was "sie" ist.

Wenn Sie Ihren Chatbot auf PubNub-Basis aufbauen, müssen Sie entscheiden, wie viel Gesprächskontext zur Verfügung gestellt werden soll. Wenn Sie PubNub-Funktionen verwenden, haben Sie Zugriff auf den gesamten Nachrichtenverlauf des Channels, und das Beispiel liefert die letzten 10 Nachrichten der Unterhaltung. Sie könnten natürlich viel mehr zur Verfügung stellen, je nach Ihren Bedürfnissen:

// Read in the last messages from the conversation to provide some context to Chat GPT
pubnub.history({
  channel: inboundChannel,
  count: 10
}).then((response) => {
  response['messages'].forEach((value, index) => {
    if (value.entry.sender && value.entry.sender == "ChatGPT")
      historicalMsgs.push({"role": "assistant", "content": value.entry.content.text})
    else
      historicalMsgs.push({"role": "user", "content": value.entry.content.text})
});
Enter fullscreen mode Exit fullscreen mode

Da der Chat-Kontext bereits in PubNub vorhanden ist, ist es trivial, diesen Kontext OpenAI zur Verfügung zu stellen. Beachten Sie, dass die Rolle unterschiedlich ist, je nachdem ob die Nachricht an OpenAI gesendet oder von OpenAI empfangen wurde.

Langlaufende Abfragen

Bei der Entwicklung Ihres ChatGPT-ähnlichen Chatbots und der Konfiguration der Parameter, die von Ihrem KI-Modell verwendet werden, sollten Sie die erwartete Antwortzeit auf Ihre Anfrage berücksichtigen. Standardmäßig bieten PubNub-Funktionen eine maximale Laufzeit von 10 Sekunden pro Aufruf, die durch Kontaktaufnahme mit dem Support erhöht werden kann. Im Allgemeinen wird ein Chatbot, der zu lange braucht, um auf die Frage eines Benutzers zu antworten, vom Benutzer negativ wahrgenommen, daher ist es eine gute Praxis, die Parameter Ihres Modells zu wählen, um ein Gleichgewicht zwischen Reaktionsfähigkeit und Fähigkeiten zu erreichen, wie bereits erwähnt.

Wenn Sie OpenAI in Ihre PubNub-Lösung integrieren und erwarten, dass die Dauer der Antwort die Standardlaufzeit der Funktion überschreitet, setzen Sie sich bitte mit uns in Verbindung, damit wir Ihnen Empfehlungen und Ratschläge geben können.

Zusammenfassung

Mit einer Kombination aus PubNub und OpenAI / ChatGPT ist es möglich, schnell sehr leistungsfähige Echtzeitlösungen zu erstellen, um KI und Chat zu jedem Online-Erlebnis hinzuzufügen.

Wenn Sie bereit sind, loszulegen, besuchen Sie unser Admin-Dashboard, um sich für ein kostenloses Set von PubNub-Schlüsseln anzumelden. Wir haben eine Reihe von Tutorials und Demos, die jede Branche abdecken, oder schauen Sie sich unseren PubNub-Showcase (auch auf Github verfügbar) an, um einen Beispiel-Chatbot zu sehen, der von OpenAI betrieben wird.

Inhalt

High-Level-ArchitekturKonfigurationIhrer PubNub-FunktionErstellen SieIhre PubNub-Funktion wie folgt:Hier ist ein Beispiel für eine PubNub-Funktion, die OpenAI / ChatGPTP aufruftPraktischeÜberlegungen beim Aufrufen der OpenAI APIChatCompletion API PropertiesBereitstellung vonKontext für ChatLanglaufendeAbfragenZusammenfassung

Wie kann PubNub Ihnen helfen?

Dieser Artikel wurde ursprünglich auf PubNub.com veröffentlicht.

Unsere Plattform unterstützt Entwickler bei der Erstellung, Bereitstellung und Verwaltung von Echtzeit-Interaktivität für Webanwendungen, mobile Anwendungen und IoT-Geräte.

Die Grundlage unserer Plattform ist das größte und am besten skalierbare Echtzeit-Edge-Messaging-Netzwerk der Branche. Mit über 15 Points-of-Presence weltweit, die 800 Millionen monatlich aktive Nutzer unterstützen, und einer Zuverlässigkeit von 99,999 % müssen Sie sich keine Sorgen über Ausfälle, Gleichzeitigkeitsgrenzen oder Latenzprobleme aufgrund von Verkehrsspitzen machen.

PubNub erleben

Sehen Sie sich die Live Tour an, um in weniger als 5 Minuten die grundlegenden Konzepte hinter jeder PubNub-gestützten App zu verstehen

Einrichten

Melden Sie sich für einen PubNub-Account an und erhalten Sie sofort kostenlosen Zugang zu den PubNub-Schlüsseln

Beginnen Sie

Mit den PubNub-Dokumenten können Sie sofort loslegen, unabhängig von Ihrem Anwendungsfall oder SDK

💖 💪 🙅 🚩
pubnubdevrel
PubNub Developer Relations

Posted on March 11, 2024

Join Our Newsletter. No Spam, Only the good stuff.

Sign up to receive the latest update from our blog.

Related