在本快速入门中,你将了解如何使用 OpenAI 或 Azure OpenAI SDK 库创建最少的 AI 助手。 AI 助手提供代理功能,帮助用户使用 AI 工具和模型完成任务。 在前面的部分中,你将了解以下内容:
- AI 助手的核心组件和概念
- 如何使用 Azure OpenAI SDK 创建助手
- 如何增强和自定义助手的功能
先决条件
- 安装 .NET 8.0 或更高版本
- Visual Studio Code (可选)
- Visual Studio(可选)
- OpenAI 模型的访问密钥
- 安装 .NET 8.0 或更高版本
- Visual Studio Code (可选)
- Visual Studio(可选)
- 通过 Azure 标识或访问密钥访问 Azure OpenAI 实例
AI 助手的核心组件
AI 助手是围绕与用户的对话线程构建的。 用户向会话线程上的助手发送提示,该提示指示助手使用其可用的工具完成任务。 助手可以处理和分析数据、做出决策以及与用户或其他系统交互以实现特定目标。 大多数助手包括以下组件:
组件 | 说明 |
---|---|
助手 | 使用 Azure OpenAI 模型、管理聊天线程以及利用已配置工具的核心 AI 客户端和逻辑。 |
线程 | 助理和用户之间的对话会话。 线程存储消息并自动处理截断,以便将内容放入模型的上下文中。 |
消息 | 由助理或用户创建的消息。 消息可以包括文本、图像和其他文件。 消息作为列表存储在线程上。 |
运行 | 激活助手以根据线程的内容开始运行。 助手使用其配置和线程的消息通过调用模型和工具来执行任务。 作为运行的一部分,助手会将消息追加到线程。 |
运行步骤 | 助手在运行期间所采取的步骤的详细列表。 助手可以在运行期间调用工具或创建消息。 通过检查运行步骤,可以了解助手如何获取其最终结果。 |
还可以将助手配置为并行使用多个工具来完成任务,包括:
- 代码解释器工具:在沙盒执行环境中编写和运行代码。
- 调用的函数:运行在代码中定义的本地自定义函数。
- 文件搜索功能:使用模型外部的知识来增强助手能力。
通过了解这些核心组件及其交互方式,可以构建和自定义功能强大的 AI 助手以满足你的特定需求。
创建 .NET 应用
完成以下步骤以创建 .NET 控制台应用并添加使用助手所需的包:
在终端窗口中,导航到设备上的空目录,并使用
dotnet new
命令创建新应用:dotnet new console -o AIAssistant
将 OpenAI 包添加到应用:
dotnet add package OpenAI --prerelease
在所选编辑器中打开新应用,例如 Visual Studio Code。
code .
在终端窗口中,导航到设备上的空目录,并使用
dotnet new
命令创建新应用:dotnet new console -o AIAssistant
将 Azure.AI.OpenAI 包添加到应用:
dotnet add package Azure.AI.OpenAI --prerelease
在所选编辑器中打开新应用,例如 Visual Studio Code。
code .
创建 AI 助手客户端
Program.cs
打开该文件,将文件的内容替换为以下代码以创建所需的客户端:using OpenAI; using OpenAI.Assistants; using OpenAI.Files; using Azure.AI.OpenAI; using Azure.Identity; // Create the OpenAI client OpenAIClient openAIClient = new("your-apy-key"); // For Azure OpenAI, use the following client instead: AzureOpenAIClient azureAIClient = new( new Uri("your-azure-openai-endpoint"), new DefaultAzureCredential()); #pragma warning disable OPENAI001 AssistantClient assistantClient = openAIClient.GetAssistantClient(); OpenAIFileClient fileClient = openAIClient.GetOpenAIFileClient();
创建内存中示例文档并将其上传到
OpenAIFileClient
:// Create an in-memory document to upload to the file client using Stream document = BinaryData.FromBytes(""" { "description": "This document contains the sale history data for Contoso products.", "sales": [ { "month": "January", "by_product": { "113043": 15, "113045": 12, "113049": 2 } }, { "month": "February", "by_product": { "113045": 22 } }, { "month": "March", "by_product": { "113045": 16, "113055": 5 } } ] } """u8.ToArray()).ToStream(); // Upload the document to the file client OpenAIFile salesFile = fileClient.UploadFile( document, "monthly_sales.json", FileUploadPurpose.Assistants);
通过
AssistantCreationOptions
启用文件搜索和代码解释器工具功能:// Configure the assistant options AssistantCreationOptions assistantOptions = new() { Name = "Example: Contoso sales RAG", Instructions = "You are an assistant that looks up sales data and helps visualize the information based" + " on user queries. When asked to generate a graph, chart, or other visualization, use" + " the code interpreter tool to do so.", Tools = { new FileSearchToolDefinition(), // Enable the assistant to search and access files new CodeInterpreterToolDefinition(), // Enable the assistant to run code for data analysis }, ToolResources = new() { FileSearch = new() { NewVectorStores = { new VectorStoreCreationHelper([salesFile.Id]), } } }, };
创建
Assistant
和线程来管理用户与助手之间的交互:// Create the assistant Assistant assistant = assistantClient.CreateAssistant("gpt-4o", assistantOptions); // Configure and create the conversation thread ThreadCreationOptions threadOptions = new() { InitialMessages = { "How well did product 113045 sell in February? Graph its trend over time." } }; ThreadRun threadRun = assistantClient.CreateThreadAndRun(assistant.Id, threadOptions); // Sent the prompt and monitor progress until the thread run is complete do { Thread.Sleep(TimeSpan.FromSeconds(1)); threadRun = assistantClient.GetRun(threadRun.ThreadId, threadRun.Id); } while (!threadRun.Status.IsTerminal); // Get the messages from the thread run var messages = assistantClient.GetMessagesAsync( threadRun.ThreadId, new MessageCollectionOptions() { Order = MessageCollectionOrder.Ascending });
打印消息,并从与助手的对话中保存生成的图像:
// Process the messages from the assistant await foreach (ThreadMessage message in messages) { // Print out the messages from the assistant Console.Write($"[{message.Role.ToString().ToUpper()}]: "); foreach (MessageContent contentItem in message.Content) { if (!string.IsNullOrEmpty(contentItem.Text)) { Console.WriteLine($"{contentItem.Text}"); if (contentItem.TextAnnotations.Count > 0) { Console.WriteLine(); } // Include annotations, if any foreach (TextAnnotation annotation in contentItem.TextAnnotations) { if (!string.IsNullOrEmpty(annotation.InputFileId)) { Console.WriteLine($"* File citation, file ID: {annotation.InputFileId}"); } if (!string.IsNullOrEmpty(annotation.OutputFileId)) { Console.WriteLine($"* File output, new file ID: {annotation.OutputFileId}"); } } } // Save the generated image file if (!string.IsNullOrEmpty(contentItem.ImageFileId)) { OpenAIFile imageInfo = fileClient.GetFile(contentItem.ImageFileId); BinaryData imageBytes = fileClient.DownloadFile(contentItem.ImageFileId); using FileStream stream = File.OpenWrite($"{imageInfo.Filename}.png"); imageBytes.ToStream().CopyTo(stream); Console.WriteLine($"<image: {imageInfo.Filename}.png>"); } } Console.WriteLine(); }
在应用
bin
目录中找到并打开保存的图像,应如下所示: