RAG + Agent + X = 下一代智能代理框架。一个由个人独立开发完成的 AI Agent 全栈应用,深入实践 RAG 检索增强、多工具调用、MCP 扩展、提示词工程等核心 AI 技术。
| 应用 | 定位 | 核心能力 | 学习价值 |
|---|---|---|---|
| LoveApp(情感分析师) | 垂直领域 RAG 聊天机器人 | 检索增强、多轮对话、流式响应 | RAG 完整链路、提示词工程、文档处理 |
| YuManus(超级智能体) | 通用工具调用 Agent | 工具选择、任务分解、多步推理 | AI Agent 架构、工具调用链、MCP 扩展 |
- RAG 检索增强原理:从文档加载、向量化、存储到检索的完整流程
- AI Agent 设计模式:如何构建具备工具调用能力的智能体
- 提示词工程:如何通过精心设计的 Prompt 引导模型行为
- 多模型适配:同时支持云平台(DashScope)和本地模型(Ollama)
- MCP 服务扩展:自定义工具服务的制作与集成方法
核心流程: 文档加载 → 文本切分 → 向量化 → 向量存储 → 语义检索 → 上下文增强 → 生成回复
关键实现:
// 1. 自定义文档加载器 - 自动提取元数据
public List<Document> loadMarkdowns() {
Resource[] resources = resourcePatternResolver.getResources("classpath:document/*.md");
for (Resource resource : resources) {
// 从文件名提取标签(单身/恋爱/已婚)
String status = fileName.substring(fileName.length() - 6, fileName.length() - 4);
MarkdownDocumentReaderConfig config = MarkdownDocumentReaderConfig.builder()
.withAdditionalMetadata("status", status) // 注入状态标签
.build();
// ...
}
}// 2. 精准检索 - 支持状态过滤
Filter.Expression expression = new FilterExpressionBuilder()
.eq("status", status) // 按恋爱状态过滤文档
.build();
DocumentRetriever retriever = VectorStoreDocumentRetriever.builder()
.vectorStore(vectorStore)
.filterExpression(expression)
.similarityThreshold(0.5)
.topK(3)
.build();RAG 三种部署模式:
- 云 RAG: 基于 DashScope 云检索服务
- 自建向量库: 基于 PgVector 的私有化部署
- 自定义检索器: 支持过滤条件的精准检索
工具能力矩阵:
| 工具 | 功能 | 实现方式 |
|---|---|---|
FileOperationTool |
文件读写操作 | Java NIO |
SerperWebSearchTool |
网络搜索 | Serper API |
WebScrapingTool |
网页内容抓取 | Jsoup |
TerminalOperationTool |
终端命令执行 | ProcessBuilder |
PDFGenerationTool |
PDF 文档生成 | iText 库 |
ResourceDownloadTool |
资源下载 | HttpClient |
智能体决策流程:
sequenceDiagram
participant User as 用户
participant Agent as YuManus
participant LLM as LLM
participant Tools as ToolCallback[]
User->>Agent: 请求: "帮我搜索最新的AI新闻并保存"
Agent->>LLM: system_prompt + user_query
alt 需要调用工具
LLM-->>Agent: tool_call: {name: "web_search", params: {"query": "AI新闻"}}
Agent->>Tools: 执行 web_search
Tools-->>Agent: 返回搜索结果
Agent->>LLM: 用户请求 + 工具结果
LLM-->>Agent: tool_call: {name: "file_write", params: {...}}
Agent->>Tools: 执行 file_write
Tools-->>Agent: 保存成功
Agent->>LLM: 用户请求 + 所有工具结果
LLM-->>Agent: 总结回复
Agent-->>User: 任务完成总结
else 直接回答
LLM-->>Agent: 直接生成回答
Agent-->>User: 回复内容
end
MCP(Model Context Protocol) 是 Spring AI 提供的工具扩展协议,允许将工具部署为独立服务。
项目中的 MCP Server:
ynwe-image-search-mcp-server - 图像搜索 MCP 服务
├── src/main/java/com/ynwe/ynweimagesearchmcpserver/
│ ├── tools/
│ │ └── ImageSearchTool.java # 图像搜索工具实现
│ └── YnweImageSearchMcpServerApplication.java # MCP 服务入口
└── src/main/resources/
├── application-sse.yml # SSE 模式配置
└── application-stdio.yml # STDIO 模式配置
MCP 客户端集成:
@Resource
private ToolCallbackProvider toolCallbackProvider;
public String doChatWithMcp(String message, String chatId) {
ChatResponse response = chatClient
.prompt()
.user(message)
.tools(toolCallbackProvider) // 自动发现 MCP 工具
.call()
.chatResponse();
return response.getResult().getOutput().getText();
}项目支持两种模型调用方式:
| 模式 | 配置 | 适用场景 |
|---|---|---|
| 云平台模型 | DashScope API | 生产环境、需要高性能模型 |
| 本地模型 | Ollama + Gemma3 | 隐私敏感、离线部署 |
配置切换:
spring:
ai:
ollama:
base-url: http://localhost:11434
chat:
model: gemma3n:e4b
enabled: false # 关闭本地模型
dashscope:
api-key: ${DASHSCOPE_API_KEY} # 云平台 API Key代码层面的抽象:
public LoveApp(ChatModel dashscopeChatModel) {
// ChatModel 是 Spring AI 统一接口
// 无论是 DashScope 还是 Ollama,使用方式完全一致
chatClient = ChatClient.builder(dashscopeChatModel)
.defaultSystem(SYSTEM_PROMPT)
.build();
}LoveApp 系统提示词设计:
private static final String SYSTEM_PROMPT = "扮演深耕恋爱心理领域的专家。开场向用户表明身份,告知用户可倾诉恋爱难题。" +
"围绕单身、恋爱、已婚三种状态提问:单身状态询问社交圈拓展及追求心仪对象的困扰;" +
"恋爱状态询问沟通、习惯差异引发的矛盾;已婚状态询问家庭责任与亲属关系处理的问题。" +
"引导用户详述事情经过、对方反应及自身想法,以便给出专属解决方案。";提示词设计原则:
- 角色定位:明确 AI 的身份和专业领域
- 任务描述:清晰说明要执行的任务
- 约束条件:定义边界和规则
- 输出格式:指定期望的响应格式
YuManus 工具调用提示词:
String NEXT_STEP_PROMPT = """
Based on user needs, proactively select the most appropriate tool or combination of tools.
For complex tasks, you can break down the problem and use different tools step by step to solve it.
After using each tool, clearly explain the execution results and suggest the next steps.
If you want to stop the interaction at any point, use the `terminate` tool/function call.
""";AI 框架: Spring AI 1.0.0-M6
大模型: 阿里云百炼 DashScope | Ollama (Gemma3)
向量数据库: PostgreSQL + PgVector (HNSW 索引)
后端: Spring Boot 3.4.9 + Java 21
前端: Vue 3 + Vite 4 + Vue Router
工具链: 文件操作 | 网页搜索 | 网页抓取 | 终端执行 | PDF生成
扩展机制: MCP Server
sequenceDiagram
participant User as 用户
participant Frontend as 前端
participant Controller as AiController
participant LoveApp as LoveApp
participant VectorDB as PgVector
participant LLM as DashScope/Ollama
User->>Frontend: 输入恋爱问题
Frontend->>Controller: GET /api/ai/love_app/chat/sse
Controller->>LoveApp: doChatByStream(message, chatId)
LoveApp->>LoveApp: 从 FileBasedChatMemory 获取对话历史
LoveApp->>VectorDB: search_similar(query_vector, filter="恋爱")
VectorDB-->>LoveApp: 返回 topK=3 相关文档
LoveApp->>LLM: Prompt = {SYSTEM_PROMPT + 历史 + 检索文档 + 用户问题}
LLM-->>LoveApp: 流式 Token 响应
loop 逐块返回
LoveApp-->>Controller: Flux<String>
Controller-->>Frontend: SSE Event Stream
Frontend-->>User: 实时显示
end
- JDK 21 - 必须使用 Java 21
- PostgreSQL 15+ - 安装 pgvector 扩展
- Ollama (可选) - 本地模型支持
- DashScope API Key - 阿里云百炼 API Key
# 1. 创建数据库
psql -c "CREATE DATABASE ynwe_ai_agent; CREATE EXTENSION vector;"
# 2. 配置环境变量
export DASHSCOPE_API_KEY=your-api-key
export SERPER_API_KEY=your-serper-key
# 3. 启动后端
cd ynwe-ai-agent
mvn spring-boot:run
# 4. 启动前端
cd yu-ai-agent-frontend
npm install && npm run dev
# 5. (可选) 启动 MCP Server
cd ynwe-image-search-mcp-server
mvn spring-boot:run| 端点 | 方法 | 描述 |
|---|---|---|
/api/ai/love_app/chat/sync |
GET | 情感分析师同步问答 |
/api/ai/love_app/chat/sse |
GET | 情感分析师流式问答 |
/api/ai/manus/chat |
GET | 超级智能体问答 |
/api/swagger-ui.html |
GET | API 文档 |
如果你想系统学习这个项目中的 AI 技术:
- 基础篇: 理解
LoveApp的核心逻辑,掌握 RAG 的基本概念 - 进阶篇: 研究
YuManus的工具调用机制,学习 AI Agent 设计 - 扩展篇: 尝试制作自己的 MCP 服务,扩展工具能力
- 实践篇: 修改提示词,观察模型行为变化
如果这个项目对你有帮助,请给个支持的 star!谢谢 ⭐️