<!-- title: 官方PDF件拆解：门后还有一道门 -->

# 官方PDF件拆解：门后还有一道门

## 概述

本期是 Skills 生态系列第 2 轮：单件深拆。对象选官方文档四件套里唯一没开过盖的 **pdf** 件——docx、pptx、xlsx 前几轮都被写过了，只剩它。拆解材料全部为第一手：本机 anthropic-agent-skills 市场渠道安装的 example-skills 插件包，SKILL.md 正文逐段读原文，目录里 12 个文件逐个点名。核心发现有三个：一，它是「渐进披露」教科书写法的活标本，门后还有门；二，正文只字未提的 8 个脚本，构成一台完整的表单机器；三，官方自己的 skill-creator 规范里写明——「读一下这个 PDF」这种简单任务根本不会触发它，这对怎么用、怎么仿写都有直接含义。

## 一、为什么拆它

pdf 是官方 example-skills 插件包（anthropic-agent-skills 市场）文档四件套 docx / pptx / xlsx / pdf 的收官件。前几轮系列里，docx 拆出的结论是「改 XML 不重建」，pptx 六件横评过装机重影，xlsx 在数据处理横评里露过脸。pdf 补上最后一块，而且它和 docx 恰好是一组对照：同样是「让确定性工具干活」的家族哲学，docx 选了直接动 OOXML 的 XML，pdf 选了调库——pypdf、pdfplumber、reportlab，一行 XML 都不碰。

## 二、先看货架：12 个文件逐个点名

本机插件缓存里的 pdf 目录，实际文件清单如下（Glob 实测）：

```
pdf/
├── SKILL.md                 # 正文：通用操作手册 + 双门路标
├── forms.md                 # 门一：表单专项手册
├── reference.md             # 门二：进阶参考
├── LICENSE.txt
└── scripts/
    ├── check_fillable_fields.py
    ├── extract_form_structure.py
    ├── extract_form_field_info.py
    ├── fill_fillable_fields.py
    ├── fill_pdf_form_with_annotations.py
    ├── check_bounding_boxes.py
    ├── create_validation_image.py
    └── convert_pdf_to_images.py
```

两个值得注意的细节：

**第一，没有 assets/ 目录。** 官方 skill-creator 规范给出的标准解剖图是 `scripts/ + references/ + assets/` 三件套，pdf 只用了 scripts，参考文档直接平铺在根目录（`forms.md`、`reference.md`），没有按规范放进 `references/` 子目录。官方自己的件也没严格遵守自己写的规范——写 SKILL.md 的读者可以放宽心。

**第二，文件名大小写不一致。** SKILL.md 正文里的引用写的是大写的 `FORMS.md` 和 `REFERENCE.md`，磁盘上实际是小写的 `forms.md`、`reference.md`。在大小写不敏感的解析器下无碍，但在 Linux 这类大小写敏感的文件系统上，如果加载器不做归一化处理，按正文原样相对路径读取就会落空。这是本机实测观察到的打包瑕疵，写自己 Skill 的人应当引以为戒：**引用文件名要和磁盘文件名严格一致**。

## 三、SKILL.md 正文逐段拆

正文结构是干净的七段：Overview → Quick Start → Python Libraries → Command-Line Tools → Common Tasks → Quick Reference → Next Steps。逐段看它写了什么、为什么这么写。

### 第 1 段 Overview：一次做完三件事

原文：

> This guide covers essential PDF processing operations using Python libraries and command-line tools. For advanced features, JavaScript libraries, and detailed examples, see REFERENCE.md. If you need to fill out a PDF form, read FORMS.md and follow its instructions.

开头三句话各干一件事：划边界（Python 库 + 命令行工具）、开第一扇门（进阶看 REFERENCE.md）、开第二扇门（填表单读 FORMS.md）。注意「填表单」在正文里出现了**三次**——Overview 一次、Quick Reference 表格里一次（`Fill PDF forms | pdf-lib or pypdf (see FORMS.md)`）、Next Steps 里又一次。同一指路信息重复三遍不是笔误，是对触发可靠性的下注：模型跳读正文时，无论落在哪一段都能看到这扇门。

### 第 2 段 Quick Start：十行定调

