awesome-copilot 的 PDF 转 Markdown 技能:convert-pdf-to-md 安装、脚本原理与故障排查实战指南

发布时间:2026/9/13 15:03:08
awesome-copilot 的 PDF 转 Markdown 技能:convert-pdf-to-md 安装、脚本原理与故障排查实战指南 awesome-copilot 的 PDF 转 Markdown 技能convert-pdf-to-md 安装、脚本原理与故障排查实战指南【免费下载链接】awesome-copilotCommunity-contributed instructions, agents, skills, and configurations to help you make the most of GitHub Copilot.项目地址: https://gitcode.com/GitHub_Trending/aw/awesome-copilot导读当用户丢来一份.pdf文件让你读一下总结一下把表格提取出来时直接当作纯文本解析是行不通的——PDF 是面向排版/打印的格式而不是可靠的可读文本。GitHub 社区贡献的 awesome-copilot 仓库为此提供了一项名为convert-pdf-to-md的 Copilot 技能在 SKILL.md 中定义触发规则在 scripts/convert_pdf_to_md.py 中实现基于 MarkItDown PyMuPDF 的转换逻辑。读完本文你将掌握该技能的完整使用流程何时触发、一次性环境准备、单文件与批量转换命令、输出目录约定、以及 7 类常见故障的根因与修复方式并能结合源码理解文本表格由 MarkItDown 提取、图片由 PyMuPDF 单独抽离的双引擎设计原理。一、技能定位什么时候应该触发 convert-pdf-to-md1.1 触发条件所有涉及 .pdf 的理解与处理请求按照 SKILL.md 的定义只要用户分享、引用或询问一个.pdf文件即使没有明确说出 convert 或 markdownAgent 都应当触发本技能。典型的隐性请求包括read让 Agent 阅读一份 PDF 报告summarize要求总结论文、合同或发票review要求审阅或复核一份 PDF 文档extract data from要求从表单、扫描件、对账单中抽取指定字段compare / analyze要求对多份 PDF 文档进行对比或分析batch一次处理整个文件夹中的多个 PDF 文档。技能明确要求必须先运行捆绑的转换脚本产出 Markdown再基于 Markdown 做后续分析禁止直接尝试解析 PDF 内容或临时编写 ad-hoc 提取代码。原因在于 PDF 是版面/打印格式文本不以逻辑流存储直接读取会丢失表格结构、段落顺序乃至内容本身。1.2 仅支持 .pdf为什么没有 .doc / .xls 历史包袱该技能只支持.pdf因为它是 MarkItDown 的 PDF 家族唯一格式。与 Word.doc/.docx或 Excel.xls/.xlsx存在新旧格式之分不同PDF 没有对应的遗留格式需要额外兼容因此转换逻辑可以保持单一、纯净。1.3 混合文件类型必须并行调用三个兄弟技能当用户引用一个包含多种受支持文件类型的文件夹或文档集时.pdf、.docx、.xlsx并存本技能只负责.pdfAgent 必须并行调用另外两个兄弟技能不能静默跳过任何一种受支持的文件类型任何.docx文件 → 调用 convert-word-to-md任何.xlsx文件 → 调用 convert-excel-to-md任何.pdf文件 → 调用本技能。三者的 frontmatter 中互相引用彼此构成一个闭环的多格式文档批处理约定处理文件夹时要么全转要么明确告知用户哪些类型被忽略绝不静默遗漏。二、环境准备每个环境只需执行一次转换脚本依赖 Python 3.10、pip、markitdown[pdf]与pymupdf。首次在某个环境执行转换前应按 setup.md 逐步操作。脚本本身在启动时也会检查依赖是否齐全缺失时会打印指向该文件的明确提示因此即使不确定环境状态也可以先直接尝试转换失败后再回头补装。2.1 检查 Python 3.10python --version如果命令不存在安装 Python 3.10 或更新版本Windowswinget install --id Python.Python.3.12 -emacOSbrew install python3.12LinuxDebian/Ubuntusudo apt-get update sudo apt-get install -y python3 python3-pip python-is-python3如果版本低于 3.10MarkItDown 要求 3.10用同样的命令安装新版 Python。2.2 确认 pip 可用python -m pip --version如果失败用python -m ensurepip --upgrade引导安装 pip。2.3 安装依赖MarkItDownPDF 支持 PyMuPDF使用技能捆绑的 requirements.txt 安装锁定版本依赖保证可复现python -m pip install -r scripts/requirements.txt该文件内容为markitdown[pdf]0.1.0 pymupdf1.24.0其中 PyMuPDF导入名fitz是必须单独安装的MarkItDown 的 PDF 转换器只提取文本和表格完全不支持嵌入图片因此技能脚本需要自己用 PyMuPDF 完成图片抽取。2.4 验证安装python -c from markitdown import MarkItDown; import fitz; print(markitdown pymupdf OK)期望输出markitdown pymupdf OK且无报错。如果出现ModuleNotFoundError重复步骤 2.3——很可能是 pip 装到了与当前python解释器不同的环境可用python -m pip --version与python --version对比确认是否为同一路径。2.5 注意事项设置只需每个环境/虚拟环境做一次不需要每次转换都做脚本启动时会检查markitdown和fitz缺失则提示回到 setup 文档因此重复执行 setup 是安全且幂等的扫描/纯图片型 PDF无内嵌文本层经 MarkItDown 转换后文本可能为空或近乎为空——它不做 OCR详见第六节。三、脚本源码剖析双引擎如何协作3.1 整体职责划分convert_pdf_to_md.py 的 docstring 明确了两条分工线MarkItDown 负责文本与表格MarkItDown().convert()提取正文文本与表格结构PyMuPDF 负责嵌入图片MarkItDown 的 PDF 转换器完全不会检测或输出嵌入图片it does not detect or emit anything for embedded images at all因此脚本自行调用 PyMuPDF 将每页的真实图片抽成独立文件。3.2 图片提取两个来源 字节级去重从源码看extract_images()convert_pdf_to_md.py合并了两种图片来源并做去重来源一Image XObject通过page.get_images(fullTrue)枚举再以doc.extract_image(xref)取回原始字节。这覆盖了现代 PDF 中绝大多数嵌入图片。来源二内联图片块通过page.get_text(dict, flagsfitz.TEXT_PRESERVE_IMAGES)扫描内容流中的type 1图像块。这类直接写在页面内容流里的图片get_images()会完全漏掉。去重策略基于SHA-256 字节哈希hashlib.sha256(img_bytes).digest()同一页面上相同的位图无论来自哪个来源都只落盘一次。文件名遵循page{P:03d}_img{N:03d}.ext的规范命名例如page001_img001.png保证按页码和页内序号稳定排序。每个来源的枚举与提取都被 try/except 包裹损坏或不可读的图片只会打印WARNING并跳过不会中断整个转换流程——这是脚本在健壮性上的刻意设计。3.3 输出结构自包含目录每个源文件名为name.pdf都会生成一个同名文件夹name/ img/ page001_img001.ext page001_img002.ext page002_img001.ext ... name.md如果文档没有嵌入图片则不创建img/文件夹也不会在 Markdown 中出现## Extracted Images章节。3.4 为什么图片放在文末附录而非正文内联MarkItDown 的 PDF 文本提取不保留可靠的逐页标记页面只是被简单拼接某些情况下甚至作为一整块无标记文本返回因此脚本无法安全地判断某张图片在正文中的精确插入位置。为了避免把图片错放在错误的段落旁边脚本采取诚实的取舍在 Markdown 末尾追加一个## Extracted Images章节每个有图的页面给出### Page N子标题并在该页下列出所有图片文件名。从build_image_appendix()convert_pdf_to_md.py的实现可以确认该章节按页码升序输出读者应把图片区与正文分开阅读需要时通过### Page N标题结合上下文交叉对照。3.5 退出码约定脚本定义了 4 个退出码便于 Agent 与 CI 场景自动判断结果退出码含义触发条件0全部转换成功所有请求的转换均成功1部分或全部转换失败批量模式下至少一个文件失败部分成功2依赖缺失markitdown或pymupdf未安装3输入非法路径不存在或单文件输入不是.pdf对应源码中的常量convert_pdf_to_md.pyEXIT_OK / EXIT_CONVERSION_FAILED / EXIT_MISSING_DEPENDENCY / EXIT_INVALID_INPUT。其中依赖缺失的提示会给出具体安装命令pip install markitdown[pdf]或pip install pymupdf输入非法的报错信息则区分路径不存在与文件类型不支持两种场景。四、使用方式单文件与批量转换4.1 单文件转换python scripts\convert_pdf_to_md.py C:\path\to\document.pdf在源文件旁边生成document\文件夹内含document.md若有图片则含document\img\。如需显式指定目标文件夹python scripts\convert_pdf_to_md.py C:\path\to\document.pdf -o C:\path\to\output_folder4.2 批量转换文件夹模式python scripts\convert_pdf_to_md.py C:\path\to\folder遍历目录下直接包含的每个.pdf各自生成name\输出文件夹。加--recursive可深入子目录python scripts\convert_pdf_to_md.py C:\path\to\folder --recursive4.3 批量模式的输出路径语义默认每个name\文件夹生成在其对应源文件旁边指定-o-o被视为输出父目录所有生成的name\文件夹汇集到该目录下与--recursive组合时相对子目录结构会被保留。这一点与单文件模式的-o语义视为确切目标文件夹不同。从 convert_pdf_to_md.py 的源码可以确认差异批量模式下用pdf_path.relative_to(source)计算每个文件的相对路径再拼到输出父目录下从而保留目录层级。4.4 批量处理的容错行为脚本按文件逐个转换并统计结果最后打印Converted {success}/{total} file(s).。某个文件损坏、加密或不可读时只会在 stderr 打印FAILED file - ...同批其他文件继续成功最终退出码为1部分成功。文件夹中的非 PDF 文件会被计数并在批处理末尾以NOTE: skipped N non-.pdf file(s)提示属预期行为。4.5 转换完成后脚本的职责只到产出准确的 Markdown 与图片为止不负责理解内容。Agent 应读取生成的.md文件去完成用户真正要求的分析、总结、数据抽取等任务。五、输出位置决策规则与路径确认SKILL.md 对输出位置做了严格约定避免 Agent 自作主张默认永远输出在源文件旁边name/文件夹创建在与源.pdf相同的目录这是所有情况下的强制默认除非用户明确要求其他位置否则不得覆盖。只有在用户明确给出输出路径时才使用-o例如用户说把输出保存到C:\output或结果放到D:\work。禁止基于 Agent 当前工作目录、会话状态文件夹或任何隐含位置去传递-o。源文件路径无法完全解析时例如用户只给了文件名没给目录或路径有歧义应使用ask_user向用户确认完整绝对路径后再执行转换绝不猜测目录。这三条规则共同防止转换结果落到用户找不到的地方这一最常见的 Agent 失误。六、故障排查症状、根因与修复对照表SKILL.md 附带的排查表覆盖了从依赖缺失到 OCR 局限的全部已知失败模式转换失败时先对照此表症状可能原因修复方法ModuleNotFoundError: No module named markitdown或fitz退出码 2MarkItDown 或 PyMuPDF 未安装按 setup.md 逐步操作ERROR: Unsupported file type ...退出码 3输入不是.pdf文件请用户提供正确文件若是.doc/.docx/.xlsx改用对应的兄弟技能ERROR: Input path not found退出码 3路径写错或文件已被移动与用户确认正确路径批量输出中出现FAILED file - ...该文件损坏、受密码保护或无法读取报告具体失败文件批内其余文件仍成功NOTE: skipped N non-.pdf file(s)文件夹中存在非 PDF 文件属预期行为这些文件被有意忽略Markdown 正文为空或近乎为空但图片已提取PDF 为扫描/纯图片型无内嵌文本层MarkItDown 不做 OCR告知用户不支持 OCR——提取出的页面图片仍可提供给用户查看图片出现在附录而非正文内联位置刻意设计的限制——MarkItDown 的 PDF 文本没有可靠的逐页标记无法安全定位内联插入点属预期行为如需对应关系可将### Page N标题与正文上下文交叉参照七、技能边界与设计哲学无 OCR扫描件、图片型 PDF 在没有文本层的情况下MarkItDown 无法产出正文。技能不伪装能力而是如实告知用户并把每页提取出的图片保留下来供人工查看。宁做附录不做错误内联在图片可能放错段落与图片统一放文末之间脚本选择了后者并在附录中保留页码信息以便交叉引用——这是可审计、可回退的诚实取舍。错误可定位依赖缺失退出码 2、输入非法退出码 3、单文件失败退出码 1三类错误路径在源码中均有独立常量与明确报错文案配合 SKILL.md 的排查表Agent 可以自助收敛问题。掌握本技能后你可以把任何.pdf——报告、论文、发票、表单、合同或扫描文档——稳定地转化为可搜索、可分析、可引用的 Markdown 语料这是后续一切 PDF 理解类任务总结、抽取、对比、批量入库的可靠前置流水线。对于包含 Word/Excel 的混合文档集请记住与 convert-word-to-md、convert-excel-to-md 并行调用确保没有任何一种受支持的文件类型被静默跳过。【免费下载链接】awesome-copilotCommunity-contributed instructions, agents, skills, and configurations to help you make the most of GitHub Copilot.项目地址: https://gitcode.com/GitHub_Trending/aw/awesome-copilot创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考