Agent 中的 Skill 与 Tool
Agent 中的 Skill 与 Tool
Skill 与 Tool
对于我们垃圾开发来说:Tool 是基础工具,Skill 是业务技能
对于 Agent 来说:
Tool = 带说明书的函数
Skill = 一个或多个 Tool 的业务抽象
例如:
工单稽核 Skill
可能包含:
- 读取工单 Tool
- 查询用户状态 Tool
- 数据对比 Tool
- 总结分析 Prompt
关系大概是:
Skill
├─ Tool A
├─ Tool B
├─ Tool C
└─ Workflow
所以:
Tool 负责能力
Skill 负责业务
MCP 的本质
MCP(Model Context Protocol)本质上是给大模型暴露 Tool 的标准协议。
Agent 并不关心底层到底是什么系统。
例如:
HTTP API
RPC
数据库
CSF
ESB
对于 Agent 来说,它只看到:
Tool Name
Tool Description
Tool Parameters
例如:
@mcp.tool()
async def query_user_status(user_id: str):
"""
查询用户当前状态。
当需要确认用户是否正常、
欠费或停机时必须调用。
"""
大模型根据:
- Tool 名称
- 参数定义
- Tool 描述
决定是否调用。
因此可以简单理解为:
MCP = Tool 的标准化协议
为什么要自己写 MCP Server
我所在的公司采用 MCP 协议调用原有 CSF 平台接口。
但是公司的 CSF 平台并不天然支持 MCP。
因此需要额外编写 MCP Server 作为中间层。
整体结构:
Agent
↓
MCP Server
↓
CSF API
或者:
业务系统
↓
CSF/OpenAPI
↓
MCP Server
↓
Agent
这里的 MCP Server 本质上就是:
Adapter(适配器)
负责:
- 鉴权
- 参数转换
- 数据清洗
- 异常处理
Agent 不需要知道底层系统实现细节。
一个简单的 MCP Tool
# csf_mcp_server.py
from mcp.server.fastmcp import FastMCP
import httpx
mcp = FastMCP("CSF_Gateway_Server")
CSF_BASE_URL = "http://XXXXXXXXXX/api"
CSF_ACCESS_TOKEN = "token"
@mcp.tool()
async def query_user_status(user_id: str) -> str:
"""
用于查询核心业务系统中指定用户的当前状态。
当需要确认用户是否正常、
欠费或停机时,
必须调用此工具。
"""
headers = {
"Authorization": f"Bearer {CSF_ACCESS_TOKEN}",
"Content-Type": "application/json"
}
payload = {
"userId": user_id
}
try:
async with httpx.AsyncClient() as client:
response = await client.post(
f"{CSF_BASE_URL}/v1/user/status",
json=payload,
headers=headers,
timeout=5.0
)
response.raise_for_status()
data = response.json()
status_desc = (
data.get("data", {})
.get("statusDesc", "未知状态")
)
return (
f"用户 {user_id} 当前状态:"
f"{status_desc}"
)
except httpx.HTTPStatusError as e:
return (
f"查询失败,HTTP状态码:"
f"{e.response.status_code}"
)
except Exception as e:
return (
f"系统异常:{str(e)}"
)
if __name__ == "__main__":
mcp.run_stdio()
MCP Server 的价值
如果 Agent 直接调用业务系统:
Agent
↓
CSF
会出现几个问题:
鉴权问题
Agent 不应该直接持有:
AK/SK
Token
数据库密码
这些应该统一放在 MCP Server 中。
接口格式不统一
底层接口可能返回:
{
"code": 0,
"message": "success",
"data": {
"status": "1",
"statusDesc": "正常"
}
}
但 Agent 实际关心的是:
用户状态:正常
因此 MCP Server 可以负责结果清洗。
权限控制
例如:
客服 Agent
只能查用户
财务 Agent
只能查账单
运维 Agent
只能查机器
同一个 CSF:
100 个接口
不同 Agent:
只暴露对应 Tool
异常处理
如果底层接口:
超时
限流
503
网络异常
MCP Server 可以统一处理。
避免 Agent 直接崩溃。
Agent 如何调用 MCP Tool
通过 MCP Client 获取 Tool:
all_tools = await load_mcp_tools(session)
例如:
query_user_status
query_order
query_ticket
query_bill
然后根据权限过滤:
allowed_tools = [
t for t in all_tools
if t.name == "query_user_status"
]
这样当前 Agent 实际只拥有:
query_user_status
这点有点像给员工发权限。
LangGraph 在这里负责什么
MCP 解决的是:
如何调用 Tool
LangGraph 解决的是:
多个 Tool 如何协作
简单理解:
MCP = Tool层
LangGraph = Workflow层
LangGraph 编排示例
workflow = StateGraph(MessagesState)
workflow.add_node("router", router)
workflow.add_node(
"query_node",
ToolNode(allowed_tools)
)
workflow.add_edge(
START,
"router"
)
workflow.add_conditional_edges(
"router",
router,
{
"query_node": "query_node",
END: END
}
)
workflow.add_edge(
"query_node",
END
)
流程:
START
│
▼
Router
│
▼
ToolNode
│
▼
END
关于 Skill 的一个理解
目前我的理解是:
Tool 提供能力
Skill 提供业务价值
例如:
查询用户状态
只是一个 Tool。
但是:
用户风险分析
就是一个 Skill。
因为它可能需要:
查询用户状态
+
查询账单
+
查询历史工单
+
LLM分析
最终输出业务结论。
Skill、Tool、Agent 的关系
当前比较认可的抽象:
Agent
├─ Skill
│
├─ Skill
│
└─ Skill
而:
Skill
├─ Prompt
├─ Workflow
└─ Tool
因此:
Tool < Skill < Agent
或者:
Tool
↓
Skill
↓
Agent
当前理解的企业落地结构
业务系统
↓
CSF/OpenAPI
↓
MCP Server
↓
Tool
↓
Skill
↓
Agent
展开一点:
User
│
▼
Agent
│
┌────────┼────────┐
▼ ▼ ▼
SkillA SkillB SkillC
│ │ │
▼ ▼ ▼
Tools Tools Tools
(MCP)
│
▼
MCP Server
│
▼
CSF API
│
▼
业务系统集群
当前阶段的总结
一句话总结:
Tool 是能力。
Skill 是业务能力。
MCP 是暴露 Tool 的协议。
MCP Server 是业务系统与 Agent 之间的适配层。
LangGraph/Dify 等框架负责组织多个 Tool 的协作流程。
企业里的 Agent 本质上就是:
LLM + Skill + Tool + Workflow
目前的理解:
Agent = LLM + Memory + Skill
Skill = Prompt + Workflow + Tool
Tool = MCP 暴露出来的能力