开头就是一个 pypdf 读文件、数页数、抽文本的最小示例。没有一句废话解释 PDF 是什么。这份正文假设读者（模型）已经会用 Python，只负责告诉它「用哪个库、抄哪段代码」。

### 第 3 段 Python Libraries：三大库各司其职

- **pypdf**：合并（逐页 `add_page` 进 PdfWriter）、拆分（一页一文件）、读元数据、旋转页面，外加加水印（`page.merge_page(watermark)`）和加密（`writer.encrypt("userpassword", "ownerpassword")`）。
- **pdfplumber**：按版面抽文本、抽表格，示例一直给到 `pd.DataFrame(table[1:], columns=table[0])` 再 `to_excel` 落盘——从 PDF 表格直接到 Excel 文件的完整链路。
- **reportlab**：两条造 PDF 路线，canvas 手画坐标和 platypus 排故事流（`SimpleDocTemplate` + `story` 列表）。

### 第 4 段：一段 IMPORTANT，整篇唯一的加粗警告

> Never use Unicode subscript/superscript characters (₀₁₂₃…⁰¹²³…) in ReportLab PDFs. The built-in fonts do not include these glyphs, causing them to render as solid black boxes.

不要在 reportlab 里用 Unicode 上下标字符——内置字体没有这些字形，渲染出来是实心黑块。替代方案也给全了：Paragraph 里用 `<sub>`/`<super>` 标签，canvas 场景手动调字号和位置。这类规则是典型的「伤疤条款」：作者显然在这个坑上翻过车，才会把具体到 U+2011 级别的细节钉死在正文里。全文唯一一处 IMPORTANT 加给了它，其余部分通篇平铺直叙——**稀缺的强调权限，花在唯一必然翻车的点上**，这是值得抄的克制。

值得注意的是，官方 skill-creator 规范自己说过：「如果你发现自己在用全大写的 ALWAYS 或 NEVER，那是个黄牌信号，应该改为解释原因」。而这条 IMPORTANT 恰恰是解释了原因的 NEVER（字体缺字形→黑块）。可见黄牌不是禁止 NEVER，而是禁止**不解释的** NEVER。

### 第 5-6 段：CLI 兜底 + 快查表二次路由

Command-Line Tools 段给了 pdftotext（`-layout` 保版面）、qpdf（合并、拆页、旋转、`--password=xxx --decrypt` 解密）、pdftk 三个命令行备胎。Common Tasks 段处理散装需求：扫描件 OCR（pdf2image 转图 + pytesseract 认字）、批量抽图（`pdfimages -j`）。

然后是全文的点睛之笔——Quick Reference 表，八行任务到工具的映射：

| Task | Best Tool |
|------|-----------|
| Merge PDFs | pypdf |
| Split PDFs | pypdf |
| Extract text | pdfplumber |
| Extract tables | pdfplumber |
| Create PDFs | reportlab |
| Command line merge | qpdf |
| OCR scanned PDFs | pytesseract |
| Fill PDF forms | pdf-lib or pypdf（见 FORMS.md）|

这张表的本质是**二次路由**：前面各段是按库组织的长文，模型可能读偏；末尾这张表按任务组织，做最后一道纠偏。「这个任务该用哪个工具」的答案被压缩到一行一格，是整篇正文信息密度最高的十行。

### 第 7 段 Next Steps：路标复读

结尾把三扇门再指一遍：进阶 pypdfium2、JavaScript 的 pdf-lib、疑难排障 → REFERENCE.md；填表单 → FORMS.md。首尾呼应，路由闭环。

## 四、渐进披露：三层结构实测

拿官方 skill-creator 规范对照，pdf 件是三层加载的标准实现：

```mermaid
flowchart TB
    A["第0层 name与description 常驻系统提示"] -->|触发时| B["第1层 SKILL.md 正文"]
    B -->|合并拆分抽文本等常规活| C["直接调库 到此为止"]
    B -->|要填表单| D["第2层 forms.md"]
    B -->|进阶与疑难| E["第2层 reference.md"]
    D -->|按手册指令调用| F["第3层 scripts 八枚脚本"]
```

规范原文写明：元数据层（name + description，约 100 词）常驻上下文；SKILL.md 正文触发时才加载，理想控制在 500 行以内；捆绑资源按需加载，且「脚本可以不加载就执行」。pdf 正文目测两百行上下，远在红线之内；两个参考文件把进阶内容和表单机器整体挡在门外，正文只保留路标。

