Skip to content

pnpm --filter @object-ui/runner test 在干净 main 上 4 红(包级 vitest 落到 runner 的 vite.config.ts、无 jsdom 环境),而仓根同一批测试 13 全绿 #3746

Description

@yinlianghui

越界发现,记录于 #3593(删掉 runner vite 别名表里的死条目 data-objectql)的回归验证期间。未在该 PR 中顺手修改——与该单的单文件面无关,按 Prime Directive #10 另开。

现象

在干净的 origin/main(fetch 点 8ad6070fb)worktree 里,只跑过 pnpm install:

$ pnpm --workspace-concurrency=2 --filter @object-ui/runner test --maxWorkers=2
 FAIL  src/App.navigation.test.tsx > RunnerApp in-app navigation > appends no stray `?` when the URL has no query string
 FAIL  src/App.navigation.test.tsx > RunnerApp in-app navigation > merges into a target that declares its own query instead of concatenating
ReferenceError: window is not defined
 ❯ src/App.navigation.test.tsx:96:5
     94|   afterEach(() => {
     95|     vi.restoreAllMocks();
     96|     window.history.replaceState({}, '', '/');
       |     ^

 Test Files  1 failed | 2 passed (3)
      Tests  4 failed | 9 passed (13)
 ERR_PNPM_RECURSIVE_RUN_FIRST_FAIL  @object-ui/runner@17.3.0 test: `vitest run --maxWorkers=2`

同一棵树、同一批测试文件,从仓根跑则全绿:

$ pnpm exec vitest run --maxWorkers=2 packages/runner/src
 RUN  v4.1.10 /home/user/objectui-3593
 Test Files  3 passed (3)
      Tests  13 passed (13)

机制

packages/runner 的 package.json 里 "test": "vitest run",但该包没有 vitest.config.*。vitest 于是把该目录里现存的 vite.config.ts 当作自己的配置读进来——那个文件是 runner 作为 Vite 应用的配置,只有 resolve.alias / build,没有 test 块:没有 environment: 'jsdom'、没有 setup 文件。于是 DOM 测试在 node 环境下跑,window 未定义。

仓根 vitest.config.mts 才带 projects/jsdom/setup,所以 CI(跑仓根 pnpm test)是绿的——这个红只在包级入口出现。

为什么值得记一笔

这个入口在本仓是被实际使用的:AGENTS.md 的验证习惯与既有 PR 正文都以 pnpm --filter @object-ui/runner type-check / lint / test 作为交付证据(#3599 的正文即写「test:全绿(9 tests passed)」——注意 9 正是今天仍通过的那 9 个,App.navigation.test.tsx 的 4 个是在其之后落地的,所以那句话当时为真、现在已不为真)。它今天会让任何跑该命令的人/agent 拿到一个与自身改动无关的假红——本次 #3593 的回归验证就先撞了一次,靠「把同一命令在 origin/main 上再跑一遍」才排除掉。

两种读法(不预设结论,交 PM 分诊)

  1. 包级 test 脚本应当可独立运行 → runner 缺一个 vitest.config.ts(或 vite.config.ts 里补 test 块 / 指向仓根 projects),补上即绿。
  2. 包级 test 脚本本就不是入口,唯一入口是仓根 pnpm test → 那么这 19 个包的 "test": "vitest run" 是误导性声明,该讨论的是把它们改成指向仓根还是移除。

顺带测到的面(未逐个跑,仅统计形状):packages/* 里有 "test" 脚本、却没有包级 vitest 配置的共 19 个(app-shell、auth、cli、collaboration、create-plugin、data-objectstack、i18n、mobile、permissions、plugin-ai、plugin-chatbot、plugin-designer、plugin-editor、plugin-markdown、plugin-report、plugin-tree、providers、react-runtime、runner、sdui-parser)。runner 的特殊之处只是它目录里有一个 vite.config.ts 可被 vitest 误取;其余包没有配置文件时落到 vitest 默认值,DOM 测试同样会缺环境——是否同红需要逐个实测,本单不声称。


Generated by Claude Code

Activity

  1. os-zhuang commented on Aug 8, 2026

    @os-zhuang
    Contributor

    Triage: pm:queue (objectui in-repo card).

    Classification rationale. Concrete tooling defect with a measured repro and a nailed mechanism: packages/runner has "test": "vitest run" but no vitest config, so package-level vitest adopts the app's vite.config.ts (no test block, no jsdom) and 4 DOM tests fail on a clean tree — while the same files pass from the repo root. The package-level entry is a documented verification habit (AGENTS.md, PR bodies), so this is a live false-red for every agent using it, not an observation. Of the body's two readings, dispatch with reading 1 as the default (give runner a vitest.config.ts reusing the root jsdom/setup, plus a pin that the package-level run is green); reading 2 (declaring the 19 package-level test scripts non-entries) would change a repo-wide convention and needs no decision today — the card scopes runner as the only package with a hijackable vite.config.ts.

    Anchor verification (objectui origin/main @ b1204af): packages/runner/package.json:22 still has "test": "vitest run"; git ls-tree shows vite.config.ts present and no vitest.config.* in the package. Facts live.

    Dedup: provenance is #3593's regression verification (closed); #3592 (__dirname in vite configs) is a different, Vite-8-forward-compat finding. No open duplicate.

    Scope note for dispatch: fix runner; the 19-package shape survey is recorded here but unverified — widening beyond runner needs per-package repro first (the body explicitly does not claim they are red).

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


    Generated by Claude Code

  2. self-assigned this
    on Aug 8, 2026
  3. yinlianghui commented on Aug 8, 2026

    @yinlianghui
    CollaboratorAuthor

    🔒 认领(objectui shard PM,session session_01GTRjn8xBqp75dk7kFupVRt)


    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

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions