Skip to content

docs-gen: 正文里裸露的 ../x.zod.ts 路径,../ 前缀被漏在链接外面 —— 2 张已发布参考页 #6229

Description

@os-zhuang

Blocked-by: #6136

在实施 #5553 / #6136(PR #6224)时,给渲染链补 pin 用例顺带扫出。与那两单不同根因、不同输入形态,故单独立单;PR #6224 已刻意绕开这条形态,没有 pin 它(pin 了等于追认),并在用例注释里指向本单。

现象(origin/main,PR #6224 落地后依然如此)

packages/spec/scripts/lib/file-description.ts 里把「正文中裸露的源码路径」改写成链接的那一步:

.replace(/(?<!\()\b((?:\.\.\/)?[\w-]+\/[\w.-]+\.zod\.ts)\b(?!\))/g, …)

\b 写在可选的 (?:\.\.\/)? 前面。匹配起点若落在 ../ 的第一个 . 上,前面是空格、当前是 .,两侧都不是单词字符,\b 不成立;于是引擎只能从 integration 这类标识符处起匹,../ 被留在链接外面。

落到已发布页面上(两处):

content/docs/references/api/http-cache.mdx
See also: ../../[system/cache.zod.ts](/docs/references/system/cache) for application-level caching

content/docs/references/system/cache.mdx
See also: ../../[automation/etl.zod.ts](/docs/references/api/http-cache) for HTTP-level caching

读者看到「另见」前面挂着一截裸的 ../../,链接文本也不是完整路径。

与 #6136 的区别(为什么不是同一条)

#6136 是无标题 {@link 路径} 先产出链接、改写器再包一层(链接套链接);修法是让改写器跳过已成型链接,PR #6224 已修。本单的输入里没有 {@link} —— 源码写的是裸标签 @see ../../system/cache.zod.ts(api/http-cache.zod.ts:35、system/cache.zod.ts:28),链接完全由这一步自己产出,../ 从一开始就没进去。#6224 修好后这两处仍在,可直接复现:

$ grep -rn '\.\./\[' content/docs/references/
api/http-cache.mdx:…  system/cache.mdx:…

两个叠加的子缺陷

  1. \b 位置错(如上),../ 掉在链接外。
  2. (?:\.\.\/)? 只写了一层,而实际语料用的是 ../../(跨 category 引用必然两层)。即便修好 (1),两层前缀也只能吃掉一层。

修法方向(未验证)

把可选前缀移到 \b 之外并允许重复,例如 ((?:\.\.\/)*[\w-]+\/[\w.-]+\.zod\.ts)\b,起点锚定改用「前面不是路径字符」的前瞻而非 \b。注意 sourcePathToDocsRoute()(build-docs.ts:278)本身用 (?:^|\/) 起匹,对 ../../a/b.zod.ts 已能正确解析出 category,所以路由侧无需改。

验收:grep -rn '\.\./\[' content/docs/references/ 归零,两句恢复成完整可点链接。渲染链已由 scripts/file-description.test.ts 覆盖,新用例可直接加在那里,不必跑整个生成器再 grep .mdx。

影响面

2 张已发布参考页的正文各一处,读者今天访问就能看到。纯展示层,无运行时/协议语义。


Generated by Claude Code

Activity

  1. claude commented on Aug 7, 2026

    @claude
    Contributor

    Triage: pm:blocked + Blocked-by: objectstack-ai/objectstack#6136. domain:spec-tooling was already correct and is kept; the missing half was a pm-state label — without one this issue was invisible to every queue view, which is the same gap #6188 and #6186 hit in earlier rounds.

    Stale-premise check — origin/main 72847c5

    Both halves hold, verbatim:

    • packages/spec/scripts/lib/file-description.ts:185 still reads
      /(?<!\()\b((?:\.\.\/)?[\w-]+\/[\w.-]+\.zod\.ts)\b(?!\))/g — \b before the optional (?:\.\.\/)?, one level only.
    • The two published pages still carry the naked prefix:
      content/docs/references/api/http-cache.mdx:52 and content/docs/references/system/cache.mdx:40.

    One correction to the acceptance criterion — it cannot be measured until #6136 lands

    The body proposes grep -rn '\.\./\[' content/docs/references/ going to zero as the acceptance. On main that grep returns 5 hits, not 2, and only 2 of them belong to this issue:

    file:line shape owner
    api/http-cache.mdx:52 ../../[system/cache.zod.ts](…) this issue
    system/cache.mdx:40 ../../[api/http-cache.zod.ts](…) this issue
    automation/etl.mdx:54 [../[integration/connector.zod.ts](…)](…) #6136 (nested link)
    integration/connector.mdx:102 [../[automation/etl.zod.ts](…)](…) #6136 (nested link)
    data/feed.mdx:16 `../[ui/component.zod.ts](…)` inside a code span #6136

    So the "zero hits" criterion is a joint criterion for #6136 + this issue, and running it before PR #6224 merges reports a failure this fix cannot cause. Whoever takes this should either wait for that merge (which the Blocked-by: enforces) or narrow the assertion to the two pages above.

    Why pm:blocked rather than pm:queue

    PR #6224 (#5553 / #6136, pm:dispatched) is in flight and edits the same rewriter chain in the same file — the {@link …} passes at :178/:180 immediately above, and it changes what reaches :185. Two devs on file-description.ts at once is the merge race step 3 serializes on. The body already records that #6224 deliberately did not pin this shape (pinning it would have ratified it) and points at this issue from its test comments, so the ordering is the filer's intent too. Unblocks when #6136 closes.

    Not on the release board

    Presentation-only, two reference pages, no runtime or protocol semantics — improvement class, not a blocker under any of the four criteria. It is cheap and visible, so it will likely ride the next spec-tooling batch on its merits rather than on a board label.

    Dedup (three repos, open issues and PRs)

    ⚠️ The GitHub search API is not reachable from this seat (/search/issues answers "sessions are bound to their configured repositories", returning a structurally empty result rather than an error). Dedup was done by paginating all 442 open issues and PRs across the three repos and matching locally on file-description, docs-gen, ../[.

    The docs-gen family is crowded, and all three neighbours are distinct inputs to the same renderer — no duplicate: #6136 (untitled {@link} → nested link; the dependency above), #5553 (JSDoc line layout, same PR #6224), #5853 (getCategoryTitle() capitalisation). This issue is the only one whose input carries no {@link} at all — the link is produced entirely by the :185 rewriter, which is why it survives #6224.

    本评论来自分诊座位 Routine(#5474 试点),不构成认领。


    Generated by Claude Code

  2. self-assigned this
    on Aug 7, 2026
  3. os-zhuang commented on Aug 7, 2026

    @os-zhuang
    ContributorAuthor

    认领 / Claim — os-dev agent

    • Session: session_014wsZeReNTqiceBfLb5Pyf5
    • Branch: claude/issue-6229-bare-path-parent-prefix
    • Worktree: ../objectstack-issue-6229

    阻塞已解除(#6136 由 PR #6224 合入)。开始前会在当前 origin/main 上重新核验缺陷是否仍复现,并以实际行号与实际正则为准(issue 正文中的正则被 GitHub body sanitizer 破坏,不可直接引用)。


    Generated by Claude Code

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

documentationImprovements or additions to documentationpm:queue

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions