Tool Calling 技术实战:解决大模型时间感知问题

21 阅读6分钟

 

1. 背景问题

在使用本地部署的 Ollama Qwen3:1.7b 模型时,我们遇到了一个典型的大模型知识局限问题:

  • 访问 /tool/date/whattime?msg=你是谁现在几点 ,模型返回:

    我是一个由阿里云研发的大型语言模型,名
    为通义千问,专门用于回答各种问题和提供
    帮助。现在的时间是北京时间2023年10月
    15日,大约中午12点。如果你有其他问题,
    随时告诉我! 😊
    

  • 实际时间:2026-01-30
    模型返回的时间停留在2023年,这是因为大模型的训练数据有时间限制,无法获取实时信息。

2. 解决方案:Tool Calling 技术

2.1 核心原理

Tool Calling(工具调用)技术通过以下流程解决实时信息获取问题:

  1. 定义工具:创建获取实时信息的函数
  2. 注册工具:将工具注册到模型的工具列表中
  3. 提示工程:指导模型在适当场景下调用工具
  4. 执行调用:模型根据需要调用工具获取实时数据
  5. 结果处理:模型基于工具返回的结果生成最终答案

tool调用流程图
在这里插入图片描述​编辑

2.2 代码实现 DateTimeTools.java - 工具定义

package com.conca.ai.tool.toolsdate;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.ai.tool.annotation.Tool;

import java.time.LocalDateTime;

/**
 * @auther zzyybs@126.com
 * @create 2025-07-31 20:39
 * @Description TODO
 */
public class DateTimeTools
{
    private static final Logger log = LoggerFactory.getLogger(DateTimeTools.class);
    
    /**
     * 1.定义 function call(tool call)
     * 2. returnDirect
     *    true = tool直接返回不走大模型,直接给客户
     *    false = 默认值,拿到tool返回的结果,给大模型,最后由大模型回复
     */
    @Tool(description = "获取当前的准确时间,当用户询问当前时间、现在几点、几点了等问题时必须使用此工具", returnDirect = true)
    public String getCurrentTime()
    {
        String currentTime = LocalDateTime.now().toString();
        log.info("DateTimeTools被调用,当前时间:{}", currentTime);
        return currentTime;
    }
}

2.3 代码实现 ToolDateController.java

package com.conca.ai.tool.toolsdate;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.ai.chat.model.ChatModel;
import org.springframework.ai.chat.prompt.ChatOptions;
import org.springframework.ai.chat.prompt.Prompt;
import org.springframework.ai.model.tool.ToolCallingChatOptions;
import org.springframework.ai.support.ToolCallbacks;
import org.springframework.ai.tool.ToolCallback;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

import jakarta.annotation.Resource;

@RestController
public class ToolDateController {

	private static final Logger log = LoggerFactory.getLogger(ToolDateController.class);

	@Resource(name = "ollamaDeepseekChatModel")
	private ChatModel chatModel;

	/**
	 * http://localhost:8080/tool/date/whattime?msg=你是谁现在几点 
	 */
	@GetMapping("/tool/date/whattime")
	public String whattime(@RequestParam(name = "msg", defaultValue = "你是谁现在几点") String msg) {
	
		return chatModel.call(msg);
	}

	/**
	 * http://localhost:8080/tool/date/chat?msg=你是谁现在几点 1.定义 function call(tool call)
	 * 2. returnDirect true = tool直接返回不走大模型,直接给客户 false =
	 * 默认值,拿到tool返回的结果,给大模型,最后由大模型回复
	 */
	@GetMapping("/tool/date/chat")
	public String chat(@RequestParam(name = "msg", defaultValue = "你是谁现在几点") String msg) {
		// 1.工具注册到工具集合里
		ToolCallback[] tools = ToolCallbacks.from(new DateTimeTools());

		// 2.将工具集配置进ChatOptions对象
		ChatOptions options = ToolCallingChatOptions.builder().toolCallbacks(tools).build();

		// 3.构建提示词,明确告知大模型使用工具获取当前时间
		String enhancedPrompt = msg + "\n\n系统指令:当用户询问当前时间、现在几点、几点了等问题时,必须使用getCurrentTime工具获取准确时间,不能自己猜测时间。";
		Prompt prompt = new Prompt(enhancedPrompt, options);
		log.info("调用大模型,prompt={}", prompt);
		// 4.调用大模型
		return chatModel.call(prompt).getResult().getOutput().getText();
	}

}

