news 2026/9/10 23:45:09

Semantic Kernel 实战指南:用 Python 与 .NET 构建企业级 AI Agent 与多智能体系统

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Semantic Kernel 实战指南:用 Python 与 .NET 构建企业级 AI Agent 与多智能体系统

Semantic Kernel 实战指南:用 Python 与 .NET 构建企业级 AI Agent 与多智能体系统

【免费下载链接】semantic-kernelIntegrate cutting-edge LLM technology quickly and easily into your apps项目地址: https://gitcode.com/GitHub_Trending/se/semantic-kernel

本篇指南以 Semantic Kernel 官方仓库根目录的 README.md 为主体骨架,结合仓库内 Python SDK 与 .NET SDK 的真实源码实现展开深度解读。你将系统掌握:Semantic Kernel 的核心概念、环境要求与安装方式、如何用 Python/.NET 快速创建第一个可运行的 Agent、如何通过插件(Plugin)与结构化输出扩展 Agent 能力,以及如何编排多个专业化 Agent 协同完成复杂任务。

1. Semantic Kernel 是什么

Semantic Kernel 是一个模型无关(model-agnostic)的 SDK,它帮助开发者构建、编排并部署 AI Agent 与多智能体(Multi-Agent)系统。无论是简单的聊天机器人,还是需要多个 Agent 协作的复杂工作流,Semantic Kernel 都提供了一致的抽象与工具,并强调企业级所需的可靠性与灵活性。

从仓库结构来看,该项目覆盖三种主流语言:

  • Python 实现位于 python/semantic_kernel,包含 agents、connectors、functions、processes 等模块;
  • .NET 实现位于 dotnet/src,其中 Agents/Core 提供了ChatCompletionAgent等核心 Agent 类型,Connectors 聚合了 OpenAI、Azure OpenAI、Google、MistralAI、Ollama、ONNX 等众多模型接入;
  • Java 分支(仓库内 java/README.md)目前仅保留仓库分离说明,构建指引指向独立的 semantic-kernel-java 仓库。

1.1 系统要求

根据 README 中的官方声明,运行 Semantic Kernel 需要:

平台最低版本要求
Python3.10+
.NET.NET 10.0+
JavaJDK 17+
操作系统Windows、macOS、Linux

1.2 核心特性一览

  • 模型灵活性:内置对 OpenAI、Azure OpenAI、Hugging Face、NVIDIA 等 LLM 服务的支持,可随时切换不同模型提供方;
  • Agent 框架:构建模块化的 AI Agent,支持访问工具/插件、记忆与规划能力;
  • 多智能体系统:编排多个专家型 Agent 协同完成复杂工作流;
  • 插件生态:可通过原生代码函数、提示词模板、OpenAPI 规范或模型上下文协议(MCP)进行扩展;
  • 向量数据库支持:与 Azure AI Search、Elasticsearch、Chroma 等无缝集成;
  • 多模态支持:可处理文本、视觉与音频输入;
  • 本地部署:支持 Ollama、LMStudio、ONNX 等本地推理运行时;
  • 流程框架(Process Framework):以结构化工作流方式建模复杂业务流程;
  • 企业级就绪:面向可观测性、安全性与稳定 API 设计。

上述特性在仓库中均有对应落点:例如 dotnet/src/Connectors/Connectors.Ollama、dotnet/src/Connectors/Connectors.Onnx 对应本地部署;dotnet/src/Experimental/Process.Core 与 python/semantic_kernel/processes 对应流程框架;docs/decisions/0069-mcp.md 记录了 MCP 集成相关的架构决策。

[!NOTE] README 顶部明确说明:Semantic Kernel 的继任者是 Microsoft Agent Framework(MAF),MAF 1.0 已作为生产就绪版本发布,提供企业级多智能体编排、多模型提供方支持以及通过 A2A 与 MCP 实现的跨运行时互操作。若你的项目面向全新长期演进,建议评估迁移方案。

2. 环境配置与安装

2.1 配置 AI 服务环境变量

在使用任何示例前,需要先为 AI 服务设置环境变量。以 Azure OpenAI 为例:

export AZURE_OPENAI_API_KEY=AAA....

或直接使用 OpenAI:

export OPENAI_API_KEY=sk-...
  • 环境变量配置错误是 README「Troubleshooting」中列出的首要常见问题,排查时应首先确认 API Key 环境变量是否已正确设置,其次确认 Azure OpenAI 的 deployment 或 OpenAI 模型访问权限是否可用。

2.2 Python 安装

pip install semantic-kernel

2.3 .NET 安装

