Communitygithub.com

网站文案审阅

从网站代码库中提取所有面向访客的文案(模板、组件、本地化文件以及CMS/站点设置,如导航标签和元描述),生成一份可供客户直接审阅的横向.docx审阅文档,其中包含可寻址的引用码、空白的“建议修订”列,以及一个CSV清单,以便将批准的编辑内容还原回源代码。

网站文案审阅 是什么?

这是一个用于网站文案专业审阅流程的AI代理技能。它能将网站代码库中的全部面向用户文案(包括硬编码在模板/组件中的、CMS数据库中的以及站点全局设置中的)系统化地提取出来,并生成一份结构化的Word文档。该文档为每一段文本都分配了一个唯一的引用码,方便非技术审阅者逐页阅读并标记修改建议,最终编辑后的CSV清单可用于机械地将修改内容还原回源代码。此技能支持多种前端框架和CMS平台,通过一系列自动化脚本(如合并验证脚本和文档构建脚本)确保提取的完整性和准确性。其核心价值在于解决了传统文案审阅中“无法精准定位修改位置”和“缺乏上下文”的痛点,使得开发团队和内容团队之间的协作更加顺畅高效。

兼容平台✓Claude Code~Codex CLI~Cursor
npx skills add https://github.com/brianitsup/website-copy-review/tree/main

在你喜欢的 AI 中提问

打开一个已预加载此 Agent Skill 的新对话。

文档

网站文案审阅 是做什么的?

将网站代码库转换为非技术审阅者可以逐页阅读和标记的文档, 其中每个字符串都保留一个地址(引用码),以便其编辑内容可以机械地还原回源代码。

为什么这样构建

网站文案不是散文。它是由成千上万个短字符串组成,这些字符串被放置在标记语言内的固定布局槽位中。因此:

  • 带有修订的纯文本转储会返回一堆无法在不加猜测的情况下放回标记语言中的插入内容。因此,每行对应一个字符串,并带有一个引用码。
  • 一个审阅者将一个4个单词的卡片标题改为12个单词,会破坏布局,并且无法在Word中看到这一点。因此,对受约束的行显示字符数和通俗易懂的长度指导。
  • 审阅者永远看不到代码。因此,每行都用通俗的语言说明它是什么(“按钮标签”、“替代文本”),并且每个页面部分都说明它在实际站点上的位置。

文档必须按页自上而下阅读(以便判断语气和叙述),同时保持每个字符串单独可寻址。

捆绑文件

scripts/merge_and_verify.py、scripts/build_review_docx.py、references/extraction-brief.md 和 assets/pages.example.json 与此文件位于同一目录下。如果它们缺失(该技能仅作为 SKILL.md 安装),请在 ~/my-skills/website-copy-review/ 或 brianitsup/website-copy-review 仓库中查找;如果两者都不可访问,请告知用户,而不是自行修改文档布局,因为它在每次运行之间不得改变。

基本规则

  • 只读。 绝不要编辑仓库。所有输出都将写入暂存区,除非用户要求将其放入仓库中。
  • 在暂存区的虚拟环境中安装 python-docx,而不是全局安装: python3 -m venv <scratch>/venv && <scratch>/venv/bin/pip install python-docx
  • 如实报告。如果某个文件无法解析或某个检查无法运行,请说明;永远不要悄悄缩小范围。
  • 如果仓库在 AGENTS.md、CLAUDE.md、PROJECT_WORKFLOW.md 或 CONTRIBUTING.md 中采用了 issue-first(或类似)的工作流程惯例,请告知用户,返回的编辑内容和任何缺陷在实施之前都需要创建一个 issue。不要在未经询问的情况下主动创建 issue。

预期规模:一个中型宣传网站大约有 400–600 个项目,分布在 15–20 个页面,生成 50–60 页的文档。这是正常的;按页划分的表格使其易于导航。

第 1 步 — 确定范围(一次性询问,附带默认值)

