baseline: Clover 独立仓库首次基线提交
将 Clover 从上层产品包旧仓库中独立出来,建立专属版本控制。 当前状态=纵切片端到端已打通(登录→选品→出文出图→审核→下载包), M1文案质量去套路化已验收。此提交作为后续按核销清单逐条修复的基线。 Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
124
plans/13环目标导向-修改验收总纲.md
Normal file
124
plans/13环目标导向-修改验收总纲.md
Normal file
@@ -0,0 +1,124 @@
|
||||
# Clover 13环目标导向 · 修改+验收总纲
|
||||
|
||||
> 倩倩姐2026-06-12定调:以**13环目标为导向**,做交叉验证,Ralph loop循环,真质量达标、流程完整,不假性验证。
|
||||
> 13环出处:`北哥回填解读与落点.md:33-49`。banana本给最硬4环引擎(找竞品/写文案/配图/裂变),本轮补全缺失的引擎环。
|
||||
|
||||
---
|
||||
|
||||
## 〇、模型与通道(2026-06-12拍板,先改这个)
|
||||
|
||||
- Claude 系 → **claude-opus-4-8**(现 `gemini_factory.py:44` 写死 claude-sonnet-4-5,要改)
|
||||
- GPT 系 → **gpt-5.5**(生图 gpt-image-2 不变)
|
||||
- 通道:**仍只用 apiports 一套**,文案不补 codeproxy 第二路径(推翻上一版修7)
|
||||
- 落点:`gemini_factory.py:44 _model_text`、`:166 MODEL_TEXT` 默认值、`.env` 的 MODEL_TEXT
|
||||
|
||||
> ⚠️先确认 apiports 是否真有 claude-opus-4-8 / gpt-5.5(记忆 clover-apiports-real-config 记的是 claude系+gpt5.4/5.5)。改前我会先打一个探活请求验证模型可用,不可用立即回报,不偷偷降级。
|
||||
|
||||
---
|
||||
|
||||
## 一、13环 × 现状 × 本轮动作(全景对照)
|
||||
|
||||
| 环 | 名称 | 现状 | 本轮 | 说明 |
|
||||
|---|---|---|---|---|
|
||||
| 1 | 选题 | ❌ | 不做(人工) | 热搜+爆款词库,人工环节,非系统功能 |
|
||||
| 2 | **竞品爆款分析** | ❌ | **本轮补·引擎环** | =标杆8特征。banana有Invariants骨架,需北哥给8维定义 |
|
||||
| 3 | 关键词 | 🟡隐含 | 随2环 | 长尾词,并入标杆分析产出 |
|
||||
| 4 | 卖点 | 🟡手填 | 随2环 | 竞品评价提炼,并入标杆分析 |
|
||||
| 5 | 写文案 | ✅ | 修bug | 90分过滤/品牌词/客户prompt录入/模型升级 |
|
||||
| 6 | 配图 | ⚠️乱码 | 修bug+3套 | 瓶身叠字/3套差异/强制3:4 |
|
||||
| 7 | 排版 | ❌空白 | 二期 | 字体模板,原始就缺,非阻断 |
|
||||
| 8 | 组长审核 | ✅ | 验收 | 一票否决清单已实现,核对完整度 |
|
||||
| 9 | 发布 | ✅人工 | 不变 | 不自动发,交付包人工发 |
|
||||
| 10 | 复盘 | ❌ | 不做(人工) | 看数据增量,人工环节 |
|
||||
| 11 | **裂变** | ❌ | **本轮补·引擎环** | 1爆款→N套完整笔记包,工作台内独立页 |
|
||||
| 12 | 归档 | 🟡history | 完善 | 日期品类分类 |
|
||||
| 13 | 达人 | ❌ | 不做(人工) | 蒲公英对接,人工环节 |
|
||||
|
||||
**本轮系统要补的引擎环 = 第2环(标杆分析) + 第11环(裂变)。**
|
||||
**本轮要修真bug的环 = 第5环(文案) + 第6环(配图)。**
|
||||
**核对完整的环 = 第8环(审核) + 第12环(归档)。**
|
||||
|
||||
---
|
||||
|
||||
## 二、按环组织的修改清单(替代旧三批分法,以13环为纲)
|
||||
|
||||
### 引擎环·第5环 写文案 — 修bug
|
||||
- 修5a 90分过滤生效(pipeline_io.py:96)+ 0条回退兜底
|
||||
- 修5b 品牌词字段(客户输入,产品级)→ 文案每条植入
|
||||
- 修5c custom_prompt 前端录入框(现表单只有name/category,客户填不进prompt)
|
||||
- 修5d 模型升级 claude-opus-4-8
|
||||
- 修5e 文案网络退避重试(text_variants.py:49)
|
||||
|
||||
### 引擎环·第6环 配图 — 修bug+3套
|
||||
- 修6a 生图3套(角度×风格×叙事结构三正交维度)
|
||||
- 修6b 品牌词进特写图(第2/6张)
|
||||
- 修6c 瓶身中文叠字(先最小版:只叠品牌词一处)
|
||||
- 修6d 强制3:4比例(image_postprocessor.py)
|
||||
- 修6e 生图 ai_call_logs 留痕
|
||||
|
||||
### 引擎环·第2环 竞品爆款分析(标杆8特征)— 新建【需北哥给8维定义】
|
||||
- 建2a 标杆笔记加 features_json 字段+迁移
|
||||
- 建2b 标杆分析service:截图/文本→AI出8特征
|
||||
- 建2c 前端标杆展示8特征
|
||||
- ⏸️ 阻塞:8个维度具体定义,北哥不给做不了
|
||||
|
||||
### 引擎环·第11环 裂变 — 新建·XL【工作台内呈现】
|
||||
- 建11a 裂变表+迁移(裂变记录/参考度/维度)
|
||||
- 建11b 裂变service:1爆款→N套笔记包(文案+图全重做,复用image引擎)
|
||||
- 建11c 裂变router
|
||||
- 建11d 前端裂变页(选爆款→参考度档位→裂变维度→看N套结果),挂工作台导航
|
||||
- ⏸️ 部分阻塞:参考度档位/裂变维度具体值,参考产品包扒包落盘.md:77-84 已有方案骨架
|
||||
|
||||
### 配套·第8环审核 / 第12环归档 — 核对+完善
|
||||
- 修8 导航404(删死链+补/review入口)
|
||||
- 修10 无key置灰引导
|
||||
- 建7 图片lightbox放大
|
||||
- 修12a 归档按日期/品类分类(现history是平铺)
|
||||
|
||||
### 工程底座(贯穿所有环)
|
||||
- 修底1 每用户5并发上限
|
||||
- 修底2 上传magic number校验
|
||||
- 修底3 开任务选标杆入口(benchmark_ids现固定空数组,第2环要用)
|
||||
|
||||
---
|
||||
|
||||
## 三、验收标准(目标导向·可勾门禁·禁假性验证)
|
||||
|
||||
> 每项验收=**可观测的真实结果**,不是"代码写完"。带"怎么验"的具体操作。
|
||||
|
||||
见 `13环验收清单.md`(独立文件,逐项可勾)。
|
||||
|
||||
---
|
||||
|
||||
## 四、Ralph loop 循环验证机制(防假性验证)
|
||||
|
||||
每个环改完,走固定循环,不通过不进下一环:
|
||||
|
||||
1. **改** — 按本环清单改代码
|
||||
2. **跑** — 真实跑一次端到端(不是单测mock,是真调apiports出真文案真图)
|
||||
3. **验** — 对照验收清单逐项勾,**截图/贴输出为证**
|
||||
4. **交叉验** — 另起agent独立读改后代码+独立跑一次,核对结论是否一致
|
||||
5. **不过则回1** — 任一验收项没真勾上,回到改,不允许"差不多了"进下一环
|
||||
6. **门禁** — 每环结束自问:"13环里这一环真勾上了吗?还是只是码更多了?"
|
||||
|
||||
**禁止的假性验证**(倩倩姐红线):
|
||||
- ❌ 只跑单元测试就说"通过"(要真端到端)
|
||||
- ❌ mock掉apiports返回假数据说"能跑"(要真出图真出文案)
|
||||
- ❌ "代码逻辑上应该没问题"(要真观测到结果)
|
||||
- ❌ 跳过验收清单某项说"这个应该OK"(每项都要勾,勾不上如实说)
|
||||
|
||||
---
|
||||
|
||||
## 五、执行顺序建议(纵切片优先)
|
||||
|
||||
**P0 先把第5环+第6环修到真质量达标**(这是已能跑的主链,先让它过关):
|
||||
修5a→5b→5c→5d→5e → 6d→6e→6a→6b → 6c最小版
|
||||
每步走Ralph loop。
|
||||
|
||||
**P1 补第2环标杆分析**(等北哥给8维定义)+ 配套修8/10/12/底1-3。
|
||||
|
||||
**P2 补第11环裂变**(XL,参考扒包落盘方案,工作台内独立页)。
|
||||
|
||||
**待北哥给的定义(卡住P1/P2,先要):**
|
||||
1. 标杆8特征具体哪8维
|
||||
2. 裂变参考度档位(高/中/低)各意味多大改动、裂变维度可选哪些
|
||||
93
plans/13环验收清单.md
Normal file
93
plans/13环验收清单.md
Normal file
@@ -0,0 +1,93 @@
|
||||
# Clover 13环验收清单(逐项可勾·禁假性验证)
|
||||
|
||||
> 每项=可观测真实结果。验收必须真跑端到端+贴输出/截图为证。
|
||||
> 勾选规则:□未做 / ◐做了没验 / ✅真验过(附证据)。报"✅"必附证据,无证据=没完成。
|
||||
|
||||
---
|
||||
|
||||
## 第5环 写文案 验收
|
||||
|
||||
| # | 验收项(怎么验) | 状态 |
|
||||
|---|---|---|
|
||||
| 5-1 | 跑真任务,文案列表只出现≥90分的;查DB text_candidates 无<90分入库(除回退场景) | □ |
|
||||
| 5-2 | 人为造全低分场景,确认回退展示TopN且带"未达90分"标记,不空屏 | □ |
|
||||
| 5-3 | hard_block违禁词的文案永不出现在列表(查DB+查前端) | □ |
|
||||
| 5-4 | 产品填品牌词"龙石",跑任务,**每条文案正文+标题都含"龙石"**(逐条数) | □ |
|
||||
| 5-5 | 产品填custom_prompt"主打油皮",前端能录入,且生成文案体现该指向 | □ |
|
||||
| 5-6 | 确认实际调用模型是 claude-opus-4-8(查ai_call_logs.model字段或抓请求) | □ |
|
||||
| 5-7 | 模拟apiports 503,确认文案自动退避重试而非直接掉本地兜底(查日志) | □ |
|
||||
| 5-8 | 文案符合北哥方法论:佛系人设/无AI味词/5步框架/350-400字(北哥抽看3条认可) | □ |
|
||||
|
||||
## 第6环 配图 验收
|
||||
|
||||
| # | 验收项(怎么验) | 状态 |
|
||||
|---|---|---|
|
||||
| 6-1 | 跑真任务,确认出**3套**图,每套6张,前端能按套切换选择 | □ |
|
||||
| 6-2 | 3套确实不同:套1痛点先行/套2场景先行/套3成分背书先行,角度+风格也不同(肉眼比对不雷同) | □ |
|
||||
| 6-3 | 第2张(特写)、第6张(closer)画面真带品牌词"龙石"(看图) | □ |
|
||||
| 6-4 | 瓶身品牌词清晰不乱码(最小版:代码叠的字清楚)——北哥看图认可 | □ |
|
||||
| 6-5 | 所有输出图严格3:4(1080×1440),查图片实际尺寸 | □ |
|
||||
| 6-6 | 跑完查ai_call_logs有生图条,provider/model/success/latency齐 | □ |
|
||||
| 6-7 | 产品入镜但无参考图时硬失败不降级纯文生图(验铁律未被绕过) | □ |
|
||||
|
||||
## 第2环 竞品爆款分析(标杆8特征)验收【待北哥给8维】
|
||||
|
||||
| # | 验收项 | 状态 |
|
||||
|---|---|---|
|
||||
| 2-1 | 录标杆截图+文本,触发分析,DB features_json 写入8个维度值 | □ |
|
||||
| 2-2 | 前端标杆卡展示8特征 | □ |
|
||||
| 2-3 | 开任务选了标杆,文案/图生成确实参考了标杆特征(对比有无标杆的差异) | □ |
|
||||
| 2-4 | 8维度是北哥确认的定义,不是开发猜的 | □ |
|
||||
|
||||
## 第11环 裂变 验收【XL·工作台内呈现】
|
||||
|
||||
| # | 验收项 | 状态 |
|
||||
|---|---|---|
|
||||
| 11-1 | 工作台有裂变入口(导航/页面可达) | □ |
|
||||
| 11-2 | 选1条爆款→选参考度档位→选裂变维度→生成N套 | □ |
|
||||
| 11-3 | 每套是**完整笔记包**(文案+图+标签+分镜),不只换文案 | □ |
|
||||
| 11-4 | 高参考度学结构但替换表达防抄袭;低参考度只学骨架(对比验证档位真有差异) | □ |
|
||||
| 11-5 | 裂变锁定卖点/标签/人群不变(验证锁定生效) | □ |
|
||||
| 11-6 | 裂变结果可进审核→打包交付(串通主链) | □ |
|
||||
|
||||
## 第8环 审核 验收
|
||||
|
||||
| # | 验收项 | 状态 |
|
||||
|---|---|---|
|
||||
| 8-1 | 所有侧边栏导航点击无404(逐个点) | □ |
|
||||
| 8-2 | 组长能看到待审队列、通过/打回带原因 | □ |
|
||||
| 8-3 | 打回后operator能感知并重选(验证回路闭环,现在是缺口) | □ |
|
||||
|
||||
## 第12环 归档 验收
|
||||
|
||||
| # | 验收项 | 状态 |
|
||||
|---|---|---|
|
||||
| 12-1 | history按日期/品类可分类筛选(现是平铺) | □ |
|
||||
| 12-2 | approved任务能下载交付包,zip结构完整(笔记夹+命名+文案.txt+清单+合规说明) | □ |
|
||||
| 12-3 | 客户输入物(产品/标杆)可导出(数据归属红线) | □ |
|
||||
|
||||
## 工程底座 验收
|
||||
|
||||
| # | 验收项 | 状态 |
|
||||
|---|---|---|
|
||||
| 底-1 | 同一用户开第6个任务被拒/排队(验5并发上限) | □ |
|
||||
| 底-2 | .exe改名.jpg+伪造content-type上传被拒(验magic number) | □ |
|
||||
| 底-3 | 开任务页能选标杆(benchmark_ids不再固定空) | □ |
|
||||
| 底-4 | 无key时开任务按钮置灰+引导去配置 | □ |
|
||||
| 底-5 | 图片可点击放大看细节(lightbox) | □ |
|
||||
| 底-6 | 前端无任何token余额/用量展示(红线,全页扫) | □ |
|
||||
| 底-7 | SSE用一次性ticket,URL无JWT(抓connection验证) | □ |
|
||||
|
||||
---
|
||||
|
||||
## 一条龙总验收(纵切片,最高门禁)
|
||||
|
||||
**唯一的"真完成"定义**:一个新用户,从零走通——
|
||||
登录 → 建产品(填品牌词+custom_prompt+传图) → 录标杆 → 开任务(选标杆) → 出≥90分文案(含品牌词) → 出3套不雷同的图(3:4,特写带品牌词) → 确认 → 提审 → 组长过 → 下载到结构完整的交付包。
|
||||
|
||||
**全程不报错、不假数据、北哥抽检文案+图认可质量。**
|
||||
|
||||
□ 一条龙真跑通(录屏为证)
|
||||
□ 北哥抽检认可(北哥确认)
|
||||
|
||||
> 这两项不勾上,其余全勾也不算完(CLAUDE.md验收线:质量过关才算完,最终北哥认可)。
|
||||
107
plans/Clover前端逻辑诊断-数据流与交互.md
Normal file
107
plans/Clover前端逻辑诊断-数据流与交互.md
Normal file
@@ -0,0 +1,107 @@
|
||||
# Clover 前端逻辑诊断 · 数据流与交互(第一次扒·另一窗口改完需重扒)
|
||||
|
||||
> 你的直觉对了:"功能呈现和数据流转交互太弱"——但弱在**数据流架构**,不只在界面长相。
|
||||
> 扒的是:3个zustand store(generation/task/preference) + api.ts + useSse + sse.ts。
|
||||
> ⚠️ 另一窗口正在改前端,本次结论是当前快照,改完重扒对比。
|
||||
|
||||
---
|
||||
|
||||
## 一、先画出前端真实的数据流
|
||||
|
||||
```
|
||||
┌─ 进任务页 ─────────────────────────────────────────────┐
|
||||
│ useSse(taskId) 启动 │
|
||||
│ ① 立即 GET /tasks/{id} → hydrateFromTask (回填历史候选) │
|
||||
│ ② 建 SSE: 先POST换ticket → EventSource连stream │
|
||||
│ ③ SSE事件 → handleEvent → 写 generationStore │
|
||||
└──────────────────────────────────────────────────────┘
|
||||
↓ 组件从 store 订阅渲染
|
||||
text/images页 读 generationStore.textCandidates 等
|
||||
↓ 用户选择
|
||||
taskStore.selectedTextIds (纯本地数组)
|
||||
↓ 点"下一步"
|
||||
for循环逐个 POST select → router.push 下一页
|
||||
```
|
||||
|
||||
**三个store各管一摊:**
|
||||
- `generationStore`:SSE进度+候选+飞轮注入(生成态)
|
||||
- `taskStore`:当前任务id+已选id数组(选择态)
|
||||
- `preferenceStore`:飞轮偏好摘要(注入态)
|
||||
|
||||
<!-- 后续Edit补充:二、数据流的7个弱点 / 三、交互弱的根因 / 四、对照俊达该补什么 / 五、待重扒清单 -->
|
||||
|
||||
---
|
||||
|
||||
## 二、数据流的7个弱点(每条带代码证据)
|
||||
|
||||
### 弱点1:策略维度A/B/C在前端被彻底抹平 🔴最关键
|
||||
- 后端生图按3套策略各N张(`pipeline_io.py:201`),SSE的`image_candidate`事件**带了strategy字段**(`useSse.ts:104`接收了)。
|
||||
- 但 `generationStore.imageCandidates` 是**一维平铺数组**(store注释明写"image_candidate无batch字段所以平铺"),images页直接`grid`铺开。
|
||||
- **后果**:后端辛苦做的"3个叙事方向×N张给你对比挑选",前端变成一堆看不出分组的散图。用户不知道哪些是同一策略、为什么有18张。这是"交互弱"最硬的证据——**信息结构在展示层塌掉了**。
|
||||
|
||||
### 弱点2:文案五维分要二次请求补全,且每条都重拉整个task 🔴
|
||||
- `useSse.ts:75-94`:SSE的`text_candidate`只推total分,五维明细**靠再次 GET /tasks/{id} 补全**。
|
||||
- 致命:**每来一条文案候选就GET一次整个task**(line88),8条文案=8次全量请求,每次返回所有候选。N条候选→N次重复拉全量,越往后越浪费。
|
||||
- **后果**:五维分有延迟跳变(先0后补),且网络浪费。交互上是"分数闪一下才出来"。
|
||||
|
||||
### 弱点3:选择态是纯本地数组,不落后端、刷新即丢 🟡
|
||||
- `taskStore.selectedTextIds/selectedImageIds` 只在内存(line13)。
|
||||
- 选文案时`toggleTextSelection`只改本地数组,**点"下一步"才 for循环逐个POST select**(`text/page.tsx:29-32`)。
|
||||
- **后果**:①选到一半刷新页面,选择全没了 ②多选N条就发N个请求(不是批量) ③选中状态和后端`is_selected`字段不实时同步。
|
||||
|
||||
### 弱点4:跳转用 router.push,候选数据靠"重新拉" 🟡
|
||||
- 每个环节(text→images→confirm)是独立页面,靠`router.push`跳转。
|
||||
- 进每页 `useSse` 都`store.reset()`再`hydrateFromTask`重新GET(`useSse.ts:21,30`)。
|
||||
- **后果**:环节间无"连续流"感,每跳一页是一次重新加载+重连SSE。confirm页要的已选数据,靠`generationStore`里还留着的候选`filter`出来(`confirm/page.tsx:22-23`)——**万一store被reset就空了**。
|
||||
|
||||
### 弱点5:confirm页数据来源脆弱 🟡
|
||||
- `confirm/page.tsx:22` 用`textCandidates.filter(selectedTextIds.includes)`拿已选内容。
|
||||
- 但`selectedTextIds`在taskStore、`textCandidates`在generationStore,**两个store没绑定**。SSE的reset只清generationStore,selectedTextIds还在taskStore——两者生命周期不一致,容易错位。
|
||||
|
||||
### 弱点6:错误处理静默吞掉 🟡
|
||||
- `useSse.ts:37,93` 多处`.catch(() => {})`空吞错误;`preferenceStore:31`无偏好"不阻塞流程"也静默。
|
||||
- **后果**:数据没拉到时用户无感知,界面就是"空着",不知道是没数据还是出错了。这放大了"空"的感受。
|
||||
|
||||
### 弱点7:SSE的task_done/error事件没驱动UI 🟡
|
||||
- `useSse.ts:123-127`:`error`/`task_done`/`analyze_done`/`heartbeat`全部`break`空处理。
|
||||
- **后果**:生成完成了(task_done)前端不弹提示、不自动跳转;出错了(error)也不显式告诉用户。状态机的关键节点在前端是哑的。
|
||||
|
||||
---
|
||||
|
||||
## 三、为什么"交互弱"——根因归纳
|
||||
|
||||
| 表象 | 数据流根因 |
|
||||
|---|---|
|
||||
| 图一堆看不出门道 | 策略维度被平铺抹平(弱点1) |
|
||||
| 分数闪一下才出 | 五维分二次请求补全(弱点2) |
|
||||
| 选着选着没了 | 选择态纯本地不持久(弱点3) |
|
||||
| 翻页像重新加载 | 页面级跳转+每页重连重拉(弱点4) |
|
||||
| 完成/出错没反馈 | 关键SSE事件空处理(弱点7)+错误静默(弱点6) |
|
||||
|
||||
> **本质**:前端是"**被动渲染后端推什么显示什么**"的薄层,没有自己的"数据组织能力"。后端给的多维数据(策略/评分/角色/理由),前端要么拍平、要么二次拉、要么不展示。**不是界面不好看,是数据进了前端没被'组织'成有结构的交互。**
|
||||
|
||||
---
|
||||
|
||||
## 四、对照俊达:他的前端为什么"饱满流畅"
|
||||
|
||||
俊达界面给人"饱满"感,本质是**数据被组织出了层次**:
|
||||
- 同一组图按策略/角色分组对比 → Clover平铺(弱点1)
|
||||
- 每个产出带可见的评分/理由/标签 → Clover评分要补拉、理由没全显(弱点2)
|
||||
- 操作即时反馈、状态流转有动效 → Clover关键事件空处理(弱点7)
|
||||
- 进化页/复盘页是"数据看板" → Clover dashboard是3个按钮
|
||||
|
||||
> 借鉴点(不抄原文):**把"后端已有的多维数据"在前端组织成有结构的呈现**——分组、即时反馈、状态可见。这是纯前端重构,不依赖后端加功能,也不碰俊达的knowhow。
|
||||
|
||||
---
|
||||
|
||||
## 五、待重扒清单(另一窗口改完后)
|
||||
|
||||
本次基于当前快照。另一窗口改完前端后,重点复查这几项有没有变:
|
||||
1. `generationStore` 的 imageCandidates 有没有改成按strategy分组
|
||||
2. `useSse` 的五维分补全有没有改掉"每条拉全量task"
|
||||
3. taskStore 选择态有没有改成持久化/批量提交
|
||||
4. 关键SSE事件(task_done/error)有没有接UI反馈
|
||||
5. dashboard 有没有加数据看板
|
||||
6. images页有没有按A/B/C分组展示
|
||||
|
||||
> 重扒方法:对这6个文件做 diff,对照本文档逐条核实改了没。本文档是"改之前"的基线。
|
||||
172
plans/Clover完整修改清单与方案.md
Normal file
172
plans/Clover完整修改清单与方案.md
Normal file
@@ -0,0 +1,172 @@
|
||||
# Clover 完整修改清单 + 方案(基于全量代码扒解)
|
||||
|
||||
> 来源:汇总《链路缺失诊断》《真实能力盘点》《前端逻辑诊断》三份扒解结论,去重去错判后的可执行清单。
|
||||
> 口径:每条带【问题】【位置】【改法】【冲突】【工作量】。冲突=与另一窗口改前端的碰撞风险。
|
||||
> ⚠️ 另一窗口在改前端,🔴冲突项落地前必须先 git status + 与那边对齐。
|
||||
> 日期:2026-06-12
|
||||
|
||||
---
|
||||
|
||||
## 总览:四类问题
|
||||
|
||||
| 类 | 条数 | 性质 |
|
||||
|---|---|---|
|
||||
| A. Bug类(必修) | 1 | 死链404,立刻劝退用户 |
|
||||
| B. 前端数据流(交互弱根因) | 7 | 后端数据进了前端没组织好 |
|
||||
| C. 前端展示薄(能力没露) | 4 | 后端算了前端没显示 |
|
||||
| D. 后端真缺口(从0做) | 3 | 改稿信号/数据复盘/爆款拆解AI |
|
||||
|
||||
> 关键认知:**A+B+C 共12条都是"前端接线/重构",不依赖后端加功能**。D类3条才是真·新功能。**先做A/B/C投入产出比最高**——把后端已有能力露出来,界面立刻"饱满"。
|
||||
|
||||
<!-- 后续Edit补充:A类详情 / B类详情 / C类详情 / D类详情 / 执行顺序建议 -->
|
||||
|
||||
---
|
||||
|
||||
## A 类 · Bug(必修)
|
||||
|
||||
### A1. Sidebar 导航死链 404 🔴必修
|
||||
- **问题**:侧边栏4个入口指向不存在的路由,一点就404。
|
||||
- **位置**:`frontend/src/components/layout/Sidebar.tsx:22-25`,写死 `/tasks`、`/images`、`/tasks/build`、`/tasks/list`,真实只有 `/tasks/[id]/text`、`/tasks/[id]/images`,且需taskId。
|
||||
- **改法**:导航语义改成"任务流"——侧栏只放真实可达的全局页(工作台/开新任务/审核台/历史/配置),删掉"选择文案/选择图片/建立任务/任务列表"这类需taskId的环节级入口;环节入口由"当前任务"动态带id跳转(dashboard已有RecentTasksBar可复用)。
|
||||
- **冲突**:🟢低(Sidebar是导航文件,另一窗口大概率没动,先 git status 确认)
|
||||
- **工作量**:0.5天
|
||||
|
||||
---
|
||||
|
||||
## B 类 · 前端数据流(交互弱的根因,7条)
|
||||
|
||||
### B1. 生图策略 A/B/C 维度被前端抹平 🔴最关键
|
||||
- **问题**:后端按3套叙事策略各N张生图(要6张→生18张),SSE带strategy字段、前端也收到了,但存成一维平铺数组,images页一堆散图看不出分组。
|
||||
- **位置**:`stores/generationStore.ts`(imageCandidates平铺) + `app/tasks/[id]/images/page.tsx:55-68`(grid平铺) + `useSse.ts:101-108`(收了strategy没用来分组)。
|
||||
- **改法**:generationStore 的 imageCandidates 改成**按 strategy 分组**(`{A:[], B:[], C:[]}` 或 groupBy);images页改成**3列/3段分策略展示**,每套标注"方向A/B/C",让用户在3个叙事方向间对比挑选。这正是俊达"多方向选优"的呈现。
|
||||
- **冲突**:🔴高(直接改前端核心store+页面,另一窗口最可能在这一带)
|
||||
- **工作量**:1-2天
|
||||
|
||||
### B2. 五维分二次请求 + 每条重拉全量task 🔴
|
||||
- **问题**:SSE只推总分,五维明细靠再GET整个task补全,且每来一条候选就GET一次全量(8条=8次重复全量请求),分数先0后跳变。
|
||||
- **位置**:`useSse.ts:75-94`。
|
||||
- **改法(二选一)**:①推荐——让后端SSE的`text_candidate`事件**直接带五维明细**(score_detail),前端一次到位不用补拉(要后端配合改sse事件payload,碰后端);②纯前端——补拉改成**全部候选生成完后只GET一次**批量补分,不要每条拉。
|
||||
- **冲突**:🟡中(改useSse;方案①还要碰后端sse_utils)
|
||||
- **工作量**:0.5-1天
|
||||
|
||||
### B3. 选择态纯本地、刷新即丢、不批量 🟡
|
||||
- **问题**:selectedTextIds/selectedImageIds只在内存,刷新全没;点下一步才for循环逐个POST(N条N请求)。
|
||||
- **位置**:`stores/taskStore.ts:13` + `app/tasks/[id]/text/page.tsx:29-32`。
|
||||
- **改法**:①选择即时 POST select(或localStorage暂存),刷新可恢复;②或保留本地但提供**批量select接口**一次提交(要后端加批量端点)。最低成本:选择态存localStorage按taskId隔离,进页面恢复。
|
||||
- **冲突**:🟡中(改taskStore)
|
||||
- **工作量**:0.5天
|
||||
|
||||
### B4. 页面级跳转,每页 reset+重连SSE 🟡
|
||||
- **问题**:text→images→confirm独立页,每进一页useSse都reset再重新GET+重建SSE,无连续流感。
|
||||
- **位置**:`useSse.ts:21,30`(每次reset+hydrate) + 各页independent。
|
||||
- **改法**:①已完成阶段的候选不必重连SSE(只生成中才连)——按task.status判断要不要建SSE连接,已selection/review态只拉一次数据不连流;②或用单一任务容器布局保留store不reset跨环节。
|
||||
- **冲突**:🟡中
|
||||
- **工作量**:1天
|
||||
|
||||
### B5. confirm页数据来源脆弱(跨store错位)🟡
|
||||
- **问题**:confirm用 generationStore.textCandidates.filter(taskStore.selectedTextIds) 拼已选,两store生命周期不一致,reset一边另一边错位就显空。
|
||||
- **位置**:`app/tasks/[id]/confirm/page.tsx:22-23`。
|
||||
- **改法**:confirm页**独立GET /tasks/{id}** 拿权威的is_selected候选,不依赖两个store的内存拼接。后端get_task已返is_selected,直接用。
|
||||
- **冲突**:🟡中
|
||||
- **工作量**:0.5天
|
||||
|
||||
### B6. 错误静默吞掉,放大"空"感 🟡
|
||||
- **问题**:多处 `.catch(()=>{})` 空吞,数据没拉到用户只见空白,不知是没数据还是出错。
|
||||
- **位置**:`useSse.ts:37,93`、`preferenceStore.ts:31` 等。
|
||||
- **改法**:catch里至少 set一个error态,页面区分"加载中/空数据/出错可重试"三态,给空状态配文案+重试按钮(review页已有空态范例可抄)。
|
||||
- **冲突**:🟢低(加错误态,不动主逻辑)
|
||||
- **工作量**:0.5天
|
||||
|
||||
### B7. 关键SSE事件(task_done/error)空处理 🟡
|
||||
- **问题**:task_done生成完不提示不跳转、error出错不告知,状态机关键节点前端是哑的。
|
||||
- **位置**:`useSse.ts:123-127`(全部break)。
|
||||
- **改法**:task_done→toast"生成完成"+按钮去挑选/自动滚动;error→显式错误条+重试入口;heartbeat可继续忽略。
|
||||
- **冲突**:🟢低
|
||||
- **工作量**:0.5天
|
||||
|
||||
---
|
||||
|
||||
## C 类 · 前端展示薄(后端算了没露,4条)
|
||||
|
||||
### C1. dashboard 门面空 🔴
|
||||
- **问题**:工作台只有1句问候+3个按钮,后端那么多能力(今日生成/待审/飞轮进度/近期任务)一个没露。第一眼就"空"。
|
||||
- **位置**:`app/dashboard/page.tsx`。
|
||||
- **改法**:加数据看板——今日生成任务数/待审数/已通过数(GET /tasks?status=统计)、近期任务流(RecentTasksBar已有)、飞轮已学信号数(GET preference/context)。把后端有的数字摆出来。
|
||||
- **冲突**:🟢低(dashboard另一窗口少碰,新增展示)
|
||||
- **工作量**:1天
|
||||
|
||||
### C2. 审核卡不显示七维分 🔴
|
||||
- **问题**:审核员通过/打回时**看不到AI评委打分**,盲拍。后端有score但review队列没返、卡没显。
|
||||
- **位置**:`components/review/ReviewCard.tsx`(只显product/theme/正文2行) + `api/v1/review.py:_fmt_queue_item`(没返score_json)。
|
||||
- **改法**:`_fmt_queue_item`补返已选文案的score_json+verdict+summary;ReviewCard复用ScoreDimBars组件显分。让审核基于分数。
|
||||
- **冲突**:🟡中(碰review.py,但approve/reject逻辑不动,只加返回字段)
|
||||
- **工作量**:0.5天
|
||||
|
||||
### C3. 图片候选只显url+role 🟡
|
||||
- **问题**:后端storyboard算了每张图的goal/卖点/视觉策略/角色,`_fmt_image`只返role/url/strategy/seq,前端只显url+role。
|
||||
- **位置**:`api/v1/tasks.py:_fmt_image` + images页/ImageProgressCard。
|
||||
- **改法**:先定要不要把分镜role中文化(hook→"封面钩子")+显示该图承担的叙事角色;进阶可让后端存storyboard的overlay_text等供前端显示"这张图要表达什么"。
|
||||
- **冲突**:🟡中
|
||||
- **工作量**:0.5-1天
|
||||
|
||||
### C4. ConfigPreviewPanel 注释与实现不符 🟢
|
||||
- **问题**:注释说"显示成分/质地/参考图3张",实际代码只渲染名称/品类/卖点/风格/角度,没参考图没成分。
|
||||
- **位置**:`components/tasks/ConfigPreviewPanel.tsx`。
|
||||
- **改法**:要么补上参考图缩略(product.image_path后端有)+目标人群target_audience/brand_keyword(后端012字段已有),要么改注释对齐实现。建议补字段,产品档案信息更全。
|
||||
- **冲突**:🟢低
|
||||
- **工作量**:0.5天
|
||||
|
||||
---
|
||||
|
||||
## D 类 · 后端真缺口(从0做,3条)
|
||||
|
||||
### D1. 改稿→飞轮信号(最强信号)🔴价值最高
|
||||
- **问题**:俊达最强飞轮信号是"人改AI稿",Clover完全没有。enums无text_edit、TextCandidate无edited字段。
|
||||
- **位置**:`constants/enums.py:57`(SignalType)+`ai_engine/constants.py`(FLYWHEEL_WEIGHTS两处)、`models/task.py:TextCandidate`、新端点、`preference_aggregator.py`(注入改稿示范)、`TextCandidateCard.tsx`(加可编辑)。
|
||||
- **改法**:已有独立细案《俊达增量①-改稿diff-实施细案.md》,S1-S5全拆好+并发避让(走task_actions不碰review.py)。直接按那份做。
|
||||
- **冲突**:🔴高(碰enums,两处权重要手工merge;细案已设计绕开review.py)
|
||||
- **工作量**:2-3天
|
||||
|
||||
### D2. 数据复盘——发布后数据回收 🔴真缺
|
||||
- **问题**:链路止于下载交付包,发出去的赞藏评/转化完全不回收,飞轮缺"结果反馈"闭环。全后端无此模块。
|
||||
- **位置**:全新——新表(note_performance)+录入入口(手填或导入)+复盘页+回灌飞轮。
|
||||
- **改法**:一期可极简——人工回填"这篇发布后数据如何"(赞藏评/是否爆),进库当强信号回灌。不必自动抓小红书(合规+反爬风险高)。
|
||||
- **冲突**:🟢低(全新模块)
|
||||
- **工作量**:3-5天(含UI)
|
||||
|
||||
### D3. 爆款拆解 AI 解析逻辑 🟡
|
||||
- **问题**:BenchmarkNote有features_json+analyze_status字段、fission.py有裂变引擎,但**爆款8特征的AI解析逻辑+UI没接**。
|
||||
- **位置**:`models/product.py:BenchmarkNote`(字段已建)、`fission.py`(引擎已建)、缺service+缺UI入口。
|
||||
- **改法**:补"标杆笔记→AI拆8特征→写features_json"的service+触发按钮;裂变引擎接前端入口(选爆款→设套数→生成)。字段和引擎都在,主要是接线+AI prompt。
|
||||
- **冲突**:🟢低(基本全新接线)
|
||||
- **工作量**:2-3天
|
||||
|
||||
---
|
||||
|
||||
## 执行顺序建议(按ROI + 并发安全)
|
||||
|
||||
> 原则:先低冲突高收益、把后端已有能力露出来,再碰高冲突和从0做的。具体哪些交AI、哪些你亲自看,你拍。
|
||||
|
||||
**第一波·低冲突立竿见影(可立刻做,避开另一窗口热区):**
|
||||
- A1死链(0.5d) + B6错误态(0.5d) + B7关键事件(0.5d) + C4配置面板(0.5d) + C1 dashboard看板(1d)
|
||||
- 小计~3天,界面立刻不报错+变饱满,几乎不碰另一窗口核心文件
|
||||
|
||||
**第二波·数据流重构(需与另一窗口对齐后做):**
|
||||
- B1策略分组(1-2d,最关键) + B2五维分(0.5-1d) + C2审核显分(0.5d) + B5 confirm独立拉(0.5d)
|
||||
- 小计~3-4天,解决"交互弱"主因
|
||||
|
||||
**第三波·收尾前端:**
|
||||
- B3选择持久(0.5d) + B4跳转优化(1d) + C3图片信息(0.5-1d)
|
||||
|
||||
**第四波·后端新功能(从0做,独立推进):**
|
||||
- D1改稿diff(2-3d,价值最高) → D3爆款拆解接线(2-3d) → D2数据复盘(3-5d)
|
||||
|
||||
> ⚠️ 三条铁律:①🔴冲突项动手前必 git status + 跟另一窗口对齐 ②D1严格按已有细案走(绕开review.py) ③每波做完先验证(build+跑通)再下一波。
|
||||
|
||||
---
|
||||
|
||||
## 一句话给倩倩姐
|
||||
|
||||
**12条前端问题(A+B+C)本质是"接线/重构",把后端已经做好的能力露出来,界面立刻饱满、交互立刻顺——这是性价比最高的。3条后端缺口(D)才是真新功能,其中改稿diff价值最高、细案已就绪。**
|
||||
|
||||
> 待另一窗口改完,B/C类要按《前端逻辑诊断》第五节6项重扒对比,确认哪些那边已经改了,避免重复劳动。
|
||||
143
plans/Clover真实能力盘点与对照修正.md
Normal file
143
plans/Clover真实能力盘点与对照修正.md
Normal file
@@ -0,0 +1,143 @@
|
||||
# Clover 真实能力盘点 + 对照修正(读完6365行后端后的诚实版)
|
||||
|
||||
> ⚠️ 重要:本文档**修正**我之前《俊达vsClover-逐界面对照缺陷清单》里的多处错判。
|
||||
> 之前只读了前端8页+零星后端就下结论,冤枉了好几处。这次读完后端全部API+核心services+workers后重写。
|
||||
> 倩倩姐在另一窗口"看到功能挺多"是对的——很多能力**在后端实现了,只是前端没接/没可视化**。
|
||||
|
||||
---
|
||||
|
||||
## 一、先认错:我之前判错的地方
|
||||
|
||||
| 我之前的判断 | 真实情况(代码为证) | 性质 |
|
||||
|---|---|---|
|
||||
| "改稿环节缺失" | ✅确实没有改稿。但我没说清:选优/重生成/导入轨都有(`task_actions.py`) | 判断对,但描述把整体说薄了 |
|
||||
| "图片卡信息薄=只有url+role" | 后端 `ImageCandidate` 确实只存role/url/strategy/seq,**但生图引擎极丰富**(见下) | 🔴**冤枉**:薄的是展示,不是能力 |
|
||||
| "拆解中心只能录入不能拆配方" | `fission.py`是**第11环裂变引擎**(1爆款→N套笔记包),不是"只录入" | 🔴**判错**:裂变能力建了表,是没接UI |
|
||||
| "平台对抗待确认Clover做到哪" | `image_postprocessor.py`**已实现**:去元数据+削像素水印+SynthID破除+Gemini重绘兜底 | 🔴**漏看**:对抗层早做了 |
|
||||
| "双通道生图待确认" | `image_gen.py`**已实现**主备通道(gpt-image-2主/Gemini备)+多中转站(apiports/codeproxy)切换+重试退避 | 🔴**漏看**:双通道在 |
|
||||
| "模板库藏代码里" | storyboard有完整分镜模板体系(`storyboard_templates.py`174行) | 部分对,但低估了成熟度 |
|
||||
|
||||
> 教训:我拿"前端没显示"当"功能不存在",这是硬伤。**Clover后端比前端展示出来的强得多。**
|
||||
|
||||
<!-- 后续Edit补充:二、后端真实能力全景 / 三、真正的缺口(修正版) / 四、前后端能力落差 / 五、对照俊达的真实差距 -->
|
||||
|
||||
---
|
||||
|
||||
## 二、后端真实能力全景(读完代码确证·这些都已实现)
|
||||
|
||||
**文案生成链(强):**
|
||||
- `_text_prompt.py`:人设/随机变量池ABC/5步框架/四段结构/5类标题公式/反AI味/emoji规则,方法层vs数据层分离
|
||||
- `text_variants.py`:双轨(AI生成+导入)、分批生成(避60s网关超时)、三层兜底、可选优化轮、本地草稿兜底
|
||||
- `llm_scorer.py`:**AI评委打分**——模型真读文案给6维分+理由+verdict+summary,合规第7维机械硬拦,失败回退机械打分
|
||||
- `replenish_task.py`:合格数不足时**后台异步补充**到目标条数(先展示后台补铁律)
|
||||
|
||||
**生图链(很强,我之前严重低估):**
|
||||
- `storyboard.py`:**分镜引擎**——按图数排叙事角色(3/6/8张不同链路)、品牌词第2/6张植入、逐图差异化9字段prompt、成组视觉统一
|
||||
- `image_gen.py`:**主备双通道**(gpt-image-2带产品图edits / Gemini备)、多中转站切换、限并发、指数退避重试
|
||||
- `image_postprocessor.py`:**去AI化对抗**——去C2PA元数据+轻/重采样削像素水印+SynthID破除(可选)+Gemini重绘兜底
|
||||
|
||||
**飞轮链(已转):**
|
||||
- `preference_aggregator.py`:聚合最近50条信号→偏好角度+打回原因→注入prompt;冷启动用产品档案;按product_id隔离防串货;三层继承(L1品牌>L2矩阵>L3个人)
|
||||
- `task_actions.py`:选文案+3/选图+3/重生成-1 信号都记录
|
||||
- `flywheel_service.py`:record_signal + get_preference_context
|
||||
|
||||
**裂变链(建了表+引擎,待接UI):**
|
||||
- `fission.py`:第11环裂变引擎,1爆款→N套完整笔记包,带reference_level/fanout_count/status状态机
|
||||
|
||||
**交付链(完整):**
|
||||
- `delivery.py`:打包→一次性下载令牌(60s)→FileResponse下载,双认证(token/JWT)
|
||||
|
||||
---
|
||||
|
||||
## 三、真正的缺口(修正版·只留确证的)
|
||||
|
||||
读完后端后,真正站得住的缺口收敛到这几条:
|
||||
|
||||
| 缺口 | 性质 | 确证依据 |
|
||||
|---|---|---|
|
||||
| **1. 改稿→飞轮信号** | 真缺 | `SignalType`(enums.py:57)无text_edit;`TextCandidate`无edited字段。这条仍成立 |
|
||||
| **2. 裂变引擎没接前端UI** | 真缺UI | `fission.py`引擎在,但前端无裂变页、无入口 |
|
||||
| **3. 数据复盘(发布后回收)** | 真缺 | 全后端无"发布后赞藏评回收"模块,链路止于交付包 |
|
||||
| **4. dashboard门面空** | 真缺 | `dashboard/page.tsx`只有3按钮,后端那么多能力一个没露 |
|
||||
| **5. Sidebar死链404** | 真bug | `Sidebar.tsx:22-25`指向不存在路由 |
|
||||
| **6. 图片候选展示薄** | 展示缺,非能力缺 | 后端storyboard算了role/goal/卖点/视觉策略,但`_fmt_image`只返role/url/strategy/seq,前端只显示url+role |
|
||||
| **7. AI评委理由没充分展示** | 展示缺 | 后端有verdict/summary/6维note,前端TextCandidateCard展示了,但confirm页等只显示总分 |
|
||||
|
||||
> **关键转变**:之前我列的"素材库缺失/拆解缺失/对抗缺失/双通道缺失"大半是错的——**对抗、双通道、分镜、裂变引擎后端都有**。真缺口收敛到:①改稿信号 ②裂变没接UI ③数据复盘 ④门面空 ⑤死链 + 两处展示薄。
|
||||
|
||||
---
|
||||
|
||||
## 四、前后端能力落差(这才是"空"的真因)
|
||||
|
||||
**这是核心洞察**:Clover 的问题不是"功能少",是**后端能力没在前端露出来**。
|
||||
|
||||
| 后端有的能力 | 前端露出了吗 |
|
||||
|---|---|
|
||||
| 分镜引擎(每张图有role/goal/卖点/视觉策略/依据) | 🔴只显示url+role两字段 |
|
||||
| 主备双通道+对抗去AI化 | 🔴用户完全无感(后台默默跑) |
|
||||
| AI评委6维分+理由+verdict | 🟡文案卡露了,其他页只剩总分 |
|
||||
| 后台补充合格文案 | 🔴用户不知道在补 |
|
||||
| 裂变引擎 | 🔴无入口 |
|
||||
| 飞轮偏好注入 | 🟡只一条banner |
|
||||
|
||||
> 俊达"界面饱满"的感觉,本质是**他把后台算的每一步都可视化了**。Clover后台算得不比他少,但**前端只露了冰山一角**,所以显得"空"。这跟"功能缺失"是两个完全不同的问题——**前者是接线/可视化工作量,后者是从0造功能。Clover大多属前者。**
|
||||
|
||||
---
|
||||
|
||||
## 五、对照俊达的真实差距(收敛后)
|
||||
|
||||
| 维度 | 真实结论 |
|
||||
|---|---|
|
||||
| 文案生成 | **不弱于俊达**,AI评委+飞轮+反AI味都有 |
|
||||
| 生图质量工程 | **可能不弱**,双通道+分镜+对抗去AI化都有 |
|
||||
| 飞轮 | 骨架在,**缺最强信号(改稿diff)**,且可视化弱 |
|
||||
| 资产化/裂变 | **引擎在,缺UI接线** |
|
||||
| 数据复盘 | **真缺**(俊达有发布后回收,Clover止于交付) |
|
||||
| SCRM销售线 | 整块没做(商业决策,待倩倩姐判) |
|
||||
| **呈现/可视化** | **这是最大差距**——后端能力强,前端露太少,所以"显空" |
|
||||
|
||||
> 一句话修正:**不是Clover功能比俊达少很多,是Clover把做好的能力藏在后端没给用户看。** 你那个窗口看到"功能挺多",看到的就是这些后端实现。我之前只扫前端,所以误判成"空、缺失"。
|
||||
|
||||
---
|
||||
|
||||
## 六、仍未读、不装看到的
|
||||
|
||||
- `products.py`(308行,最大文件) — 产品档案完整能力未读
|
||||
- `pipeline_io.py`(298行) — 文案/图片生成存储编排未读
|
||||
- `gemini_factory.py`(225行) — AI客户端构造未读
|
||||
- `storyboard_templates.py`/`_score_prompt.py`/`_scoring_dims.py` — 模板和评分维度细节未读
|
||||
- 前端:`ImageProgressCard`/`ReviewCard`/`ConfigPreviewPanel`等组件本体未读
|
||||
- 数据库迁移到011,011/010之后有无新增未确认
|
||||
|
||||
> 要补到100%确证,这几个还得读。但**主干结论(后端强、前端露得少、真缺口5条)已经站得住**。
|
||||
|
||||
---
|
||||
|
||||
## 七、补读完成(已清零未读区)— 又发现3处关键事实
|
||||
|
||||
读完 `products.py`/`pipeline_io.py`/`review.py` + 前端剩余组件后,新增确证:
|
||||
|
||||
### 新发现1:生图实际跑「3套正交策略 × N张」,前端拍平丢了策略维度 🔴
|
||||
- `pipeline_io.py:201` 明写 `for strategy in ("A","B","C")`,每套各生 image_count 张。**用户要6张→后端实际生18张候选**。
|
||||
- `ImageProgressCard.tsx` 本是为"批次/策略"设计的(有BatchState),**但 images 页(line55-68)是平铺所有图、没按A/B/C分组**,`_fmt_image` 返回了strategy字段但前端没用来分组。
|
||||
- 结论:**后端做了"3种叙事方向给你挑",前端拍平成一堆散图**。这是俊达"双通道选优"思路Clover其实有雏形(3策略),但展示层没体现。
|
||||
|
||||
### 新发现2:产品图 vision 智能分析已实现 🟢(我完全没提过)
|
||||
- `products.py:254` `analyze-image` 接口:上传产品图→GPT vision 读图→自动产出卖点/人群/场景/关键词/违禁词/拍摄方向 JSON。
|
||||
- 这等于俊达"拆解"能力的一种——**只是用在产品建档,不是用在爆款逆向**。Clover有读图理解能力,我之前一字未提。
|
||||
|
||||
### 新发现3:爆款8特征分析字段已建 🟡
|
||||
- `BenchmarkNote.features_json` + `analyze_status`(pending/analyzing/done/failed):标杆笔记预留了"AI解析8特征"的字段和状态机。
|
||||
- 说明"爆款拆解"在数据层已开口子,差AI解析逻辑+UI。比我之前说的"只能录入"更进一步。
|
||||
|
||||
### 复核确认的展示薄(确证):
|
||||
- `ReviewCard`:审核卡只显示 product/operator/theme/正文2行+图,**不显示七维分**——审核员看不到AI评委打分就要拍板通过/打回。这是确证的展示缺失。
|
||||
- `ConfigPreviewPanel`:注释说"显示成分/质地/参考图3张",**实际代码没渲染参考图、没成分**,只有名称/品类/卖点/风格/角度。注释与实现不符。
|
||||
- `ScoreDimBars`:✅做得好,数据驱动渲染AI评委dims+note,有hover理由。
|
||||
- `FlywheelBanner`:✅但确实只是一条横幅,飞轮存在感弱。
|
||||
|
||||
### 最终未读(已很次要,不影响结论):
|
||||
- `gemini_factory.py`/`storyboard_templates.py`/`_score_prompt.py`/`_scoring_dims.py`:都是"已确证存在能力"的实现细节,读不读不改变结论。
|
||||
- `pipeline_io` 已读到生图主循环,确认无遗漏大功能。
|
||||
|
||||
> **补读后主干结论不变,反而更强**:Clover后端能力比前端展示的多得多(生图3策略18张→前端拍平、vision分析→没UI入口体现、爆款8特征→留了字段)。**"空"的根因100%确证是"前后端能力落差",不是功能缺失。** 真缺口仍是那几条:①改稿信号 ②裂变/爆款拆解的AI逻辑+UI ③数据复盘 ④门面空 ⑤死链,外加多处"后端算了前端没露"。
|
||||
113
plans/Clover链路缺失诊断与开工清单.md
Normal file
113
plans/Clover链路缺失诊断与开工清单.md
Normal file
@@ -0,0 +1,113 @@
|
||||
# Clover 链路缺失诊断 + 代码层/Prompt层开工清单
|
||||
|
||||
> 对照俊达"完整闭环",逐行扒 Clover 真实代码后的诊断。每条都标了**文件:行号**和**改法**。
|
||||
> ⚠️ 并发:backend/frontend 另一窗口在改(15:34时间戳),本清单只诊断+给改法,落地前先看冲突列。
|
||||
|
||||
---
|
||||
|
||||
## 一、定性结论(先看这个)
|
||||
|
||||
你说的三个症状,根因各不相同,别一锅炖:
|
||||
|
||||
| 你的感受 | 真实根因 | 性质 |
|
||||
|---|---|---|
|
||||
| "点文案按钮404" | Sidebar导航写死了4个不存在的路由 | **死链bug**,半天能修 |
|
||||
| "界面比较空" | prompt产出丰富,但前端没把"五维分/角度/飞轮/资产"可视化出来 | **呈现层缺失** |
|
||||
| "逻辑链路有缺失" | 能跑通,但是"断点式8孤岛",不是俊达的"一个任务流过的闭环" | **链路编排缺失** |
|
||||
|
||||
> 反常识发现:**prompt层不空,反而饱满**。`_text_prompt.py` 已有人设/变量池ABC/5步框架/四段结构/5类标题公式/反AI味/emoji规则,做了方法层vs数据层分离。空的是"产出之后怎么呈现、怎么串环、怎么沉淀"。
|
||||
|
||||
<!-- 后续Edit补充:二、404死链详情 / 三、链路缺失 / 四、呈现层缺失 / 五、prompt层缺什么 / 六、开工优先级 / 七、并发冲突列 -->
|
||||
|
||||
---
|
||||
|
||||
## 二、404死链详情(最急,先修这个)
|
||||
|
||||
**`frontend/src/components/layout/Sidebar.tsx:19-28` NAV_ITEMS 写死了占位路径:**
|
||||
|
||||
| Sidebar标签 | 写的href | 真实路由 | 现状 |
|
||||
|---|---|---|---|
|
||||
| 选择文案 | `/tasks` | 只有 `/tasks/[id]/text` | 🔴404 |
|
||||
| 选择图片 | `/images` | 只有 `/tasks/[id]/images` | 🔴404 |
|
||||
| 建立任务 | `/tasks/build` | 不存在 | 🔴404 |
|
||||
| 任务列表 | `/tasks/list` | 不存在 | 🔴404 |
|
||||
|
||||
**根因**:文案/图片页是挂在具体任务下的(路由含 `[id]`,见 `app/tasks/[id]/text/page.tsx`),但侧边栏把它们做成了**无taskId的全局入口**。没有"当前任务"时点击→跳无id路由→404。
|
||||
|
||||
**改法(二选一,推荐B)**:
|
||||
- A临时止血:把这4个死项从NAV_ITEMS删掉/置灰,只留真实可达的(工作台/开新任务/审核台/历史/配置)。
|
||||
- **B正解**:导航改成"任务流"语义——侧边栏不再放"选择文案"这种环节级入口,环节入口由"当前进行中的任务"动态带 taskId 跳转(dashboard已有 `RecentTasksBar` 组件可复用)。这正是俊达"一个任务流过所有环"的呈现方式。
|
||||
|
||||
---
|
||||
|
||||
## 三、逻辑链路缺失(你说的"链路不完整")
|
||||
|
||||
**真实可跑通的链路**(从代码反推):
|
||||
```
|
||||
dashboard → tasks/new → [id]/text → [id]/images → [id]/confirm → review → history
|
||||
✅ ✅ ✅ ✅ ✅ ✅ ✅
|
||||
```
|
||||
单条链路是通的。但对照俊达**缺3个闭环回路**:
|
||||
|
||||
| 缺的回路 | 俊达有 | Clover现状 | 触达文件 |
|
||||
|---|---|---|---|
|
||||
| **改稿→飞轮** | 人改AI草稿,diff喂回去(最强信号) | `SignalType`(enums.py:57-63)只有5种,**无text_edit**;TextCandidate(task.py:73)**无edited字段** | 见配套《增量①改稿diff细案》 |
|
||||
| **审核→爆款库** | 过审的爆款拆解进资产库复用 | `fission`表已建有`reference_level`,但**无service/api接线** | 配套映射文档②|
|
||||
| **任务列表回看** | 全局看所有任务状态流转 | **页面根本不存在**(Sidebar指向的`/tasks/list`是空的)| 需新建 `app/tasks/list/page.tsx` |
|
||||
|
||||
> 链路不是"断",是"只有一条单向流,没有俊达那种'产出→沉淀→回灌'的回路"。这跟底层逻辑逆向文档§2飞轮四动作完全对应——Clover的飞轮①捕获缺最强信号、资产库②没接线。
|
||||
|
||||
---
|
||||
|
||||
## 四、呈现层缺失(你说的"界面空")—— 已逐组件核实,需修正
|
||||
|
||||
**核实后修正:文案卡 `TextCandidateCard.tsx` 其实很饱满**,渲染了:角度标签(55)、正文+展开收起(56-67)、违禁词状态(70-78)、**七维分数条ScoreDimBars(81)**、AI评委总评verdict+summary(84-93)。这张卡不空。
|
||||
|
||||
所以"界面空"不在文案卡。真正可能空的位置,重新定位:
|
||||
|
||||
| 怀疑位置 | 待核实文件 | 为什么怀疑 |
|
||||
|---|---|---|
|
||||
| **工作台dashboard** | `app/dashboard/page.tsx`(已读) | 🔴**确证空**:只有3个DashCard+一句问候,无数据看板、无近期任务、无飞轮进度。俊达进系统是仪表盘,Clover是3个按钮 |
|
||||
| 图片卡 | `ImageProgressCard.tsx` | 未核,存疑 |
|
||||
| 审核卡 | `ReviewCard.tsx` | 未核,存疑 |
|
||||
| 历史/归档页 | `app/history/page.tsx` | 未核,可能只是列表无成品预览 |
|
||||
| 任务列表页 | 不存在 | 🔴确证缺失 |
|
||||
|
||||
> **修正结论**:不是"卡片空",是"**着陆页和全局视图空**"。用户一进来是dashboard(3个按钮),缺俊达那种"今天生成X条/待审Y条/飞轮已学Z条"的仪表盘感。空的是**框**,不是**卡**。这个判断比之前准。
|
||||
|
||||
---
|
||||
|
||||
## 五、Prompt层到底缺什么(其实缺得不多)
|
||||
|
||||
`_text_prompt.py` 已很饱满。对照俊达**只缺2块**:
|
||||
|
||||
1. **改稿示范注入**:俊达把"人改过的好稿"当few-shot塞进prompt。Clover的 `build_prompt`(line126) 现在只注入产品数据+随机变量,**没有"参考这些人工修订过的范本"这一段**。← 配套改稿diff细案S4要补的就是这个。
|
||||
2. **图片prompt的资产复用**:文案prompt成熟,但生图prompt(`storyboard.py`)有没有复用"历史选中的好图风格"待查。俊达双通道+后台选优,Clover是否只是单通道一次性生图待确认。
|
||||
|
||||
> 结论:**prompt层不需要大改,只需把飞轮的"改稿范本"接进 `build_prompt` 的注入段**。这跟"界面空"是两码事,别混。
|
||||
|
||||
---
|
||||
|
||||
## 六、开工优先级(按ROI和并发安全排序)
|
||||
|
||||
| 序 | 干什么 | 工作量 | 并发风险 | 价值 |
|
||||
|---|---|---|---|---|
|
||||
| **P0** | 修Sidebar死链404 | 半天 | 🟢低(纯前端导航) | 立刻不404 |
|
||||
| **P1** | 核查并补全卡片字段渲染(五维分/角度/违禁词) | 1-2天 | 🟡中(动卡片组件) | 界面立刻"饱满" |
|
||||
| **P2** | 改稿diff飞轮(见独立细案) | 已拆好 | 🔴高(碰enums/review) | 最强飞轮信号 |
|
||||
| **P3** | 新建任务列表页 + 导航改任务流语义 | 1-2天 | 🟡中 | 链路闭环呈现 |
|
||||
| **P4** | 爆款库接线 | 二期 | 🟢低(新模块) | 资产化 |
|
||||
|
||||
---
|
||||
|
||||
## 七、并发冲突列(另一窗口在改,落地前必看)
|
||||
|
||||
| 文件 | 冲突等级 | 说明 |
|
||||
|---|---|---|
|
||||
| `api/v1/review.py` | 🔴最高 | 改稿diff细案已确认绕开它走task_actions |
|
||||
| `constants/enums.py` | 🟡 | 加text_edit信号要动这里,**仅此处需手工merge** |
|
||||
| `components/tasks/*.tsx` | 🟡 | 补字段渲染会动卡片,先git status看另一窗口动没动 |
|
||||
| `Sidebar.tsx` | 🟢 | 导航文件,另一窗口大概率没碰,P0可先动 |
|
||||
|
||||
> 落地任何一条前:先 `git status` + `git log --oneline -5` 看另一窗口提交到哪了,再动手。
|
||||
|
||||
59
plans/产品图禁降级方案.md
Normal file
59
plans/产品图禁降级方案.md
Normal file
@@ -0,0 +1,59 @@
|
||||
# 实施方案:生图带产品参考图 + 禁止降级 + 产品库
|
||||
|
||||
> 倩倩姐 2026-06-08 拍板:①上传产品图按钮做必填项(需产品图场景)②建任务时用户选"本次要不要产品入镜"③这轮一起做产品库(内置+上传)
|
||||
|
||||
## 一、现状(已查清)
|
||||
|
||||
**已存在、能用的**:
|
||||
- 产品图上传接口 `POST /products/{id}/upload-image` ✅
|
||||
- 前端上传组件 `ProductImageUpload`(在配置页产品管理里)✅
|
||||
- worker 读参考图 → 传 generate_storyboard_images 的链路 ✅
|
||||
- 产品表已有 `source enum('preset','custom')` 字段(产品库内置/自建早有预留)✅
|
||||
- 主备生图通道(本轮已修,apiports 503 自动切 codeproxy)✅
|
||||
|
||||
**缺口/坑**:
|
||||
1. 无图时 worker 默默降级纯文生图,无任何阻断(核心要堵)
|
||||
2. 产品图存/读用**相对路径**,api 容器 cwd 与 worker cwd=`/` 不一致 → worker 可能读不到(隐患,需改绝对路径)
|
||||
3. 建任务时用户看不到"产品有没有图"、也没有"要不要产品入镜"的选择
|
||||
4. 产品库目前只有 1 个 preset 产品、无图;没有产品库浏览/选择 UI
|
||||
5. `ProductCreate` DTO 无 image_path,建产品时无法带图
|
||||
|
||||
## 二、产品决策落地(按倩倩姐拍板)
|
||||
|
||||
- 建任务页加开关 **「本次产品是否入镜」**(need_product_image,默认"是")
|
||||
- 选"是" → 该产品**必须有参考图**才能点"生成",否则按钮置灰提示"请先上传产品图"
|
||||
- 选"否" → 允许纯文生图(氛围/科普/话题类内容)
|
||||
- 产品来源:**内置产品库 + 上传**,靠 `source` 字段区分
|
||||
|
||||
## 三、改动清单(分纵切片,逐块可验收)
|
||||
|
||||
### 切片 A:路径修稳(最高优先,不修后面全是空中楼阁)
|
||||
- `products.py` upload-image:存**绝对路径**(`/app/uploads/...`)进 image_path,不存相对路径
|
||||
- `pipeline_io.py` 读参考图:用绝对路径校验 + 读取
|
||||
- 验收:上传一张图 → worker 日志出现"产品参考图已加载 N bytes"
|
||||
|
||||
### 切片 B:后端禁降级 + 建任务字段
|
||||
- `task.py` 模型 + migration:GenerationTask 加 `need_product_image: bool default True`
|
||||
- `CreateTaskRequest` DTO 加 `need_product_image: bool = True`
|
||||
- `task_service` 建任务时:若 need_product_image=True 且产品无 image_path → 直接拒绝(422,"该产品未上传参考图")
|
||||
- `image_gen.py`:`ALLOW_TEXT_ONLY_IMAGE` 改由任务的 need_product_image 驱动;need=True 时无参考图**硬报错**不降级
|
||||
- 验收:无图产品 + 需入镜 → 建任务被拒;有图 → 生图带参考图
|
||||
|
||||
### 切片 C:前端建任务页
|
||||
- NewTaskForm 加「产品是否入镜」开关 + 展示当前产品图缩略图/未上传状态
|
||||
- 需入镜且无图 → "生成"按钮置灰 + 提示"请先到产品库上传参考图"
|
||||
- 验收:浏览器走一遍,无图拦住、有图放行
|
||||
|
||||
### 切片 D:产品库(内置+上传)
|
||||
- 后端:`GET /products` 支持按 source 筛选;预置 2-3 个常用内置产品(带图)入库 seed
|
||||
- 前端:配置页产品管理区分"内置库/我的产品",支持从内置库选用、上传自己的
|
||||
- `ProductCreate` DTO 加 image_path(建产品即可带图)
|
||||
- 验收:产品库能看到内置产品、能上传新产品、建任务能选到
|
||||
|
||||
## 四、风险/待北哥确认
|
||||
- **内置产品库放哪些产品+图**:需北哥给真实产品图素材,否则内置库是空壳。先搭框架+占位,图等北哥给。
|
||||
- 合规:产品图入镜后,gpt-image-2 仍可能把功效词画进图([[clover-image-gen-compliance-risk]]),需北哥合规 prompt 方案。
|
||||
|
||||
## 五、建议执行顺序
|
||||
A(路径)→ B(后端禁降级)→ C(前端建任务)→ D(产品库)
|
||||
每切片做完即验收,A+B+C 通了"禁降级"主线就闭环,D 是产品库增强。
|
||||
118
plans/俊达vsClover-逐界面对照缺陷清单.md
Normal file
118
plans/俊达vsClover-逐界面对照缺陷清单.md
Normal file
@@ -0,0 +1,118 @@
|
||||
# 俊达 vs Clover 逐界面/逐功能对照 · 缺陷清单
|
||||
|
||||
> 目的:拿俊达完整产品当标尺,逐个功能、逐个界面比,**只找 Clover 不完整/缺失/单薄的地方**。怎么改是后面的事,这里只列问题。
|
||||
> 已读全貌:Clover前端8页面+25组件全部读完;俊达13功能模块(系统A内容中台7 + 系统B SCRM 6)。
|
||||
> 对照口径:✅有且饱满 / 🟡有但薄 / 🔴缺失 / ⚪不适用(北哥不做这块业务)
|
||||
|
||||
---
|
||||
|
||||
## 零、先说一个总判断
|
||||
|
||||
Clover ≈ **只实现了俊达「系统A内容中台」里"单条内容生产线"那一段**(开任务→挑文案→挑图→确认→审核→归档下载)。
|
||||
俊达的 **系统B SCRM 整块、系统A的"进化页/数据复盘/拆解中心/素材库/关键词"几乎全缺或很薄**。
|
||||
|
||||
换句话说:**Clover 是一条"生成流水线",俊达是一个"会进化、能复盘、带资产库、还接销售"的运营操作系统。** 你感觉"空、不完整",根子在这。
|
||||
|
||||
<!-- 后续Edit补充:一、系统A逐功能对照 / 二、系统B逐功能对照 / 三、UI呈现层对照 / 四、链路完整性对照 / 五、缺陷汇总分级 -->
|
||||
|
||||
---
|
||||
|
||||
## 一、系统A(内容中台)逐功能对照
|
||||
|
||||
| # | 俊达功能 | 俊达怎么做 | Clover对应 | 状态 | 缺什么/薄在哪 |
|
||||
|---|---|---|---|---|---|
|
||||
| A1 | **AI助手中心/进化页** | 每个环节是一张agent卡,能看到"这个环学了多少、进化到第几代",是系统的脸 | 只有 `FlywheelBanner` 一个横幅条(new/text/images页顶) | 🔴**几乎缺失** | 没有"agent进化"的可视化主页。飞轮只在生成页闪一条banner,平时看不见"系统在变聪明"。俊达的魂在Clover是个配角 |
|
||||
| A2 | **内容创作工作流** | 选题→生成→选优→改稿→成稿,一条可视流水线 | text→images→confirm 三页 | 🟡**有但断**| ①无"选题"环节(直接填theme) ②**无"改稿"环节**(选了就走,不能改AI稿) ③三页之间是跳转,不是一条能回看的流水线 |
|
||||
| A3 | **素材库(资产化+评级)** | 图/压字/标题/卖点/评论分门别类入库,每条打参考等级,下次直接调 | `fission`表有`reference_level`字段,但**无页面无service** | 🔴**缺失** | 完全没有"素材库"这个界面。产出用完即弃,不沉淀、不能复用、不能调库生成 |
|
||||
| A4 | **拆解中心(爆款逆向)** | 贴竞品爆款→拆出标题公式/结构/卖点/配图节奏→进库 | `benchmarks`(标杆笔记)只能录入,`fission`表建了没接线 | 🟡**只录入不拆解** | 能存标杆笔记,但**没有"自动拆解出配方"的功能**。俊达是拆完进库复用,Clover只是存了个参考 |
|
||||
| A5 | **数据复盘** | 发布后回收数据(赞藏评/转化)→反哺哪种内容好 | `history`只有任务列表,**无发布后数据回收** | 🔴**缺失** | 链路在"下载交付包"就断了。发出去之后的效果完全没回来,飞轮缺了"结果反馈"这一环 |
|
||||
| A6 | **关键词分析** | 关键词→聚光词包打通,指导选题 | 无 | 🔴**缺失** | 没有关键词/选题指导,运营靠自己拍脑袋填theme |
|
||||
| A7 | **模板库** | 沉淀可复用的内容模板 | `_text_prompt.py`有内置模板,但用户**不可见不可管** | 🟡**藏在代码里** | 模板写死在后端,运营看不到、改不了、存不了自己的 |
|
||||
|
||||
---
|
||||
|
||||
## 二、系统B(SCRM运营)逐功能对照
|
||||
|
||||
> ⚠️ 先判断:北哥业务是否要做SCRM?这块大部分可能是 ⚪不适用。但**列出来让倩倩姐自己判**,不替你砍。
|
||||
|
||||
| # | 俊达功能 | 俊达怎么做 | Clover对应 | 状态 |
|
||||
|---|---|---|---|---|
|
||||
| B1 | AI销售/追单Agent | 线上自动追单、每天成交 | 无 | ⚪/🔴 看北哥要不要做销售转化 |
|
||||
| B2 | AI企微客服 | 自动接待答疑 | 无 | ⚪ 北哥若无私域则不适用 |
|
||||
| B3 | 采集定制 | 定制内容生产线 | 无 | ⚪ |
|
||||
| B4 | 收款单/支付 | 订单收款管理 | 无 | ⚪ |
|
||||
| B5 | 投放复盘Agent | 每日诊断投放ROI | 无 | 🔴 若北哥投流则强相关 |
|
||||
| B6 | 乘风账户财务 | 账户资金管理 | 无 | ⚪ |
|
||||
|
||||
> 系统B的意义:俊达是"内容→销售→复盘"全闭环,**Clover只到"内容产出"就停了**,后面的转化和钱完全没接。这是"工具"和"经营系统"的分水岭——但要不要走这步是商业决策,得倩倩姐拍。
|
||||
|
||||
---
|
||||
|
||||
## 三、UI呈现层逐页对照(基于真实代码逐页核实)
|
||||
|
||||
> 这节回答"界面为什么空"。逐页看了真实代码,分清哪页饱满、哪页空。
|
||||
|
||||
| Clover页面 | 文件 | 内容丰富度 | 对照俊达的差距 |
|
||||
|---|---|---|---|
|
||||
| **工作台 dashboard** | `dashboard/page.tsx` | 🔴**确证空** | 只有1句问候+3个DashCard按钮。**无任何数据**:今天生成多少、待审多少、飞轮进度、近期任务全没有。俊达进门是仪表盘,Clover进门是3个按钮 |
|
||||
| 挑文案 text | `[id]/text/page.tsx` + `TextCandidateCard` | ✅**饱满** | 卡片有角度/正文/违禁词/七维分条/AI评委总评。这页不空,反而是全站最好的 |
|
||||
| 挑图 images | `[id]/images/page.tsx` | 🟡**偏薄** | 图只显示 url+role 两个信息(line65-66),**无评分、无策略、无为什么选它**。对比文案卡的七维分,图卡信息量差一大截 |
|
||||
| 确认 confirm | `[id]/confirm/page.tsx` | 🟡 一般 | 左文案右图预览,文案只显示角度+正文+总分。能用但朴素 |
|
||||
| 审核台 review | `review/page.tsx` + `ReviewCard` | 🟡 待核ReviewCard | 队列+通过/打回+toast,框架在。ReviewCard内容丰富度未核 |
|
||||
| 历史归档 history | `history/page.tsx` + `components.tsx` | ✅ 较好 | 有筛选/表格/分页/下载交付包。是个正经表格页 |
|
||||
| 配置台 config | `config/page.tsx` | ✅ 较好 | 4个tab(产品/标杆/违禁词/key),结构清晰 |
|
||||
| 开新任务 new | `tasks/new/page.tsx` | ✅ 饱满 | 表单+产品选择+配置预览面板+近期任务+飞轮banner,信息量足 |
|
||||
|
||||
> **"空"的真相修正**:不是全站空,是**门面空**——用户第一眼看到的 dashboard 是3个按钮,没有"操作系统"的感觉。加上 images 页偏薄。其余页面其实都不错。
|
||||
|
||||
---
|
||||
|
||||
## 四、链路完整性对照
|
||||
|
||||
**Clover 真实链路**(已验证可跑通):
|
||||
```
|
||||
登录 → dashboard → 开新任务 → 挑文案 → 挑图 → 确认 → 提交审核 → 审核台 → 通过 → 历史归档 → 下载交付包
|
||||
```
|
||||
**对照俊达,链路有4处断点**:
|
||||
|
||||
| 断点 | Clover现状 | 俊达有 |
|
||||
|---|---|---|
|
||||
| ①**入口断**:Sidebar导航 | `Sidebar.tsx:22-25`指向`/tasks`等4个不存在路由→404 | 导航即任务流,不会点空 |
|
||||
| ②**改稿断**:选文案后不能改 | text页选了直接`select`走人(line29-32),无改稿入口 | 人改AI稿→喂回飞轮(最强信号) |
|
||||
| ③**反馈断**:下载即终点 | history下载交付包后链路结束 | 发布后数据回收→复盘→反哺 |
|
||||
| ④**回看断**:无任务全局视图 | 无`/tasks/list`,进行中的任务无处统一看 | 任务看板,所有任务状态一目了然 |
|
||||
|
||||
> 链路不是"坏",是"**只有一条单向直线,没有俊达的两个回路**":改稿回路(②)、数据反馈回路(③)。这俩正是飞轮转起来的关键。
|
||||
|
||||
---
|
||||
|
||||
## 五、缺陷汇总分级(只列问题,不谈怎么改)
|
||||
|
||||
**🔴 一级缺失(让Clover像"半成品"的):**
|
||||
1. dashboard门面空——无操作系统仪表盘感
|
||||
2. 进化页/飞轮主视图缺失——系统的"魂"是个配角banner
|
||||
3. 素材库缺失——产出不沉淀、不能复用
|
||||
4. 改稿环节缺失——飞轮最强信号没接
|
||||
5. 数据复盘缺失——链路下载即断,效果不回收
|
||||
6. Sidebar死链404——入口就劝退
|
||||
|
||||
**🟡 二级单薄(能用但不饱满的):**
|
||||
7. 图片卡信息量薄(只有url+role)
|
||||
8. 拆解中心只能录入不能拆配方
|
||||
9. 模板库藏在代码里用户不可见
|
||||
10. 关键词/选题指导缺失
|
||||
11. 任务全局看板缺失
|
||||
|
||||
**⚪ 待商业决策(系统B整块):**
|
||||
12. 销售追单/客服/投放复盘/收款——要不要做SCRM,倩倩姐拍
|
||||
|
||||
---
|
||||
|
||||
## 六、还需核实的(我没看到的,不装看到)
|
||||
|
||||
- `ReviewCard.tsx` 审核卡到底多丰富——未读
|
||||
- `ImageProgressCard.tsx` 完整内容——只看了images页内联渲染,组件本身未读
|
||||
- 后端 `benchmarks.py`/`delivery.py` 接口完整度——未读
|
||||
- 俊达视频里"进化页/数据复盘"的具体界面长相——摩尔纹,只能辨认大概
|
||||
|
||||
> 这几项我标明"未核",不纳入确证缺陷。要不要我继续把这几个也读了,把清单补到100%确证?
|
||||
223
plans/俊达产品-完整逐功能拆解.md
Normal file
223
plans/俊达产品-完整逐功能拆解.md
Normal file
@@ -0,0 +1,223 @@
|
||||
# 俊达产品 · 完整逐功能拆解
|
||||
|
||||
> 2026-06-15 重做(上一版扒得太粗,只啃了PPT标题层)。本版榨干三类素材:PPT 31页 + 俊达口述全文稿(说话人C) + 现场演示视频2段密集抽帧(92帧)。
|
||||
> 定位:先把俊达这套东西**扒透**(是什么、有哪些功能、怎么实现、什么参数),映射到北哥/大卫是下一步的事,不在本文。
|
||||
> ⚠️ 视频是手机拍投影(有摩尔纹),界面文字属辨认+口述/URL交叉验证,标注了把握度:【确证】=口述或PPT明说 /【辨认】=视频可读 /【推断】=据上下文推。
|
||||
|
||||
---
|
||||
|
||||
## §0 最重要的澄清:俊达有「两套系统」,不是一套
|
||||
|
||||
上一版把它当成"一个内容中台 + 一堆外围",**错了**。视频里 URL 和左侧导航证实是**两个独立部署**:
|
||||
|
||||
| 系统 | 地址 | 性质 | 左侧导航主题 |
|
||||
|---|---|---|---|
|
||||
| **小红书内容中台**(Content OS) | `localhost:3000/xhs/...` | 开发环境,PPT演示主体 | 围绕"小红书内容生产" |
|
||||
| **心声时刻 SCRM**(全平台运营) | `scrm.xinshengshike.com/...` | 线上生产环境,每天在跑 | 围绕"全平台运营/销售/客服/定制生产" |
|
||||
|
||||
> 两套都是俊达**一个人**用 Claude Code/Codex 开发的(口述【确证】:"之前有几个技术,后来变成我一个了")。
|
||||
> 公司主体疑似"心声时刻",主营**定制歌曲 + 定制冰箱贴**(把照片/歌做成实体卖,AI生成内容)。
|
||||
|
||||
下面 §2 内容中台、§3 SCRM 分别逐功能拆。
|
||||
|
||||
---
|
||||
|
||||
## §1 业务本体(先懂生意,才懂系统为什么这么设计)
|
||||
|
||||
【确证·口述】
|
||||
- **主营**:定制歌曲、定制冰箱贴(垂直定制类目)。产品本身=AI生成(歌AI写、图AI做),打印成实体(冰箱贴/标签)卖。
|
||||
- **客单**:定制歌曲类约 ¥450(成本几十~100),电商类约 ¥100(成本~十几),毛利高。PPT原话"AI让成本趋近于零,于是能规模化卖"——关键不是降本,是"凭空造出一门生意"。
|
||||
- **打法**:小红书打线索 + 打聚光(投放驱动),纯千川式。本质"卖图/卖歌",把内容打到标签/链接上。
|
||||
- **场景词**(选题方向,来自笔记复盘饼图【辨认】):新婚送礼·新人夫妻(占比最大54%/270条)、亲子纪念·宝妈、出生纪念、闺蜜生日、情侣纪念、结婚纪念、毕业季·学生闺蜜等。**强情感/纪念向**。
|
||||
- **账号体量**:心声纪歌曲定制礼物号≈1.9w粉/136篇/4.7w赞(PPT关键词页【辨认】)。自有号+代发号,不做大量素人。
|
||||
|
||||
> 这块决定了俊达系统的灵魂:**高情感定制 + 投放驱动 + 重内容质量**,所以他才需要"飞轮"把"运营手感"沉淀进系统——同质化内容在他这个品类是致命的。
|
||||
|
||||
---
|
||||
|
||||
## §2 系统A:小红书内容中台(Content OS)逐功能
|
||||
|
||||
> 地址 `localhost:3000/xhs/...`,PPT演示主体。左侧导航【辨认】:今日待办 / 内容中心 / 素材库 / 模板库 / 拆解中心 / 数据复盘(账号笔记·笔记复盘) / 商品管理 / 不投流量? / 新计划? / 关联授权 / 管理中心。
|
||||
|
||||
### 2.1 AI 助手中心 / 进化页(魂) 【确证+辨认】
|
||||
- **URL**:`/xhs/manage/evolution`("evolution=进化",证实这是飞轮UI)。
|
||||
- **是什么**:把每个内容生产环节做成一个"AI员工(agent)",集中管理+可进化。
|
||||
- **流程agent列表**(PPT第10页+视频f009):①推选题 ②写标题 ③写正文 ④配图压字 ⑤写评论;**辅助能力**:图片打标 / 文本打标 / 拆解爆款。
|
||||
- **每个agent卡片字段**【辨认】:熟练度(暂无/学习中1/3)、"学了你X次·记住X个范例"、状态(还没开始学/有升级待你确认)。
|
||||
- **关键交互**:"『写正文』助手升级——它根据你近期的改稿,琢磨出更好的写法,等你拍板"→ 按钮"看它学到什么"。**这就是俊达说的"改稿→AI进化→人点采纳"飞轮,做成了UI。**
|
||||
- **认知**:口述"提示词没那么重要,重要的是动态生成"——所有提示词结合产品+场景+参考图动态拼。
|
||||
|
||||
### 2.2 内容创作工作流(生产线) 【辨认·视频f069】
|
||||
- **URL**:`/xhs/manage/workspace`,示例任务"520礼物"。
|
||||
- **6步收起式步骤栏**:①模板 ②正文 ③标题 ④配图 ⑤评论 ⑥发布(左侧带✅进度勾)。
|
||||
- **分STAGE呈现**:STAGE A 发布前审核 / STAGE B 套模板 / STAGE C 发布中心交付。
|
||||
- **AI发布前审核**(PPT第10页右):3项待改,逐条检查 title_length/placeholders_filled/body_quality/cta_present/topic_tags,给"重新审核"按钮。**=发布前质检100%覆盖。**
|
||||
- 右侧实时显示生成结果(标题/正文/标签/评论区话术示范)。
|
||||
|
||||
### 2.3 素材库(资产化+评级) 【确证+辨认·视频f005/f060】
|
||||
- **URL**:`/xhs/manage/materials`。分类tab【辨认】:定制证书 / 情侣 / 歌曲定制 / 生日祝福。
|
||||
- **搜索**:文字描述搜图(**向量搜图**【辨认"向量检索"】)+ 以图搜图 + 最新创建。
|
||||
- **颗粒度**(PPT第11页+口述【确证】):图片 / 视频 / 图片压字 / 评论 / 标题 / 文案结构 / 关键词——**各成一库**,进库即AI打标。
|
||||
- **每个素材卡字段**【辨认f005右栏】:出图提示词、拍摄要点、来源、压字、评论、标题、文案结构、关键词。
|
||||
- **评级**(PPT第11页【确证】):进库即打标,按真实互动评 **S/A/B/C/D 级**。"颗粒越细,大模型调用/拆解越准"。
|
||||
- **入库流**:AI先拆解→人工校正→入库;逆向(爆款)也走这条:粘链接→拆→该入库的入库。
|
||||
- **结果**:素材积累 5/月 → 50+/月(×10)。
|
||||
|
||||
### 2.4 拆解中心(爆款逆向) 【确证·PPT第14页+短视频v2】
|
||||
- **URL**:`scrm...com/pc-maker/upload-backfile`(注意:在SCRM域名下,叫"以图搜单·回纸管理/采集定制",与内容中台打通)。
|
||||
- **流**:粘小红书爆款链接 → AI拆 → 一键存入素材库当下次生成样例。
|
||||
- **拆出的配方维度**(PPT第14页【确证】):标题公式、句子类型、正文结构、卖点、配图节奏、emoji用法、话题标签、目标人群。
|
||||
- **示例**(PPT原文):标题公式"把某人的某种照片[做成定制产品名]|[捕捉场景]礼物";正文骨架同步拆出。
|
||||
- **口号**:72小时把竞品爆款变成你的可复用配方。
|
||||
|
||||
### 2.5 数据复盘 【辨认·视频f020/f024】
|
||||
- **账号笔记/选题分析**(`/xhs/...compilation`,PPT第10页+f020):把账号笔记标题+正文交AI归纳选题方向,统计各方向**笔记数/占比/平均阅读/平均点赞/平均互动率/平均单条变现价值**。带"增量分析""全量重判"按钮。
|
||||
- **笔记复盘**(`/xhs/manage/notes`,f024):单条笔记拉**内容数据+复盘数据**(曝光/阅读/点赞/收藏/评论/分享/互动率/点击率/涨粉/商品转化),一键AI复盘+人工校准。
|
||||
- **竞品监控**:竞品笔记数据全监控,反推关键词、分析选题类型,回写素材库。
|
||||
|
||||
### 2.6 关键词分析 【确证·PPT第18页】
|
||||
- 大量抓候选词 → AI批量判断是否贴合业务 → 筛出真正有用的。
|
||||
- **和小红书聚光关键词词包打通**:显示搜索量/竞争度/建议出价(截图共639条,上游=聚光付费接口)。词包类型:笔记词包/黑马词包/高点击包。
|
||||
- 跑出的词植入笔记;竞品笔记反推关键词。
|
||||
|
||||
### 2.7 模板库 【辨认】
|
||||
- 图片模板(四宫格 /xhs/manage/x-content f048、大字报等),定义文字摆放位置+生成样式。生成时"这张套四宫格、那张套大字报"。
|
||||
|
||||
## §3 系统B:心声时刻 SCRM(全平台运营)逐功能
|
||||
|
||||
> 地址 `scrm.xinshengshike.com/...`,线上生产环境(**每天在跑、现场都在成交**·口述【确证】)。左侧导航【辨认f003/f006/f022】:公众号管理 / 城市管理 / 简域管理 / 消息中心 / CMS管理 / 客户端管理 / 歌词制作 / 音乐制作 / 音乐发布 / 客户信息管理 / **采集定制** / **AI销售** / **企微自动化** / 客户SOP / 群发SOP / SOP执行管理 / 追单任务 / 退单SOP / 订单执行 / 定制客户管理 / 营销内容管理 / 智能体 / 知识库 / 模型管理 / AI生成 / 列表配置 / 多语言客服 / **支付管理**。
|
||||
|
||||
### 3.1 AI 销售 / 追单 Agent(线上每天成交) 【确证+辨认·视频f003】
|
||||
- **URL**:`scrm...com/automation/aaa-edition`(自动化)。是配置完整的**追单Agent**。
|
||||
- **左栏=Agent系统指令全文**【辨认f003】,"定制歌曲未付费追单",结构:
|
||||
- 系统角色定义
|
||||
- 触发条件(用户消息进来)
|
||||
- **判断规则约7条**:如客户没回复不主动发;客户说在忙→发祝福语,不硬追;客户问价→走专属付费链接报价;客户嫌贵→发优惠/案例;客户明确拒绝→停止;调用 submit_chase_decision 决策;输出结果按格式不能自创字段。
|
||||
- 输出动作枚举(继续追/停止/转人工)。
|
||||
- **右栏=配置面板**【辨认】:模型选 **doubao-2.0**;GA预估值;发送阶段(首次/第N次);自动触发开关;工具调用(已配置);客户产品维度。
|
||||
- **口述价值**【确证】:"人解决过一次的问题,下次为什么还要人?该AI解决"→任务包模式;追单"人工追不好就AI追",企微AI客服转化率比人工高1-3%。
|
||||
|
||||
### 3.2 AI 企微客服 【确证·PPT(企微页)】
|
||||
- 多账号会话(共19201位客户【辨认】),左侧切账号、中间会话、右侧客户档案。
|
||||
- 右栏:AI自动回复开关、客户备注、客户标签(小红书/未付费)、添加时间/方式、**客户记忆**(更新日期)、副驾(资料/话术/素材/音乐 tab)。
|
||||
- **AI接管/我来接管**切换(PPT客服页【辨认】),人机协作。
|
||||
|
||||
### 3.3 采集定制(定制生产线) 【辨认·短视频v2】
|
||||
- 子菜单:粉图技能初验 / 配置 / 生成链路 / 任务管理 / 快速过图 / 我的作图任务 / 模板广场 / 设计师设计 / 快速生成PSD。
|
||||
- "以图搜单·回纸管理":打到工人/纸张层面(冰箱贴是实体印刷品)。**这是把"内容生成"接到"实体生产"的环节**——对应口述"AI优化生产流程,冰箱贴成本8块→4块"。
|
||||
|
||||
### 3.4 收款单 / 支付管理 【辨认·视频f022】
|
||||
- "收款单管理":统一生成专属付款链接,定向/限金额收款,付完后台人工确认。列表显示客户/专属付款链接/金额/状态/付款时间。示例待支付总额 ¥3759.91。
|
||||
|
||||
### 3.5 每日投放复盘 Agent 【辨认·视频f068/f066/f016】
|
||||
- **URL**:`/xhs/manage/ad-review-daily`(注:此页URL在内容中台域,但与投放数据打通)。
|
||||
- 左栏=投放复盘Agent指令全文【辨认】:账户概览、今日花费/今日销售额/今日转化成本(CPL)、计划诊断("已停推/未达量等→是否要调"),输出动作卡。
|
||||
- **数据打通**【确证】:聚光 + 千川 + 乘风 + 专业号 + 小红书后台 + 电商带货 + 线索,全怼进去喂模型。能看单条笔记实际卖多少货、点击率。
|
||||
- **价值**【确证】:投手从每天泡6小时报表→自动出动作卡;DNT投放 ROI 1:4→1:8(618回稳1:6+)。
|
||||
|
||||
### 3.6 乘风账户财务 【辨认·视频f036】
|
||||
- "乘风账户财务"页:账户余额(¥6,274.30)、消耗、按日期明细表。投放平台资金侧打通。
|
||||
|
||||
---
|
||||
|
||||
## §4 技术栈 / 模型 / 成本 / 选型理由 【确证·口述问答】
|
||||
|
||||
| 项 | 内容 | 出处 |
|
||||
|---|---|---|
|
||||
| **后端** | **纯代码开发**,自建数据库。明确**不用扣子/Dify** | 口述 |
|
||||
| 不用扣子理由 | 扣子只能调国内几个模型、生成质量差;放生产级要接一堆插件/节点,没人维护就不稳定 | 口述【确证】 |
|
||||
| **文案拆解模型** | GPT-5.5(口述说"GPT5.5",指拆解/文案) | 口述 |
|
||||
| **生图模型** | GPT Image2(中转站的image2)+ 官方双通道 | 口述 |
|
||||
| 生图双通道设计 | 通道1=中转站(便宜~¥0.18/张);通道2=官方(质量稳)。后台跑评分机制选优,所以生图偏慢 | 口述【确证】 |
|
||||
| 追单/客服模型 | **doubao-2.0**(成本低,关键词分析"豆包就能分析得很好") | 视频f003+口述 |
|
||||
| 统一模型底座 | 豆包/Claude 可切换;生图接 nano banana / GPT Image | PPT第28页 |
|
||||
| 单张生图成本 | 中转站约 **¥0.18/张** | 口述【确证】 |
|
||||
| 消水印 | 生图自带两层水印(浅色日期+OpenAI像素级隐写),出图后处理转码消除 | 口述【确证】 |
|
||||
| 查重对抗 | 提示词全动态生成→重复度极低,过小红书查重+AI检测 | 口述 |
|
||||
| 开发工具 | Claude Code / Codex("配满CC/Codex,一个月1000-1600/号") | PPT第24页+口述 |
|
||||
| 开发速度 | 拉需求2-3天聊明白,系统2天全跑出来 | 口述【确证】 |
|
||||
|
||||
## §5 业务成果数据(俊达给的真实数字) 【确证·PPT第30页+口述】
|
||||
|
||||
| 指标 | 数字 | 备注 |
|
||||
|---|---|---|
|
||||
| 单篇内容产能 | **×20** | 一篇内容20倍增长 |
|
||||
| 周报/复盘工时 | **−90%** | 90%+ 让AI干掉 |
|
||||
| 投放日常重复劳动 | **−95%** | 投手只剩充钱+看AI计划对不对 |
|
||||
| 素材积累速度 | **×100** | (PPT写×100,口述×10,取PPT) |
|
||||
| 发布前质检覆盖 | **100%** | AI发布前审核 |
|
||||
| AI内容质量 | 越用越强 | 进化 |
|
||||
| 单篇笔记制作 | 60分钟 → **5分钟** | 且不被平台识别为AI |
|
||||
| 投放ROI | 1:4 → **1:8**(618回1:6+) | DNT项目 |
|
||||
| 冰箱贴成本 | 8块 → **4块** | AI优化生产流程一个人工环节 |
|
||||
| 单条爆款笔记 | 卖8000元货 | "凑合"状态 |
|
||||
| 公司AI化程度 | 自评**约10%** | 还有90%路要走 |
|
||||
| 开发人力 | **1人**(原几个技术→现1人) | 内容中台+SCRM+ERP+客服+企微+定制全是他一人 |
|
||||
|
||||
> ⚠️ PPT第30页诚实标注"以上为测算/目标值"——不全是已达成实测,部分是目标。引用时别当成100%落地实绩。
|
||||
|
||||
---
|
||||
|
||||
## §6 组织与方法论(产品背后的打法) 【确证】
|
||||
|
||||
### 6.1 三个认知转变(俊达原创框架核心)
|
||||
1. **工具 → 系统**:AI不是工具,是组织成员/员工(24h无休、稳定)。
|
||||
2. **生成 → 流水线**:不让AI一口气写完,拆工序、每步AI出活、人审一眼(对应prompt→context→harness工程师演进)。
|
||||
3. **定型 → 进化**:AI买来不该定型,每天因真实反馈进化(提到Hermes自进化概念)。
|
||||
|
||||
### 6.2 任务包模式(原创框架)
|
||||
AI先解决→自动评估(分数不够/疑难标记)→升级为"任务包"交专家→专家解法反哺训练AI。趋势:任务包越来越少,人从"处理任务"退到"定策略"。
|
||||
|
||||
### 6.3 角色重构
|
||||
- 运营从"打螺丝(作图/找模板)"→"审批专家":招的不是小红书运营,是**设计师**(懂美感/风格,基础逻辑都写进系统了)。
|
||||
- 交给AI:选题初筛/标题初稿/正文骨架/配图打标/数据聚合复盘。
|
||||
- 必须人来:定调品牌把关/创意情绪判断/终审发布/投放要不要拍板。
|
||||
|
||||
### 6.4 落地三铁律
|
||||
1. **一把手工程**:AI账号谁买、预算谁出、进不进绩效、人事财务绩效要不要进——只有一把手能拍板,否则死在每一关。
|
||||
2. **小公司1+1起步**:1个老技术(外包出身、技术面广、懂沟通需求,杭州成本1.5-2w)+1-2个新人(985应届/实习),配满CC/Codex。
|
||||
3. **一条标准线**:只要环节用脑子→先交给AI,人是护栏和协同。
|
||||
|
||||
### 6.5 关键判断(俊达原话提炼)
|
||||
- "AI不是抢生意的,是做好产品的"——他不卖软件,自己做电商。
|
||||
- "未来出现怪兽级电商公司",产能把人工部分全吃掉,甚至返推工厂降本。
|
||||
- "比模型更难的,是让一家公司真的用起来"(全员用得上+团队重组)。
|
||||
- 终极目标 AI native / OPC(One Person Company),自评还差90%路。
|
||||
|
||||
---
|
||||
|
||||
## §7 一句话总评(给倩倩姐的判断锚)
|
||||
|
||||
俊达的强不在某个功能炫,而在**两件事**:①一个人用CC/Codex把"全链路"(内容+投放+客服+销售+定制生产+收款)全做成了能跑的系统,验证了"AI给一个人的杠杆";②每个能动脑的环节都做成了"会进化的agent",且坚持"人审拍板+诚实克制"(评分选优、不盲目自动发)。
|
||||
**他比北哥Clover强在广度(全链路)+ 进化UI的成熟度;Clover比他可能强在单点深度(生图锁产品工程化)。** 具体逐条映射见配套《俊达对标-增量落地映射.md》。
|
||||
|
||||
---
|
||||
|
||||
## §8 可信度与使用边界(拿去用之前必读)
|
||||
|
||||
> 素材限制:视频是**手机拍投影+摩尔纹**,没法问俊达要原图/录屏(人家花时间做的成果,明着要不合适)。所以这份拆解**能借鉴"思路和形态",不能当"复刻原文和参数"的依据**。三档可信度划清:
|
||||
|
||||
### 🟢 地基级——可直接当借鉴依据(来源:口述【确证】+PPT明示)
|
||||
- 俊达有两套系统(内容中台 + SCRM)这个事实
|
||||
- 5条认知 / 任务包模式 / 角色重构 / 落地三铁律(§6 全部)
|
||||
- 飞轮"进化页"的**产品形态**(每环节做成会进化的agent、人改稿→AI学→人点采纳)
|
||||
- 技术选型**理由**:不用扣子/Dify的原因、生图双通道(便宜+稳)+后台评分选优、消两层水印、提示词全动态防查重
|
||||
- 素材资产化的**分类思路**(图/压字/评论/标题/文案结构/关键词各成库、进库打标评级)
|
||||
- 爆款拆解的**配方维度**(标题公式/正文结构/卖点/配图节奏…)
|
||||
- 关键词与聚光词包打通的**逻辑**
|
||||
- 业务成果数字(但俊达自己标了"测算/目标值",非全实测)
|
||||
|
||||
### 🟡 线索级——只用来"确认功能存在/大概长啥样",不照搬(来源:视频【辨认】)
|
||||
- 具体界面字段名、URL路径、agent卡片文案
|
||||
- **两个Agent指令的逐条规则**(追单7条、投放复盘诊断逻辑)——方向对,但个别字词我可能辨认错
|
||||
- 模型版本号(doubao-2.0等是辨认值)、¥0.18/张等数字
|
||||
|
||||
### 🔴 不可获取——别试图还原,也不该问他要(核心knowhow)
|
||||
- 两个Agent的系统提示词**原文**、素材库打标的prompt、评分机制的维度与权重、双通道选优的具体算法
|
||||
|
||||
### 使用三原则
|
||||
1. **借思路、形态,不抄原文、参数**。前者是俊达公开分享的方法论(借鉴正当);后者是他的knowhow(我们辨认不全,也不该抄)。
|
||||
2. **凡要落进 Clover 代码的设计,依据只取 🟢 级**;🟡 级仅用于"确认该功能值得做、界面大概什么样",绝不照搬字段/规则原文。
|
||||
3. **我们的 prompt / 字段 / 算法全部自研**——俊达做素颜霜定制歌曲,我们做北哥的品类,prompt 本就不可能通用,重新设计是对的、不是偷懒。
|
||||
|
||||
> 一句话:这份文档是**"看人家做到了什么、用什么思路做的"的参考**,不是**"照着抄的图纸"**。映射到 Clover 的每条增量(见配套映射文档),依据都已对齐 🟢 级 + Clover 自己的代码现状,没有一条是"照抄俊达原文"。
|
||||
190
plans/俊达产品-底层逻辑逆向.md
Normal file
190
plans/俊达产品-底层逻辑逆向.md
Normal file
@@ -0,0 +1,190 @@
|
||||
# 俊达产品 · 底层逻辑逆向
|
||||
|
||||
> 目的:抛开界面/字段/提示词原文(那些辨认不全也不该抄),**只逆向"这套系统为什么这么转、内核机理是什么、能抽象出什么可迁移的底层模型"**。
|
||||
> 素材:口述【确证】+ PPT明示 为主——底层逻辑恰好是俊达大方分享的方法论层,是现有资料里最可靠的部分。
|
||||
> 定位:这是"原理图",不是"原文图纸"。可直接用来指导北哥 Clover 的设计取舍。
|
||||
|
||||
---
|
||||
|
||||
## §0 一句话内核
|
||||
|
||||
**把"靠人、且经验留不住"的小红书电商内容生产,重构成"靠系统、且系统随用随聪明"的复利机器。**
|
||||
|
||||
拆成两个动词:
|
||||
- **重构**:人做的每一步(选题/生成/选优/改稿/审核/追单/复盘)都拆成系统里一个"会进化的环",而不是一次性工具。
|
||||
- **复利**:人干活时产生的每一个决策,都被捕获成数据、沉淀成资产、回灌进下一次生成——用得越多,系统越聪明,人越省力。
|
||||
|
||||
---
|
||||
|
||||
## §1 第一性:他到底在解决什么本质问题
|
||||
|
||||
小红书电商有三个结构性矛盾,俊达整套系统每一块都对着其中之一:
|
||||
|
||||
| 本质矛盾 | 通俗说 | 俊达用什么对它 |
|
||||
|---|---|---|
|
||||
| **产能 vs 质量** | 要量大(铺笔记),又要篇篇能转化,人手不够 | 流水线生成 + 飞轮选优(§2§3) |
|
||||
| **经验 vs 流失** | 高手知道怎么写爆款,但经验在脑子里,人走了就没了 | 资产化沉淀(§4),把经验变成库 |
|
||||
| **跑量 vs 平台规则** | 量一大就判重/限流/封 | 平台对抗工程化(§5) |
|
||||
|
||||
> 关键洞察:**别人把 AI 当"生成器",俊达把 AI 当"会积累的生产系统"。** 生成只是表面,积累才是内核。这是他和"套个GPT写文案"的根本区别。
|
||||
|
||||
<!-- 后续章节由 Edit 补充:§3 流水线 / §4 资产化 / §5 平台对抗 / §6 交付商业 / §7 可迁移底层模型 / §8 映射Clover -->
|
||||
|
||||
---
|
||||
|
||||
## §2 复利内核:数据飞轮怎么转(最重要的一层)
|
||||
|
||||
这是整套系统的发动机。逆向出来的机理:
|
||||
|
||||
### 2.1 飞轮的四个动作(缺一不转)
|
||||
```
|
||||
①捕获信号 → ②聚合偏好 → ③回灌生成 → ④再捕获
|
||||
↑ │
|
||||
└──────────────── 闭环 ───────────────────────┘
|
||||
```
|
||||
- **①捕获**:人的每个决策都是信号——选了哪条文案、选了哪张图、审核通过/打回(带理由)、**把AI草稿改成了什么**。
|
||||
- **②聚合**:把一段时间内的信号统计成"偏好画像"(爱什么角度、拒什么理由、改稿往哪个方向改)。
|
||||
- **③回灌**:下次生成时,把偏好画像拼进 prompt,让 AI 一开始就贴着人的口味产出。
|
||||
- **④再捕获**:新产出又被人决策,信号继续进库。
|
||||
|
||||
### 2.2 为什么"改稿diff"是最强信号(俊达的杀手锏)
|
||||
其他信号是**二选一/打分**(信息量低:只知道A比B好);
|
||||
**改稿diff 是"人主动写出了正确答案"**(信息量最高:直接告诉系统"应该长这样")。
|
||||
|
||||
> 机理:选优信号教系统"别犯错",改稿信号教系统"照这样做"。前者是负反馈,后者是正反馈+监督样本。**一条改稿 ≈ 几十条选优**。这是俊达飞轮转得比别人快的根因。
|
||||
|
||||
### 2.3 冷启动怎么破(飞轮的鸡生蛋问题)
|
||||
飞轮要数据才转,但一开始没数据。逆向出他的解法:
|
||||
- **种子期靠人**:FDE驻场/一把手先用,快速喂前几十条决策(口述里的"1+1起步、任务包"就是在攒种子信号)。
|
||||
- **够量了才自动**:信号攒过阈值,系统从"等人喂"切到"自动贴偏好生成"。
|
||||
- → 对应 Clover 代码里已有的 `FLYWHEEL_COLD_START=5` / `FLYWHEEL_LOOKBACK=50`,**这俩常量就是冷启动阈值和记忆窗口,方向完全一致**。
|
||||
|
||||
### 2.4 飞轮的隐藏前提:信号必须"归属清晰"
|
||||
多租户/多客户场景,A客户的偏好不能污染B客户。
|
||||
→ 对应 Clover 的 `workspace_id` 逻辑隔离 + 飞轮事件带 `data_ownership` 字段。**俊达必然也有这层,否则SCRM多客户会串味。**
|
||||
|
||||
---
|
||||
|
||||
## §3 流水线引擎:为什么每个环节都做成"会进化的agent"
|
||||
|
||||
### 3.1 工具 vs 流水线 vs 进化体(三级跳)
|
||||
俊达口述的"工具→系统、生成→流水线、定型→进化",逆向成机理就是:
|
||||
|
||||
| 阶段 | 形态 | 问题 |
|
||||
|---|---|---|
|
||||
| 工具 | 一次性生成,用完即弃 | 经验不沉淀,每次从零 |
|
||||
| 流水线 | 多环节串成自动流 | 能跑量,但不会变好 |
|
||||
| **进化体** | **每环节是个会被飞轮喂养的agent** | **跑得越多,每环越聪明** |
|
||||
|
||||
> 内核:俊达把"流水线"和"飞轮"**焊死在一起**——流水线负责"跑量",飞轮负责"每跑一轮都进化"。单有流水线 = 量大但平庸;单有飞轮 = 聪明但产能低。**两者咬合才是他的护城河。**
|
||||
|
||||
### 3.2 "环"的统一结构(可复用的抽象)
|
||||
逆向出他每个环节(选题/生成/选优/改稿/追单/复盘)都是同一个模子:
|
||||
```
|
||||
输入 → agent生成 → 人决策(产生信号) → 信号进飞轮 → 喂养这个环的下一次
|
||||
```
|
||||
**所以"加一个新能力" = "加一个符合这个模子的新环"**,而不是重写系统。这解释了他为什么能从内容中台长出SCRM——同一个模子复制到销售场景。
|
||||
|
||||
<!-- 后续章节由 Edit 补充:§5 平台对抗 / §6 交付商业 / §7 可迁移底层模型 / §8 映射Clover -->
|
||||
|
||||
---
|
||||
|
||||
## §4 资产化引擎:经验为什么不会随人流失
|
||||
|
||||
### 4.1 核心动作:把"一次性产出"变成"可复用资产"
|
||||
普通玩法:写完一篇笔记 → 发出去 → 结束。
|
||||
俊达玩法:写完一篇 → **拆成零件入库**(标题进标题库、配图进图库、卖点进卖点库、结构进结构库、关键词进词库)→ 每个零件打标评级 → 下次生成直接调库。
|
||||
|
||||
> 机理:他把"内容"拆成**可组合的最小单元**,每个单元独立沉淀、独立进化。这样高手的经验不是存在某个人脑子里,而是**长在库里**——人走了,库还在,新人调库就能产出接近高手的东西。
|
||||
|
||||
### 4.2 爆款拆解 = 给资产库"喂外部养料"
|
||||
自己产的内容是"内循环",会越来越同质。
|
||||
爆款拆解(逆向别人的爆款 → 拆出配方 → 进库)是"外循环",**持续从市场吸收新配方**,防止资产库近亲繁殖。
|
||||
> 内核:内循环保证"稳定复用",外循环保证"不断进化"。资产库要两条腿走路。
|
||||
|
||||
### 4.3 评级是资产化的灵魂
|
||||
入库不打标 = 垃圾场。俊达给每个资产打"参考等级"(爆款级/可用级/淘汰级)。
|
||||
→ 对应 Clover `fission.py` 里已有的 `reference_level` 字段。**这个字段就是资产评级的载体,表已建好,只是还没接线。**
|
||||
|
||||
---
|
||||
|
||||
## §5 平台对抗引擎:为什么"跑量"能持续不被封
|
||||
|
||||
俊达系统能持续跑量,背后是一整套对抗工程,逆向出三个动作:
|
||||
|
||||
| 对抗动作 | 解决什么 | 机理 |
|
||||
|---|---|---|
|
||||
| **提示词全动态** | 防文案查重/同质判定 | 每次prompt都变 → 产出天然不同,不触发平台判重 |
|
||||
| **消两层水印 + 锐化/去摩尔纹** | 防图片溯源/判搬运 | 图片指纹被打散 |
|
||||
| **双通道生图+后台选优** | 防单一模型风格被识别 + 保质量 | 便宜通道走量、官方通道保底,后台评分选最优 |
|
||||
|
||||
> 内核:**跑量的天敌是平台规则,所以"对抗"必须工程化、自动化**——不能靠人工每次改。俊达把对抗做进了流水线,所以能无人化跑量。这是"能跑量"和"敢跑量"的区别。
|
||||
|
||||
---
|
||||
|
||||
## §6 交付与商业逻辑:为什么是"驻场陪跑"而不是"卖软件"
|
||||
|
||||
逆向他的商业模式内核:
|
||||
|
||||
- **不卖工具,卖"长进客户业务里的系统"**:任务包模式 + FDE驻场 + 1+1起步——本质是降低客户"用起来"的门槛,因为飞轮要客户真用才转得起来。
|
||||
- **一把手工程**:必须老板亲自推,否则一线不喂信号,飞轮空转。
|
||||
- **商业飞轮 = 产品飞轮的镜像**:客户用得越深 → 数据越多 → 系统越聪明 → 客户越离不开 → 续费/扩单。**产品的复利和商业的复利是同一个飞轮。**
|
||||
|
||||
> 内核:他卖的不是"AI能写文案",是"一套会跟着你公司一起变聪明的生产系统"——这东西越用越值钱,所以能驻场收费、能续费。
|
||||
|
||||
---
|
||||
|
||||
## §7 可迁移底层模型(抽象出来,套到北哥任何品类)
|
||||
|
||||
把俊达整套抽象成一个**与品类无关**的模型——这才是真正能借鉴的东西:
|
||||
|
||||
```
|
||||
┌─────────────────────────────┐
|
||||
│ 会进化的内容生产系统 │
|
||||
└─────────────────────────────┘
|
||||
[流水线] [飞轮] [资产库]
|
||||
把人做的每步 捕获人的每个决策 把产出拆成
|
||||
拆成agent环 ←→ 聚合成偏好回灌 ←→ 可复用零件入库
|
||||
(负责跑量) (负责进化) (负责不流失)
|
||||
│ │ │
|
||||
└──────────────────┼──────────────────┘
|
||||
[平台对抗层]
|
||||
(动态化/去指纹,保证能持续跑量)
|
||||
│
|
||||
[交付:驻场陪跑]
|
||||
(一把手+FDE,保证飞轮被真正喂养)
|
||||
```
|
||||
|
||||
**四条可迁移定律:**
|
||||
1. **任何重复的人工决策,都是飞轮信号**——能捕获就别浪费(尤其改稿diff)。
|
||||
2. **任何一次性产出,都该拆成可复用资产**——入库、打标、评级。
|
||||
3. **流水线和飞轮必须咬合**——光跑量不进化=平庸,光进化不跑量=没产能。
|
||||
4. **能无人化跑量的前提是对抗工程化**——对抗不能靠人工。
|
||||
|
||||
> 这个模型和品类无关。素颜霜能套,北哥的品类也能套——**只需要换掉每个环里的prompt和资产维度,骨架不变**。
|
||||
|
||||
---
|
||||
|
||||
## §8 落到北哥 Clover:底层逻辑层面我们缺什么
|
||||
|
||||
| 底层引擎 | Clover现状 | 缺口 |
|
||||
|---|---|---|
|
||||
| 流水线 | ✅ 13环目标导向已是流水线 | 基本到位 |
|
||||
| 飞轮-捕获 | 🟡 有选优/审核信号 | **缺改稿diff信号(最强那条)← 一期就补** |
|
||||
| 飞轮-聚合回灌 | ✅ preference_aggregator已有 | 改稿样本要接进来 |
|
||||
| 资产库 | 🟡 fission表已建(reference_level在) | **没接线,经验还没真正资产化** |
|
||||
| 平台对抗 | ❓ 待确认Clover做到哪 | 需排查动态prompt/去指纹 |
|
||||
| 交付 | — | 商业层,非代码 |
|
||||
|
||||
> 结论:**底层逻辑上,Clover的"流水线"和"飞轮回灌"骨架已对齐俊达,差的是两块——①飞轮少了最强信号(改稿diff),②资产库建了表没接线。这两块恰好就是配套映射文档里定的一期/二期增量,方向完全自洽。**
|
||||
|
||||
---
|
||||
|
||||
## §9 这份逆向的可信度声明
|
||||
|
||||
- §1-§7 的**底层逻辑/机理/可迁移模型**:来源是口述【确证】+PPT明示,**是俊达大方分享的方法论层,可信、可直接借鉴**。
|
||||
- §2.3 / §4.3 / §8 里凡提到 Clover 具体常量/字段(FLYWHEEL_COLD_START、reference_level等):来源是**我们自己的代码**,确证。
|
||||
- 全程**不含**俊达的prompt原文、评分权重、界面字段——那些辨认不全也不该抄,逆向底层逻辑根本不需要它们。
|
||||
- 一句话:**逆向的是"他为什么这么设计",不是"他具体写了什么"。前者是原理,能借;后者是knowhow,不抄。**
|
||||
|
||||
|
||||
223
plans/俊达增量①-改稿diff-实施细案.md
Normal file
223
plans/俊达增量①-改稿diff-实施细案.md
Normal file
@@ -0,0 +1,223 @@
|
||||
# 俊达增量① · 改稿 diff 飞轮信号 — 实施细案
|
||||
|
||||
> 配套 `俊达对标-增量落地映射.md` §二。本文是可直接交给开发窗口执行的细案。
|
||||
> 代码勘验:2026-06-15,迁移已到 011。**所有定位用函数名/类名,不用行号**(另一窗口在改 P0,行号会漂)。
|
||||
> 一句话:飞轮当前只有"选/审"弱信号,本增量加"运营改稿"强信号——AI 不只学到"这条不好",还学到"该改成什么样"。
|
||||
|
||||
---
|
||||
|
||||
## §0 并发窗口避让总则(最重要,先读)
|
||||
|
||||
另一个窗口正在改 **P0:第5环文案 / 第6环配图 / 第8环审核**(见 `plans/总核销表.md` M1/M2/M3)。本增量挂点与之**部分重叠**,按下表避让:
|
||||
|
||||
| 本增量要动的文件 | P0 是否在动 | 冲突等级 | 避让策略 |
|
||||
|---|---|---|---|
|
||||
| `constants/enums.py` | 可能(改模型/枚举) | 🟡中 | 只**追加**枚举值和权重项,不改存量行;合并时手动 review 这一处 |
|
||||
| `ai_engine/constants.py` | 可能(FLYWHEEL_WEIGHTS) | 🟡中 | 同上,只追加 `text_edit` 一行 |
|
||||
| `models/task.py` `TextCandidate` | M1文案可能动 | 🟠高 | **只加2个新字段**(nullable),不碰现有字段;新迁移012独立 |
|
||||
| `api/v1/task_actions.py` | 选文案在此 | 🟠高 | **新增独立端点函数**,不改 `select_text`;放文件末尾减少 diff 碰撞 |
|
||||
| `ai_engine/preference_aggregator.py` | 第5环可能动 | 🟠高 | 新增独立 helper 函数 `_extract_edit_samples`,主函数只插一行调用 |
|
||||
| `review.py` | M3审核**正在改** | 🔴最高 | **本增量不碰 review.py**(改稿入口走 task_actions,不走审核) |
|
||||
| 前端 `TextCandidateCard.tsx` | 可能 | 🟡中 | 加可编辑态用新 prop,默认关闭,不影响现有只读渲染 |
|
||||
|
||||
**总原则**:能新增就不修改;新增函数/端点/字段集中放,减少与 P0 的 diff 行重叠;`enums.py` 两处权重是唯一必须手动合并点,开工前跟那个窗口对一句"我要往 SignalType 加 text_edit"。
|
||||
|
||||
**落库顺序建议**:等 P0 的 M1/M3 合并完,再起本增量分支,避免 rebase 地狱。后端 S1-S4 先上线(飞轮真变强),前端 S5 随后。
|
||||
|
||||
---
|
||||
|
||||
## §1 五步细化(每步:动什么·代码骨架·验证)
|
||||
|
||||
### S1 加信号类型 `text_edit`(⚠️两处权重都要加)
|
||||
|
||||
**1a. `backend/app/constants/enums.py` → `class SignalType`**
|
||||
追加一个枚举值(放 REGENERATE 后):
|
||||
```python
|
||||
TEXT_EDIT = "text_edit" # 运营改稿(强信号,俊达"改稿diff最值钱")
|
||||
```
|
||||
同文件 `SIGNAL_WEIGHTS` 字典追加一行:
|
||||
```python
|
||||
SignalType.TEXT_EDIT: 4, # 强于普通选择(+3),弱于审过(+5)
|
||||
```
|
||||
|
||||
**1b. `backend/app/services/ai_engine/constants.py` → `FLYWHEEL_WEIGHTS`**
|
||||
> ⚠️ 这是**第二处权重定义**(聚合器用的是这个,不是enums那个),漏了会导致改稿信号权重算成0。追加:
|
||||
```python
|
||||
"text_edit": 4,
|
||||
```
|
||||
|
||||
**权重为什么是+4**:选文案=运营从N条挑1条(弱监督,只说"这条还行");改稿=运营动手写出"正确答案"(强监督,给了方向)。所以高于选择(+3);但单条改稿样本量小、未经组长终审,低于审核通过(+5)。北哥可在调教时校准。
|
||||
|
||||
**验证**:`python -c "from app.constants.enums import SIGNAL_WEIGHTS, SignalType; print(SIGNAL_WEIGHTS[SignalType.TEXT_EDIT])"` → 4。
|
||||
|
||||
---
|
||||
|
||||
### S2 存改后内容(`TextCandidate` +2字段 + 迁移012)
|
||||
|
||||
**2a. `backend/app/models/task.py` → `class TextCandidate`**
|
||||
在 `is_selected` 字段后**追加**(不动现有字段,遵§0🟠避让):
|
||||
```python
|
||||
edited_content: Mapped[str | None] = mapped_column(Text) # 运营改后正文,NULL=没改过
|
||||
edited_at: Mapped[datetime | None] = mapped_column(DateTime) # 改稿时间
|
||||
```
|
||||
|
||||
**设计取舍:为什么不单建一张 diff 表**
|
||||
- 存"AI原文 `content` + 改后 `edited_content`"两份即可,diff 在聚合时实时算(Python `difflib` 或直接把"原→改"两段喂 prompt)。
|
||||
- 省一张表、省一次 join,且原文已在 `content` 里,天然成对。
|
||||
|
||||
**2b. 新迁移 `backend/app/alembic/versions/012_text_edit_flywheel.py`**
|
||||
> 版本号续 011(总核销表已用到011),命名避开撞车。
|
||||
```python
|
||||
"""012 改稿diff飞轮:TextCandidate加edited_content/edited_at"""
|
||||
def upgrade():
|
||||
op.add_column('text_candidates', sa.Column('edited_content', sa.Text(), nullable=True))
|
||||
op.add_column('text_candidates', sa.Column('edited_at', sa.DateTime(), nullable=True))
|
||||
def downgrade():
|
||||
op.drop_column('text_candidates', 'edited_at')
|
||||
op.drop_column('text_candidates', 'edited_content')
|
||||
```
|
||||
> down_revision 填当前 head(011)。先 `alembic heads` 确认 head 是不是011——**若那个窗口已加了012/013,顺延改号**。
|
||||
|
||||
**验证**:`alembic upgrade head` 后 `DESC text_candidates;` 见两新列且可空(存量数据不受影响)。
|
||||
|
||||
### S3 采集端点(`task_actions.py` 新增独立函数)
|
||||
|
||||
> ⚠️§0🟠:**不改 `select_text`**,在 `task_actions.py` **末尾**新增端点,减少与 P0 选文案逻辑的 diff 碰撞。
|
||||
|
||||
参照同文件 `select_text` 的写法(已有 `record_signal` import 范式):
|
||||
```python
|
||||
from pydantic import BaseModel
|
||||
|
||||
class EditTextRequest(BaseModel):
|
||||
edited_content: str # 运营改后的正文全文
|
||||
|
||||
@router.post("/{task_id}/text-candidates/{cid}/edit")
|
||||
def edit_text(
|
||||
task_id: int, cid: int, body: EditTextRequest,
|
||||
current_user: Annotated[CurrentUser, Depends(require_write_permission)] = None,
|
||||
db: Session = Depends(get_db),
|
||||
):
|
||||
"""运营改稿(飞轮信号 text_edit +4,强信号)。"""
|
||||
from app.services.flywheel_service import record_signal
|
||||
from datetime import datetime, timezone
|
||||
task = _check_task_ownership(
|
||||
db.query(GenerationTask).filter(GenerationTask.id == task_id).first(),
|
||||
current_user.workspace_id,
|
||||
)
|
||||
tc = db.query(TextCandidate).filter(
|
||||
TextCandidate.id == cid, TextCandidate.task_id == task_id
|
||||
).first()
|
||||
if not tc:
|
||||
raise_not_found("文案候选不存在")
|
||||
original = tc.content # 留底,给 reason 存"原→改"
|
||||
tc.edited_content = body.edited_content
|
||||
tc.edited_at = datetime.now(timezone.utc)
|
||||
db.commit()
|
||||
# diff 摘要存 reason(复用现成 Text 字段,不新增列)
|
||||
diff_summary = _build_edit_diff(original, body.edited_content)
|
||||
record_signal(db, current_user, task, "text_edit",
|
||||
candidate_id=tc.id, angle_label=tc.angle_label, reason=diff_summary)
|
||||
return ok({"candidate_id": cid, "edited": True})
|
||||
```
|
||||
|
||||
**`_build_edit_diff` 放哪**:放 `task_actions.py` 末尾或 `flywheel_service.py`。MVP 可极简——直接存"原文→改文"两段拼接(聚合时再让大模型理解差异),不必上 difflib:
|
||||
```python
|
||||
def _build_edit_diff(original: str, edited: str) -> str:
|
||||
# MVP:原文+改后并存,差异交给生成时的大模型理解(不做规则diff,遵"打回原因不AI归纳"同源克制)
|
||||
return f"原稿:{(original or '')[:200]}|改后:{edited[:200]}"
|
||||
```
|
||||
|
||||
**为什么不走 review.py**:审核台正被 P0(M3) 改(🔴最高冲突),且改稿是"运营在选择/确认阶段动手"的动作,归 task_actions 更合理——审核是组长的事,改稿是运营的事,职责也对。
|
||||
|
||||
**验证**:`curl POST /api/v1/tasks/{id}/text-candidates/{cid}/edit -d '{"edited_content":"..."}'` → 查 `preference_events` 有 `signal_type=text_edit, signal_weight=4` 行 + `text_candidates.edited_content` 已写。
|
||||
|
||||
---
|
||||
|
||||
### S4 聚合注入 prompt(`preference_aggregator.py`,改稿片段置顶)
|
||||
|
||||
> ⚠️§0🟠:主函数 `aggregate_preference_context` 只插一行调用,逻辑放**新增 helper**,减少与 P0 第5环改动的重叠。
|
||||
|
||||
**4a. 新增 helper**(放 `preference_aggregator.py` 内 `_build_prompt_fragment` 旁):
|
||||
```python
|
||||
def _extract_edit_samples(relevant: list[dict], limit: int = 3) -> list[str]:
|
||||
"""抽改稿信号的 reason(即'原→改'摘要),最近 limit 条。强信号置顶用。"""
|
||||
samples = [
|
||||
str(e.get("reason", "")).strip()
|
||||
for e in relevant
|
||||
if e.get("signal_type") == "text_edit" and e.get("reason")
|
||||
]
|
||||
return samples[-limit:]
|
||||
```
|
||||
|
||||
**4b. 主函数 `aggregate_preference_context` 里取样**(在已有的 angle/reject 统计循环后加):
|
||||
```python
|
||||
edit_samples = _extract_edit_samples(relevant)
|
||||
```
|
||||
传给 `_build_prompt_fragment`(给该函数加一个 `edit_samples` 形参)。
|
||||
|
||||
**4c. `_build_prompt_fragment` 把改稿片段插到最前**(强信号最高优先):
|
||||
```python
|
||||
# 函数开头、top_angles 之前 insert:
|
||||
if edit_samples:
|
||||
formatted = ";".join(f"「{s}」" for s in edit_samples)
|
||||
lines.append(f"【改稿示范·最高优先】运营曾这样修改文案:{formatted}。请直接对齐这种写法与措辞。")
|
||||
# ...原有 top_angles / reject_reasons / custom 逻辑接在后面
|
||||
```
|
||||
> 因为 `_build_prompt_fragment` 是 `lines.append` 顺序拼接,把改稿段放在**函数最前面 append**即可天然置顶;返回值同时把 `edit_count` 加进去供前端显示。
|
||||
|
||||
**4d. 同步两个调用方**:
|
||||
- `flywheel_service.py:get_preference_context`(API侧实时聚合)——它是另一套**简化重实现**,也要补 `text_edit` 的取样(否则 API 返回的"已注入"摘要漏算改稿)。两处聚合逻辑重复是现状技术债,本增量先各补各的,**不顺手合并**(避免扩大改动面、撞 P0)。
|
||||
- worker 侧 `pipeline_steps.py:load_flywheel_context` → 它调 `aggregate_preference_context`,4a-4c 改完自动生效,无需改 worker。
|
||||
|
||||
**验证**:造3条 text_edit 信号后调生成,看 `flywheel_injected` SSE 事件 + MongoDB debug trace 里 user_prompt 含"【改稿示范】"。
|
||||
|
||||
---
|
||||
|
||||
### S5 前端改稿框(`TextCandidateCard.tsx`,可编辑态可选开)
|
||||
|
||||
> ⚠️§0🟡:现卡片 `content` 是只读 `<p>`。加可编辑用**新 prop 默认关闭**,不影响现有只读渲染与 P0 可能的改动。
|
||||
|
||||
**5a. `frontend/src/components/tasks/TextCandidateCard.tsx`**
|
||||
- props 加 `editable?: boolean`(默认 false)和 `onEdit?: (cid, newContent) => void`。
|
||||
- `editable` 为真时,把 `<p>{candidate.content}</p>` 换成受控 `<textarea>`,失焦(onBlur)且内容有变化时调 `onEdit`。
|
||||
- 默认 false → 现有所有调用方行为不变(零回归)。
|
||||
|
||||
**5b. 文案选择页 `frontend/src/app/tasks/[id]/text/page.tsx`**
|
||||
- 给 `<TextCandidateCard>` 传 `editable={true}` 和 `onEdit` 回调。
|
||||
- `onEdit` 里调:`api.post(\`/api/v1/tasks/${taskId}/text-candidates/${cid}/edit\`, { edited_content })`(参照同文件已有的 `select` 调用范式)。
|
||||
|
||||
**5c. 注入提示** `frontend/src/components/FlywheelBanner.tsx`
|
||||
- 已显示"本次已注入:最近偏好/打回原因",加一行 `已注入 N 条改稿示范`(读 S4c 返回的 `edit_count`)。
|
||||
|
||||
**前端可延后**:若赶 6/27,后端 S1-S4 上线飞轮就已真变强。前端临时兜底:运营把改写后文案当"打回原因"填(走现有 reject)先喂信号。但**不推荐长期兜底**——reject 是 -3 负信号,语义和 +4 改稿相反,会污染权重,只能短期应急。
|
||||
|
||||
---
|
||||
|
||||
## §2 端到端验证脚本(飞轮四点全测)
|
||||
|
||||
按架构方案铁律"飞轮必须可测,不靠感觉更准",跑一遍:
|
||||
|
||||
```
|
||||
1. events写入 :改一条文案 → SELECT * FROM preference_events WHERE signal_type='text_edit'
|
||||
断言:有行、signal_weight=4、reason含"原→改"、workspace_id+product_id正确
|
||||
2. 聚合返片段 :同product造≥5条信号(含3条text_edit) → GET /tasks/{id}/preference/context
|
||||
断言:返回含改稿示范摘要、edit_count≥1
|
||||
3. 下次prompt含 :发起同product新生成任务 → 查 MongoDB debug trace 的 user_prompt
|
||||
断言:含"【改稿示范·最高优先】"且在 top_angles 之前
|
||||
4. UI显示 :FlywheelBanner 显示"已注入 N 条改稿示范"
|
||||
```
|
||||
对应已有测试:`backend/tests/test_flywheel_wiring.py` 加 `test_text_edit_signal_injected`,仿现有飞轮用例写。
|
||||
|
||||
---
|
||||
|
||||
## §3 回滚
|
||||
|
||||
- DB:`alembic downgrade -1`(012 down 删两列,存量 content 不动)。
|
||||
- 代码:enums 两处删 text_edit 行、task_actions 删 edit_text 端点、aggregator 删 helper+调用、前端 editable 传 false。
|
||||
- 因全程"只新增不改存量",回滚=删新增,不留残端。
|
||||
|
||||
---
|
||||
|
||||
## §4 给北哥/倩倩的拍板点
|
||||
1. **改稿权重 +4 是否合理**?(建议先 +4 跑,北哥用一周后校准——权重表本就设计成可调)。
|
||||
2. **改稿样本要不要经组长终审才入飞轮**?MVP="运营一改就入",学得快;保守="改稿+该条最终被审核通过"才记 text_edit(防学到运营改错的)。**建议 MVP 先激进,三期加 outcome 校验**。
|
||||
170
plans/俊达对标-增量落地映射.md
Normal file
170
plans/俊达对标-增量落地映射.md
Normal file
@@ -0,0 +1,170 @@
|
||||
# 俊达产品 → Clover 增量落地映射(对照代码版)
|
||||
|
||||
> 2026-06-15 落盘。来源:俊达万牛会分享(PPT 31页《电商XAI·一家小公司的探索》+ 现场演示视频2段 + 倩倩/俊达口述全文稿)。
|
||||
> 目的:把俊达那套小红书电商全链路AI系统里**值得借鉴的增量**,逐条对照 Clover 现有代码拆到「动哪个文件、加哪张表、改哪个函数」,开工直接照做。
|
||||
> 对齐基准:Clover 走 **13环目标导向**(见 `plans/13环目标导向-修改验收总纲.md`),当前 P0 修第5/6环、P2 等北哥给定义。本文增量**全部挂到 13 环语言下**,不另起炉灶。
|
||||
> 代码事实底座:勘验于 2026-06-15,backend 迁移已到 011,6容器可跑通(task41 端到端 312s 成功)。
|
||||
|
||||
---
|
||||
|
||||
## 〇、一句话结论(先看这个)
|
||||
|
||||
俊达和 Clover 是**同构但错位**:俊达铺的是**全链路广度**(内容+客服+企微+ERP+投放闭环+AI做产品),Clover 扎的是**内容生产单点深度**(尤其生图工程化,比俊达展示的更细)。
|
||||
所以借鉴 = **用俊达的广度,补 Clover 深度之外的空白**,不是照抄。
|
||||
|
||||
**经代码核实后,真正的增量只有 4 个(按 ROI 排序):**
|
||||
|
||||
| 优先级 | 增量 | Clover 现状 | 落到 13 环 | 建议窗口 |
|
||||
|---|---|---|---|---|
|
||||
| ⭐P0-轻 | **改稿 diff 作飞轮最强信号** | 🔴 缺:飞轮缺这一路信号 | 增强第8环审核回路 | 一期 1B 可补 |
|
||||
| ⭐P1 | **爆款拆解中心(产品化)** | 🟡 表建了没接线 | 第11环裂变的「前置入口」 | 一期可补 |
|
||||
| P2 | **素材资产化 + 效果评级库** | 🔴 完全没有 | 第12环归档的「升级版」 | 留二期 |
|
||||
| P3 | **提示词版本化中台 + 投放数据闭环** | 🔴 没有 | 超出13环范围 | 留二/三期 |
|
||||
|
||||
> ⚠️ 两个**伪增量**(看着像缺、其实不缺,别浪费工时)见 §五。
|
||||
|
||||
---
|
||||
|
||||
## 一、Clover 代码现状基线(落盘锚点,后续每条增量对照这个)
|
||||
|
||||
> 增量要挂在已有代码上,先把"已经有什么"钉死,避免重复造或挂错地方。
|
||||
|
||||
### 飞轮(已跑通,是 Clover 的魂)
|
||||
- **信号枚举**:`backend/app/constants/enums.py` → `SignalType` 5个值(text_select/image_select/approve/reject_with_reason/regenerate)+ `SIGNAL_WEIGHTS` 权重表(选+3/审过+5/打回-3)。
|
||||
- **信号写入**:`app/services/flywheel_service.py:record_signal()` — 业务接口内部调用,不暴露独立埋点端点(契约红线)。
|
||||
- **信号采集入口**:`app/api/v1/task_actions.py`(选文案/选图)+ `app/api/v1/review.py`(审核 approve/reject)。
|
||||
- **聚合注入**:`app/services/ai_engine/preference_aggregator.py:aggregate_preference_context()` — 取最近50条 → 最常选角度 + 打回原因近3条原文 → 拼 `prompt_fragment`。
|
||||
- **prompt 组装**:`app/services/ai_engine/prompt_composer.py:compose_variants()` — 飞轮片段追加到 user_prompt 末尾(不污染 system 红线)。
|
||||
- **数据表**:`app/models/flywheel.py` → `preference_events`(迁移004)+ `ai_call_logs`。
|
||||
- **前端**:`frontend/src/components/FlywheelBanner.tsx`("本次已注入"提示)+ `stores/preferenceStore.ts`。
|
||||
|
||||
### 爆款拆解(地基埋了,没接线)
|
||||
- **表已建**:`app/models/fission.py` → `fission_tasks`(迁移010)+ `generation_tasks.source_fission_id`(迁移011)。
|
||||
- **❌ 缺**:无 fission 的 service / api / worker / 前端(已 grep 确认 `app/api app/services app/workers` 零引用)。
|
||||
- **关联**:13环里这是「第11环裂变」,总核销表 M7 状态 = ⏸️等北哥给档位定义。
|
||||
|
||||
### 标杆分析(第2环,等北哥给8维)
|
||||
- `app/models/task.py:GenerationTask.benchmark_ids` + 迁移009 `features_json/analyze_status`;总核销表 M6 = ⏸️等北哥给8维。
|
||||
|
||||
### 生图(比俊达展示的深)
|
||||
- `app/services/ai_engine/storyboard.py`(分镜+`overlay_text` 压字)+ `image_gen.py:146-153`(AI生图直接把字排图上)+ `image_postprocessor.py`(去C2PA水印+转JPG+削像素水印,对应俊达"消水印")。
|
||||
- **关键**:配图与压字**已合一**(生图即排字),不是两道工序。这点影响 §五 伪增量判断。
|
||||
|
||||
### 归档(第12环)
|
||||
- `frontend/src/app/history/` + `delivery_packages` 表(交付包)。总核销表 M4 含日期/品类筛选+导出。
|
||||
|
||||
## 二、增量①:改稿 diff 飞轮信号 ⭐最该补
|
||||
|
||||
### 俊达怎么做的
|
||||
俊达把三类反馈信号分了强弱:**「改稿 diff」标为「强」**,评级 A/B/C/D 和「采纳·重做」标为「中」。他原话:"运营把 AI 写的改了 —— 直接看人怎么改,最值钱。" 因为选/审是**二选一的弱监督**,而人动手改稿是**带具体方向的强监督**——AI 能学到的不只是"这条不好",而是"应该改成什么样"。
|
||||
|
||||
### Clover 缺口(对照代码)
|
||||
- `SignalType` 只有 5 个值,**没有 `text_edit`**。
|
||||
- `TextCandidate`(`app/models/task.py:73`)只有 `content`(AI原文)+ `is_selected`,**没有"运营改后内容"字段**,改稿这个动作根本没地方落。
|
||||
- 现状:运营在审核台看到文案,只能"选/打回写原因",不能直接改——改了也不入飞轮。
|
||||
|
||||
### 怎么落(概要,细化执行见配套文档)
|
||||
|
||||
> ⚠️ **完整可执行方案(含代码骨架+并发窗口避让)已拆到独立文档:`plans/俊达增量①-改稿diff-实施细案.md`**。
|
||||
> 因为另一个窗口正在改 P0(第5/6/8环),改稿diff 恰好挂在审核回路+task_actions,是冲突高危区,细案里逐处标了避让策略。
|
||||
|
||||
五步骨架(详见细案):
|
||||
1. **加信号类型** `text_edit`(权重+4)——注意权重在**两处**定义,都要改。
|
||||
2. **存改后内容**——`TextCandidate` 加 `edited_content`/`edited_at` 两字段,新迁移 012。
|
||||
3. **采集端点**——`task_actions.py` 加 `POST .../text-candidates/{cid}/edit`。
|
||||
4. **聚合注入**——`preference_aggregator.py` 加"改稿示范"片段,置于 prompt_fragment 最前。
|
||||
5. **前端改稿框**——`TextCandidateCard.tsx` 只读 `<p>` 改可编辑。
|
||||
|
||||
### 验收(沿用架构方案"飞轮四点可测")
|
||||
events写入 `text_edit` ✓ / 聚合返回改稿片段 ✓ / 下次 prompt trace 含该片段 ✓ / UI 显示"已注入改稿示范" ✓。
|
||||
|
||||
### 风险与建议
|
||||
- **工程量**:1迁移 + 1端点 + 聚合~15行 + 前端1框,**半天到一天**。
|
||||
- **窗口冲突**:见细案§0,核心是"加字段/加端点用新增不改存量、enums两处权重等P0改完再合"。
|
||||
- **窗口判断**:KR2(飞轮1B)截止6/27,这条不大且价值最高,**这次补**。
|
||||
|
||||
## 三、增量②:爆款拆解中心(产品化)⭐
|
||||
|
||||
### 俊达怎么做的
|
||||
独立的「**拆解中心**」功能(PPT第14页):粘一条小红书爆款链接 → AI 拆成「标题公式 / 句子类型 / 正文结构 / 卖点 / 配图节奏」可复用配方 → **一键存入素材库,变成 AI 下次生成时的样例**。口号"72小时:竞品爆款 → 你的可复用配方"。本质是把"人肉总结套路"自动化。
|
||||
|
||||
### Clover 缺口(对照代码)
|
||||
- **地基已埋**:`fission_tasks` 表(迁移010)+ `generation_tasks.source_fission_id`(迁移011)都建好了。
|
||||
- **但完全没接线**:无 service/api/worker/前端(已确认零引用),总核销表 M7 = ⏸️等北哥给档位。
|
||||
- **现状**:Clover 已有 `benchmark_notes`(标杆笔记)+ 第2环标杆8特征分析(M6,等北哥给8维),但那是"录入参考",**不是俊达式"粘链接→自动拆配方→反哺生成"的闭环**。
|
||||
|
||||
### 关键对齐:俊达"拆解" vs Clover"裂变"是两件事,别混
|
||||
- **Clover 第11环裂变** = 1爆款 → **N 套完整笔记包**(输出成品)。
|
||||
- **俊达拆解中心** = 1爆款 → **1 份可复用配方**(输出方法,存库当样例)。
|
||||
- **俊达的拆解,正好是 Clover 裂变的「前置入口」**:先拆出配方,配方再喂给裂变/常规生成。两者串起来比单独做裂变更完整。
|
||||
|
||||
### 怎么落(复用现有 analyze 能力,不新造模型调用)
|
||||
|
||||
**核心思路**:Clover 第2环标杆分析(`benchmark` 8特征 analyze)和俊达"拆配方"是**同一个 AI 能力**,只是出口不同。不要新写一套 AI 调用,**复用 analyze,加一个"拆解→存配方→反哺"的产品壳**。
|
||||
|
||||
**S1|配方落点**:拆出的配方存哪?两个选项——
|
||||
- 选A(轻,推荐一期):存进现成的 `benchmark_notes.features_json`(迁移009已有字段),拆解结果就是结构化特征,天然契合。前端加"拆解中心"入口,结果进标杆库。
|
||||
- 选B(重):新建 `recipe`/配方表。一期不必,留到素材资产库(§四)一起做。
|
||||
|
||||
**S2|拆解 service**:新建 `app/services/ai_engine/note_decompose.py`,复用 `gemini_factory` + 标杆 analyze 的 prompt,输入笔记文本/截图,输出 `{标题公式, 正文结构, 卖点, 配图节奏}` JSON。
|
||||
|
||||
**S3|采集入口**:链接读取受小红书风控限制——**对齐架构方案已拍板的洞1**:对外主通道 = **截图+手填**(零封号风险),登录态自动采集只作北哥内部插件。所以"拆解中心"输入框 = 粘文本/传截图,不做"系统自动抓链接"。
|
||||
|
||||
**S4|反哺生成**:拆出的配方进 `benchmark_notes`,生成任务选标杆时即可引用 → 已有链路(`generation_tasks.benchmark_ids`)自动打通,无需改生成侧。
|
||||
|
||||
**S5|前端**:新增"拆解中心"页(仿俊达PPT第14页左右分栏:左原笔记、右拆解结果+「一键存入标杆库」)。
|
||||
|
||||
### 风险与建议
|
||||
- **依赖北哥**:和 M6(标杆8维)、M7(裂变档位)都等北哥定义。**建议把"拆解中心"和 M6 合并需求一起问北哥**——既然拆解配方=标杆特征,让北哥一次性给"要拆哪几个维度"即可。
|
||||
- **工程量**:选A路径,service + api + 前端页,约 1-2 天,但**前置依赖北哥给维度**。
|
||||
- **窗口**:一期能做,但**别和 P0 修bug 抢工**。建议 M6 标杆分析做完后,顺势加拆解中心入口(复用同一 analyze)。
|
||||
|
||||
## 四、增量③④:素材资产库 / 提示词中台 / 投放闭环(留二三期)
|
||||
|
||||
> 这三块价值大、但工程量也大,**明确不进一期**,避免冲乱 6/20-6/27 节奏。先记下口子,二期接。
|
||||
|
||||
### 增量③ 素材资产化 + 效果评级库(→ 二期,第12环升级版)
|
||||
- **俊达**:图/视频/压字/评论/标题/文案结构/关键词**各成一库**,进库即 AI 打标 + 按真实互动评 **S/A/B/C/D 级**;素材积累 5/月 → 50+/月。
|
||||
- **Clover 现状**:只有 `delivery_packages`(交付包)+ `history` 归档,**没有"按类型分库 + 效果评级 + 向量搜图"**。
|
||||
- **落点**:二期在 `history`/归档之上建素材库;评级依赖**真实互动数据回填**(架构方案三期"发布效果回填 outcome_score"),所以**评级必须等投放闭环(增量④)先有数据**,顺序上③依赖④。
|
||||
- **eval_score 已留 NULL 口子**(`TextCandidate.eval_score`/`ImageCandidate.eval_score`),架构方案明确"等真评分再装"——正好接俊达的评级,**别用 banana 假评分(88分)污染飞轮**,这条铁律不能破。
|
||||
|
||||
### 增量④ 投放数据闭环(→ 二/三期,超 13 环范围)
|
||||
- **俊达**:打通聚光/千川/乘风/专业号 + 电商后台,单条笔记能看"卖多少货/点击率",AI 出**动作卡**(评A/B/C+建议停/加投)。投手 6h → 自动。
|
||||
- **Clover 现状**:13环里第10环复盘 = ❌不做(人工)。完全没有数据中心。
|
||||
- **落点**:这是独立大模块(要对接小红书各后台API+企业资质),**架构方案三期才提**。俊达验证了 ROI 极高(他DNT ROI 1:4→1:8),值得做,但**是 Clover 二期对外 SaaS 之后的事**。
|
||||
- **提示词版本化中台**(俊达:每提示词版本历史可回滚、标人工改/AI进化、记为什么改):Clover 有 `loader.py PromptLoader 版本alias` 死代码可复活(架构方案§四🟡),但做成俊达那样的"UI可调中台"是二期。一期 prompt 改模板即可,不必上版本管理 UI。
|
||||
|
||||
---
|
||||
|
||||
## 五、两个伪增量(看着像缺、其实不缺,别做)
|
||||
|
||||
### 伪增量1:把"配图/压字"拆成两道独立工序 ❌
|
||||
- 俊达PPT把"配图"和"压字"列成内容流水线里两个独立模块,看着像 Clover 少了一环。
|
||||
- **但 Clover 已经合一实现**:`storyboard.py` 出分镜带 `overlay_text`,`image_gen.py:146-153` 生图时直接把文字排到图上出成品。这是**更先进的做法**(一次成图 vs 先出图再压字两步)。
|
||||
- **结论**:不要为了"对齐俊达模块数"去把它拆开。俊达分两步可能正因为他没做到一次成图。**Clover 这里是优势,保持。**
|
||||
|
||||
### 伪增量2:爆款"逆向工程"当全新功能 ❌(部分)
|
||||
- 看着 Clover 没有"爆款逆向",其实第2环标杆8特征分析 = 同一个 AI 能力(拆爆款)。
|
||||
- **结论**:增量②不是"新造逆向引擎",而是"给已有 analyze 加产品化入口+反哺出口"。别重复造 AI 拆解逻辑。
|
||||
|
||||
---
|
||||
|
||||
## 六、俊达最该抄的 5 条认知(非功能,是方法论)
|
||||
|
||||
这 5 条比任何功能都值钱,且和 Clover 设计哲学高度一致,可直接写进北哥项目的产品理念:
|
||||
|
||||
1. **AI 当组织成员/员工管,不当工具** —— 拆成"选题员工/标题员工/配图员工",每个都是 agent。对应 Clover 多步流水线。
|
||||
2. **生成 → 流水线** —— 不让 AI 一口气写完,拆工序、每步 AI 出活、人审一眼。Clover 已是这套。
|
||||
3. **定型 → 进化** —— AI 不该买来就定型,每天因真实反馈变聪明。= Clover 飞轮(魂)。
|
||||
4. **任务包模式** —— 人只处理 AI 搞不定的疑难,顺手把解法训练回 AI;任务包越来越少。可作为 Clover 飞轮+审核的长期叙事。
|
||||
5. **颗粒度无限细分 → 素材库索引 → 生成** —— 把经验拆到最细存库,生成时索引。对应增量③素材资产化。
|
||||
6. **诚实克制**(俊达"冠军-挑战者+人审,绝不盲目自动上线")—— 和 Clover"eval_score留NULL不用假分""飞轮四点可测"完全同源。**这是双方最该互相印证的设计底线。**
|
||||
|
||||
---
|
||||
|
||||
## 附:俊达全产品模块地图(视频左侧导航补全,供北哥扩展参考)
|
||||
|
||||
视频里俊达系统左侧菜单(手机拍投影,已尽力辨认):
|
||||
内容中台(选题/标题/正文/配图/评论/素材库/拆解中心)· 音乐创作 · 客户管理 · 岸署管理 · AI销售 · 机器人管理 · 微信Agent · Agent工具包 · 发布管理 · 全平台自动化 · 客户SOP · 群发SOP · SOP执行管理 · 数据复盘 · 乘风账户财务(投放数据)· 知识库。
|
||||
> 这是"一个人开发的全链路"全貌。Clover 一期只对应其中"内容中台"一块,其余是北哥项目二期/三期或独立产品线的想象空间。
|
||||
190
plans/修改处理方案-第一批.md
Normal file
190
plans/修改处理方案-第一批.md
Normal file
@@ -0,0 +1,190 @@
|
||||
# Clover 修改处理方案 · 第一批(⚠️ 做了不合格)
|
||||
|
||||
> 倩倩姐审方案专用。**未拍板不动代码**。每项含:现状代码 / 改后代码 / 改动文件清单 / 风险 / 验收。
|
||||
> 现状代码均已逐行读核,行号真实。
|
||||
|
||||
---
|
||||
|
||||
## 修1 · 90分阈值过滤形同虚设
|
||||
|
||||
**根因**:`pipeline_io.py:96-106` 循环把 `candidates_raw` 全部入库,没看 `passed`。
|
||||
text_variants.py 已给每条算了 `passed`(`text_variants.py:101`),但 pipeline 没用它过滤。
|
||||
|
||||
**现状代码**(pipeline_io.py:95-108):
|
||||
```python
|
||||
seq = seq_start
|
||||
for i, c in enumerate(candidates_raw):
|
||||
tc = TextCandidate(
|
||||
workspace_id=workspace_id, task_id=task.id,
|
||||
source=CandidateSource.AI,
|
||||
angle_label=c.get("angle_label") or c.get("angle", ""),
|
||||
content=json.dumps(c, ensure_ascii=False),
|
||||
score_json=json.dumps(c.get("score_detail", []), ensure_ascii=False),
|
||||
banned_word_status=BannedWordStatus(c.get("banned_word_status", "pass")),
|
||||
)
|
||||
db.add(tc)
|
||||
db.flush()
|
||||
```
|
||||
|
||||
**改后代码**:
|
||||
```python
|
||||
# 90分过滤:只入库 passed 的;硬拦截(hard_block)无论分数都剔除
|
||||
qualified = [c for c in candidates_raw
|
||||
if c.get("passed") and c.get("banned_word_status") != "hard_block"]
|
||||
# 回退兜底:全员未达标时不空屏,取分最高的 N 条入库并标记 below_threshold
|
||||
if not qualified:
|
||||
fallback = sorted(candidates_raw, key=lambda x: x.get("score", 0), reverse=True)
|
||||
qualified = [c for c in fallback if c.get("banned_word_status") != "hard_block"][:task.text_count]
|
||||
for c in qualified:
|
||||
c["below_threshold"] = True # 前端可标"未达90分,仅供参考"
|
||||
|
||||
seq = seq_start
|
||||
for i, c in enumerate(qualified):
|
||||
tc = TextCandidate(...) # 同现状,circ 改成遍历 qualified
|
||||
db.add(tc)
|
||||
db.flush()
|
||||
...
|
||||
push_fn(..., "text_candidate", {
|
||||
..., "below_threshold": c.get("below_threshold", False), # 新增透传
|
||||
}, seq)
|
||||
```
|
||||
|
||||
**改动文件**:
|
||||
- `backend/app/workers/pipeline_io.py`(run_text_generation,约改15行)
|
||||
- `frontend/src/components/tasks/TextCandidateCard.tsx`(below_threshold时显黄标,约5行,可选)
|
||||
|
||||
**风险**:阈值90偏严,正常出文案可能常触发回退。回退逻辑必须有,否则用户看到空列表(比现在更糟)。
|
||||
**验收**:①跑任务,列表只剩≥90分 ②人为造全低分,确认回退展示TopN且带黄标 ③hard_block的永不出现。
|
||||
**待拍板**:回退要不要?我建议要(空屏体验更差)。below_threshold黄标前端做不做?
|
||||
|
||||
---
|
||||
|
||||
## 修2 · 品牌词字段缺失(文案+生图同根因,一次解两处)
|
||||
|
||||
**根因**:`products` 表无 `brand_keyword` 列(model:product.py:28-40 无此字段)。
|
||||
但三处代码都在读它:`_text_prompt.py:137`、`storyboard.py:133`、`image_gen.py:140`。
|
||||
→ `product.get("brand_keyword")` 永远 None → 文案不植入品牌词、生图特写图不带品牌词,静默失效。
|
||||
|
||||
**改动分5步:**
|
||||
|
||||
**① 新建迁移** `backend/alembic/versions/008_product_brand_keyword.py`:
|
||||
```python
|
||||
"""add brand_keyword to products
|
||||
Revision ID: 008
|
||||
Revises: 007
|
||||
"""
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
revision = "008"
|
||||
down_revision = "007"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
def upgrade():
|
||||
op.add_column("products", sa.Column(
|
||||
"brand_keyword", sa.String(64), nullable=True,
|
||||
comment="品牌词,植入文案每条+生图特写图(第2/6张)"))
|
||||
|
||||
def downgrade():
|
||||
op.drop_column("products", "brand_keyword")
|
||||
```
|
||||
|
||||
**② 模型加字段** `models/product.py`(image_path 后插一行):
|
||||
```python
|
||||
brand_keyword: Mapped[str | None] = mapped_column(String(64)) # 品牌词,植入文案+生图
|
||||
```
|
||||
|
||||
**③ DTO加字段** `api/v1/products.py:24 ProductCreate`:
|
||||
```python
|
||||
brand_keyword: str | None = None # 品牌词
|
||||
```
|
||||
`create_product`(L85) 构造 Product 时加 `brand_keyword=body.brand_keyword`;
|
||||
`_fmt_product`(L49) 返回加 `"brand_keyword": p.brand_keyword`。
|
||||
|
||||
**④ 前端录入框**:产品表单加"品牌词"输入(`ProductSubComponents.tsx` 或产品创建表单)。
|
||||
|
||||
**⑤ 确认读取生效**:三处读取代码已存在,加字段后自动拿到值,无需改。
|
||||
|
||||
**改动文件**:008迁移(新)、model/product.py、api/v1/products.py、前端产品表单。
|
||||
**风险**:①北哥环境要 `alembic upgrade head` 跑迁移 ②老产品该列NULL→读到空串,三处已用 `or ""` 兜底,不报错。
|
||||
**验收**:建产品填"龙石"→生成文案每条含"龙石"、生图第2/6张画面带"龙石"。
|
||||
**待拍板**:品牌词录在**产品级**(随产品固定,方案默认)还是**任务级**(每次任务可改)?
|
||||
|
||||
---
|
||||
|
||||
## 修4 · 侧边栏导航404(先放修4,修3叠字单列文末)
|
||||
|
||||
**根因**:`Sidebar.tsx:19-28` 的 NAV_ITEMS 8条里,4条指向不存在的页:
|
||||
- `/tasks`(无 page)、`/images`(无 page)、`/tasks/build`(无 page)、`/tasks/list`(无 page)
|
||||
实际存在的页:/dashboard /tasks/new /tasks/[id]/text /tasks/[id]/images /tasks/[id]/confirm /review /history /config
|
||||
|
||||
**现状代码**(Sidebar.tsx:19-28):
|
||||
```tsx
|
||||
const NAV_ITEMS: NavItem[] = [
|
||||
{ label: '工作台', href: '/dashboard', icon: '🏠' },
|
||||
{ label: '开新任务', href: '/tasks/new', icon: '✏️' },
|
||||
{ label: '选择文案', href: '/tasks', icon: '📝' }, // 404
|
||||
{ label: '选择图片', href: '/images', icon: '🖼️' }, // 404
|
||||
{ label: '建立任务', href: '/tasks/build', icon: '⚙️' }, // 404
|
||||
{ label: '任务列表', href: '/tasks/list', icon: '📋' }, // 404
|
||||
{ label: '历史归档', href: '/history', icon: '🗂️' },
|
||||
{ label: '配置中心', href: '/config', roles: ['admin'], icon: '⚙️' },
|
||||
];
|
||||
```
|
||||
|
||||
**改后代码**:删掉4条死链。选文案/选图片是任务流程内的步骤页(/tasks/[id]/text 等),不该做全局导航,进了具体任务才有。审核页`/review`原本漏在导航里,补上。
|
||||
```tsx
|
||||
const NAV_ITEMS: NavItem[] = [
|
||||
{ label: '工作台', href: '/dashboard', icon: '🏠' },
|
||||
{ label: '开新任务', href: '/tasks/new', icon: '✏️' },
|
||||
{ label: '审核', href: '/review', roles: ['admin', 'leader'], icon: '✅' },
|
||||
{ label: '历史归档', href: '/history', icon: '🗂️' },
|
||||
{ label: '配置中心', href: '/config', roles: ['admin'], icon: '⚙️' },
|
||||
];
|
||||
```
|
||||
|
||||
**改动文件**:`frontend/src/components/layout/Sidebar.tsx`(改NAV_ITEMS数组)。
|
||||
**风险**:无,纯导航项删改。
|
||||
**验收**:点遍每个导航项都进到真实页,无404。
|
||||
**待拍板**:审核页要不要进侧边栏(现状代码注释提到/review角色守卫但导航里没有)?建议补上。
|
||||
|
||||
---
|
||||
|
||||
## 修5 · 文案调用无网络退避重试
|
||||
|
||||
**根因**:`text_variants.py:49 _generate_one_batch` 只在JSON解析失败时重试2次,网络层503/超时不退避。
|
||||
生图侧已有成熟退避 `_retry`(image_gen.py:51-63),文案没复用。
|
||||
|
||||
**现状代码**(text_variants.py:47-56):
|
||||
```python
|
||||
async def _generate_one_batch(llm_client, product, batch_n, extra) -> list[dict]:
|
||||
for attempt in range(2):
|
||||
raw = await _call_llm(llm_client, build_prompt(product, batch_n, extra_rules=extra))
|
||||
parsed = parse_json_array(raw)
|
||||
if parsed:
|
||||
return parsed
|
||||
logger.warning(...)
|
||||
return []
|
||||
```
|
||||
|
||||
**改后代码**:_call_llm 返回空(含503/超时)时退避重试。注意:退避会拉长耗时,须控制总时长不撞60s网关——故退避只1次、间隔短(2s)。
|
||||
```python
|
||||
async def _generate_one_batch(llm_client, product, batch_n, extra) -> list[dict]:
|
||||
for attempt in range(3): # 解析失败/网络空 共最多3次
|
||||
raw = await _call_llm(llm_client, build_prompt(product, batch_n, extra_rules=extra))
|
||||
parsed = parse_json_array(raw)
|
||||
if parsed:
|
||||
return parsed
|
||||
if not raw and attempt < 2: # 网络层空响应→短退避再试
|
||||
await asyncio.sleep(2 * (attempt + 1)) # 2s,4s
|
||||
logger.warning(...)
|
||||
return []
|
||||
```
|
||||
|
||||
**改动文件**:`backend/app/services/ai_engine/text_variants.py`(_generate_one_batch,约改5行)。
|
||||
**风险**:退避叠加可能逼近60s网关上限;故只退避2次、间隔短。若仍超时,本地兜底(build_local_drafts)已兜底。
|
||||
**验收**:模拟apiports 503,确认自动退避重试而非直接掉本地兜底。
|
||||
|
||||
---
|
||||
|
||||
> 修3(瓶身中文叠字)技术最不确定,与建1(3套图)合并放"第三批·需新建/重构"文件细化,避免和无歧义的纯bug混在一起。
|
||||
196
plans/修改处理方案-第三批.md
Normal file
196
plans/修改处理方案-第三批.md
Normal file
@@ -0,0 +1,196 @@
|
||||
# Clover 修改处理方案 · 第三批(❌ 需新建/重构)+ 修3叠字
|
||||
|
||||
> 这批是新建模块或重构,技术不确定性高、且多数需北哥给业务定义。
|
||||
> 不像第一二批能直接给 before/after,这里给:现状/改造思路/影响文件/风险/待定义点。
|
||||
|
||||
---
|
||||
|
||||
## 修3 · 瓶身中文小字乱码(叠字兜底)【L·技术最不确定】
|
||||
|
||||
**根因**:gpt-image-2 画中文小字会糊/乱码(记忆 clover-image-gen-mixed-text-rendering 已记)。
|
||||
现状 storyboard 把所有文字(overlay_text)都塞进prompt让模型画(image_gen.py:140附近)。
|
||||
|
||||
**改造思路**(模型出底图 + 代码叠字):
|
||||
1. storyboard 区分"模型画的"vs"代码叠的":大标题模型画(已清晰),瓶身小字/品牌词/卖点改代码叠。
|
||||
2. 新建 `image_text_overlay.py`:PIL 加载中文字体(思源黑体开源),按坐标叠字到底图。
|
||||
3. image_gen 生图后、后处理前,调叠字。
|
||||
4. prompt 负向约束模型"不要在瓶身画文字"。
|
||||
|
||||
**影响文件**:新增 `image_text_overlay.py`、`storyboard.py`(标记哪些字代码叠)、`image_gen.py`(接叠字)、字体资源(assets/fonts/)。
|
||||
**风险(高)**:①叠字坐标/字号要按每张构图调,模型出图位置不固定→坐标难定 ②哪些字叠/哪些画的边界要试 ③字体版权(用SIL开源思源) ④可能要调好几轮才自然。
|
||||
**待定义点**:这期做不做?我的建议——**先验证模型把大标题画清楚(已能),瓶身小字这种高不确定项放二期**,一期先用"少画字、关键字代码叠品牌词"最小版本试。
|
||||
**最小版本(降risk)**:只代码叠"品牌词"一处(位置固定在底部),不碰瓶身小字。工作量降到M。
|
||||
|
||||
---
|
||||
|
||||
## 建1 · 生图≥3套【L】
|
||||
|
||||
**根因**:`storyboard.py:119 plan_image_set` 只产1套storyboard,`image_gen.py:156 generate_storyboard_images` 只跑1套,返回扁平list。无"套"概念。
|
||||
|
||||
**现状结构**:
|
||||
```
|
||||
plan_image_set → {storyboard: [6张item]} # 1套
|
||||
generate_storyboard_images → gather 6张 → [6个结果] # 扁平
|
||||
pipeline_io → 存6张 ImageCandidate
|
||||
```
|
||||
|
||||
**改造思路**:外层套循环。
|
||||
```
|
||||
for set_idx in range(3): # 3套
|
||||
plan = plan_image_set(..., variant=set_idx) # 套间差异
|
||||
套结果 = gather(...)
|
||||
返回 [[套1的6张],[套2的6张],[套3的6张]]
|
||||
ImageCandidate 加 set_no 字段;前端按套分组展示选择
|
||||
```
|
||||
|
||||
**影响文件**:`storyboard.py`(plan加variant参数做差异)、`image_gen.py`(外层循环)、`pipeline_io.py`(存set_no)、`models/task.py`(ImageCandidate加set_no列+迁移)、前端图片选择页(按套展示)。
|
||||
**风险**:①生图成本×3、apiports限流(记忆:限并发2)→3套18张要控并发别打爆 ②"套间差异"是什么没定 ③前端展示改动较大。
|
||||
**待定义点(必须北哥/你定)**:
|
||||
- 3套的差异维度?候选:a)不同文案角度各出一套 b)同角度不同视觉风格 c)不同封面方案
|
||||
- 套数固定3还是用户可选1/3/5?
|
||||
- 是否每套都6张,还是套数×张数用户配?
|
||||
|
||||
---
|
||||
|
||||
## 建2 · 产品图视觉分析 visualIdentity【M】
|
||||
|
||||
**根因**:banana 有(上传产品图→提主色/字体/风格),Clover 的 `build_visual_system`(storyboard.py:127)只用了文案锚点,没做产品图视觉提取。
|
||||
|
||||
**改造思路**:产品图上传后(或生图前)调多模态分析→提主色/包装风格→存产品档案→生图prompt注入"保持与参考图一致的主色/风格"。
|
||||
|
||||
**影响文件**:新增 `visual_identity.py`、products上传接口接入分析、product表加 visual_json 列+迁移、storyboard注入。
|
||||
**风险**:多模态调用成本+延迟;分析准确度。
|
||||
**待定义点**:一期必要还是二期?我建议二期(现已强制带产品参考图给 /images/edits,视觉一致性已有基本保证,视觉提取是锦上添花)。
|
||||
|
||||
---
|
||||
|
||||
## 建3 · 标杆 AI 出8特征【L·需北哥定义】
|
||||
|
||||
**根因**:`benchmarks.py` 纯CRUD,BenchmarkCreate 只 screenshot_url/highlights/link_url 三字段,零AI分析。
|
||||
|
||||
**改造思路**:录标杆(截图/文本)→AI分析出8个特征维度→存库→生成时可参考。
|
||||
|
||||
**影响文件**:`api/v1/benchmarks.py`、新增标杆分析service、BenchmarkNote加 features_json 列+迁移、前端标杆展示。
|
||||
**风险**:与建4(裂变)强耦合——8特征是裂变的输入。
|
||||
**待定义点(必须北哥给)**:8特征具体是哪8个?(如:钩子类型/痛点/人设/结构/卖点呈现/情绪/视觉/标题公式?)北哥不给定义,做不了。
|
||||
|
||||
---
|
||||
|
||||
## 建4 · 爆款裂变全套【XL·最大块·需北哥给完整流程】
|
||||
|
||||
**根因**:全栈零代码,整块缺失。
|
||||
|
||||
**完整流程(待北哥确认)**:选标杆→选参考度档位(高/中/低)→选裂变维度→基于标杆8特征生成变体→裂变后评分。
|
||||
|
||||
**影响文件(大量新增)**:后端 裂变service+router、裂变记录表+迁移、前端裂变页(选标杆/档位/维度/看结果)。强依赖建3的8特征。
|
||||
**风险**:**这是独立新功能,不是修补**。工作量远超其他项。依赖建3。
|
||||
**待定义点(必须北哥给)**:
|
||||
- 完整裂变流程定义
|
||||
- "参考度档位"高/中/低分别意味着多大改动?
|
||||
- 裂变维度有哪些可选?
|
||||
- 裂变后评分用现五维还是另立标准?
|
||||
**建议**:**单独立项**,与bug修复彻底分开。北哥不给流程定义无法开工。
|
||||
|
||||
---
|
||||
|
||||
## 建5 · 去水印强制3:4比例【S】
|
||||
|
||||
**根因**:`image_postprocessor.py process_image` 只重编码+重采样,无比例校验/裁切。
|
||||
|
||||
**现状代码**(image_postprocessor.py:41-49):
|
||||
```python
|
||||
img = Image.open(io.BytesIO(image_bytes)).convert("RGB")
|
||||
original_size = img.size
|
||||
if resample_strength >= 1:
|
||||
w, h = original_size
|
||||
small_w, small_h = int(w * 0.98), int(h * 0.98)
|
||||
img = img.resize((small_w, small_h), Image.LANCZOS)
|
||||
img = img.resize(original_size, Image.LANCZOS)
|
||||
```
|
||||
|
||||
**改后**:开头加3:4校验+居中裁切。
|
||||
```python
|
||||
img = Image.open(io.BytesIO(image_bytes)).convert("RGB")
|
||||
# 强制3:4(1080×1440):偏差超阈值则居中裁切
|
||||
w, h = img.size
|
||||
target_ratio = 3 / 4
|
||||
cur_ratio = w / h
|
||||
if abs(cur_ratio - target_ratio) > 0.02:
|
||||
if cur_ratio > target_ratio: # 太宽→裁宽
|
||||
new_w = int(h * target_ratio)
|
||||
left = (w - new_w) // 2
|
||||
img = img.crop((left, 0, left + new_w, h))
|
||||
else: # 太高→裁高
|
||||
new_h = int(w / target_ratio)
|
||||
top = (h - new_h) // 2
|
||||
img = img.crop((0, top, w, top + new_h))
|
||||
original_size = img.size # 裁后尺寸
|
||||
```
|
||||
|
||||
**影响文件**:`backend/app/services/ai_engine/image_postprocessor.py`(约12行)。
|
||||
**风险**:居中裁切可能切到边缘内容;gpt-image-2 本就按1080×1440出图,多数已是3:4,裁切是兜底保险。
|
||||
**验收**:故意喂非3:4图→输出严格3:4。
|
||||
|
||||
---
|
||||
|
||||
## 建6 · 客户输入物整体导出【M】
|
||||
|
||||
**根因**:只有产出物打包(package_exporter),无产品/标杆等输入物导出。数据归属红线:客户原始数据可导出。
|
||||
|
||||
**改造思路**:加 `GET /products/export`、`GET /benchmarks/export`,导出该workspace全部输入物为zip(含json+上传的图)。
|
||||
**影响文件**:新增导出router+service。
|
||||
**风险**:导出格式(json/csv/zip)、是否含上传的图要定。
|
||||
**待定义点**:格式?一期必要还是二期?建议二期(飞轮启动+北哥测试期客户数据导出诉求不急)。
|
||||
|
||||
---
|
||||
|
||||
## 建7 · 图片 lightbox 放大【S】
|
||||
|
||||
**根因**:全局无放大逻辑,img直接渲染,看不清细节。
|
||||
**改造思路**:图片卡加点击放大遮罩(轻量自写或 yet-another-react-lightbox)。
|
||||
**影响文件**:前端图片相关组件(images页/confirm页)+新增Lightbox组件。
|
||||
**风险**:无。
|
||||
**验收**:点图弹出大图遮罩。
|
||||
**建议**:直接做,体验刚需且简单。
|
||||
|
||||
---
|
||||
|
||||
## 建8 · 套版预览(封面+内页拼笔记)【M】
|
||||
|
||||
**根因**:confirm页只网格分开展示图(ConfirmPreviewImages),没拼成"一条小红书笔记长相"。
|
||||
**改造思路**:confirm页加"笔记预览"视图:封面图+内页轮播+文案标题正文,按小红书样式排。
|
||||
**影响文件**:前端confirm页+新增笔记预览组件。
|
||||
**风险**:还原小红书样式要调。
|
||||
**待定义点**:一期必要还是二期?建议二期(confirm已能逐个看图+文案,拼版是体验增强非阻断)。
|
||||
|
||||
---
|
||||
|
||||
## 建9 · 任务级并发上限【M】
|
||||
|
||||
**根因**:只有 celery worker_prefetch_multiplier=1(worker层),无用户/任务级并发限制。用户狂点开任务可能堆爆。
|
||||
**改造思路**:任务创建时查该用户在跑任务数(DB status查或Redis计数),超N则拒绝/排队。
|
||||
**影响文件**:任务创建router、可能加Redis计数。
|
||||
**风险**:限制策略要定。
|
||||
**待定义点**:每用户允许几个并发任务(建议2-3)?超限拒绝还是排队?
|
||||
|
||||
---
|
||||
|
||||
## 第三批小结
|
||||
|
||||
| 项 | 性质 | 建议期次 | 阻塞点 |
|
||||
|---|---|---|---|
|
||||
| 修3叠字 | 重构·高不确定 | 一期最小版(只叠品牌词)/二期完整 | 技术验证 |
|
||||
| 建1 3套图 | 重构 | 看北哥要不要 | 套间差异定义 |
|
||||
| 建2 视觉分析 | 新建 | 二期 | — |
|
||||
| 建3 标杆8特征 | 新建 | 看北哥 | **8特征定义** |
|
||||
| 建4 爆款裂变 | 新建·XL | **单独立项** | **完整流程定义** |
|
||||
| 建5 强制3:4 | 改造·小 | 一期可做 | — |
|
||||
| 建6 输入导出 | 新建 | 二期 | 格式 |
|
||||
| 建7 lightbox | 新建·小 | 一期可做 | — |
|
||||
| 建8 套版预览 | 新建 | 二期 | — |
|
||||
| 建9 并发上限 | 改造 | 一期可做 | 并发数 |
|
||||
|
||||
**无歧义可直接做**:建5(3:4)、建7(lightbox)、建9(并发,定个数即可)。
|
||||
**需北哥给定义才能动**:建3(8特征)、建4(裂变流程)。
|
||||
**建议二期**:建2、建6、建8。
|
||||
**技术验证后再定**:修3叠字。
|
||||
148
plans/修改处理方案-第二批.md
Normal file
148
plans/修改处理方案-第二批.md
Normal file
@@ -0,0 +1,148 @@
|
||||
# Clover 修改处理方案 · 第二批(🟡 做了一半)
|
||||
|
||||
> 现状代码均已逐行读核。每项含现状/改后/文件/风险/验收。
|
||||
|
||||
---
|
||||
|
||||
## 修6 · ai_call_logs 记录不全
|
||||
|
||||
**根因**:
|
||||
- `pipeline_io.py:78-91` 只在文案后写1条,且 `prompt_tokens/completion_tokens` 从不填(httpx响应没解析usage)。
|
||||
- `run_image_generation`(L122-216) 整个函数**无任何 AiCallLog 写入**——生图调用零留痕。
|
||||
|
||||
**现状代码**(pipeline_io.py:78-91,文案日志):
|
||||
```python
|
||||
log = AiCallLog(
|
||||
workspace_id=workspace_id, user_id=task.operator_id, key_id=key_id,
|
||||
task_id=task.id, provider="apiports", model=clients._model,
|
||||
call_type="text", success=llm_success, latency_ms=latency_ms,
|
||||
) # 缺 prompt_tokens / completion_tokens
|
||||
```
|
||||
|
||||
**改后**:分两处。
|
||||
**① 文案日志补token**(依赖_call_llm返回usage,需text_variants.py一并改透传usage,工作量上升)。一期可降级:token填None保持现状,但**至少把生图日志补上**。
|
||||
|
||||
**② 生图日志新增**(run_image_generation 末尾,db.commit前):
|
||||
```python
|
||||
# 生图调用留痕(与文案对称)
|
||||
try:
|
||||
img_log = AiCallLog(
|
||||
workspace_id=workspace_id, user_id=task.operator_id, key_id=None,
|
||||
task_id=task.id, provider=getattr(clients, "_image_provider", "apiports"),
|
||||
model="gpt-image-2", call_type="image",
|
||||
success=any(not r.get("error") for r in image_results),
|
||||
latency_ms=image_latency_ms, # 需在gather前后记时间
|
||||
)
|
||||
db.add(img_log)
|
||||
except Exception as e:
|
||||
logger.warning("生图 ai_call_logs 写入失败(非阻断): %s", e)
|
||||
```
|
||||
gather 前加 `t0 = time.monotonic()`,后算 `image_latency_ms`。
|
||||
|
||||
**改动文件**:`pipeline_io.py`(生图日志,约12行);token数透传需 text_variants.py + 调整_call_llm返回(约20行,建议二期)。
|
||||
**风险**:飞轮一期是否强依赖token数?若不依赖,token降级、只补生图成败/耗时/provider即可。
|
||||
**验收**:跑一次任务,ai_call_logs 表里文案+生图各一条,生图条 provider/model/success/latency 齐。
|
||||
**待拍板**:token数这期补不补?建议先补生图留痕,token二期。
|
||||
|
||||
---
|
||||
|
||||
## 修7 · 文案 Gemini 兜底层未接
|
||||
|
||||
**根因**:现链路 LLM(Claude)→本地模板 两层(text_variants.py:89-91)。`gemini_factory.gemini_generate` 只服务生图,文案无Gemini通道。
|
||||
|
||||
**现状代码**(text_variants.py:89-91):
|
||||
```python
|
||||
copies: list[dict] = await _generate_in_batches(llm_client, product, count, extra)
|
||||
if not copies:
|
||||
copies = list(build_local_drafts(product, count)) # 直接掉本地兜底
|
||||
```
|
||||
|
||||
**改后**:Claude失败后、本地兜底前插Gemini文案。需 gemini_factory 加 chat 方法(现只有图)。
|
||||
```python
|
||||
copies = await _generate_in_batches(llm_client, product, count, extra)
|
||||
if not copies:
|
||||
logger.warning("Claude文案失败,尝试Gemini兜底")
|
||||
try:
|
||||
copies = await _generate_via_gemini(product, count, extra) # 新函数
|
||||
except Exception as e:
|
||||
logger.error("Gemini文案兜底也失败: %s", e)
|
||||
if not copies:
|
||||
copies = list(build_local_drafts(product, count)) # 最终本地兜底
|
||||
```
|
||||
新增 `_generate_via_gemini`:调 gemini chat → 复用 parse_json_array。
|
||||
|
||||
**改动文件**:`text_variants.py`(约15行)、`gemini_factory.py`(加chat_complete方法,约15行)。
|
||||
**风险**:①Gemini文案质量/JSON格式遵守度要验,可能不如Claude ②Gemini key 是否各operator都配了?没配则这层形同虚设。
|
||||
**验收**:停Claude(模拟503),确认走Gemini出文案而非直接本地模板。
|
||||
**待拍板**:一期是否需要三层?我建议——若operator普遍没配Gemini key,先不接,留两层(Claude+本地)即可。
|
||||
|
||||
---
|
||||
|
||||
## 修8 · 上传只查 content-type 无 magic number
|
||||
|
||||
**根因**:`products.py:174` 只查 `file.content_type`(HTTP header,可伪造)。无字节头校验。
|
||||
|
||||
**现状代码**(api/v1/products.py:174-179):
|
||||
```python
|
||||
if file.content_type not in _ALLOWED_CONTENT_TYPES:
|
||||
raise_business(f"不支持的文件类型 {file.content_type}...")
|
||||
data = await file.read()
|
||||
if len(data) > _MAX_SIZE_BYTES:
|
||||
raise_business("文件超过 10 MB 限制")
|
||||
```
|
||||
|
||||
**改后**:读完data后加真实字节头校验。
|
||||
```python
|
||||
data = await file.read()
|
||||
if len(data) > _MAX_SIZE_BYTES:
|
||||
raise_business("文件超过 10 MB 限制")
|
||||
# magic number 校验真实文件类型(防伪造content-type)
|
||||
if not (data[:3] == b"\xff\xd8\xff" # JPEG
|
||||
or data[:8] == b"\x89PNG\r\n\x1a\n" # PNG
|
||||
or (data[:4] == b"RIFF" and data[8:12] == b"WEBP")): # WebP
|
||||
raise_business("文件内容不是有效的 JPEG/PNG/WebP 图片")
|
||||
```
|
||||
|
||||
**改动文件**:`backend/app/api/v1/products.py`(约6行)。
|
||||
**风险**:无。
|
||||
**验收**:把 .exe 改名 .jpg + 伪造 content-type 上传 → 被拒。
|
||||
|
||||
---
|
||||
|
||||
## 修9 · 文案优化轮默认关(确认题,非bug)
|
||||
|
||||
**现状**(text_variants.py:107-110):`TEXT_OPTIMIZE_ENABLED=false` 默认关。
|
||||
注释写明:apiports 60s网关下,优化轮的失败要白等60s才503,拖慢出文案+100s+。
|
||||
|
||||
**这是有意为之的工程权衡,不是bug。** 两个选择:
|
||||
- **A(建议)保持关**:等北哥prompt方案到位再开,架构已留位(改环境变量即开)。
|
||||
- **B 改造绕60s**:优化轮也走分批小请求(≤4条/批),降低单请求触发60s概率。工作量M。
|
||||
|
||||
**改动文件**:A=0改动;B=text_variants.py优化轮分批(约20行)。
|
||||
**待拍板**:A还是B?我建议A。
|
||||
|
||||
---
|
||||
|
||||
## 修10 · 无 key 不置灰引导
|
||||
|
||||
**根因**:配置页有"暂无Key请录入"提示(ApiKeysTab.tsx:92),但 `/tasks/new` 开任务页不检测key、不置灰入口。用户没录key也能点开始→任务必然失败。
|
||||
|
||||
**现状**:`NewTaskForm.tsx:38,112-115` 只处理"产品入镜但无参考图"的置灰(blockedByNoImage),无key检测。
|
||||
|
||||
**改后**:开任务页加载时查当前用户是否有key,无则置灰"开始"+引导。
|
||||
```tsx
|
||||
// NewTaskForm 加载时
|
||||
const { data: keys } = useApiKeys(); // 复用配置页的key查询
|
||||
const noKey = !keys || keys.length === 0;
|
||||
const blocked = blockedByNoImage || noKey;
|
||||
// 开始按钮 disabled={blocked}
|
||||
{noKey && <Banner>请先到「配置中心」录入 API Key 才能开任务 <Link href="/config">去录入</Link></Banner>}
|
||||
```
|
||||
|
||||
**改动文件**:`frontend/src/components/tasks/NewTaskForm.tsx`(约10行)、可能复用key查询hook。
|
||||
**风险**:无。
|
||||
**验收**:清空key→开任务页"开始"置灰+引导文案+跳配置链接。
|
||||
|
||||
---
|
||||
|
||||
> 第二批小结:修8(magic number)无歧义可直接做;修6(生图日志)建议做、token降级;修7/修9需你拍板(多半可降级/保持现状);修10纯前端体验补强。
|
||||
276
plans/北哥验收反馈与功能差距盘点.md
Normal file
276
plans/北哥验收反馈与功能差距盘点.md
Normal file
@@ -0,0 +1,276 @@
|
||||
# 北哥/倩倩姐验收反馈 + 功能差距盘点
|
||||
|
||||
> 记录时间:2026-06-12
|
||||
> 触发:倩倩姐用 qianqian 账号实跑前端,发现大量问题。要求:①先记录全部问题 ②原始需求 vs 现状做完整对比,代码层验证,交叉2-3轮,列出未实现项。
|
||||
|
||||
---
|
||||
|
||||
## 一、倩倩姐本次实跑提出的问题(原话拆解,一条不漏)
|
||||
|
||||
### A. 产品管理
|
||||
- A1. 选品/建任务时**不能填写其他产品**,库里只有一个"素颜霜预置样本"。
|
||||
- A2. **没有产品上传入口**——产品参考图没地方上传。
|
||||
|
||||
### B. 文案(选择文案页,截图1)
|
||||
- B1. 前两个文案卡片(83分、66分)的**评分明细进度条全是0**(标题0/情绪0/买点0/关键词0/合规0),但总分却有83/66——评分明细丢失或没渲染。后三个(75/59/76)有明细。
|
||||
- B2. **80分以下的文案为什么还放出来**了(66/59/76 都<80)——评分门槛/过滤逻辑存疑(需确认原始需求是过滤还是全展示)。
|
||||
- B3. **文案到底用的什么文案方法论**——质疑文案套路(佛系人设 vs 源头小红书7步SOP,此前 deferred 未决)。
|
||||
|
||||
### C. 图片(选择图片页,截图2/3/4)
|
||||
- C1. **产品不一致**——生成图里的产品包装和参考图对不上(参考图是64字节占位图导致)。
|
||||
- C2. **图片没办法自动缩放**——窗口变化时图片不自适应。
|
||||
- C3. **第一张(hook)字体是错的**——大标题"5符种岜门/熿韵遾愳/扶妢/絹琝诙妢"全是乱码错字(gpt-image-2 中文渲染翻车,连大标题都错)。
|
||||
- C4. **只生成1套6张图,应该最少3套不同的供选择**。
|
||||
- C5. **没有一张图能放大**——点击图片无法查看大图。
|
||||
- C6. **窗口最小化后内容被截断**(响应式布局缺失)。
|
||||
- C7. **生成的更像电商详情图,跟小红书压根不匹配**——风格定位错误。
|
||||
|
||||
### D. 路由/页面
|
||||
- D1. **任务列表等页面 404**(截图4:/tasks/40/images 切到任务列表报 404 This page could not be found)。
|
||||
|
||||
### E. 功能缺失
|
||||
- E1. **没有看到"爆款裂变"功能**——飞轮/裂变板块缺失或没入口。
|
||||
|
||||
### F. 流程/进度
|
||||
- F1. 文案页"前面两个进度条没展示"(同 B1,进度/评分条渲染问题)。
|
||||
|
||||
---
|
||||
|
||||
## 二、原始确认的功能板块(已从 PRD/验收清单/API契约/通关路线图/北哥回填提取)
|
||||
|
||||
> 来源:PRD-0总纲 §5 全流程5环节 / PRD-前端 / PRD-后端 / 验收清单1A+1B / API契约 / 北哥回填解读
|
||||
|
||||
### 一期(1A 生产链)必做的5大环节(PRD-0 §5)
|
||||
1. **产品配置**(管理员录):卖点/品牌词/违禁词三级/标签/风格调性/可调prompt/**参考图上传**
|
||||
2. **生成文案(双轨)**:轨A一次出N角度 / 轨B导入外部文案;五维评分(标题25/情绪25/买点25/关键词20/合规5),**总分<90不进候选池**
|
||||
3. **生成图(分镜)**:gpt-image-2主+edits带产品参考图+禁纯文生图;storyboard N张(1-8)各担角色;6图对齐北哥标准序;provider主备+重试退避
|
||||
4. **爆款裂变(1爆款→N笔记包)**:每包完整(标题+正文+标签+分镜);卖点/标签/人群锁定;参考度低30/中/高85可调 ← **一期范围**
|
||||
5. **存档打包交付**:达人素材包(按笔记分文件夹+01/02命名+文案.txt+发布清单+合规说明);去水印(重编码去C2PA+削像素水印)
|
||||
|
||||
### 飞轮四点(1B,基石E)
|
||||
- events写入(选文案+3/选图+3/通过+5/打回-3/重生成-1) / aggregator返片段 / 下次prompt含片段 / UI显"本次已注入"
|
||||
|
||||
### 前端页面(PRD-前端)
|
||||
- 登录 / 工作台 / 开新任务(选品+主题+数量+双轨入口+右侧配置预览3参考图+本次已注入横幅) / 选择文案(N卡+五维分条) / 选择图片(N批+SSE谁好谁先冒+套版预览) / 确认预览 / 组长审核台(/review) / 历史归档(任务列表+导出包) / 配置台(/config, 产品CRUD+参考图上传+标杆+成员+key只录不显余额+违禁词CRUD)
|
||||
- 角色守卫:/review限组长+管理员, /config限管理员
|
||||
- SSE:先换60s短票再建连, 禁token直传; 5次重连退避; event_seq去重
|
||||
|
||||
### 关键细节点(逐条可核)
|
||||
- D-1 产品参考图上传入口(配置台屏1明确要)
|
||||
- D-2 文案五维评分展示+总分
|
||||
- D-3 文案90分门槛后端过滤(<90不进池)
|
||||
- D-4 图片放大: **PRD未明确要求**(但属基础体验)
|
||||
- D-5 图片响应式缩放: **PRD未明确**(PC最小1280px)
|
||||
- D-6 一次生成: 1套N张(N=image_count) ←PRD设计; **倩倩姐要3套选=超出原PRD,待确认**
|
||||
- D-7 爆款裂变页: 一期范围, 当前**疑似缺失**
|
||||
- D-8 任务列表页: /history 应有
|
||||
- D-9 小红书风格(非电商): 无独立定义, 靠 style_tone 字段 + prompt
|
||||
- D-10 SSE实时进度(谁好谁先冒/单批失败重试/能离开)
|
||||
- D-11 第1张图中文乱码: gpt-image-2渲染硬伤(记忆已记, 未解)
|
||||
|
||||
### 【补全】上一轮盘点遗漏的原始需求(来自北哥回填/洞1-7/扒包萃取/豆包prompt)
|
||||
|
||||
> 倩倩姐指出"讨论方案时远比这多"。重新通读 北哥回填解读 / test洞1-7 / 官网V1萃取 / 产品包扒包 / banana扒包 后补全,这些是之前漏掉的硬需求:
|
||||
|
||||
**北哥文案方法论(豆包prompt原话,最高优先级)**
|
||||
- N-文1 佛系反推销人设"东西放这了买不买跟我没关系"
|
||||
- N-文2 随机变量池ABC:身份场景5×起因情绪3×小缺点3,每条随机抽不撞(反同质化命脉)
|
||||
- N-文3 5步框架:Hook暴击低价→痛点共鸣→救星登场→卖点罗列(带✅小标题)→逼单(**不是旧7步SOP**)
|
||||
- N-文4 正文四段:痛点→实测→种草→引导;350-400字;3-5段空行
|
||||
- N-文5 70%场景 30%产品 比例
|
||||
- N-文6 标题5公式:肤质/价格/功效/夸张/标题党,每条不同类型
|
||||
- N-文7 反AI味负向词禁入正文(神器/福音/遮羞布/日常维稳/精简底妆/不仅而且/焕发/守护)——是prompt负向约束**不是事后auto_fix替换**
|
||||
- N-文8 品牌词必植入文案正文(北哥"种品牌词引导天猫搜"核心诉求)
|
||||
|
||||
**北哥生图规则(豆包prompt+回填原话)**
|
||||
- N-图1 6张固定套路序:①封面痛点大字②单品特写+品牌词③成分④质地⑤上脸对比⑥促单
|
||||
- N-图2 品牌词出现在第2/6张,转化句在第6张,对比在第5张
|
||||
- N-图3 好图标准:高清+构图居中+字粗大+图文匹配
|
||||
- N-图4 效果对比图AI优先(实拍备),静物图实拍优先(AI备)
|
||||
- N-图5 排版并入生图(AI直接把字排图上出成品),不做独立排版环
|
||||
- N-图6 成组视觉统一(buildVisualSystem):一套N张共享主色/字体/贴纸
|
||||
- N-图7 素材路由:产品图=商品锚点不可改 / 实拍图=肤感场景 / 爆款图=只学版式不用内容
|
||||
|
||||
**标杆/爆款分析(北哥13环+扒包split.js)**
|
||||
- N-标1 标杆分析出**8特征**(SSE analyze_done带features:[8特征])——提取标题句式/开篇痛点/评论刚需
|
||||
- N-标2 爆款参考度三档:低30(只学结构)/中(学节奏局部替换)/高85(学标题节奏换表达防抄袭)
|
||||
- N-标3 裂变维度标注:换了哪个维度/目标人群/场景/痛点点位
|
||||
- N-标4 裂变必须改全文+重拍图,不变卖点/标签/人群(N-19北哥死命令)
|
||||
- N-标5 裂变笔记综合评分(scoreCompleteNote=文案五维+图文完整度15分)
|
||||
|
||||
**违禁词三级(洞5拍板)**
|
||||
- N-违1 三级:🟢auto_fix视觉类自动改(前后对比→质地说明) /🟡soft_warn功效词标黄给建议(美白→提亮?) /🔴hard_block高危词必改(医用/药妆)
|
||||
- N-违2 词库可配置+可批量导入(北哥词远超预置5条)+北哥可调分级
|
||||
- N-违3 "遮羞布"等AI味词要单独分类入库(北哥最大痛点)
|
||||
- N-违4 双保险:生成时prompt规避 + 发布前检查两道关
|
||||
|
||||
**去水印(洞3拍板)**
|
||||
- N-水1 出图后**必经工序**:重编码去C2PA元数据 + 转JPG/轻重采样削SynthID像素水印 + 压缩
|
||||
- N-水2 诚实边界:C2PA 100%可去,像素水印只能削弱
|
||||
- N-水3 去水印严守3:4比例不变形
|
||||
|
||||
**交付/数据归属(洞6+洞7拍板)**
|
||||
- N-交1 素材包结构:发布清单.txt(自解释发几条/配图序/文案/标签) + 笔记N_角色/文件夹(01/02/03命名) + 文案.txt(标题+正文+标签) + 合规说明.txt
|
||||
- N-交2 数据归属分层:客户输入物+产出物归客户可导出 / 飞轮偏好归平台不随客户走
|
||||
- N-交3 **数据可导出一期就做**(洞7),全表加workspace_id隔离
|
||||
- N-交4 下载必须fetch+blob(window.open无法带token会401)
|
||||
|
||||
**标杆采集(洞1拍板)**
|
||||
- N-采1 一期对外标配=截图上传+手填亮点(零平台风险),系统不碰小红书服务器
|
||||
- N-采2 登录态采集插件=二期北哥内部自用opt-in,不进对外标配
|
||||
|
||||
**工程底座(架构方案+banana扒包)**
|
||||
- N-工1 ai_call_logs:每次AI调用记谁/用多少token,失败归因到个人key(**一期必做**)
|
||||
- N-工2 健康检查 GET /health
|
||||
- N-工3 同用户并发生成任务上限2(可配)
|
||||
- N-工4 上传安全:magic number校验+扩展名白名单+路径穿越防护
|
||||
- N-工5 三层兜底文案:Claude→Gemini→本地模板(buildLocalDrafts永不空手)
|
||||
- N-工6 去重系统:标题相似度≥0.82判重 / 正文开头签名去重
|
||||
- N-工7 角度槽位机制(每条强制不同角度)做成可迁移数据
|
||||
- N-工8 product.js产品图视觉分析→visualIdentity(主色/字体/包装风格)供生图用
|
||||
|
||||
**前端工程(PRD-前端)**
|
||||
- N-前1 errorCodeMap错误码映射表(9类错误码→文案+处理动作)
|
||||
- N-前2 骨架屏(文案卡/图卡/审核队列loading)
|
||||
- N-前3 无key时按钮置灰+首登强制引导配key页
|
||||
- N-前4 4个Store(authStore/taskStore/generationStore/preferenceStore)
|
||||
- N-前5 token刷新(JWT失效自动刷新,失败跳登录)
|
||||
- N-前6 套版预览(选中图+文案→拼成笔记长相)
|
||||
|
||||
---
|
||||
|
||||
## 三、现状 vs 需求 差距清单(代码层 3 轮交叉验证)
|
||||
|
||||
> 验证方式:4 个 Explore agent 并行扫码(前端/后端接口/生图文案/DB飞轮),关键质疑项倩倩姐亲自复核读码 2 轮。每条附 `文件:行号` 证据。
|
||||
> 图例:✅已实现 / 🟡半实现 / ❌未实现 / 🐛有bug
|
||||
|
||||
### 3.1 倩倩姐质疑项 — 逐条结论
|
||||
|
||||
| 编号 | 问题 | 结论 | 代码证据 | 根因 |
|
||||
|---|---|---|---|---|
|
||||
| A1 | 不能填别的产品 | 🟡 能建产品但入口只在配置台 | products CRUD全在 `api/v1/products.py:64-131`;新建表单只挂 `/config`,`NewTaskForm.tsx:47` 任务页只能选不能建 | 任务页缺"快捷新建产品"按钮(设计取舍,非bug) |
|
||||
| A2 | 没有产品上传入口 | ✅ 入口存在 | 后端 `products.py:150` `POST /products/{id}/upload-image` 写 image_path;前端 `ProductSubComponents.tsx:73` file input | 入口在配置台产品卡内,倩倩姐没找到≈可见性问题 |
|
||||
| B1 | 评分明细进度条全是0 | 🐛 SSE推送时五维占位0靠异步补 | `useSse.ts:83` 推送时填 `{title:0,emotion:0...total:X}`,88-93行再异步GET补全 | SSE只推总分(`useSse.ts:77` score是number),五维详情靠后续接口补,慢/缺字段就长期显示0 |
|
||||
| B2 | 80分以下文案为何放出来 | 🐛 **90分门槛形同虚设** | `text_variants.py:136` 返回含passed=False全部候选;`pipeline_io.py:96-106` 无差别写库无`if not passed:continue` | 门槛只算分标记`passed`,存库时根本不按它过滤。低分全进池 |
|
||||
| B3 | 文案用什么方法论 | ✅ 佛系人设+5步+变量池ABC+反AI味 | `_text_prompt.py:12`(佛系人设)/`:66`(5步框架)/`:19`(变量池ABC)/`:94`(反AI味) | 方法论已落地,是否对北哥胃口=产品决策 |
|
||||
| C1 | 产品不一致 | 🟡 测试时参考图是64字节占位 | `pipeline_io.py:150` 无参考图硬失败逻辑正确;本次是测试数据问题 | 上真实产品图即可解,非代码缺陷 |
|
||||
| C2/C6 | 图片不缩放/窗口截断 | ✅ 响应式CSS已有 | `images/page.tsx:55` `grid-cols-3 xl:grid-cols-5`;`:65` `w-full aspect-square object-cover` | agent判定不会截断;需倩倩姐复现确认是否别处 |
|
||||
| C3 | 第一张字体乱码错字 | 🐛 **纯靠模型画中文字,无叠字兜底** | `image_gen.py:145` prompt只描述文字让模型自画;全`ai_engine/`无PIL叠字 | gpt-image-2中文渲染弱是已知模型局限,缺服务端Pillow叠字方案 |
|
||||
| C4 | 只1套6张,要≥3套 | 🐛 **架构只产1套N张** | `image_gen.py:121-173` 单个storyboard逐张生成返回扁平list;调用链只跑一次 | 无"套"概念,需加外层循环生N套 |
|
||||
| C5 | 图片不能放大 | ❌ 无lightbox | 全局搜lightbox/放大/zoom = 0结果;`images/page.tsx:60` onClick只做选中 | 功能未做 |
|
||||
| C7 | 像电商图不像小红书 | 🟡 风格词有但防御弱 | `constants.py:58` 有"小红书种草风";但仅closer角色禁电商风(`storyboard_templates.py:53`),其他角色无负向词 | 缺强负向约束"禁白底产品图/禁电商详情图" |
|
||||
| D1 | 任务列表404 | 🐛 **导航指向不存在的路由** | `Sidebar.tsx:22-26` `/images`、`/tasks/build`、`/tasks/list` 三个href均无对应page.tsx | 导航错配 |
|
||||
| E | 没看到爆款裂变 | ❌ **全栈零实现** | 前后端+DB+worker全局搜裂变/split/fission = 0业务代码 | PRD一期范围,完全没建 |
|
||||
|
||||
### 3.2 原始需求模块 — 整体实现度
|
||||
|
||||
**后端接口(API契约)**:核心链路基本齐
|
||||
- ✅ 认证/工作区切换、API Key(只显后4位)、产品CRUD+图上传、违禁词三级、SSE一次性ticket、审核台approve/reject、打包下载、飞轮三信号+context — 全部有码
|
||||
- 🐛 90分过滤失效(见B2)
|
||||
- 🟡 轨B导入文案`task_actions.py:76` 只存库**不评分不查违禁词**(worker版`text_variants.py:139`才完整)
|
||||
- ❌ 标杆"出8特征"分析:`BenchmarkNote`只存手填highlights,无AI结构化分析
|
||||
- ❌ 爆款裂变接口
|
||||
|
||||
**生图/文案核心**:
|
||||
- ✅ 6图角色对齐北哥序(`storyboard.py:75`)、provider主备+退避(`image_gen.py:34-117`)、禁纯文生图硬拦(`pipeline_io.py:150`)、去水印(`image_postprocessor.py`)、文案双轨+方法论、五维评分逻辑(`_scoring_dims.py`)
|
||||
- 🐛 生图只1套(C4)、中文叠字乱码(C3)、90分不硬拦(B2)
|
||||
- 🟡 品牌词:注入逻辑在(`storyboard.py:133`)但**products表无brand_keyword列**(`models/product.py:20-54`确认无),运行时永远空,第2/6张品牌词静默失效
|
||||
- 🟡 电商风负向约束弱(C7)
|
||||
|
||||
**数据库**:15张表齐全有迁移(001-007)。唯一缺口:products表缺`brand_keyword`列。eval_score正确留NULL未接假评分。多租户`workspace_id`双层过滤到位。
|
||||
|
||||
**飞轮四点**:✅ 全通——写入(`task_actions.py:49`选文案/`review.py:113`通过/`:139`打回)、聚合(`flywheel_service.py:71`)、注入(`pipeline_steps.py:71`+`pipeline_io.py:69`)、UI已注入事件(`tasks.py:94`)、前端横幅(`FlywheelBanner.tsx`挂3页)。
|
||||
|
||||
**前端页面**:9个核心页在(login/dashboard/tasks.new/text/images/confirm/review/history/config)。缺:`/tasks/list`、`/tasks/build`、`/images`、爆款裂变页。
|
||||
|
||||
### 3.3 必须修的清单(按优先级)
|
||||
|
||||
**P0 阻断验收**
|
||||
1. 🐛 90分门槛过滤 — `pipeline_io.py:96` 加 `if not c.get("passed"): continue`(B2)
|
||||
2. 🐛 导航404 — `Sidebar.tsx:22-26` 删/改三个坏链接(D1)
|
||||
3. 🐛 生图≥3套 — `image_gen.py` 加外层循环 / 新增 image_sets_count(C4)
|
||||
4. 🐛 中文乱码 — `image_postprocessor` 后加 Pillow 中文字体叠标题(C3)
|
||||
|
||||
**P1 核心缺口**
|
||||
5. 🟡 brand_keyword字段 — ORM加列+迁移008+`build_product_dict`映射+DTO(品牌词)
|
||||
6. ❌ 图片放大 lightbox(C5)
|
||||
7. 🟡 电商风负向prompt强化(C7)
|
||||
8. 🐛 五维分条全0 — SSE直接推score对象 / 前端补全兜底(B1)
|
||||
|
||||
**P2 功能立项**
|
||||
9. ❌ 爆款裂变(1爆款→N笔记)— PRD一期范围,需从0设计表+worker+前端页(E)
|
||||
10. ❌ 标杆8特征分析
|
||||
11. 🟡 轨B导入补评分+违禁词检测
|
||||
|
||||
**产品决策待倩倩姐/北哥拍板**
|
||||
- 文案方法论:代码已落地北哥5步框架(非旧7步),是否对北哥胃口需北哥真看(B3)
|
||||
- 3套的"套间差异"策略(不同角度/不同风格/不同封面?)
|
||||
- brand_keyword 录入在产品级还是任务级
|
||||
|
||||
---
|
||||
|
||||
## 四、补全需求的代码层验证(本轮新增,对应第二章【补全】项)
|
||||
|
||||
> 倩倩姐指出上一轮漏了大量讨论过的需求。这一节对补全项逐条给代码结论。**重大发现:北哥文案方法论此前项目文档标记"只落地25-30%"(BUG-14),本轮亲自读 `_text_prompt.py` 全文确认——已全部落地,那条诊断是过时记录。**
|
||||
|
||||
### 4.1 北哥文案方法论 — ✅ 已全部落地(推翻旧诊断)
|
||||
|
||||
亲自读 `_text_prompt.py` 逐行确认:
|
||||
|
||||
| 需求 | 结论 | 证据 |
|
||||
|---|---|---|
|
||||
| N-文1 佛系人设 | ✅ | `_text_prompt.py:12-15` `_PERSONA`原话"东西放这了…" |
|
||||
| N-文2 变量池ABC | ✅ | `:19-46` 三池+`_pick_combo`每条随机抽;`:140` 按count抽N组 |
|
||||
| N-文3 5步框架 | ✅ | `:67-73` Hook→痛点→救星→卖点✅→逼单,**确是5步非7步** |
|
||||
| N-文4 四段350-400字 | ✅ | `:75-82` 四段结构+`:81`字数+空行 |
|
||||
| N-文5 70/30比例 | ✅ | `:15` "70%场景30%产品绝不颠倒" |
|
||||
| N-文6 标题5公式 | ✅ | `:85-92` 肤质/价格/功效/夸张/标题党各带词例 |
|
||||
| N-文7 反AI味负向词 | ✅ | `:50-54`+`:94-101` 负向词prompt约束(非事后替换,机制正确) |
|
||||
| N-文8 品牌词植入文案 | 🟡 | `:147` 注入逻辑在,但读`product.get("brand_keyword")`,**products表无此列→永远空→静默失效**(同生图品牌词根因) |
|
||||
|
||||
### 4.2 其余补全项 — 代码结论
|
||||
|
||||
| 需求 | 结论 | 证据/缺口 |
|
||||
|---|---|---|
|
||||
| N-标1 标杆出8特征 | ❌ | `BenchmarkNote`只存手填highlights,无AI分析;SSE虽定义analyze_done但无8特征产出 |
|
||||
| N-标2~5 爆款裂变全套 | ❌ | 全栈零实现(参考度/维度/裂变评分都没有) |
|
||||
| N-违1 违禁词三级 | ✅ | `banned_word_checker.py:71-112` 三级auto_fix/soft_warn/hard_block |
|
||||
| N-违2 词库可配置 | ✅ | banned_words表+CRUD接口;批量导入未见独立接口(可逐条POST) |
|
||||
| N-违3 遮羞布入库 | ✅ | `_text_prompt.py:51` 负向词含"遮羞布/日常维稳/精简底妆" |
|
||||
| N-水1 去水印必经工序 | ✅ | `image_postprocessor.py` 重编码去C2PA+转JPG+重采样;`pipeline_io.py:174`已集成 |
|
||||
| N-水3 严守3:4比例 | 🟡 | 后处理按原尺寸重采样,未见强制3:4校验(生图prompt要1080×1440) |
|
||||
| N-交1 素材包结构 | ✅ | `package_exporter.py` 笔记夹+01/02命名+文案.txt+发布清单+合规说明 |
|
||||
| N-交3 数据可导出 | 🟡 | 打包下载=产出物导出有;**输入物(产品/标杆)整体导出未见**专门接口 |
|
||||
| N-交4 下载fetch+blob | ❓ | 需查前端下载实现是否用window.open(待验证) |
|
||||
| N-采1 截图手填标杆 | ✅ | `benchmarks.py` 截图url+highlights手填 |
|
||||
| N-工1 ai_call_logs | ✅ | `models/flywheel.py:63` 表在;`pipeline_io.py:80` 有写入 |
|
||||
| N-工2 GET /health | ❓ | 待确认路由是否注册 |
|
||||
| N-工3 并发上限2 | ❓ | 环境变量IMAGE_CONCURRENCY=2是生图并发,任务级并发限制待确认 |
|
||||
| N-工4 上传安全 | ❓ | products上传是否做magic number校验待查 |
|
||||
| N-工5 三层兜底文案 | 🟡 | 本地兜底`build_local_drafts`在;Claude→Gemini双层兜底待确认是否接 |
|
||||
| N-工6 去重系统 | ✅ | `dedupe_copies`(text_variants.py:136调用) |
|
||||
| N-工7 角度槽位 | ✅ | text_angles产品档案字段+`build_prompt:146`注入 |
|
||||
| N-工8 产品图视觉分析 | ❌ | 无product.js等价的visualIdentity分析(主色/字体提取) |
|
||||
| N-前1 errorCodeMap | ❓ | 前端错误码映射表待查 |
|
||||
| N-前2 骨架屏 | ❓ | 待查 |
|
||||
| N-前3 无key置灰引导 | ❓ | 待查 |
|
||||
| N-前6 套版预览 | 🟡 | confirm页有预览,"封面+内页拼笔记长相"完整度待查 |
|
||||
|
||||
### 4.3 本轮新增的"未实现/待查"清单(补进第三章P级)
|
||||
|
||||
**新确认 ❌ 未实现(之前漏列)**
|
||||
- 标杆8特征分析(N-标1)
|
||||
- 爆款裂变全套(N-标2~5,与E同)
|
||||
- 产品图视觉分析visualIdentity(N-工8)
|
||||
- 输入物整体导出(N-交3部分)
|
||||
|
||||
**🟡 半实现/隐患(之前漏列)**
|
||||
- 文案品牌词植入静默失效(N-文8,与生图品牌词同根因:products表缺brand_keyword列)
|
||||
- 去水印3:4比例无强制校验(N-水3)
|
||||
|
||||
**❓ 需补一轮验证(本轮时间未及,诚实标注未确认)**
|
||||
- 下载是否fetch+blob还是window.open(N-交4,影响401)
|
||||
- GET /health、任务并发上限2、上传magic number校验、Claude→Gemini文案兜底
|
||||
- 前端:errorCodeMap、骨架屏、无key置灰引导、套版预览完整度
|
||||
|
||||
> ❓项我没有当场全部读码确认,不糊弄、如实标注。倩倩姐若要,我下一轮把❓全部读码坐实。
|
||||
53
plans/总核销表.md
Normal file
53
plans/总核销表.md
Normal file
@@ -0,0 +1,53 @@
|
||||
# Clover 总核销表(做完一项勾一项·任务只减不增)
|
||||
|
||||
> 孙总方法论载体:总核销表+分模块核销表,每模块小步快跑+高频check,门禁硬卡。
|
||||
> 勾选规则:□未做 / ◐做了没验 / ✅真端到端验过(附证据) / ⏸️阻塞(等北哥定义)。
|
||||
> **报"✅"必附证据。绝不信第一遍自评,每环必独立交叉核对(孙总:实测AI谎报"都做了"实际20-30%)。**
|
||||
> 事实底座:勘验workflow wf_d4c1dbab-583(2026-06-12,6容器全Up,task41端到端312s成功)。
|
||||
|
||||
## 终点线(倩倩姐2026-06-12拍板·全量)
|
||||
KR1链路连通 + KR2质量达标 + KR3自主可验 + KR4引擎补全(第2环+第11环) 全绿 = 全勾完。
|
||||
|
||||
---
|
||||
|
||||
> 🟢 全部7份模块核销表已细化到90分级(每份含 Ralph修改步骤 + auto/human验收清单 + 已吸收独立交叉验证修正⚠️)。
|
||||
|
||||
## P0 主链修真bug(第5环文案 + 第6环配图)
|
||||
|
||||
| ID | 任务 | 模块核销表 | 细化 | 状态 |
|
||||
|----|------|-----------|------|------|
|
||||
| M0 | 模型探活(opus-4-8/gpt-5.5)→定模型 | — | — | ✅ 2026-06-12探活:opus-4-8/gpt-5.5/sonnet-4-5全HTTP200真可用,/models已列出。按拍板用opus-4-8(文案) |
|
||||
| M1 | 第5环 写文案修bug | plans/核销-第5环-写文案.md | 🟢S1-S9/AC1-6 | □ |
|
||||
| M2 | 第6环 配图修bug+3套 | plans/核销-第6环-配图.md | 🟢S1-S8/A1-A8(含A6b) | ✅ 2026-06-15 task62端到端真跑:3套A/B/C各2张入库,6张全1024×1536,瓶身只印素颜霜不P品牌词,背景干净无杂物,三套真拉开差异(A痛点/B场景/C成分背书),倩倩姐过目认可前后对比图能用。倩倩姐独立核对全绿 |
|
||||
|
||||
## P1 配套+底座(第8环审核 / 第12环归档 / 工程底座)
|
||||
|
||||
| ID | 任务 | 模块核销表 | 细化 | 状态 |
|
||||
|----|------|-----------|------|------|
|
||||
| M3 | 第8环 审核(死链/打回回路) | plans/核销-第8环-审核.md | 🟢S1-S6/A1-A8 | □ |
|
||||
| M4 | 第12环 归档(日期品类筛选/导出) | plans/核销-第12环-归档.md | 🟢S1-S8/A1-A12 | □ |
|
||||
| M5 | 工程底座(5并发/magic/选标杆/置灰/lightbox) | plans/核销-工程底座.md | 🟢S1-S6/A1-A8 | □ |
|
||||
|
||||
## P2 引擎补全(第2环标杆 / 第11环裂变)
|
||||
|
||||
| ID | 任务 | 模块核销表 | 细化 | 状态 |
|
||||
|----|------|-----------|------|------|
|
||||
| M6 | 第2环 标杆8特征分析 | plans/核销-第2环-标杆.md | 🟢S1-S12(S12拆a/b)/A1-A12 | ⏸️等北哥给8维 |
|
||||
| M7 | 第11环 裂变(工作台内) | plans/核销-第11环-裂变.md | 🟢S1-S13(含S10.5)/AC1-12 | ⏸️等北哥给档位 |
|
||||
|
||||
## 🔴 跨模块迁移版本号统一(防三环撞008车)
|
||||
008=brand_keyword(第5环) / 009=features_json+analyze_status(第2环) / 010=fission_tasks表(第11环) / 011=benchmark_ids+source_fission_id(第2环S12+第11环合并)
|
||||
|
||||
## 总验收(最高门禁)
|
||||
|
||||
| ID | 任务 | 状态 |
|
||||
|----|------|------|
|
||||
| Z1 | 一条龙真跑通(录屏为证) | □ |
|
||||
| Z2 | 北哥抽检文案+图认可 | □ |
|
||||
|
||||
---
|
||||
|
||||
## 待北哥给的定义(卡P2,需提前要)
|
||||
1. 标杆8特征具体哪8维
|
||||
2. 裂变参考度档位(高/中/低)各意味多大改动、裂变维度可选哪些
|
||||
3. 90分过滤后不足数量:展示不足 or 补充生成?
|
||||
58
plans/核销-P0-卖点三套来源.md
Normal file
58
plans/核销-P0-卖点三套来源.md
Normal file
@@ -0,0 +1,58 @@
|
||||
# 核销表 · P0 卖点三套来源(通用化根基)
|
||||
|
||||
> 90分级验收(孙总方法论·硬门禁)。倩倩姐2026-06-15拍板:先打 P0。
|
||||
> **标绿门槛=北哥真实数据端到端跑通**(倍分子素颜霜膏霜罐真图 + 文案3.txt真卖点),占位数据自测只能标🟡。
|
||||
> **绝不信AI第一遍自评,必独立交叉核对。**
|
||||
|
||||
## 模块目标(倩倩姐纠偏后的正确方向)
|
||||
|
||||
系统是**通用**的,产品靠**上传才有**,不内置写死任何产品。卖点支持**三套来源**(产品包本来就有,Clover重写时漏了套1、套2字段缺口):
|
||||
- **套1 从产品图片提取**(Gemini Vision 读图→卖点/人群/成分/视觉系统)——❌ Clover完全缺失,本轮补
|
||||
- **套2 用户上传填写**(北哥文案3.txt就是这套真实输入)——⚠️ brand_keyword/人群字段没暴露在API,本轮补
|
||||
- **套3 产品库内置**(fallback模板)——⚠️ 留口即可,本轮不重点做
|
||||
|
||||
## 🔴 已确认的现状(调研+亲读源码,不是猜)
|
||||
|
||||
| 项 | 现状 | 文件:行 |
|
||||
|---|------|---------|
|
||||
| 主流程是否写死素颜霜 | **没有**,文案/生图prompt都从products表动态读 | `_text_prompt.py:126` / `pipeline_steps.py:58` |
|
||||
| brand_keyword 字段 | model有,**API全链路没暴露**(DTO/fmt/create/update都没有) | `product.py:41` vs `products.py:24-128` |
|
||||
| target_audience 人群 | **字段不存在**,但storyboard在读(`product.get("target_audience")`恒空) | `storyboard.py:52` |
|
||||
| 套1图片提取 | **完全没有**,gemini_factory只有生图无vision读图 | `gemini_factory.py` 全文 |
|
||||
| 标题公式 | **已做**(肤质/价格/功效/夸张/标题党5型) | `_text_prompt.py:84-93` |
|
||||
|
||||
## 验收清单(做完一个勾一个,先全列再做)
|
||||
|
||||
> 状态图例:⬜未开始 / 🟡占位数据自测通过 / ✅北哥真实数据端到端通过
|
||||
|
||||
### 套2 字段暴露(改API,model已有brand_keyword无需迁移;人群需迁移)
|
||||
- ✅ **AC1**〔auto〕迁移012:products表加 `target_audience VARCHAR(128)`。**team-lead独立核对容器DB:SHOW COLUMNS确认brand_keyword varchar64/target_audience varchar128,alembic current=012(head)**
|
||||
- ✅ **AC2**〔auto〕ProductCreate DTO 暴露 `brand_keyword` + `target_audience`;POST/PUT 写入;`_fmt_product` 返回。**实证INSERT/UPDATE语句含两列**
|
||||
- ✅ **AC3**〔auto〕`build_product_dict` 透传 `target_audience`(pipeline_steps.py:68)。**实证dict透传人群='黄黑皮想素颜的女生'品牌='倍分子'非空**
|
||||
- ✅ **AC4**〔auto〕建产品→回读三字段都在。**team-lead独立跑通PASS(非采信coder自评)**
|
||||
|
||||
> 🔴 交叉验证发现:coder自评"测试产品已清理无残留"是**假的**,DB残留id=3,team-lead已删。印证「绝不信第一遍自评」。
|
||||
> 附带:已修复product_id=1(真实素颜霜)真实数据:5条真实卖点+人群(黄黑皮想素颜的女生)+品牌(倍分子),为AC9铺路。
|
||||
|
||||
### 套1 图片提取(新增vision,对齐产品包callGeminiVision)
|
||||
- ✅ **AC5**〔auto〕gemini_factory 新增 vision 读图方法(传产品图bytes→返回结构化分析),模型走最强档不降级。**team-lead独立交叉核验:签名正确,model默认claude-opus-4-8无硬编码sonnet,import无报错**
|
||||
- ✅ **AC6**〔auto〕新增 analyze-product 接口:上传产品图 → 返回 {productName,sellingPoints,targetAudience,category,...}。**team-lead独立真跑核验(非采信coder):IMG_9454真图跑通,source=vision,4条sellingPoints非空,结构完整,key链路走用户key,finally有aclose,fallback存在。⚠️更正coder虚标:coder报conf=0.85,实测conf=0.4、productName空——vision诚实承认包装无字未瞎编(prompt'不沿用历史/不默认护肤品'生效,系统通用化方向对)。**
|
||||
- ⬜ **AC7**〔human〕真实膏霜罐图(IMG_9439)提取:跑analyze → 卖点/人群合理(非乱编),倩倩姐认可。
|
||||
|
||||
### 标题公式核对(已做,核对措辞贴北哥)
|
||||
- ⬜ **AC8**〔human〕核对`_TITLE_FORMULA`5型措辞,对齐北哥例"黄皮素颜霜天花板!伪素颜焊在脸上"风格。
|
||||
|
||||
### 端到端真绿门槛(最高优先)
|
||||
- ✅ **AC9**〔human·最小闭环已过〕真实数据全链路真跑通(task61,team-lead亲眼核对非采信状态码):真膏霜罐图(IMG_9454)+真卖点(烟酰胺/水解珍珠/角鲨烷)+真人群(黄黑皮)+品牌(倍分子) → 出1文1图。**逐项核对**:①链路打通登录态→选品→文案→配图→pending_selection ✅ ②产品形态对(白磨砂罐非透明瓶)✅ ③背景无笔记本串味(新加负向约束⑤生效)✅ ④卖点真实(奶油质地/烟酰胺改善暗沉)✅ ⑤文案"倍分子"植入正确+banned_word=pass ✅ ⑥去AI化排版到位(中文标题清晰+emoji+卡点)✅。**认知纠正**:瓶身只印"素颜霜"=正确(瓶身=产品本身忠于参考图,品牌词进文案+图片文字层不P瓶身,倩倩姐2026-06-15拍板)。品牌词进生图特写图(第2/6张)需扩多图才能验,最小闭环只跑hook封面属正常。北哥最终认可待扩3套后整体过目。
|
||||
|
||||
## 待倩倩姐批次确认(攒批集中问,不一条条点)
|
||||
- ✅合格线 80(倩倩姐2026-06-15二次拍板,coder擅改85已驳回改回80,落盘CLAUDE.md)
|
||||
- ✅vision 走 GPT 现有通道最强档,不补 GEMINI_KEY
|
||||
- ✅成分不单列字段,并入 selling_points
|
||||
|
||||
## 🔴 AC9 端到端真绿素材(北哥真实数据,已确认产品形态)
|
||||
真身=**透明玻璃膏霜罐+白色磨砂拉丝盖+金边**,印"倍分子焕颜沁透水润/素颜霜/SKIN CREAM"。**与之前占位透明长瓶+木盖完全不同,task58/60产品形态全错**。
|
||||
- **生图参考图首选**:`客户资料-北哥/素颜霜素材图/原图/IMG_9454.JPG`(单手持单罐,正面文字最清晰,形态完整)
|
||||
- 质地近景实拍:`原图/IMG_9444.JPG`(手臂白色膏体涂抹,对应北哥"质地近景/涂抹过程")
|
||||
- 双罐展示:IMG_9439/9441
|
||||
- 套2真实输入(来自文案3.txt):品牌词=倍分子;产品名=素颜霜;卖点(并入selling_points)=烟酰胺改善暗沉提亮/水解珍珠锁水匀肤/角鲨烷裸妆奶油肌不卡纹/伪素颜不假白/洗面奶可卸;人群target_audience=黄黑皮;合规红线=禁美白祛斑速效,用提亮/自然/伪素颜
|
||||
33
plans/核销-工程底座.md
Normal file
33
plans/核销-工程底座.md
Normal file
@@ -0,0 +1,33 @@
|
||||
# 核销表 · 工程底座
|
||||
|
||||
> 90分级验收(孙总方法论·硬门禁)。已吸收独立交叉验证修正(⚠️)。auto=机器判定,human=目视。
|
||||
> ⚠️审计结论:S1-S6 全部"待执行"(代码现状未改)。行号经核对准确。
|
||||
|
||||
## 模块目标
|
||||
7项底座硬伤:①并发上限5 ②上传 magic number ③选标杆 ④无key置灰 ⑤lightbox ⑥前端不显token余额(红线) ⑦SSE一次性ticket(红线)。
|
||||
|
||||
## Ralph 修改步骤
|
||||
|
||||
| # | 改什么 | 落点 |
|
||||
|---|--------|------|
|
||||
| S1 | MAX_CONCURRENT_TASKS_PER_USER 默认 2→5 | config.py:45 |
|
||||
| S2 | create_generation_task 在 _check_user_has_key 后加并发校验:count(status in pending/running) >= MAX 则 raise_business;顶部 import get_settings | task_service.py:~44 |
|
||||
| S3 | await file.read() 后校验 magic number:JPEG `\xff\xd8\xff`/PNG `\x89PNG\r\n\x1a\n`/WebP `RIFF`+data[8:12]==`WEBP`,都不匹配 raise_business('文件内容与扩展名不符') | products.py:~177 |
|
||||
| S4 | page.tsx 加 loadKeys 调 GET /api/v1/api-keys 存 hasKey;NewTaskForm 按钮 disabled 加 `hasKey===false`,false 时 alert 区显示"未配置Key,去配置-API Key录入" | tasks/new/page.tsx:36 + NewTaskForm.tsx:112 |
|
||||
| S5 | 新建 BenchmarkSelector.tsx(≤80行) 调 GET /products/{id}/benchmarks 多选 checkbox;NewTaskForm 引入放"今天主题"后,传 form.benchmark_ids+onFormChange | 新建 + NewTaskForm.tsx |
|
||||
| S6 | 新建 ImageLightbox.tsx(≤80行) fixed inset-0 z-50 遮罩+居中img,点背景/Esc 关闭;ImageProgressCard 图片加 onClick 触发 | 新建 + ImageProgressCard.tsx |
|
||||
|
||||
## 验收清单(做完一个勾一个)
|
||||
|
||||
- [ ] **A1**〔auto〕并发默认5:`grep MAX_CONCURRENT_TASKS_PER_USER config.py` 含 '= 5'。
|
||||
- [ ] **A2**〔auto〕并发校验在:`grep task_service.py` 出现 status.in_ + MAX_CONCURRENT 引用。(建议补真跑:第6个任务被拒,底-1)
|
||||
- [ ] **A3**〔auto〕magic number 校验:`grep products.py` 出现 ≥2种 magic bytes 字面量。(建议补真跑:.exe改.jpg 上传被拒)
|
||||
- [ ] **A4**〔auto〕无key置灰:`grep tasks/new/page.tsx` 含 /api/v1/api-keys + hasKey;`grep NewTaskForm.tsx` hasKey 在 disabled 条件中。
|
||||
- [ ] **A5**〔auto〕选标杆:`ls BenchmarkSelector.tsx` 存在 + `grep NewTaskForm.tsx` 含 BenchmarkSelector/benchmark_ids。
|
||||
- [ ] **A6**〔human〕lightbox:`ls ImageLightbox.tsx` 存在 + ImageProgressCard 含 onClick;人工点图确认放大弹层、Esc 关闭。
|
||||
- [ ] **A7**〔auto〕前端无token余额(红线):⚠️审计修正——`grep -rn '余额\|用量\|balance\|token_usage' frontend/src` 排除 ApiKeysTab 的引导语"余额和用量请到中转站后台查看"(合规用法),其余必须为空。
|
||||
- [ ] **A8**〔auto〕SSE 用 ticket(红线):`grep sse.ts` 含 'ticket=' 不含 'token=';`grep stream.py` 含 ticket Query;`grep sse_ticket.py` 含 issue_ticket+consume_ticket。
|
||||
|
||||
## 待北哥定义(不阻断代码)
|
||||
- 并发上限 5 是否按客户实跑量调整(改 config.py 一行即可)。
|
||||
- benchmark_ids 选入后 prompt 如何消费标杆 highlights/screenshot(归入第2环 S10/S11)。
|
||||
49
plans/核销-第11环-裂变.md
Normal file
49
plans/核销-第11环-裂变.md
Normal file
@@ -0,0 +1,49 @@
|
||||
# 核销表 · 第11环 裂变
|
||||
|
||||
> 90分级验收(孙总方法论·硬门禁)。已吸收独立交叉验证修正(⚠️)。本环是本轮**补全的缺失引擎环**。
|
||||
|
||||
## 模块目标
|
||||
①1个爆款笔记 → 裂变出 N 套**完整笔记包**(非只换文案,含文案+配图整套) ②裂变在工作台内呈现(不是独立页割裂) ③裂变任务可追溯源(source_fission_id) ④参考度档位(高/中/低)控制与原爆款的相似度。
|
||||
|
||||
## 🔴 迁移版本号统一
|
||||
- **010 = fission_tasks 表(本环)**
|
||||
- 011 = benchmark_ids(第2环) + **source_fission_id(本环,合并进011)**
|
||||
|
||||
## Ralph 修改步骤
|
||||
|
||||
| # | 改什么 | 落点 |
|
||||
|---|--------|------|
|
||||
| S1 | 迁移010:新建 fission_tasks 表(id/source_note/reference_level/fanout_count/status/created_at) | 010_*.py(新) |
|
||||
| S2 | FissionTask ORM 新建 | models/fission_task.py(新) |
|
||||
| S3 | fission_service.py 新建(≤120行):接收源爆款+参考度+扇出数 → 构造 N 个子生成任务 | services/fission_service.py(新) |
|
||||
| S4 | 裂变 prompt 模板:按 reference_level(高=贴原爆款结构/中=保卖点换角度/低=只借选题) 调 prompt | prompts/fission.py(新) |
|
||||
| S5 | POST /fission 触发:写 fission_tasks,扇出 N 个 task(每个完整走文案+配图) | fission.py(新) |
|
||||
| S6 | ⚠️函数名修正:子任务配图调 **image_gen.py:121 generate_storyboard_images**(原清单写 generate_image_set 不存在) | fission_service.py |
|
||||
| **S7** | ⚠️归并(原 S2+S7 source_fission_id 重复):迁移011 task 表加 `source_fission_id INT NULL`+ORM 字段;fission 扇出时回填,标识子任务来源 | 011_*.py + task.py |
|
||||
| S8 | 异步:扇出走 Celery generation 队列(N 套并发受 MAX_CONCURRENT 限) | fission_task.py(新) |
|
||||
| S9 | dto.fission.ts 新建 | dto.fission.ts(新) |
|
||||
| S10 | 工作台内呈现:任务列表区加"裂变"入口(非独立路由),FissionPanel 子组件 | workbench 或 tasks 页内 FissionPanel.tsx(新,≤80行) |
|
||||
| **S10.5** | ⚠️审计补(AC9 遗漏):dashboard/page.tsx 加裂变任务统计/入口卡片 | dashboard/page.tsx |
|
||||
| S11 | 参考度选择 UI:高/中/低 单选 + 扇出数 input(1-N,受 MAX_CONCURRENT) | FissionPanel.tsx |
|
||||
| S12 | 进度回流:N 套子任务状态聚合显示(x/N 完成) | FissionPanel.tsx |
|
||||
| S13 | 源追溯:子任务详情页显"来自裂变 #{fission_id}"角标 | tasks/[id] 页 |
|
||||
|
||||
## 验收清单(做完一个勾一个)
|
||||
|
||||
- [ ] **AC1**〔auto〕迁移010+011:`alembic upgrade head` 成功,fission_tasks 表存在,task 表含 source_fission_id。
|
||||
- [ ] **AC2**〔auto〕触发裂变:POST /fission(源+参考度=中+扇出=3) → 200,返回 fission_id + 3个子 task_id。
|
||||
- [ ] **AC3**〔auto〕完整笔记包:每个子任务跑完后**既有文案又有配图**(非只换文案)——查子 task 既有 TextCandidate 又有 ImageCandidate。
|
||||
- [ ] **AC4**〔auto〕source 回填:`SELECT source_fission_id FROM task WHERE id IN(子)`全==该 fission_id(防链路断)。
|
||||
- [ ] **AC5**〔auto〕参考度生效:高/中/低三档抓 prompt 请求体不同(高含原爆款全文,低只含选题),三档 prompt 互不相同(反向断言)。
|
||||
- [ ] **AC6**〔auto〕配图函数:抓日志/打点确认走 generate_storyboard_images(非报 generate_image_set undefined)。
|
||||
- [ ] **AC7**〔auto〕扇出受并发限:扇出数=10 但 MAX_CONCURRENT=5 → 排队不报错,最终全跑完。
|
||||
- [ ] **AC8**〔human〕工作台内呈现:裂变入口在工作台/任务区**内**(非孤立新路由),点开有参考度+扇出数控件。
|
||||
- [ ] **AC9**〔human〕dashboard 入口:⚠️dashboard 有裂变统计卡片/入口(S10.5),点击进裂变。
|
||||
- [ ] **AC10**〔human〕进度聚合:裂变后 FissionPanel 显 "x/N 完成" 实时更新。
|
||||
- [ ] **AC11**〔human〕源追溯:子任务详情页有"来自裂变 #X"标识,可回查源爆款。
|
||||
- [ ] **AC12**〔human〕参考度肉眼差异:同源裂高/中/低各1套,高与原最像、低差异最大(北哥目视认可)。
|
||||
|
||||
## 待北哥定义(🔴阻断 S4/AC5/AC12)
|
||||
- **参考度档位(高/中/低)的具体含义** + **裂变维度定义**(沿哪些轴裂变:选题/结构/卖点/人群/场景?)。北哥未给前 S4 用占位规则(高=结构+卖点全保/中=保卖点换角度/低=只借选题),AC12 暂以"三档肉眼有梯度差异"验收。
|
||||
- 扇出数上限(受 MAX_CONCURRENT=5 约束,是否允许排队超 5)。
|
||||
- 裂变是否消耗与正常任务相同的额度/并发名额。
|
||||
39
plans/核销-第12环-归档.md
Normal file
39
plans/核销-第12环-归档.md
Normal file
@@ -0,0 +1,39 @@
|
||||
# 核销表 · 第12环 归档
|
||||
|
||||
> 90分级验收(孙总方法论·硬门禁)。已吸收独立交叉验证修正(⚠️)。auto=机器判定,human=目视。
|
||||
|
||||
## 模块目标
|
||||
①history 按日期/品类筛选(现平铺) ②approved 下载交付包 zip 结构完整 ③多套打包(1-3套各独立笔记夹) ④客户输入物(产品/标杆)可导出(数据归属红线)。
|
||||
|
||||
## Ralph 修改步骤
|
||||
|
||||
| # | 改什么 | 落点 |
|
||||
|---|--------|------|
|
||||
| S1 | list_tasks 加 date_from/date_to/product_id query param;fromisoformat 转换,invalid 返回 40001 | tasks.py:137-149 |
|
||||
| S2 | _fmt_task 加 product_name(调用方传入);list_tasks 一次性 `Product.id.in_([...])` 建 id→name dict 避免N+1;⚠️顶部补 `from app.models.product import Product`(当前无此import) | tasks.py:58-64 |
|
||||
| S3 | history/page.tsx 加 dateFrom/dateTo state + 两个 `<input type=date>`(提 DateRangeFilter 子组件防超100行) | history/page.tsx:28-44 + JSX 50-94 |
|
||||
| S4 | HistoryTable 表头/行加"产品"列(显 product_name ?? '-') | history/components.tsx:70-127 |
|
||||
| S5 | TaskListItem 加 `product_name?:string` | dto.tasks.ts:8-16 |
|
||||
| S6 | ⚠️多套打包:查所有 is_selected=True TextCandidate 按 angle_label 分组每组取第一;notes 列表长度=选中套数(改 line 77-85 为 for loop);images_data 循环外查一次,每套传 `list(images_data)` 副本(退化:图共享复制进各套夹) | packaging_task.py:45-47,77-85 |
|
||||
| S7 | 新建 GET /products/export + /benchmarks/export(format=json/csv);require_write_permission;⚠️benchmarks/export 需 Product JOIN 填 product_name(复用 _fmt_benchmark 不够,只有 product_id) | products.py + benchmarks.py |
|
||||
| S8 | 配置页产品 tab + 历史归档页各加"导出数据"按钮,通用 ExportButton(url,filename) 调 getBlob 下载 | history/components.tsx 或 config/ExportTab.tsx |
|
||||
|
||||
## 验收清单(做完一个勾一个)
|
||||
|
||||
- [ ] **A1**〔auto〕日期筛选:传 date_from/date_to → items 全落区间;传 date_from=2099 → 空数组 total=0。⚠️审计补:再验 `date_from=not-a-date` → code=40001(非500)。
|
||||
- [ ] **A2**〔auto〕product_id 筛选:传 product_id=1 → 每条 product_id=1 且 product_name 非空。
|
||||
- [ ] **A3**〔human〕前端产品列:/history 表头有"产品"列,每行显产品名(非数字),与 GET /products/{id}.name 一致。
|
||||
- [ ] **A4**〔human〕日期控件:有开始/结束 date input,填后表格刷新,XHR URL 含 date_from/date_to,结果≤全量。
|
||||
- [ ] **A5**〔human〕下载交付包:approved 任务点"下载交付包",≤60s 触发下载 delivery-{id}.zip(>1KB);`unzip -l` 含 note_01/文案.txt/发布清单/合规说明。
|
||||
- [ ] **A6**〔auto〕zip 结构完整:`unzip -l` grep 文案.txt/发布清单/合规说明/note_01//.jpg 全非空。⚠️审计补:若 .jpg 空先查 ImageCandidate.url 文件容器内可达(packaging_task.py:64-70 读失败静默跳过)。
|
||||
- [ ] **A7**〔auto〕文案.txt 格式:`unzip -p note_01/文案.txt` 含"【标题】"、不以 `{` 开头(JSON 已解析)。
|
||||
- [ ] **A8**〔human+auto〕多套打包:⚠️审计改 human(需先 seed 3条 is_selected TextCandidate)→构造后 `unzip -l|grep 'note_0[1-3]/'|wc -l`≥3,三套标题互不相同。
|
||||
- [ ] **A9**〔auto〕产品 JSON 导出:GET /products/export → 200,application/json,数组,每元素含 id/name/selling_points,且 selling_points 是数组(非JSON字符串)。
|
||||
- [ ] **A10**〔auto〕标杆 CSV 导出:GET /benchmarks/export?format=csv → 200,text/csv,首行表头含 product_id/highlights/created_at,行数≥已录标杆数。
|
||||
- [ ] **A11**〔auto〕导出权限:⚠️审计注——require_write_permission 当前只查 workspace_members 不分角色(workspace_guard.py:65-88);未登录调 → code=40101,workspace 成员 → 200。
|
||||
- [ ] **A12**〔human〕不显 token 余额(红线):⚠️审计改 human(curl 拿不到Next.js水合后DOM)——浏览器 Ctrl+F 搜"余额/用量/tokens/balance"无结果。
|
||||
|
||||
## 待北哥定义(不阻断代码)
|
||||
- 多套打包图片套间对应:ImageCandidate 无 set_index,是否加列关联文案?还是退化"图共享复制进每套夹"(本期默认退化)。
|
||||
- 导出入口位置(产品管理 tab 按钮 / 历史归档页全局)。
|
||||
- CSV 是否加 UTF-8 BOM(Windows Excel 不乱码)。
|
||||
49
plans/核销-第2环-标杆.md
Normal file
49
plans/核销-第2环-标杆.md
Normal file
@@ -0,0 +1,49 @@
|
||||
# 核销表 · 第2环 竞品标杆分析(标杆8特征)
|
||||
|
||||
> 90分级验收(孙总方法论·硬门禁)。已吸收独立交叉验证修正(⚠️)。本环是本轮**补全的缺失引擎环**。
|
||||
|
||||
## 模块目标
|
||||
①用户截图/手填竞品爆款 → 提取标杆8特征(features_json) ②标杆可在任务里被选中(benchmark_ids) ③选中的标杆特征**真注入文案生成 prompt**(不能只存不用) ④分析结果落库可复用。
|
||||
|
||||
## 🔴 迁移版本号统一(防三环撞车 008)
|
||||
- 008 = brand_keyword(第5环)
|
||||
- **009 = features_json + analyze_status(本环)**
|
||||
- 010 = fission_tasks 表(第11环)
|
||||
- **011 = benchmark_ids(task) + source_fission_id(本环S12 + 第11环合并)**
|
||||
|
||||
## Ralph 修改步骤
|
||||
|
||||
| # | 改什么 | 落点 |
|
||||
|---|--------|------|
|
||||
| S1 | 迁移 009:benchmark 表加 `features_json TEXT NULL` + `analyze_status VARCHAR(20) DEFAULT 'pending'` | alembic versions/009_*.py |
|
||||
| S2 | ⚠️行号修正:benchmark ORM 在 created_at(line 73)后插 features_json/analyze_status(非68-79) | models/benchmark.py:73 |
|
||||
| S3 | benchmark_analyzer.py 新建(≤120行):入参截图URL/手填文本,调 chat_complete 出8特征 dict,走 MODEL_TEXT(claude-opus-4-8) | services/benchmark_analyzer.py(新) |
|
||||
| S4 | 8特征 prompt 模板新建:输出严格 JSON(8个 key),含 few-shot;温度0.3 | prompts/benchmark_features.py(新) |
|
||||
| S5 | POST /benchmarks/{id}/analyze:触发分析,写 features_json,analyze_status=done/failed | benchmarks.py |
|
||||
| S6 | analyze 异步:丢 Celery generation 队列(同步会超 60s 网关);analyze_status=running→done | tasks/benchmark_task.py(新) |
|
||||
| S7 | BenchmarkSelector.tsx(底座 S5 已建)展示8特征 chips + analyze_status 角标 | BenchmarkSelector.tsx |
|
||||
| S8 | dto.benchmark.ts 加 features_json?:Record<string,string> + analyze_status | dto.benchmark.ts |
|
||||
| S9 | 提取失败兜底:JSON parse 失败 retry 1次仍失败→analyze_status=failed,前端显"重新分析" | benchmark_analyzer.py |
|
||||
| S10 | 8特征注入文案 prompt:text_variants.py 组 prompt 处拼入选中标杆 features | text_variants.py(组prompt处) |
|
||||
| **S11** | ⚠️构造校验:analyze 输出必须8个 key 齐(缺 key→failed),防模型偷工 | benchmark_analyzer.py |
|
||||
| **S12a** | ⚠️拆分:迁移011 task 表加 `benchmark_ids TEXT NULL`(JSON list);task.py ORM 加字段;task_service.py:60-73 构造任务时补传 benchmark_ids | 011_*.py + task.py + task_service.py:60-73 |
|
||||
| **S12b** | ⚠️拆分:pipeline 读取 task.benchmark_ids → 查 features_json → 注入(S10 的数据来源接通) | pipeline_io.py + text_variants.py |
|
||||
|
||||
## 验收清单(做完一个勾一个)
|
||||
|
||||
- [ ] **A1**〔auto〕迁移009:`alembic upgrade head` 成功,`DESC benchmark` 含 features_json/analyze_status。
|
||||
- [ ] **A2**〔auto〕analyze 接口:POST /benchmarks/{id}/analyze → 202/200,analyze_status 转 running。
|
||||
- [ ] **A3**〔auto〕8特征产出:分析完 features_json 是 dict 且**恰好8个 key**(非空、非 null、key 名与北哥定义一致)。
|
||||
- [ ] **A4**〔auto〕走最强档:抓 chat_complete 请求体 model==claude-opus-4-8(非 sonnet)。
|
||||
- [ ] **A5**〔auto〕异步不超时:analyze 触发后接口 <2s 返回(非阻塞等模型)。
|
||||
- [ ] **A6**〔auto〕失败兜底:喂坏输入(乱码截图)→analyze_status=failed(非500/非永久 running)。
|
||||
- [ ] **A7**〔human〕前端8特征:选标杆 → 卡片显8个特征 chip + 状态角标(分析中/已完成/失败)。
|
||||
- [ ] **A8**〔human〕重新分析:failed 标杆有"重新分析"按钮,点后重跑。
|
||||
- [ ] **A9**〔auto〕注入文案:选中标杆生文案,抓文案 prompt 请求体**含该标杆 features 文本**(grep 特征关键词命中)。
|
||||
- [ ] **A10**〔auto〕不选不注入:不选标杆生文案,prompt **不含** benchmark features 段(反向断言,防硬编码常驻)。
|
||||
- [ ] **A11**〔human〕复用:同标杆第二个任务直接读 features_json(不重新调模型,analyze_status 已 done)。
|
||||
- [ ] **A12**〔auto〕⚠️审计补·最高风险:benchmark_ids **真持久化**——建任务带 benchmark_ids=[1,2]→ `SELECT benchmark_ids FROM task WHERE id=?` 取回==[1,2]。(防链路断:S10/S9 仍可能因 benchmark_ids 没存而 A9/A11 假过)。
|
||||
|
||||
## 待北哥定义(🔴阻断 S4/A3,标杆8维度必须先定义)
|
||||
- **标杆8特征的名称+定义**(如:钩子类型/痛点切入/卖点呈现/信任背书/场景/情绪/CTA/排版风格?)——北哥未给前 S4 prompt 用占位8维,A3 key 名校验放宽到"恰好8个 key"不校验具体名。
|
||||
- 截图提取:截图是先 OCR 还是直接喂多模态(gpt 多模态 vs claude vision)?本期默认手填文本优先,截图 OCR 留接口。
|
||||
59
plans/核销-第5环-写文案.md
Normal file
59
plans/核销-第5环-写文案.md
Normal file
@@ -0,0 +1,59 @@
|
||||
# 核销表 · 第5环 写文案
|
||||
|
||||
> 90分级验收清单(孙总方法论·硬门禁)。已吸收独立交叉验证修正(⚠️标注处)。
|
||||
> 规则:做完一个勾一个,每勾必附证据(SQL结果/日志行/截图)。auto=机器判定,human=倩倩姐/北哥目视。
|
||||
|
||||
## 模块目标
|
||||
文案生成做到:①只展示≥90分合格文案 ②合格不足时先展示后台补 ③品牌词每条植入 ④模型升 opus-4-8 ⑤503真退避重试。
|
||||
|
||||
## Ralph 修改步骤(先全列,按序执行)
|
||||
|
||||
| # | 改什么 | 落点 |
|
||||
|---|--------|------|
|
||||
| S1 | run_text_generation 存库前过滤:`if not (c.get('passed') and c.get('score',0)>=90 and c.get('banned_word_status')!='hard_block'): continue`;合格数<目标时返回 needs_replenish=True | pipeline_io.py:96-118 |
|
||||
| S2 | Celery 主函数检查 needs_replenish:合格<text_count 时 apply_async 补充子任务(同 task_id 补 deficit),主任务不等待直接推 task_done SSE;子任务跑完追加写库+推 text_candidate SSE | 先 grep `@app.task`/`celery.task` 确认入口文件 |
|
||||
| S3 | build_product_dict 补 brand_keyword 透传(`product.brand_keyword or ''`),与 custom_prompt 同行 | pipeline_steps.py:58-68 |
|
||||
| S4 | ORM Product 加 `brand_keyword` 列(String(64) nullable)+ alembic migration 008 | product.py:39 + alembic/versions/008_brand_keyword.py(新建) |
|
||||
| S5 | products.py ProductCreate DTO 补 brand_keyword;_fmt_product 序列化补;create/update 写库赋值 | products.py:24-97 |
|
||||
| S6 | 前端 dto.ts Product/CreateProductRequest 补 brand_keyword;ProductForm 加品牌词输入框 | dto.ts:40-62 + ProductSubComponents.tsx:138-165 |
|
||||
| S7 | MODEL_TEXT 默认值改 claude-opus-4-8(**三处必须全改**:gemini_factory.py:166 + config.py:27 + .env:20) | 见左 |
|
||||
| S8 | _call_llm 捕获 httpx.HTTPStatusError,503/429 做指数退避重试(≤3次,2^attempt 秒),其他异常仍 return '' 降级 | text_variants.py:22-39 |
|
||||
| S9 | 前端 ProductForm 补 custom_prompt 文本域(品牌词下方,rows=3,label='自定义指令(可选)') | ProductSubComponents.tsx:154 |
|
||||
|
||||
⚠️ **交叉验证补强(执行前必看)**
|
||||
- **S7 三处缺一假通过**:若只改 gemini_factory 默认值、.env 没改,log 里 model 仍是旧值且不报错。执行后 `docker exec clover_worker env | grep MODEL_TEXT` 确认环境变量已生效。
|
||||
- **S8 双保险盲点**:text_variants.py:136 `dedupe_copies(...)[:count]` 的截断在 S1 过滤之前,截断后列表仍可能含 hard_block(dedupe 只去重不过滤)。S1 存库前过滤是兜底,但需确认 generate_text_variants 返回值本身的口径——单保险还是双保险,执行时定。
|
||||
|
||||
## 验收清单(做完一个勾一个)
|
||||
|
||||
> 🔄 2026-06-15重大变更:评分从机械5维→AI评委真读文案7维(忠于富贵理论);合格线90→**80(临时线)**。
|
||||
> 已用 task54 端到端真验(product_id=1,text_count=3,image_count=0),证据见下。
|
||||
|
||||
- [x] **AC-1**〔auto〕✅ 合格线过滤生效:task54 入库5条 score 80~86 全≥80 且无 hard_block。阈值 constants.py QUALITY_PASS_SCORE=80。
|
||||
- [x] **AC-2**〔human〕✅ 先展示+后台补:task54 首轮2条<目标3→触发补充→达标即停(日志"库内合格=N/3 replenished")。
|
||||
- [x] **AC-3**〔auto〕✅ 品牌词全链路:临时配 product_id=1 brand_keyword='龙石'跑 task54 → 5条 title+content 全含'龙石'。**已按倩倩姐2026-06-15要求清回NULL(品牌词客户填不预置)**。
|
||||
- [x] **AC-3b**〔auto〕✅ 反向断言:task54 `content NOT LIKE '%龙石%'` 条数=0(全植入)。
|
||||
- [ ] **AC-4**〔human〕前端有品牌词框+自定义指令域:录入保存 → GET 产品响应 brand_keyword/custom_prompt 一致。(待前端浏览器验)
|
||||
- [x] **AC-5**〔auto〕✅ 实际调 opus-4-8:ai_call_logs task54 model='claude-opus-4-8' success=1;worker env MODEL_TEXT=claude-opus-4-8。
|
||||
- [x] **AC-6**〔auto〕✅ 503真退避:task51~54 日志多次出现"LLM 返回 503,第1/4次重试,等待5s"后恢复。
|
||||
- [x] **AC-7**〔human〕✅ 前端最后一公里(2026-06-15浏览器真验):admin登录 localhost:3000 → /tasks/54/text → 用户视角看到 5/5 条文案全展示 + 每条 7维评分条(情绪张力/痛点人群/产品聚焦/买点转化/开头钩子/标题点击/合规性+总分)真实渲染;总分80~86全过线;顶部飞轮偏好回填("已选41次信号")同时生效。ScoreDimBars 成功消费后端 dims 数组。
|
||||
|
||||
## 🔴 后续待补正式工作(倩倩姐2026-06-15拍板·质量优先级)
|
||||
- **提升文案生成质量把分数自然顶上去,不靠继续降评分线**。80是临时观察值。
|
||||
方向:优化生成prompt/角度正交/卖点翻译成买点的深度。质量优化是独立工作项,非本环已完成范围。
|
||||
|
||||
## ✅ M1 质量优化(2026-06-15 去套路化·已真跑验收)
|
||||
|
||||
> 针对"后续待补正式工作"做的第一轮质量优化:①去掉收尾套路句 ②卖点翻译加深。
|
||||
> 改动落点:`_text_prompt.py`(_PERSONA 去写死范例+收尾铁律 line16;_STRUCTURE_RULES 收尾策略池A-F line74-81;build_prompt 卖点翻译范例 line159;兜底模板去套路 line203)。
|
||||
> 真跑证据:task65(3条)+task66(5条)=8条样本,product_id=1 真瓶身,image_count=0。
|
||||
|
||||
- [x] **Q1**〔auto+human〕✅ 收尾套路句清零:8条收尾**0条**含"买不买跟我没关系/东西放这了"(目标≤1)。
|
||||
- [x] **Q2**〔human〕✅ 收尾多样性达标:8条覆盖 **A留白/B反问/C场景延续/D克制回购** 四种策略(目标≥4种),无单一策略霸屏。
|
||||
- [x] **Q3**〔auto〕✅ 分数不降:8条 score_json 总分 82~92 全≥80(80=合格线,未动)。
|
||||
- [x] **Q4**〔auto〕✅ 无违禁:8条 banned_word_status 全 pass,无 hard_block。
|
||||
- [x] **Q5**〔human〕✅ 卖点翻译到位:全为可感知使用感受("熬夜后脸没那么黄""推开不卡纹路""洗面奶就能洗掉不用卸"),无裸功效词堆列。
|
||||
- ⚠️ 旁证:两次跑均碰 apiports 503 短时过载致单任务少出1条(目标6实得3/5),503退避重试生效但过载窗口内仍掉条——网络层问题非质量问题,已记 eval_score 列设计留NULL(真分在score_json)。
|
||||
|
||||
## 待北哥/倩倩姐定义(不阻断本环代码)
|
||||
- 合格不足的上限重试次数(现默认补到达标或 MAX_REPLENISH_ROUNDS=3 即止,实测生效)。
|
||||
82
plans/核销-第6环-配图.md
Normal file
82
plans/核销-第6环-配图.md
Normal file
@@ -0,0 +1,82 @@
|
||||
# 核销表 · 第6环 配图
|
||||
|
||||
> 90分级验收清单(孙总方法论·硬门禁)。已吸收独立交叉验证修正(⚠️标注处,含1处严重落点错误已修)。
|
||||
> 规则:做完一个勾一个,每勾必附证据。auto=机器判定,human=目视。
|
||||
>
|
||||
> 🔴 **2026-06-15 倩倩姐拍板重大调整**:
|
||||
> 1. **本轮目标收缩=先打通单套配图**(含去AI化+尺寸可选),3套正交A/B/C扩展挪到下一轮。
|
||||
> 2. **去AI化对齐大卫xhs实测版**(`大卫/小红书系统图片定制/xhs-tool/backend/infrastructure/imagePostProcess.js` 只读素材源,运营实测去AI化能力强)。
|
||||
> 3. **尺寸按大卫=3:4默认1024×1536(gpt原生免拉伸)**,原 S4/A5 写的"强缩1080×1440"**作废**——大卫±2%容差内不resize,零失真。
|
||||
> 4. 三套叙事措辞由倩倩姐起草,不临时占位。
|
||||
>
|
||||
> 🔴 **2026-06-15 端到端验证发现(task58 codeproxy主通道实测)**:
|
||||
> - **根因修复**:`.env` 图片主通道曾误配 `IMAGE_PROVIDER_PRIMARY=apiports`,但 apiports 无 gpt-image-2 的 edits 端点(返回SPA首页HTML→`Expecting value`报错),违反红线「生图主=codeproxy」。已改回 codeproxy,worker重建,task58 六图全出(provider=codeproxy/success=1)。详见记忆 clover-apiports-no-image-edits-endpoint。
|
||||
> - ⚠️ **产品名占位污染产出(待北哥真数据)**:product_id=1 name="素颜霜(预置样本)","(预置样本)"被画进图(02特写标题)。同"龙石"类,是测试数据污染非链路bug,换真实产品名即正常。
|
||||
> - ⚠️ **status enum 无 'failed'**:任务失败只能无限重试或硬改 rejected,设计缺口待补。
|
||||
|
||||
## 🟢 本轮施工图(单套配图打通·先列后做)
|
||||
|
||||
| # | 改什么 | 落点 | 对应大卫 |
|
||||
|---|--------|------|---------|
|
||||
| P1 | image_postprocessor 重写:加 RATIO_MAP(1:1/3:4/4:3/9:16/16:9)、±2%容差跳过、SynthID破除(缩2px裁1px边+modulate亮度1.005/饱和0.998,env SYNTHID_HARD_MODE开关)、quality 88→100/chroma4:4:4 | image_postprocessor.py | imagePostProcess.js逐项 |
|
||||
| P2 | process_image 加 aspect_ratio='3:4' 参数;pipeline_io 调用处传尺寸 | image_postprocessor.py + pipeline_io.py:204 | RATIO_MAP默认3:4 |
|
||||
| P3 | 生图请求尺寸对齐 1024×1536(gpt原生3:4),确认 image_gen size 正确 | constants.py + image_gen.py | 1024×1536 |
|
||||
| P4 | 配图段写 ai_call_logs(call_type='image',provider,success,latency,error_code) | pipeline_io.py:244前 | Clover自有 |
|
||||
|
||||
> 🔴 **2026-06-15 倩倩姐纠偏:标绿门槛=真实数据端到端跑通**:
|
||||
> task58 是**占位产品**("素颜霜(预置样本)")跑的,**不算端到端成功**。下方 B1-B8 的"✅"降级为"🟡链路自测通过(占位数据)",**必须用北哥真实数据(产品名=素颜霜/品牌词=倍分子)重跑通才能标真绿**。倩倩姐原话"标绿不能随便标,得端到端测试成功之后才能标"。
|
||||
> - apiports **确实有生图接口**(后台image key已启用/有余额/历史54万tokens),只是接法与 `/images/edits` 不同,在大卫xhs里是可用备用通道,待coder查正确接法后修成真备用。本轮主线先codeproxy。
|
||||
|
||||
## 🟡 验收清单(本轮·单套)— 占位数据自测通过,待真实数据复验
|
||||
|
||||
> 下列✅=占位产品task58链路自测通过;🔴 = 待倍分子素颜霜真实数据重跑确认。
|
||||
|
||||
- [x] **B1**〔auto〕单套6图入库:✅task58 `image_candidates` COUNT=6(id171-176),role齐(hook/product_closeup/ingredient/texture/applied_proof/closer),url非空,/app/uploads/3/58/ 6个jpg真落盘(1.1-1.35MB)。
|
||||
- [x] **B2**〔auto〕尺寸3:4=1024×1536:✅task58 PIL独立读6张全部(1024,1536),容差内未拉伸。
|
||||
- [x] **B3**〔auto〕去元数据:✅task58 6张 exif全NONE。(SYNTHID缩边验证归B8 coder交叉)
|
||||
- [x] **B4**〔auto〕尺寸可选真生效:✅单测 process_image('1:1')→(1024,1024)、('3:4')→(1024,1536)、传1080×1440→resize到(1024,1536)。
|
||||
- [x] **B5**〔auto〕生图写日志:✅task58 `ai_call_logs` call_type='image'/provider='codeproxy'/success=1/latency_ms=345907/error_code=NULL。
|
||||
- [x] **B6**〔auto〕禁降级硬失败保持:✅task57 need_product_image=True无参考图→拒绝降级(日志"拒绝降级纯文生图"),image_candidates COUNT=0,无"降级"成功字眼。
|
||||
- [x] **B7**〔human〕浏览器真验:✅倩倩姐+我目视task58封面(01_hook"早八来不及"大字清晰/三卖点勾选/产品与参考图一致/场景去AI化真实/瓶身无虚假品牌词合规)+02特写(产品居中/卖点+气泡框清晰),3:4比例画质佳。⚠️仅"(预置样本)"占位字样待真数据。
|
||||
- [x] **B8**〔auto〕交叉验证:✅coder独立起脚本重核task58,结论与team-lead一致:B1(COUNT=6/role齐)、B2(6张全1024×1536/exif=None/icc=None/xmp=None)、B4=B5(provider=codeproxy/success/无Expecting value报错)真绿,B3 N/A(SYNTHID_HARD_MODE未开)。无谎报无放水。
|
||||
|
||||
---
|
||||
|
||||
## 📦 下一轮:3套正交扩展(本轮不做,归档备查)
|
||||
|
||||
> 单套打通后再做。叙事措辞等倩倩姐起草。原 S1/S2/S3/S7/S8 + A1/A2/A3/A4/A7/A8 归此。
|
||||
|
||||
### Ralph 修改步骤(下一轮)
|
||||
|
||||
| # | 改什么 | 落点 |
|
||||
|---|--------|------|
|
||||
| S1 | generate_storyboard_images 循环3次(strategy A/B/C),每次传不同 strategy_hint 影响叙事维度;返回 list[dict]→list[list[dict]] | image_gen.py:121-173 |
|
||||
| S2 | plan_image_set 接收 strategy 参数,按 strategy 切换叙事描述(新增A痛点先行/B场景先行/C成分背书先行3条),写进 base_prompt 叙事链路段 | storyboard.py:119-193 + constants.py:66-70 |
|
||||
| S3 | run_image_generation 对 A/B/C 各调一次,存 ImageCandidate 时 strategy 分别写 A/B/C(修掉:207硬编码'A');SSE strategy 随之正确 | pipeline_io.py:156-213 |
|
||||
| S4 | ⚠️**强制 resize**(落点已修正,见下):`Image.open(...).convert('RGB')` 后**立即**插入 `img=img.resize((1080,1440),Image.LANCZOS)`,并把第47-49行 `resize(original_size)` 改为 `resize((1080,1440))` | image_postprocessor.py:41 之后 |
|
||||
| S5 | run_image_generation 仿 run_text_generation:77-93,三套全完后写 AiCallLog(call_type='image',provider取实际路由,success/latency覆盖整批,单套失败不阻断,success=False写error_code) | pipeline_io.py:215 db.commit() 前 |
|
||||
| S6 | ALLOW_TEXT_ONLY_IMAGE 默认 'true'→'false',与 pipeline_io:150 硬失败对齐 | image_gen.py:70 |
|
||||
| S7 | 前端 generationStore 新增 imageSets:Record<'A'\|'B'\|'C',ImageCandidate[]>,addImageCandidate 按 strategy 分流,reset/hydrate 同步 | generationStore.ts:15-122 |
|
||||
| S8 | 图片选择页加 A/B/C 切换 Tab,默认套A,每套内单张可选;DTO strategy 字段已存在无需改类型 | 新建 ImageSetTabs.tsx 或 page 内联 |
|
||||
|
||||
⚠️ **交叉验证补强(执行前必看)**
|
||||
- **🔴S4 严重修正**:原清单写"在 buf.save 之前插入 resize"是**错的**——那个位置已经过了基于 original_size 的缩放,拿到的还是 gpt-image-2 返回的 1024×1536。正确落点:`Image.open().convert('RGB')` 之后立即锁死 1080×1440,且第47-49行原 `resize(original_size)` 同步改成 `resize((1080,1440))`。
|
||||
- **S1+S3 必须同步**:S1 改返回值 list→list[list],pipeline_io.py:165 的 `enumerate(image_results)` 解包会变。**不能只做 S1 不做 S3**,中间是崩溃态。
|
||||
- **S6 两层说清**:pipeline_io:150 是第一层(按产品 need_product_image 字段拦);image_gen:70 是第二层(直调 generate_one_image 的兜底)。两层同时维护,别只改一处。
|
||||
|
||||
## 验收清单(做完一个勾一个)
|
||||
|
||||
- [ ] **A1**〔auto〕3套各6张:`SELECT strategy,COUNT(*) FROM image_candidates WHERE task_id=<id> GROUP BY strategy` → 3行,每行 count=6(或=image_count),strategy=A/B/C。
|
||||
- [ ] **A2**〔auto〕SSE strategy 三值:DevTools Network 找 SSE 流,grep image_candidate,strategy 出现 A/B/C 各>0次(非全'A')。
|
||||
- [ ] **A3**〔human〕⚠️前置:S1+S2 已完成。三套 base_prompt 叙事段不同:在 plan_image_set 加 `logger.info("strategy=%s base_prompt前100字=%s", strategy, base_prompt[:100])`,确认套A含'痛点先行'/套B含'场景先行'/套C含'成分背书先行'。
|
||||
- [ ] **A4**〔拆两层〕⚠️品牌词进特写图:
|
||||
- ①〔auto〕代码层:storyboard.py 中 strategy=A 的第2/6张 item 包含 brand_keyword 与 brand_keyword_rule 字段(DEBUG日志或单测断言)。**这是 pass/fail 判据**。
|
||||
- ②〔human〕效果层:下载第2/6张目视有'龙石'(best-effort,模型概率性,**不作代码验收判据**——gpt-image-2瓶身小字会糊已记录在案)。
|
||||
- [ ] **A5**〔auto〕尺寸严格 1080×1440:⚠️先确认实际写盘路径(worker 日志,默认 UPLOAD_BASE_PATH='uploads/packages' 不是 /app/uploads)→ `python3 -c "from PIL import Image;print(Image.open('<实际路径>/01_hook.jpg').size)"` 必须 (1080,1440)。
|
||||
- [ ] **A6**〔auto〕生图写日志:`SELECT provider,success,latency_ms FROM ai_call_logs WHERE task_id=<id> AND call_type='image'` → ≥1行,provider非空、latency_ms>0、success IN(0,1)。
|
||||
- [ ] **A6b**〔auto〕⚠️日志内容正确性(S5核心差错逻辑):三套全成功时 success=1;至少一套失败时 success=0 且 error_code 非空。
|
||||
- [ ] **A7**〔auto〕无参考图硬失败:建 need_product_image=True 但产品无参考图的任务 → task status='failed',image_candidates 无该 task 记录,worker 日志**不含**'降级为纯文生图'。
|
||||
- [ ] **A8**〔human〕前端 A/B/C Tab:图片选择页有 A/B/C 可点 Tab,点击切换图片网格内容,三套 URL 不同(非平铺混在一起)。
|
||||
|
||||
## 待北哥定义(不阻断本环代码骨架,prompt 占位先留)
|
||||
- 三套叙事维度的具体文案措辞(先用 痛点/场景/成分背书 占位,北哥方案到位再填)。
|
||||
35
plans/核销-第8环-审核.md
Normal file
35
plans/核销-第8环-审核.md
Normal file
@@ -0,0 +1,35 @@
|
||||
# 核销表 · 第8环 审核
|
||||
|
||||
> 90分级验收(孙总方法论·硬门禁)。已吸收独立交叉验证修正(⚠️)。auto=机器判定,human=目视。
|
||||
> ⚠️审计结论:原清单 S1-S6 全部"描述了但代码里没有"——即这是**待执行**清单,不是已完成。落点行号经核对基本准确。
|
||||
|
||||
## 模块目标
|
||||
①Sidebar 死链清零 + 加审核台入口 ②组长待审队列(通过/打回带原因) ③打回回路闭环(operator 能感知重选)。
|
||||
|
||||
## Ralph 修改步骤
|
||||
|
||||
| # | 改什么 | 落点 |
|
||||
|---|--------|------|
|
||||
| S1 | 删4条死链(/tasks /images /tasks/build /tasks/list),加 `{label:'审核台',href:'/review',roles:['supervisor','admin'],icon:'✅'}`,共5条全有页面 | Sidebar.tsx:19-28 NAV_ITEMS |
|
||||
| S2 | _fmt_task return dict 末尾加 `reject_reason`/`review_status`(均可None);模型 task.py:50-55 已有字段直接引用 | tasks.py:58-64 |
|
||||
| S3 | TaskListItem 加 `reject_reason?:string\|null` + `review_status?:'pending'\|'approved'\|'rejected'\|null` | dto.tasks.ts:8-16 |
|
||||
| S4 | 状态 span 下加 `{task.reject_reason && <p className='text-xs text-status-error mt-0.5 line-clamp-1'>打回:{task.reject_reason}</p>}`(需先 S3) | RecentTasksBar.tsx:49-61 |
|
||||
| S5 | h2 后插3个 Tab(待审/已通过/已打回),已通过→router.push('/history?status=approved'),已打回→rejected;顶部 import useRouter | review/page.tsx:54-57 |
|
||||
| S5b | ⚠️审计补:history/page.tsx 改 `useSearchParams` 初始化 statusFilter,否则跳来后筛选器停"全部"(A7假通过) | history/page.tsx:26 |
|
||||
| S6 | useEffect setCurrentTask 后补 GET /tasks/{id} 取 reject_reason 存 state;ProgressBar 下、FlywheelBanner 上插红色 alert 横幅(需先 S2/S3) | tasks/[id]/text/page.tsx:23-25 |
|
||||
|
||||
## 验收清单(做完一个勾一个)
|
||||
|
||||
- [ ] **A1**〔auto〕Sidebar 无死链:`grep -n href Sidebar.tsx` 不含四条死链且含 '/review'。
|
||||
- [ ] **A2**〔auto〕待审队列可用:supervisor GET /api/v1/review/queue → code=0 且 data.items 是数组。
|
||||
- [ ] **A3**〔auto〕通过写库正确:`SELECT status,review_status,approved_at,reviewer_id FROM generation_tasks WHERE id=<id>` → 四项全满足(status=review_status='approved'、approved_at 与 reviewer_id 均非NULL)。⚠️审计修正:assert 要含 reviewer_id(r[3])。
|
||||
- [ ] **A4**〔auto〕打回写库正确:RejectModal 空提交报"原因必填"不发请求;填后 `SELECT status,review_status,reject_reason` → status='pending_selection'、review_status='rejected'、reject_reason 非空。
|
||||
- [ ] **A5**〔auto〕GET /tasks 含字段:被打回任务 reject_reason 为字符串、review_status='rejected';未打回为 null,接口不500。
|
||||
- [ ] **A6**〔human〕operator 感知打回:supervisor 打回填"标题太硬广"→切 operator 访问 /tasks/new,RecentTasksBar 卡上见红字"打回:标题太硬广"→点卡进 text 页顶部有含该文字红色横幅。
|
||||
- [ ] **A7**〔human〕Tab 跳转无404:/review 三 Tab,点已通过→/history?status=approved 页面有内容**且筛选器自动选中"已通过"**(非"全部"),点已打回同理。⚠️审计补:需验筛选器自动预选。
|
||||
- [ ] **A8**〔auto〕角色守卫:⚠️审计修正——分两查:`curl -w '%{http_code}'` 验 HTTP 403 + 读 body 验 `code==40301`(原命令 -o /dev/null 读不到 body)。
|
||||
|
||||
## 待北哥定义(不阻断代码)
|
||||
- 已通过/已打回 Tab 是跳 /history 还是 /review 内分 Tab 调独立接口。
|
||||
- 打回原因卡片截断字数 + 展开交互(tooltip/点击)。
|
||||
- RejectModal 是否预设快选分类(标题太广告体/图文不符/违规词)。
|
||||
101
plans/程1复盘与后续设计.md
Normal file
101
plans/程1复盘与后续设计.md
Normal file
@@ -0,0 +1,101 @@
|
||||
# 程1复盘 + 后续执行设计(断点续)
|
||||
|
||||
> 2026-06-13。程1(wf_d840d358-d3e)跑1.9h后failed。本文件记根因+已落成果+程2/3设计,断点可续。
|
||||
|
||||
## 程1根因(已诊断)
|
||||
workflow 的 stall 检测 = **180s 无工具调用完成就杀 agent**。
|
||||
Clover 端到端生成本身要 **312s**。任何把"跑完整生成验证"当单步阻塞的 agent → 必超180s被杀 → 6次重试全栽同一坑 → workflow failed。
|
||||
这是**编排设计问题,不是代码问题**。
|
||||
|
||||
## 程1已落成果(没白跑,真进项目)
|
||||
1. ✅ 环境勘验完成:
|
||||
- codeRoot=`Clover/backend`,frontendRoot=`Clover/frontend`(不在docker compose,需npm单独跑)
|
||||
- docker-compose.yml 在 `backend/` 子目录(不在项目根),compose命令要加 `-f` 或 cd backend
|
||||
- 后端代码挂载热重载(api带--reload,改.py自动生效);**worker无热重载,改worker/service代码后须 `docker compose restart worker`**
|
||||
- 迁移命令 `docker exec clover_api alembic upgrade head`;api启动也自动跑一次
|
||||
- 6容器全Up健康;端到端跑法见环境勘验result(登录admin/Clover2026!→product_id=1→建任务→轮询)
|
||||
- ⚠️backend的.py改动不在大repo的git status里(被ignore?),无法git回滚追踪
|
||||
2. ✅ 迁移008-011真跑成功落库(alembic 007→011):
|
||||
- 008 products.brand_keyword VARCHAR(64)
|
||||
- 009 benchmark_notes.features_json TEXT + analyze_status VARCHAR(20)
|
||||
- 010 fission_tasks 表新建
|
||||
- 011 generation_tasks.benchmark_ids TEXT + source_fission_id INT
|
||||
- 新建 app/models/fission.py FissionTask ORM;models/__init__.py 已导出
|
||||
3. ◐ M1文案三处改动已写进代码(待端到端验证):
|
||||
- S7模型三处全改对:config.py:27 + gemini_factory.py:166 + .env:20 = claude-opus-4-8
|
||||
- S8重试退避:text_variants.py:43-49 503/429指数退避 2^attempt
|
||||
- S1合格过滤+needs_replenish:pipeline_io.py:98-138 passed且score>=QUALITY_PASS_SCORE且非hard_block,saved<text_count触发补充
|
||||
- 验证中:task42(2026-06-13)端到端真跑确认
|
||||
|
||||
## 后续执行设计(倩倩姐拍板:拆细workflow+我跑验证)
|
||||
铁律:**agent 只改代码不跑312s长验证**;端到端真跑验证由主线程(我)用 Monitor 后台盯,不受stall限。
|
||||
- workflow里的agent活拆到180s内能完成:读清单+改文件+跑只读/快命令(grep/SELECT/import检查)
|
||||
- 抓"模型是不是opus-4-8"用 grep 代码+抓单次请求体,不靠跑完整生成
|
||||
- 端到端一条龙、312s生成 → 我在主线程 Monitor
|
||||
- 每环仍独立交叉验证(另起agent重核代码层),但效果层(真出文案/图)我主线程验
|
||||
|
||||
## 程2待办(M3审核/M4归档/M5底座) — 多碰pipeline_io/task/tasks/config须串行
|
||||
## 程3待办(M6标杆/M7裂变 用占位规则)
|
||||
## M1验证中断点:task42 状态待Monitor回报;通过则M1勾✅,进程2
|
||||
|
||||
## M1验证实况(2026-06-13,真跑抓到3个真bug,绝不信自评的价值)
|
||||
- **bug1 模型没切**:task42 worker日志跑的还是 claude-sonnet-4-5。根因=worker容器env_file固化4天前旧值,restart无效,必须 `docker compose up -d worker` 重建(已记忆 clover-worker-env-reload-trap)。修后 printenv MODEL_TEXT=claude-opus-4-8 ✅
|
||||
- **bug2 返回值解包炸**:程1把 run_text_generation 改成返回3元组(加needs_replenish),但 tasks.py:102 只解包2个 → `too many values to unpack (expected 2)`,整个pipeline崩+retry循环。这正是核销表"S1+S3必须同步"风险。已修 tasks.py:102 解包3元组。
|
||||
- **bug3 后台补充task缺失**:needs_replenish只算出来没人消费(先展示后台补铁律没落地)。已新建 app/workers/replenish_task.py 的 replenish_text_candidates(MAX_REPLENISH_ROUNDS=3),tasks.py:108 needs_replenish时.delay触发,celery_app include+tasks.py re-export注册。
|
||||
- **确认链路**:task44日志铁证 model=claude-opus-4-8 success=1 latency296s(opus确实慢~300s)。opus单次响应慢,注意网关60s上限风险。
|
||||
- **task45**:发干净任务验证全部修复后的完整链路(opus+解包+补充),Monitor盯中。
|
||||
- sonnet旧分数(task42):3条total 80/81/80全不过90,第4/5分项系统性低(9分/0-5分)——待opus这轮看能否过90,要倩倩姐判质量。
|
||||
|
||||
## 程2待办(M3审核/M4归档/M5底座) — 多碰pipeline_io/task/tasks/config须串行
|
||||
|
||||
## M1验证收尾(2026-06-13下午,60s网关根因彻底解决+又揪2个真bug)
|
||||
### ✅ 已铁证跑通(task47完整闭环)
|
||||
- **60s网关503根因锁定**:不是apiports过载/opus慢,是 `max_tokens=8192写死`——opus会撑满输出空间导致单批>60s撞网关。实测单条max_tokens=1500~2500仅16~18s。
|
||||
- **修复3处全验证生效**:①`_call_llm`的max_tokens参数化 ②`_generate_one_batch`按批量`min(8192,max(1800,n*1800))`缩放 ③`.env`的TEXT_BATCH_SIZE=1。
|
||||
- **task47链路全绿**:首轮3条串行112s全成功零503→评分→过滤(只1条≥90)→先展示入库→needs_replenish触发→后台补充任务received。"先展示后台补"两截都跑通。
|
||||
- **opus文案质量样本(task47 id=227)**:91分(标题23/情绪25/买点25/关键词13/合规5),真实素人口吻、痛点切入、emoji自然、合规满分。明显优于sonnet旧档(80分)。
|
||||
|
||||
### 🐞 又揪2个真bug(绝不信自评的价值)
|
||||
- **bug4 补充任务计数维度错**:replenish_task.py第76行`added_total += len(raw)`把"原始生成数"当"合格入库数",task47实测len(raw)=2但saved=0(都没过90)→误判"累计3/3"提前停,库里实际仍缺2条。已修=改用DB真实count(`db.expire_all()`+`db.query(TextCandidate).count()`)做循环条件,return真实`current-existing`。
|
||||
- **bug5 tasks.py日志措辞误导**:`已合格=%d`实际填的是len(candidates_raw)原始生成数。已修措辞为"本轮生成"+注释说明以库内saved_count为准。
|
||||
|
||||
### ⚠️ apiports实时负载波动(非代码问题,需留意)
|
||||
- task48验证补充修复时撞apiports高负载:同样batch1单条,第1条35s成功,第2条起涨到61s→503,3次退避重试都撞高负载窗口。基线18s→35s→61s说明是中转站负载翻倍不是代码。
|
||||
- **代码已是最优**(串行单条+动态max_tokens+退避),apiports抽风时单条也会被拖过60s,重试救不回。这是产品级风险点,要攒给倩倩姐判断容错策略。
|
||||
|
||||
### M1状态:代码层✅全绿(3修复+2bug已修验);效果层◐ task47闭环已证,补充DBcount修复待apiports恢复后真跑确认
|
||||
|
||||
## M1最后一跑(task49,2026-06-15):机制全绿但合格率暴露结构性问题
|
||||
### ✅ 机制层全部验证通过(哪怕极端0合格case)
|
||||
- task49跑出9条文案分数:79/83/71/71/87/81/79...**无一自然≥90**。
|
||||
- 先展示:0条合格也置pending_selection不卡用户 ✅
|
||||
- 后台补充:3轮全跑,用DB真实count判断(bug4修复生效,没再误报"够了") ✅
|
||||
- 诚实上报:`replenished=0 rounds=3 final=0 target=3`,达上限停止不无限补 ✅
|
||||
- 容错(倩倩姐拍板加大重试):max_attempts=5+退避5/10/20/30s 已生效 ✅
|
||||
- bug6修复:image_count=0早退守卫(纯文案任务不再空跑生图通道) ✅
|
||||
|
||||
### 🔴 暴露的结构性质量问题(需倩倩姐判断,非bug)
|
||||
- **90分线对素颜霜合格率极低**(task47首轮3条过1条,task49首轮3条+补充6条共9条过0条≈合格率0-25%)。
|
||||
- **根因=评分权重结构**:满分=标题25+情绪25+买点25+关键词20+合规5。实测每条卡在**关键词覆盖13/20**(必扣5-7分,note总是"建议补品类词/长尾词")。光这项扣7分→要过90必须其余四项几乎全满分,实际把及格线推到"四项满分"。
|
||||
- task47那条91分=标题23+情绪25+买点25+关键词13+合规5,是"四项接近满"的运气case。
|
||||
- **opus文案本身质量不差**(真实素人口吻/痛点切入/emoji自然/合规满分),是90线+关键词20分权重太严,不是文案烂。
|
||||
|
||||
### 待倩倩姐判断(攒批):①90线降不降/关键词权重调不调 ②还是先让北哥抽检原文再定线 ③合格率低时补充上限3轮够不够
|
||||
|
||||
## 根因实锤+错误回滚(task50,2026-06-15晚)
|
||||
### 🎯 关键词维度卡死的真正底因(已实测坐实)
|
||||
- 之前说"依赖products.keywords配置"还不够准。**实测products表根本没有keywords字段**(只有name/category/selling_points/style_tone/text_angles/custom_prompt/image_path/brand_keyword),build_product_dict()也没传keywords。
|
||||
- 所以score_keyword的`matched=[k for k in keywords...]`里keywords恒为[]→matched恒空→matched≥1(+6)+matched≥2(+5)=11分**永远拿不到**,关键词维度天花板被锁在9-13分(只靠tags≥3+5/有#+4/tags≥5+4凑)。
|
||||
- 入库3条实测明细坐实:id225=标19情23买25**关9**合5=81;id226=18/23/25/**9**/5=80;id227=23/25/25/**13**/5=**91✅**。关键词全卡9-13。
|
||||
|
||||
### ❌ "调权重"是错误方向,已回滚
|
||||
- 试过keyword20→10、把10分补给title/emotion(30/30)。task50实测84/67/75**反而更低**。
|
||||
- 失败原因:title/emotion的加分项要文案命中特定硬词表(场景词/情绪词/品类词)才填得满,封顶34/33。文案没变命中的词没变,新增的权重空间填不满→总分不升反降。删了keyword能稳拿的分,没换来title/emotion的新增分。
|
||||
- **已回滚constants.py到原始权重25/25/25/20/5**,worker重启确认生效。constants.py注释已记录真相+正确解方向。
|
||||
|
||||
### ✅ 正确解(等北哥标准到位,二选一或都做)
|
||||
1. 给products表补keywords字段+前端录入(让matched能真匹配)——治标,让现有硬词表评分跑通。
|
||||
2. 评分用LLM语义判分替代硬编码词表(score_keyword/title/emotion都改成让模型判)——治本,但要北哥的质量标准/prompt到位。
|
||||
- 现阶段:维持原始权重占位,真过关靠北哥抽检,不靠机器调权重凑数(机器分高≠过关,CLAUDE.md铁律)。
|
||||
|
||||
### M1结论:机制层✅全绿(已勾);合格率=占位规则的已知局限,不阻断进程2,等北哥质量标准到位再治本
|
||||
49
plans/配图3套叙事草稿-北哥过目版.md
Normal file
49
plans/配图3套叙事草稿-北哥过目版.md
Normal file
@@ -0,0 +1,49 @@
|
||||
# 配图3套正交叙事草稿(北哥过目版)
|
||||
|
||||
> 2026-06-15 提炼。**不是凭空编**——直接扒北哥给的3个真实爆款"图片爆款原因",映射成3套正交叙事。
|
||||
> 产品:倍分子素颜霜(品牌词=倍分子,客户输入)。
|
||||
> 用途:填进 `constants.NARRATIVE_BY_COUNT` 的套1/套2/套3 + 每套侧重,3套整组拉开差异、不重复。
|
||||
> **请北哥确认措辞,确认后我让 coder 填进生图 prompt。**
|
||||
|
||||
## 三套对应的北哥真实爆款来源
|
||||
|
||||
| 套 | 正交轴 | 来源爆款 | 爆款原因原话 |
|
||||
|---|--------|---------|------------|
|
||||
| 套1 | **痛点先行** | 爆款2 (649b) | 「脸越黄亮越快」直击痛点·针对暗黄人群;产品特写+文字突出;感叹号+对比词制造紧迫感 |
|
||||
| 套2 | **场景先行** | 爆款3 (680a) | "早八""伪素颜自由"场景钩子;简洁清晰产品突出;价格"二十几"性价比 |
|
||||
| 套3 | **成分背书先行** | 爆款1 (63db) | 对比强烈真实感强情绪共鸣;适合加成分图解、使用前后时间线、用户评论增强信任 |
|
||||
|
||||
---
|
||||
|
||||
## 套1 · 痛点先行(暗黄/伪素颜焦虑切入)
|
||||
|
||||
**叙事链路(6图)**:
|
||||
痛点暴击封面 → 暗黄脸实拍对比 → 倍分子素颜霜单品特写 → 成分为什么能救暗黄 → 上脸提亮实证 → "别再顶着黄脸早八"促单。
|
||||
|
||||
**整组基调**:紧迫感、强对比、情绪共鸣。文字短促带感叹号,直戳"脸黄显疲惫""素颜不敢出门"。
|
||||
|
||||
---
|
||||
|
||||
## 套2 · 场景先行(早八/通勤伪素颜自由)
|
||||
|
||||
**叙事链路(6图)**:
|
||||
"早八来不及"场景封面 → 手忙脚乱通勤场景 → 倍分子素颜霜一抹搞定特写 → 养肤成分让你敢素颜 → 30秒上脸效果 → "伪素颜自由+平价"促单。
|
||||
|
||||
**整组基调**:轻松、生活化、代入感。突出"快""省时""伪素颜自由",点到性价比但不堆砌。
|
||||
|
||||
---
|
||||
|
||||
## 套3 · 成分背书先行(信任/真实感/前后对比)
|
||||
|
||||
**叙事链路(6图)**:
|
||||
成分权威封面 → 核心成分图解 → 倍分子素颜霜单品特写 → 使用前后时间线对比 → 真实上脸细节 → "成分党闭眼入"促单。
|
||||
|
||||
**整组基调**:专业、可信、真实测评感。强调成分逻辑、前后对比、像有用户实证背书。
|
||||
|
||||
---
|
||||
|
||||
## 待北哥确认点
|
||||
|
||||
1. 三套基调/链路方向对不对北哥的味?
|
||||
2. 措辞要不要更口语/更狠?
|
||||
3. 性价比"二十几"这种具体价格要不要进图(涉及真实定价,需北哥给准数)?
|
||||
Reference in New Issue
Block a user