02. Apr. 2025

KI-Boost für deine App mit Semantic Kernel

Die Integration von KI in eine Applikation ist nicht immer einfach. Die Auswahl der richtigen Modelle und die Anbindung von APIs unterschiedlicher Anbieter bringen zahlreichte Hürden mit sich. Semantic Kernel bietet hier eine einfache Integration neuester KI-Modelle in C#-, Python- und Java-Applikationen.
Accso Avatar auf grauem Font

Autor:in

Jacob Heins

Ein Mann sitzt an einem Schreibtisch in einem Büro und programmiert. Hinter dem Computerbildschirm erscheint ein bläulicher Kopf, der eine KI symbolisiert.

Der erste Teil dieser zweiteiligen Reihe gibt einen Überblick darüber, welche Möglichkeiten Semantik Kernel bietet und wie mit einem geringem Aufwand KI in eine Applikation integriert werden kann. Der zweite Teil beleuchtet dann die Themen Prompting und Prompt-Templates sowie den Function-Calling-Loop. Ebenfalls wird dort erklärt, wie eine KI-Anwendung mit Filtern abgesichert und gegen Missbrauch geschützt werden kann. 

KI – Warum und Wie? 

KI findet in modernen Anwendungen immer mehr Verwendung. Sei es in Form von Chat-Bots, zur Automatisierung und Unterstützung von Businessprozessen, in der Bild- und Textverarbeitung oder in Form von Copilot-Unterstützung bei komplexen und vielfältigen Aufgaben. Bei all diesen Anwendungen geht es entweder darum, den Anwendern bestmögliche Unterstützung zu bieten oder aber komplexe Aufgaben an KI-Modelle zu delegieren und von diesen ausführen zu lassen.  

Für diese Art von KI-Unterstützung kommen in der Regel Large Language Models (LLMs) zum Einsatz. Viele der Anbieter solcher Modelle stellen APIs zur Verfügung, um mit den Modellen zu interagieren. Die APIs sind aber oft sehr komplex, die Integration erfordert viel Know-how und ist aufwendig. Sollen dann auch noch Modelle verschiedener Anbieter für einzelne Teilaufgaben verwendet werden, vergrößert sich der Aufwand umso mehr. 

An dieser Stelle kommen Tools wie Semantic Kernel ins Spiel. Sie sind nativ in die Sprache integriert und bieten eine einfache Abstraktion der meist komplexen APIs. Somit ist es möglich mit einem geringen Aufwand seine Applikation, um KI-Funktionen zu erweitern. Semantic Kernel ist ein SDK, das von Microsoft entwickelt wird, und steht für Anwendungen, die in C#, Java und Python entwickelt werden, zur Verfügung. 

 

Der Kernel 

Der Kernel arbeitet als Bindeglied zwischen der Anwendung bzw. dem Anwender, den LLMs und etwaigen Drittsysteme. Semantic Kernel bietet nicht nur eine einfache Schnittstelle zur Interaktion mit LLMs, sondern unterstützt auch den Function-Calling-Mechanismus. Dieser ermöglicht es, einem Modell über Plugins zusätzliche Funktionen zur Verfügung zu stellen, die dieses selbständig aufrufen kann. Der Kernel stellt hierbei die zentrale Komponente da, die – ähnlich zu einem Dependency Injection Container – sämtliche Services enthält, um eine Aufgabe mit Hilfe von KI zu lösen. Dadurch, dass es nur eine zentrale Komponente gibt, ist der Kernel sehr einfach zu konfigurieren und auch zu monitoren.  

slide 1 of 1

Immer wenn mit einem LLM interagiert wird, ist der Kernel involviert. Er stellt die KI-Services zur Verfügung, rendert gegebenenfalls die Prompts und tätigt die Aufrufe Richtung LLM. Sobald ein Ergebnis von diesem vorliegt, wird es vom Kernel verarbeitet, wenn nötig ein Plugin aufgerufen und schließlich eine Antwort erzeugt.  

 

KI-Services 

Semantic Kernel kommt mit einer Reihe von vorgefertigter KI-Services: 

  • Chat Completion
  • Embedding Generation
  • Text-to-Audio / Audio-to-Text
  • Text-to-Image / Image-to-Text 

Je nachdem welcher Service genutzt werden soll, gilt es, das richtige Modell auszuwählen. Dabei muss berücksichtig werden, ob das Modell die benötigte Funktionalität unterstützt, wie schnell eine Antwort erzeugt wird, wie akkurat diese ist und wie hoch die Kosten sind, die bei der Nutzung entstehen. 

Chat Completion 

