dataset-doctor · git:20260727.807afb6 · 2026-07-27 · sha256 230acea9dee45012
dataset-doctor git:20260727.807afb6A
Immutable. This exact content never changes and is served at /api/v1/blob/230acea9dee45012.
---
name: dataset-doctor
description: Audit a LoRA training dataset and its captions before training on lora-scripts-next / SD-Trainer (Anima-first), and fix the findings with safe one-line commands. Use when the user wants to check / validate / inspect / fix / clean / 体检 / 修 a dataset, captions, or tags for LoRA training — image count, repeats and the training step budget, resolution and aspect-ratio buckets, duplicate or corrupt or non-RGB images, missing or empty or inconsistent captions, trigger-word consistency, and tag-frequency distribution. Runs read-only scan scripts, returns a PASS / WARN / FAIL readiness report with prioritized fixes, and applies confirmed fixes via fix_dataset.py (dry-run by default; originals quarantined, never deleted), including WD14 re-tagging via the trainer API.
---
# dataset-doctor — LoRA 数据集 / caption 体检 + 修复
在训练前对 LoRA 数据集与标注做质量体检,给出 **PASS / WARN / FAIL** 结论和按优先级排序的修复建议;确认后用 `fix_dataset.py` 一行命令执行修复。**体检只读**;修复**默认 dry-run**,加 `--apply` 才动文件,且**从不删除**——被移除的文件全部进数据集内的 `_quarantine/`(体检与训练都会忽略它),随时可还原。任何 `--apply` 都必须先得到用户确认。
底层针对 `lora-scripts-next`(SD-Trainer)的数据集约定:`train_data_dir` 下放 `<repeats>_<concept>` 子文件夹(如 `7_zkz` = 重复 7 次、概念 `zkz`),caption 是与图同名的 sidecar `.txt`——**单行**、逗号分隔、可在末尾用「`. `」接自然语言(已验证格式见 `../references/caption-guide.md`)。Anima `.json` caption 仅是 UI 宣称的可选项,训练端 v2.7.0 未发现读取实现,不要依赖。
## 默认职责
接收一个数据集路径,运行体检脚本,解读 JSON/报告,向用户说明问题与修复顺序;用户确认后用 `fix_dataset.py` 执行修复并重检。trainer 本身**只检查目录是否存在、有没有图**,不检查质量——质量这块由本 skill 负责,二者互补。
## 适用范围(不限 SD-Trainer)
体检与修复是**训练器无关**的:检查对象是标准 kohya 数据集约定(`<repeats>_<concept>` 文件夹 + 同名 sidecar caption),sd-scripts / kohya_ss / OneTrainer 等训练器通用;脚本全程离线、不碰 GPU、不需要 trainer 在线。用户打算在**任何**训练器上练 LoRA,体检都照做。只有两处例外:
- **WD14 打标**走 SD-Trainer 的 `POST /api/interrogate`——trainer 不在线/不存在时,改为建议用户用本地 tagger 打标,打完回来重检,不要因此跳过 caption 检查。
- **Anima `.json` caption 校验**只对已经持有 `.json` 标注的数据集有意义,且 `.json` 是否真被训练端读取**未经验证**(v2.7.0 本地代码中无读取实现)——一律建议以 `.txt` 为准;用户练 SD1.5/SDXL/Flux 或用别的训练器时,`json_structure` 问题可降级为忽略。
## 触发与分支
有「训练前检查数据集 / caption / tag 质量」意图时触发:体检、检查数据集、看看标注、tag 有没有问题、能不能开训、trigger 一致吗、有没有重复图、步数够不够。
- 只是要**自动打标**(还没标注)→ 直接走打标(`POST /api/interrogate`,见 `../references/trainer-api.md`),打完再回来体检。
- 要**开始训练 / 调参** → 交给 `lora-trainer`;它会在开训前调用本 skill 作为闸门。
- 要查 caption 怎么写 / trigger 怎么取 → 读 `../references/caption-guide.md`。
## 读取导航
| 需要处理的事 | 读取 / 执行 |
| --- | --- |
| 跑一次完整体检(默认) | `scripts/doctor.py`(见「运行体检」) |
| 修复体检发现的问题(dry-run → 确认 → `--apply`) | `scripts/fix_dataset.py`(见「修复手册」) |
| 只看图像层面问题 | `scripts/scan_dataset.py` |
| 只看 caption / tag 问题 | `scripts/check_captions.py` |
| caption 格式、trigger、JSON 结构 | `../references/caption-guide.md` |
| 打标 / 重打标 API | `../references/trainer-api.md` |
| 训练参数与步数预算 | `../references/anima-params.md` |
## 运行体检
脚本依赖 **Pillow**(纯 stdlib + Pillow,无需 numpy)。用一个装了 Pillow 的 Python 运行——trainer 自带的 embedded Python 最稳妥:
- 本机示例:`C:\SD-Trainer\python_embeded\python.exe`
- 通用:任何 `python`(缺 Pillow 时 `pip install pillow`)
主入口 `doctor.py`(同时跑 scan + caption 并给总结论):
```powershell
& "<PYTHON>" "<SKILL_DIR>/scripts/doctor.py" "<TRAIN_DATA_DIR>" `
--trigger <TRIGGER> --epochs <N> --batch-size <B> --target-reso 1024,1024 --json
```
- `<TRAIN_DATA_DIR>`:`<repeats>_<concept>` 的**父目录**(也可直接指向某个概念子文件夹)。
- `--trigger`:预期的触发词;不给则脚本会**推断**一个候选。
- `--epochs/--batch-size`:用于算总步数预算(可选但推荐)。
- 输出:`--json`(机器读,含 `verdict` / `summary` / `recommendations` / `scan` / `captions`)、`--report`(人读 Markdown)、默认两者都打印。
- 退出码:PASS/WARN = 0,FAIL = 2。
需要分别看时用 `scan_dataset.py` / `check_captions.py`,参数同名。
## 解读结论
- **FAIL(critical)**:有图无法解码(会让训练崩)、根本没有图。**必须先修,禁止开训。**
- **WARN(high/medium)**:缺 caption、**多行 caption(训练端只读第一行)**、trigger 不一致、重复图、非 RGB、低于训练分辨率、过/欠标、artifact tag、JSON 结构错。**可训,但先把建议过一遍并向用户确认。**
- **PASS(low/info 或无)**:可以训。
按 `recommendations`(已按严重度排序、去重)逐条处理。`scan.issues` / `captions.issues` 里每条都带 `code`、`message`、`fix`、`items`(示例文件,最多 12 个)。
## 修复手册(对应 issue code)
`fix_dataset.py` 与 `doctor.py` 用同一个 Python 运行。**所有命令默认 dry-run**(只打印计划),把计划摊给用户、确认后**同一条命令加 `--apply`** 执行。被移走的文件进 `<dataset>/_quarantine/`,不删除。
```powershell
& "<PYTHON>" "<SKILL_DIR>/scripts/fix_dataset.py" <command> "<TRAIN_DATA_DIR>" [选项] [--apply]
```
| code | 修复命令 |
| --- | --- |
| `no_concept_folders` | `fix_dataset.py organize <dir> --repeats <R> --concept <name>` |
| `corrupt_images` | `fix_dataset.py quarantine-corrupt <dir>` |
| `exact_duplicates` | `fix_dataset.py dedupe <dir>`(保留分辨率最高的一张) |
| `near_duplicates` | `fix_dataset.py dedupe <dir> --near` |
| `non_rgb_mode` | `fix_dataset.py to-rgb <dir>`(原件备份进 `_quarantine/`) |
| `trigger_inconsistent` | `fix_dataset.py add-trigger <dir> --trigger <T>`(.txt 提到首位;.json 写 `character`) |
| `artifact_tags` / `duplicate_tags` | `fix_dataset.py strip-tags <dir>`(可加 `--tags "a,b"` 一并删指定 tag) |
| `multiline_caption` | 训练端只读 `.txt` 第一行,后续行**静默丢失**。手动把每个 caption 合并成单行:tag 在前、`. ` 接自然语言(格式见 `../references/caption-guide.md`) |
| `ubiquitous_tags` | 先核对哪个是有意的 trigger,其余用 `strip-tags --tags "..."` 删 |
| `missing_captions` / `empty_captions` | WD14 打标:`POST /api/interrogate`,`additional_tags=<TRIGGER>`,`batch_output_action_on_conflict="ignore"`(不覆盖已有) |
| `below_target_resolution` / `tiny_images` | 换更高分辨率源;`bucket_no_upscale` 下小图细节受限(无自动修复) |
| `mixed_repeats` | 核对各概念「有效图片数」比例是否符合预期(无需修复) |
打标 / 修复后,**重新跑一次 `doctor.py`** 确认问题已清。误修了想还原 → 把 `_quarantine/` 里的文件移回原位即可。
## 自检
1. 路径指向的是 `train_data_dir`(`<repeats>_<concept>` 的父目录),不是散图目录;散图会触发 `no_concept_folders`。
2. 用了带 Pillow 的 Python;脚本能正常输出 JSON。
3. 已知 trigger 时传了 `--trigger`,并核对 `trigger.presence_pct` / `first_position_pct`。
4. 解读了 `verdict` 并按 `recommendations` 顺序给建议。
5. 任何 `fix_dataset.py --apply` / 打标操作**已先 dry-run 摊牌并取得用户确认**;从不手写删除命令,从不直接删文件(一律走 `_quarantine/`)。
6. 修复后重跑体检确认。
## 可验证案例
用户:训练前帮我看看 `D:/data/marin`(trigger 是 `m4r1n`,打算 10 epoch)。
```powershell
& "C:\SD-Trainer\python_embeded\python.exe" `
"<SKILL_DIR>/scripts/doctor.py" "D:/data/marin" --trigger m4r1n --epochs 10 --report
```
读 `verdict`:若 WARN 且 `missing_captions`+`exact_duplicates`,则:① 提议用 WD14 给缺标的图打标(trigger 放 `additional_tags`);② `fix_dataset.py dedupe "D:/data/marin"` dry-run 列出重复组 → 用户确认 → 加 `--apply`(被移除的进 `_quarantine/`);③ 修完重跑体检;④ PASS 后把数据集 + 建议的 repeats/epochs 交给 `lora-trainer`。
## 执行交接
- 体检与修复在本 skill;**实际开训、组装 config、`POST /api/run`、监看 SSE log 交给 `lora-trainer`。**
- 打标执行细节(端点、字段、轮询)见 `../references/trainer-api.md`;caption 写法见 `../references/caption-guide.md`。
- 本 skill 不自行启动训练;修复一律 dry-run 先行、确认后 `--apply`、移除走 `_quarantine/` 不删除。