Install
openclaw skills install ielts-reading-reviewIELTS Reading passage review, scoring, and progress tracking skill. Generates structured review data (JSON) and deploys to tuyaya.online via saveReview API. The server's review.html template renders JSON into unified pages. No standalone HTML generation needed. Supports batch import of legacy reviews with auto-discovery of review folders. Trigger phrases: 雅思复盘, 帮我复盘阅读, IELTS reading review, 分析错题, 阅读错题分析, 成绩单, 打分, 统计, 进步趋势, 批量导入历史复盘, 历史笔记转 JSON, 把文件夹里的复盘都生成 JSON, 扫一下我电脑里的复盘, 帮我找出所有历史笔记, 自动发现复盘, score, band, progress, batch import, auto scan.
openclaw skills install ielts-reading-review帮用户把雅思阅读做题结果变成结构化数据(JSON),通过 saveReview API 入库后由后端 review.html 模板统一渲染页面。
只要主人在对话里发了雅思阅读题(截图 / 文字答案 / 错题列表 / 任何阅读相关材料),就必须一气呵成跑完以下闭环,不允许中途停在文字分析阶段:
读截图 → 错题确认 → 写错题分析 → ★生成 v4.0 JSON★ → ★saveReview/upload 入库★ → ★getReviews 回查 ✅★ → 汇报线上链接
判定"复盘完成"的唯一标准 = getReviews 回查显示该篇已入库(不是"我写完文字分析了")。
绝对禁止的"假完成"模式(历史血泪):
本铁律覆盖所有其他流程。即使主人只说"帮我看看这题对不对""分析这道错题""这套该几分",只要内容是雅思阅读,就走完整闭环。
历史教训(2026-05-22):剑8 T3P1+T3P2 复盘只在聊天里写了文字分析没入库,主人在 dashboard 看不到,22:49 提醒后才补救。这种事再也不能发生。
⚠️ v5.4.2 最重大变更(2026-05-22):将"必须入库"提升为最高铁律。SKILL.md 顶部新增「最高铁律」段,加入 Step 8 Final Gate 强制 checklist——任何复盘任务,未通过 getReviews 回查 ✅ 不允许结束,不允许只交付文字分析。
⚠️ v5.1 新增三道防线(防 saveReview 漏调 / 本地副本陈旧):
clawhub install --force 到 ~/.workbuddy/skills/⚠️ v5.0 重大简化:服务端已预置 C4-C20 全量 answer-key(204条 reading)+ bilingual_data(100条核心双语),复盘流程不再需要更新这两个文件,部署清单大幅缩减。
⚠️ 不再生成复盘 HTML! 后端 review.html 模板页统一渲染 JSON,单独生成的 HTML 完全无用。
产出物:
review.html?file=xxx.json 在线渲染v5.1 变更(2026-05-11 晚):三道防线避免再犯 saveReview 漏调 + 本地副本不更新的坑。
v5.0 变更(2026-05-11):服务端预置 C4-C20 全量 answer-key + bilingual_data,复盘流程不再需要本地维护这两个文件。仅当复盘 C20 之后的新书才需要扩展。部署清单从 5 个文件缩减到 4 个(仅 JSON + 词汇相关)。
v4.0 变更:不再生成复盘 HTML。后端 review.html 模板页统一渲染 JSON,单独生成 HTML 无用。复盘只需 JSON + saveReview API 入库。
v3.9.1 新增:Step 0 自动版本检查(scripts/check-update.js),每次激活时比对本地与 ClawHub 版本。
v3.9.0 新增:词库覆盖校验(dict_full.json 缺词 = 词卡展开不工作)、saveReview API 入库步骤、answers[] 字段名规范、线上词卡验证步骤。
第一件事:判断当前是「作者模式」还是「客户端模式」。两种模式行为完全不同,绝不能搞错。
# 模式判定逻辑(执行下列检测):
test -f ~/.ssh/workbuddy.pem && grep -q "openclaw-tunnel" ~/.ssh/config 2>/dev/null && echo "作者机" || echo "客户端机"
| 信号 | 模式 | 行为 |
|---|---|---|
检测到 ~/.ssh/workbuddy.pem + openclaw-tunnel SSH 别名 | 作者模式 | Step 7 走完整 SSH 部署链路(gzip 流、cat 管道、systemctl restart) |
找不到上述凭据,但有 IELTS_USER_TOKEN 环境变量 | 客户端模式 | Step 7 跳过所有 SSH 操作,只走 HTTPS batchImport 入库 |
| 都没有 | 未配置客户端模式 | 提示用户先配 IELTS_USER_TOKEN(详见客户端 onboarding 章节),然后切到客户端模式 |
模式横幅必须输出(每次激活时):
🎯 IELTS Reading Review · vX.Y.Z
🔐 运行模式:作者模式 / 客户端模式
👤 token 主体:dengjiawei / lishuzhuo / (匿名)
作者模式与客户端模式的关键差异(必读):
| 步骤 | 作者模式 | 客户端模式 |
|---|---|---|
| Step 7a 词库覆盖校验 | ✅ 必跑(要部署 dict_full.json) | ⏭️ 跳过(词库由作者维护,客户端无写权限) |
| Step 7b 部署 site/reviews/ JSON | ✅ SCP 到服务器 | ⏭️ 跳过(batchImport 已写入数据库) |
| Step 7b 部署 dict_full.json + synonym_data.json | ✅ gzip 流推送 | ⏭️ 跳过 |
| Step 7c saveReview API | ✅ ssh + localhost:3100 | ⏭️ 改用 batchImport(HTTPS + token) |
| Step 7d 后端代码部署 | ✅ 必要时执行 | 🚫 严禁触碰 |
| Step 7e 后端重启 | ✅ systemctl restart | 🚫 严禁触碰 |
| Step 7g 入库回查 | ✅ getReviews 校验 | ✅ getReviews 校验(HTTPS) |
| 本地保存 JSON | ✅ site/reviews/ | ✅ 用户自选目录(如 ~/Documents/雅思复盘/) |
客户端模式下绝对禁止:执行
ssh openclaw-tunnel、scp、gzip -c | ssh、systemctl restart、修改/var/www/ielts/任何文件。
每次 Skill 被激活时,第一件事必须显式输出当前版本横幅:
node ~/.workbuddy/skills/ielts-reading-review/scripts/check-update.js
强制行为规范:
🆕 有新版本可用 → 立即提示用户并询问是否更新:
⚠️ ielts-reading-review 有新版本 vX.Y.Z(当前 vA.B.C),强烈建议先更新再开始复盘。
现在更新?
node ~/.workbuddy/skills/ielts-reading-review/scripts/check-update.js --auto,等待安装完成后让用户重新激活 Skill(已加载的 context 不会热更)⚠️ 正在使用旧版本 vA.B.C,可能错过 v5.0+ 的简化流程如果
check-update.js不存在(旧版本安装),跳过版本检查继续工作。 绝对禁止:不输出版本号、隐瞒版本差距、用户没同意就开始复盘流程。
确保以下信息齐全(缺什么问什么):
MM:SS,如 28:01)。必问项,不能标"可选"——Web 端进步趋势图依赖此字段。用户若没计时,明确询问"这套大概做了多久"让其估算,别直接跳过用户发答题截图时必须执行 3 步:
禁止:跳过确认直接写分析、用 answer comparison 覆盖截图标记。
不同 App/平台的答案标记方式各不相同,AI 必须能识别以下所有变体:
| 平台/场景 | 正确标记 | 错误标记 | 额外特征 |
|---|---|---|---|
| 官方答题卡手批 | 绿色/✓ | 红色/✗ | 手写批注 |
| 雅思哥 (IELTSBro) | 绿色圆圈/✓/对号 | 红色圆圈/✗/叉号 | 界面有"答案解析"按钮;题号左侧有状态图标;底部显示得分统计(如 8/13);可能同时显示"你的答案"和"正确答案"两列 |
| 雅思哥成绩单复制文本 | 格式可能为:1. D ✓ 或 Q1: D (正确) | 2. A ✗ → 正确: C 或 Q2: A (错误,正确答案: C) | 复制文本可能包含:题号、用户答案、对错标记、正确答案 |
| 小站雅思 | 蓝色/✓ | 橙色/✗ | 卡片式布局 |
| 新东方雅思 | 绿色背景 | 红色背景 | 答案对比表格 |
| 剑桥官方 CBT | 显示最终得分 | — | 不逐题标记 |
| 其他 App(通用) | ✓/✔/☑/✅/绿色/蓝色 | ✗/✘/☒/❌/红色/橙色 | — |
识别策略(按优先级):
site/answer-key.json 读取正确答案,可辅助验证截图识别结果是否合理(但截图仍是第一真相)🔴 当截图来自第三方 App 时的特殊处理:
用户可能直接从雅思哥 App 复制答案记录粘贴过来,常见格式:
# 格式 A:逐题结果(最常见)
1. TRUE ✓
2. FALSE ✗ (正确答案: NOT GIVEN)
3. NOT GIVEN ✓
4. B ✗ (正确答案: D)
...
# 格式 B:成绩概要
Cambridge 5 Test 1 Reading Passage 1
得分:10/13
错题:Q2, Q7, Q11
# 格式 C:答案对照表
题号 | 我的答案 | 正确答案 | 结果
1 | TRUE | TRUE | ✓
2 | FALSE | NG | ✗
...
解析要点:
site/answer-key.json 补充⚠️ 不再生成复盘 HTML! 后端 review.html 模板页统一渲染 JSON,单独生成 HTML 无用。
直接生成结构化 JSON 文件,供 saveReview API 入库 + 后端 review.html 模板渲染。
输出文件命名规则:剑X-TestX-PassageX-中文主题复盘.json
示例:
剑5-Test1-Passage2-鲸鱼感官复盘.jsonsource.titleCN: "鲸鱼感官"命名说明:文件名使用中文标题(
source.titleCN),方便用户在文件管理器中一眼识别内容。Web 端导入时通过 JSON 内的source.book/test/passage识别篇目,不依赖文件名。
🔴 timing 字段必须填充:
minutes:数值型分钟(支持小数,如 28.0 / 35.4)formatted:"MM:SS" 字符串(如 "28:01")分钟 + 秒/60,保留 1 位小数null,但必须在回复里提醒"缺用时,进步图将缺一个点"{
"version": "4.0.0",
"generatedAt": "2026-04-28T10:00:00.000Z",
"source": {
"book": 7,
"test": 1,
"passage": 3,
"title": "English Title",
"titleCN": "中文标题"
},
"score": {
"correct": 9,
"total": 14,
"band": "6.0",
"breakdown": {
"fillBlank": { "correct": 4, "total": 6 },
"tfng": { "correct": 3, "total": 4 },
"matching": { "correct": 2, "total": 4 }
}
},
"timing": {
"minutes": 25,
"formatted": "25:00"
},
"date": "2026-04-28",
"progressNote": "简短进步总评(如'比上次提升2分')",
"alertNote": "核心告警信息(如'Summary填空全军覆没',可选)",
"answers": [
{ "q": 1, "my": "TRUE", "correct": "TRUE", "result": "correct" },
{ "q": 2, "my": "FALSE", "correct": "NOT GIVEN", "result": "wrong" }
],
"wrongQuestions": [
{
"q": 3,
"type": "tfng",
"badge": "TFNG",
"myAnswer": "TRUE",
"correctAnswer": "NOT GIVEN",
"errorCategory": "ng-false-confusion",
"analysis": "错因分析文字",
"lesson": "教训一句话",
"quote": "原文引用(英文)",
"quoteRef": "Para B, Line 3",
"analysisPoints": ["分析要点1", "分析要点2"]
}
],
"actionItems": [
"下次做 TFNG 前必须标注否定词",
"Summary 填空必须三步走"
],
"synonyms": [
{
"original": "原文表达",
"replacement": "题目表达",
"meaning": "中文释义",
"questionRef": "Q3"
}
],
"vocabulary": [
{
"word": "exemplify",
"phonetic": "/ɪɡˈzemplɪfaɪ/",
"pos": "v.",
"definition": "举例说明",
"ieltsFreq": 3,
"source": "538 #42",
"appearance": "剑7T1P3"
}
],
"problems": [
{
"type": "同义替换识别失败",
"detail": "具体表现",
"questions": "Q3, Q7",
"improvement": "改进方法"
}
]
}
v4.0 相对 v3.0 新增字段(均可选,v3.0 JSON 仍能被模板页渲染):
progressNote:进步总评alertNote:告警信息answers[]:全部答案对照表(含 result: correct/wrong/skipped)actionItems[]:行动清单wrongQuestions[].badge:错误分类简写标签(如 "NG/FALSE混淆"、"过度推理选TRUE"、"Summary填空定位错误"),与 type(题型)区分开wrongQuestions[].quote / quoteRef:原文引用 + 定位wrongQuestions[].analysisPoints[]:分析要点列表🔴 wrongQuestions 中 type 与 badge 的区别(MUST FOLLOW):
type:题型标识,使用标准 ID(tfng / fillBlank / summary / multipleChoice / matching / heading / sentenceCompletion)badge:错误分类标签(如 "NG/FALSE混淆"、"过度推理"、"Summary填空没回原文")error_analysis 只有 error_type(错误分类),没有题型信息,review.html 会从 questions[] 交叉获取题型🔴 answers[] 字段名规范(MUST FOLLOW):
answers 数组中每条记录的字段名必须严格使用以下格式:
{ "q": 1, "my": "TRUE", "correct": "TRUE", "result": "correct" }
my:用户答案(不是 myAnswer)correct:正确答案字符串(不是布尔值)result:"correct" / "wrong" / "skipped"(字符串,不是布尔值)注意:
wrongQuestions[]里用的是myAnswer/correctAnswer(全拼),和answers[]的缩写不同。这是历史设计,review.html 模板已做兼容处理,两种格式都能正确渲染。
⚠️ v5.0 变更(2026-05-11):服务端已预置 C4-C20 100 篇核心双语数据,复盘流程不再需要生成或维护 bilingual_data.json。
仅以下场景需要扩展:
- 复盘 C20 之后的新书(C21+)
- 用户明确要求为某篇生成精翻双语
默认跳过此步骤。
v3.8 起不再需要。旧
bilingual/*.html已清理,Web 端通过bilingual.html模板页动态加载bilingual_data.json渲染。
如果用户明确需要 PDF,可从线上复盘页面打印。本地不再生成 HTML,因此也不支持 puppeteer PDF 生成。
复盘完成后更新 working memory:新增的错误模式、词汇、成绩数据。
复盘 JSON 生成后,必须立即通过 saveReview API 入库(Step 7c),不需要用户手动操作。
完成后输出:
📤 复盘完成!
JSON 已入库,线上查看 👉 review.html?file=剑X-TestX-PassageX-主题复盘.json
方式 B:Skill 伴侣脚本(私有部署场景)
如果有 ielts-server-sync skill(个人专用),可命令行批量上传:
# 单文件上传
node ~/.workbuddy/skills/ielts-server-sync/scripts/upload.js 剑5-T1-P2.json
# 批量上传目录
node ~/.workbuddy/skills/ielts-server-sync/scripts/upload.js --batch ./reviews/
方式 C:手动上传
打开 submit.html?mode=json 拖入 JSON 文件。
🔴 每次复盘完成后,必须逐项执行以下检查清单。不能靠记忆,必须逐条过。
🔀 先看 Step 0a 模式横幅,按模式走对应分支:
site/reviews/generate_vocab_synonym.py 已运行,更新 dict_full.json + synonym_data.jsondict_full.json 中有完整条目(含 meaning_cn + examples)v5.0 变更:
answer-key.json 更新和bilingual_data.json 更新已从清单中移除。服务端已预置 C4-C20 全量数据,复盘流程无需再维护这两个文件。复盘 C21+ 时才需要扩展 answer-key(参考末尾「扩展新书」章节)。
# 词库覆盖校验(复盘生成后必跑)
import json
with open('site/dict_full.json') as f:
dmap = {w['word'].lower(): w for w in json.load(f) if 'word' in w}
with open('site/reviews/剑X-TestX-PassageX-主题复盘.json') as f:
vocab = json.load(f).get('vocabulary', [])
missing = [v['word'] for v in vocab if v['word'].lower() not in dmap]
if missing:
print(f'❌ dict_full.json 缺失 {len(missing)} 词:{missing}')
print('→ 必须补充这些词(含 meaning_cn/examples/synonyms)后再部署')
else:
print('✅ 词库覆盖完整')
如果有缺失词:立即补充到 dict_full.json(每词需含 meaning_cn、phonetic、root、examples、synonyms、antonyms),补完重新部署。 绝不能跳过此步——缺词 = 线上词卡点击无响应 = 用户体验崩坏。
v5.0 精简后只需部署以下 3 个文件(answer-key/bilingual 已服务端预置):
site/reviews/剑X-TestX-PassageX-主题复盘.json → /var/www/ielts/reviews/
site/dict_full.json → /var/www/ielts/
site/synonym_data.json → /var/www/ielts/
🔴 大文件传输规则(>1MB 用 gzip 流,不要分块!):
大于 1MB 的文件(如 dict_full.json ~6MB)禁止直接 SCP,禁止 split 分块,必须用 gzip 管道一行秒传:
# 🔴 唯一正确方式:gzip 流(一行搞定,不分块)
gzip -c site/dict_full.json | ssh openclaw-tunnel "gunzip > /var/www/ielts/dict_full.json"
# 验证完整性
ssh openclaw-tunnel "python3 -c \"import json; d=json.load(open('/var/www/ielts/dict_full.json')); print(f'OK: {len(d)} words')\""
⚠️ 历史教训:split 分块传输复杂且易出错(分批 SCP 超时、拼合顺序错乱),已于 2026-05-08 彻底弃用。gzip 流利用 SSH 隧道的持久连接,一次性完成压缩传输,稳定可靠。
小文件(<1MB)仍可直接 SCP:
scp -o ConnectTimeout=15 \
-o StrictHostKeyChecking=accept-new \
-o UserKnownHostsFile=~/.ssh/known_hosts_cfd \
-o "ProxyCommand=/Users/dengjiawei/bin/cloudflared access tcp --hostname ssh.tuyaya.online" \
-i ~/.ssh/workbuddy.pem \
<本地文件> ubuntu@ssh.tuyaya.online:/var/www/ielts/
或用 SSH stdin 管道(<500KB 的文件最快):
ssh openclaw-tunnel "cat > /var/www/ielts/synonym_data.json" < site/synonym_data.json
复盘数据必须写入后端数据库,否则首页进度图看不到这篇:
ssh openclaw-tunnel 'python3 -c "
import json, urllib.request
payload = json.dumps({
\"action\": \"saveReview\",
\"token\": \"<USER_TOKEN>\",
\"book\": X, \"test\": Y, \"passage\": Z,
\"score\": <correct>, \"total\": <total>, \"duration\": <minutes>,
\"date\": \"YYYY-MM-DD\",
\"answers\": {}
})
req = urllib.request.Request(\"http://localhost:3100/api/ielts\", data=payload.encode(), headers={\"Content-Type\": \"application/json\"})
resp = urllib.request.urlopen(req)
print(resp.read().decode())
"'
API 路径是
POST /api/ielts,通过action字段分发(不是/api/ielts/saveReview)。
如果本次涉及 server 代码变更,需同步后端:
# 后端小文件可直接 stdin 传
ssh openclaw-tunnel "cat > /home/ubuntu/ielts-api/index.js" < server/index.js
# 新增的 lib/ 目录
ssh openclaw-tunnel "mkdir -p /home/ubuntu/ielts-api/lib"
ssh openclaw-tunnel "cat > /home/ubuntu/ielts-api/lib/llmExtractor.js" < server/lib/llmExtractor.js
ssh openclaw-tunnel "cat > /home/ubuntu/ielts-api/lib/schemaUpgrader.js" < server/lib/schemaUpgrader.js
ssh openclaw-tunnel "cat > /home/ubuntu/ielts-api/lib/tencentOcr.js" < server/lib/tencentOcr.js
# 如有新 npm 依赖
ssh openclaw-tunnel "cd /home/ubuntu/ielts-api && npm install"
🔴 部署红线:
/etc/systemd/system/ielts-api.service——里面有 AI_API_URL/KEY/MODEL 等生产密钥/etc/systemd/system/ielts-api.service.d/secrets.conf.workbuddy/upload-upgrade-ops.mdssh openclaw-tunnel "sudo systemctl restart ielts-api"
必须重启——后端启动时 buildReviewFileIndex() 扫描 reviews/ 目录建索引。不重启 = 新文件不出现在首页。
getReadingPageData API 返回新篇目数据(POST /api/ielts + action: getReadingPageData)review.html?file=剑X-TestX-PassageX-主题复盘.jsonbilingual.html?book=X&test=Y&passage=Z血泪教训(2026-05-11):复盘 JSON 部署成功了,但 saveReview API 没调通,导致首页看不到新篇。部署 ≠ 入库,必须回查数据库验证。
完成 7c 后必须立即执行以下检查:
# 用 getReviews 回查本篇是否真的入库(替换 BOOK/TEST/PASSAGE)
curl -s https://tuyaya.online/api/ielts -H 'Content-Type: application/json' \
-d '{"action":"getReviews","token":"<USER_TOKEN>","book":<BOOK>,"test":<TEST>}' \
| python3 -c "
import json,sys
d = json.load(sys.stdin)
records = [r for r in d.get('data',[]) if r['book']==<BOOK> and r['test']==<TEST> and r['passage']==<PASSAGE>]
if records:
print('✅ 入库成功:', records[0])
else:
print('❌ 入库失败!必须重新调 saveReview API')
sys.exit(1)
"
如果验证失败:立即重新调 saveReview API,再回查,直到 ✅。绝对不能跳过此步——本步骤 PASS 才算复盘真正完成。
曾犯的典型遗漏(引以为戒):
my/correct(字符串)/result(字符串),不能用布尔值gzip -c | ssh gunzip > 搞定questions[] 和 error_analysis[] 都有错题时,review.html 会去重。但生成 v4.0 JSON 时应只用 wrongQuestions[],不要同时写两种格式type 是题型(tfng/fillBlank),badge 是错误分类(NG/FALSE混淆)。禁止互相赋值何时走这条:Step 0a 检测到「客户端模式」(如老婆机器、外部用户机器)。
核心原则:客户端没 SSH 凭据、没 /var/www/ielts/ 写权限,只能通过 HTTPS 接口写数据库。词库、模板、双语数据全部由作者机维护,客户端不参与。
让用户选个保存目录(推荐 ~/Documents/雅思复盘/ 或当前工作目录的 reviews/),把生成的 JSON 写进去。不要往 site/reviews/ 写——客户端没这个目录或者目录是别人的。
batchImport 是带 token 的官方 HTTPS 通道,能吃 v4.0 富 JSON(服务端 schemaUpgrader 自动转换扁平字段写入),最适合客户端:
# 单篇上传(推荐用 review-upload skill 的脚本)
bash ~/.workbuddy/skills/ielts-review-upload/scripts/sync-review.sh \
~/Documents/雅思复盘/剑X-TestX-PassageX-主题复盘.json
或者直接 curl:
TOKEN="$IELTS_USER_TOKEN" # 从环境变量读
JSON_FILE="~/Documents/雅思复盘/剑X-TestX-PassageX-主题复盘.json"
PAYLOAD=$(python3 -c "
import json, sys
with open(sys.argv[1]) as f:
review = json.load(f)
print(json.dumps({
'action': 'batchImport',
'token': sys.argv[2],
'reviews': [review]
}, ensure_ascii=False))
" "$JSON_FILE" "$TOKEN")
curl -s -X POST https://tuyaya.online/api/ielts \
-H 'Content-Type: application/json' \
-d "$PAYLOAD"
预期返回:
{"code":0,"message":"导入完成:1 条成功,0 条跳过","data":{"imported":1,"skipped":0,"upgraded":1}}
upgraded:1 表示服务端识别到 v4.0 富格式并跑了 schemaUpgrader。
curl -s https://tuyaya.online/api/ielts \
-H 'Content-Type: application/json' \
-d "{\"action\":\"getReviews\",\"token\":\"$IELTS_USER_TOKEN\",\"book\":<BOOK>,\"test\":<TEST>}" \
| python3 -m json.tool | head -30
确认返回的 data 数组里有刚上传那篇(book/test/passage 三元组匹配),并且 username 是登录账号(如 lishuzhuo),不是 dengjiawei。
✅ 复盘已入库
📊 在主页查看进度图、词汇本、错题本:
👉 https://tuyaya.online/ielts/reading.html
(登录账号:<username>)
📄 复盘详情页:
👉 https://tuyaya.online/ielts/review.html?file=剑X-TestX-PassageX-主题复盘.json
客户端模式注意:复盘详情页
review.html?file=...依赖服务端/var/www/ielts/reviews/下的 JSON 文件。客户端模式只把数据写进数据库,不上传 JSON 文件到服务器,所以详情页可能 404。但首页进度图、词汇本、错题本能正常工作(这些数据都从数据库读)。如果用户特别想要详情页可访问,提醒他把 JSON 发给作者人工部署,或者作者机用
ielts-server-syncskill 同步。
ssh openclaw-tunnel ...scp ... ubuntu@ssh.tuyaya.online:...gzip -c | ssh openclaw-tunnel "gunzip > /var/www/..."sudo systemctl restart ielts-apidict_full.json / synonym_data.json / bilingual_data.json / answer-key.json 后试图部署site/reviews/ 下的 JSON 文件到服务器客户端只做两件事:本地存 JSON + HTTPS batchImport 入库。
如果用户首次跑客户端模式,缺 IELTS_USER_TOKEN,按以下流程引导:
localStorage.token,回车,复制返回字符串(一长串 base64)~/.zshrc 末尾加:
export IELTS_USER_TOKEN='粘贴token'
source ~/.zshrc 或重开终端echo "${IELTS_USER_TOKEN:0:20}..." 应输出前 20 个字符token 默认有效期 10 年,配一次基本一劳永逸。
服务端预置数据仅覆盖 C4-C20。复盘剑21及以后的书时,需要额外做:
site/answer-key.json 追加条目(格式:C{book}-T{test}-R{passage},R 不是 P)/var/www/ielts/answer-key.jsonsite/bilingual_data.json 并 SCPssh openclaw-tunnel "sudo systemctl restart ielts-api"C4-C20 范围内的复盘不需要这一步。
触发场景:用户说"帮我把 XX 目录下的历史复盘都转成 JSON"、"批量导入我以前的复盘笔记"、"扫一下我电脑里的复盘"、"帮我找出所有历史笔记"等。
此模式下 Buddy 自主循环,无需用户自己找路径、无需一篇篇喂。
不要开口就问用户"复盘文件夹在哪?"——先自动扫常见位置:
node ~/.workbuddy/skills/ielts-reading-review/scripts/scan-legacy-reviews.js --auto
脚本会扫描以下位置并按命中数推荐:
~/Documents、~/Documents/个人、~/Documents/个人/WorkBuddy~/Desktop、~/Downloads~/Library/Mobile Documents/com~apple~CloudDocs(iCloud)~/WorkBuddy、~/WorkBuddy/Claw输出 discoveries(去重后的真实命中目录,命中数多的子目录优先)和 recommended(首选目录)。
把发现结果呈现给用户:
我扫了你电脑常见位置,找到你的复盘应该在这里:
🎯 推荐:/Users/xxx/Documents/个人/WorkBuddy/雅思学习(60 个候选文件)
样例:剑6-Test3-Passage3-抗衰老药物复盘.html / 剑4-Test1-听力Part2-河滨工业村复盘.html …
其他候选:
- /Users/xxx/Downloads(4 个)
要用推荐目录还是选其他的?
用户点头后进入 Step B1 做精扫。只有当自动发现完全找不到候选(discoveries 为空)时,才问用户要具体路径。
调用扫描脚本生成候选清单:
# 默认只扫顶层
node ~/.workbuddy/skills/ielts-reading-review/scripts/scan-legacy-reviews.js <目录> --out=/tmp/ielts-scan.json
# 需要递归子目录
node ~/.workbuddy/skills/ielts-reading-review/scripts/scan-legacy-reviews.js <目录> --deep --out=/tmp/ielts-scan.json
输出 JSON 结构(groups 按篇目聚合):
{
"totalFiles": 18,
"identifiedPassages": 6,
"groups": [
{
"passage": "C5-T1-P2",
"fileCount": 3,
"files": [
{ "path": "...", "ext": ".html", "hints": { "book": 5, "test": 1, "passage": 2, "title": "鲸鱼感官" } },
{ "path": "...", "ext": ".md" },
{ "path": "...", "ext": ".png" }
]
},
{ "passage": "__unknown__", "files": [...] }
]
}
读取 scan 结果后,必须先给用户一份执行计划,不要直接开干:
扫描完成,找到 18 个候选文件,识别出 6 篇复盘:
✅ 可识别:
1. 剑5-T1-P2 · 鲸鱼感官(HTML + MD + 截图,共 3 个文件)
2. 剑5-T1-P3 · 儿童认知(HTML)
3. 剑6-T2-P1 · ...
...
⚠️ 无法识别篇目(需你人工分配):
- notes-2026-03-15.md
- 错题整理.docx
我将逐篇处理可识别的 6 篇,每篇生成一个 JSON。预计 10-15 分钟。
确认开始?
用户点头后才进入 Step B3。
逐篇循环,每次处理一组:
site/answer-key.json(本地答案库,401 题全覆盖)score.correct = null 让用户后续补wrongQuestions: []剑X-TestX-PassageX-中文主题复盘.json./batch-output/)✅ [3/6] 剑5-T1-P3 · 儿童认知 → 剑5-Test1-Passage3-儿童认知复盘.json全部完成后输出总结:
批量导入完成!
✅ 成功:5 篇(已生成 5 个 JSON 到 ./batch-output/)
⚠️ 部分数据缺失:1 篇(剑6-T2-P1 找不到用户答案,score.correct 置空)
❌ 跳过:0 篇
下一步:
👉 打开 https://tuyaya.online/ielts/submit.html?mode=json
👉 把 ./batch-output/ 里所有 JSON 拖进去,一键导入
site/answer-key.json 核对,笔记里的可能是老婆写错的./batch-output/,不污染用户工作目录关键区分:
however + adj = no matter how(让步),不是因果such as ___ → 必须填具体例子the ___ of X → 必须填能和 "of X" 搭配的名词参见 references/error-taxonomy.md,共 18 类错误分类。JSON 中 errorCategory 字段使用以下 ID:
| ID | 错误类型 |
|---|---|
synonym-failure | 同义替换识别失败 |
ng-false-confusion | NOT GIVEN / FALSE 混淆 |
over-inference | 过度推理 |
stem-repetition | 填空重复题干词 |
grammar-mismatch | 语法/让步句理解错 |
incomplete-option | 选项不完全匹配 |
vocab-gap | 词汇缺口 |
carelessness | 粗心/时间压力 |
word-form-error | 填空词形/词性错 |
scope-confusion | 跨代/范围混淆 |
category-reasoning | 类别推理误判 |
adjacent-distractor | 邻近干扰词 |
heading-example-reuse | Heading匹配复用Example已用选项 |
concessive-clause-confusion | Although/While让步从句混淆主句 |
double-negative-misread | 双重否定读不出肯定 |
summary-no-source | Summary填空没回原文定位 |
comparison-signal-ignored | 对比信号词(difference from等)忽略 |
selection-contradicts-thesis | 选择题选了和全文论点矛盾的选项 |
任何复盘对话,在你即将给出收尾回复("复盘完成 / 总结 / 错题分析全部跑完")之前,必须先逐条过完以下 4 个 Gate。任何一条 ❌ 一律返回继续干,禁止结束。
| Gate | 自检问题 | 判定来源 |
|---|---|---|
| Gate 1 | 我有没有为本次每一篇生成 v4.0 富 JSON 写到 site/reviews/? | ls site/reviews/ 看到对应文件 |
| Gate 2 | 我有没有调 saveReview(作者模式)或 upload.js/batchImport(客户端模式)? | 看上面命令的返回值是 success/code:0 |
| Gate 3 | 我有没有用 getReviews 回查确认入库 ✅? | 回查 JSON 里有匹配 book/test/passage 的 record |
| Gate 4 | 我有没有把线上链接(tuyaya.online/ielts/review.html?file=...)写进给主人的最终回复? | 检查最终回复文本 |
自检模板(在收尾前内部默念一遍):
Gate 1: site/reviews/剑X-TestX-PassageX-主题复盘.json ✅ / ❌
Gate 2: saveReview / upload.js ✅ / ❌
Gate 3: getReviews 回查命中 ✅ / ❌
Gate 4: 最终回复包含线上链接 ✅ / ❌
若任意一条 ❌:立即回到对应 Step 补做,绝不允许"先交付文字版,再说"。
作者机一键回查命令(复制即用):
TOKEN=$(cat ~/.ielts-tuyaya-token | python3 -c "import json,sys; print(json.load(sys.stdin)['token'])")
curl -s 'https://tuyaya.online/api/ielts' -H 'Content-Type: application/json' \
-d "{\"action\":\"getReviews\",\"token\":\"$TOKEN\",\"book\":<BOOK>,\"test\":<TEST>}" \
| python3 -c "import json,sys; d=json.load(sys.stdin); recs=[r for r in d.get('data',[]) if r['book']==<BOOK> and r['test']==<TEST>]; print('✅ 已入库篇目:', [(r['passage'], r['score'], r['total']) for r in recs])"
若主人对话里只发了某一两篇阅读题:完成那几篇的 4 个 Gate 即可,不要扩展到整个 Test。
若做完一篇主人立刻发下一篇:先把当前篇 4 Gate 全过 ✅,再开下一篇。绝对不允许积压。
这道 Gate 是 v5.4.2 的灵魂。其他所有 step 都可以小幅偷懒,唯独这道 Gate 必须 100% 过完。
外部用户/老婆机器首次配置看这里:references/CLIENT_MODE_ONBOARDING.md
一键脚本:bash ~/.workbuddy/skills/ielts-reading-review/scripts/setup-client-mode.sh