**本篇最大的发现在这里：SKILL.md 正文从头到尾没有出现过 scripts 这个词。** 8 个脚本没有一个在正文里被点名。它们全部是表单与校验用途（从文件名可判断：探测、抽结构、抽字段、回填、注释覆盖法回填、边界框检查、生成校验图、PDF 转图），合理的推断是由 forms.md 在门后召唤——正文没读 forms.md，此判断标注为推断。但正文层面的事实是确定的：**通用操作不需要脚本，表单机器被整体下沉到了第二扇门后面。** 这是一个很高级的取舍：填表单是低频高危操作（要动别人的文档），把它藏起来，让高频的合并拆分抽文本走零脚本快速通道。

## 五、表单机器：八脚本流水线复原

8 个脚本按名字可以复原出一条流水线（ roles 为推断，清单为实测）：

```mermaid
flowchart LR
    A["拿到一份PDF"] --> B["check_fillable_fields 探测表单字段"]
    B -->|有AcroForm字段| C["extract_form_field_info 摸清字段清单"]
    B -->|无字段| D["fill_pdf_form_with_annotations 注释覆盖法"]
    C --> E["fill_fillable_fields 逐字段回填"]
    D --> F["convert_pdf_to_images 渲染成PNG"]
    E --> F
    F --> G["check_bounding_boxes 加 create_validation_image 校验"]
```

两条支路对应 PDF 表单的两种现实：有 AcroForm 字段的走 `fill_fillable_fields.py` 正路回填；扫码机扫出来的、看起来是表单实际是一张画的，走 `fill_pdf_form_with_annotations.py` 的注释覆盖法——在正确坐标上把文字「盖」上去。最后统一转 PNG 人工目检，`check_bounding_boxes.py` 和 `create_validation_image.py` 负责让模型能自己检查自己盖没盖歪。

这条流水线还有个隐藏含义：**脚本目录本身就是文档**。就算不读脚本源码，八个文件名已经把「探测→摸底→回填→渲染→校验」的工序讲完了。给脚本起自解释的名字，等于给第二层门配了免费目录页。

## 六、可以抄走的四个写法

**写法一：门后门。** 正文管总账，专项任务开专属手册，进阶内容开参考手册，每扇门在正文里至少出现两次。判断标准：某一子任务的说明书如果超过正文一个章节的合理体量，就拆成门。

**写法二：末尾快查表。** 长文按库、按模块组织，读者（模型）容易迷路；结尾放一张「任务→工具」表按任务组织，做二次纠偏。成本十行，收益是兜底。

**写法三：伤疤条款占唯一的加粗位。** 把自己翻过车的坑写成「禁止 + 原因 + 替代方案」三件套，全文最多一两处。处处加粗等于没有加粗。

**写法四：低频高危下沉。** 高频低危操作（读、合并、拆）放正文快速通道；低频高危操作（改表单、动别人的文件）连同样脚本整体下沉到专项手册，正文只留一句「要填表单，读 FORMS.md 并照做」。

## 七、适用与不适用

**适用场景**：多步文档工程——批量合并拆分、加水印、加密、扫描件 OCR 抢救文字、PDF 表格转 Excel、reportlab 生成报告、以及整台表单机器。

**不适用场景**：官方规范里有一段罕见的坦白，原文：

> Claude only consults skills for tasks it can't easily handle on its own — simple, one-step queries like "read this PDF" may not trigger a skill even if the description matches perfectly.

翻译过来：模型只对靠自己搞不定的任务才去翻技能——「帮我读一下这个 PDF」这种一步任务，描述写得再完美也可能不触发。也就是说，**这个件的设计定位根本不是「读 PDF」，而是「对 PDF 做工程」**。你让它合并三十个合同、填一份 W-9、把扫描合同转成可搜索文本，它值回票价；你让它读两页说明书，直接丢文件就好，技能不技能的无所谓。另一个边界是密码：qpdf 解密命令是给自有文档准备的，拿来处理无权处理的加密文件不在此件讨论范围。

## 八、装机命令