dotnet add package Microsoft.SemanticKernel dotnet add package Microsoft.SemanticKernel.Agents.Core

其中Microsoft.SemanticKernel.Agents.Core正是 dotnet/src/Agents/Core 对应的 NuGet 包,它提供了ChatCompletionAgentAgentGroupChat等核心 Agent 抽象。

2.4 Java

Java 构建与安装说明见独立的 semantic-kernel-java 仓库的 BUILD 文档(README 中以外部链接形式给出,此处不再重复)。

3. 快速开始:创建第一个 Agent

README 提供了 Python 与 .NET 两个对等的快速入门示例。下面逐段拆解其运行机制与底层源码。

3.1 Python:基础 Agent

import asyncio from semantic_kernel.agents import ChatCompletionAgent from semantic_kernel.connectors.ai.open_ai import AzureChatCompletion async def main(): # Initialize a chat agent with basic instructions agent = ChatCompletionAgent( service=AzureChatCompletion(), name="SK-Assistant", instructions="You are a helpful assistant.", ) # Get a response to a user message response = await agent.get_response(messages="Write a haiku about Semantic Kernel.") print(response.content) asyncio.run(main())

这段代码的关键点在 chat_completion_agent.py 的ChatCompletionAgent类中均有对应实现:

  • 构造参数service接收一个ChatCompletionClientBase实例;name用于标识 Agent;instructions作为系统级指令注入对话。从 构造器源码 可见,它还可接收descriptionidkernelargumentspluginsprompt_template_configfunction_choice_behavior等参数。
  • service 与 kernel 的关系configure_service()方法会将传入的serviceoverwrite=True方式注册到内核中(见 configure_service)。若同时传入 kernel 与 service,当两者service_idai_model_id一致时,service 优先生效。
  • get_response调用链get_response会先确保线程存在、将线程内历史消息装载为ChatHistory,再经_inner_invoke完成一次完整的 Agent 调用并返回最后一个响应(见 get_response 实现)。此外还提供invoke(迭代式响应)与invoke_stream(流式响应,返回StreamingChatMessageContent)两种入口,分别对应trace_agent_invocationtrace_agent_streaming_invocation遥测装饰器。

3.2 .NET:基础 Agent

using Microsoft.SemanticKernel; using Microsoft.SemanticKernel.Agents; var builder = Kernel.CreateBuilder(); builder.AddAzureOpenAIChatCompletion( Environment.GetEnvironmentVariable("AZURE_OPENAI_DEPLOYMENT"), Environment.GetEnvironmentVariable("AZURE_OPENAI_ENDPOINT"), Environment.GetEnvironmentVariable("AZURE_OPENAI_API_KEY") ); var kernel = builder.Build(); ChatCompletionAgent agent = new() { Name = "SK-Agent", Instructions = "You are a helpful assistant.", Kernel = kernel, }; await foreach (AgentResponseItem<ChatMessageContent> response in agent.InvokeAsync("Write a haiku about Semantic Kernel.")) { Console.WriteLine(response.Message); }

对应的 .NET 实现位于 dotnet/src/Agents/Core/ChatCompletionAgent.cs:

  • ChatCompletionAgent继承自ChatHistoryAgent,是基于IChatCompletionService的 Agent 特化(见 类定义与注释),其中明确提示:使用 Agent 插件需要启用PromptExecutionSettings.FunctionChoiceBehavior(即设置Arguments)。
  • 该类提供InstructionsRole属性,默认值为AuthorRole.System;源码注释特别指出,某些「O*」系列深度推理模型要求以developer角色提供指令,而某些模型两种角色均不支持,此时 Agent 能力将完全由插件决定(见 InstructionsRole 注释)。
  • InvokeAsync返回IAsyncEnumerable<AgentResponseItem<ChatMessageContent>>,采用流式迭代消费方式逐条输出消息;执行时会自动处理函数调用内容(FunctionCallContent/FunctionResultContent)在 AutoInvoke 开关下的线程写入策略(见 InvokeAsync 中关于 function call 的注释)。

仓库的 .NET 侧还提供了完整的分步入门示例,见 dotnet/samples/GettingStartedWithAgents,其中 Step01_Agent.cs 等文件展示了从单 Agent 到多 Agent 编排的演进路径;Python 侧对应示例见 python/samples/getting_started_with_agents。

4. 用插件扩展 Agent:函数调用与结构化输出

README 的第二个示例展示了「插件(Plugin)+ 结构化输出」的组合用法,这也是 Semantic Kernel 最具生产力的能力之一。

4.1 Python:Agent 搭配 Plugin

