先理解:清洗是为了让知识可被信任
原始文档通常不适合直接给 AI 用:标题不统一、内容重复、版本混乱、负责人缺失。清洗不是美化排版,而是把文档变成机器能稳定处理、人能追溯责任的知识条目。
本篇把 Markdown 文档转换成 JSONL。每行代表一条可入库知识,并带上分类、负责人、权限、版本等元数据。
元数据不要贪多
第一版只保留真正会用到的字段:id、title、category、owner、visibility、version、updated_at。字段太多会增加维护成本,最后大家会乱填或不填。
清洗后的抽检
脚本跑完后一定要人工抽检。看标题是否完整、分类是否合理、权限是否正确、内容是否被截断。自动化脚本负责效率,人工抽检负责方向。
本篇把原始 Markdown 文档转换成结构化 JSONL。每条 JSONL 是一个知识块,带来源、权限、版本和负责人。
本篇成品
text
docs/after_sales_policy.md
processed/chunks.jsonl
tools/process_docs.py样例文档
docs/after_sales_policy.md:
md
# 售后政策
owner: 客服运营
version: 2026.04
permission: internal
domain: business
topic: after_sales
## 七天无理由退货
签收后 7 天内,商品未拆封、配件齐全,可申请无理由退货。
## 免费保修
保修期内的非人为性能故障可申请免费检测。进水、摔落、私拆不属于免费保修范围。处理脚本
tools/process_docs.py:
python
import hashlib
import json
import re
from pathlib import Path
DOC_DIR = Path("docs")
OUT = Path("processed/chunks.jsonl")
def clean(text: str) -> str:
return re.sub(r"\n{3,}", "\n\n", text).strip()
def doc_id(path: Path, text: str) -> str:
digest = hashlib.sha1(text.encode("utf-8")).hexdigest()[:10]
return f"{path.stem}-{digest}"
def parse_metadata(lines: list[str]) -> tuple[dict, list[str]]:
meta = {}
body_start = 0
for i, line in enumerate(lines):
if ":" in line and not line.startswith("#"):
key, value = line.split(":", 1)
meta[key.strip()] = value.strip()
elif line.startswith("## "):
body_start = i
break
return meta, lines[body_start:]
def split_sections(body: str) -> list[str]:
parts = re.split(r"\n(?=## )", body)
return [clean(p) for p in parts if len(clean(p)) > 20]
def main():
OUT.parent.mkdir(parents=True, exist_ok=True)
rows = []
for path in DOC_DIR.glob("*.md"):
lines = path.read_text(encoding="utf-8").splitlines()
meta, body_lines = parse_metadata(lines)
for section in split_sections("\n".join(body_lines)):
rows.append({
"id": doc_id(path, section),
"text": section,
"source": str(path),
"owner": meta.get("owner"),
"version": meta.get("version"),
"permission": meta.get("permission"),
"domain": meta.get("domain"),
"topic": meta.get("topic"),
"quality_status": "draft",
})
OUT.write_text("\n".join(json.dumps(r, ensure_ascii=False) for r in rows), encoding="utf-8")
print(f"wrote {len(rows)} chunks")
if __name__ == "__main__":
main()执行和验收
bash
mkdir -p tools processed
python tools/process_docs.py
head -n 1 processed/chunks.jsonl每条记录必须包含:
idtextsourceownerversionpermissiondomaintopic
缺少这些字段的文档不要进入正式索引。

