oh-my-opencode 4.15.1 → 4.16.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.agents/skills/codex-qa/SKILL.md +9 -7
- package/.agents/skills/codex-qa/references/logging-debug.md +6 -4
- package/.agents/skills/opencode-qa/SKILL.md +9 -9
- package/.agents/skills/opencode-qa/references/tui-tmux.md +10 -8
- package/dist/cli/codex-ulw-loop.d.ts +8 -0
- package/dist/cli/doctor/checks/tui-plugin-config.d.ts +4 -4
- package/dist/cli/get-local-version/types.d.ts +1 -1
- package/dist/cli/index.js +792 -744
- package/dist/cli/install-senpi/index.d.ts +1 -0
- package/dist/cli/run/poll-for-completion.d.ts +4 -0
- package/dist/cli/run/session-resolver.d.ts +1 -0
- package/dist/cli/senpi-platform-flag.d.ts +4 -0
- package/dist/cli/types.d.ts +2 -1
- package/dist/cli-node/index.js +792 -744
- package/dist/features/background-agent/manager.d.ts +16 -0
- package/dist/features/builtin-commands/templates/start-work.d.ts +1 -1
- package/dist/features/monitor/process.d.ts +17 -1
- package/dist/hooks/anthropic-context-window-limit-recovery/aggressive-truncation-strategy.d.ts +1 -0
- package/dist/index.js +2206 -1971
- package/dist/skills/debugging/references/methodology/06-fix.md +6 -0
- package/dist/skills/frontend/ATTRIBUTION.md +10 -1
- package/dist/skills/frontend/SKILL.md +12 -7
- package/dist/skills/frontend/references/design/README.md +8 -4
- package/dist/skills/frontend/references/design/_INDEX.md +2 -2
- package/dist/skills/frontend/references/design/design-system-architecture.md +24 -2
- package/dist/skills/frontend/references/design/lazyweb.md +77 -0
- package/dist/skills/frontend/references/design/stitch-design-example.md +121 -0
- package/dist/skills/frontend/references/designpowers/README.md +2 -2
- package/dist/skills/frontend/references/designpowers/lane-b-execution.md +1 -1
- package/dist/skills/programming/SKILL.md +10 -1
- package/dist/skills/programming/references/logging.md +91 -0
- package/dist/skills/start-work/SKILL.md +2 -2
- package/dist/skills/ulw-plan/SKILL.md +5 -5
- package/dist/skills/ulw-plan/references/full-workflow.md +7 -7
- package/dist/skills/ulw-plan/references/intent-unclear.md +3 -3
- package/dist/skills/ulw-research/ATTRIBUTION.md +2 -2
- package/dist/skills/ulw-research/SKILL.md +28 -7
- package/dist/skills/visual-qa/SKILL.md +13 -17
- package/dist/tools/skill/description-formatter.d.ts +1 -0
- package/dist/tools/skill/description-formatter.test-support.d.ts +9 -0
- package/dist/tools/skill/zauc-mocks-skill-tools/test-support.d.ts +25 -0
- package/dist/tui.js +121 -419
- package/docs/reference/web-terminal-visual-qa.md +39 -45
- package/package.json +48 -25
- package/packages/git-bash-mcp/dist/cli.js +2 -2
- package/packages/omo-codex/plugin/.codex-plugin/plugin.json +1 -1
- package/packages/omo-codex/plugin/components/bootstrap/AGENTS.md +55 -0
- package/packages/omo-codex/plugin/components/bootstrap/dist/cli.js +19 -16
- package/packages/omo-codex/plugin/components/bootstrap/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/bootstrap/package.json +1 -1
- package/packages/omo-codex/plugin/components/codegraph/AGENTS.md +51 -0
- package/packages/omo-codex/plugin/components/codegraph/dist/cli.js +936 -248
- package/packages/omo-codex/plugin/components/codegraph/dist/serve.js +233 -135
- package/packages/omo-codex/plugin/components/codegraph/package.json +1 -1
- package/packages/omo-codex/plugin/components/codegraph/src/cache-gc.ts +29 -0
- package/packages/omo-codex/plugin/components/codegraph/src/cli.ts +13 -0
- package/packages/omo-codex/plugin/components/codegraph/src/hook-sweep.ts +25 -0
- package/packages/omo-codex/plugin/components/codegraph/src/hook-types.ts +3 -1
- package/packages/omo-codex/plugin/components/codegraph/src/hook.ts +30 -1
- package/packages/omo-codex/plugin/components/codegraph/src/serve.ts +16 -2
- package/packages/omo-codex/plugin/components/codegraph/src/sweep-cli.ts +80 -0
- package/packages/omo-codex/plugin/components/codegraph/test/cache-gc.test.ts +34 -0
- package/packages/omo-codex/plugin/components/codegraph/test/hook-exclusion.test.ts +107 -0
- package/packages/omo-codex/plugin/components/codegraph/test/hook-registration.test.ts +26 -0
- package/packages/omo-codex/plugin/components/codegraph/test/hook-sweep.test.ts +29 -0
- package/packages/omo-codex/plugin/components/codegraph/test/hook.test.ts +8 -21
- package/packages/omo-codex/plugin/components/codegraph/test/mcp-bridge-fixtures.ts +108 -0
- package/packages/omo-codex/plugin/components/codegraph/test/serve-built-wrapper.test.ts +76 -0
- package/packages/omo-codex/plugin/components/codegraph/test/serve-mcp-bridge.test.ts +17 -111
- package/packages/omo-codex/plugin/components/codegraph/test/serve-provision.test.ts +1 -1
- package/packages/omo-codex/plugin/components/codegraph/test/serve.test.ts +45 -67
- package/packages/omo-codex/plugin/components/codegraph/test/sweep-cli.test.ts +56 -0
- package/packages/omo-codex/plugin/components/comment-checker/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/comment-checker/package.json +1 -1
- package/packages/omo-codex/plugin/components/git-bash/AGENTS.md +31 -0
- package/packages/omo-codex/plugin/components/git-bash/hooks/hooks.json +2 -2
- package/packages/omo-codex/plugin/components/git-bash/package.json +1 -1
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/AGENTS.md +45 -0
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/package.json +1 -1
- package/packages/omo-codex/plugin/components/lsp/hooks/hooks.json +2 -2
- package/packages/omo-codex/plugin/components/lsp/package.json +1 -1
- package/packages/omo-codex/plugin/components/rules/bundled-rules/hephaestus.md +37 -102
- package/packages/omo-codex/plugin/components/rules/hooks/hooks.json +4 -4
- package/packages/omo-codex/plugin/components/rules/package.json +1 -1
- package/packages/omo-codex/plugin/components/start-work-continuation/directive.md +2 -2
- package/packages/omo-codex/plugin/components/start-work-continuation/hooks/hooks.json +2 -2
- package/packages/omo-codex/plugin/components/start-work-continuation/package.json +1 -1
- package/packages/omo-codex/plugin/components/teammode/AGENTS.md +46 -0
- package/packages/omo-codex/plugin/components/teammode/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/teammode/package.json +1 -1
- package/packages/omo-codex/plugin/components/telemetry/dist/cli.js +6 -0
- package/packages/omo-codex/plugin/components/telemetry/dist/posthog.js +6 -0
- package/packages/omo-codex/plugin/components/telemetry/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/telemetry/package.json +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/AGENTS.md +5 -2
- package/packages/omo-codex/plugin/components/ultrawork/CHANGELOG.md +2 -0
- package/packages/omo-codex/plugin/components/ultrawork/README.md +3 -3
- package/packages/omo-codex/plugin/components/ultrawork/directive.md +18 -10
- package/packages/omo-codex/plugin/components/ultrawork/dist/cli.js +51 -2
- package/packages/omo-codex/plugin/components/ultrawork/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/package.json +2 -1
- package/packages/omo-codex/plugin/components/ultrawork/scripts/sync-directive.mjs +14 -1
- package/packages/omo-codex/plugin/components/ultrawork/skills/ultrawork/SKILL.md +388 -0
- package/packages/omo-codex/plugin/components/ultrawork/skills/ulw-plan/SKILL.md +16 -2
- package/packages/omo-codex/plugin/components/ultrawork/skills/ulw-plan/references/full-workflow.md +4 -4
- package/packages/omo-codex/plugin/components/ultrawork/skills/ulw-plan/references/intent-unclear.md +2 -2
- package/packages/omo-codex/plugin/components/ultrawork/src/codex-hook.ts +5 -3
- package/packages/omo-codex/plugin/components/ultrawork/src/skill-pointer.ts +56 -0
- package/packages/omo-codex/plugin/components/ultrawork/test/codex-hook.test.ts +26 -5
- package/packages/omo-codex/plugin/components/ultrawork/test/directive-source.test.ts +12 -0
- package/packages/omo-codex/plugin/components/ultrawork/test/package-smoke.test.ts +1 -0
- package/packages/omo-codex/plugin/components/ultrawork/test/skill-pointer.test.ts +82 -0
- package/packages/omo-codex/plugin/components/ulw-loop/CHANGELOG.md +5 -0
- package/packages/omo-codex/plugin/components/ulw-loop/directive.md +18 -10
- package/packages/omo-codex/plugin/components/ulw-loop/dist/cli-commands.js +15 -2
- package/packages/omo-codex/plugin/components/ulw-loop/dist/cli-steering.js +2 -1
- package/packages/omo-codex/plugin/components/ulw-loop/dist/cli.js +145 -32
- package/packages/omo-codex/plugin/components/ulw-loop/dist/codex-hook.d.ts +1 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/codex-hook.js +5 -1
- package/packages/omo-codex/plugin/components/ulw-loop/dist/plan-io.d.ts +6 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/plan-io.js +55 -9
- package/packages/omo-codex/plugin/components/ulw-loop/dist/steering-snapshot.d.ts +15 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/steering-snapshot.js +33 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/steering-types.d.ts +10 -3
- package/packages/omo-codex/plugin/components/ulw-loop/dist/steering.js +15 -11
- package/packages/omo-codex/plugin/components/ulw-loop/dist/ultrawork-directive.d.ts +2 -1
- package/packages/omo-codex/plugin/components/ulw-loop/dist/ultrawork-directive.js +5 -3
- package/packages/omo-codex/plugin/components/ulw-loop/dist/ultrawork-skill-pointer.d.ts +7 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/ultrawork-skill-pointer.js +46 -0
- package/packages/omo-codex/plugin/components/ulw-loop/hooks/hooks.json +2 -2
- package/packages/omo-codex/plugin/components/ulw-loop/package.json +1 -1
- package/packages/omo-codex/plugin/components/ulw-loop/skills/ulw-loop/SKILL.md +1 -1
- package/packages/omo-codex/plugin/components/ulw-loop/skills/ulw-loop/references/full-workflow.md +7 -7
- package/packages/omo-codex/plugin/components/ulw-loop/src/cli-commands.ts +17 -2
- package/packages/omo-codex/plugin/components/ulw-loop/src/cli-steering.ts +2 -1
- package/packages/omo-codex/plugin/components/ulw-loop/src/codex-hook.ts +5 -1
- package/packages/omo-codex/plugin/components/ulw-loop/src/plan-io.ts +59 -11
- package/packages/omo-codex/plugin/components/ulw-loop/src/steering-snapshot.ts +38 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/steering-types.ts +11 -3
- package/packages/omo-codex/plugin/components/ulw-loop/src/steering.ts +15 -7
- package/packages/omo-codex/plugin/components/ulw-loop/src/ultrawork-directive.ts +9 -3
- package/packages/omo-codex/plugin/components/ulw-loop/src/ultrawork-skill-pointer.ts +55 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-create-goals.test.ts +16 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/plan-io.test.ts +260 -2
- package/packages/omo-codex/plugin/components/ulw-loop/test/steering-snapshot.test.ts +124 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/steering.test.ts +101 -2
- package/packages/omo-codex/plugin/components/ulw-loop/test/ultrawork-directive.test.ts +49 -0
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-git-bash-mcp-reminder.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-lsp-diagnostics-cache.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-project-rule-cache.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-codegraph-init-guidance.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-comments.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-lsp-diagnostics.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-thread-title-hygiene.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-matching-project-rules.json +1 -1
- package/packages/omo-codex/plugin/hooks/pre-tool-use-enforcing-unlimited-goal-budget.json +1 -1
- package/packages/omo-codex/plugin/hooks/pre-tool-use-recommending-git-bash-mcp.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-checking-auto-update.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-checking-bootstrap-provisioning.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-checking-codegraph-bootstrap.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-loading-project-rules.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-recording-session-telemetry.json +1 -1
- package/packages/omo-codex/plugin/hooks/stop-checking-start-work-continuation.json +1 -1
- package/packages/omo-codex/plugin/hooks/subagent-stop-checking-start-work-continuation.json +1 -1
- package/packages/omo-codex/plugin/hooks/subagent-stop-verifying-lazycodex-executor-evidence.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-checking-ultrawork-trigger.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-checking-ulw-loop-steering.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-loading-project-rules.json +1 -1
- package/packages/omo-codex/plugin/package-lock.json +13 -13
- package/packages/omo-codex/plugin/package.json +1 -1
- package/packages/omo-codex/plugin/scripts/build-components.mjs +63 -17
- package/packages/omo-codex/plugin/scripts/hook-status-message.mjs +10 -6
- package/packages/omo-codex/plugin/scripts/materialize-shared-upstreams.mjs +10 -3
- package/packages/omo-codex/plugin/scripts/sync-skills.mjs +1 -0
- package/packages/omo-codex/plugin/shared/test/config-loader.test.ts +18 -0
- package/packages/omo-codex/plugin/skills/debugging/references/methodology/06-fix.md +6 -0
- package/packages/omo-codex/plugin/skills/frontend/ATTRIBUTION.md +10 -1
- package/packages/omo-codex/plugin/skills/frontend/SKILL.md +12 -7
- package/packages/omo-codex/plugin/skills/frontend/references/design/README.md +8 -4
- package/packages/omo-codex/plugin/skills/frontend/references/design/_INDEX.md +2 -2
- package/packages/omo-codex/plugin/skills/frontend/references/design/design-system-architecture.md +24 -2
- package/packages/omo-codex/plugin/skills/frontend/references/design/lazyweb.md +77 -0
- package/packages/omo-codex/plugin/skills/frontend/references/design/stitch-design-example.md +121 -0
- package/packages/omo-codex/plugin/skills/frontend/references/designpowers/README.md +2 -2
- package/packages/omo-codex/plugin/skills/frontend/references/designpowers/lane-b-execution.md +1 -1
- package/packages/omo-codex/plugin/skills/programming/SKILL.md +10 -1
- package/packages/omo-codex/plugin/skills/programming/references/logging.md +91 -0
- package/packages/omo-codex/plugin/skills/start-work/SKILL.md +2 -2
- package/packages/omo-codex/plugin/skills/ultrawork/SKILL.md +388 -0
- package/packages/omo-codex/plugin/skills/ultrawork/agents/openai.yaml +2 -0
- package/packages/omo-codex/plugin/skills/ulw-loop/SKILL.md +1 -1
- package/packages/omo-codex/plugin/skills/ulw-loop/references/full-workflow.md +7 -7
- package/packages/omo-codex/plugin/skills/ulw-plan/SKILL.md +16 -2
- package/packages/omo-codex/plugin/skills/ulw-plan/references/full-workflow.md +4 -4
- package/packages/omo-codex/plugin/skills/ulw-plan/references/intent-unclear.md +2 -2
- package/packages/omo-codex/plugin/skills/ulw-research/ATTRIBUTION.md +2 -2
- package/packages/omo-codex/plugin/skills/ulw-research/SKILL.md +28 -7
- package/packages/omo-codex/plugin/skills/visual-qa/SKILL.md +13 -17
- package/packages/omo-codex/plugin/test/aggregate-hooks.test.mjs +4 -4
- package/packages/omo-codex/plugin/test/bootstrap-hooks.test.mjs +1 -1
- package/packages/omo-codex/plugin/test/hook-status-message.test.mjs +22 -9
- package/packages/omo-codex/plugin/test/install-time-build-runtime.test.mjs +1 -1
- package/packages/omo-codex/plugin/test/sync-hook-status-messages.test.mjs +6 -6
- package/packages/omo-codex/plugin/test/sync-skills-test-support.mjs +2 -0
- package/packages/omo-codex/plugin/test/ultrawork-skill-pointer.test.mjs +56 -0
- package/packages/omo-codex/plugin/test/ulw-plan-skill-contract.test.mjs +52 -0
- package/packages/omo-codex/plugin/test/ulw-research-epistemic-contract.test.mjs +98 -0
- package/packages/omo-codex/plugin/test/ulw-research-skill-contract.test.mjs +6 -6
- package/packages/omo-codex/scripts/install-dist/install-local.mjs +310 -3979
- package/packages/omo-codex/scripts/install-lazycodex-version-stamp.test.mjs +2 -2
- package/packages/shared-skills/skills/debugging/references/methodology/06-fix.md +6 -0
- package/packages/shared-skills/skills/frontend/ATTRIBUTION.md +10 -1
- package/packages/shared-skills/skills/frontend/SKILL.md +12 -7
- package/packages/shared-skills/skills/frontend/references/design/README.md +8 -4
- package/packages/shared-skills/skills/frontend/references/design/_INDEX.md +2 -2
- package/packages/shared-skills/skills/frontend/references/design/design-system-architecture.md +24 -2
- package/packages/shared-skills/skills/frontend/references/design/lazyweb.md +77 -0
- package/packages/shared-skills/skills/frontend/references/design/stitch-design-example.md +121 -0
- package/packages/shared-skills/skills/frontend/references/designpowers/README.md +2 -2
- package/packages/shared-skills/skills/frontend/references/designpowers/lane-b-execution.md +1 -1
- package/packages/shared-skills/skills/programming/SKILL.md +10 -1
- package/packages/shared-skills/skills/programming/references/logging.md +91 -0
- package/packages/shared-skills/skills/start-work/SKILL.md +2 -2
- package/packages/shared-skills/skills/ulw-plan/SKILL.md +5 -5
- package/packages/shared-skills/skills/ulw-plan/references/full-workflow.md +7 -7
- package/packages/shared-skills/skills/ulw-plan/references/intent-unclear.md +3 -3
- package/packages/shared-skills/skills/ulw-research/ATTRIBUTION.md +2 -2
- package/packages/shared-skills/skills/ulw-research/SKILL.md +28 -7
- package/packages/shared-skills/skills/visual-qa/SKILL.md +13 -17
- package/script/qa/strip-ansi.mjs +10 -0
- package/script/qa/web-terminal-visual-qa.mjs +112 -195
- package/script/qa/xterm-live-terminal.mjs +180 -0
- package/script/qa/web-terminal-renderer.mjs +0 -218
|
@@ -1,81 +1,75 @@
|
|
|
1
1
|
# Web Terminal Visual QA
|
|
2
2
|
|
|
3
|
-
Use `script/qa/web-terminal-visual-qa.mjs` whenever QA needs TUI visual evidence. It
|
|
3
|
+
Use `script/qa/web-terminal-visual-qa.mjs` whenever QA needs TUI visual evidence. It runs the command in a real pty (node-pty), renders it through a **real xterm.js terminal in headless Chrome**, drives scripted interaction through that browser terminal, and screenshots it. The color path is xterm.js, so truecolor, 256-color, box-drawing, and CJK width are faithful. **NEVER use `tmux capture-pane` for color/visual/layout/CJK TUI evidence** - it degrades truecolor and misaligns wide glyphs. tmux stays useful only for boot smoke ("did it render, did it accept a key"), never for the pixel evidence a reviewer trusts.
|
|
4
4
|
|
|
5
5
|
## Evidence Contract
|
|
6
6
|
|
|
7
7
|
Each run writes these files under the chosen evidence directory:
|
|
8
8
|
|
|
9
|
-
- `terminal.
|
|
10
|
-
- `terminal
|
|
11
|
-
- `terminal.
|
|
12
|
-
- `
|
|
13
|
-
- `metadata.json`: connector, source, output paths, and cleanup receipt.
|
|
9
|
+
- `terminal.png`: the xterm.js screenshot (true color). The primary artifact - cite and attach this.
|
|
10
|
+
- `terminal.txt`: redacted rendered screen text (from the xterm.js buffer) for review and assertions.
|
|
11
|
+
- `terminal-ansi.txt`: the redacted raw pty byte stream, for debugging.
|
|
12
|
+
- `metadata.json`: connector, color path, source, interaction, output paths, and cleanup receipt.
|
|
14
13
|
|
|
15
|
-
The PR should cite `metadata.json` and attach
|
|
14
|
+
The PR should cite `metadata.json` and attach `terminal.png` for OpenCode/Codex TUI proof. For PR-body image hosting, use GitHub user attachments as documented in [docs/reference/github-attachment-upload.md](github-attachment-upload.md); do not commit temporary PNGs, use releases, or use external image hosts.
|
|
16
15
|
|
|
17
|
-
##
|
|
18
|
-
|
|
19
|
-
The helper redacts terminal content before writing `terminal.txt`, `terminal-ansi.txt`, `terminal.html`, or `terminal.png`. Built-in rules cover common authorization headers, token/password/key assignments, GitHub tokens, and OpenAI-style `sk-...` tokens.
|
|
20
|
-
|
|
21
|
-
Add exact local values with `--redact <literal>` and project-specific patterns with `--redact-regex <expr>`:
|
|
16
|
+
## Live Capture (default)
|
|
22
17
|
|
|
23
18
|
```bash
|
|
24
19
|
node script/qa/web-terminal-visual-qa.mjs \
|
|
25
20
|
--title "Codex TUI QA" \
|
|
26
|
-
--
|
|
27
|
-
--
|
|
28
|
-
--
|
|
29
|
-
--
|
|
21
|
+
--command "codex --help" \
|
|
22
|
+
--source-label "codex help smoke" \
|
|
23
|
+
--cwd "$PWD" \
|
|
24
|
+
--evidence-dir .omo/evidence/run/codex-web-terminal
|
|
30
25
|
```
|
|
31
26
|
|
|
32
|
-
|
|
27
|
+
Drive an interactive TUI by scripting keystrokes with repeatable `--input`, applied in order through the browser terminal. Literal text is typed; `{Enter}`, `{Tab}`, `{Escape}`, `{ArrowDown}`, `{Ctrl+C}` and similar tokens are pressed as keys:
|
|
28
|
+
|
|
29
|
+
```bash
|
|
30
|
+
node script/qa/web-terminal-visual-qa.mjs --title "menu nav" --command "my-tui" \
|
|
31
|
+
--input "{ArrowDown}" --input "{ArrowDown}" --input "{Enter}" \
|
|
32
|
+
--dwell-ms 2000 --evidence-dir .omo/evidence/run/menu
|
|
33
|
+
```
|
|
33
34
|
|
|
34
|
-
|
|
35
|
+
## Redaction Contract
|
|
35
36
|
|
|
36
|
-
|
|
37
|
+
The helper redacts terminal content before writing `terminal.txt`, `terminal-ansi.txt`, and - when a rule matches - re-renders the masked stream so `terminal.png` never shows the secret. Built-in rules cover common authorization headers, token/password/key assignments, GitHub tokens, and OpenAI-style `sk-...` tokens.
|
|
37
38
|
|
|
38
|
-
|
|
39
|
+
Add exact local values with `--redact <literal>` and project-specific patterns with `--redact-regex <expr>`:
|
|
39
40
|
|
|
40
41
|
```bash
|
|
41
42
|
node script/qa/web-terminal-visual-qa.mjs \
|
|
42
|
-
--title "Codex TUI QA" \
|
|
43
|
-
--
|
|
44
|
-
--
|
|
43
|
+
--title "Codex TUI QA" --command "codex --help" \
|
|
44
|
+
--evidence-dir .omo/evidence/run/codex-web-terminal \
|
|
45
|
+
--redact "$LOCAL_TOKEN" \
|
|
46
|
+
--redact-regex 'session_[A-Za-z0-9]+'
|
|
45
47
|
```
|
|
46
48
|
|
|
47
|
-
|
|
49
|
+
The raw --command string is process data and may contain inline secrets, so it is never persisted to metadata; use `--source-label` for a reviewer-safe description. Do not rely on screenshots to hide secrets: if a capture might include cookies, auth headers, raw env dumps, or provider keys, redact first or summarize the run instead of storing the transcript.
|
|
48
50
|
|
|
49
|
-
##
|
|
51
|
+
## Replay And Chrome-less Fallback
|
|
50
52
|
|
|
51
|
-
|
|
53
|
+
Render an existing raw terminal byte stream through xterm.js:
|
|
52
54
|
|
|
53
55
|
```bash
|
|
54
|
-
node script/qa/web-terminal-visual-qa.mjs \
|
|
55
|
-
--
|
|
56
|
-
--command "opencode --help" \
|
|
57
|
-
--source-label "opencode help smoke" \
|
|
58
|
-
--cwd "$PWD" \
|
|
59
|
-
--evidence-dir .omo/evidence/run/opencode-web-terminal
|
|
56
|
+
node script/qa/web-terminal-visual-qa.mjs --title "Replay" \
|
|
57
|
+
--from-file .omo/evidence/run/capture.ansi --evidence-dir .omo/evidence/run/replay
|
|
60
58
|
```
|
|
61
59
|
|
|
62
|
-
`--
|
|
60
|
+
`--no-browser` skips xterm.js/Chrome and writes only the text and raw-stream artifacts (no PNG). Use it on hosts without Chrome; it is text-only evidence, not color/visual proof.
|
|
63
61
|
|
|
64
62
|
## OS Notes
|
|
65
63
|
|
|
66
|
-
-
|
|
67
|
-
- Windows:
|
|
68
|
-
- Windows-native ConPTY live capture should plug into this same artifact and metadata contract before becoming required.
|
|
64
|
+
- The harness needs `node-pty` (real pty) plus a system Chrome/Chromium (`--chrome-bin` or `CHROME_BIN` to override). `node-pty` ships prebuilds for macOS and Windows; Linux builds from source on install.
|
|
65
|
+
- Windows: node-pty uses ConPTY, so live capture works natively - no tmux, no Git Bash PTY shim required.
|
|
69
66
|
|
|
70
67
|
## QA Guidance
|
|
71
68
|
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
4. Review `terminal.txt`, `terminal-ansi.txt`, and `metadata.json` for accidental secrets before citing them.
|
|
78
|
-
5. Include `terminal.png`, `terminal.txt`, and `metadata.json` in the evidence summary.
|
|
79
|
-
6. Verify cleanup receipts: no leftover tmux sessions, PIDs, ports, or temp state.
|
|
69
|
+
1. Drive the TUI with `--command` (plus `--input` for interactive flows), or replay a saved stream with `--from-file`.
|
|
70
|
+
2. Store the output under `.omo/evidence/<YYYYMMDD>-<slug>/`.
|
|
71
|
+
3. Review `terminal.txt` and `terminal-ansi.txt` for accidental secrets before citing them.
|
|
72
|
+
4. Include `terminal.png`, `terminal.txt`, and `metadata.json` in the evidence summary.
|
|
73
|
+
5. Verify the cleanup receipt in `metadata.json`: no leftover pty, Chrome, PIDs, ports, or temp state.
|
|
80
74
|
|
|
81
|
-
Tests alone are not TUI visual QA. The passing artifact is the rendered terminal
|
|
75
|
+
Tests alone are not TUI visual QA. The passing artifact is the xterm.js-rendered `terminal.png` plus a binary observation - expected text present, colors correct, no overflow, no border or CJK-width misalignment.
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "oh-my-opencode",
|
|
3
|
-
"version": "4.
|
|
3
|
+
"version": "4.16.1",
|
|
4
4
|
"description": "The Best AI Agent Harness - Batteries-Included OpenCode Plugin with Multi-Model Orchestration, Parallel Background Agents, and Crafted LSP/AST Tools",
|
|
5
5
|
"main": "./dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
@@ -14,6 +14,7 @@
|
|
|
14
14
|
"packages/lsp-core",
|
|
15
15
|
"packages/utils",
|
|
16
16
|
"packages/model-core",
|
|
17
|
+
"packages/omo-config-core",
|
|
17
18
|
"packages/prompts-core",
|
|
18
19
|
"packages/comment-checker-core",
|
|
19
20
|
"packages/hashline-core",
|
|
@@ -27,6 +28,10 @@
|
|
|
27
28
|
"packages/agents-md-core",
|
|
28
29
|
"packages/shared-skills",
|
|
29
30
|
"packages/omo-codex",
|
|
31
|
+
"packages/omo-senpi",
|
|
32
|
+
"packages/senpi-task",
|
|
33
|
+
"packages/pi-goal",
|
|
34
|
+
"packages/pi-webfetch",
|
|
30
35
|
"packages/omo-opencode"
|
|
31
36
|
],
|
|
32
37
|
"bin": {
|
|
@@ -41,10 +46,11 @@
|
|
|
41
46
|
"dist",
|
|
42
47
|
"bin",
|
|
43
48
|
"postinstall.mjs",
|
|
49
|
+
"script/qa/strip-ansi.mjs",
|
|
44
50
|
"script/qa/web-terminal-redaction.d.mts",
|
|
45
51
|
"script/qa/web-terminal-redaction.mjs",
|
|
46
|
-
"script/qa/web-terminal-renderer.mjs",
|
|
47
52
|
"script/qa/web-terminal-visual-qa.mjs",
|
|
53
|
+
"script/qa/xterm-live-terminal.mjs",
|
|
48
54
|
"docs/reference/github-attachment-upload.md",
|
|
49
55
|
"docs/reference/web-terminal-visual-qa.md",
|
|
50
56
|
".opencode/command",
|
|
@@ -83,6 +89,7 @@
|
|
|
83
89
|
"packages/omo-codex/plugin/.codex-plugin",
|
|
84
90
|
"!packages/omo-codex/plugin/node_modules",
|
|
85
91
|
"!packages/omo-codex/plugin/**/node_modules",
|
|
92
|
+
"!packages/omo-codex/plugin/components/workflow-selector",
|
|
86
93
|
"packages/omo-codex/scripts",
|
|
87
94
|
"!packages/omo-codex/scripts/install"
|
|
88
95
|
],
|
|
@@ -96,10 +103,11 @@
|
|
|
96
103
|
"./schema.json": "./dist/oh-my-opencode.schema.json"
|
|
97
104
|
},
|
|
98
105
|
"scripts": {
|
|
99
|
-
"build": "bun run
|
|
106
|
+
"build": "bun run script/build.ts",
|
|
100
107
|
"build:cli-node": "bun run script/build-cli-node.ts",
|
|
101
108
|
"build:codex-install": "bun run script/build-codex-install.ts",
|
|
102
109
|
"build:codex-plugin": "npm --prefix packages/omo-codex/plugin ci && bun run --cwd packages/omo-codex/plugin build",
|
|
110
|
+
"build:senpi-plugin": "node packages/omo-senpi/plugin/scripts/build-extension.mjs && node packages/omo-senpi/plugin/scripts/sync-skills.mjs && node packages/omo-senpi/plugin/scripts/embed-directive.mjs --check",
|
|
103
111
|
"build:materialize-frontend": "node packages/omo-codex/plugin/scripts/materialize-shared-upstreams.mjs --strict",
|
|
104
112
|
"build:shared-skills-assets": "bun run build:materialize-frontend && rm -rf dist/skills && cp -R packages/shared-skills/skills dist/skills",
|
|
105
113
|
"build:lsp-tools-mcp": "npm --prefix packages/lsp-tools-mcp ci && npm --prefix packages/lsp-tools-mcp run build",
|
|
@@ -108,6 +116,7 @@
|
|
|
108
116
|
"build:all": "bun run build && bun run build:binaries",
|
|
109
117
|
"build:binaries": "bun run script/build-binaries.ts",
|
|
110
118
|
"build:schema": "bun run script/build-schema.ts",
|
|
119
|
+
"build:omo-schema": "bun run script/build-omo-schema.ts",
|
|
111
120
|
"build:model-capabilities": "bun run script/build-model-capabilities.ts",
|
|
112
121
|
"clean": "rm -rf dist",
|
|
113
122
|
"prepack": "bun run build:materialize-frontend",
|
|
@@ -116,10 +125,11 @@
|
|
|
116
125
|
"prepublishOnly": "bun run clean && bun run build:lsp-tools-mcp && bun run build:lsp-daemon && bun run build",
|
|
117
126
|
"test:model-capabilities": "bun test packages/model-core/src/model-capability-aliases.test.ts packages/model-core/src/model-capability-guardrails.test.ts packages/model-core/src/model-capabilities.test.ts packages/omo-opencode/src/cli/doctor/checks/model-resolution.test.ts --bail",
|
|
118
127
|
"typecheck": "tsgo --noEmit && bun run typecheck:script && bun run typecheck:packages",
|
|
119
|
-
"typecheck:packages": "tsgo --noEmit -p packages/rules-engine/tsconfig.json && tsgo --noEmit -p packages/delegate-core/tsconfig.json && tsgo --noEmit -p packages/mcp-stdio-core/tsconfig.json && tsgo --noEmit -p packages/mcp-client-core/tsconfig.json && tsgo --noEmit -p packages/git-bash-mcp/tsconfig.json && tsgo --noEmit -p packages/lsp-core/tsconfig.json && tsgo --noEmit -p packages/utils/tsconfig.json && tsgo --noEmit -p packages/model-core/tsconfig.json && tsgo --noEmit -p packages/prompts-core/tsconfig.json && tsgo --noEmit -p packages/comment-checker-core/tsconfig.json && tsgo --noEmit -p packages/hashline-core/tsconfig.json && tsgo --noEmit -p packages/tmux-core/tsconfig.json && tsgo --noEmit -p packages/team-core/tsconfig.json && tsgo --noEmit -p packages/openclaw-core/tsconfig.json && tsgo --noEmit -p packages/boulder-state/tsconfig.json && tsgo --noEmit -p packages/telemetry-core/tsconfig.json && tsgo --noEmit -p packages/claude-code-compat-core/tsconfig.json && tsgo --noEmit -p packages/skills-loader-core/tsconfig.json && tsgo --noEmit -p packages/agents-md-core/tsconfig.json && tsgo --noEmit -p packages/omo-codex/plugin/shared/tsconfig.json && tsgo --noEmit -p packages/omo-codex/tsconfig.json && tsgo --noEmit -p packages/omo-opencode/tsconfig.json",
|
|
128
|
+
"typecheck:packages": "tsgo --noEmit -p packages/rules-engine/tsconfig.json && tsgo --noEmit -p packages/delegate-core/tsconfig.json && tsgo --noEmit -p packages/mcp-stdio-core/tsconfig.json && tsgo --noEmit -p packages/mcp-client-core/tsconfig.json && tsgo --noEmit -p packages/git-bash-mcp/tsconfig.json && tsgo --noEmit -p packages/lsp-core/tsconfig.json && tsgo --noEmit -p packages/utils/tsconfig.json && tsgo --noEmit -p packages/model-core/tsconfig.json && tsgo --noEmit -p packages/omo-config-core/tsconfig.json && tsgo --noEmit -p packages/prompts-core/tsconfig.json && tsgo --noEmit -p packages/comment-checker-core/tsconfig.json && tsgo --noEmit -p packages/hashline-core/tsconfig.json && tsgo --noEmit -p packages/tmux-core/tsconfig.json && tsgo --noEmit -p packages/team-core/tsconfig.json && tsgo --noEmit -p packages/openclaw-core/tsconfig.json && tsgo --noEmit -p packages/boulder-state/tsconfig.json && tsgo --noEmit -p packages/telemetry-core/tsconfig.json && tsgo --noEmit -p packages/claude-code-compat-core/tsconfig.json && tsgo --noEmit -p packages/skills-loader-core/tsconfig.json && tsgo --noEmit -p packages/agents-md-core/tsconfig.json && tsgo --noEmit -p packages/omo-codex/plugin/shared/tsconfig.json && tsgo --noEmit -p packages/omo-codex/tsconfig.json && tsgo --noEmit -p packages/omo-senpi/tsconfig.json && tsgo --noEmit -p packages/senpi-task/tsconfig.json && tsgo --noEmit -p packages/pi-goal/tsconfig.json && tsgo --noEmit -p packages/pi-webfetch/tsconfig.json && tsgo --noEmit -p packages/omo-opencode/tsconfig.json",
|
|
120
129
|
"typecheck:script": "tsgo --noEmit -p script/tsconfig.json",
|
|
121
130
|
"test": "bun test",
|
|
122
131
|
"test:codex": "bun run build:codex-install && bun run build:git-bash-mcp && bun run build:lsp-tools-mcp && bun run build:lsp-daemon && npm --prefix packages/lsp-tools-mcp test && npm --prefix packages/omo-codex/plugin ci && bun run --cwd packages/omo-codex/plugin build && npm --prefix packages/omo-codex/plugin/components/codegraph run typecheck && npm --prefix packages/omo-codex/plugin/components/codegraph test && node scripts/check-third-party-notices.mjs --ship && bun test packages/omo-opencode/src/cli/cli-installer.platform.test.ts packages/omo-codex/src/install/codex-cache.test.ts packages/omo-codex/src/install/codex-cleanup.test.ts packages/omo-codex/src/install/codex-config-agent-cleanup.test.ts packages/omo-codex/src/install/codex-config-autonomous-features.test.ts packages/omo-codex/src/install/codex-config-reasoning.test.ts packages/omo-codex/src/install/codex-config-toml.test.ts packages/omo-codex/src/install/codex-project-local-cleanup.test.ts packages/omo-codex/src/install/install-codex-project-local-cleanup.test.ts packages/omo-codex/src/install/install-codex.test.ts packages/omo-codex/src/install/install-codex-packaged.test.ts packages/omo-codex/src/install/link-cached-plugin-agents.test.ts packages/omo-codex/src/**/*.test.ts packages/utils/src/jsonc-parser.test.ts packages/utils/src/frontmatter.test.ts packages/hashline-core/src/hash-computation.test.ts packages/hashline-core/src/smoke-untested-modules.test.ts packages/rules-engine/src/index.test.ts packages/rules-engine/src/security-boundary.test.ts packages/agents-md-core/src/injector.test.ts packages/omo-codex/plugin/components/lsp/test/package-smoke.test.ts && node --test packages/omo-codex/plugin/test/*.test.mjs packages/omo-codex/scripts/install-cache-copy.test.mjs packages/omo-codex/scripts/install-cli-args.test.mjs packages/omo-codex/scripts/install-delegated-command.test.mjs packages/omo-codex/scripts/install-config-autonomous-features.test.mjs packages/omo-codex/scripts/install-config-autonomous.test.mjs packages/omo-codex/scripts/install-config-reasoning.test.mjs packages/omo-codex/scripts/install-config.test.mjs packages/omo-codex/scripts/install-hook-targets.test.mjs packages/omo-codex/scripts/install-project-local-cleanup.test.mjs packages/omo-codex/scripts/install-lazycodex-version-stamp.test.mjs packages/omo-codex/scripts/install-local-entrypoint.test.mjs packages/omo-codex/scripts/install-local-git-bash-preflight.test.mjs packages/omo-codex/scripts/install-local.test.mjs packages/omo-codex/scripts/install-marketplace-cache.test.mjs packages/omo-codex/scripts/install-mcp-context7-runtime.test.mjs packages/omo-codex/scripts/install-mcp-runtime.test.mjs packages/omo-codex/scripts/install-packaged-local.test.mjs packages/omo-codex/scripts/install-generated-bundle.test.mjs packages/omo-codex/scripts/install-agent-links.test.mjs packages/omo-codex/scripts/install-bin-links.test.mjs",
|
|
132
|
+
"test:senpi": "node packages/omo-senpi/plugin/scripts/build-extension.mjs && node packages/omo-senpi/plugin/scripts/sync-skills.mjs && node packages/omo-senpi/plugin/scripts/embed-directive.mjs --check && bun test packages/omo-senpi",
|
|
123
133
|
"test:windows-codex": "bun run test:codex",
|
|
124
134
|
"build:git-bash-mcp": "bun run --cwd packages/git-bash-mcp build"
|
|
125
135
|
},
|
|
@@ -163,48 +173,61 @@
|
|
|
163
173
|
"zod": "^4.4.3"
|
|
164
174
|
},
|
|
165
175
|
"devDependencies": {
|
|
166
|
-
"@oh-my-opencode/git-bash-mcp": "workspace:*",
|
|
167
|
-
"@oh-my-opencode/lsp-core": "workspace:*",
|
|
168
|
-
"@oh-my-opencode/mcp-stdio-core": "workspace:*",
|
|
169
|
-
"@oh-my-opencode/mcp-client-core": "workspace:*",
|
|
170
176
|
"@oh-my-opencode/agents-md-core": "workspace:*",
|
|
171
177
|
"@oh-my-opencode/boulder-state": "workspace:*",
|
|
172
178
|
"@oh-my-opencode/claude-code-compat-core": "workspace:*",
|
|
173
|
-
"@oh-my-opencode/skills-loader-core": "workspace:*",
|
|
174
179
|
"@oh-my-opencode/comment-checker-core": "workspace:*",
|
|
175
180
|
"@oh-my-opencode/delegate-core": "workspace:*",
|
|
181
|
+
"@oh-my-opencode/git-bash-mcp": "workspace:*",
|
|
176
182
|
"@oh-my-opencode/hashline-core": "workspace:*",
|
|
177
|
-
"@oh-my-opencode/
|
|
178
|
-
"@oh-my-opencode/
|
|
179
|
-
"@oh-my-opencode/
|
|
183
|
+
"@oh-my-opencode/lsp-core": "workspace:*",
|
|
184
|
+
"@oh-my-opencode/mcp-client-core": "workspace:*",
|
|
185
|
+
"@oh-my-opencode/mcp-stdio-core": "workspace:*",
|
|
180
186
|
"@oh-my-opencode/model-core": "workspace:*",
|
|
181
187
|
"@oh-my-opencode/omo-codex": "workspace:*",
|
|
188
|
+
"@oh-my-opencode/omo-config-core": "workspace:*",
|
|
189
|
+
"@oh-my-opencode/omo-senpi": "workspace:*",
|
|
190
|
+
"@oh-my-opencode/openclaw-core": "workspace:*",
|
|
191
|
+
"@oh-my-opencode/pi-goal": "workspace:*",
|
|
192
|
+
"@oh-my-opencode/pi-webfetch": "workspace:*",
|
|
182
193
|
"@oh-my-opencode/prompts-core": "workspace:*",
|
|
183
194
|
"@oh-my-opencode/rules-engine": "workspace:*",
|
|
195
|
+
"@oh-my-opencode/senpi-task": "workspace:*",
|
|
184
196
|
"@oh-my-opencode/shared-skills": "workspace:*",
|
|
197
|
+
"@oh-my-opencode/skills-loader-core": "workspace:*",
|
|
198
|
+
"@oh-my-opencode/team-core": "workspace:*",
|
|
185
199
|
"@oh-my-opencode/telemetry-core": "workspace:*",
|
|
200
|
+
"@oh-my-opencode/tmux-core": "workspace:*",
|
|
186
201
|
"@oh-my-opencode/utils": "workspace:*",
|
|
187
|
-
"@typescript/native-preview": "7.0.0-dev.20260518.1",
|
|
188
202
|
"@types/js-yaml": "^4.0.9",
|
|
189
203
|
"@types/picomatch": "^4.0.3",
|
|
204
|
+
"@typescript/native-preview": "7.0.0-dev.20260518.1",
|
|
205
|
+
"@xterm/addon-unicode11": "^0.9.0",
|
|
206
|
+
"@xterm/xterm": "^6.0.0",
|
|
190
207
|
"bun-types": "1.3.14",
|
|
208
|
+
"node-pty": "^1.1.0",
|
|
209
|
+
"puppeteer-core": "^25.3.0",
|
|
191
210
|
"typescript": "^6.0.3"
|
|
192
211
|
},
|
|
193
212
|
"optionalDependencies": {
|
|
194
|
-
"oh-my-opencode-darwin-arm64": "4.
|
|
195
|
-
"oh-my-opencode-darwin-x64": "4.
|
|
196
|
-
"oh-my-opencode-darwin-x64-baseline": "4.
|
|
197
|
-
"oh-my-opencode-linux-arm64": "4.
|
|
198
|
-
"oh-my-opencode-linux-arm64-musl": "4.
|
|
199
|
-
"oh-my-opencode-linux-x64": "4.
|
|
200
|
-
"oh-my-opencode-linux-x64-baseline": "4.
|
|
201
|
-
"oh-my-opencode-linux-x64-musl": "4.
|
|
202
|
-
"oh-my-opencode-linux-x64-musl-baseline": "4.
|
|
203
|
-
"oh-my-opencode-windows-arm64": "4.
|
|
204
|
-
"oh-my-opencode-windows-x64": "4.
|
|
205
|
-
"oh-my-opencode-windows-x64-baseline": "4.
|
|
213
|
+
"oh-my-opencode-darwin-arm64": "4.16.1",
|
|
214
|
+
"oh-my-opencode-darwin-x64": "4.16.1",
|
|
215
|
+
"oh-my-opencode-darwin-x64-baseline": "4.16.1",
|
|
216
|
+
"oh-my-opencode-linux-arm64": "4.16.1",
|
|
217
|
+
"oh-my-opencode-linux-arm64-musl": "4.16.1",
|
|
218
|
+
"oh-my-opencode-linux-x64": "4.16.1",
|
|
219
|
+
"oh-my-opencode-linux-x64-baseline": "4.16.1",
|
|
220
|
+
"oh-my-opencode-linux-x64-musl": "4.16.1",
|
|
221
|
+
"oh-my-opencode-linux-x64-musl-baseline": "4.16.1",
|
|
222
|
+
"oh-my-opencode-windows-arm64": "4.16.1",
|
|
223
|
+
"oh-my-opencode-windows-x64": "4.16.1",
|
|
224
|
+
"oh-my-opencode-windows-x64-baseline": "4.16.1"
|
|
206
225
|
},
|
|
207
226
|
"overrides": {
|
|
227
|
+
"@earendil-works/pi-agent-core": "0.80.3",
|
|
228
|
+
"@earendil-works/pi-ai": "0.80.3",
|
|
229
|
+
"@earendil-works/pi-coding-agent": "0.80.3",
|
|
230
|
+
"@earendil-works/pi-tui": "0.80.3",
|
|
208
231
|
"hono": "^4.12.18",
|
|
209
232
|
"@hono/node-server": "^1.19.13",
|
|
210
233
|
"express-rate-limit": "^8.5.1",
|
|
@@ -286,7 +286,7 @@ function whereCommand(command) {
|
|
|
286
286
|
}
|
|
287
287
|
}
|
|
288
288
|
// src/runner.ts
|
|
289
|
-
import { spawn
|
|
289
|
+
import { spawn } from "node:child_process";
|
|
290
290
|
import { closeSync, mkdtempSync, openSync, readFileSync, rmSync } from "node:fs";
|
|
291
291
|
import { tmpdir } from "node:os";
|
|
292
292
|
import { join } from "node:path";
|
|
@@ -313,7 +313,7 @@ async function runGitBashCommand(input) {
|
|
|
313
313
|
rmSync(outputDirectory, { recursive: true, force: true });
|
|
314
314
|
return { stdout, stderr };
|
|
315
315
|
}
|
|
316
|
-
const child =
|
|
316
|
+
const child = spawn(input.bashPath, ["-lc", input.command], {
|
|
317
317
|
cwd: input.cwd,
|
|
318
318
|
env: input.env,
|
|
319
319
|
windowsHide: true,
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
# bootstrap: Codex SessionStart Runtime Provisioner
|
|
2
|
+
|
|
3
|
+
**Generated:** 2026-07-03
|
|
4
|
+
|
|
5
|
+
## OVERVIEW
|
|
6
|
+
|
|
7
|
+
`@sisyphuslabs/codex-bootstrap` (private, engines node >=20). Runs on every Codex `SessionStart` via `hooks/hooks.json`: POSIX runs `node dist/cli.js hook session-start`, Windows runs `scripts/bootstrap.ps1` through `commandWindows` (30s timeout). The hook drains stdin, reads the plugin version from `<PLUGIN_ROOT>/.codex-plugin/plugin.json`, and skips when `state.json` already marks `completedForVersion` for that version, when a fresh lock exists, or when `PLUGIN_ROOT`/`PLUGIN_DATA` are missing. Otherwise it spawns a detached, unref'd worker (`process.execPath dist/cli.js worker`) and emits a `hookSpecificOutput.additionalContext` restart notice. Every path exits 0.
|
|
8
|
+
|
|
9
|
+
The worker acquires BOTH the bootstrap and auto-update locks under `PLUGIN_DATA`, re-checks completion under lock (TOCTOU), then runs two steps:
|
|
10
|
+
- `setup` (`src/setup.ts`): idempotent, degraded-not-fatal re-run of the installer surface: Git Bash preflight (win32), bundled agent TOML linking (staged under `PLUGIN_DATA`, never `PLUGIN_ROOT`), `config.toml` blocks + trusted-hook-hash re-stamp, `git_bash` MCP env stamp, version-aware component bin links plus the `omo` runtime wrapper.
|
|
11
|
+
- `sg` (`src/provision.ts`): pinned ast-grep binary into `<CODEX_HOME>/runtime/ast-grep/<slug>/`; skipped when a preexisting binary resolves unless `OMO_BOOTSTRAP_FORCE_PROVISION=1`; a `--version` probe must match `SG_PINNED_VERSION` or the binary is deleted.
|
|
12
|
+
|
|
13
|
+
Result is written to `state.json` (`completedForVersion`, `lastStatus: success|degraded`, degraded ledger) and JSONL log lines to `<PLUGIN_DATA>/bootstrap/bootstrap.log`. Runtime failures NEVER exit non-zero; the degraded ledger plus the `npx lazycodex-ai doctor` hint is the error channel.
|
|
14
|
+
|
|
15
|
+
CLI: `hook session-start` | `worker [--codex-home <dir>] [--once] [--only <step>] [--manifest-dir <dir>]` | `download <manifest> <platform> <destination-dir>`.
|
|
16
|
+
|
|
17
|
+
## KEY FILES
|
|
18
|
+
|
|
19
|
+
| File | Purpose |
|
|
20
|
+
|------|---------|
|
|
21
|
+
| `src/cli.ts` | Entry + barrel exports; command routing; entry guard via `realpathSync` |
|
|
22
|
+
| `src/hook.ts` | SessionStart handler: skip logic, detached worker spawn, restart notice |
|
|
23
|
+
| `src/worker.ts` | Worker orchestration: flags, locks, state.json, bootstrap.log, step runner |
|
|
24
|
+
| `src/setup.ts` | Setup step; esbuild inlines `packages/omo-codex/src/install/*` at build time |
|
|
25
|
+
| `src/provision.ts` | ast-grep provisioning via `packages/utils/src/ast-grep` helpers |
|
|
26
|
+
| `src/download.ts` | Checksummed manifest downloader: sha256 verify, `.partial` temp + rename, no proxy tunneling in v1 |
|
|
27
|
+
| `src/environment.ts` | `CODEX_HOME` resolution (env, then 6-level walk-up for `config.toml`, then `~/.codex`); install-flow detection (npx-local vs marketplace via `lazycodex-install.json` + marketplace source); lock/state paths |
|
|
28
|
+
| `hooks/hooks.json` | SessionStart wiring, `commandWindows` PowerShell branch |
|
|
29
|
+
| `scripts/bootstrap.ps1` | Windows PowerShell 5.1 hook (see NOTES) |
|
|
30
|
+
| `scripts/node-dispatch.ps1` | Generic Windows Node resolver/dispatcher for hook targets; exit 127 when Node unresolved |
|
|
31
|
+
| `manifests/node.json` | Pinned Node LTS (win32-x64 zip URL + sha256) |
|
|
32
|
+
| `scripts/generate-manifests.mjs` | Regenerates `manifests/node.json`; the ONLY network-touching code here |
|
|
33
|
+
| `scripts/build.mjs` | `bun x esbuild` bundle to `dist/cli.js`; keeps a prebuilt dist when esbuild is unavailable |
|
|
34
|
+
| `test/*.test.ts` | bun:test suites: download, environment, provision |
|
|
35
|
+
|
|
36
|
+
## WHERE TO LOOK
|
|
37
|
+
|
|
38
|
+
| Task | Location |
|
|
39
|
+
|------|----------|
|
|
40
|
+
| Add a worker step | `src/worker.ts` `defaultWorkerSteps()`; return `{ degraded }`, never throw upward |
|
|
41
|
+
| Change skip/lock semantics | `src/hook.ts` + `src/environment.ts` `bootstrapLocks()` (stale window from `plugin/scripts/auto-update-state.mjs`) |
|
|
42
|
+
| Move the pinned Node LTS | `node scripts/generate-manifests.mjs [--node-version <x.y.z>]`, review + commit the manifest diff |
|
|
43
|
+
| Installer-parity behavior | `src/setup.ts`, which wraps `packages/omo-codex/src/install/` modules |
|
|
44
|
+
| Windows Node/Git Bash resolution | `scripts/bootstrap.ps1`; hook-level parity checks in `packages/omo-codex/plugin/test/bootstrap-ps-guard.test.mjs` |
|
|
45
|
+
| Cross-component orchestration tests | `packages/omo-codex/plugin/test/bootstrap-{hooks,setup,binlinks,orchestration,ps-guard}.test.mjs` |
|
|
46
|
+
|
|
47
|
+
## NOTES
|
|
48
|
+
|
|
49
|
+
- **Deliberately NOT in the plugin workspaces array** (`packages/omo-codex/plugin/package.json`). `plugin/scripts/build-components.mjs` builds it on the standalone path: component-local `npm run build`, then a `bun build` re-bundle with `node:` import normalization. Keeping it out of workspaces lets esbuild inline cross-package TS sources (`packages/omo-codex/src/install/*`, `packages/utils/src/ast-grep`) so `PLUGIN_ROOT` ships nothing beyond `dist/cli.js`.
|
|
50
|
+
- **Ships in the published payload explicitly:** root `package.json` `files` lists `components/bootstrap/dist/cli.js`, `scripts/bootstrap.ps1`, and `scripts/node-dispatch.ps1` (other component sources are covered by the broader `packages/omo-codex/plugin` glob, but bootstrap's dist is pinned by name).
|
|
51
|
+
- **Never persists under `PLUGIN_ROOT`** (the Codex-managed marketplace cache). All state, staging, and logs live under `PLUGIN_DATA` (default `~/.local/share/lazycodex`).
|
|
52
|
+
- **Never writes permission keys.** `updateCodexConfig` is called with `autonomousPermissions: false`; approval/sandbox/network policies stay installer-flag-only.
|
|
53
|
+
- **Windows:** Codex runs hooks through `%COMSPEC%`, so Node may be absent from PATH. `bootstrap.ps1` resolves Node via `NODE_REPL_NODE_PATH` (env or `config.toml`), then the portable zip pinned by `manifests/node.json` (sha256-verified into `<CODEX_HOME>/runtime/node/`), then common install dirs and PATH; when still unresolved it emits a provisioning-incomplete notice instead of delegating. It resolves Git Bash best-effort (persists `OMO_CODEX_GIT_BASH_PATH` in the USER environment when found via PATH), never mutates the user PATH, logs to `<PLUGIN_DATA>/bootstrap/ps-bootstrap.log`, and always exits 0.
|
|
54
|
+
- **Manifests are committed, never generated at build time.** Builds stay offline and deterministic; unit tests inject `fetchImpl`, never the network.
|
|
55
|
+
- Component tests run with `bun test test/*.test.ts` even though the runtime is Node; typecheck is `noEmit` with `allowImportingTsExtensions`.
|
|
@@ -146,7 +146,7 @@ async function downloadFromManifest(options) {
|
|
|
146
146
|
}
|
|
147
147
|
|
|
148
148
|
// components/bootstrap/src/hook.ts
|
|
149
|
-
import { spawn
|
|
149
|
+
import { spawn } from "node:child_process";
|
|
150
150
|
import { stat as stat6 } from "node:fs/promises";
|
|
151
151
|
import { fileURLToPath as fileURLToPath3 } from "node:url";
|
|
152
152
|
|
|
@@ -493,6 +493,7 @@ function runtimeSlug(platform = process.platform, arch = process.arch) {
|
|
|
493
493
|
function sgBinaryName(platform = process.platform) {
|
|
494
494
|
return normalizeRuntimePlatform(platform) === "win32" ? "sg.exe" : "sg";
|
|
495
495
|
}
|
|
496
|
+
|
|
496
497
|
// ../../utils/src/ast-grep/sg-provisioner.ts
|
|
497
498
|
import { createHash as createHash2, randomUUID as randomUUID2 } from "node:crypto";
|
|
498
499
|
import { chmod, mkdir as mkdir3, rename as rename2, rm as rm3, writeFile as writeFile2 } from "node:fs/promises";
|
|
@@ -644,6 +645,7 @@ async function provisionSgBinary(options) {
|
|
|
644
645
|
throw new SgProvisionError("write_failed", `failed to provision ast-grep ${SG_PINNED_VERSION} into ${targetDir}: ${describeFailure2(error)}`, { cause: error });
|
|
645
646
|
}
|
|
646
647
|
}
|
|
648
|
+
|
|
647
649
|
// ../../utils/src/ast-grep/sg-resolver.ts
|
|
648
650
|
import { execFileSync } from "node:child_process";
|
|
649
651
|
import { existsSync, statSync } from "node:fs";
|
|
@@ -781,6 +783,7 @@ function findSgBinarySync(options = {}) {
|
|
|
781
783
|
return null;
|
|
782
784
|
}
|
|
783
785
|
}
|
|
786
|
+
|
|
784
787
|
// components/bootstrap/src/provision.ts
|
|
785
788
|
var SG_PROVISION_COMPONENT = "ast_grep";
|
|
786
789
|
var SG_FORCE_PROVISION_ENV_KEY = "OMO_BOOTSTRAP_FORCE_PROVISION";
|
|
@@ -2545,9 +2548,14 @@ function readBooleanSetting(sectionText, key) {
|
|
|
2545
2548
|
// ../src/install/codex-config-toml.ts
|
|
2546
2549
|
async function updateCodexConfig(input) {
|
|
2547
2550
|
await mkdir6(dirname7(input.configPath), { recursive: true });
|
|
2548
|
-
let config
|
|
2549
|
-
|
|
2551
|
+
let config;
|
|
2552
|
+
try {
|
|
2550
2553
|
config = await readFile10(input.configPath, "utf8");
|
|
2554
|
+
} catch (error) {
|
|
2555
|
+
if (!isMissingFileError(error))
|
|
2556
|
+
throw error;
|
|
2557
|
+
config = "";
|
|
2558
|
+
}
|
|
2551
2559
|
const pluginSet = new Set(input.pluginNames);
|
|
2552
2560
|
for (const legacyMarketplaceName of legacyMarketplaceNames(input.marketplaceName)) {
|
|
2553
2561
|
config = removeMarketplaceBlock(config, legacyMarketplaceName);
|
|
@@ -2581,15 +2589,8 @@ async function updateCodexConfig(input) {
|
|
|
2581
2589
|
await writeFileAtomic(input.configPath, `${config.trimEnd()}
|
|
2582
2590
|
`);
|
|
2583
2591
|
}
|
|
2584
|
-
|
|
2585
|
-
|
|
2586
|
-
await readFile10(path, "utf8");
|
|
2587
|
-
return true;
|
|
2588
|
-
} catch (error) {
|
|
2589
|
-
if (error instanceof Error)
|
|
2590
|
-
return false;
|
|
2591
|
-
return false;
|
|
2592
|
-
}
|
|
2592
|
+
function isMissingFileError(error) {
|
|
2593
|
+
return error instanceof Error && "code" in error && error.code === "ENOENT";
|
|
2593
2594
|
}
|
|
2594
2595
|
|
|
2595
2596
|
// ../src/install/codex-git-bash-mcp-env.ts
|
|
@@ -2653,7 +2654,7 @@ var EVENT_LABELS = new Map([
|
|
|
2653
2654
|
]);
|
|
2654
2655
|
async function trustedHookStatesForPlugin(input) {
|
|
2655
2656
|
const manifestPath = join17(input.pluginRoot, ".codex-plugin", "plugin.json");
|
|
2656
|
-
if (!await
|
|
2657
|
+
if (!await exists3(manifestPath))
|
|
2657
2658
|
return [];
|
|
2658
2659
|
const manifest = JSON.parse(await readFile12(manifestPath, "utf8"));
|
|
2659
2660
|
if (!isPlainRecord(manifest))
|
|
@@ -2661,7 +2662,7 @@ async function trustedHookStatesForPlugin(input) {
|
|
|
2661
2662
|
const states = [];
|
|
2662
2663
|
for (const hookPath of hookManifestPaths(manifest.hooks)) {
|
|
2663
2664
|
const hooksPath = join17(input.pluginRoot, hookPath);
|
|
2664
|
-
if (!await
|
|
2665
|
+
if (!await exists3(hooksPath))
|
|
2665
2666
|
continue;
|
|
2666
2667
|
const parsed = JSON.parse(await readFile12(hooksPath, "utf8"));
|
|
2667
2668
|
if (!isPlainRecord(parsed) || !isPlainRecord(parsed.hooks))
|
|
@@ -2744,7 +2745,7 @@ function canonicalJson(value) {
|
|
|
2744
2745
|
function stripDotSlash(value) {
|
|
2745
2746
|
return value.startsWith("./") ? value.slice(2) : value;
|
|
2746
2747
|
}
|
|
2747
|
-
async function
|
|
2748
|
+
async function exists3(path) {
|
|
2748
2749
|
try {
|
|
2749
2750
|
await readFile12(path, "utf8");
|
|
2750
2751
|
return true;
|
|
@@ -2769,6 +2770,7 @@ function resolveCodexInstallerBinDir(input) {
|
|
|
2769
2770
|
return join18(resolvedCodexHome, "bin");
|
|
2770
2771
|
return resolve6(homeDir, ".local", "bin");
|
|
2771
2772
|
}
|
|
2773
|
+
|
|
2772
2774
|
// ../../utils/src/runtime/git-bash.ts
|
|
2773
2775
|
import { execFileSync as execFileSync2 } from "node:child_process";
|
|
2774
2776
|
import { existsSync as existsSync2 } from "node:fs";
|
|
@@ -2851,6 +2853,7 @@ function whereCommand(command) {
|
|
|
2851
2853
|
throw error;
|
|
2852
2854
|
}
|
|
2853
2855
|
}
|
|
2856
|
+
|
|
2854
2857
|
// ../src/install/git-bash.ts
|
|
2855
2858
|
var resolveGitBashForCurrentProcess2 = (input = {}) => {
|
|
2856
2859
|
return toCodexResolution(resolveGitBashForCurrentProcess(input));
|
|
@@ -3306,7 +3309,7 @@ async function executeSessionStartHook(options) {
|
|
|
3306
3309
|
return { action: "spawned", exitCode: 0 };
|
|
3307
3310
|
}
|
|
3308
3311
|
function spawnDetachedWorker(invocation) {
|
|
3309
|
-
const child =
|
|
3312
|
+
const child = spawn(invocation.command, [...invocation.args], {
|
|
3310
3313
|
detached: true,
|
|
3311
3314
|
env: invocation.env,
|
|
3312
3315
|
stdio: "ignore"
|
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
"command": "node \"${PLUGIN_ROOT}/components/bootstrap/dist/cli.js\" hook session-start",
|
|
9
9
|
"commandWindows": "powershell -NoProfile -ExecutionPolicy Bypass -File \"${PLUGIN_ROOT}\\components\\bootstrap\\scripts\\bootstrap.ps1\"",
|
|
10
10
|
"timeout": 30,
|
|
11
|
-
"statusMessage": "(OmO) Checking Bootstrap Provisioning"
|
|
11
|
+
"statusMessage": "(OmO 4.16.1) Checking Bootstrap Provisioning"
|
|
12
12
|
}
|
|
13
13
|
]
|
|
14
14
|
}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
# packages/omo-codex/plugin/components/codegraph/ — CodeGraph MCP Wrapper + Bootstrap Hooks
|
|
2
|
+
|
|
3
|
+
**Generated:** 2026-07-03
|
|
4
|
+
|
|
5
|
+
## OVERVIEW
|
|
6
|
+
|
|
7
|
+
`@sisyphuslabs/codex-codegraph` (private, Node >=20, bin `omo-codegraph`). Wraps the external CodeGraph CLI (`@colbymchenry/codegraph`, pinned `1.0.1` as optionalDependency + `CODEGRAPH_VERSION` constant) behind a stdio MCP server plus Codex lifecycle hooks. Two committed dists ship in the published payload; rebuild `dist/` in the same change as `src/` edits.
|
|
8
|
+
|
|
9
|
+
Codex wiring (all repo-relative to `packages/omo-codex/plugin/`):
|
|
10
|
+
- **MCP:** `.mcp.json` server `codegraph` → `node components/codegraph/dist/serve.js` (`required: false`).
|
|
11
|
+
- **SessionStart hook:** `hooks/session-start-checking-codegraph-bootstrap.json` → `dist/cli.js hook session-start` (timeout 5).
|
|
12
|
+
- **PostToolUse hook:** `hooks/post-tool-use-checking-codegraph-init-guidance.json`, matcher `^(codegraph[._].*|mcp__codegraph__.*)$` → `dist/cli.js hook post-tool-use`.
|
|
13
|
+
- Both hooks registered in `.codex-plugin/plugin.json`; Windows variants dispatch via `components/bootstrap/scripts/node-dispatch.ps1`.
|
|
14
|
+
|
|
15
|
+
Serve pipeline (`src/serve.ts`): OMO SOT config gate (`[codex].codegraph.enabled=false` → unavailable stub) → resolve binary (`OMO_CODEGRAPH_BIN` env → bundled → provisioned `~/.omo/codegraph/bin` → PATH) → Node support gate (major 20–24; >=25 crashes CodeGraph mid-indexing; `CODEGRAPH_ALLOW_UNSAFE_NODE=1` overrides) → auto-provision into `~/.omo/codegraph` unless `codegraph.auto_provision=false` → bridge JSON-RPC to `codegraph serve --mcp`. Project cwd resolved from `OMO_CODEGRAPH_PROJECT_CWD` → `OMO_CODEGRAPH_SESSION_START_CWD` → `PWD` → wrapper cwd. When the binary is missing/disabled, `mcp-unavailable.ts` still answers `initialize`/`tools/*` with the skip reason so Codex startup never fails.
|
|
16
|
+
|
|
17
|
+
Hook pipeline (`src/hook.ts` + `src/session-start-worker.ts`): `hook session-start` probes `status --json` (2s timeout); uninitialized project → spawns a detached `hook session-start-worker` (prepare workspace + gitignore → `status --json` → `init` or `sync`, 60s per command) and emits a SessionStart `additionalContext` notice. Worker outcomes append to `~/.omo/codegraph/session-start.jsonl`. `hook post-tool-use` emits init guidance when a codegraph tool result indicates an uninitialized project. `cli.js` with no hook subcommand falls through to serve.
|
|
18
|
+
|
|
19
|
+
## includeCode CONTRACT (commit 4cf383c5b)
|
|
20
|
+
|
|
21
|
+
`src/mcp-bridge.ts` rewrites the upstream `codegraph_node` contract in-flight: `tools/list` responses get a clarified description + `includeCode` schema description, and `tools/call` results replace "Structural outline only" text. Contract: `includeCode=true` returns leaf-symbol source only; container symbols (classes, interfaces, structs, enums, modules, namespaces) return structural outlines with member lists BY DESIGN — for container source, request a specific member symbol or file mode with `symbolsOnly=false` plus `offset`/`limit`. Pinned by `test/serve-mcp-bridge.test.ts`.
|
|
22
|
+
|
|
23
|
+
## KEY FILES
|
|
24
|
+
|
|
25
|
+
| File | Purpose |
|
|
26
|
+
|------|---------|
|
|
27
|
+
| `src/serve.ts` | MCP entry: config/resolution/Node gates, provisioning, bridge or unavailable stub |
|
|
28
|
+
| `src/cli.ts` | Hook CLI router: `hook session-start` / `hook post-tool-use` / `hook session-start-worker` / serve fallback |
|
|
29
|
+
| `src/hook.ts` | SessionStart probe + detached worker spawn, PostToolUse guidance emission |
|
|
30
|
+
| `src/session-start-worker.ts` | Background bootstrap: provision → workspace prep → `init`/`sync`, jsonl outcome log |
|
|
31
|
+
| `src/mcp-bridge.ts` | Stdio JSON-RPC forwarder; per-request framed/line response-mode tracking; codegraph_node contract rewrites |
|
|
32
|
+
| `src/mcp-unavailable.ts` | Reason-bearing stub MCP server for disabled/missing binary |
|
|
33
|
+
| `src/serve-invocation.ts` | win32 invocation shim: `.cmd`/`.bat` via `cmd.exe /d /s /c`, `.js`/`.mjs`/`.cjs` via `process.execPath` (mirrored by `resolveCodegraphCommandInvocation` in session-start-worker) |
|
|
34
|
+
| `src/hook-types.ts` | Shared hook/worker option + outcome types |
|
|
35
|
+
|
|
36
|
+
## WHERE TO LOOK
|
|
37
|
+
|
|
38
|
+
| Task | Location |
|
|
39
|
+
|------|----------|
|
|
40
|
+
| Resolution order, provisioning, Node gate, env, gitignore/workspace prep | `packages/utils/src/codegraph/` (`resolve.ts`, `provision.ts`, `node-support.ts`, `env.ts`, `workspace.ts`, `guidance.ts`) — bundled at build time |
|
|
41
|
+
| `[codex].codegraph` config keys (`enabled`, `auto_provision`, `trustedCodegraphInstallDir`) | `packages/omo-codex/plugin/shared/src/config-loader.ts` |
|
|
42
|
+
| JSON-RPC framing primitives | `packages/mcp-stdio-core/src/` |
|
|
43
|
+
| Build / test / typecheck | `bun run build` (bun build → `dist/serve.js` + `dist/cli.js`, target node ESM), `bun test ./test`, `tsc --noEmit` |
|
|
44
|
+
|
|
45
|
+
## NOTES
|
|
46
|
+
|
|
47
|
+
- This component tests with `bun test` (unlike the vitest-based `lsp` sibling); given/when/then style.
|
|
48
|
+
- `src/` imports reach sibling packages via relative paths (`../../../../../utils/src/...`); they are inlined by `bun build`, so runtime `dist/` has zero deps beyond Node.
|
|
49
|
+
- `CODEGRAPH_VERSION` is duplicated in `serve.ts` and `session-start-worker.ts` and must match the `@colbymchenry/codegraph` optionalDependency version.
|
|
50
|
+
- `trustedCodegraphInstallDir` overrides the `~/.omo/codegraph` install dir and is forwarded to children as `CODEGRAPH_INSTALL_DIR`.
|
|
51
|
+
- `resolution.source === "env"` is never auto-provisioned over: a user-set `OMO_CODEGRAPH_BIN` pointing at a missing file skips the MCP instead of silently substituting a download.
|