资讯详情

深入 get-shit-done:ROADMAP 解析器如何依据 GFM 围栏语义免疫嵌套代码块中的伪 Phase 标题

📅 2026/9/10 2:46:35 | 华诺云谱 👁 阅读
深入 get-shit-done:ROADMAP 解析器如何依据 GFM 围栏语义免疫嵌套代码块中的伪 Phase 标题
深入 get-shit-doneROADMAP 解析器如何依据 GFM 围栏语义免疫嵌套代码块中的伪 Phase 标题【免费下载链接】get-shit-doneA light-weight and powerful meta-prompting, context engineering and spec-driven development system for Claude Code by TÂCHES.项目地址: https://gitcode.com/GitHub_Trending/getshi/get-shit-done导读本篇文章以 get-shit-done 仓库中的对抗性解析测试夹具nested-fenced-code.md为主线剖析 ROADMARK 解析器在遭遇嵌套围栏代码块这一恶意/混乱输入时如何保证只识别真实阶段标题。你将理解 GFM 围栏的开关语义开围栏可带 info string、闭围栏必须同字符且无附加文本、双解析器CJS 正则解析器与 SDK TypeScript 解析器的实现差异以及如何通过对抗性测试把已知缺陷固定为回归防线。读完即可在自己的规格驱动开发工具链中复刻这套先剥离代码块、再匹配阶段标题的防御思路。一、问题背景代码块里的假 Phase为什么是真实威胁get-shit-done 是面向 Claude Code 的规格驱动开发系统其核心规划文件ROADMAP.md由解析器以正则扫描## Phase N: Name形式的标题来定位阶段Phase。一旦某个真实项目的ROADMAP.md中嵌入了文档片段、示例或运行手册——它们恰好以代码块fenced code block形式包含形如## Phase 999: ...的标题行解析器若不加区分地匹配就会出现两类故障遮蔽真实阶段## Phase 999之类的假标题抢占了阶段命名空间或干扰当前里程碑切片的边界判断导致后续真实阶段被截断、隐藏结果不可复现同一份 ROADMAP 在不同解析器CJS 命令行工具与 SDK 查询层中返回不同结果破坏下游工作流的确定性。这正是历史回归#2787记录的教训代码块内的标题曾长期干扰阶段解析。仓库在 tests/fixtures/adversarial/roadmap/README.md 中把该回归及其同类问题整理为对抗性 ROADMAP 输入Adversarial Roadmap Fixtures#3594测试集nested-fenced-code.md就是其中专门考察嵌套围栏的用例。二、夹具逐行解剖四层反引号包裹三层反引号关联文档 tests/fixtures/adversarial/roadmap/nested-fenced-code.md 全文如下它被刻意设计为每个围栏层内都藏着假阶段标题# Roadmap md Outer block opened with four backticks. md ## Phase 998: nested fake phase Inner block opened with three backticks. ## Phase 997: outer fake phase Still inside the outer four-tick block — the three-tick close above does NOT terminate it. ## Phase 1: real phase **Goal:** the only real phase in this file.夹具的构造意图非常明确外层围栏以 4 个反引号开启并携带 info stringmd内部藏有## Phase 997: outer fake phase内层围栏以 3 个反引号开启内部藏有## Phase 998: nested fake phase内层那 3 个反引号的闭合符无法终止外层 4 反引号围栏——这正是 GFM 围栏语义的关键详见第四节只有文件末尾的## Phase 1: real phase是真实阶段夹具注释明示 the only real phase in this file。按 tests/fixtures/adversarial/roadmap/README.md 的规范Headings inside either layer must be ignored——两层围栏内的标题都必须被忽略这就是本夹具的不变量。三、测试如何固定行为从夹具到gsd-tools roadmap get-phase夹具本身不产生行为行为由消费它的测试定义。tests/feat-3594-parser-adversarial-roadmap.test.cjs 是这批对抗性测试的载体它把每个夹具当作临时项目的.planning/ROADMAP.md写入再通过公开 CLI 面gsd-tools roadmap get-phase N断言返回的结构化 JSON 载荷而非 stderr 文案测试断言目标是 the typed JSON shape the CLI emits。nested-fenced-code.md具体被两类测试消费跨语料不变量测试roadmap parser does not crash on ANY corpus fixture遍历tests/fixtures/adversarial/roadmap/下所有.md夹具对每个夹具依次查询[1, 2, 99, 999, 0, 2.1]唯一硬性断言是hasStackTrace false——解析器面对任何恶意输入不得抛出 V8 堆栈退出码为 0找到或非 0未找到都是合法结果。这保证了嵌套围栏这类畸形结构不会击穿解析链路同主题显式用例夹具phase-heading-inside-fenced-code.md单层围栏版的测试直接验证真实阶段 1 在存在围栏内假阶段 999 时依然能被找到且当前 CJS 解析器对围栏内Phase 999仍然会命中——测试以注释明示 open: needs fence-stripping 固定了这一已知缺陷。嵌套夹具则是该问题的更深一层变体。测试文件头部还明确了纪律这些夹具暴露出的既有解析器缺陷并不在本 PR 内修复测试只固定当前观察到的行为一旦未来真正修复落地从 RED 翻 GREEN 只需改动一行断言。这是把已知 bug变成回归防线的工程实践。四、GFM 围栏语义与isInsideFencedCodeBlock源码实现要正确忽略嵌套围栏内的标题首先必须精确判定某个位置是否位于代码块内部。SDK 解析器在 sdk/src/query/roadmap.ts 提供了核心工具函数isInsideFencedCodeBlock(content, offset)其注释完整阐述了 GFM 围栏语义bug #2787开围栏以至少 3 个反引号或 3 个波浪号开头的行允许附带 info string如md、~~~markdown闭围栏以至少 3 个同字符开头的行且不允许携带 info string——所以js出现在一个text围栏内部时并不会将其闭合状态机从内容开头逐行走到目标 offset用fenceChar游标记录当前围栏字符或~游标为 null 表示在代码块外非 null 表示在代码块内。对应实现逐行扫描、以换行符切分、对每行执行^(\{3,}|~{3,})(\s*)([^\n]*)$匹配并按上述规则切换状态。这一语义直接解释了本夹具的行为外层 4 反引号开围栏后内层 3 反引号闭围栏虽然字符相同但 4 3——按正则{3,} 它仍匹配开围栏判定而 GFM 规则要求闭围栏长度至少等于开围栏才生效因此内层 3 反引号行既关闭不了外层、又开启了一个新的字符相同的内层围栏最终整个文本块都处于代码块内状态。isInsideFencedCodeBlock被extractCurrentMilestone同文件 sdk/src/query/roadmap.ts用于里程碑边界扫描当扫描到疑似下一个里程碑标题时先用它检查该位置是否在代码块内sdk/src/query/roadmap.ts是则跳过继续扫描。注释里给出了真实事故场景一行# Ops runbook — v1.0 compat出现在bash内会把里程碑切片截断隐藏其后所有阶段。五、双解析器架构下的差异SDK 已跟踪围栏CJS 仍待补齐get-shit-done 存在两套 ROADMAP 解析入口解析器位置阶段标题匹配围栏处理CJS 命令行工具get-shit-done/bin/lib/roadmap.cjssearchPhaseInContent#{2,4}\s*Phase\sX:\s*...不剥离围栏会命中围栏内假标题已知缺陷测试固定之SDK TypeScript 查询层sdk/src/query/roadmap.tssearchPhaseInContent与roadmapGetPhase同构正则 前缀精确匹配两段式里程碑边界扫描已接入isInsideFencedCodeBlock#2787阶段标题级剥离尚未覆盖测试代码在feat-3594的 fenced-code-block 用例中明确记录了该差距The CJS regex parser does not strip fenced code blocks before matching. The SDK roadmap parser tracks fenced blocks (per #2787 comment in sdk/src/query/roadmap.ts) — the CJS path has not caught up. 测试以assert.equal(result.parsed.found, true)固定 CJS 当前会命中围栏内Phase 999的行为并断言返回的phase_name必须匹配围栏内标题的特征子串防止未来修复时误匹配到一个并不存在的真实阶段 999仍蒙混过关。这种测试为已知 bug 立碑的做法保证了缺陷修复时刻的翻转一定是语义正确的。此外roadmapGetPhase的两段式查找sdk/src/query/roadmap.ts还体现了对畸形 ROADMAP 的兜底先在当前里程碑切片经extractCurrentMilestone处理内查找再回退到全量内容经stripShippedMilestones剔除已发布里程碑查找最后才返回{ found: false }避免一个假标题或陈旧切片掩盖真实阶段。六、围栏防御之外的对抗测试全景nested-fenced-code.md只是 #3594 对抗性测试集的一员tests/fixtures/adversarial/roadmap/README.md 完整列出了全部类别它们共同构成 ROADMAP 解析器的恶意输入防火墙phase-heading-inside-fenced-code.md单层块内藏## Phase 999: fake历史回归 #2787nested-fenced-code.md外层 4 反引号 内层 3 反引号两层标题都必须忽略本文主角unicode-phase-titles.md非 ASCII 阶段标题必须原样保留在phase_name测试断言日文、emoji 智能引号、希腊字母全部往返无损repeated-phase-ids.md同一阶段号出现两次解析行为必须确定当前为 first-wins测试固定decimal-phase-mixed.md整数阶段 2 与小数阶段 2.1/2.10 前缀共享查询必须精确命中各自目标历史回归 #3537配套phaseMarkdownRegexSource的补零容忍片段markdown-headings-inside-html-comment.md!-- ## Phase 999 --注释内的标题不得误导解析器。再叠加 tests/fixtures/adversarial/frontmatter重复键、CRLF、空字节、未闭合块等与 tests/fixtures/adversarial/security上下文注入、伪造 frontmatter、heredoc 逃逸等可见该项目把解析器输入卫生当作一等公民对待。七、实战启示如何为自己的 Markdown 解析器加入围栏免疫从本夹具及其实现中可提炼出三条可直接复用的工程结论先判围栏、再扫标题任何 Markdown 结构化解析阶段、里程碑、章节边界都应先建立当前是否在代码块内的游标状态再决定标题行是否有效GFM 闭围栏同字符 无 info string 长度不小于开围栏三条规则缺一不可。对抗性夹具要分层嵌套单层围栏测试只能覆盖简单场景像nested-fenced-code.md这样构造内层闭围栏无法终止外层开围栏的嵌套用例才能逼出状态机实现中真正的边界条件错误。为已知缺陷写固定行为测试当缺陷暂时无法修复时用断言钉死当前行为并注释开放问题编号#2787比放任未定义行为更利于后续定位与翻转。验证路径要亲手复现本夹具的行为可将 tests/fixtures/adversarial/roadmap/nested-fenced-code.md 的内容写入某项目的.planning/ROADMAP.md依次运行gsd-tools roadmap get-phase 1应返回真实阶段与任意伪造编号应返回found: false或命中围栏内假标题的当前 CJS 行为再运行 tests/feat-3594-parser-adversarial-roadmap.test.cjs 验证跨语料不崩溃的不变量。【免费下载链接】get-shit-doneA light-weight and powerful meta-prompting, context engineering and spec-driven development system for Claude Code by TÂCHES.项目地址: https://gitcode.com/GitHub_Trending/getshi/get-shit-done创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
📝

华诺云谱内容团队

资深建站顾问 · 行业研究员

10年+企业数字化服务经验,专注智能建站、SEO优化与品牌营销,持续输出建站技巧、行业洞察与营销干货,已帮助5000+企业实现数字化增长。

你可能需要的服务

订阅华诺云谱资讯周报

每周一封,精选建站技巧、SEO与营销干货,直达邮箱。已有 8,000+ 企业主订阅,助你少走弯路。