Sdílet prostřednictvím


Plánování

Jakmile budete mít více modulů plug-in, budete potřebovat způsob, jak ho agent umělé inteligence používat společně k řešení potřeby uživatele. Tady přichází plánování.

V rané fázi představilo sémantické jádro koncept plánovačů, které použily výzvy k vyžádání umělé inteligence, aby zvolilo, které funkce se mají vyvolat. Vzhledem k tomu, že bylo zavedeno sémantické jádro, OpenAI však zavedl nativní způsob, jak model vyvolat nebo "volat" funkci: volání funkce. Jiné modely umělé inteligence, jako je Gemini, Claude a Mistral, od té doby přijaly volání funkcí jako základní funkce, což z něj dělá podporovanou funkci napříč modely.

Z těchto pokroků se sémantické jádro vyvinulo tak, aby jako primární způsob plánování a provádění úkolů používalo volání funkcí.

Důležité

Volání funkcí je dostupné jenom v modelech OpenAI, které jsou 0613 nebo novější. Pokud používáte starší model (např. 0314), vrátí tato funkce chybu. K využití této funkce doporučujeme používat nejnovější modely OpenAI.

Jak volání funkce vytvoří "plán"?

V nejjednodušším volání funkce je jen způsob, jak AI vyvolat funkci se správnými parametry. Představte si například, že uživatel chce zapnout žárovku. Za předpokladu, že AI má správný plugin, může spustit funkci pro zapnutí světla.

Role Zpráva
🔵 uživatel Zapněte světlo č. 1.
🔴 Assistant (volání funkce) Lights.change_state(1, { "isOn": true })
🟢 nástroj { "id": 1, "name": "Table Lamp", "isOn": true, "brightness": 100, "hex": "FF0000" }
🔴 asistent Lampa je teď zapnutá.

Ale co když uživatel nezná ID světla? Nebo co když chce uživatel zapnout všechna světla? Tady přichází plánování. Dnešní modely LLM jsou schopné iterativním voláním funkcí vyřešit potřeby uživatele. Toho dosáhnete tak, že vytvoříte smyčku zpětné vazby, ve které může AI volat funkci, zkontrolovat výsledek a pak rozhodnout, co dělat dál.

Uživatel může například požádat AI, aby "přepnul" žárovku. AI by nejprve potřebovala zkontrolovat stav žárovky, než se rozhodnete, jestli ji chcete zapnout nebo vypnout.

Role Zpráva
🔵 uživatel Přepněte všechna světla.
🔴 Assistant (volání funkce) Lights.get_lights()
🟢 nástroj { "lights": [ { "id": 1, "name": "Table Lamp", "isOn": true, "brightness": 100, "hex": "FF0000" }, { "id": 2, "name": "Ceiling Light", "isOn": false, "brightness": 0, "hex": "FFFFFF" } ] }
🔴 Assistant (volání funkce) Lights.change_state(1, { "isOn": false }) Lights.change_state(2, { "isOn": true })
🟢 nástroj { "id": 1, "name": "Table Lamp", "isOn": false, "brightness": 0, "hex": "FFFFFF" }
🟢 nástroj { "id": 2, "name": "Ceiling Light", "isOn": true, "brightness": 100, "hex": "FF0000" }
🔴 asistent Světla byla přepnuta.

Poznámka:

V tomto příkladu jste také viděli paralelní volání funkcí. V tomto případě může AI současně volat více funkcí. Jedná se o výkonnou funkci, která pomáhá AI rychleji řešit složité úlohy. Byla přidána do modelů OpenAI v roce 1106.

Smyčka automatického plánování