```bash
# 路线一：从官方仓库拷贝（通用、稳妥）
git clone https://github.com/anthropics/skills.git
find skills -type d -name pdf        # 定位仓库内 pdf 目录
mkdir -p ~/.claude/skills
cp -r <找到的pdf目录> ~/.claude/skills/pdf

# 路线二：插件市场渠道（本机实测即由此安装）
# Claude Code 内执行 /plugin，在 anthropic-agent-skills 市场安装 example-skills 包
```

依赖按需补齐（正文给出的清单）：

```bash
pip install reportlab pdfplumber pypdf     # 三大件
pip install pytesseract pdf2image          # 仅 OCR 需要
# 系统级：poppler-utils（pdftotext/pdfimages）、qpdf
```

## 九、侧记：同名的另一件

最后补一个本机实测的趣闻：这台机器上其实装着**两个** pdf 件。除了官方件，用户目录里还有一个同名的个人版 pdf 件，哲学完全相反——它通篇是「渲染成 PNG、逐页目检、最新一次目检零缺陷之前不许交付」的视觉验证闭环，几乎不谈库的选择。同一个名字，一个信代码、一个信眼睛。Claude Code 的技能解析里，个人级同名件会先被命中（本会话实测：调用 `pdf` 加载到的是个人版，要官方版得带 `example-skills:` 前缀）。装机时同名冲突不是报错，而是静默遮蔽——这一点，装得多的人迟早会撞上。

## 评测表

| 维度 | 权重 | 评分 | 评语 |
|------|------|------|------|
| 功能完整度 | 25% | ★★★★☆ | 读建表单 OCR 加密水印全覆盖；短板：无数字签名、OCR 依赖系统语言包 |
| 设计质量 | 25% | ★★★★★ | 双门渐进披露 + 快查表二次路由 + 伤疤条款，教科书级 |
| 实战效果 | 20% | ★★★★☆ | 表单流水线设计完备；本篇为文本层拆解，未做实测跑分 |
| 上手难度 | 15% | ★★★★★ | 零配置，三条 pip 一条 apt 即起 |
| 社区活跃度 | 15% | ★★★★☆ | 官方文档四件套成员、随 example-skills 插件持续分发；本期未采集星标数据 |
| **加权总分** | | **4.40** | |

（评分基于第一手文本与官方规范对照；未采集第三方统计，星标、下载量等数字本期一概不给，防止编造。）

## 推荐排行榜：谁该装它

1. **每周填 PDF 表单的人**——八脚本流水线就是为此而造，装。
2. **做文档流水线的后端**——合并拆分水印加密批量活，装。
3. **档案抢救党**——扫描件 OCR + 表格转 Excel 链路完整，装。
4. **用代码生成报告的岗位**——reportlab 段落直接抄，装。
5. **只是偶尔读 PDF 的人**——别装。官方规范自己说了，简单读取不会触发，装了也是白占一行描述。

## 参考来源

1. [anthropics/skills — 官方 Skills 仓库](https://github.com/anthropics/skills) — pdf 件的上游仓库，文档四件套均出自此处
2. 本机 anthropic-agent-skills 市场插件 example-skills（`plugins/cache/anthropic-agent-skills/example-skills/`）— SKILL.md 正文、forms.md、reference.md 与 8 个脚本文件清单均实测于此
3. 同插件包内 skill-creator 件 — 三层渐进披露、触发机制（「简单任务不触发」）、脚本捆绑原则等官方规范原文出处

> [!tip] 51学通信知识星球
> **星主：爱卫生**（微信：gprshome201101）——公众号「51学通信」创办者，19 年通信行业运维与讲师经验，著有《GPRS网络信令实例详解》《EPC原理与实践》《5G核心网原理与实践》三本纸质书（各大电商平台有售）。
> **星球定位**：深耕 5G 核心网、IMS、NFV/AI、云原生等 ICT 领域，主打运维岗位与信令分析。
> **当前规模**：5200 篇主题 / 990 个回答，198 元/年。
> **加入福利**：加入星球后请加爱卫生微信，拉您进知识星球年度陪伴与答疑群——不限量回复您的各种问题，另有群内分享。
> **AI 加持**：51学通信知识星球已作为 skill 接入 WorkBuddy，使用 deepseek-4-flash 在海量星球帖子中精准找贴、找视频、找 FAQ 和案例，做总结、找文档和 PPT 等场景全覆盖。

![51学通信知识星球海报-扫码加入](https://wiki.500nian.com/images/zhixingqiu_qrcode.png)