import asyncio from typing import Annotated from pydantic import BaseModel from semantic_kernel.agents import ChatCompletionAgent from semantic_kernel.connectors.ai.open_ai import AzureChatCompletion, OpenAIChatPromptExecutionSettings from semantic_kernel.functions import kernel_function, KernelArguments class MenuPlugin: @kernel_function(description="Provides a list of specials from the menu.") def get_specials(self) -> Annotated[str, "Returns the specials from the menu."]: return """ Special Soup: Clam Chowder Special Salad: Cobb Salad Special Drink: Chai Tea """ @kernel_function(description="Provides the price of the requested menu item.") def get_item_price( self, menu_item: Annotated[str, "The name of the menu item."] ) -> Annotated[str, "Returns the price of the menu item."]: return "$9.99" class MenuItem(BaseModel): price: float name: str async def main(): # Configure structured output format settings = OpenAIChatPromptExecutionSettings() settings.response_format = MenuItem # Create agent with plugin and settings agent = ChatCompletionAgent( service=AzureChatCompletion(), name="SK-Assistant", instructions="You are a helpful assistant.", plugins=[MenuPlugin()], arguments=KernelArguments(settings) ) response = await agent.get_response(messages="What is the price of the soup special?") print(response.content)

这段示例包含两个核心技术点:

@kernel_function装饰器:定义于 kernel_function_decorator.py,它会把普通 Python 方法标记为可被 LLM 调用的工具函数,并自动解析元数据:

  • namedescription不传时,默认使用函数名与 docstring;
  • 参数类型与描述从函数签名解析,通过typing.Annotated提供参数描述(如示例中的Annotated[str, "The name of the menu item."]);
  • 解析结果存储于__kernel_function_parameters____kernel_function_return_type__等私有属性中,供后续向 LLM 或 MCP Server 暴露函数表示时使用;
  • 若在参数注解中加入{"include_in_function_choices": False}之类的 dict,可将该参数从函数选择表示中排除(详见 装饰器 docstring)。

② 结构化输出(Structured Output):通过OpenAIChatPromptExecutionSettingsresponse_format字段绑定 Pydantic 模型MenuItem,强制模型按pricename两个字段的 schema 返回 JSON 结构。仓库的 python/samples/concepts/structured_outputs 目录提供了更多相关示例;.NET 侧的对应设计决策见 docs/decisions/0053-dotnet-structured-outputs.md。

4.2 .NET:Agent 搭配 Plugin

using System.ComponentModel; using Microsoft.SemanticKernel; using Microsoft.SemanticKernel.Agents; using Microsoft.SemanticKernel.ChatCompletion; var builder = Kernel.CreateBuilder(); builder.AddAzureOpenAIChatCompletion( Environment.GetEnvironmentVariable("AZURE_OPENAI_DEPLOYMENT"), Environment.GetEnvironmentVariable("AZURE_OPENAI_ENDPOINT"), Environment.GetEnvironmentVariable("AZURE_OPENAI_API_KEY") ); var kernel = builder.Build(); kernel.Plugins.Add(KernelPluginFactory.CreateFromType<MenuPlugin>()); ChatCompletionAgent agent = new() { Name = "SK-Assistant", Instructions = "You are a helpful assistant.", Kernel = kernel, Arguments = new KernelArguments(new PromptExecutionSettings() { FunctionChoiceBehavior = FunctionChoiceBehavior.Auto() }) }; await foreach (AgentResponseItem<ChatMessageContent> response in agent.InvokeAsync("What is the price of the soup special?")) { Console.WriteLine(response.Message); } sealed class MenuPlugin { [KernelFunction, Description("Provides a list of specials from the menu.")] public string GetSpecials() => """ Special Soup: Clam Chowder Special Salad: Cobb Salad Special Drink: Chai Tea """; [KernelFunction, Description("Provides the price of the requested menu item.")] public string GetItemPrice( [Description("The name of the menu item.")] string menuItem) => "$9.99"; }

.NET 侧的对应要点:

  • 插件类MenuPlugin通过[KernelFunction][Description]特性标记,经KernelPluginFactory.CreateFromType<MenuPlugin>()注册到内核的Plugins集合;
  • 关键配置是Arguments中的FunctionChoiceBehavior = FunctionChoiceBehavior.Auto(),即自动函数选择行为——这正是 ChatCompletionAgent.cs 注释中强调的「启用 Agent 插件」的前提条件;若省略该配置,模型将不会获知并调用插件函数;
  • README 中该示例的预期输出为:The price of the Clam Chowder, which is the soup special, is $9.99.,体现了「LLM 自主决定调用GetItemPrice并整合结果」的完整链路。