Podpora volání funkcí bez sémantického jádra je poměrně složitá. Museli byste napsat smyčku, která by provedla následující:

  1. Vytvoření schémat JSON pro každou z vašich funkcí
  2. Poskytněte LLM předchozí historii chatu a schémata funkcí
  3. Parsujte odpověď LLM a zjistěte, jestli chce odpovědět zprávou nebo volat funkci.
  4. Pokud LLM chce volat funkci, budete muset analyzovat název a parametry funkce z odpovědi LLM.
  5. Vyvolání funkce se správnými parametry
  6. Vrátí výsledky funkce, aby LLM mohl určit, co by měl udělat dál.
  7. Opakujte kroky 2 až 6, dokud se LLM nerozhodne, že dokončil úkol nebo potřebuje pomoc od uživatele.

V Semantic Kernel vám usnadňujeme volání funkcí tím, že tuto smyčku automatizujeme za vás. Díky tomu se můžete zaměřit na vytváření modulů plug-in potřebných k řešení potřeb uživatele.

Poznámka:

Pochopení toho, jak funguje smyčka volání funkcí, je nezbytné pro vytváření výkonných a spolehlivých AI agentů. Podrobné informace o tom, jak smyčka funguje, najdete v článku volání funkce .

Použití automatického volání funkce

Pokud chcete použít automatické volání funkce v sémantickém jádru, musíte udělat toto:

  1. Zaregistrujte plug-in v jádru
  2. Vytvořte objekt nastavení pro provádění, který dává umělé inteligenci pokyny, aby automaticky volala funkce
  3. Vyvolání služby pro dokončování chatu s historií chatu a jádrem

Návod

Následující ukázka kódu používá kód LightsPlugin, jak je zde definováno.

using System.ComponentModel;
using Microsoft.SemanticKernel;
using Microsoft.SemanticKernel.ChatCompletion;
using Microsoft.SemanticKernel.Connectors.OpenAI;

// 1. Create the kernel with the Lights plugin
var builder = Kernel.CreateBuilder().AddAzureOpenAIChatCompletion(modelId, endpoint, apiKey);
builder.Plugins.AddFromType<LightsPlugin>("Lights");
Kernel kernel = builder.Build();

var chatCompletionService = kernel.GetRequiredService<IChatCompletionService>();

// 2. Enable automatic function calling
OpenAIPromptExecutionSettings openAIPromptExecutionSettings = new() 
{
    FunctionChoiceBehavior = FunctionChoiceBehavior.Auto()
};

var history = new ChatHistory();

string? userInput;
do {
    // Collect user input
    Console.Write("User > ");
    userInput = Console.ReadLine();

    // Add user input
    history.AddUserMessage(userInput);

    // 3. Get the response from the AI with automatic function calling
    var result = await chatCompletionService.GetChatMessageContentAsync(
        history,
        executionSettings: openAIPromptExecutionSettings,
        kernel: kernel);

    // Print the results
    Console.WriteLine("Assistant > " + result);

    // Add the message from the agent to the chat history
    history.AddMessage(result.Role, result.Content ?? string.Empty);
} while (userInput is not null)
import asyncio

from semantic_kernel import Kernel
from semantic_kernel.connectors.ai import FunctionChoiceBehavior
from semantic_kernel.connectors.ai.chat_completion_client_base import ChatCompletionClientBase
from semantic_kernel.connectors.ai.open_ai import (
    AzureChatCompletion,
    AzureChatPromptExecutionSettings,
)
from semantic_kernel.contents import ChatHistory
from semantic_kernel.functions import kernel_function

async def main():
    # 1. Create the kernel with the Lights plugin
    kernel = Kernel()
    kernel.add_service(AzureChatCompletion())
    kernel.add_plugin(
        LightsPlugin(),
        plugin_name="Lights",
    )

    chat_completion: AzureChatCompletion = kernel.get_service(type=ChatCompletionClientBase)

    # 2. Enable automatic function calling
    execution_settings = AzureChatPromptExecutionSettings()
    execution_settings.function_choice_behavior = FunctionChoiceBehavior.Auto()

    # Create a history of the conversation
    history = ChatHistory()

    userInput = None
    while True:
        # Collect user input
        userInput = input("User > ")

        # Terminate the loop if the user says "exit"
        if userInput == "exit":
            break

        # Add user input to the history
        history.add_user_message(userInput)

        # 3. Get the response from the AI with automatic function calling
        result = await chat_completion.get_chat_message_content(
            chat_history=history,
            settings=execution_settings,
            kernel=kernel,
        )

        # Print the results
        print("Assistant > " + str(result))

        # Add the message from the agent to the chat history
        history.add_message(result)

