Spring AI MCP案例

MCP 案例-Stdio传输模式

在该案例中,我们会创建MCP Server 和MCP Client 两个SpringBoot项目,MCP Server项目中会创建一个getWeather工具,该工具通过OpenWeather可以查询某个城市天气情况;MCP Client 项目中创建相应的Controller,根据配置通过STDIO 方式与MCP Server进行通信,实现调用天气工具。

Mcp Server开发

  1. 在项目中加入如下Maven依赖
java 复制代码
```
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>3.5.3</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.example</groupId>
    <artifactId>SpringAIMCPStdioServer</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>SpringAIMCPStdioServer</name>
    <description>SpringAIMCPStdioServer</description>

    <properties>
        <java.version>17</java.version>
    </properties>

    <!-- 导入 Spring AI BOM,用于统一管理 Spring AI 依赖的版本,
    引用每个 Spring AI 模块时不用再写 <version>,只要依赖什么模块 Mavens 自动使用 BOM 推荐的版本 -->
    <dependencyManagement>
        <dependencies>
            <dependency>
                <groupId>org.springframework.ai</groupId>
                <artifactId>spring-ai-bom</artifactId>
                <version>1.0.0-SNAPSHOT</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
        </dependencies>
    </dependencyManagement>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <!-- 依赖的MCP 包 ,只支持 STDIO 传输-->
        <dependency>
            <groupId>org.springframework.ai</groupId>
            <artifactId>spring-ai-starter-mcp-server</artifactId>
        </dependency>

        <!-- 依赖的json 包-->
        <dependency>
            <groupId>org.json</groupId>
            <artifactId>json</artifactId>
            <version>20210307</version>
        </dependency>
    </dependencies>

    <!-- 打包插件 -->
    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <version>3.4.4</version>
                <configuration>
                    <mainClass>com.example.springaimcpstdioserver.SpringAimcpStdioServerApplication</mainClass>
                </configuration>
                <executions>
                    <execution>
                        <goals>
                            <goal>repackage</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>
        </plugins>
    </build>

    <!-- 声明仓库, 用于获取 Spring AI 以及相关预发布版本-->
    <repositories>
        <repository>
            <id>spring-snapshots</id>
            <name>Spring Snapshots</name>
            <url>https://repo.spring.io/snapshot</url>
            <releases>
                <enabled>false</enabled>
            </releases>
        </repository>
        <repository>
            <name>Central Portal Snapshots</name>
            <id>central-portal-snapshots</id>
            <url>https://central.sonatype.com/repository/maven-snapshots/</url>
            <releases>
                <enabled>false</enabled>
            </releases>
            <snapshots>
                <enabled>true</enabled>
            </snapshots>
        </repository>
    </repositories>

</project>
  1. 创建 WeatherService.java构建查询天气工具

在项目中创建service包,在该包中创建WeatherService.java类,构建查询天气工具:

java 复制代码
package com.example.springaimcpstdioserver.service;


import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;

import org.json.JSONArray;
import org.json.JSONObject;
import org.springframework.ai.tool.annotation.Tool;
import org.springframework.ai.tool.annotation.ToolParam;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * 天气服务类,用于获取指定城市的天气信息
 * @Service 标记为 Spring 服务层组件
 */

@Service
public class WeatherService {
    private static final Logger logger = LoggerFactory.getLogger(WeatherService.class);

    private static final String BASE_URL = "http://api.openweathermap.org/data/2.5/weather";

    @Value("${OPEN_WEATHER_API_KEY}")
    private String OPEN_WEATHER_API_KEY;

    /**
     * 根据城市名称获取天气信息(使用 OpenWeatherMap)
     * @param city 城市名称,如 "Beijing"
     * @return 天气信息文本
     */
    @Tool(description = "获取指定城市的当前天气情况,格式化后的天气报告字符串。")
    public String getWeather(@ToolParam(description = "城市名称,必须是英文格式,比如 London 或 Beijing") String city) {

        logger.info("====== 调用了getWeather工具 ======");

        try {
            String charset = "UTF-8";

            String query = String.format(
                    "q=%s&appid=%s&units=metric&lang=zh_cn",
                    URLEncoder.encode(city, charset),
                    URLEncoder.encode(OPEN_WEATHER_API_KEY, charset)
            );

            URL url = new URL(BASE_URL + "?" + query);
            logger.info("====== 访问URL: ======"+url.toString());

            HttpURLConnection connection = (HttpURLConnection) url.openConnection();
            connection.setRequestMethod("GET");

            BufferedReader reader = new BufferedReader(new InputStreamReader(connection.getInputStream(), charset));

            StringBuilder response = new StringBuilder();
            String line;
            while ((line = reader.readLine()) != null) {
                response.append(line);
            }
            reader.close();

            JSONObject data = new JSONObject(response.toString());

            if (data.getInt("cod") == 404) {
                return "未找到该城市的天气信息。";
            }

            JSONObject main = data.getJSONObject("main");
            JSONArray weatherArray = data.getJSONArray("weather");
            JSONObject weather = weatherArray.getJSONObject(0);
            JSONObject wind = data.getJSONObject("wind");

            String weatherDescription = weather.optString("description", "无描述");
            double temperature = main.optDouble("temp", Double.NaN);
            double feelsLike = main.optDouble("feels_like", Double.NaN);
            double tempMin = main.optDouble("temp_min", Double.NaN);
            double tempMax = main.optDouble("temp_max", Double.NaN);
            int pressure = main.optInt("pressure", 0);
            int humidity = main.optInt("humidity", 0);
            double windSpeed = wind.optDouble("speed", Double.NaN);

            return String.format("""
                    城市: %s
                    天气描述: %s
                    当前温度: %.1f°C
                    体感温度: %.1f°C
                    最低温度: %.1f°C
                    最高温度: %.1f°C
                    气压: %d hPa
                    湿度: %d%%
                    风速: %.1f m/s
                    """,
                    data.optString("name", city),
                    weatherDescription,
                    temperature,
                    feelsLike,
                    tempMin,
                    tempMax,
                    pressure,
                    humidity,
                    windSpeed
            );

        } catch (Exception e) {
            return "获取天气信息时出错: " + e.getMessage();
        }
    }

    public static void main(String[] args) {
        //测试方法
        WeatherService client = new WeatherService();
        String beijing = client.getWeather("Beijing");
        System.out.println(beijing);
    }
}

Mcp Client 开发

按照如下步骤创建MCP Client的SpringBoot项目。该MCP Client 项目中可以使用不同的LLM模型,只需要在对应配置文件中引入不同的模型对应的apikey及相关依赖即可。

  1. 创建SpringBoot项目

SpringBoot项目命名为SpringAIMCPStdioClient,设置使用的JDK为17版本。

  1. 在项目中加入如下Maven依赖
html 复制代码
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>3.5.3</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.example</groupId>
    <artifactId>SpringAIMCPStdioClient</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>SpringAIMCPStdioClient</name>
    <description>SpringAIMCPStdioClient</description>

    <properties>
        <java.version>17</java.version>
    </properties>

    <!-- 导入 Spring AI BOM,用于统一管理 Spring AI 依赖的版本,
    引用每个 Spring AI 模块时不用再写 <version>,只要依赖什么模块 Mavens 自动使用 BOM 推荐的版本 -->
    <dependencyManagement>
        <dependencies>
            <dependency>
                <groupId>org.springframework.ai</groupId>
                <artifactId>spring-ai-bom</artifactId>
                <version>1.0.0-SNAPSHOT</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
        </dependencies>
    </dependencyManagement>

    <dependencies>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <!-- 基于 STDIO 传输客户端依赖 -->
        <dependency>
            <groupId>org.springframework.ai</groupId>
            <artifactId>spring-ai-starter-mcp-client</artifactId>
        </dependency>

        <!-- DeepSeek 模型依赖 -->
        <dependency>
            <groupId>org.springframework.ai</groupId>
            <artifactId>spring-ai-starter-model-deepseek</artifactId>
        </dependency>
    </dependencies>


    <!-- 声明仓库, 用于获取 Spring AI 以及相关预发布版本-->
    <repositories>
        <repository>
            <id>spring-snapshots</id>
            <name>Spring Snapshots</name>
            <url>https://repo.spring.io/snapshot</url>
            <releases>
                <enabled>false</enabled>
            </releases>
        </repository>
        <repository>
            <name>Central Portal Snapshots</name>
            <id>central-portal-snapshots</id>
            <url>https://central.sonatype.com/repository/maven-snapshots/</url>
            <releases>
                <enabled>false</enabled>
            </releases>
            <snapshots>
                <enabled>true</enabled>
            </snapshots>
        </repository>
    </repositories>

</project>
相关推荐
紫琪软件工作室1 小时前
SpringBoot Java邮件发送工具类
java·spring boot·spring
郝学胜-神的一滴1 小时前
干货版《算法导论》04:渐近复杂度与序列接口实战
java·开发语言·数据结构·c++·python·算法
zzzsde1 小时前
【Linux】信号处理(3)信号处理&&valatile关键字
linux·运维·服务器·开发语言·算法
神明9311 小时前
CSS 背景图滑动切换:纯 CSS 实现右进左出轮播效果
jvm·数据库·python
星栈1 小时前
投影挂了怎么办?我的 CQRS 三层容错方案
数据库·后端·开源
2301_811130541 小时前
【保姆级教程】Android Studio完整安装步骤(2026最新版,新手零踩坑)
android·java
_Evan_Yao1 小时前
缓存与数据库的“双写悖论”:一致性的常见陷阱与破局之道
java·后端·缓存
东风破1371 小时前
DM8数据库读写分离集群安装部署
数据库·oracle·dm达梦数据库
IT研究所1 小时前
从系统选型到ITR智能服务流落地的关键一步
大数据·运维·服务器·数据库·人工智能·科技·自动化