函数选择行为的更多设计与实现,可参考 docs/decisions/0061-function-call-behavior.md 与 docs/decisions/0063-function-calling-reliability.md 两份架构决策记录。

5. 多智能体系统:专业 Agent 协同

README 的第三个示例展示如何构建一个「分诊 + 专业处理」的多 Agent 系统:BillingAgent(账单)、RefundAgent(退款)作为垂直专家,TriageAgent(分诊)负责判断用户请求应转发给谁,并把专家 Agent 的结果汇总给用户。

5.1 Python:三 Agent 协作示例

import asyncio from semantic_kernel.agents import ChatCompletionAgent, ChatHistoryAgentThread from semantic_kernel.connectors.ai.open_ai import AzureChatCompletion, OpenAIChatCompletion billing_agent = ChatCompletionAgent( service=AzureChatCompletion(), name="BillingAgent", instructions="You handle billing issues like charges, payment methods, cycles, fees, discrepancies, and payment failures." ) refund_agent = ChatCompletionAgent( service=AzureChatCompletion(), name="RefundAgent", instructions="Assist users with refund inquiries, including eligibility, policies, processing, and status updates.", ) triage_agent = ChatCompletionAgent( service=OpenAIChatCompletion(), name="TriageAgent", instructions="Evaluate user requests and forward them to BillingAgent or RefundAgent for targeted assistance." " Provide the full answer to the user containing any information from the agents", plugins=[billing_agent, refund_agent], ) thread: ChatHistoryAgentThread = None async def main() -> None: print("Welcome to the chat bot!\n Type 'exit' to exit.\n Try to get some billing or refund help.") while True: user_input = input("User:> ") if user_input.lower().strip() == "exit": print("\n\nExiting chat...") return False response = await triage_agent.get_response( messages=user_input, thread=thread, ) if response: print(f"Agent :> {response}")

该示例透露了三个重要机制:

  1. Agent 即插件(Agent-as-Plugin)plugins=[billing_agent, refund_agent]直接把两个ChatCompletionAgent实例作为TriageAgent的插件传入。这说明 Semantic Kernel 中的 Agent 实现了函数调用接口,可以被其他 Agent 当作工具调用——这一点在 .NET 侧也有专门示例 Step08_AgentAsKernelFunction.cs。
  2. 混合模型BillingAgent/RefundAgent使用AzureChatCompletion,而TriageAgent使用OpenAIChatCompletion,验证了「模型无关」特性——不同 Agent 可绑定不同模型提供方。
  3. 线程(Thread)贯穿多轮对话thread: ChatHistoryAgentThread保存对话状态并跨轮次复用。从 ChatHistoryAgentThread 实现 可见:线程内部持有ChatHistoryget_messages()可遍历历史消息,_on_new_message()会将新消息写入历史(通过thread_id元数据去重避免重复),reduce()则支持基于ChatHistoryReducer对超长历史做压缩,防止上下文窗口溢出。

README 中还给出了该示例的一次完整运行输出(Agent 引导用户提供账号、扣款日期、交易 ID 等信息,再分别走账单核实与退款流程,并说明退款通常需要 5-10 个工作日),可作为验证多 Agent 路由行为的参照基线。

5.2 线程与响应模型的源码解读

从 ChatHistoryAgentThread 的构造逻辑 可以看到:

  • 未显式传入chat_history时会自动创建新的ChatHistory实例;
  • 未传入thread_id时自动生成thread_{uuid4().hex}形式的唯一 ID;
  • 线程_delete()会清空历史消息。

get_responseinvoke都遵循「确保线程存在 → 装载历史 → 内部调用 → 产出响应」的统一流程,两者的差异在于get_response只返回最后一个响应(responses[-1]),而invoke以异步迭代器方式逐条产出,适合需要观察中间步骤的场景(见 invoke 实现)。

6. 更多学习资源与示例导航

