全部技能 / 文档与知识 / wps-doc-scraper
文档与知识 · daymade/claude-code-skills

wps-doc-scraper

Faithfully archive public WPS/KDocs/金山文档 links, especially embedded ProcessOn .pof mind maps and canvases, as raw source data, original SVG/PNG, and Markdown. Use when a user gives a kdocs.cn or wps.processon.com link and asks to scrape, save, download, 扒下来, 归档, or 转 Markdown without logging in or saving the document to an account.

风险提醒:黄色 · 留意使用AI 侦查报告
作者 daymadeGitHub daymade/claude-code-skills ↗Stars 1392许可 MIT(仓库根 LICENSE,Copyright (c) 2025 daymade;GitHub API spdx MIT)commit d5c4678cb5
agent 宿主通常会约束 skill 执行权限;风险提醒为 AI 侦查观点,不构成质量或安全保证。第三方 skill 仅作拆解与展示,安装使用风险自负,版权归原作者。

1实现原理 · 为什么它能做到

它走「公开数据 API 直取」而非「浏览器渲染抓屏」:先解析链接类型,KDocs 分享链先读无鉴权元数据接口拿到 file_id/group_id,再用这两个 id 打 ProcessOn 的 view API 拿含 definition 的 JSON。全程不登录。

wps-doc-scraper/scripts/wps_processon_extract.py
PROCESSON_API_BASE = "https://wps.processon.com/wpsapi/diagrams/view/api" KDOCS_LINK_RE = re.compile(r"https?://(?:www\.)?kdocs\.cn/(?:view/)?l/([^/?#]+)")
注:配合 reference 的端点说明:KDocs 元数据端点为 https://drive.kdocs.cn/api/v5/links/<share_id>?review=true,ProcessOn 数据 API 为 https://wps.processon.com/wpsapi/diagrams/view/api?file_id=…&group_id=…。代码中体现为 link_api_url = f"https://drive.kdocs.cn/api/v5/links/{share_id}?review=true"。

「保真」被落实为一条工程原则:Markdown 只是源结构的转换产物,不允许重写、概括或推断缺失内容——脚本只做树结构到列表的映射。

wps-doc-scraper/SKILL.md
This is an extraction skill, not a writing skill. Do not use an LLM to rewrite, summarize, smooth, or infer missing document content unless the user explicitly asks for a separate analysis after the archive is complete.
注:reference 侧给出具体映射规则:node title→bullet、嵌套→嵌套 bullet、summaries→标签「摘要」、comments→标签「评论」,且 'Do not reorder, smooth, summarize, or infer text.'

登录墙被当作显式失败而不是「尽力而为」:脚本对响应文本做关键字检测(「用户未登录」/login 且无 definition),命中即抛错,避免把登录页壳当成可用的源数据。

wps-doc-scraper/scripts/wps_processon_extract.py
if "用户未登录" in text or "login" in text.lower() and "definition" not in text: raise ExtractionError(f"Response looks like a login wall: {url}")
注:SKILL.md 的硬规则同步声明:'HTTP 200 is not enough. Detect login-wall payloads such as `用户未登录`, empty definitions, and placeholder shells.'

归档产物是「原始件 + 派生件」分层:先落 processon-api.json(原始响应)与 processon-definition.json(解析后定义),再落 Markdown、序列化 SVG、PNG,并写 capture-manifest.json 记录来源与计数。

