Spring AI 智能体 3 : 关于AskUserQuestionTool

传统的 AI 交互遵循一种常见模式:你给出提示词,AI 自行做出各种假设,然后生成回复。当这些假设与你的实际需求不符时,你就需要反复进行修正。每一个假设都会带来额外的返工,浪费时间与上下文。

如果 AI 智能体能够在给出答案之前先向你提出澄清问题,会怎么样?

AskUserQuestionTool 正是为此而生。它让 AI 智能体在回答之前先提出澄清问题,以交互式方式收集需求,并从一开始就创建与你的实际需求完全匹配的结果。

Spring AI 的这一实现将“先澄清再处理”这种交互模式带入 Java 生态系统,并确保大模型可移植性 —— 你只需定义一次问题处理器,即可在 OpenAI、Anthropic、Google Gemini 或任何其他受支持的模型中使用。

AskUserQuestionTool 可以将 AI 智能体转变为能够以交互式方式收集需求的协作伙伴。

AskUserQuestionTool 工作原理

AskUserQuestionTool 是 spring-ai-agent-utils 工具包的一部分,是 Claude Code 的 AskUserQuestion 工具在 Spring AI 中的可移植实现,让 AI 智能体在执行过程中可以向用户提出选择题式问题。

该工具遵循问答工作流:

  1. AI 生成问题: 智能体判断需要用户输入,并构造问题(每个问题包含问题文本、标题、2–4 个选项,以及多选标识),然后调用 askUserQuestion 工具函数。
  2. 用户提供答案: 你的自定义处理器接收这些问题,通过你的界面展示给用户,收集答案并返回给 AI。
  3. 追加提问: 如有必要,重复步骤 1 和 2,收集更多用户反馈。
  4. AI 基于上下文继续执行: 智能体使用收集到的答案提供定制化解决方案。

每个问题支持:

  • 单选或多选
  • 自由文本输入: 用户始终可以提供预定义选项之外的自定义内容
  • 丰富上下文: 每个选项都包含说明,解释其含义与权衡

可移植性与模型无关,无厂商锁定

与绑定特定大模型平台的实现不同,Spring AI 的这一实现可跨多家大模型提供商使用,让你无需重写代码或问题处理器即可切换模型。

与 MCP Elicitation 的关系

AskUserQuestionTool 是智能体本地的交互式用户输入方案,在概念上与 MCP Elicitation 能力类似。MCP Elicitation 让 MCP 服务器通过 JSON 模式请求结构化用户输入,而 AskUserQuestionTool 无需依赖 MCP 服务器,即可在你的智能体内部直接提供相同的交互式模式。Spring AI 还通过 @McpElicitation 注解为服务端驱动场景提供完整的 MCP Elicitation 支持。

示例:旅行推荐助手

以下是旅行推荐场景中的实际应用(来自 ask-user-question-demo 示例):

智能体通过交互式问题完整收集需求,然后提供个性化推荐 —— 无假设、无反复修正。

快速开始

1. 添加依赖

2. 配置智能体:

3. 实现 QuestionHandler

使用下面的控制台或 Web 示例实现 QuestionHandler

当智能体需要澄清信息时,会自动调用该工具,并使用答案提供定制化解决方案。

示例代码: ask-user-question-demo

QuestionHandler 示例

1. 基于控制台的 QuestionHandler

代码如下:

代码中的 Handler 实现会展示问题选项,接受数字选择(如 “1,2”)或自由文本(如 “中等预算”),并将答案返回给智能体。

2. 基于 Web 的 QuestionHandler

对于 Web 应用,使用 CompletableFuture 桥接异步 UI 交互与同步 QuestionHandler API 来获取问题。

而后通过 WebSocket/SSE 将问题发送到前端,并在 future.get() 处阻塞;当用户通过 REST 接口提交答案时,完成该 future。

这里没有示例代码了。

结论

AskUserQuestionTool 将 AI 智能体从 “基于假设的应答者” 转变为 “先收集需求再行动的协作者”,从而一次就能给出符合需求的答案。

原文见:AskUserQuestionTool – Agents That Clarify Before Acting