Files
wecom_it_smart_desk/docs/02-产品需求/Dify_App改造与AI供给链路修复方案-v1.0.md
T

330 lines
13 KiB
Markdown
Raw Normal View History

# Dify App 改造与 AI 供给链路修复方案
> **版本**: v1.0
> **日期**: 2026-07-13
> **涵盖任务**: P1-4App精简)、P1-5Prompt部署)、P1-6(知识库优化)
> **前置条件**: P0 代码改造已完成(`_call_dify_native()` + `DIFY_NATIVE_*` 环境变量)
---
## 一、当前阻塞点(P0-3 验证结果)
### 1.1 Dify 应用状态
| 应用 | API Key | 状态 | 说明 |
|------|---------|------|------|
| 智能IT支持-员工咨询 | `app-7jkRkAzvX4QM9v9SM3P8mMEO` | ❌ 400 | "Workflow not published"(工作流未发布) |
| 老线上应用 | `app-UaTWYdBSwN6VktKQlbh5YN5H` | ✅ 200 | 返回纯文本Markdown(非JSON),已标记禁用 |
| 分诊应用 | `app-z3S9AEUUAVPbtR2rioxpiIvp` | ✅ 200 | 返回结构化JSON,正常工作 |
| 自建应用 | `app-J3s8sHarZQ2SCaNF3xCppliL` | ❌ 400 | "Model credentials not initialized" |
### 1.2 根因分析
Dify 应用 `app-7jkRkAzvX4QM9v9SM3P8mMEO` 是一个 **advanced-chat(聊天流)** 类型的应用,包含 85 个节点。该应用的工作流 **尚未发布**,导致 API 调用返回 `"Workflow not published"` 错误。
**影响**
- 后端 `_call_dify_native()` 调用 Dify 原生 API → 返回 400 → 降级到代理路径
- 代理路径(dify2openai)返回 `[object Object]` → JSON 解析失败 → 降级为纯文本
- **最终结果**:所有 Phase 1-6 前端改造的结构化功能(卡片渲染、选项按钮、诊断阶段)均无法触发
### 1.3 修复路径
```
用户在 Dify 平台发布工作流
Dify API 返回 200 + JSON answer
后端 _call_dify_native() 解析 JSON
双 WS 推送(ai_reply + dynamic_recommend
前端渲染结构化消息(文字气泡 + 卡片 + 选项按钮)
```
---
## 二、P1-4Dify App 精简方案(85 → ~35 节点)
### 2.1 精简原则
1. **后端已接管的功能**:审批意图分类、关键词预过滤、BYOD 拦截、图片增强 → Dify 中对应节点可删除
2. **Prompt 已覆盖的功能**:JSON 输出格式、诊断阶段标注、审批卡片推送规则 → Dify 中的格式化/路由节点可删除
3. **保留核心能力**RAGFlow 知识检索、LLM 推理、多轮对话上下文 → 这三块是 Dify 的核心价值
4. **Vision 节点**:后端 `VisionService` 已独立接入,但 Dify 内的图片理解节点暂保留(双路径冗余)
### 2.2 节点分类与精简计划
#### 可删除节点(50个)
| 类别 | 节点类型 | 数量 | 删除原因 |
|------|---------|------|---------|
| 审批意图路由 | if-else + answer | 12 | 后端 `_check_approval_intent()` 已接管,关键词收窄至~25个 |
| BYOD 拦截 | if-else + code + assigner | 8 | 后端 `h5_ai_task.py` 已实现 BYOD 拦截逻辑 |
| 格式化输出 | code + template-transform | 10 | Prompt v1.1 已要求 LLM 直接输出 JSON,无需后处理 |
| 变量中转 | assigner | 12 | 精简后不再需要多步变量传递 |
| 打招呼/人工判断 | if-else + answer | 4 | 后端 `h5_ai_task.py` 已实现打招呼和人工坐席判断 |
| 保底机制 | code + if-else + assigner | 4 | 后端有 30s 超时降级 + 15s still_thinking 推送 |
#### 保留节点(~35个)
| 类别 | 节点类型 | 数量 | 保留原因 |
|------|---------|------|---------|
| 核心 | start + answer | 3 | 工作流入口和最终输出 |
| 知识检索 | knowledge-retrieval | 3 | RAGFlow 检索(IT知识库 + 审批流程库 + FAQ库) |
| LLM 推理 | llm | 4 | 主对话 LLM + 意图理解 + 上下文总结 + 图片描述 |
| 条件路由 | if-else | 5 | 图片/文本分流 + 知识库命中/未命中分流 + 上下文长度判断 |
| 变量管理 | assigner | 6 | 对话变量(servyou_query, memory_query, memory_ans, mmq |
| 代码处理 | code | 6 | 查询预处理 + 结果后处理 + 上下文拼接 + 图片URL提取 |
| HTTP 请求 | http-request | 4 | RAGFlow API 调用 + 图片理解 API + 外部知识源 |
| 模板转换 | template-transform | 2 | 上下文模板 + 答案模板 |
| 列表操作 | list-operator | 1 | 历史消息列表处理 |
| 其他 | 1 | 保底 answer 节点 |
### 2.3 精简后的工作流结构
```
[Start]
→ [Code: 预处理用户输入]
→ [IF-ELSE: 图片消息?]
├─ Yes → [HTTP: 调用图片理解API] → [LLM: 图片描述生成]
└─ No → 直接继续
→ [Code: 拼接上下文(memory_query + memory_ans + servyou_query)]
→ [IF-ELSE: 上下文长度 > 阈值?]
├─ Yes → [LLM: 上下文压缩总结]
└─ No → 直接继续
→ [Knowledge-Retrieval: RAGFlow 检索]
→ [IF-ELSE: 检索结果命中?]
├─ Yes → [LLM: 基于知识库回答(JSON格式)] → [Answer]
└─ No → [LLM: 通用回答(JSON格式)] → [Answer]
→ [Code: 更新对话变量]
```
### 2.4 精简操作步骤
1. **导出当前 DSL**:在 Dify 后台导出 `app-7jkRkAzvX4QM9v9SM3P8mMEO` 的完整 YAML(已导出,见 `scripts/dify_export_clean.yaml`
2. **在 Dify 后台编辑工作流**
- 删除审批意图路由相关节点(12个 if-else + answer
- 删除 BYOD 拦截相关节点(8个)
- 删除格式化输出节点(10个 code + template-transform
- 删除冗余变量中转节点(12个 assigner
- 删除打招呼/人工判断节点(4个)
- 删除保底机制节点(4个)
3. **更新 LLM 节点的 System Prompt**:将 `dify_main_chat_prompt_v1.md` 的完整 Prompt 粘贴到主 LLM 节点
4. **重新连接节点**:确保工作流从 Start 到 Answer 的路径完整
5. **测试工作流**:在 Dify 后台的调试面板中测试以下场景:
- "密码忘记了怎么办" → 应返回 JSON with options
- "我要申请VPN" → 应返回 JSON with action
- "你好" → 应返回 JSON 纯文字
6. **发布工作流**:点击「发布」按钮,使工作流生效
---
## 三、P1-5Dify Prompt v1.1 部署内容
### 3.1 Prompt 文件位置
完整 Prompt 已准备好,位于:
```
docs/02-产品需求/dify_main_chat_prompt_v1.md
```
### 3.2 部署步骤
1. **登录 Dify 平台**http://yw-dify.dc.servyou-it.com
2. **打开应用**:找到「智能IT支持-员工咨询」(API Key: `app-7jkRkAzvX4QM9v9SM3P8mMEO`
3. **进入编排页面**:点击「编排」→ 进入工作流编辑器
4. **找到主 LLM 节点**:在精简后的工作流中,主 LLM 节点(用于生成最终回复的节点)
5. **替换 System Prompt**
-`dify_main_chat_prompt_v1.md` 中「## System Prompt 正文」以下的所有内容复制
- 粘贴到 LLM 节点的「SYSTEM」输入框中
- 确保 USER 输入框设置为 `{{#sys.query#}}`(用户原始输入)
6. **配置模型参数**
- 模型:`gpt-3.5-turbo`(或可用的 OpenAI 兼容模型)
- Temperature0.3(低温度保证 JSON 格式稳定)
- Max Tokens500JSON 输出不需要太长)
7. **测试验证**
- 在调试面板输入 "密码忘了" → 验证返回 JSON 包含 `text` + `options` + `diagnosis_stage`
- 在调试面板输入 "我要申请VPN" → 验证返回 JSON 包含 `action`
- 在调试面板输入 "谢谢" → 验证返回 JSON 纯文字
8. **发布**:确认无误后点击「发布」
### 3.3 Prompt 核心要点
Prompt v1.1 的关键设计:
| 要点 | 说明 |
|------|------|
| JSON 强制输出 | 4个字段:`text``action``options``diagnosis_stage` |
| 文字简短 | `text` 字段 ≤50字,口语化 |
| 诊断阶段 | 6种值:initial/gathering_info/diagnosing/recommending/resolved/escalating |
| 审批卡片 | `action.type = "approval_card"`8种审批类型 |
| 交互选项 | `options` 最多4个,label ≤8字 |
| 无 markdown | 直接输出 JSON 原文,不用代码块包裹 |
### 3.4 后端适配确认
后端 `_call_dify_native()``_parse_structured_response()` 已完成适配:
- `_call_dify_native()`:直连 Dify `/v1/chat-messages`blocking 模式,返回 `answer` 字段
- `_parse_structured_response()`:解析 `answer` 字段为 JSON,提取 `text`/`action`/`options`/`diagnosis_stage`
- 失败降级:JSON 解析失败 → 纯文本回复(不中断用户体验)
---
## 四、P1-6:知识库内容优化计划
### 4.1 当前知识库状态
RAGFlow 生产环境:`http://10.80.0.85:8080/`API: `:9380`
Dify 中引用的知识库:
1. **IT知识库**:日常IT问题解答(密码重置、VPN连接、打印机等)
2. **审批流程库**12种审批类型的操作流程
3. **FAQ库**:高频问题快速回答
### 4.2 优化目标
| 指标 | 当前 | 目标 |
|------|------|------|
| 检索准确率 | ~60%(粗估) | ≥85% |
| 知识库文档数 | ~200篇 | ~150篇(精简+补充) |
| 平均检索时间 | ~3s | ≤2s |
| 无效检索率 | ~25% | ≤10% |
### 4.3 优化策略
#### 策略1:知识库结构化重构
```
IT知识库/
├── 01-账号密码/ # 密码重置、账号解锁、二次验证
│ ├── 企微密码重置.md
│ ├── 邮箱密码重置.md
│ ├── aTrust密码重置.md
│ └── GitLab密码重置.md
├── 02-网络VPN/ # VPN连接、网络故障、WiFi
│ ├── 零信任aTrust连接.md
│ ├── 传统VPN配置.md
│ └── 网络不通排查.md
├── 03-设备硬件/ # 电脑、显示器、打印机
│ ├── 打印机连接.md
│ ├── 蓝屏排查.md
│ └── 设备报修流程.md
├── 04-软件安装/ # 软件安装、授权、更新
│ ├── 软件安装指南.md
│ └── 软件授权申请.md
├── 05-审批流程/ # 12种审批类型
│ ├── 设备申请流程.md
│ ├── VPN账号申请.md
│ └── ...
└── 06-常见FAQ/ # 高频问题
├── 电脑卡顿.md
└── 邮件配置.md
```
#### 策略2:文档内容标准化
每篇知识库文档统一格式:
```markdown
# [问题标题]
## 问题描述
[1-2句话描述问题场景]
## 解决方案
### 步骤1[操作名称]
[具体操作步骤]
### 步骤2[操作名称]
[具体操作步骤]
## 相关链接
- [操作入口URL]
- [相关文档]
## 关键词
密码、重置、企微、登录
```
#### 策略3RAGFlow 检索优化
1. **Chunk 策略调整**
- 将大文档拆分为 ≤500 token 的 chunk
- 每个 chunk 包含完整的「问题描述 + 解决方案」
- 避免跨 chunk 的信息断裂
2. **Embedding 模型**
- 确认使用中文优化的 embedding 模型(如 `bge-large-zh`
- 如果当前用的是英文模型,切换后检索准确率可提升 15-20%
3. **检索参数调优**
- Top-K5→3(减少噪音)
- 相似度阈值:0.5→0.65(提高精度)
- Rerank:启用 rerank 模型(如 `bge-reranker-base`
#### 策略4:知识库内容补充
基于员工咨询高频场景,需补充以下内容:
| 场景 | 当前状态 | 补充内容 |
|------|---------|---------|
| 企微使用问题 | 缺失 | 企微登录/消息/审批/会议常见问题 |
| 税友安全助手 | 缺失 | 安装/认证失败/网络断开排查 |
| 域控账号 | 部分 | 域控密码同步机制 + 常见故障 |
| 云桌面 | 缺失 | 云桌面连接/卡顿/文件传输 |
| 视频会议 | 部分 | 腾讯会议/企微会议常见问题 |
### 4.4 实施时间线
| 阶段 | 内容 | 预计工作量 |
|------|------|-----------|
| 第1周 | 知识库结构化重构 + 文档标准化 | 2天 |
| 第1周 | RAGFlow 检索参数调优 | 0.5天 |
| 第2周 | 高频场景内容补充(20篇) | 2天 |
| 第2周 | Embedding 模型评估 + 切换 | 1天 |
| 第3周 | 端到端测试 + 效果评估 | 1天 |
---
## 五、完整执行清单
### 5.1 用户需在 Dify 平台操作(阻塞项)
- [ ] **D-1**:登录 http://yw-dify.dc.servyou-it.com
- [ ] **D-2**:打开「智能IT支持-员工咨询」应用(`app-7jkRkAzvX4QM9v9SM3P8mMEO`
- [ ] **D-3**:精简工作流(按 P1-4 方案,85→~35节点)
- [ ] **D-4**:更新主 LLM 节点的 System Prompt(按 P1-5 部署步骤)
- [ ] **D-5**:在调试面板测试3个场景(密码/VPN/打招呼)
- [ ] **D-6**:点击「发布」按钮
- [ ] **D-7**:发布后通知我验证 API 连通性
### 5.2 我来完成(Dify 发布后)
- [ ] **M-1**:验证 Dify 原生 API 返回 JSON 格式(复用 `test_dify_native.py`
- [ ] **M-2**:请用户在企微内发消息测试端到端链路
- [ ] **M-3**:检查后端日志确认 `调用 Dify 原生 API` + JSON 解析成功
- [ ] **M-4**:验证前端结构化消息渲染(文字气泡 + 卡片 + 选项按钮)
- [ ] **M-5**:开始知识库优化(P1-6
### 5.3 临时方案(如需立即可用)
如果用户暂时无法在 Dify 平台操作,可临时切换到旧 Key(需用户授权):
```
# 临时切换 .env 中的 DIFY_NATIVE_API_KEY
DIFY_NATIVE_API_KEY=app-UaTWYdBSwN6VktKQlbh5YN5H
```
**注意**:旧 Key 返回纯文本(非JSON),后端会降级为纯文字回复。结构化功能(卡片/选项)不可用,但至少 AI 对话能正常工作。
---
## 六、风险评估
| 风险 | 等级 | 缓解措施 |
|------|------|---------|
| Dify 工作流精简后遗漏关键路径 | 中 | 精简前已导出完整 DSL YAML 备份 |
| Prompt v1.1 在 Dify 中 JSON 输出不稳定 | 中 | Temperature=0.3 + 后端有 JSON 解析降级 |
| RAGFlow 检索准确率不达标 | 低 | 可通过调整检索参数 + 补充内容逐步优化 |
| 知识库内容过时 | 中 | 建立月度知识库审查机制 |