Einen KI-Chatbot in Delphi bauen: Gesprächsgedächtnis und Streaming

· Komponenten

Kurze Antwort: Ein Chatbot ist eine Chat-Vervollständigung plus Gedächtnis. sgcWebSockets liefert eine eigene TsgcAIChat-Komponente mit, die den vollständigen Nachrichtenverlauf für Sie behält, sodass jede Runde mit dem bisherigen Gespräch gesendet wird und das Modell im Kontext antworten kann. Legen Sie die Komponente ab, setzen Sie API-Schlüssel und Modell und rufen Sie dann Chat für eine Antwort oder ChatStream für einen Live-Schreibeffekt Token für Token auf. Das Gespräch zu leeren ist ein Aufruf von ClearHistory.

Wenn Sie bereits ein LLM aus Delphi aufgerufen haben, ist Ihnen wahrscheinlich etwas Frustrierendes aufgefallen: Stellen Sie eine Folgefrage, und das Modell tut so, als hätte es nie mit Ihnen gesprochen. Das ist kein Fehler, so funktioniert eine One-Shot-Vervollständigung. Daraus einen echten Gesprächsassistenten zu machen, ist der Unterschied zwischen einem Spielzeug und einem Chatbot, und es läuft auf eine Idee hinaus: Gedächtnis.

One-Shot-Vervollständigung vs. ein Chatbot

Eine LLM-API ist zustandslos. Jede Anfrage ist unabhängig, sodass das Modell nur weiß, was Sie in dieser Anfrage angegeben haben. Ein One-Shot-Aufruf sendet einen einzelnen Prompt:

// User: "What is the capital of France?"  ->  "Paris."
// User: "And its population?"             ->  "Population of what?"

Die zweite Frage scheitert, weil der Server nichts von der ersten behalten hat. Ein Chatbot behebt das, indem er bei jedem Mal den gesamten Austausch erneut sendet: die Systemnachricht, jede Benutzerrunde und jede Assistentenantwort, der Reihe nach. Das Modell liest den Verlauf, sieht, dass sich „seine" auf Paris bezieht, und antwortet korrekt. Sie brauchen dafür keine Datenbank oder einen Sitzungsserver, nur eine Nachrichtenliste, die mit dem Gespräch wächst. Die einzige echte Arbeit besteht darin, diese Liste aufzubauen und zu pflegen, und genau das erledigt die Chatbot-Komponente für Sie.

Die Komponente TsgcAIChat: Gedächtnis für Sie erledigt

Statt ein Nachrichtenarray von Hand zu verdrahten, legen Sie ein TsgcAIChat auf Ihr Formular. Es besitzt den Gesprächsverlauf intern, hängt jede Benutzernachricht und jede Assistentenantwort automatisch an und sendet den angesammelten Kontext bei jedem Aufruf. Sie setzen den Anbieter, den API-Schlüssel und ein Modell und rufen dann einfach Chat auf.

uses
  sgcAI, sgcAI_Chat;

var
  Bot: TsgcAIChat;
begin
  Bot := TsgcAIChat.Create(nil);
  Bot.Provider := aicpOpenAI;
  Bot.ChatOptions.ApiKey := 'sk-...';
  Bot.ChatOptions.Model  := 'gpt-4o-mini';
  Bot.SystemMessage := 'You are a concise assistant for Delphi developers.';

  // Each call adds to the same conversation:
  ShowMessage(Bot.Chat('What is the capital of France?'));  // "Paris."
  ShowMessage(Bot.Chat('And its population?'));             // answers about Paris
end;

Weil die Komponente sich die erste Runde merkt, funktioniert die Folgefrage einfach. Die SystemMessage legt die Persona des Assistenten fest und wird bei jeder Anfrage mitgesendet. Wenn Sie ein frisches Gespräch wünschen, rufen Sie Bot.ClearHistory auf; um das Gesagte zu inspizieren oder zu persistieren, gibt Bot.GetHistory die Nachrichtenliste zurück. Sie können das Gedächtnis auch mit MaxHistoryMessages begrenzen, damit ein langer Chat nicht unbegrenzt wächst (ältere Runden werden automatisch beschnitten).

Dieselbe Komponente spricht mit jedem Anbieter, den sgcWebSockets unterstützt. Schalten Sie Provider auf aicpAnthropic, aicpGemini, aicpDeepSeek, aicpOllama, aicpGrok oder aicpMistral um, ändern Sie den Modellnamen, und der Rest Ihres Chatbot-Codes bleibt identisch. Siehe die Seite zur ChatBot-Komponente und den Hub für KI- & LLM-Komponenten.

Eine Live-Antwort streamen

