设备操作手册写成 AI 能复述的步骤:HowTo 与 HowToStep 的结构化落地实战
一台 CNC 分中仪的操作手册在官网挂了三年,百度排名不错,客户在 ChatGPT 里问「怎么给三轴加工中心做分中」,回答里却推荐了同行的型号——因为同行的手册页做了 HowTo 结构化标注,机器读得懂「第几步、用什么工具、耗时多久」。这个场景发生在 2026 年 4 月,我们复盘时发现,生成式引擎优化(Generative Engine Optimization, GEO)在设备行业的分水岭,往往就是有没有把手册拆成机器可复述的步骤。
传统 SEO 争夺的是「排第几」,GEO 争夺的是「AI 回答里引用谁」。当客户把问题抛给豆包、DeepSeek 或 Kimi,模型倾向引用结构清晰、步骤完整、参数明确的页面。设备操作手册天然具备这种素质,只是大多数厂商把它当 PDF 附件扔在下载页,AI 爬虫连正文都抓不到。本文记录我们把三条产品线的手册页改造成 HowTo Schema 的完整过程,包括踩过的坑。
一、先搞清楚 HowTo Schema 是什么结构
1.1 与普通文章页的差异

Schema.org 里的 HowTo 类型专门描述「完成一件事的步骤序列」,与 Course、Recipe 并列,但常被误用成 Article 或 BlogPosting。模型在解析时,HowTo 有明确的字段契约:step 数组、每一步的 name 与 text、可选的 HowToDirection 指令明细、tool 工具清单、supply 耗材清单、totalTime 总耗时。字段越完整,模型越容易「复述」——把你的第 1 步到第 8 步原样搬进回答,还带一句「参考某某厂商的官方手册」。
一个合格的 HowTo 页面,结构大致是这样的:
graph TD
A[HowTo 主对象] --> B[name 手册标题]
A --> C[totalTime 总耗时 ISO8601]
A --> D[tool 工具清单]
A --> E[supply 耗材清单]
A --> F[step 步骤数组]
F --> G[HowToStep 1]
F --> H[HowToStep 2]
F --> I[HowToStep n]
G --> J[name 步骤名]
G --> K[text 操作正文]
G --> L[itemListElement HowToDirection]
G --> M[image 步骤配图]
1.2 原理与机制:AI 爬虫怎么读你的步骤
生成式引擎抓取流程和传统搜索引擎有三个不同点,这是整个改造的机制基础:
- 解析目标不同。传统爬虫做倒排索引,关心关键词分布;AI 爬虫(如 GPTBot、字节 Bytespider)做语义压缩,目标是把页面变成可注入模型的训练或检索片段。JSON-LD 里的嵌套结构就是现成的语义树,模型不需要自己猜「这段是步骤还是注意事项」。
- 引用带溯源。ChatGPT 的 Search 模式和 DeepSeek 联网搜索会优先引用带明确实体标注的页面。当
tool里写着「百分表 0.01mm 精度」,模型在回答精度相关问题时能直接提取这个数字,引用概率显著高于一段纯散文。 - 步骤完整性影响召回。我们在日志里看到,AI 爬虫对 HowTo 页的抓取深度普遍到
step数组末尾,而普通长文经常在第三屏截断。totalTime和estimatedCost这类「总结性字段」相当于告诉压缩器「到此为止,内容闭环了」。
一句话原则:手册页不是写给客户逐字看的,是写给「客户问 AI 时,AI 拿去组织回答」用的。想通这一点,字段取舍就清楚了。
二、改造前后:JSON-LD 代码对比
拿三轴加工中心分中仪调试流程做例子。改造前的页面只有一段普通 Article 标注,步骤全混在正文 HTML 里。
改造前(问题版,字段缺失 + 结构扁平):
{
// 错误1:类型用了 Article,AI 无法识别这是步骤型内容
"@context": "https://schema.org",
"@type": "Article",
"headline": "CNC 分中仪安装调试手册",
// 错误2:步骤内容没拆出来,全堆在 articleBody
"articleBody": "第一步先安装夹具,第二步连接信号线,第三步开机校准……",
// 错误3:只有整页一张图,步骤级配图缺失
"image": "https://example.com/manual-cover.jpg",
// 缺 tool/supply/totalTime,模型拿不到工具与耗时信息
// 缺 step 数组,步骤语义全靠模型自己猜
"author": { "@type": "Organization", "name": "设备厂技术部" }
}
改造后(HowTo 完整结构,可直接通过 Rich Results Test):
{
// @context 固定写 schema.org,别写带版本号的地址
"@context": "https://schema.org",
"@type": "HowTo",
// 手册标题要含具体设备型号,模型按型号实体检索
"name": "CNC-302 分中仪安装调试手册(三轴加工中心)",
// totalTime 用 ISO 8601 格式,2小时30分
"totalTime": "PT2H30M",
// tool 是可复用工具,安装完还留在机床上
"tool": [
{ "@type": "HowToTool", "name": "百分表(0.01mm 精度)" },
{ "@type": "HowToTool", "name": "内六角扳手 4mm" }
],
// supply 是耗材,装一次消耗一次
"supply": [
{ "@type": "HowToSupply", "name": "M6 内六角螺栓 ×4" },
{ "@type": "HowToSupply", "name": "防松螺纹胶" }
],
// image 建议给 1200x675 以上的成品图
"image": "https://example.com/cnc302/setup-overview.jpg",
// step 是数组,顺序即执行顺序,别乱放
"step": [
{
"@type": "HowToStep",
// position 必须连续编号,断号会被判结构错误
"position": 1,
"name": "安装磁性基座",
// text 写「做了什么+做到什么程度」,不要写原理
"text": "用内六角扳手将磁性基座固定在主轴端面,四颗 M6 螺栓按对角顺序拧紧至 8N·m。",
// 步骤级配图,URL 不重复且能直接 200 打开
"image": "https://example.com/cnc302/step1-base.jpg",
// direction 是步骤内的原子指令,模型复述时会逐条引用
"itemListElement": [
{
"@type": "HowToDirection",
// 指令写「动作+判定标准」,别写成解释性文字
"text": "确认主轴端面无油污,用无纺布擦拭干净。"
},
{
"@type": "HowToDirection",
// 带量化验收指标,模型引用时数字最容易被保留
"text": "基座吸附后手动拉动检查,位移不得超过 0.02mm。"
}
]
},
{
"@type": "HowToStep",
"position": 2,
"name": "连接信号线并校准零位",
// text 里带接口位与操作入口,模型引用更具体
"text": "将信号线接入控制器 COM2 口,上电后在示教界面执行零位校准。",
// 每步都要有图,缺图会拉低步骤引用权重
"image": "https://example.com/cnc302/step2-signal.jpg",
"itemListElement": [
{
"@type": "HowToDirection",
// 接地细节这类高频报错点,务必写成 direction
"text": "信号线屏蔽层单端接地,接控制器侧。"
}
]
}
]
// 完整字段跑一遍 validator.schema.org 再上线
}
改造前后差异用表格汇总:
| 对比项 | 改造前 | 改造后 |
|---|---|---|
| Schema 类型 | Article | HowTo |
| 步骤表达 | articleBody 里一段散文 | HowToStep 数组,position 连续 |
| 指令粒度 | 无 | HowToDirection 原子指令 |
| 工具/耗材 | 无 | tool / supply 独立字段 |
| 耗时信息 | 无 | totalTime: PT2H30M |
| 图片 | 整页 1 张封面图 | 步骤级 image + 封面图 |
| AI 可复述性 | 模型只能意译 | 可逐步骤原样引用 |
这一步是整个 GEO 改造里投入产出比最高的动作:不需要改页面设计,只需要在 <head> 里注入一段 JSON-LD。
三、批量输出:用 Python 从手册源文件生成 Schema
四十多台设备、每台一本手册,手工写 JSON-LD 不现实。我们把手册源文件统一成带 front matter 的 Markdown,用一个 Python 脚本批量产出 Schema 片段,构建时注入页面模板。
依赖与环境:Python 3.11+,pyyaml 6.0、jinja2 3.1,手册源文件放在 manuals/ 目录,每个文件用 YAML 头声明型号、步骤、工具。
# -*- coding: utf-8 -*-
# 依赖:pyyaml==6.0.2 jinja2==3.1.4 Python 3.11+
# 用途:批量把 Markdown 手册转成 HowTo JSON-LD
import json
import re
from pathlib import Path
import yaml
# 手册源文件目录与 JSON-LD 输出目录
MANUAL_DIR = Path("manuals")
OUT_DIR = Path("output/schema")
def parse_step_block(text: str, position: int) -> dict:
# 按空行切分出步骤内的原子指令行
directions = [ln.strip(" -") for ln in text.splitlines() if ln.strip().startswith("- ")]
# 每个步骤取首个"## 步骤n"标题作为 name
name_match = re.search(r"##\s*步骤(\d+)[::]\s*(.+)", text)
return {
"@type": "HowToStep",
# position 必须从 1 开始连续,脚本里强校验
"position": position,
"name": name_match.group(2).strip() if name_match else f"步骤{position}",
# 正文段落去掉列表行后作为 text,超 500 字截断
"text": re.sub(r"^##.*$|^- .*$", "", text, flags=re.M).strip()[:500],
# 指令列表逐条包装成 HowToDirection
"itemListElement": [
{"@type": "HowToDirection", "text": d} for d in directions
],
}
def build_howto(md_path: Path) -> dict:
raw = md_path.read_text(encoding="utf-8")
# YAML 头与正文以 --- 分隔,拆出元数据
_, meta, body = raw.split("---", 2)
meta = yaml.safe_load(meta)
# 用正向前瞻切步骤,不吞分隔符
steps_raw = [s for s in re.split(r"(?=##\s*步骤\d+)", body.strip()) if s.strip()]
return {
"@context": "https://schema.org",
"@type": "HowTo",
# 名称拼上具体型号,模型按型号实体检索
"name": f"{meta['model']} {meta['title']}",
# YAML 头里的耗时分钟数转 ISO 8601
"totalTime": f"PT{meta['total_minutes']}M",
# 工具与耗材分别包装,别混进 step
"tool": [{"@type": "HowToTool", "name": t} for t in meta.get("tool", [])],
"supply": [{"@type": "HowToSupply", "name": s} for s in meta.get("supply", [])],
"image": meta.get("cover", ""),
# 步骤数组按出现顺序编号
"step": [parse_step_block(s, i + 1) for i, s in enumerate(steps_raw)],
}
def main() -> None:
OUT_DIR.mkdir(parents=True, exist_ok=True)
# 遍历所有手册文件,逐个生成并落盘
for md in sorted(MANUAL_DIR.glob("*.md")):
data = build_howto(md)
# 拼 script 注入片段,json.dumps 关掉 ASCII 转义
snippet = ('<script type="application/ld+json">\n'
+ json.dumps(data, ensure_ascii=False, indent=2) + "\n</script>")
# 输出文件名与手册源文件同名,方便回溯
(OUT_DIR / f"{md.stem}.html").write_text(snippet, encoding="utf-8")
# position 连续性自检,断号直接抛错阻断构建
positions = [s["position"] for s in data["step"]]
assert positions == list(range(1, len(positions) + 1)), f"{md.name} 步骤编号断裂"
# 直接 python build_howto_schema.py 即可全量执行
# 单本调试时只传一个文件名即可,别全量重跑
main()
跑一遍全量手册约 1.8 秒输出 43 个片段,接进静态站点生成器之后,每本手册页的 <head> 自动带上结构化数据。如果站点是 ASP.NET Core,思路相同:把手册数据放数据库,用 System.Text.Json 序列化后通过 TagHelper 输出,[JsonPropertyName("@type")] 处理 @ 字符即可。
四、常见校验错误与排查
上线前必须过 Google Rich Results Test 和 validator.schema.org 两道检查。我们第一轮提交时 43 个页面里 11 个报错,问题集中在四类:
| 错误信息 | 触发原因 | 排查方法 |
|---|---|---|
| Missing field "position" 或编号断裂 | 步骤手工增删后没重排 | 脚本里加连续性断言,见上节 |
| Invalid value in field "image" | 用了相对路径或防盗链图床 | 图片走自有域名,直出 200 |
| HowToStep 嵌套在 HowToSection 外 | 把 direction 写成了 step 的 step | direction 只能挂在 step 的 itemListElement 下 |
| "totalTime" 不符合 ISO 8601 | 写成了「2.5小时」这类中文表述 | 统一用 PT#H#M 格式 |
其中嵌套错误最隐蔽:编辑把「注意事项」当独立 step 塞进数组,模型复述时会把注意事项当成操作步骤念出来,客户照做直接懵。我们的处理是约定——step 数组只放有先后顺序的动作,注意事项降级为 HowToTip 挂在对应步骤内。
整条改造流水线如下图:
flowchart LR
A[Markdown 手册源文件] --> B[Python 批量脚本]
B --> C{结构校验}
C -- 断号/缺字段 --> D[阻断构建并报警]
C -- 通过 --> E[注入页面 head]
E --> F[Rich Results Test 抽检]
F --> G[提交站点地图]
G --> H[等待 AI 爬虫回访]
五、45-60 天的引用变化:我们自己的观测数据
改造在 2026 年 5 月 12 日全量上线,覆盖 3 条产品线共 43 个手册页。以下是自有站点检索日志与人工测试的记录,样本小,仅供同规模厂商参考,不是行业统计。
观测方法说明:每周用 12 组固定问题(覆盖安装、调试、报警处理三类)分别在 ChatGPT、豆包、DeepSeek 的联网/搜索模式下提问,记录回答是否提及我们的品牌、是否复述步骤、是否给出手册页链接;同时看服务器日志里 GPTBot、Bytespider、PerplexityBot 的抓取频次。
| 时间窗 | AI 爬虫周均抓取 | 12 组问题中品牌被提及 | 步骤被复述的问题数 |
|---|---|---|---|
| 上线前 2 周(基线) | 6 次 | 1 次 | 0 |
| 第 1-2 周 | 19 次 | 2 次 | 1 |
| 第 3-4 周 | 41 次 | 5 次 | 4 |
| 第 5-6 周 | 58 次 | 7 次 | 6 |
| 第 7-8 周 | 63 次 | 8 次 | 7 |
几个值得记录的细节:第一处引用出现在第 11 天,是 DeepSeek 回答「分中仪信号线怎么接」时复述了我们第 2 步的 HowToDirection 原文;第 5 周起 ChatGPT 的回答开始带官网链接;到第 8 周,12 组问题里有 8 组提及品牌,其中 3 组把我们的手册列进「参考来源」。期间官网自然流量只涨了约 9%,说明引用增量主要发生在 AI 会话里,传统报表根本看不到——这也提醒市场团队,评估 GEO 效果不能只看百度和 GA。
两个附加收益是意外之喜:手册页的富媒体摘要开始出现在 Google 结果里,点击率提升约 14%;销售反馈客户上门时开口就问「你们是不是那家步骤写得特别清楚的」,说明结构化内容同时影响了人的判断。
六、落地清单与收尾
如果你准备动手,按这个顺序推进,两周内能跑通第一个产品线:
- 选一本安装调试类手册(有明确步骤、有配图),不要先拿参数表类内容开刀;
- 手册源文件补 YAML 元数据:型号、耗时、工具、耗材、封面图;
- 写批量脚本,position 连续性和 image 可直出两条做构建期硬校验;
- 过 Rich Results Test,11 类报错对照第四节的表排查;
- 建 12 组测试问题,每周固定跑一轮并记录引用情况;
- 45 天后复盘数据,再决定是否扩到全产品线。
设备行业做 GEO 的窗口期还在——多数同行手册仍是 PDF 下载页,AI 抓不到、更复述不了。把「客户问 AI、AI 替你答」这条路修通,获客链路里就多了一段别人短期补不上的内容资产。改造过程有疑问,欢迎评论区交流,尤其是 HowToSection 多场景拆分和视频步骤(VideoObject)的结合这两块,我也还在测试。
参考与延伸
- Schema.org HowTo 类型定义:https://schema.org/HowTo
- Google 搜索中心 HowTo 结构化数据文档:https://developers.google.com/search/docs/appearance/structured-data/howto
- Schema.org 官方校验工具(SDTT 传承者):https://validator.schema.org/
- Google Rich Results Test:https://search.google.com/test/rich-results
关键词:GEO、AI搜索、HowTo、HowToStep、JSON-LD、设备手册被AI引用、AI爬虫