一起询问这些问题(如果可用,使用 AskUserQuestion),推荐使用默认值:

  1. 哪些文案? 仅限模板/组件中的硬编码文案 (默认 — 编辑器内容可以在 CMS 中修复,无需更改代码),或者也包括 CMS 撰写的文章/页面?
  2. 审阅者将如何标记更改? 空白的“建议修订”列 (默认 — 明确且可机械应用),或者 Word 注释/修订(自然,但难以还原回去)。
  3. 哪个内容状态? 工作树,还是生产环境?需标记本地数据库或内容快照可能落后于实际发布的内容。

如果用户不在线,则采用默认值,并在报告顶部说明。答案将放在封面页上(pages.json 中的 meta.scope)。

第 2 步 — 发现文案所在位置

不要假设技术栈。检查仓库(package.json、主题清单、框架配置、目录布局)并列出文案来源:

  • 代码中: .hbs、JSX/TSX、Vue、Svelte、Astro、Blade、ERB、Twig、PHP 主题、HTML、Markdown/MDX 内容文件、i18n/本地化 JSON 或 YAML。
  • 代码外: CMS 数据库/API(Ghost、WordPress、Sanity、Contentful、Strapi)以及不在仓库中的面向访客的站点设置 — 站点标题、元描述、导航标签、在管理后台设置的 CTA/按钮标签。当你拉取这些时,将原始导出保存到 <scratch>/snapshots/ 中,以便可以像其他来源一样进行验证(参见第 4 步)。

始终涵盖这些容易被遗漏的类别,每个类别都贴上标签,以便审阅者知道他们看到的是什么: alt 文本(屏幕阅读器和搜索引擎会读取它 — 合作伙伴/产品名称必须正确)、aria-label、表单占位符、提交按钮标签、成功/错误/验证消息、空状态、404/错误页面、版权声明和法律页脚。

将每个页面模板映射到其实际 URL 路径(routes.yaml、基于文件的路由、路由器配置、CMS 页面→模板分配)。如果模板没有对应的页面或路由,请在该页面的注释中明确说明 — 其文案不可访问,审阅者应在花费时间之前知晓。

然后根据 assets/pages.example.json 编写 <scratch>/pages.json:文档应呈现的顺序中每个页面一个条目,包含 key、title、url、source、可选的 note,以及 meta 块(项目、范围答案、排除项、没有硬编码文案的模板)。构建脚本读取此文件 — 页面元数据永远不会硬编码。

第 3 步 — 使用固定契约并行提取

  1. 首先枚举整个表面:每个页面模板 以及 这些页面包含的每个局部/共享组件(页眉、页脚、卡片、新闻简报表单、CTA)。局部组件是当文件在代理之间拆分时最容易丢失的部分。
  2. 拆分为非重叠的组(大约 3–6 个文件或大约 1,500 行),并明确分配每个文件。共享的局部组件获得自己的页面条目(例如 FOOTER、NAV),并附带说明它们出现在整个站点中,而不是在每个页面下重复。
  3. 在单次轮次中为每个组生成一个子代理,使用中端模型(例如 Sonnet):工作是机械性的,但遗漏是不可见的并且是致命的。将 references/extraction-brief.md 逐字粘贴到每个提示中,然后是该代理的文件列表、每个文件要使用的 page_key、仓库根目录以及输出路径 <scratch>/extract/<group>.json。
  4. 当它们返回时,确认每个枚举的文件都出现在某个输出中(或者被报告为不包含任何文案)。重新分配任何缺失的内容。

收集每个代理报告的判断;你将在第 4 步和最终报告中需要它们。

第 4 步 — 独立合并和验证(不要跳过)

代理自检不是验证。运行:

<venv>/bin/python scripts/merge_and_verify.py \
  --extract-dir <scratch>/extract --pages <scratch>/pages.json \
  --repo <repo-root> [--snapshot-dir <scratch>/snapshots] --out <scratch>/out

它按 pages.json 的顺序合并所有提取的内容,分配 PAGEKEY-NN 引用,重新计算 chars,并使用三种逐级宽松的规范化方法 — 原始(空白折叠)、标签剥离、空白压缩 — 重新检查每个字符串与其源文件,因为每种方法捕获不同的问题(属性文本会通过原始检查并且不会通过标签剥离检查,这是设计的;这是预期的)。它还断言不存在重复的引用、没有空文本,并且每个项目的 page_key 都存在于 pages.json 中。输出:items.json、copy-review-manifest.csv、verification.md。