Mehrere Sekunden auf das Erscheinen einer vollständigen Antwort zu warten, fühlt sich langsam an. Echte Chatbots streamen die Antwort, sodass Wörter erscheinen, während sie erzeugt werden, der vertraute Schreibeffekt. TsgcAIChat stellt dies über ChatStream plus das Ereignis OnChatStream bereit, das für jeden Textchunk ausgelöst wird, sobald er eintrifft.

Bot.OnChatStream := BotChatStream;
Bot.ChatStream('Explain WebSockets in two sentences.');

procedure TForm1.BotChatStream(Sender: TObject; const aChunk: string;
  var Cancel: Boolean);
begin
  Memo1.Text := Memo1.Text + aChunk;  // append each token as it arrives
  // set Cancel := True to stop the response early
end;

Die Chunks werden im Hintergrund inkrementell über Server-Sent Events geliefert, aber Sie berühren die SSE-Mechanik nie. Wenn der Stream endet, wird die vollständige Assistentenantwort dem Verlauf hinzugefügt, genau wie bei einem nicht-gestreamten Aufruf, sodass die nächste Runde weiterhin den vollen Kontext hat. Der Cancel-Parameter erlaubt Ihnen, eine „Generierung stoppen"-Schaltfläche umzusetzen. Es gibt außerdem OnChatMessage für die endgültig zusammengesetzte Nachricht und OnChatError, um etwaige API-Fehler sichtbar zu machen.

Ein Sprach-Chatbot, von Anfang bis Ende

Wenn Sie möchten, dass der Assistent zuhört und spricht, umhüllt die Komponente TsgcAIOpenAIChatBot die gesamte Schleife: Sie nimmt Mikrofon-Audio auf, transkribiert es mit Whisper, sendet den Text an Chat Completions und spricht die Antwort über einen Text-to-Speech-Anbieter zurück. Stecken Sie einen Audiorekorder und eine Text-to-Speech-Engine ein, setzen Sie den Schlüssel und rufen Sie Start auf.

uses
  sgcAI, sgcAI_OpenAI_Audio_ChatBot,
  sgcAI_AudioRecorder_MCI, sgcAI_TextToSpeech_System;

var
  ChatBot: TsgcAIOpenAIChatBot;
begin
  ChatBot := TsgcAIOpenAIChatBot.Create(nil);
  ChatBot.OpenAIOptions.ApiKey := 'sk-...';
  ChatBot.AudioRecorder := TsgcAudioRecorderMCI.Create(nil);
  ChatBot.TextToSpeech  := TsgcTextToSpeechSystem.Create(nil);
  ChatBot.OnChatCompletion := ChatBotChatCompletion;

  ChatBot.Start;                          // begin listening; Stop ends it
  ChatBot.ChatAsUser('Tell me a joke');   // or push a turn programmatically
end;

Das Ereignis OnChatCompletion gibt Ihnen die Rolle und den Inhalt jeder Antwort, und OnTranscription erlaubt es Ihnen, das Gehörte zu inspizieren oder zu bearbeiten, bevor es gesendet wird. Es ist dieselbe Gesprächsidee wie bei TsgcAIChat, nur mit Audio an beiden Enden.

Lieber die Liste selbst verwalten?

Sie müssen die Chatbot-Komponente nicht verwenden. Wenn Sie volle Kontrolle wollen, halten Sie Ihre eigene Liste von { role, content }-Nachrichten und senden Sie sie bei jedem Aufruf mit TsgcHTTP_API_OpenAI._CreateChatCompletion. Hängen Sie die Benutzernachricht an, senden Sie das Array und hängen Sie dann die Antwort des Assistenten wieder in dieselbe Liste, bevor die nächste Runde beginnt. Das ist genau die Buchführung, die TsgcAIChat intern erledigt, weshalb die meisten die Komponente das übernehmen lassen. Die untergeordnete API wird im Tutorial OpenAI-API in Delphi und auf der Seite zur OpenAI-Komponente behandelt.

Erste Schritte

Alles hier ist in sgcWebSockets enthalten. Holen Sie sich die kostenlose Testversion, legen Sie ein TsgcAIChat auf ein Formular, setzen Sie API-Schlüssel und Modell, und Sie haben einen kontextbewussten Chatbot, der Folgefragen in wenigen Zeilen beantwortet. Fügen Sie ChatStream für den Live-Schreibeffekt hinzu, wenn Sie bereit sind.

Fragen, Feedback oder Hilfe beim Einbinden in Ihre App? Kontaktieren Sie uns — Sie erhalten eine Antwort von den Leuten, die den Code geschrieben haben.

Verwandte Themen