一、MCP 核心技术原理
MCP 本质是基于 JSON-RPC 2.0 的标准化 RPC 协议,核心解决「大模型与外部工具 / 数据的统一交互问题」,其技术架构可拆解为三层,完全适配 Java 的分层设计思想:
| 层级 | 角色(Java 对应实现) | 核心职责 |
|---|---|---|
| 应用层 | Host(你的 Java 业务系统) | 接收用户指令→调用大模型→解析模型的 MCP 调用意图→转发指令到 MCP Client |
| 协议层 | Client(Java MCP 客户端) | 标准化封装指令(JSON-RPC 格式)→与 MCP Server 建立通信→处理请求 / 响应序列化 |
| 工具适配层 | Server(Java MCP 服务端) | 适配具体工具(MySQL/Redis/ 本地文件)→执行实际操作→按 MCP 标准返回结果 |
MCP 核心通信流程(时序)
- Host(Java 系统)接收用户指令:「查询上月华东区销售数据并生成报表」;
- Host 调用大模型,模型识别出需要「调用 MySQL 查询 + 生成 Excel」,返回 MCP 调用指令;
- Java MCP Client 将指令封装为 JSON-RPC 2.0 格式(如
{"jsonrpc":"2.0","method":"mysql/query","params":{"sql":"SELECT ..."},"id":"123"}); - Client 通过 HTTP/TCP 将指令发送给 MCP Server(已适配 MySQL);
- MCP Server 执行 SQL,将结果按 MCP 标准返回(结构化 JSON);
- Client 解析结果后回传给 Host,Host 再调用大模型生成报表,最终返回给用户。
MCP 与 Java 生态的适配点
- 协议层:JSON-RPC 可通过 Jackson/Gson 轻松序列化,兼容 Java 主流 JSON 库;
- 通信层:支持 HTTP/WebSocket,可复用 Spring Boot 的 RestTemplate/Netty;
- 工具适配层:可基于 Spring Bean 封装 MCP Server,适配你现有项目的数据源、工具类;
- 安全层:可集成 Spring Security 实现权限控制(如限制 AI 只能读特定表),适配企业级安全需求。
二、Java 项目落地 MCP 实战:AI 调用本地 MySQL 生成销售报表
场景背景
你现有 Spring Boot 项目已集成 MySQL(销售数据)、POI(Excel 生成),现在要新增「AI 助手」功能,让用户通过自然语言查询销售数据并生成报表,要求:
- 标准化调用 MySQL,避免为 AI 写定制化 SQL 查询接口;
- 权限控制:AI 只能读
sales表,禁止执行 DELETE/UPDATE; - 兼容现有项目的数据源配置,不侵入核心业务代码。
步骤 1:架构设计(适配现有 Java 项目)