# Run the main function
if __name__ == "__main__":
    asyncio.run(main())

    OpenAIAsyncClient client = new OpenAIClientBuilder()
        .credential(new AzureKeyCredential(AZURE_CLIENT_KEY))
        .endpoint(CLIENT_ENDPOINT)
        .buildAsyncClient();

    // Import the LightsPlugin
    KernelPlugin lightPlugin = KernelPluginFactory.createFromObject(new LightsPlugin(),
        "LightsPlugin");

    // Create your AI service client
    ChatCompletionService chatCompletionService = OpenAIChatCompletion.builder()
        .withModelId(MODEL_ID)
        .withOpenAIAsyncClient(client)
        .build();

    // Create a kernel with Azure OpenAI chat completion and plugin
    Kernel kernel = Kernel.builder()
        .withAIService(ChatCompletionService.class, chatCompletionService)
        .withPlugin(lightPlugin)
        .build();

    // Add a converter to the kernel to show it how to serialise LightModel objects into a prompt
    ContextVariableTypes
        .addGlobalConverter(
            ContextVariableTypeConverter.builder(LightModel.class)
                .toPromptString(new Gson()::toJson)
                .build());

    // Enable planning
    InvocationContext invocationContext = new InvocationContext.Builder()
        .withReturnMode(InvocationReturnMode.LAST_MESSAGE_ONLY)
        .withToolCallBehavior(ToolCallBehavior.allowAllKernelFunctions(true))
        .build();

    // Create a history to store the conversation
    ChatHistory history = new ChatHistory();

    // Initiate a back-and-forth chat
    Scanner scanner = new Scanner(System.in);
    String userInput;
    do {
      // Collect user input
      System.out.print("User > ");

      userInput = scanner.nextLine();
      // Add user input
      history.addUserMessage(userInput);

      // Prompt AI for response to users input
      List<ChatMessageContent<?>> results = chatCompletionService
          .getChatMessageContentsAsync(history, kernel, invocationContext)
          .block();

      for (ChatMessageContent<?> result : results) {
        // Print the results
        if (result.getAuthorRole() == AuthorRole.ASSISTANT && result.getContent() != null) {
          System.out.println("Assistant > " + result);
        }
        // Add the message from the agent to the chat history
        history.addMessage(result);
      }
    } while (userInput != null && !userInput.isEmpty());

Když použijete automatické volání funkce, všechny kroky ve smyčce automatického plánování se za vás zpracují a přidají do objektu ChatHistory . Po dokončení volací smyčky funkce můžete zkontrolovat ChatHistory objekt a zobrazit všechna volání funkce a výsledky, které poskytlo sémantické jádro.

Co se stalo s plánovači Stepwise a Handlebars?

Plánovače Stepwise a Handlebars byly zastaralé a odstraněny z balíčku Semantic Kernel. Tyto plánovače už nejsou podporované v Pythonu, .NET nebo Javě.

Doporučujeme používat volání funkcí, což je pro většinu scénářů výkonnější a jednodušší.

Pokud chcete aktualizovat existující řešení, postupujte podle pokynů v průvodci migrací v Rámci plánovače Stepwise Planner.

Návod

U nových agentů AI místo zastaralých plánovačů používejte volání funkcí. Nabízí lepší flexibilitu, integrovanou podporu nástrojů a jednodušší vývojové prostředí.

Další kroky

Teď, když rozumíte tomu, jak plannery fungují v sémantickém jádru, můžete se dozvědět více o tom, jak ovlivňují agenta AI, aby mohli nejlépe plánovat a spouštět úkoly jménem uživatelů.