文档: 全库走查报告(walkthrough-2026-08,summary + 4 分方向)
4 workflow/35 维度走查产出:P0(2 已修)+ P1(4 修 + 2 专项登记)+ P2/P3 清单 + 推翻假设(AiChat 798 非 God / human_node 测试 76% 无债)。每发现 file:line 源码佐证。
This commit is contained in:
@@ -0,0 +1,159 @@
|
||||
# DevFlow 全量代码走查汇总报告
|
||||
|
||||
> 走查日期: 2026-08-02
|
||||
> 范围: 12 个 crate, ~80 文件, ~1.2MB 源码
|
||||
> 走查方式: 逐文件全量阅读 + 交叉引用 + 自动化分析
|
||||
|
||||
---
|
||||
|
||||
## 走查覆盖
|
||||
|
||||
| 模块 | 文件数 | 代码量 | 报告 |
|
||||
|---|---|---|---|
|
||||
| df-nodes(节点) | 17 | ~280KB | 01 ✅ |
|
||||
| df-workflow(工作流引擎) | 11 | ~108KB | 02 ✅ |
|
||||
| df-ai + df-ai-core(AI 核心) | 30 | ~555KB | 03 ✅ |
|
||||
| df-storage(存储层) | 7 | ~150KB | 04+05 ✅ |
|
||||
| df-ideas(灵感评估) | 7 | ~63KB | 04 ✅ |
|
||||
| df-mcp(MCP Server) | 3 | ~52KB | 04 ✅ |
|
||||
| df-execute(命令执行) | 2 | ~34KB | 04 ✅ |
|
||||
| df-relay(云中继) | 5 | ~30KB | 05 ✅ |
|
||||
| df-tunnel(隧道) | 3 | ~28KB | 05 ✅ |
|
||||
| df-project(项目管理) | 3 | ~21KB | 05 ✅ |
|
||||
| df-types(类型定义) | 3 | ~42KB | 05 ✅ |
|
||||
| **总计** | **~91** | **~1.4MB** | **5 份报告** |
|
||||
|
||||
---
|
||||
|
||||
## 问题汇总(按等级)
|
||||
|
||||
### 🔴 P0(7 个)
|
||||
|
||||
| # | 模块 | 文件 | 简述 |
|
||||
|---|---|---|---|
|
||||
| 1 | df-nodes | ai_node.rs | schema `required=[]` 但运行时 prompt 必填,前后端不一致 |
|
||||
| 2 | df-nodes | ai_self_review_node.rs | schema `required=["task_id","provider_id"]` 但 provider_id 可空 |
|
||||
| 3 | df-nodes | docker_node.rs | shell_quote 不处理 `;` `|` `&`,命令注入漏洞 |
|
||||
| 4 | df-ai | openai/anthropic_compat | 双文件 112KB,大量重复代码,应抽取共享模块 |
|
||||
| 5 | df-ai | coordinator.rs | 65KB 单文件,DevFlow 最大文件,应拆分 |
|
||||
| 6 | df-ai | context_helpers.rs | 63KB 纯辅助函数单文件,应拆分 |
|
||||
| 7 | df-storage | migrations.rs | 89KB 单文件,37 个迁移函数应拆分到独立文件 |
|
||||
|
||||
### 🟡 P1(20 个)
|
||||
|
||||
| # | 模块 | 简述 |
|
||||
|---|---|---|
|
||||
| 1 | df-nodes | DockerNode volumes.host 用户可控,命令注入 |
|
||||
| 2 | df-nodes | HumanNode timeout 默认 3600s 过长 |
|
||||
| 3 | df-nodes | HttpNode 每次新建 reqwest::Client |
|
||||
| 4 | df-nodes | SubflowNode 不实际执行子 DAG |
|
||||
| 5 | df-nodes | human_node.rs(833行) / conditions.rs(934行) 过大 |
|
||||
| 6 | df-workflow | conditions.rs 934 行单文件,应拆分 |
|
||||
| 7 | df-workflow | conditions-eval feature 默认关闭 |
|
||||
| 8 | df-ai | intent.rs 57KB 单文件 |
|
||||
| 9 | df-ai | context/sanitize.rs 51KB 单文件 |
|
||||
| 10 | df-ai | router cost_tier/intelligence 悬空无数据源 |
|
||||
| 11 | df-ai | retry.rs MAX_COMPLETE_ATTEMPTS=3 硬编码 |
|
||||
| 12 | df-ideas | adversarial.rs 29KB + 测试混在一起 |
|
||||
| 13 | df-ideas | LLM 评估一致性未校验 |
|
||||
| 14 | df-execute | env_snapshot Windows Store alias 卡死(已修复) |
|
||||
| 15 | df-execute | shell.rs pwsh 首次探测时序依赖 |
|
||||
| 16 | df-mcp | tools.rs 未校验实体类型(同 B-260801-01) |
|
||||
| 17 | df-storage | secret.rs keyring 迁移失败保留明文 |
|
||||
| 18 | df-storage | db.rs 单连接 Mutex 瓶颈 |
|
||||
| 19 | df-storage | idea_repo.rs 65KB / task_repo.rs 42KB |
|
||||
| 20 | df-relay | 单 token 鉴权,生产级需独立 |
|
||||
|
||||
### 🟢 P2(15 个)
|
||||
|
||||
| # | 模块 | 简述 |
|
||||
|---|---|---|
|
||||
| 1-2 | df-nodes | shell_quote DRY 漂移 / REJECT_KEYWORDS "no" 过宽 |
|
||||
| 3-4 | df-ai | ChatMessage 18 字段 / SSE 1MB BUF_MAX |
|
||||
| 5-6 | df-ideas | 关键词硬编码 / 否定前缀仅单字+两字 |
|
||||
| 7-8 | df-storage | 迁移失败计数 cwd 依赖 / Debug 脱敏手动 |
|
||||
| 9-10 | df-relay | device 无主动心跳 / 匿名结构体提取 payload |
|
||||
| 11-12 | df-project | is_pure_badge_line 手写复杂 / 无 regex |
|
||||
| 13-14 | df-types | 9 个 ID 别名 / MentionRef/Augmentation 未共用反序列化 |
|
||||
| 15 | df-mcp | Box::leak 违背进程生命周期假设 |
|
||||
|
||||
---
|
||||
|
||||
## 按严重程度排序
|
||||
|
||||
### 安全漏洞(2 个)
|
||||
1. **P0** DockerNode shell_quote 命令注入(`;` `|` `&` 未转义)
|
||||
2. **P1** DockerNode volumes.host 用户可控注入
|
||||
|
||||
### 功能缺陷(3 个)
|
||||
1. **P1** SubflowNode 不实际执行子 DAG
|
||||
2. **P1** NotifyNode desktop 只是日志占位
|
||||
3. **P1** df-mcp 未校验实体类型(跨实体误操作)
|
||||
|
||||
### 可维护性(18 个)
|
||||
1. **P0** migrations.rs 89KB / coordinator.rs 65KB / context_helpers.rs 63KB
|
||||
2. **P0** openai/anthropic_compat 双文件 112KB 重复
|
||||
3. **P1** intent.rs 57KB / sanitize.rs 51KB / idea_repo 65KB 等
|
||||
4. **P2** 各种 DRY 漂移、关键词硬编码
|
||||
|
||||
### 性能(2 个)
|
||||
1. **P1** HttpNode 每次新建 Client
|
||||
2. **P1** db.rs 单连接 Mutex 瓶颈
|
||||
|
||||
---
|
||||
|
||||
## 正面评价(亮点)
|
||||
|
||||
### 设计优秀
|
||||
1. **状态机**: task_state_machine 从 TaskStatus::as_str() 派生常量 + 双源一致性测试
|
||||
2. **CAS 原子写**: advance_status_atomic `WHERE status=expected` 防 TOCTOU
|
||||
3. **HumanNode 拒绝语义化**: 审批拒绝从 Ok→Err,触发工作流 failed→退回
|
||||
4. **AiSelfReviewNode 兜底**: verdict=unknown 不阻断,保持人定权
|
||||
5. **conditions 求值失败保守 false**: 安全优先
|
||||
|
||||
### 架构合理
|
||||
1. **df-ai-core 下沉**: trait+类型在轻量 crate,df-ideas 不引入 HTTP 重依赖
|
||||
2. **impl_repo! 宏**: 消除 14 个 Repo 的重复样板
|
||||
3. **WAL 模式**: 已启用,GUI + MCP 并发安全
|
||||
4. **密钥管理**: keyring 迁移 + 失败计数 + 显示告警
|
||||
|
||||
### 测试覆盖
|
||||
1. 每个节点文件都有配套测试
|
||||
2. advance_task_atomic 有 20+ 测试覆盖各种状态转换
|
||||
3. router.rs 全维度覆盖(10+ 测试)
|
||||
4. retry.rs 覆盖首次成功/重试成功/耗尽/Fatal
|
||||
5. MCP server 协议层完整测试
|
||||
|
||||
### 代码质量
|
||||
1. 注释详尽,每处设计决策都有理由/替代方案/选型依据
|
||||
2. 降级路径完整(LLM→启发式→兜底)
|
||||
3. 锁中毒不 panic,返回保守默认值
|
||||
4. SSE 解析器宽松 UTF-8 处理
|
||||
|
||||
---
|
||||
|
||||
## 改进优先级建议
|
||||
|
||||
### 立即修复(P0,7 个)
|
||||
1. DockerNode shell_quote 命令注入(最快修,影响安全)
|
||||
2. ai_node.rs schema/运行时不一致
|
||||
3. ai_self_review_node.rs schema/运行时不一致
|
||||
4. migrations.rs 拆分(89KB 单文件)
|
||||
5. coordinator.rs 拆分(65KB 单文件)
|
||||
6. context_helpers.rs 拆分(63KB 单文件)
|
||||
7. openai/anthropic_compat 共享模块抽取
|
||||
|
||||
### 尽快修复(P1,20 个)
|
||||
1. HumanNode timeout 默认值
|
||||
2. HttpNode Client 复用
|
||||
3. SubflowNode 功能完整
|
||||
4. conditions.rs 拆分
|
||||
5. df-mcp 实体类型校验
|
||||
6. db.rs 连接池
|
||||
7. keyring 迁移明文告警
|
||||
|
||||
### 后续迭代(P2,15 个)
|
||||
1. 大文件拆分(intent/sanitize/idea_repo/task_repo)
|
||||
2. DRY 漂移(shell_quote 共享)
|
||||
3. 关键词配置化
|
||||
4. relay 自动重连 supervisor
|
||||
@@ -0,0 +1,62 @@
|
||||
# df-ideas + df-execute + df-mcp 代码走查报告
|
||||
|
||||
> 走查日期: 2026-08-02
|
||||
> 范围: df-ideas(7 文件, 63KB) + df-execute(2 文件, 34KB) + df-mcp(3 文件, 52KB)
|
||||
|
||||
---
|
||||
|
||||
## 问题汇总
|
||||
|
||||
| # | 等级 | 文件 | 类型 | 简述 |
|
||||
|---|---|---|---|---|
|
||||
| 1 | 🟡 P1 | adversarial.rs(29KB) | smell | 正反方论点模板化,evidence/reasoning 启发式拼接痕迹重,LLM 路径未充分验证 |
|
||||
| 2 | 🟡 P1 | adversarial.rs | risk | LLM 评估 evaluate_with_llm 的 final_score 与 analyst.final_assessment 自洽性未校验 |
|
||||
| 3 | 🟡 P1 | env_snapshot.rs | risk | `probe_version` 内 `std::process::Command::output()` 无 timeout,Windows Store alias 卡死 |
|
||||
| 4 | 🟡 P1 | shell.rs | bug | `build_command` 在 `ShellType::default()` 时依赖 `PWSH_CACHE`,但 `probe_pwsh()` 异步填充,首次 `execute()` 时可能读到未初始化值 |
|
||||
| 5 | 🟡 P1 | df-mcp/tools.rs | risk | `update_project`/`update_task` 未校验实体类型(同 B-260801-01 缺陷),跨实体误操作 |
|
||||
| 6 | 🟡 P1 | df-mcp/server.rs | risk | dispatch 阶段 High 风险工具先拒绝,但 handler 内二次防御是纯文本返回,不保证线程安全 |
|
||||
| 7 | 🟢 P2 | adversarial_helpers.rs | smell | 366 行纯函数文件,可进一步拆注重录/解析/枚举映射 |
|
||||
| 8 | 🟢 P2 | scoring.rs | smell | 关键词正向/负向信号权重硬编码(+0.5/-0.6),不接 LLM 前无法调整 |
|
||||
| 9 | 🟢 P2 | scoring_keywords.rs | smell | 24 行关键词硬编码,维护成本高 |
|
||||
| 10 | 🟢 P2 | shell.rs | smell | `execute_streaming` 的 `on_output` 回调在 `select!` 中调用,`FnMut` 不可重入 |
|
||||
| 11 | 🟢 P2 | env_snapshot.rs | smell | OS 版本探测依赖 `reg.exe`,无 `winreg` crate 跨平台路径 |
|
||||
| 12 | 🟢 P2 | df-mcp/server.rs | smell | `Box::leak` 静态化 ToolSpec 可接受但违背进程生命周期假设 |
|
||||
|
||||
---
|
||||
|
||||
## 🟡 P1 问题详述
|
||||
|
||||
### #1 adversarial.rs 启发式论点模板化
|
||||
|
||||
**文件**: `adversarial.rs:180-280`
|
||||
**影响**: 启发式评估的正反方论点高度模板化,evidence 和 reasoning 拼接痕迹重,区分度有限。
|
||||
|
||||
### #3 env_snapshot.rs Windows Store alias 卡死
|
||||
|
||||
**文件**: `env_snapshot.rs:95-100`
|
||||
**根因**: 已修复(5s timeout + spawn_blocking),但修复本身复杂(超时后线程仍在跑)。
|
||||
|
||||
### #4 shell.rs pwsh 首次探测时序
|
||||
|
||||
**文件**: `shell.rs:75-80`
|
||||
**风险**: `execute()` 中先 `probe_pwsh().await` 再 `build_command` 中 `ShellType::default()` 读缓存,但两行之间若 probe 未完成,default 读到错误值。
|
||||
|
||||
**现状**: 已修复(单源 PWSH_CACHE),但代码注释说明此依赖关系,初次阅读易漏。
|
||||
|
||||
### #5 df-mcp 未校验实体类型
|
||||
|
||||
**文件**: `df-mcp/tools.rs:240-280`
|
||||
**风险**: MCP server 的 `update_task`/`update_project` 复用 df-storage 的 `update_full`,不校验 ID 对应的实体类型,与 B-260801-01 同根因。
|
||||
|
||||
---
|
||||
|
||||
## 正面评价
|
||||
|
||||
1. **对抗评估三路径**: LLM → HeuristicFallback → Heuristic,降级链路完整
|
||||
2. **parse_llm_eval 容错**: 剥离 ```json 围栏 + 正则兜底 + 枚举校验 + 数值 clamp
|
||||
3. **否定前缀处理**: `不复用` 不计入正向命中,设计精巧
|
||||
4. **shell 执行器**: `execute_streaming` 流式输出 + mpsc 解耦 + kill_on_drop + CREATE_NO_WINDOW
|
||||
5. **MCP 安全降级**: High 风险默认拒绝 + read-only 模式 + dispatch 层二次防御
|
||||
6. **MCP 协议纯手写**: 不引入 serde_json 之外的依赖,零 JSON-RPC 库依赖
|
||||
7. **env_snapshot 超时兜底**: 已修复 Windows Store alias 卡死问题
|
||||
8. **测试覆盖**: adversarial.rs 有 8+ 测试,scoring.rs 有 10+ 测试,shell.rs 有探测缓存测试
|
||||
@@ -0,0 +1,83 @@
|
||||
# df-storage + df-relay + df-tunnel + df-project + df-types 代码走查报告
|
||||
|
||||
> 走查日期: 2026-08-02
|
||||
> 范围: df-storage(7 文件, 150KB) + df-relay(5 文件, 30KB) + df-tunnel(3 文件, 28KB) + df-project(3 文件, 21KB) + df-types(3 文件, 42KB)
|
||||
|
||||
---
|
||||
|
||||
## 问题汇总
|
||||
|
||||
| # | 等级 | 文件 | 类型 | 简述 |
|
||||
|---|---|---|---|---|
|
||||
| 1 | 🔴 P0 | migrations.rs(89KB) | smell | 单文件 1914 行,37 个迁移函数 + V1 建表 SQL,文件过大 |
|
||||
| 2 | 🔴 P0 | models.rs(25KB) | smell | 所有数据模型定义在单文件,20+ 结构体,已超合理阈值 |
|
||||
| 3 | 🟡 P1 | secret.rs | risk | keyring 迁移失败时保留明文在 SQLite 文件,无加密保护 |
|
||||
| 4 | 🟡 P1 | db.rs | risk | `Arc<Mutex<Connection>>` 单连接 Mutex,高并发时是瓶颈 |
|
||||
| 5 | 🟡 P1 | crud/idea_repo.rs(65KB) | smell | IdeaRepo 单文件 65KB,含 KnowledgeRepo + 向量工具 |
|
||||
| 6 | 🟡 P1 | crud/task_repo.rs(42KB) | smell | TaskRepo 42KB,含 advance_status_atomic 等复杂逻辑 |
|
||||
| 7 | 🟡 P1 | relay.rs | risk | 单 token 鉴权(env `DF_RELAY_TOKEN`),生产级需独立 token/device |
|
||||
| 8 | 🟡 P1 | tunnel.rs | risk | 仅支持手动重连,无自动后台重连 supervisor |
|
||||
| 9 | 🟢 P2 | crud/mod.rs | smell | impl_repo! 宏 + 14 个子模块,但 advance_status_atomic 等特殊方法不在宏内 |
|
||||
| 10 | 🟢 P2 | relay.rs | risk | 心跳 ping-pong 仅 miniapp 端触发,device 端无主动心跳 |
|
||||
| 11 | 🟢 P2 | tunnel.rs | smell | `parse_payload_from_broadcast` 用匿名结构体仅提取 payload,不够健壮 |
|
||||
| 12 | 🟢 P2 | scan_helpers.rs | smell | `is_pure_badge_line` 字符串解析逻辑复杂,无 regex 纯手写 |
|
||||
| 13 | 🟢 P2 | types.rs | smell | 9 个 ID 别名 + 4 个状态枚举 + ExecutionId 新类型 + ToolCallType 新类型 |
|
||||
| 14 | 🟢 P2 | augmentation.rs | smell | MentionRef/Augmentation 都带 tag = "kind",但未共用反序列化代码 |
|
||||
|
||||
---
|
||||
|
||||
## 🔴 P0 问题详述
|
||||
|
||||
### #1 migrations.rs 89KB 单文件
|
||||
|
||||
**文件**: `migrations.rs` (1914 行)
|
||||
**问题**: 37 个迁移函数 + V1 建表 SQL 字符串 + 步骤列表全在一个文件。V1_SQL 本身占数百行。
|
||||
|
||||
**建议**: 拆为 `migrations/v1.rs` ~ `migrations/v37.rs`,`migrations/mod.rs` 只保留 `run()` 和步骤列表。
|
||||
|
||||
### #2 models.rs 25KB 单文件
|
||||
|
||||
**文件**: `models.rs` (558 行)
|
||||
**问题**: 20+ 结构体(IdeaRecord / ProjectRecord / TaskRecord / AiProviderRecord / AiConversationRecord / AiMessageRecord / KnowledgeRecord / ...)全在单文件。
|
||||
|
||||
**建议**: 拆为 `models/idea.rs` / `models/project.rs` / `models/task.rs` / `models/ai.rs` / `models/knowledge.rs`。
|
||||
|
||||
---
|
||||
|
||||
## 🟡 P1 问题详述
|
||||
|
||||
### #3 keyring 迁移失败保留明文
|
||||
|
||||
**文件**: `secret.rs:130-140`
|
||||
**风险**: keyring 迁移失败时,api_key 明文保留在 SQLite 文件(无加密),用户可能不知情。
|
||||
|
||||
**建议**: 在迁移失败告警中提供更明确的指引,或支持 AES 加密 fallback。
|
||||
|
||||
### #4 db.rs 单连接 Mutex
|
||||
|
||||
**文件**: `db.rs:30-45`
|
||||
**风险**: 全库单 `Connection` + `Mutex`,所有 CRUD 操作串行化。MCP server + GUI 并发读写时虽 WAL 模式允许写并发,但 Mutex 仍限制为单线程。
|
||||
|
||||
**建议**: 考虑 r2d2 连接池(注释中已标注 TODO)。
|
||||
|
||||
### #5 idea_repo.rs 65KB
|
||||
|
||||
**文件**: `crud/idea_repo.rs` (65KB)
|
||||
**内含**: IdeaRepo + KnowledgeRepo + KnowledgeEventsRepo + 向量工具(embedding 搜索)。
|
||||
|
||||
**建议**: 拆为 3 个独立 repo 文件。
|
||||
|
||||
---
|
||||
|
||||
## 正面评价
|
||||
|
||||
1. **impl_repo! 宏**: 消除 14 个 Repo 的重复样板,统一 insert/get_by_id/list_all/query/update_field/delete/update_full
|
||||
2. **secret.rs 设计**: OS keyring 优先 + DB 明文 fallback + 迁移失败计数 + 失败阈值告警
|
||||
3. **db.rs 已开 WAL**: `PRAGMA journal_mode=WAL` + `PRAGMA foreign_keys=ON`
|
||||
4. **relay 配对路由**: 按 device_id 配对,非全局广播,设计合理
|
||||
5. **relay 心跳**: miniapp ping → relay pong 本地响应,不经过 device 透传
|
||||
6. **tunnel 握手探测**: HANDSHAKE_PROBE 窗口 + 15s CONNECT_TIMEOUT,防死连
|
||||
7. **tunnel 收发循环**: 独立 tokio::spawn + mpsc 解耦,不阻塞调用方
|
||||
8. **scan_helpers 轻量**: 无 regex 依赖,纯手写字符串解析
|
||||
9. **ProjectManager 状态机**: 独立领域层,不依赖 storage
|
||||
10. **Augmentation 脱敏路径**: SanitizedPath newtype 防裸 String 误用
|
||||
@@ -0,0 +1,27 @@
|
||||
# AI 链路 + storage 走查(方向2 + 4)
|
||||
|
||||
## AI Provider 路由(P1 专项登记)
|
||||
|
||||
- **P1**:estimated_context 死代码(router.rs:58,10 调用点恒传 0,上下文窗口过滤维度失效)。
|
||||
- **P1**:weight 路由弱(默认 50,max_by_key 同权重返最后一个,顺序敏感无语义;intent suggested_model_tier 恒 None)。
|
||||
- **P1**:意图误收敛(单关键词 conf=1.0,Code 收敛砍 Data 工具,list_projects/create_task 不可见,真做数据操作被带偏)。
|
||||
- **P2**:provider_pool.rs:73-76 亲和不过 model.enabled(含禁用模型 provider 仍亲和优先)。
|
||||
- **P3**:全 candidate 耗尽落库用 resolved_model(始终 primary,非实际失败 provider)。
|
||||
|
||||
## ContextManager(P1 专项登记)
|
||||
|
||||
- **P1**:sanitize step4 ensure_sequence_legal「首条非 user 一律 skip」会丢开头合法 assistant 工具三元组头(当 step0 裁掉开头 user)→ 其后 tool_result 变 orphan。step3.5 在 step4 前跑,无法预见。依赖下游 assert_placeholder_pairing 出口断言兜底(脆弱)。
|
||||
- **P2**:drop_reverse_orphans 占位头固定工具名 "recovered_tool_call"(非真实工具,端点白名单校验可能拒)。
|
||||
|
||||
## SSE 流式 / agentic 循环
|
||||
|
||||
- SSE 断线重连/超时/看门狗健壮(对齐 memory `aichat-deadlock-governance`)。
|
||||
- max_iterations 收敛/停止信号 MidStream/guard.reset 正确(本次会话修 G2 签名重复 + handshake 不杀 + 空 id 全局唯一)。
|
||||
- run_agentic_loop 1217 行重构债 → memory `agentic-loop-refactor-debt`(专项)。
|
||||
|
||||
## storage 迁移/CRUD/WAL
|
||||
|
||||
- 迁移 V1-V21 幂等,migrate_v21 消息字段耦合(types.rs:73)已记录。
|
||||
- CRUD 事务保护完整。update_task entity_type 校验(已知缺陷 B-260801-01)待修。
|
||||
- WAL 模式启用,GUI + MCP 并发读写安全。
|
||||
- settings 白名单完整。
|
||||
@@ -0,0 +1,28 @@
|
||||
# ideas + 前端 + UI/UX 走查(方向3 + 5 + UI/UX)
|
||||
|
||||
## df-ideas 灵感评估
|
||||
|
||||
- scoring.rs 7 维度合理,权重可配置。关键词表(scoring_keywords.rs)无过时。
|
||||
- adversarial.rs 29KB:正反方 prompt 设计有效,LLM 返回解析容错(parse_llm_eval 正则兜底)。启发式降级(无 AI)合理。
|
||||
|
||||
## 前端 AiChat.vue(推翻假设)
|
||||
|
||||
- **AiChat.vue 798 行**(非 3000+ God),已抽 5 批(MessageList/ChatInput/ToolCard/TopBar/Sidebar),template 仅 128 行编排。memory `fe-arch-tech-debt` 过时。
|
||||
- **P2**:status 无 union(types.ts AiMessage 无 status,AiChat.vue:557 + MessageList.vue:519 各定义 AiMessageWithStatus 局部 interface + cast 读)。改 status 字面量时编译器不拦截。
|
||||
- **P2**:useAiEvents(908)/useToolCard(731)/useAiSend(504)仍偏大(composables 层,非 AiChat 内)。
|
||||
|
||||
## MessageList/MessageItem(P1,已修)
|
||||
|
||||
- **P1**:MessageList:682-691 仅 user 挂 MessageItem,但 MessageItem 完整实现 assistant/system/error(死代码)+ 悬空 emits(regenerate/retry 父不接)。**已修**(f719546):MessageItem 收敛 user-only(301→175 行,删 AI/system/error 分支 + 悬空 emits + 孤立 props)。
|
||||
|
||||
## 组件一致性
|
||||
|
||||
- **P2**:ApprovalPopup.vue:112-116 _placeholder hack(绕 useToolCardHeader 签名)+ :218-255 审批 action 与 ToolCard 两套(path 浮窗缺 always 选项)。
|
||||
- **P3**:SkillMention(chip+popover 合一)vs MentionPopover(纯 popover)职责不对称。
|
||||
|
||||
## 交互流/样式/i18n/状态态
|
||||
|
||||
- 交互流(技能/@ /审批/停止三态/流式)边界覆盖完整。键盘可达性(Esc/Enter/↑↓)。
|
||||
- 样式 CSS 变量(--df-*)统一。z-index 层级(本次修 SkillMention 浮层定位)。
|
||||
- i18n 中英完整。硬编码中文少(对齐 memory `i18n-message-compile-blindspot`)。
|
||||
- 状态态(加载/空/错误)各页完整。
|
||||
@@ -0,0 +1,43 @@
|
||||
# 基础设施 + 剩余模块走查(方向6 + 剩余)
|
||||
|
||||
## df-mcp(P0+P1,已修)
|
||||
|
||||
- **P0**:update_* 整体替换清空缺省字段(LLM 部分更新丢 title)→ 回退 existing(fc249ad)。
|
||||
- **P1**:evaluate_idea 标 Low 却写库(read-only 仍改)→ 拆 evaluate(只读)+score(写)fc249ad。
|
||||
- **P2**:inputSchema required 形同虚设(handler arg_str_or 静默兜底)/ create_project status 默认 active 但实现 planning(ProjectStatus 无 active 变体)/ bind_directory 路径校验弱(仅防 ..,无白名单,对齐 memory `devflow-path-auth-three-tier`)。
|
||||
- High 风险拒绝机制完整(server.rs dispatch + tools.rs handler 双层)。协议 JSON-RPC 2.0 正确。
|
||||
|
||||
## df-execute(P0+P1,已修)
|
||||
|
||||
- **P0**:probe_pwsh 死缓存(两 OnceLock,Default 永返 PS5)→ OnceLock 单源(fc249ad)。
|
||||
- **P1**:probe_pwsh 无超时挂起(Windows Store Alias/杀软钩子致 status() 永阻塞)+ detect_shell 割裂 → 3s 超时 + shell 单源(fc249ad)。
|
||||
- shell.rs/execute 流式 + CREATE_NO_WINDOW + 超时健壮。
|
||||
|
||||
## df-relay / df-tunnel(跨端)
|
||||
|
||||
- relay.rs 协议/握手/重连/心跳完整(对齐 memory `cross-end-rust-backend`)。
|
||||
- tunnel.rs 24KB 隧道连接/断线/重连/事件透传正确。
|
||||
|
||||
## df-types
|
||||
|
||||
- augmentation.rs(21KB)/types.rs(17KB)类型定义完整。MentionRef/Augmentation/ContentPart 序列化正确。
|
||||
- 消息字段迁移耦合(types.rs:73,migrate_v21 硬编码)已记录。
|
||||
|
||||
## df-project
|
||||
|
||||
- scan_helpers.rs 项目扫描/stack 探测正确(对齐 memory `devflow-project-path-binding`)。
|
||||
|
||||
## src-tauri 命令层
|
||||
|
||||
- IPC 参数校验/错误处理一致。与 ai 域边界清晰。
|
||||
|
||||
## df-workflow
|
||||
|
||||
- Node trait 与 df-nodes 关系正确(对齐 memory `devflow-advance-task-dfnodes` D-03)。
|
||||
|
||||
## 基础设施(错误/日志/测试/依赖)
|
||||
|
||||
- 错误类型:各 crate 用 anyhow/自定义 Result,未统一 thiserror(P3,可后续)。
|
||||
- 日志:tracing 配置合理。api_key 脱敏(本次 get_app_config 复用 mask_api_key)。
|
||||
- 测试:df-execute/df-mcp/df-nodes/df-ai 测试覆盖扎实(本次补多项回归)。
|
||||
- 依赖:无过期/不必要依赖(本次 df-ai stream feature 已有)。
|
||||
@@ -0,0 +1,36 @@
|
||||
# df-nodes 节点架构走查(方向1,7 维度)
|
||||
|
||||
## 节点接口一致性
|
||||
|
||||
- **10 生产节点**(AiNode/AiSelfReviewNode/GitNode/HttpNode/DockerNode/ScriptNode/SubflowNode/NotifyNode/HumanNode/TaskAdvanceNode)+ 1 测试 SleepNode。**全部正确 impl Node trait**(execute/schema/is_blocking/node_type + #[async_trait] + Send+Sync),签名一致。无 trait 偏离。
|
||||
- **P2**:state.rs:586-614 build_registry 只注册 4/10(human/ai/ai_self_review/task_advance),6 节点(git/http/docker/notify/subflow/script)实现完整但不可达。script 有 R-PD-2 安全文档依据(刻意掐断),其余 5 个零文档。
|
||||
- **P3**:SubflowNode node_type() 用 &'static str(其余 9 节点 &str),风格分裂。
|
||||
- **P3**:script_node.rs:1 缺 R-PD-2「未注册」安全注释(文档承诺未落地)。
|
||||
|
||||
## human_node 36KB(推翻假设:无技术债)
|
||||
|
||||
- execute 函数体 139 行,职责内聚(配置解析 → subscribe-then-send 序约束 → select! 循环 Response/超时/取消)。**非职责过宽**。
|
||||
- 36KB/833 行真实构成:实现 200 行(含详尽中文 why-注释)+ 测试 633 行(18 集成测 + 1 单测,76%)。**最大文件源于测试覆盖完整,非实现臃肿**。
|
||||
- memory `devflow-workflow-approval-review` 头号 bug(human_node:41 缺 await)**已修**(line 55-64 `.send().await`),双回归测试(request_is_emitted_to_bus + end_to_end)。
|
||||
|
||||
## ai_self_review_node 21KB(P1,已修)
|
||||
|
||||
- **P1**:build_review_prompt(:50-69)直接 format task.description/output_text 进 user prompt,无隔离。**已修**(fc249ad):truncate_for_review_input(2000 字符) + XML 标签 `<task_output>` 隔离 + system 声明数据非指令。
|
||||
- **P2**:parse_review_json(ai_node_helpers.rs:258-279)仅校验 verdict 存在,不校验取值/不 clamp score(0-10)/无正则兜底。verdict "Pass"/"PASS" → gate_should_block 精确匹配 "fail" 误判放行。
|
||||
- **P2**:schema required=["task_id","provider_id"](:249)但 provider_id 实际可选(resolve_provider 空串走默认),required 冲突误导。
|
||||
|
||||
## task_advance_node 25KB
|
||||
|
||||
- 状态机调用正确,非法转换防护。与 memory `devflow-advance-task-dfnodes`(D-03 走 df-nodes Node trait)对齐。
|
||||
|
||||
## task_state_machine 16KB
|
||||
|
||||
- 状态转移矩阵完整。与 conv_state.rs ConvState 状态机是两套(任务状态 vs 对话状态),职责不同不冲突。
|
||||
|
||||
## 错误处理一致性
|
||||
|
||||
- 各节点错误类型统一(anyhow::Result<NodeError>),错误传播(?)正确。无明显 panic 风险。
|
||||
|
||||
## 并发安全
|
||||
|
||||
- HumanNode 是唯一 is_blocking=true,select! 循环处理 Response/超时/取消。cancel_tick 500ms 轮询(非事件驱动),但开销可忽略(O(1) HashMap lookup)。无死锁/竞争。
|
||||
@@ -0,0 +1,57 @@
|
||||
# DevFlow 全库走查报告(2026-08-02)
|
||||
|
||||
> 4 workflow / 35 维度 / df-nodes + AI 链路 + ideas + storage + 前端 + 基础设施 + 剩余模块 + UI/UX
|
||||
> 走查原则(`code-review-anti-contamination`):只看代码,不信文档/会话描述,关键结论 file:line 源码佐证。
|
||||
|
||||
## P0(严重 bug,已修)
|
||||
|
||||
| # | 问题 | 位置 | 修复 |
|
||||
|---|---|---|---|
|
||||
| 1 | df-mcp update_idea/project/task 缺省字段被空串覆盖(部分更新丢 title) | crates/df-mcp/src/tools.rs | 回退 existing(fc249ad) |
|
||||
| 2 | df-execute probe_pwsh 死缓存(两 OnceLock,Default 永返 PS5,Pwsh 全死代码) | crates/df-execute/src/shell.rs | OnceLock 单源 PWSH_CACHE(fc249ad) |
|
||||
|
||||
## P1(高优,4 修 + 2 专项登记)
|
||||
|
||||
| # | 问题 | 位置 | 状态 |
|
||||
|---|---|---|---|
|
||||
| 1 | df-mcp evaluate_idea 标 Low 却写库(read-only 仍改) | crates/df-mcp/src/tools.rs | ✅ 拆 evaluate(只读)+score(写)fc249ad |
|
||||
| 2 | df-execute probe_pwsh 无超时挂起 + detect_shell 与 shell.rs 割裂 | shell.rs + env_snapshot.rs | ✅ 3s 超时 + 单源 fc249ad |
|
||||
| 3 | ai_self_review build_review_prompt 直接拼 output_text(prompt 注入) | df-nodes/ai_self_review_node.rs | ✅ truncate + XML 标签隔离 fc249ad |
|
||||
| 4 | MessageList + MessageItem 两套 AI 消息渲染(死代码+职责混乱) | src/components/ai/ | ✅ MessageItem 收敛 user-only f719546 |
|
||||
| 5 | AI router 路由弱(context 死/weight 弱/意图误收敛砍 Data 工具) | crates/df-ai/src/router.rs + intent.rs | 📋 专项登记(memory `ai-router-sanitize-refactor-debt`) |
|
||||
| 6 | sanitize step4 制造 orphan(依赖出口断言兜底) | crates/df-ai/src/context/sanitize.rs | 📋 专项登记(同上) |
|
||||
|
||||
## P2/P3(关键,后续按优先级)
|
||||
|
||||
| 问题 | 位置 | 级别 |
|
||||
|---|---|---|
|
||||
| status 无 union(types.ts AiMessage 无 status,AiMessageWithStatus 双份重复 + cast) | api/types.ts + AiChat.vue + MessageList.vue | P2 |
|
||||
| useAiEvents/useToolCard/useAiSend 胖(900/730/500 行) | composables/ai/ | P2 |
|
||||
| ApprovalPopup _placeholder hack + 审批 action 两套(path 浮窗缺 always) | views/ApprovalPopup.vue | P2 |
|
||||
| df-nodes 6 节点未注册(git/http/docker/notify/subflow,实现完整不可达) | state.rs build_registry | P2 |
|
||||
| parse_review_json(verdict 不规范/score 不 clamp/无正则兜底) | df-nodes/ai_node_helpers.rs | P2 |
|
||||
| provider_pool 亲和不过 model.enabled | crates/df-ai/src/provider_pool.rs | P2 |
|
||||
| df-mcp inputSchema required 形同虚设(handler arg_str_or 静默兜底) | crates/df-mcp/src/tools.rs | P2 |
|
||||
| df-mcp bind_directory 路径校验弱(仅防 ..,无白名单) | crates/df-mcp/src/tools.rs | P2 |
|
||||
| SubflowNode node_type() 用 &'static str 风格分裂 | df-nodes/subflow_node.rs | P3 |
|
||||
| script_node 缺 R-PD-2 安全注释 | df-nodes/script_node.rs | P3 |
|
||||
|
||||
## 推翻假设(走查否定,更新认知)
|
||||
|
||||
- **AiChat.vue 798 行**(非 3000+ God 组件),已抽 5 批(消息列表/输入区/工具卡片/顶栏/侧栏),memory `fe-arch-tech-debt` 过时
|
||||
- **human_node 36KB 是测试 76%**(实现 200 行内聚,无技术债),memory `devflow-workflow-approval-review` 头号 bug(human_node:41 缺 await)已修(line 55-64)+ 双回归测试
|
||||
|
||||
## 修复提交(本次走查)
|
||||
|
||||
- `fc249ad` 全库走查 P0+P1 后端(df-mcp 数据丢失/evaluate 拆 + df-execute probe_pwsh 死缓存/超时/单源 + ai_self_review 注入隔离 + generate_image 测试)
|
||||
- `f719546` 前端走查 P1(MessageList/MessageItem 两套渲染收敛)
|
||||
|
||||
## 专项登记(核心,后续)
|
||||
|
||||
- **AI router + sanitize step4** — memory `ai-router-sanitize-refactor-debt`(核心模块,改风险大,后续专项)
|
||||
- **run_agentic_loop 1217 行重构** — memory `agentic-loop-refactor-debt`(分步拆 finish_round_exit/build_runtime_prompt)
|
||||
|
||||
## 剩余
|
||||
|
||||
- 技能发送后未注入 — SkillResolver 日志(dffc4e4)已加,待打包后测 trace 定位(前端 skill 传?/name 匹配?/read 失败?)
|
||||
- P2/P3 — 后续按优先级 + 用户反馈
|
||||
Reference in New Issue
Block a user