Der Chat-Completion-Service kann verwendet werden, um eine Konversation mit einem KI-Agent zu führen. Mit ihm können aber auch z.B. autonome Services entwickelt werden, die Businessprozesse ausführen oder Code generieren. Dieser Service gehört zu den am meisten genutzten Funktionen, wenn LLMs zum Einsatz kommen.   

Embedding Generation 

Embeddings werden verwendet, wenn ein LLM mit zusätzlichen Informationen versorgt werden soll. Das können Business spezifische Daten sein oder aber Informationen, die zum Zeitpunkt des Trainings noch nicht existiert haben. 

Embeddings werden verwendet, wenn z.B. Semantic Search benötigt wird, oder Vorschläge, wie in einem Streaming-Service, generiert werden sollen. Hier bietet Semantic Kernel zusätzlich Konnektoren, um unterschiedliche Typen von Vector-Datenbanken anzubinden. 

Image- und Textprocessing 

Mit dem Image- und Textprocessing-Services lassen sich eine Vielzahl an Anwendungsfällen umsetzen. Möglich sind z.B. Vorlese- oder Übersetzungsfunktionen, um die Zugänglichkeit einer Applikation zu erhöhen.  

Plugins 

Semantic Kernel nutzt einen Plugin-Mechanismus um, einem LLM Funktionen zur Verfügung zu stellen. Plugins können auf unterschiedliche Arten definiert werden. Folgende Plugin Typen werden derzeit unterstützt: 

  • Native Code
  • Open API Endpoints
  • Azure Logic Apps 

Für ein Natives Plugin, werden die Methoden einer Klasse mit dem Attribut „KernelFunction“ versehen. Diese Klasse kann dem Kernel als Plugin bekannt gemacht werden. Der Beispielcode zeigt wie die Methoden einer Klasse als „KernelFunction“ markiert werden und dem Kernel das Plugin hinzugefügt wird. 

public class LightsPlugin 
{ 
  // Mock data for the lights 
  private readonly List<LightModel> _lights = 
  [ 
    new LightModel { Id = 1, Name = "Table Lamp", IsOn = false }, 
    new LightModel { Id = 2, Name = "Porch light", IsOn = false }, 
    new LightModel { Id = 3, Name = "Chandelier", IsOn = true } 
  ]; 
 
  [KernelFunction("get_lights")] 
  [Description("Gets a list of lights and their current state")] 
  public Task<List<LightModel>> GetLightsAsync() 
  { 
    return Task.FromResult(_lights); 
  } 
 
 
  [KernelFunction("change_state")] 
  [Description("Changes the state of the light.")] 
  public Task<LightModel?> ChangeStateAsync(int id, LightModel lightModel) 
  { 
    var light = _lights.FirstOrDefault(light => light.Id == id); 
 
    if (light == null) 
    { 
      return Task.FromResult<LightModel?>(null); 
    } 
 
    // Update the light with the new state 
    light.IsOn = lightModel.IsOn; 
 
    return Task.FromResult<LightModel?>(light); 
  } 
} 
 
kernel.Plugins.AddFromType<LightsPlugin>("Lights"); 

Soll aus einer OpenAPI-Definition ein Plugin erzeugt werden, muss dem Kernel ein Link zu dieser zur Verfügung zu stellen werden. Der Kernel generiert hieraus einen HTTP-Client, der dem LLM bekannt gemacht wird. Entscheidet das LLM, dass eine oder mehrere Routen der API aufgerufen werden müssen, führt der Kernel diese im Anschluss aus. Folgendes Beispiel zeigt, wie man dem Kernel eine solches Plugin hinzufügt.  

await kernel.ImportPluginFromOpenApiAsync( 
  pluginName: "lights", 
  uri: new Uri("https://example.com/v1/swagger.json"), 
  executionParameters: new OpenApiFunctionExecutionParameters() 
  { 
    // Determines whether payload parameter names are augmented with namespaces. 
    // Namespaces prevent naming conflicts by adding the parent parameter name 
    // as a prefix, separated by dots 
    EnablePayloadNamespacing = true 
  } 
); 

Azure Logic Apps werden analog zu Plugins auf Basis von OpenAPI-Definitionen eingebunden. Der Kernel benötigt einen Link, der auf die API-Definition verweist. Zusätzlich müssen in der Logic App die Metadaten für die Endpunkte freigeschaltet werden, damit einen passender HTTP-Client generiert werden kann. 

Generell ist bei Plugins zu beachten, dass die Funktionen und Argumente keine Abkürzungen oder anderweitige Uneindeutigkeiten enthalten. Diese machen es den LLMs sehr schwer, den Anwendungsbereich einer Funktion zu interpretieren. Zwar lassen sich zusätzliche Beschreibungen anfügen, diese verbrauchen aber bei jedem Request Token, was zu zusätzlichen Kosten führt. 