README 的「Where to Go Next」为继续深入学习提供了清晰路线(下文已转换为仓库内可访问的资源):

  1. 分步入门:.NET 侧见 dotnet/samples/GettingStarted(Step1~Step9,覆盖创建 Kernel、添加插件、YAML 提示词、依赖注入、聊天提示词、负责任 AI、可观测性、流水线、OpenAPI 插件);Python 侧见 python/samples/getting_started(含 Kernel 加载、prompt 运行、函数调用、向量存储与嵌入等 Notebook)。
  2. Agent 专项示例:.NET 见 dotnet/samples/GettingStartedWithAgents(Step01~Step10,覆盖 Agent 基础、插件、聊天、KernelFunction 策略、JSON 结果、依赖注入、遥测、Agent 作为 KernelFunction、声明式配置与多 Agent 声明式编排);Python 见 python/samples/getting_started_with_agents。
  3. 100+ 详细示例:.NET 的 dotnet/samples/Concepts 与 Python 的 python/samples/concepts 按主题划分,包括 Agents、ChatCompletion、Filtering、FunctionCalling、Memory、PromptTemplates、RAG、Search 等目录。
  4. 核心概念:仓库 docs/decisions 收录了 70+ 份 ADR(架构决策记录),如 0032-agents.md、0033-kernel-filters.md、0054-processes.md、0058-vector-search-design.md,可深入理解每一项能力的设计动机。
  5. API 参考:C# 与 Python 的官方 API 参考文档在 README 中以 learn.microsoft.com 外部链接提供,此处不展开。

此外,dotnet/samples/Demos 与 python/samples/demos 还提供了端到端 Demo(如预订餐厅、HomeAutomation、VoiceChat、VectorStoreRAG、ProcessFrameworkWithAspire 等),适合在掌握基础后参考落地。

7. 故障排查与社区支持

7.1 常见问题

  • 认证错误(Authentication Errors):检查 API Key 环境变量是否正确设置(见第 2 节);
  • 模型不可用(Model Availability):核实 Azure OpenAI 的 deployment 名称与区域、OpenAI 模型访问权限是否就绪。

7.2 寻求帮助

  • 在仓库 GitHub Issues 中检索已知问题;
  • 在官方 Discord 社区(README 中提供的 aka.ms/SKDiscord 链接)搜索解决方案;
  • 提问时附带 SDK 版本号与完整错误信息,有助于快速定位。

8. 结语

通过本指南,你可以完成从「环境准备 → 单 Agent 快速起步 → 插件与结构化输出 → 多 Agent 编排」的完整链路。基于仓库源码可以看到,Python 与 .NET 两套 SDK 在 Agent 抽象(ChatCompletionAgent)、线程模型(ChatHistoryAgentThread)、插件机制(kernel_function/KernelFunction)与函数选择行为(FunctionChoiceBehavior)上保持了高度一致的语义,因此可以「学一套、用两门」。更进一步,仓库的 docs/decisions、dotnet/samples/Concepts 与 python/samples/concepts 是深入掌握每个能力细节的权威参考,值得按需查阅。

【免费下载链接】semantic-kernelIntegrate cutting-edge LLM technology quickly and easily into your apps项目地址: https://gitcode.com/GitHub_Trending/se/semantic-kernel

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/9/10 23:43:59

Simulink代码生成在单片机开发中的实践与优化

1. Simulink与单片机开发&#xff1a;为什么选择代码生成&#xff1f;在嵌入式系统开发领域&#xff0c;工程师们经常面临一个经典矛盾&#xff1a;算法开发效率与硬件实现精度之间的博弈。传统开发流程中&#xff0c;算法工程师用MATLAB/Simulink完成仿真验证后&#xff0c;需…

作者头像 李华
网站建设 2026/9/10 23:42:16

30米DEM与shp边界文件处理全流程:以漳州为例的GDAL实战指南

简介&#xff1a;这份福建省漳州市30米分辨率DEM数字高程数据包&#xff0c;面向GIS学习者、城乡规划与地质灾害评估人员&#xff0c;可用于地形分析、坡度坡向提取、洪水模拟等场景。压缩包共12个文件&#xff0c;大小约35.1MB&#xff0c;核心为漳州市DEM.tif高程栅格&#x…

作者头像 李华
网站建设 2026/9/10 23:37:49

论文初稿怎么一次成型?一篇讲透从大纲到成文的四个承接接口

大纲写了、资料齐了&#xff0c;正文却总在结构层被推翻——论文初稿反复重写&#xff0c;多半不是文笔问题&#xff0c;而是大纲里定下的东西在成文时没有被接住。本文把「一次成型」的判定重新说清楚&#xff0c;再顺着大纲到成文之间的四个承接接口&#xff0c;给出可自查的…

作者头像 李华
网站建设 2026/9/10 23:35:06

记忆化搜索的介绍

1.斐波那契数 509. 斐波那契数 - 力扣&#xff08;LeetCode&#xff09;https://leetcode.cn/problems/fibonacci-number/description/ (通过这道题来理解记忆化搜索)这道题解法一是递归&#xff0c;dfs使命是给个数n&#xff0c;返回第n个斐波那契数。第n个斐波那契数是前…

作者头像 李华