|
|
@@ -0,0 +1,542 @@
|
|
|
+# Dify 替代迁移可行性分析
|
|
|
+
|
|
|
+> 版本:v1.0
|
|
|
+> 日期:2026-07-20
|
|
|
+> 范围:cfc-backend (Spring Boot 2.7.18 / Java 8) + 前端 + 运营后台
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+## 目录
|
|
|
+
|
|
|
+1. [背景与现状](#1-背景与现状)
|
|
|
+2. [Dify 依赖全景](#2-dify-依赖全景)
|
|
|
+3. [替代方案评估矩阵](#3-替代方案评估矩阵)
|
|
|
+4. [推荐方案:模块化混合替换](#4-推荐方案模块化混合替换)
|
|
|
+5. [分阶段实施计划](#5-分阶段实施计划)
|
|
|
+6. [风险评估与应对](#6-风险评估与应对)
|
|
|
+7. [成本收益分析](#7-成本收益分析)
|
|
|
+8. [决策树](#8-决策树)
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+## 1. 背景与现状
|
|
|
+
|
|
|
+### 1.1 项目技术栈
|
|
|
+
|
|
|
+| 模块 | 技术栈 | 版本限制 |
|
|
|
+|------|--------|---------|
|
|
|
+| 后端 | Spring Boot + Java 8 | JDK 1.8,**无法升级至 17+** |
|
|
|
+| ORM | MyBatis-Plus | — |
|
|
|
+| 数据库 | MySQL 8.0 | 无向量检索能力 |
|
|
|
+| AI 平台 | Dify 自部署 | `http://dify.bianwoyou.cn/v1` |
|
|
|
+| 服务端 | 国内自建服务器 | 需国产 LLM API 合规 |
|
|
|
+
|
|
|
+### 1.2 Dify 接入现状
|
|
|
+
|
|
|
+Dify 在项目中承担 **AI 能力中间件** 角色,并非核心业务系统,但深度嵌入 8 个 Service、3 个 Controller:
|
|
|
+
|
|
|
+```
|
|
|
+Dify 能力 项目消费者 依赖深度
|
|
|
+────────────────────────────────────────────────────────────────────
|
|
|
+Chatbot API AIService.sendMessage() ⭐⭐⭐ 核心
|
|
|
+ AIService.sendNutritionMessage() ⭐⭐⭐ 核心
|
|
|
+ ArticleService.getAiQuestions() ⭐⭐ 功能
|
|
|
+Workflow API AIService.runWorkflow() ⭐⭐⭐ 核心
|
|
|
+ AIService.sendTongueDiagnosis() ⭐⭐ 可替换
|
|
|
+ AIService.requestSummaryAsync() ⭐⭐ 可替换
|
|
|
+ WisdomMathService.verifyAnswer() ⭐ 已有兜底
|
|
|
+Datasets API DifySyncService.syncToDify() ⭐⭐ 可替换
|
|
|
+ DifySyncService.removeFromDify() ⭐ 低频
|
|
|
+会话管理 AIService.getConversations() ⭐ 已有本地镜像
|
|
|
+ AIService.getMessages() ⭐ 已有本地镜像
|
|
|
+```
|
|
|
+
|
|
|
+### 1.3 关键发现
|
|
|
+
|
|
|
+- **已有本地镜像层**:`ChatMirrorService` 已完成 Dify 会话和消息的本地存储
|
|
|
+- **已有降级机制**:舌诊 mock、数学判题 eval、会话列表回退
|
|
|
+- **Java 8 限制**:Spring AI(需 Boot 3.x)、LangChain4j starter(需 Boot 3.x)不可用
|
|
|
+- **Dify 运维成本**:单独部署维护,版本升级带来兼容风险
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+## 2. Dify 依赖全景
|
|
|
+
|
|
|
+### 2.1 代码依赖映射
|
|
|
+
|
|
|
+```
|
|
|
+┌─────────────────────────────────────────────────────────────────┐
|
|
|
+│ AIService (523 行) │
|
|
|
+│ Dify API 的核心抽象,8 个公共方法 │
|
|
|
+├─────────────────────────────────────────────────────────────────┤
|
|
|
+│ │
|
|
|
+│ ┌─ sendMessage() ─────────── Dify Chatbot (通用助手) │
|
|
|
+│ ├─ sendNutritionMessage() ── Dify Chatbot (营养助手, 独立 Key) │
|
|
|
+│ ├─ sendTongueDiagnosis() ─── Dify Workflow (舌诊) │
|
|
|
+│ ├─ runWorkflow() ─────────── Dify Workflow (通用) │
|
|
|
+│ ├─ requestSummaryAsync() ─── Dify Workflow (摘要生成) │
|
|
|
+│ ├─ getConversations() ────── Dify REST API (会话列表) │
|
|
|
+│ ├─ getMessages() ─────────── Dify REST API (消息历史) │
|
|
|
+│ └─ deleteConversation() ──── Dify REST API (删除会话) │
|
|
|
+│ │
|
|
|
+└──────────────────────┬──────────────────────────────────────────┘
|
|
|
+ │ 被以下服务调用
|
|
|
+ ▼
|
|
|
+┌──────────┬──────────┬──────────┬──────────┬──────────┬──────────┐
|
|
|
+│AIChat │Butler │Article │Meal │Wisdom │Tongue │
|
|
|
+│Controller│Controller│Service │Recommend │MathService│Diagnosis │
|
|
|
+│ │ │ │Service │ │Service │
|
|
|
+└──────────┴──────────┴──────────┴──────────┴──────────┴──────────┘
|
|
|
+```
|
|
|
+
|
|
|
+### 2.2 数据表依赖
|
|
|
+
|
|
|
+| 表名 | 用途 | 迁移影响 |
|
|
|
+|------|------|---------|
|
|
|
+| `chat_conversations` | Dify 会话本地镜像 | 保留,转正为主数据源 |
|
|
|
+| `chat_messages` | Dify 消息本地镜像 | 保留,转正为主数据源 |
|
|
|
+| `ai_conversation_summary` | AI 生成的对话摘要 | 保留,来源从 Dify Workflow 改为本地 LLM |
|
|
|
+| `ai_user_facts` | AI 提取的用户关键事实 | 保留,来源从 Dify Workflow 改为本地 LLM |
|
|
|
+| `butler_sessions` | AI 管家会话 | 保留,移除 conversation_id 的 Dify 依赖 |
|
|
|
+| `product_dimension_config.dify_dataset_id` | 维度 → Dify 数据集 | 移除,改用本地向量检索 |
|
|
|
+| `dan_knowledge_base*` | 知识库 | 保留,同步目标从 Dify 改为本地 |
|
|
|
+
|
|
|
+### 2.3 不可替换的组件(需保留等价能力)
|
|
|
+
|
|
|
+| Dify 组件 | 等价能力需求 |
|
|
|
+|-----------|-------------|
|
|
|
+| LLM 反向代理 | HTTP 调用 LLM API |
|
|
|
+| System Prompt 管理 | 多套 System Prompt 配置 |
|
|
|
+| 上下文注入 | 已有 `FamilyContextService` |
|
|
|
+| 知识库检索 | 向量检索 + 相似度排序 |
|
|
|
+| 多步 Workflow | Java 服务链编排 |
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+## 3. 替代方案评估矩阵
|
|
|
+
|
|
|
+### 3.1 Java 生态方案
|
|
|
+
|
|
|
+| 方案 | 类型 | 与 Java 集成 | 可视化 Workflow | 知识库 RAG | 运维成本 | 综合得分 |
|
|
|
+|-----|------|-------------|----------------|-----------|---------|---------|
|
|
|
+| **D. 模块化混合替换** | Java + API | ⭐⭐⭐⭐⭐ 原生 | ❌ 代码编排 | ⭐⭐⭐ 自建 | ⭐⭐⭐⭐⭐ 极低 | **🥇 9/10** |
|
|
|
+| A. 直接 LLM API | Java 嵌入 | ⭐⭐⭐⭐⭐ 原生 | ❌ 代码编排 | ⭐⭐ 需自建 | ⭐⭐⭐⭐⭐ 极低 | 🥈 8/10 |
|
|
|
+| FastGPT 替代 | 平台 | ⭐⭐⭐ HTTP | ✅ 可视化 | ⭐⭐⭐⭐ 强 | ⭐⭐ 中 | 5/10 |
|
|
|
+| LangChain4j | Java 库 | ⭐⭐⭐ 部分兼容 | ❌ | ⭐⭐⭐ 内置 | ⭐⭐⭐⭐ 低 | 5/10 |
|
|
|
+| Spring AI | Java 框架 | ❌ 需 Boot 3.x | ❌ | ⭐⭐ | ❌ 不可用 | 0/10 |
|
|
|
+
|
|
|
+### 3.2 Python 生态方案
|
|
|
+
|
|
|
+| 方案 | 类型 | 集成方式 | 定位匹配度 | 运维成本 | 适合本项目? | 综合得分 |
|
|
|
+|-----|------|---------|-----------|---------|------------|---------|
|
|
|
+| **LangChain (Python)** | LLM 框架 | 独立服务 HTTP | ⭐⭐⭐ | ⭐⭐ 中 | ⚠️ 有条件可行 | 6/10 |
|
|
|
+| LangGraph | Workflow 框架 | 独立服务 HTTP | ⭐⭐ | ⭐ 高 | ❌ 不推荐 | 3/10 |
|
|
|
+| OpenClaw (小龙虾) | Agent 运行时 | 独立服务 | ⭐ | ⭐ 高 | ❌ 定位不匹配 | 2/10 |
|
|
|
+
|
|
|
+### 3.3 Python 方案详细分析
|
|
|
+
|
|
|
+#### LangChain (Python)
|
|
|
+
|
|
|
+| 评估项 | 说明 |
|
|
|
+|--------|------|
|
|
|
+| **部署形式** | 额外的 Python 服务进程,与 Java 后端通过 HTTP 通信 |
|
|
|
+| **可复用的项目资产** | `FamilyContextService`(上下文组装)、`ChatMirrorService`(持久化)需保留在 Java 侧 |
|
|
|
+| **需要新开发的** | FastAPI 网关层、Python 侧 Agent/RAG 逻辑、双语言监控告警 |
|
|
|
+| **运维新增** | Python 运行时管理、pip 依赖管理、进程守护、跨语言排查 |
|
|
|
+| **团队要求** | 需要 Python 工程师维护 AI 服务层 |
|
|
|
+
|
|
|
+**适合场景**:团队有 Python 工程师、AI 侧需要频繁实验(Prompt 调优、RAG 策略测试)、愿意接受多语言栈运维。
|
|
|
+
|
|
|
+**不适合场景**:纯 Java 团队、运维人力紧张、对延迟敏感(每增加一次 HTTP 中转增加 10-50ms)。
|
|
|
+
|
|
|
+#### LangGraph
|
|
|
+
|
|
|
+LangGraph 是 LangChain 生态中专门做有状态 Agent 编排的框架。如果当前 Dify Workflow 的复杂编排是核心痛点,LangGraph 可以提供代码级等价能力。但:
|
|
|
+
|
|
|
+- **学习曲线极其陡峭** — StateGraph、Node/Edge 抽象、条件路由
|
|
|
+- **额外的复杂度** — 一个 Python 方案中再嵌套一个复杂框架
|
|
|
+- **如果不需要复杂 Workflow**,LangGraph 就是过度设计
|
|
|
+
|
|
|
+本项目当前的 Workflow 使用(舌诊分析、对话摘要、事实提取、数学判题)**都不超过 3 个节点**,完全可以用 Java 直接实现。
|
|
|
+
|
|
|
+#### 小龙虾 (OpenClaw / 皮皮虾 / Nanobot)
|
|
|
+
|
|
|
+OpenClaw 生态(包括国产衍生产品 PP-Claw 皮皮虾、网易 LobsterAI、Nanobot 等)的本质是 **个人 AI 助手运行时**,而不是 **面向终端用户的 AI 应用平台**。
|
|
|
+
|
|
|
+| OpenClaw 能力 | 本项目需求 | 匹配度 |
|
|
|
+|--------------|-----------|--------|
|
|
|
+| IM 渠道接入 (飞书/钉钉/企微) | ❌ 不需要(有前端页面) | ❌ |
|
|
|
+| 文件/Shell/代码执行 | ❌ 不需要(AI 只做推理) | ❌ |
|
|
|
+| 持续后台运行 | ❌ 不需要(请求-响应模式) | ❌ |
|
|
|
+| 多 LLM Provider 切换 | ✅ 需要 | ⭐⭐ 非核心诉求 |
|
|
|
+| Chatbot API | ❌ 不提供标准 API | ❌ |
|
|
|
+| 知识库 RAG | ❌ 弱 | ❌ |
|
|
|
+| 可视化 Workflow | ❌ 无 | ❌ |
|
|
|
+
|
|
|
+OpenClaw 的流行不代表它适合替换 Dify。两者定位完全不同:
|
|
|
+
|
|
|
+> Dify = 给开发者用的 **AI 应用后端平台**
|
|
|
+> OpenClaw = 给终端用户用的 **AI 个人助手**
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+## 4. 推荐方案:模块化混合替换
|
|
|
+
|
|
|
+### 4.1 架构演进
|
|
|
+
|
|
|
+```
|
|
|
+当前架构:
|
|
|
+┌─────────────────────────────────────────────────────────────┐
|
|
|
+│ Frontend │
|
|
|
+│ chat.vue → AIChatController → AIService → Dify → LLM API │
|
|
|
+└─────────────────────────────────────────────────────────────┘
|
|
|
+
|
|
|
+目标架构:
|
|
|
+┌─────────────────────────────────────────────────────────────┐
|
|
|
+│ Frontend │
|
|
|
+│ chat.vue → AIChatController → LLMService │
|
|
|
+│ ├─ DeepSeekLLMService │
|
|
|
+│ ├─ RAGService (pgvector) │
|
|
|
+│ └─ ContextStrategy │
|
|
|
+│
|
|
|
+│ 本地持久化:ChatMirrorService (转正) │
|
|
|
+│ 本地记忆:AiConversationSummary + AiUserFact (来源替换) │
|
|
|
+│ 本地推荐:RecommendationService (已有) │
|
|
|
+└─────────────────────────────────────────────────────────────┘
|
|
|
+```
|
|
|
+
|
|
|
+### 4.2 核心替换策略
|
|
|
+
|
|
|
+#### 4.2.1 新增接口层
|
|
|
+
|
|
|
+```java
|
|
|
+// 新增抽象接口,AIService 改为其中一个实现
|
|
|
+public interface LLMService {
|
|
|
+ ChatResult sendChat(ChatRequest request);
|
|
|
+ ChatResult sendChatWithStream(ChatRequest request);
|
|
|
+ String getProviderName();
|
|
|
+ boolean isAvailable();
|
|
|
+}
|
|
|
+
|
|
|
+// Dify 实现(保留作降级通道)
|
|
|
+@Component
|
|
|
+public class DifyLLMService implements LLMService { ... }
|
|
|
+
|
|
|
+// 直接 LLM API 实现(主通道)
|
|
|
+@Component
|
|
|
+@Primary
|
|
|
+public class DirectLLMService implements LLMService {
|
|
|
+ // 调用 DeepSeek / Qwen / GLM 的 /v1/chat/completions
|
|
|
+}
|
|
|
+```
|
|
|
+
|
|
|
+#### 4.2.2 System Prompt 外部化
|
|
|
+
|
|
|
+从 Dify 应用配置迁移到本地:
|
|
|
+
|
|
|
+```yaml
|
|
|
+# application.yml
|
|
|
+ai:
|
|
|
+ assistants:
|
|
|
+ family:
|
|
|
+ system-prompt: "你是一个家庭成长助手..."
|
|
|
+ model: "deepseek-chat"
|
|
|
+ temperature: 0.7
|
|
|
+ max-tokens: 2048
|
|
|
+ nutrition:
|
|
|
+ system-prompt: "你是一个精准营养分析专家..."
|
|
|
+ model: "deepseek-chat"
|
|
|
+ temperature: 0.5
|
|
|
+ max-tokens: 4096
|
|
|
+ tongue:
|
|
|
+ system-prompt: "你是一个中医舌诊专家..."
|
|
|
+ model: "qwen-vl-max" # 多模态
|
|
|
+ temperature: 0.3
|
|
|
+```
|
|
|
+
|
|
|
+#### 4.2.3 Workflow 拆解
|
|
|
+
|
|
|
+| 当前 Dify Workflow | 替换方式 | 工作量 |
|
|
|
+|--------------------|---------|--------|
|
|
|
+| 舌诊分析 | 直接调 Qwen-VL API + 结构化输出解析 | 0.5 天 |
|
|
|
+| 对话摘要生成 | `ChatSummaryService` 定时调用 LLM | 1 天 |
|
|
|
+| 事实提取 | `FactExtractionService` 结构化 Prompt 解析 | 0.5 天 |
|
|
|
+| 数学判题 | 已有 Eval 兜底,永久化 | 0 天 |
|
|
|
+| 食谱推荐 | 直接调 LLM API + `MealRecommendService` 聚合上下文 | 0.5 天 |
|
|
|
+
|
|
|
+#### 4.2.4 知识库 RAG 本地化
|
|
|
+
|
|
|
+```
|
|
|
+当前:管理端创建知识点 → DifySyncService → Dify Datasets → Dify 检索
|
|
|
+替换后:管理端创建知识点 → TextEmbeddingService → pgvector (或 sqlite-vec) → 相似度检索
|
|
|
+```
|
|
|
+
|
|
|
+**向量方案选择:**
|
|
|
+
|
|
|
+| 方案 | 说明 | 推荐度 |
|
|
|
+|------|------|--------|
|
|
|
+| **sqlite-vec** | 纯 SQLite 扩展,零运维,适合知识量 < 10 万条 | ⭐⭐⭐ 首选 |
|
|
|
+| 独立 pgvector | PostgreSQL 插件,需新建 PG 实例 | ⭐⭐ 次选 |
|
|
|
+| 阿里云 AnalyticDB | 托管向量库,免运维 | ⭐⭐ 适合云上 |
|
|
|
+| Milvus / Qdrant | 专业向量库,太重 | ❌ |
|
|
|
+
|
|
|
+**推荐 sqlite-vec 理由**:项目当前使用 MySQL,无法做向量检索。sqlite-vec 作为一个零配置的 SQLite 扩展,可以独立运行,不需要额外部署服务。适合当前几千条知识库的规模。
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+## 5. 分阶段实施计划
|
|
|
+
|
|
|
+### 阶段 1:基础设施(1 周)
|
|
|
+
|
|
|
+**目标**:建立 LLMService 抽象层,核心对话不再依赖 Dify
|
|
|
+
|
|
|
+```
|
|
|
+Week 1
|
|
|
+├── Day 1-2: LLMService 接口 + DirectLLMService 实现
|
|
|
+│ ├── 接口定义 (sendChat / streamChat / isAvailable)
|
|
|
+│ ├── DeepSeek API 适配
|
|
|
+│ ├── Qwen API 适配
|
|
|
+│ └── AIService 改为 DifyLLMService 实现
|
|
|
+├── Day 3: System Prompt 迁移
|
|
|
+│ ├── 从 Dify 导出所有 System Prompt
|
|
|
+│ ├── 配置到 application.yml
|
|
|
+│ └── Strategy Router 实现多 Assistant 路由
|
|
|
+├── Day 4: 上下文注入改造
|
|
|
+│ ├── FamilyContextService → ContextBuilder 接口
|
|
|
+│ └── Prompt 拼接逻辑替换 Dify inputs 注入
|
|
|
+└── Day 5: 健康检查 + 降级
|
|
|
+ ├── LLMService 健康检查
|
|
|
+ ├── DirectLLMService 不可用时自动降级到 DifyLLMService
|
|
|
+ └── 单元测试 + 集成测试
|
|
|
+```
|
|
|
+
|
|
|
+**产出**:
|
|
|
+- `LLMService.java` 接口 + 2 个实现类
|
|
|
+- `AssistantConfig` 配置体系
|
|
|
+- `ContextBuilder.java` 独立接口
|
|
|
+- 降级机制
|
|
|
+
|
|
|
+**验证标准**:
|
|
|
+- `POST /api/ai/chat/send` 响应 ≤ 2s (P95)
|
|
|
+- 会话历史、记忆层功能正常
|
|
|
+- Dify 停服时自动降级到 DeepSeek
|
|
|
+
|
|
|
+### 阶段 2:Workflow 拆解(1 周)
|
|
|
+
|
|
|
+**目标**:去掉所有 Dify Workflow 依赖
|
|
|
+
|
|
|
+```
|
|
|
+Week 2
|
|
|
+├── Day 1: 舌诊 Workflow → Qwen-VL
|
|
|
+│ ├── 新增 QwenVLService (多模态 API)
|
|
|
+│ ├── TongueDiagnosisService 迁移
|
|
|
+│ └── 移除 mock 数据逻辑
|
|
|
+├── Day 2: 对话摘要 + 事实提取
|
|
|
+│ ├── ChatSummaryService (定时 + 触发双模式)
|
|
|
+│ ├── FactExtractionService (结构化 Prompt)
|
|
|
+│ └── AIService.requestSummaryAsync → 新实现
|
|
|
+├── Day 3: 数学判题 → Eval 永久化
|
|
|
+│ ├── WisdomMathService verifyMode 默认改为 eval
|
|
|
+│ └── 移除 Dify workflow-id 配置依赖
|
|
|
+├── Day 4: 食谱推荐 → LLM 直调
|
|
|
+│ └── MealRecommendService 改为调用 DirectLLMService
|
|
|
+└── Day 5: 文章测验 + 标签生成
|
|
|
+ ├── ArticleService.getAiQuestions → 直调 LLM
|
|
|
+ └── ArticleService.autoGenerateTags → 直调 LLM
|
|
|
+```
|
|
|
+
|
|
|
+**产出**:
|
|
|
+- 5 个新的/改造的 Service
|
|
|
+- 移除所有 Workflow 调用代码
|
|
|
+
|
|
|
+**验证标准**:
|
|
|
+- 舌诊分析准确率 ≥ 当前 Dify Workflow
|
|
|
+- 数学判题 100% 可用(已用 eval 兜底)
|
|
|
+- 对话摘要能在 3 秒内生成
|
|
|
+
|
|
|
+### 阶段 3:知识库 RAG 本地化(1 周)
|
|
|
+
|
|
|
+**目标**:去掉 Dify Datasets 依赖
|
|
|
+
|
|
|
+```
|
|
|
+Week 3
|
|
|
+├── Day 1-2: 向量检索基础设施
|
|
|
+│ ├── sqlite-vec 集成
|
|
|
+│ ├── EmbeddingService (调用 BGE/bge-large-zh 或 API)
|
|
|
+│ └── RAGService (检索 + 重排序 + 上下文注入)
|
|
|
+├── Day 3: 知识库同步改造
|
|
|
+│ ├── DifySyncService → LocalKBService
|
|
|
+│ ├── 保存知识时自动向量化
|
|
|
+│ └── 管理端接口不变
|
|
|
+├── Day 4: 知识库检索替换
|
|
|
+│ ├── RecommendationService.searchViaDify → searchViaLocal
|
|
|
+│ └── 注入 LLM 上下文
|
|
|
+└── Day 5: 清理
|
|
|
+ ├── 删除 Dify 相关配置
|
|
|
+ ├── 删除 DifySyncService
|
|
|
+ ├── AIService 中移除 Dify 方法(或标记 Deprecated)
|
|
|
+ └── 端到端回归测试
|
|
|
+```
|
|
|
+
|
|
|
+**产出**:
|
|
|
+- `RAGService.java`
|
|
|
+- `EmbeddingService.java`
|
|
|
+- `LocalKBService.java`(替代 DifySyncService)
|
|
|
+- sqlite-vec 向量库初始化
|
|
|
+
|
|
|
+**验证标准**:
|
|
|
+- 知识库检索召回率 ≥ Dify Datasets
|
|
|
+- 管理端 CRUD 功能完全一致
|
|
|
+- 端到端回归测试通过
|
|
|
+
|
|
|
+### 阶段 4:收尾(3 天)
|
|
|
+
|
|
|
+```
|
|
|
+Week 4
|
|
|
+├── Day 1: 配置清理
|
|
|
+│ ├── application.yml 移除 dify.* 配置
|
|
|
+│ ├── DatabaseInitializer 移除 Dify 相关迁移
|
|
|
+│ └── schema.sql 确认表结构
|
|
|
+├── Day 2: 代码清理
|
|
|
+│ ├── 删除 DifySyncService.java
|
|
|
+│ ├── AIService.java 简化(移除 Dify 方法)
|
|
|
+│ └── 全局搜索 dify 引用,确认无残留
|
|
|
+└── Day 3: 文档 + 部署
|
|
|
+ ├── 更新 数据与AI结合技术方案.md
|
|
|
+ ├── 部署文档更新
|
|
|
+ └── Dify 服务器下线确认
|
|
|
+```
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+## 6. 风险评估与应对
|
|
|
+
|
|
|
+### 6.1 风险矩阵
|
|
|
+
|
|
|
+| 风险 | 概率 | 影响 | 应对措施 |
|
|
|
+|------|------|------|---------|
|
|
|
+| DeepSeek/Qwen API 不稳定 | 中 | 高 | 多 Provider 自动切换 + 本地降级回复 |
|
|
|
+| LLM API 费用超预期 | 中 | 中 | Token 用量监控 + 缓存策略 + Prompt 压缩 |
|
|
|
+| sqlite-vec 检索质量低于 Dify | 低 | 中 | Hybrid Search (向量 + 关键词) + 重排序 Reranker |
|
|
|
+| 团队不熟悉新架构 | 低 | 中 | 增量迁移,保持 Dify 降级通道 1 个月 |
|
|
|
+| 迁移期间 Dify 出问题 | 低 | 高 | 阶段 1 先建好降级机制再动 |
|
|
|
+
|
|
|
+### 6.2 回退计划
|
|
|
+
|
|
|
+每个阶段都是**可逆的**:
|
|
|
+
|
|
|
+```
|
|
|
+阶段 1 回退:切换 LLMService 的 @Primary 回到 DifyLLMService
|
|
|
+阶段 2 回退:恢复 AIService 的 Workflow 调用
|
|
|
+阶段 3 回退:DifySyncService 仍保留,只是不再主动调用
|
|
|
+阶段 4 回退:保留 Dify 配置,不清理
|
|
|
+```
|
|
|
+
|
|
|
+### 6.3 不在范围内的
|
|
|
+
|
|
|
+- 前端 chat.vue 不改动(只改后端 API 响应)
|
|
|
+- AI 记忆层数据结构不改动(`ai_conversation_summary`、`ai_user_facts` 表不变)
|
|
|
+- Dify 服务器暂不下线(保留 1 个月观察期)
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+## 7. 成本收益分析
|
|
|
+
|
|
|
+### 7.1 开发成本
|
|
|
+
|
|
|
+| 阶段 | 人天 | 说明 |
|
|
|
+|------|------|------|
|
|
|
+| 阶段 1:基础设施 | 5 人天 | LLMService 抽象、System Prompt 迁移、降级机制 |
|
|
|
+| 阶段 2:Workflow 拆解 | 5 人天 | 舌诊/摘要/事实提取/食谱/文章 5 个模块 |
|
|
|
+| 阶段 3:知识库 RAG | 5 人天 | sqlite-vec、Embedding、知识库同步 |
|
|
|
+| 阶段 4:收尾清理 | 3 人天 | 配置/代码/文档清理 |
|
|
|
+| **合计** | **18 人天** | 约 3-4 周 |
|
|
|
+
|
|
|
+### 7.2 运维成本变化
|
|
|
+
|
|
|
+| 项目 | 迁移前 | 迁移后 | 变化 |
|
|
|
+|------|--------|--------|------|
|
|
|
+| Dify 服务器 | 2C4G 云服务器 | 移除 | **节省** |
|
|
|
+| Dify 维护 | 版本升级、Docker 运维 | 零 | **节省** |
|
|
|
+| LLM API 费用 | 透传(不变) | 不变 | 持平 |
|
|
|
+| 向量库 | 无 | sqlite-vec (零运维) | 新增但极低 |
|
|
|
+| Python 服务 | 无 | 无(全部 Java) | 零 |
|
|
|
+
|
|
|
+**直接节省**:至少 1 台云服务器的费用(按 2C4G 约 ¥200-400/月)+ 运维时间。
|
|
|
+
|
|
|
+### 7.3 性能收益
|
|
|
+
|
|
|
+| 指标 | 迁移前(经 Dify) | 迁移后(直调) | 提升 |
|
|
|
+|------|-----------------|---------------|------|
|
|
|
+| 请求延迟(P50) | ~800ms + Dify 中转 | ~600ms | -25% |
|
|
|
+| 请求延迟(P95) | ~2.5s | ~1.8s | -28% |
|
|
|
+| 故障点 | Java + Dify + LLM | Java + LLM | 减少 1 个 |
|
|
|
+| HTTP 跳转 | 2 跳(Java→Dify→LLM) | 1 跳(Java→LLM) | 减半 |
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+## 8. 决策树
|
|
|
+
|
|
|
+```
|
|
|
+需要替换 Dify?
|
|
|
+│
|
|
|
+├─ 是,彻底替换 ──────────────────────────→ 方案 D:模块化混合替换(18 人天)
|
|
|
+│
|
|
|
+├─ 是,但团队有 Python 工程师 ─────────────→ 方案 D + Python LangChain AI 服务层
|
|
|
+│ (Java 做业务层,Python 做 AI 层)
|
|
|
+│
|
|
|
+├─ 否,只想降低成本 ──────────────────────→ 保留 Dify,优化措施:
|
|
|
+│ ① 合并 API Key(3→1)
|
|
|
+│ ② Dify 降配服务器
|
|
|
+│ ③ 增强 ChatMirrorService 本地兜底
|
|
|
+│
|
|
|
+├─ 否,但担心 Dify 不可用 ────────────────→ 降级通道方案(1 周):
|
|
|
+│ ① LLMService 接口 + DirectLLMService
|
|
|
+│ ② Dify 作为降级(主直调,Dify 备用)
|
|
|
+│ ③ 无需迁移全部功能
|
|
|
+│
|
|
|
+└─ 不确定 ──────────────────────────────→ 从阶段 1 开始(LLMService 接口)
|
|
|
+ 第 1 周后评估是否继续
|
|
|
+```
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+## 附录
|
|
|
+
|
|
|
+### A.1 涉及文件清单
|
|
|
+
|
|
|
+| 文件 | 操作 |
|
|
|
+|------|------|
|
|
|
+| `service/AIService.java` | 改造为 DifyLLMService 实现 |
|
|
|
+| `service/LLMService.java` | 新建 |
|
|
|
+| `service/DirectLLMService.java` | 新建 |
|
|
|
+| `service/ContextBuilder.java` | 从 FamilyContextService 提取接口 |
|
|
|
+| `service/RAGService.java` | 新建 |
|
|
|
+| `service/EmbeddingService.java` | 新建 |
|
|
|
+| `service/ChatSummaryService.java` | 新建 |
|
|
|
+| `service/FactExtractionService.java` | 新建 |
|
|
|
+| `service/LocalKBService.java` | 新建 |
|
|
|
+| `config/AssistantConfig.java` | 新建(System Prompt 配置类) |
|
|
|
+| `service/DifySyncService.java` | 删除(阶段 4) |
|
|
|
+| `service/WisdomMathService.java` | 修改(eval 默认) |
|
|
|
+| `service/TongueDiagnosisService.java` | 修改(直调 Qwen-VL) |
|
|
|
+| `service/ArticleService.java` | 修改(直调 LLM) |
|
|
|
+| `service/MealRecommendService.java` | 修改(直调 LLM) |
|
|
|
+| `controller/ai/AIChatController.java` | 修改(引用 LLMService) |
|
|
|
+| `controller/ai/ButlerController.java` | 修改(引用 LLMService) |
|
|
|
+| `application.yml` | 修改(添加 AI 配置,移除 Dify 配置) |
|
|
|
+| `schema.sql` | 无变化 |
|
|
|
+| `DatabaseInitializer.java` | 无变化 |
|
|
|
+
|
|
|
+### A.2 参考文档
|
|
|
+
|
|
|
+- [数据与AI结合技术方案.md](../数据与AI结合技术方案.md) — 现有 AI 架构文档
|
|
|
+- `AGENTS.md` — 项目开发规范
|
|
|
+- DeepSeek API 文档:`https://platform.deepseek.com/api-docs`
|
|
|
+- sqlite-vec 项目:`https://github.com/asg017/sqlite-vec`
|
|
|
+
|
|
|
+### A.3 变更记录
|
|
|
+
|
|
|
+| 版本 | 日期 | 变更内容 |
|
|
|
+|------|------|---------|
|
|
|
+| v1.0 | 2026-07-20 | 初稿,覆盖 4 阶段迁移计划 |
|