wps-doc-scraper/references/capture-manifest.md
{ "captured_at": "2026-06-26T00:00:00+00:00", "source_url": "https://www.kdocs.cn/view/l/...", "source_type": "kdocs_processon", "kdocs_share_id": "...", "kdocs_link_api_url": "https://drive.kdocs.cn/api/v5/links/...?review=true", "processon_api_url": "https://wps.processon.com/wpsapi/diagrams/view/api?...",
注:脚本侧写盘:path.write_text(json.dumps(value, ensure_ascii=False, indent=2) + "\n", encoding="utf-8") 与 markdown_path.write_text(markdown, encoding="utf-8")。

原图捕获是双轨的:能从页面拿到序列化 SVG 就存全文画布 SVG;若 SVG 用 foreignObject 装文本,则不信任 ImageMagick 单独渲染,改用 macOS Quick Look 切方块瓦片再拼接——这是针对「中文文本在 ImageMagick 直渲下丢失」的实际坑。

wps-doc-scraper/SKILL.md
If the SVG uses `foreignObject`, do not trust ImageMagick alone for text rendering. Use `scripts/render_svg_tiles.py` to make the PNG through macOS Quick Look square tiles.
注:脚本实现:run(["qlmanage", "-t", "-s", str(size), "-o", str(output_dir), str(svg_path)]) 渲染方块,再用 magick/convert 做 "-crop" 与 "-append" 拼接;make_tile_svg 通过改写 viewBox 的 y 偏移切分原图。

输入 URL 被严格按宿主分流:kdocs.cn 走链接元数据、wps.processon.com 的 view 链抽 file_id/group_id、已是 /wpsapi/diagrams/view/api 的按源 API 直用;缺关键 query 键则直接报错而不是猜。

wps-doc-scraper/scripts/wps_processon_extract.py
required = ["file_id", "group_id"] missing = [key for key in required if not one(query, key)] if missing: raise ExtractionError(f"ProcessOn URL is missing required query keys: {', '.join(missing)}")
注:另一条分支判据:if "/wpsapi/diagrams/view/api" in parsed.path:(视为源 API 直接使用)。

落盘文件名做过滤以避免路径穿越/非法字符:剥离换行、替换 \/:*?"<>| 为下划线、去首尾空格与点、压缩空白、截断 140 字符。

wps-doc-scraper/scripts/wps_processon_extract.py
def safe_filename(value: str, fallback: str = "wps-processon") -> str: value = clean_text(value).splitlines()[0] if value else "" value = re.sub(r'[\\/:*?"<>|]+', "_", value).strip(" .") value = re.sub(r"\s+", " ", value) return (value or fallback)[:140]
注:这是本 skill 里少数显式的输入净化代码(对比其 Python 侧只对文件名净化,输出目录由用户指定)。

2核心能力

01公开 KDocs/金山文档链接的元数据读取(无鉴权)
02ProcessOn .pof 思维导图/画布的数据 API 抽取(原始 JSON + 解析后 definition)
03树结构保真转 Markdown(节点→bullet、嵌套→嵌套、摘要/评论带标签)
04渲染层原图捕获:序列化整幅 SVG(含视口外内容)
05macOS Quick Look 瓦片式 SVG→PNG 渲染(绕开 ImageMagick 对 foreignObject 文本的丢失)
06归档清单与验收检查(原始件/解析件/Markdown/原图存在性、不得含替换字符 �、部分失败须标记)
07权限与失败边界规则(可做/不可做清单 + 失败须报具体边界而非糊过去)
08多阶段工作流决策树(先定 URL 类型,再按类型选 API / 导出 / 浏览器 DOM 兜底)

3外部依赖

类型依赖
apiKDocs 公开链接元数据接口(无鉴权)
apiProcessOn 文档数据 API(返回含 definition 的 JSON)
networkKDocs 站点(用户给的分享链接宿主;Referer 头指向此处)
networkProcessOn 站点(画布查看页宿主,view 链与 view/api 链的解析对象)
clipython3(3.10+ 语法:内置泛型 list[str]/dict[str, Any] 与 from __future__ import annotations)
climacOS qlmanage(Quick Look,瓦片式 SVG→PNG 渲染的必需依赖)
cliImageMagick(magick 或 convert,用于瓦片裁剪与纵向拼接)

4风险提醒 风险提醒:黄色 · 留意使用

风险提醒:黄色 · 留意使用
  • 抓回的第三方文档内容会进入 agent 上下文 — 归档产物(尤其 Markdown 与 JSON)通常紧接着被 agent 阅读或处理;公开文档的正文可能含指令性文本。SKILL.md 用「这是抽取不是写作」约束行为,但不构成隔离。建议把抓回的文本当数据处理,不要当指令源。
  • 请求头伪装为浏览器 — 脚本用 Chrome 桌面 UA 与 Referer: https://www.kdocs.cn/ 访问公开数据接口。这是为让公开接口正常响应的常见做法,但它不等于用户在用浏览器访问;对目标站点的访问策略应保持自觉(高频批量抓取可能触发风控)。
  • 输出路径未校验 — --output-dir 不做事先约束,脚本会直接在其下 mkdir + 写多份文件;虽然路径来自命令行而非远端内容(不构成外部可控的任意写入),但误传系统目录仍会散落文件。建议固定用专用归档目录。
  • PNG 链路是 macOS 专用 — qlmanage 缺失即硬失败,ImageMagick 也是必需项。Linux/Windows 用户只能拿到 SVG 与 Markdown,需要自备渲染方案。
  • 依赖上游定义完整度,可能产出「整齐但不全」的 Markdown — 若 definition 缺少节点或上游返回占位壳,产物会看起来完整而实际有缺。文档要求标 partial,但这依赖执行者如实标注;使用时应核对 manifest 的 counts(nodes/comments)与实际观感是否一致。
  • 权限判断最终由执行者承担 — 「公开链接」的判断、是否属用户有权访问的内容,文档给了红线但没有自动判定机制。对来源不明的分享链,使用前应自行确认授权。
风险提醒:黄色,留意使用。依据:它做的是「对公开文档站点的无鉴权 API 读取 + 本地落盘归档」,外发对象完全可预期(kdocs.cn / drive.kdocs.cn / wps.processon.com 三个域名,且由用户提供的链接决定),无凭据读取、无 cookie 使用、无登录流程、无安全降级(不关 TLS 校验)、无 sudo、无反爬绕过(文档反而明文禁止绕过验证码/付费墙/租户限制),也无可执行外部下载物。为什么不是蓝档:它是主动向第三方站点发起网络请求的抓取器,且请求头带浏览器 UA 与 Referer 伪装,并会批量落盘(原始 JSON + 定义 JSON + Markdown + SVG + PNG + manifest),接触面超出「仅本地工具」。为什么不是橙档:未触及任何凭证/登录态,未依赖第三方镜像包(qlmanage/ImageMagick 均为本机已装工具),也未把内容外发到非预期对象。使用提醒:①只对用户明确给出、且公开可访问的链接使用,遇登录墙/CAPTCHA 就按文档失败上报而不是绕;②抓回的文档正文属不可信第三方内容,不要直接当指令源;③PNG 链路是 macOS 专用(qlmanage),非 macOS 需改用其它渲染路径。

5第二遍独立确认

  • [ok] 「无登录、不读凭证」声明是否有反例 — 反例检索失败:两份脚本的 import 均无 http.cookiejar/requests/session 等会话设施;fetch_json 只构造 4 个固定头(User-Agent/Accept/Referer + Content-Type 隐式由 urllib 处理),无 Authorization、无 Cookie 注入、无 keychain 或环境变量读取(grep getenv/os.environ 零命中)。全目录 grep token/cookie/session/password/api_key 仅命中文档中「不得绕过密码提示」这类规则文本。声明成立。
  • [ok] 「禁止绕过」红线与「浏览器 DOM 兜底」是否冲突 — 不冲突且边界写得清楚:permission-and-failure-boundaries.md 允许「Use the user's already-open browser session only to view content the user can legitimately access.」,同时禁止「Logging into WPS/KDocs without explicit user instruction」与「Bypassing CAPTCHAs, tenant restrictions, paywalls...」。SKILL.md 的浏览器兜底也限定在「公开链接」与「已渲染出的内容」,并要求失败时按边界上报。即兜底用于取公开可见内容,不是用来越权。
  • [discrepancy] 写盘是否有路径/文件名风险 — 部分防护、部分缺口(如实记录):文件名做了 safe_filename 净化(剥离换行、把 \/:*?"<>| 替换为 _、strip(' .')、压缩空白、截断 140 字符),可防非法字符;但**输出路径本身未做任何约束**——--output-dir 与 <title>-全画布.svg 的拼接结果没有 resolve/越界检查,用户(或上游传入的路径参数)若给出 / 或系统目录,脚本会直接在其下建目录写文件。与 repomix-unmixer 的关键区别:本处的路径来自用户命令行与本地文件名,**不可由远端文档内容控制**(远端只影响 title 字符串,而 title 已经过 safe_filename 清洗),因此不构成「外部内容 → 任意写入」的攻击链。风险等级低,但「无路径校验」这一事实应予记录。
  • [ok] 是否漏记外部端点(域名全量回查) — 提取结果:drive.kdocs.cn(元数据 API)、wps.processon.com(view 页与 wpsapi 数据 API)、www.kdocs.cn(Referer 与分享页宿主)、www.w3.org(SVG 命名空间字符串,非网络请求)、example.com(文档占位)。逐条已归入 external_deps 的 7 个条目;无未记载的隐蔽外发。
  • [ok] 是否有安全降级或隐蔽执行 — 检索结果:无 CERT_NONE/verify=False/--no-verify(urllib 默认走系统 CA 校验)、无 shell=True、无 eval/exec/os.system、无 base64 大块(render_svg_tiles 的 svg 处理是文本拼接而非编码载荷)、无 >200 字符无空格长行。两份脚本全文可读、逻辑线性。
  • [ok] 「保真」宣称与实际输出是否相符(有无夸大) — 基本相符,且作者把限制写进文档:manifest 验收检查包含「No text output contains �」「Partial extraction is marked partial in notes」,SKILL.md 也要求「Report extraction gaps plainly. Do not silently produce a polished Markdown file from partial data.」。脚本确实先落原始 JSON 再落派生件(processon-api.json → processon-definition.json → <title>.md),符合「保留原始件」的宣称。唯一需注意:Markdown 的完整度上限取决于上游 definition 是否含全部节点,文档第 4 条硬规则已承认「Do not infer hidden nodes or missing text」。
  • [ok] 平台依赖是否被如实声明 — 如实:SKILL.md 明确 'Use scripts/render_svg_tiles.py to make the PNG through macOS Quick Look square tiles',脚本内也有 shutil.which("qlmanage") is None → raise RenderError("macOS qlmanage was not found") 的硬失败,reference 的失败边界清单亦列出「PNG renderer missing Quick Look or ImageMagick」。即非 macOS 环境下该渲染路径不可用是被声明的,不是隐藏缺陷。
  • [ok] pin commit 与 skill.path 是否与任务书表格一致 — git rev-parse HEAD = d5c4678cb5d4fd6acc9c922690df035dbd33d247,与任务书表格『库内 HEAD』逐字一致;目录位于仓库根,相对路径 wps-doc-scraper;本目录最后一次提交 878f947(2026-09-07)。GitHub API 复核 MIT / stars 1392 / pushed 2026-09-15T09:30:04Z。

6结论

  • 用无鉴权公开 API 直取源数据,避开「登录后抓屏」这条越权路径——这是它能在合规前提下做到高保真的根本原因。
  • 「先存原始件、再生成派生件」的归档纪律,使产物可复核(原始 JSON 在,Markdown 只是其转换)。
  • 对失败诚实:要求把具体边界写进 manifest/回复,禁止把部分数据包装成完整归档。
  • 渲染链路考虑到中文文档的真实坑(foreignObject 文本、方块瓦片、HTML-in-SVG 归一化、� 检测),不是教科书式的通用方案。
  • 权限红线明确且主动写下「不做」清单,降低被当作越权抓取工具使用的可能。
  • 适合:适合:需要把 WPS/金山文档(尤其内嵌 ProcessOn 思维导图/画布)的公开分享内容长期归档的人——知识管理、竞品资料留存、团队文档备份,且希望保留原始数据与原始视觉件以便日后复核。也适合需要「把思维导图转成可 diff 的 Markdown 树」的场景。
    不适合:不适合:需要登录/受限权限才能查看的文档(文档把它设为硬边界,不会代你登录或绕过);需要把文档内容改写/摘要的场景(这是抽取工具,明文禁止 LLM 重写);非 macOS 环境下需要 PNG 原图的场景(qlmanage 依赖);以及大规模批量采集(它面向单个公开链接的保真归档,不提供批量调度与限速策略)。
    安装 agent 直装可复制
    ① 本站镜像 更新 2026-09-15
    方式 A · 人下载镜像包下载 wps-doc-scraper.tar.gz
    sha256: dc2d17f32517aa55…
    方式 B · JSON 格式安装指南,复制给 agent
    安装指南
    agent 读 JSON 指南后会自动从本站下载安装,无需更多说明。
    ② 上游 GitHub · 原始来源
    能访问 GitHub?直接去上游安装(实时版,可能已更新)GitHub 原始 ↗
    本页镜像锁定 commit d5c4678cb5;上游为实时仓库。
    来源信息 GitHub 原始
    作者 / 仓库daymade / daymade/claude-code-skills
    Stars1392
    最近推送2026-09-15
    本 skill commitd5c4678cb5
    许可MIT(仓库根 LICENSE,Copyright (c) 2025 daymade;GitHub API spdx MIT)
    本站信息
    收录日期2026-09-06
    分类文档与知识
    侦查报告AI 侦查 · 2 遍 · 2026-09-06
    本站镜像与 GitHub 原始是不同来源:本站锁定 commit 快照经 /r2 分发;GitHub 为实时上游,内容可能已更新。
    同分类邻近