3. 技术实现详解

3.1 本地 Ollama 部署 Qwen3:1.7b

  1. 安装 Ollama :从官网下载并安装 Ollama 客户端
  2. 拉取模型 :执行命令 ollama pull qwen3:1.7b
  3. 启动服务 :Ollama 会自动启动并运行在本地端口

3.2 工具调用核心机制

  1. 工具定义 :

    • 使用 @Tool 注解标记工具方法
    • 详细的 description 字段告诉模型何时使用此工具
    • returnDirect = true 表示直接返回工具结果,不经过模型二次处理
  2. 工具注册 :

    • 使用 ToolCallbacks.from() 将工具类转换为工具回调数组
    • 通过 ToolCallingChatOptions 配置工具调用选项
  3. 提示工程 :

    • 在提示词中明确告知模型必须使用工具获取时间
    • 强调不能自己猜测时间,确保模型理解工具的必要性
  4. 结果处理 :

    • 工具返回的是原始时间字符串 2026-01-30T22:45:30.123456
    • 模型可以基于此结果生成更友好的回答

4. Tool Calling 技术的价值

4.1 解决的核心问题

  1. 知识时效性 :大模型训练数据有时间限制,无法获取实时信息
  2. 信息准确性 :避免模型基于过时知识进行错误猜测
  3. 功能扩展 :将大模型能力与外部系统集成
  4. 计算密集型任务 :将复杂计算交给专门的工具处理
  5. 数据访问 :让模型能够查询数据库、API 等外部数据源

4.2 应用场景

  1. 实时信息查询 :天气、股票、新闻、时间等
  2. 数据分析 :调用统计工具进行数据分析
  3. 系统操作 :控制 IoT 设备、执行系统命令
  4. 多步骤任务 :预订机票、酒店等需要多步骤交互的任务
  5. 专业领域 :调用专业工具进行法律、医疗、金融等领域的分析

5. 实际测试结果

5.1 传统调用(无工具)

  • 接口 : /tool/date/whattime?msg=你是谁现在几点
  • 返回 : 我是一个由阿里云研发的大型语言模型,名为通义千问,专门用于回答各种问题和提供帮助。现在的时间是北京时间2023年10月15日,大约中午12点。如果你有其他问题,随时告诉我! 😊
  • 问题 :时间严重错误(2023年 vs 2026年)

5.2 工具调用(有工具)

  • 接口 : /tool/date/chat?msg=你是谁现在几点
  • 返回 : 2026-01-30T22:45:30.123456
  • 结果 :时间完全准确

6. 技术架构优势

  1. 松耦合设计 :工具与模型分离,便于独立开发和维护
  2. 可扩展性 :可以轻松添加新的工具,扩展模型能力
  3. 安全性 :通过工具封装,控制模型对外部系统的访问权限
  4. 可监控性 :工具调用有完整的日志记录,便于问题排查
  5. 标准化 :使用 Spring AI 标准接口,便于与其他系统集成

7. 总结

Tool Calling 技术为大模型注入了实时感知能力,解决了传统大模型的知识局限问题。通过本文的实战案例,我们看到:

  1. 问题识别 :准确识别大模型的知识边界和能力局限
  2. 技术选型 :选择合适的工具调用框架(Spring AI)
  3. 实现方案 :通过简洁的代码实现工具定义和调用
  4. 效果验证 :对比测试证明工具调用能够提供准确的实时信息
    Tool Calling 不仅是解决时间感知问题的技术方案,更是大模型从"静态知识"向"动态能力"转变的关键技术。它打开了大模型与外部世界交互的大门,为构建更智能、更实用的 AI 应用提供了无限可能。