Sobald ein Plugin Daten an das LLM zurück liefert, die von diesem verarbeitet werden, sollte man sich Gedanken um IT-Sicherheit und Datenschutz machen. Sensible Daten sollten ggf. anonymisiert werden und nur die Daten bereitgestellt werden, die auch wirklich benötigt werden. Das ist auch aus Kostengründen zu bedenken, da alle Daten, die vom Model verarbeitet werden, zusätzliche Kosten verursachen. 

Frameworks 

Agent Framework 

Zusätzlich zu den schon genannten KI-Services bietet Semantic Kernel zwei Frameworks an. Mit dem Agent Framework ist die Möglichkeit gegeben KI-Agenten für dedizierte Aufgaben zu erstellen, die autonom oder teilautonom bearbeitet werden. Agenten können Nachrichten versenden sowie empfangen und so in einer Multiagent-Konversation kollaborativ komplexere Aufgaben lösen. Semantic Kernel kommt mit einigen vordefinierten Agenten.  

Chat Completion Agent 

Der Chat-Completion-Service liefert die Basis für eine Chat basierte Interaktion mit einem KI-Model. Die Integration in einen Agenten vereinfacht das Management der Chat-Historie und ermöglicht es, einen Chat-Service in eine Multi-Agent-Konversation zu integrieren. Das Beispiel zeigt, wie ein Chat Completion Agent erstellt werden kann, der das zuvor erstellte Plugin nutzt, um eine Lichtsteuerung zu realisieren. 

ar builder = Kernel 
  .CreateBuilder() 
  .AddAzureOpenAIChatCompletion(modelId, endpoint, apiKey); 
 
builder.Plugins.AddFromType<LightsPlugin>("lights"); 
 
Kernel kernel = builder.Build(); 
 
ChatCompletionAgent agent = new ()  
  { Name = "LightAgent",  
    Instructions = "You are an AI that is supposed to assist the user with controlling the lights and show the state of the lights. " + 
                   "You can turn on and off the lights and show the state of the all available lights." + 
                   "You are not supposed to do anything different." + 
                   "If a user asks for something different you tell him in a respectful way this and tell what you are able to do for him. " + 
                   "Do not rely on your memory always check the current state of the lights.", 
    Kernel = kernel, 
    Arguments = new KernelArguments( 
      new AzureOpenAIPromptExecutionSettings() 
      { 
       FunctionChoiceBehavior = FunctionChoiceBehavior.Auto() 
      }) 
  }; 
 
ChatHistory history = []; 
while (true) 
{ 
  Console.WriteLine(); 
  Console.Write("> "); 
  string? input = Console.ReadLine(); 
  Console.WriteLine(); 
   
   
  history.Add(new ChatMessageContent(AuthorRole.User, input)); 
 
  await foreach (ChatMessageContent response in agent.InvokeAsync(history)) 
  { 
    Console.WriteLine($"{response.Content}"); 
  } 
} 

Assistant Agents 

Semantic Kernel bietet auch Implementierungen für Assistant Agents. Diese ermöglichen es, einfach mit zusätzlichen Ressourcen zu interagieren wie z.B. Dateien. Sie bringen auch die Möglichkeit mit, Code zu generieren und auszuführen. Für Beispiele wie die Assitant Agents zu verwenden sind, empfehle ich das offizielle GitHub Repository [https://github.com/microsoft/semantic-kernel/tree/main/dotnet/samples/GettingStartedWithAgents] 

Process Framework 

Mit dem Prozess Framework lassen sich Business Prozesse modellieren. Es folgt einer eventgetriebenen Architektur und ermöglicht es so, komplexe Vorgänge abzubilden. Durch die Integration in das Semantic Kernel SDK stehen in jedem einzelnen Prozessschritt die vollständigen Möglichkeiten des Kernels und der KI-Services zur Verfügung. Somit lassen sich auf einfachste Weise Business-Prozesse und LLMs miteinander verknüpfen. 

Fazit 

Semantic Kernel bietet eine Vielzahl an Möglichkeiten, um eine Applikation mit Hilfe von KI zu unterstützen und zu erweitern. Die einfache Konfiguration und Benutzbarkeit erleichtern den Einstieg, wodurch sich schnell erste Ergebnisse erzielen lassen. Mit der Unterstützung von C# und Java ergeben sich somit vielfältige Einsatzmöglichkeiten auch für Business –Software-Systeme. Im kommenden Teil dieser Reihe werden die Themen Prompt-Templates und Function-Calling beleuchtet. Außerdem wird gezeigt, wie Filter helfen, eine KI-Anwendung „Business-Ready“ zu machen. 

Quellen