步骤 2:技术选型(基于 Java 生态)
- 核心依赖:JSON-RPC(
com.github.briandilley.jsonrpc4j:jsonrpc4j:1.6.0)、Spring Boot 2.7+、MySQL Connector、POI; - MCP 协议封装:自定义 MCP 消息体(兼容 MCP 标准);
- 通信方式:HTTP(复用现有项目的 Tomcat 容器)。
步骤 3:代码实现(完整可运行)
3.1 引入依赖(pom.xml)
<dependencies>
<!-- Spring Boot核心 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!-- JSON-RPC核心 -->
<dependency>
<groupId>com.github.briandilley.jsonrpc4j</groupId>
<artifactId>jsonrpc4j</artifactId>
<version>1.6.0</version>
</dependency>
<!-- MySQL驱动 -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
<!-- POI(Excel生成) -->
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId>
<version>5.2.5</version>
</dependency>
<!-- Jackson(JSON序列化) -->
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
</dependency>
</dependencies>
3.2 定义 MCP 核心模型(兼容 MCP 标准)
// MCP请求模型(JSON-RPC 2.0 + MCP扩展)
public class MCPRequest {
private String jsonrpc = "2.0";
private String id; // 请求ID,用于异步回调
private String method; // 调用方法,如"mysql/query"
private MCPParams params; // 调用参数
// getter/setter
}
// MCP参数模型
public class MCPParams {
private String sql; // SQL语句
private String dataSourceName; // 数据源名称(适配多数据源)
// 权限控制扩展字段
private List<String> allowedOperations; // 允许的操作:SELECT/INSERT等
// getter/setter
}
// MCP响应模型
public class MCPResponse {
private String jsonrpc = "2.0";
private String id;
private Object result; // 执行结果(List<Map<String, Object>>)
private MCPError error; // 错误信息
// getter/setter
}
// MCP错误模型
public class MCPError {
private int code;
private String message;
// getter/setter
}
3.3 实现 MCP Server(MySQL 适配,核心)
/**
* MCP Server:适配MySQL,处理AI的查询请求
* 集成现有项目的数据源,添加权限控制
*/
@RestController
@RequestMapping("/mcp/server/mysql")
public class MysqlMCPServer {
// 注入现有项目的数据源(复用原有配置)
@Autowired
private DataSource dataSource;
/**
* MCP调用入口:处理JSON-RPC格式的MySQL查询请求
*/
@PostMapping("/execute")
public ResponseEntity<MCPResponse> executeMysqlQuery(@RequestBody MCPRequest request) {
MCPResponse response = new MCPResponse();
response.setId(request.getId());
try {
// 1. 权限校验(核心:限制AI只能执行SELECT)
MCPParams params = request.getParams();
if (params == null || !params.getSql().trim().toUpperCase().startsWith("SELECT")) {
MCPError error = new MCPError();
error.setCode(-32602);
error.setMessage("AI仅允许执行SELECT查询,禁止修改数据");
response.setError(error);
return ResponseEntity.badRequest().body(response);
}
// 2. 执行SQL(复用现有项目的JDBC逻辑)
try (Connection conn = dataSource.getConnection();
PreparedStatement ps = conn.prepareStatement(params.getSql());
ResultSet rs = ps.executeQuery()) {
// 3. 结果转换为结构化数据(MCP标准返回)
List<Map<String, Object>> resultList = new ArrayList<>();
ResultSetMetaData metaData = rs.getMetaData();
int columnCount = metaData.getColumnCount();
while (rs.next()) {
Map<String, Object> row = new HashMap<>();
for (int i = 1; i <= columnCount; i++) {
row.put(metaData.getColumnName(i), rs.getObject(i));
}
resultList.add(row);
}
response.setResult(resultList);
return ResponseEntity.ok(response);
}
} catch (Exception e) {
MCPError error = new MCPError();
error.setCode(-32603);
error.setMessage("执行SQL失败:" + e.getMessage());
response.setError(error);
return ResponseEntity.internalServerError().body(response);
}
}
}
3.4 实现 MCP Client(调用 MCP Server)
/**
* MCP Client:标准化调用MCP Server
* 封装JSON-RPC请求,适配现有项目的HTTP调用
*/
@Component
public class MCPClient {
@Autowired
private RestTemplate restTemplate;
// MCP Server地址(可配置在application.yml)
private static final String MYSQL_MCP_SERVER_URL = "http://localhost:8080/mcp/server/mysql/execute";
/**
* 调用MCP Server执行MySQL查询
* @param sql 查询SQL
* @return 结构化查询结果
*/
public List<Map<String, Object>> callMysqlQuery(String sql) {
// 1. 构建MCP请求(JSON-RPC标准)
MCPRequest request = new MCPRequest();
request.setId(UUID.randomUUID().toString());
request.setMethod("mysql/query");
MCPParams params = new MCPParams();
params.setSql(sql);
params.setDataSourceName("sales-ds"); // 对应现有项目的数据源名称
params.setAllowedOperations(Collections.singletonList("SELECT"));
request.setParams(params);
// 2. 发送HTTP请求到MCP Server
MCPResponse response = restTemplate.postForObject(MYSQL_MCP_SERVER_URL, request, MCPResponse.class);
// 3. 处理响应
if (response == null || response.getError() != null) {
String errorMsg = response != null ? response.getError().getMessage() : "MCP Server无响应";
throw new RuntimeException("MCP调用失败:" + errorMsg);
}
return (List<Map<String, Object>>) response.getResult();
}
}
3.5 实现 Host 层(AI 助手业务逻辑)
/**
* Host层:AI助手核心逻辑
* 集成大模型+MCP Client+Excel生成,适配现有项目的业务流程
*/
@RestController
@RequestMapping("/ai/assistant")
public class AIAssistantController {
@Autowired
private MCPClient mcpClient;
// 大模型API(示例:可替换为本地LLM/企业级大模型)
private static final String LLM_API_URL = "https://api.openai.com/v1/chat/completions";
/**
* 用户入口:自然语言查询销售数据并生成报表
*/
@PostMapping("/sales-report")
public ResponseEntity<String> generateSalesReport(@RequestParam String userQuery) {
try {
// 1. 调用大模型,解析用户意图生成SQL(核心:将自然语言转为可执行的SQL)
String sql = generateSqlFromLLM(userQuery);
System.out.println("大模型生成的SQL:" + sql);
// 2. 通过MCP Client调用MySQL查询数据
List<Map<String, Object>> salesData = mcpClient.callMysqlQuery(sql);
// 3. 生成Excel报表(复用现有项目的POI逻辑)
String excelPath = generateExcelReport(salesData);
return ResponseEntity.ok("报表生成成功,路径:" + excelPath);
} catch (Exception e) {
return ResponseEntity.internalServerError().body("生成报表失败:" + e.getMessage());
}
}
/**
* 调用大模型生成SQL(示例:可替换为你项目中的大模型集成方式)
*/
private String generateSqlFromLLM(String userQuery) {
// 构建大模型提示词(引导生成标准化SQL)
String prompt = "你是Java项目的SQL生成助手,仅生成SELECT语句,数据源为sales表(字段:id, region, amount, sale_date)。" +
"用户需求:" + userQuery + ",请生成对应的MySQL SQL语句,只返回SQL,不要其他内容。";
// 调用大模型API(此处为简化示例,实际需集成你的大模型SDK)
// 替换为你项目中的大模型调用逻辑(如OpenAI/讯飞/本地LLM)
return "SELECT region, SUM(amount) AS total_amount FROM sales WHERE sale_date >= DATE_SUB(CURDATE(), INTERVAL 1 MONTH) AND region = '华东区' GROUP BY region";
}
/**
* 生成Excel报表(复用现有项目的POI工具)
*/
private String generateExcelReport(List<Map<String, Object>> data) throws Exception {
String filePath = "sales_report_" + System.currentTimeMillis() + ".xlsx";
XSSFWorkbook workbook = new XSSFWorkbook();
XSSFSheet sheet = workbook.createSheet("上月销售数据");
// 创建表头
XSSFRow headerRow = sheet.createRow(0);
headerRow.createCell(0).setCellValue("区域");
headerRow.createCell(1).setCellValue("总销售额");
// 填充数据
int rowNum = 1;
for (Map<String, Object> row : data) {
XSSFRow dataRow = sheet.createRow(rowNum++);
dataRow.createCell(0).setCellValue(row.get("region").toString());
dataRow.createCell(1).setCellValue(Double.parseDouble(row.get("total_amount").toString()));
}
// 写入文件(实际项目中可存储到OSS/本地目录)
FileOutputStream outputStream = new FileOutputStream(filePath);
workbook.write(outputStream);
workbook.close();
outputStream.close();
return filePath;
}
}
3.6 配置类(复用现有数据源)
@Configuration
public class MCPConfig {
// 配置RestTemplate(用于MCP Client的HTTP调用)
@Bean
public RestTemplate restTemplate() {
return new RestTemplate();
}
// 复用现有项目的数据源配置(此处为示例,实际使用你项目中的数据源)
@Bean
@ConfigurationProperties(prefix = "spring.datasource")
public DataSource dataSource() {
return DataSourceBuilder.create().build();
}
}
3.7 配置文件(application.yml)
spring:
datasource:
url: jdbc:mysql://localhost:3306/sales_db?useUnicode=true&characterEncoding=utf8&useSSL=false
username: root
password: your_password
driver-class-name: com.mysql.cj.jdbc.Driver
server:
port: 8080
步骤 4:测试与集成验证
- 启动 Spring Boot 项目,确保 MySQL 中
sales表有测试数据; - 调用接口:
POST http://localhost:8080/ai/assistant/sales-report?userQuery=查询上月华东区销售总额; - 预期结果:
- 大模型生成指定 SQL;
- MCP Client 调用 MCP Server 执行 SQL;
- 生成 Excel 报表,返回文件路径;
- 若尝试执行 DELETE SQL,MCP Server 会返回权限错误(符合安全控制要求)。
三、现有 Java 项目集成 MCP 的最佳实践
1. 非侵入式集成(优先推荐)
- 将 MCP Client/Server 封装为独立模块(Module),通过 Spring Boot Starter 引入现有项目;
- 复用现有数据源、权限框架(Spring Security)、日志体系,避免修改核心业务代码;
- MCP Server 与现有工具类(如 MySQLUtil、ExcelUtil)解耦,通过接口调用。
2. 权限与安全控制
- 在 MCP Server 层添加细粒度权限:按 AI 应用 / 用户限制可访问的表、字段;
- 增加操作审计:记录所有 MCP 调用的 SQL / 操作,适配企业合规要求;
- 限流降级:通过 Sentinel/Resilience4j 限制 MCP 调用频率,避免压垮数据库。
3. 扩展场景(适配不同工具)
- 适配 Redis:复制 MySQL MCP Server,修改为 Redis 操作(如
redis/get); - 适配本地文件:添加
file/read方法,限制文件读取路径; - 适配外部 API:添加
api/call方法,封装 HTTP 调用外部接口(如物流 API)。
总结
- MCP 核心原理:基于 JSON-RPC 2.0 的标准化 RPC 协议,将 AI 与外部工具的交互拆分为 Host(业务)、Client(协议封装)、Server(工具适配)三层,适配 Java 分层架构;
- Java 落地关键:复用现有生态(Spring Boot、JDBC、POI),将 MCP Server 封装为 Spring Bean,通过 RestTemplate 实现 Client 与 Server 的通信,重点做好权限控制;
- 集成原则:非侵入式接入现有项目,优先封装为独立模块,复用现有数据源、权限、日志体系,降低维护成本。
7377

被折叠的 条评论
为什么被折叠?



