Files
beaver_project/app-instance/backend/nanobot/agent/tools/spawn.py
2026-03-13 16:40:08 +08:00

106 lines
3.9 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

"""spawn 工具:用于把任务委派给后台 agent。"""
from typing import TYPE_CHECKING, Any
from nanobot.agent.tools.base import Tool
if TYPE_CHECKING:
from nanobot.agent.delegation import DelegationManager
class SpawnTool(Tool):
"""
后台委派工具。
作用:
1. 把耗时/可并行的任务委派给 DelegationManager
2. 目标可以是本地 agent、A2A 远端 agent 或 agent group
3. 后台任务异步执行,不阻塞当前对话回合。
"""
def __init__(self, manager: "DelegationManager"):
# manager 负责真正创建 asyncio 后台任务并管理生命周期。
self._manager = manager
# 默认来源会话CLI 直连场景)。实际会在每轮由 loop._set_tool_context 覆盖。
self._origin_channel = "cli"
self._origin_chat_id = "direct"
self._announce_via_bus = True
def set_context(self, channel: str, chat_id: str, announce_via_bus: bool = True) -> None:
"""设置后台委派结果回传的目标会话。"""
# 委派任务完成后并不会直接给用户发消息,
# 而是把结果发回这里记录的 originchannel/chat_id对应会话。
self._origin_channel = channel
self._origin_chat_id = chat_id
self._announce_via_bus = announce_via_bus
@property
def name(self) -> str:
# 暴露给 LLM 的工具名;模型会用这个名字发起 function call。
return "spawn"
@property
def description(self) -> str:
# 给模型看的能力描述,强调“后台执行 + 完成后回报”语义。
return (
"Delegate a task to a background agent. "
"Use this for complex or time-consuming work that can run independently. "
"You can target a specific agent, a group of agents, or let the system choose. "
"The delegated agent(s) will report back when done."
)
@property
def parameters(self) -> dict[str, Any]:
# OpenAI function schema定义模型可传入的参数结构。
return {
"type": "object",
"properties": {
"task": {
"type": "string",
"description": "The task for the delegated agent to complete",
},
"label": {
"type": "string",
"description": "Optional short label for the task (for display)",
},
"target": {
"type": "string",
"description": "Optional agent ID or name for a single target",
},
"targets": {
"type": "array",
"items": {"type": "string"},
"description": "Optional list of agent IDs/names for a group task",
},
"strategy": {
"type": "string",
"enum": ["auto", "local", "plugin", "a2a", "group"],
"description": "Routing strategy. Default is auto.",
},
},
"required": ["task"],
}
async def execute(
self,
task: str,
label: str | None = None,
target: str | None = None,
targets: list[str] | None = None,
strategy: str = "auto",
**kwargs: Any,
) -> str:
"""创建并启动一个后台委派任务。"""
# 这里仅负责转发请求,不在本工具内执行实际任务逻辑。
# 返回值是“已启动”状态文本,真正结果稍后通过主消息总线回传。
return await self._manager.dispatch(
task=task,
label=label,
target=target,
targets=targets,
strategy=strategy,
origin_channel=self._origin_channel,
origin_chat_id=self._origin_chat_id,
announce_via_bus=self._announce_via_bus,
)