只要有任何未解决的内容,退出代码为非零。对于每个 UNMATCHED 行,打开源码并查看。合法的残留通常是条件/循环块,其中代理记录了渲染后的文本而不是一个字面子字符串 — 确认它确实渲染为记录的内容,然后将其列在 <scratch>/accepted.json 中作为 {"REF": "reason"},并重新运行,带上 --accept <scratch>/accepted.json。修复提取 JSON 中的真正错误(而不是仓库),然后重新运行。引用在合并时分配,因此先修复数据,然后重新运行,最后构建。

还要抽查完整性:选择两三个最密集的文件,并将项目数与快速阅读文件的结果进行比较。缺失的字符串不会出现在任何自动检查中。

第 5 步 — 构建文档

<venv>/bin/python scripts/build_review_docx.py \
  --pages <scratch>/pages.json --items <scratch>/out/items.json \
  --out <scratch>/out/<Project>-Website-Copy-Review.docx

脚本拥有布局所有权,因此它在运行之间从不变化:横向 A4,1.4 cm 页边距;封面页(范围、包含/不包含的内容、如何审阅、保持长度敏感行靠近其长度、不要重新编号或删除引用、仔细检查事实 — 年份、员工数、数字、合作伙伴名称、职位 — 就像检查措辞一样仔细);目录,包含总数和空模板;每个页面在新页面上开始一个章节;列宽:引用 2.2 / 元素 4.3 / 当前文案 8.4 / 建议修订 8.4 / 注释 3.6 cm;深色重复表头行;彩色大写章节横幅行;斑马条纹;受约束行上的字符数指导;动态行上的彩色单元格和“保留 {{…}} 部分”警告;结尾页包含后续步骤和签收表。它会重新打开文件并断言行数匹配且修订/注释列为空。

永远不要预填充“建议修订”或“注释”。审阅者的判断才是关键。

如果用户在步骤 1 中选择了 Word 注释/修订,仍然构建此文档(引用码是使修订可追溯的关键),并告知他们编辑内容可能需要手动匹配。

第 6 步 — 交付前查看一下

结构检查证明数据是正确的,但不能证明它阅读体验良好。渲染并实际查看:封面页、设置/导航页面以及最密集的长段落页面(宽度可能不足的地方)。

soffice --headless --convert-to pdf --outdir <dir> <file>.docx
pdftoppm -png -r 80 -f <n> -l <n> <file>.pdf <prefix>

使用 Read 打开 PNG 文件。如果这些工具缺失,请明确说明没有进行视觉检查。

第 7 步 — 单独报告源代码缺陷

阅读每一行标记语言会暴露真正的缺陷。在一个单独的章节(或一个单独的 source-defects.md)中报告它们 — 它们是代码问题,不是措辞问题。常见的有:

  • 渲染的 HTML 中的字面 Markdown(页面上显示 **bold**)
  • 指向不存在的 ID 的锚点链接
  • 指向存在但包含不可操作内容的章节的链接
  • 没有页面/路由的模板,因此其文案不可访问
  • 位于覆盖它的自定义模板背后的孤立 CMS 内容
  • 在可复用模板中硬编码的占位符值

在报告之前亲自验证每一条 — 使用 grep 搜索目标 ID,打开模板。代理往往会夸大这些:一个“损坏的锚点”曾经被发现其目标存在,只是该章节没有可操作的内容。描述实际存在的内容,并包含文件和行号。

第 8 步 — 交付

将 .docx 文件发送给用户。简要提及:总项目数和页数、所做的范围决策、清单 CSV(用于按引用应用返回的编辑 — 保持它远离审阅者)、你接受的任何验证残留及其原因、缺陷列表,以及如果仓库存在该惯例则提及 issue-first 注释。

应用返回的修订(当用户回来时)

读取返回的 .docx 表格行(引用 + 建议修订 + 注释),按引用连接到 copy-review-manifest.csv,对于每个非空修订,定位 file 中靠近 line 的 text 并替换它。对于任何在受约束行上远远超过其 chars 的修订,以及任何删除了 {{…}} 表达式的修订,进行标记而不是静默截断。在编辑仓库之前向用户展示计划中的更改。

相关技能