oh-my-opencode 4.7.5 → 4.8.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/command/get-unpublished-changes.md +35 -6
- package/.agents/command/omomomo.md +1 -1
- package/.agents/command/publish.md +13 -0
- package/.agents/command/security-research.md +0 -1
- package/.agents/skills/get-unpublished-changes/SKILL.md +21 -5
- package/.agents/skills/omomomo/SKILL.md +1 -2
- package/.agents/skills/opencode-qa/scripts/export-roundtrip.sh +57 -19
- package/.agents/skills/opencode-qa/scripts/lib/common.sh +19 -7
- package/.agents/skills/opencode-qa/scripts/sse-hook-probe.sh +3 -0
- package/.agents/skills/opencode-qa/scripts/tui-smoke.sh +1 -1
- package/.agents/skills/pre-publish-review/SKILL.md +24 -4
- package/.agents/skills/publish/SKILL.md +13 -0
- package/.agents/skills/remove-deadcode/SKILL.md +0 -1
- package/.agents/skills/security-research/SKILL.md +0 -1
- package/.agents/skills/work-with-pr-workspace/iteration-1/eval-3/with_skill/outputs/code-changes.md +1 -1
- package/.agents/skills/work-with-pr-workspace/iteration-1/eval-3/without_skill/outputs/code-changes.md +2 -2
- package/.agents/skills/work-with-pr-workspace/iteration-1/review.html +1 -1
- package/.opencode/command/get-unpublished-changes.md +35 -6
- package/.opencode/command/omomomo.md +1 -1
- package/.opencode/command/publish.md +13 -0
- package/.opencode/command/security-research.md +0 -1
- package/.opencode/skills/pre-publish-review/SKILL.md +24 -4
- package/.opencode/skills/work-with-pr-workspace/iteration-1/eval-3/with_skill/outputs/code-changes.md +1 -1
- package/.opencode/skills/work-with-pr-workspace/iteration-1/eval-3/without_skill/outputs/code-changes.md +2 -2
- package/.opencode/skills/work-with-pr-workspace/iteration-1/review.html +1 -1
- package/README.ja.md +7 -7
- package/README.ko.md +9 -7
- package/README.md +14 -8
- package/README.ru.md +5 -5
- package/README.zh-cn.md +7 -7
- package/bin/oh-my-opencode.js +24 -1
- package/bin/oh-my-opencode.test.ts +79 -20
- package/dist/agents/hephaestus/agent.d.ts +1 -1
- package/dist/agents/kimi-tool-loop-guard.d.ts +1 -0
- package/dist/agents/momus.d.ts +1 -1
- package/dist/agents/sisyphus-agent-config.d.ts +4 -0
- package/dist/agents/sisyphus-agent-factory.d.ts +6 -0
- package/dist/agents/sisyphus-dynamic-prompt-builder.d.ts +2 -0
- package/dist/agents/sisyphus-dynamic-prompt-execution.d.ts +2 -0
- package/dist/agents/sisyphus-dynamic-prompt-exploration.d.ts +2 -0
- package/dist/agents/sisyphus-dynamic-prompt-role.d.ts +2 -0
- package/dist/agents/sisyphus-dynamic-prompt-sections.d.ts +18 -0
- package/dist/agents/sisyphus-dynamic-prompt-style.d.ts +2 -0
- package/dist/agents/sisyphus-dynamic-prompt.d.ts +3 -0
- package/dist/agents/sisyphus-gemini-fallback-overrides.d.ts +1 -0
- package/dist/agents/sisyphus-junior/agent.d.ts +1 -1
- package/dist/agents/sisyphus-junior/index.d.ts +0 -1
- package/dist/agents/sisyphus.d.ts +1 -6
- package/dist/agents/types.d.ts +14 -3
- package/dist/cli/cli-program.d.ts +3 -0
- package/dist/cli/doctor/checks/codex.d.ts +11 -0
- package/dist/cli/doctor/checks/dependencies.d.ts +1 -0
- package/dist/cli/doctor/checks/index.d.ts +3 -0
- package/dist/cli/doctor/checks/system.d.ts +4 -0
- package/dist/cli/doctor/constants.d.ts +1 -0
- package/dist/cli/doctor/doctor-target.d.ts +2 -0
- package/dist/cli/doctor/index.d.ts +1 -0
- package/dist/cli/doctor/types.d.ts +26 -0
- package/dist/cli/index.js +4466 -2212
- package/dist/cli/install-codex/codex-cache-bins.d.ts +21 -0
- package/dist/cli/install-codex/codex-cache-fs.d.ts +3 -0
- package/dist/cli/install-codex/codex-cache-install.d.ts +13 -0
- package/dist/cli/install-codex/codex-cache-mcp-manifest.d.ts +2 -0
- package/dist/cli/install-codex/codex-cache-prune.d.ts +10 -0
- package/dist/cli/install-codex/codex-cache.d.ts +4 -32
- package/dist/cli/install-codex/codex-cached-marketplace-manifest.d.ts +6 -0
- package/dist/cli/install-codex/codex-config-agents.d.ts +3 -0
- package/dist/cli/install-codex/codex-config-features.d.ts +1 -0
- package/dist/cli/install-codex/codex-config-marketplaces.d.ts +6 -0
- package/dist/cli/install-codex/codex-config-plugins.d.ts +8 -0
- package/dist/cli/install-codex/codex-config-toml-sections.d.ts +9 -0
- package/dist/cli/install-codex/codex-multi-agent-v2-config.d.ts +11 -0
- package/dist/cli/install-codex/codex-process.d.ts +5 -0
- package/dist/cli/install-codex/index.d.ts +1 -1
- package/dist/cli/install-codex/lazycodex-version-stamp.d.ts +19 -0
- package/dist/cli/install-codex/link-cached-plugin-agents.d.ts +4 -0
- package/dist/cli/install-validators.d.ts +3 -0
- package/dist/cli/model-fallback-types.d.ts +3 -0
- package/dist/cli/run/event-handlers.d.ts +4 -11
- package/dist/cli/run/event-message-handlers.d.ts +5 -0
- package/dist/cli/run/event-session-handlers.d.ts +5 -0
- package/dist/cli/run/event-session-ids.d.ts +24 -0
- package/dist/cli/run/event-think-block.d.ts +3 -0
- package/dist/cli/run/event-toast-handlers.d.ts +3 -0
- package/dist/cli/run/event-tool-handlers.d.ts +4 -0
- package/dist/cli/run/event-tool-output.d.ts +2 -0
- package/dist/cli/run/on-complete-hook.d.ts +8 -1
- package/dist/cli/run/opencode-binary-resolver.d.ts +2 -1
- package/dist/cli/run/runnable-agent-resolver.d.ts +11 -0
- package/dist/cli/runtime-commands.d.ts +2 -0
- package/dist/cli/sparkshell-appserver-websocket.d.ts +4 -0
- package/dist/cli/sparkshell-appserver.d.ts +16 -0
- package/dist/cli/sparkshell-parse.d.ts +21 -0
- package/dist/cli/sparkshell.d.ts +26 -0
- package/dist/cli/types.d.ts +9 -0
- package/dist/config/schema/claude-code.d.ts +1 -0
- package/dist/config/schema/hooks.d.ts +1 -0
- package/dist/config/schema/oh-my-opencode-config.d.ts +1 -0
- package/dist/create-hooks.d.ts +1 -0
- package/dist/features/background-agent/concurrency.d.ts +6 -1
- package/dist/features/background-agent/constants.d.ts +1 -0
- package/dist/features/background-agent/empty-assistant-turn.d.ts +7 -0
- package/dist/features/background-agent/manager.d.ts +12 -0
- package/dist/features/background-agent/message-updated-parent-wake-output.d.ts +1 -0
- package/dist/features/background-agent/parent-wake-dedupe.d.ts +2 -0
- package/dist/features/background-agent/parent-wake-dispatched-tracker.d.ts +21 -0
- package/dist/features/background-agent/parent-wake-flush-runner.d.ts +24 -0
- package/dist/features/background-agent/parent-wake-history-state.d.ts +5 -0
- package/dist/features/background-agent/parent-wake-notifier-types.d.ts +50 -0
- package/dist/features/background-agent/parent-wake-notifier.d.ts +8 -50
- package/dist/features/background-agent/parent-wake-pending-queue.d.ts +22 -0
- package/dist/features/background-agent/parent-wake-prompt-dispatch.d.ts +19 -0
- package/dist/features/background-agent/parent-wake-session-history.d.ts +73 -0
- package/dist/features/background-agent/parent-wake-session-inspector.d.ts +35 -0
- package/dist/features/background-agent/parent-wake-timer-handle.d.ts +5 -0
- package/dist/features/background-agent/parent-wake-window-recovery.d.ts +13 -0
- package/dist/features/background-agent/process-cleanup.d.ts +2 -0
- package/dist/features/background-agent/process-cleanup.test-helpers.d.ts +3 -0
- package/dist/features/background-agent/session-stream-activity.d.ts +6 -0
- package/dist/features/background-agent/spawner/fallback-agent.d.ts +5 -0
- package/dist/features/background-agent/spawner/task-prompt-body.d.ts +34 -0
- package/dist/features/background-agent/spawner/task-record.d.ts +2 -0
- package/dist/features/background-agent/spawner.d.ts +2 -5
- package/dist/features/builtin-commands/templates/refactor-sections/codemap-and-tests.d.ts +1 -0
- package/dist/features/builtin-commands/templates/refactor-sections/intro-and-analysis.d.ts +1 -0
- package/dist/features/builtin-commands/templates/refactor-sections/plan-and-execution.d.ts +1 -0
- package/dist/features/builtin-commands/templates/refactor-sections/team-mode-addendum.d.ts +1 -0
- package/dist/features/builtin-commands/templates/refactor-sections/verification-and-tooling.d.ts +1 -0
- package/dist/features/builtin-commands/templates/refactor.d.ts +2 -2
- package/dist/features/builtin-skills/skills/agent-browser-skill.d.ts +2 -0
- package/dist/features/builtin-skills/skills/agent-browser-template.d.ts +2 -0
- package/dist/features/builtin-skills/skills/git-master-sections/commit-atomic-planning.d.ts +1 -0
- package/dist/features/builtin-skills/skills/git-master-sections/commit-context-analysis.d.ts +1 -0
- package/dist/features/builtin-skills/skills/git-master-sections/commit-execution-verification.d.ts +1 -0
- package/dist/features/builtin-skills/skills/git-master-sections/commit-workflow.d.ts +1 -1
- package/dist/features/builtin-skills/skills/index.d.ts +1 -0
- package/dist/features/builtin-skills/skills/playwright-mcp-skill.d.ts +2 -0
- package/dist/features/builtin-skills/skills/playwright.d.ts +2 -3
- package/dist/features/builtin-skills/skills/visual-qa.d.ts +2 -0
- package/dist/features/claude-code-agent-loader/agent-definitions-loader.d.ts +2 -2
- package/dist/features/claude-code-agent-loader/claude-model-mapper.d.ts +1 -1
- package/dist/features/claude-code-agent-loader/loader.d.ts +2 -2
- package/dist/features/claude-code-plugin-loader/agent-loader.d.ts +1 -1
- package/dist/features/claude-code-plugin-loader/discovery-core.d.ts +2 -0
- package/dist/features/claude-code-plugin-loader/discovery-paths.d.ts +3 -0
- package/dist/features/claude-code-plugin-loader/discovery.d.ts +3 -4
- package/dist/features/claude-code-plugin-loader/install-path-resolver.d.ts +1 -0
- package/dist/features/claude-code-plugin-loader/installed-plugin-database.d.ts +3 -0
- package/dist/features/claude-code-plugin-loader/loaded-plugin.d.ts +2 -0
- package/dist/features/claude-code-plugin-loader/plugin-key.d.ts +1 -0
- package/dist/features/claude-code-plugin-loader/plugin-manifest.d.ts +4 -0
- package/dist/features/claude-code-plugin-loader/plugin-settings.d.ts +3 -0
- package/dist/features/claude-code-plugin-loader/types.d.ts +1 -0
- package/dist/features/hook-message-injector/context-resolver.d.ts +6 -0
- package/dist/features/hook-message-injector/id-generation.d.ts +2 -0
- package/dist/features/hook-message-injector/index.d.ts +1 -1
- package/dist/features/hook-message-injector/injector.d.ts +7 -69
- package/dist/features/hook-message-injector/json-message-lookup.d.ts +3 -0
- package/dist/features/hook-message-injector/message-directory.d.ts +1 -0
- package/dist/features/hook-message-injector/message-injection.d.ts +2 -0
- package/dist/features/hook-message-injector/sdk-message-context.d.ts +6 -0
- package/dist/features/hook-message-injector/sdk-message-lookup.d.ts +28 -0
- package/dist/features/hook-message-injector/types.d.ts +9 -0
- package/dist/features/mcp-oauth/callback-server.d.ts +10 -2
- package/dist/features/opencode-runtime-skills/source-server.d.ts +1 -0
- package/dist/features/skill-mcp-manager/http-client.d.ts +2 -0
- package/dist/features/team-mode/deps.d.ts +8 -1
- package/dist/features/team-mode/team-layout-tmux/layout.d.ts +2 -0
- package/dist/features/team-mode/team-mailbox/send.d.ts +3 -0
- package/dist/features/team-mode/team-registry/paths.d.ts +17 -2
- package/dist/features/team-mode/team-runtime/shutdown.d.ts +1 -1
- package/dist/features/team-mode/team-runtime/unresolved-team-members.d.ts +3 -0
- package/dist/features/team-mode/team-state-store/active-resume.d.ts +5 -0
- package/dist/features/team-mode/team-state-store/creating-resume.d.ts +4 -0
- package/dist/features/team-mode/team-state-store/deleting-resume.d.ts +4 -0
- package/dist/features/team-mode/team-state-store/error-normalization.d.ts +2 -0
- package/dist/features/team-mode/team-state-store/reservation-reconciliation.d.ts +4 -0
- package/dist/features/team-mode/team-state-store/resume-report.d.ts +7 -0
- package/dist/features/team-mode/team-state-store/resume.d.ts +2 -7
- package/dist/features/team-mode/team-state-store/runtime-cleanup.d.ts +4 -0
- package/dist/features/team-mode/team-state-store/session-liveness.d.ts +9 -0
- package/dist/features/team-mode/team-state-store/worker-resume-status.d.ts +9 -0
- package/dist/features/team-mode/tools/lifecycle-create-tool.d.ts +17 -0
- package/dist/features/team-mode/tools/lifecycle-inline-spec.d.ts +19 -0
- package/dist/features/team-mode/tools/lifecycle-participant.d.ts +25 -0
- package/dist/features/team-mode/tools/lifecycle-shutdown-tools.d.ts +18 -0
- package/dist/features/team-mode/tools/lifecycle-test-fixture.d.ts +3 -3
- package/dist/features/team-mode/tools/lifecycle.d.ts +3 -37
- package/dist/features/team-mode/tools/messaging-live-delivery-client.d.ts +25 -0
- package/dist/features/team-mode/tools/messaging-live-delivery-recipient.d.ts +19 -0
- package/dist/features/team-mode/tools/messaging-live-delivery-reservation.d.ts +10 -0
- package/dist/features/team-mode/tools/messaging-live-delivery-state.d.ts +5 -0
- package/dist/features/team-mode/tools/messaging-live-delivery.d.ts +6 -0
- package/dist/features/team-mode/tools/messaging-runtime.d.ts +17 -0
- package/dist/features/team-mode/tools/messaging.d.ts +4 -29
- package/dist/features/tmux-subagent/manager.d.ts +20 -1
- package/dist/features/tmux-subagent/session-created-handler.d.ts +4 -0
- package/dist/features/tmux-subagent/types.d.ts +1 -0
- package/dist/hooks/anthropic-context-window-limit-recovery/message-builder.d.ts +1 -1
- package/dist/hooks/atlas/idle-completion-nudge.d.ts +10 -0
- package/dist/hooks/atlas/idle-constants.d.ts +4 -0
- package/dist/hooks/atlas/idle-continuation.d.ts +23 -0
- package/dist/hooks/atlas/idle-session-eligibility.d.ts +8 -0
- package/dist/hooks/atlas/tool-execute-after-direct-work.d.ts +9 -0
- package/dist/hooks/atlas/tool-execute-after-plan-tasks.d.ts +3 -0
- package/dist/hooks/atlas/tool-execute-after-subagent-completion.d.ts +14 -0
- package/dist/hooks/auto-update-checker/hook/background-update-check.d.ts +6 -0
- package/dist/hooks/auto-update-checker/hook/ignore-toast-error.d.ts +1 -0
- package/dist/hooks/hephaestus-agents-md-injector/hook.d.ts +37 -0
- package/dist/hooks/hephaestus-agents-md-injector/index.d.ts +1 -0
- package/dist/hooks/index.d.ts +1 -0
- package/dist/hooks/json-error-recovery/hook.d.ts +1 -1
- package/dist/hooks/ralph-loop/command-arguments.d.ts +1 -0
- package/dist/hooks/ralph-loop/event-handler-activity.d.ts +10 -0
- package/dist/hooks/ralph-loop/event-handler-completion.d.ts +9 -0
- package/dist/hooks/ralph-loop/event-handler-continuation.d.ts +16 -0
- package/dist/hooks/ralph-loop/event-handler-feedback.d.ts +16 -0
- package/dist/hooks/ralph-loop/event-handler-idle.d.ts +15 -0
- package/dist/hooks/ralph-loop/event-handler-impl.d.ts +10 -0
- package/dist/hooks/ralph-loop/event-handler-runtime-error.d.ts +4 -0
- package/dist/hooks/ralph-loop/event-handler-types.d.ts +20 -0
- package/dist/hooks/ralph-loop/loop-state-controller.d.ts +1 -0
- package/dist/hooks/ralph-loop/ralph-loop-event-handler.d.ts +4 -24
- package/dist/hooks/ralph-loop/ralph-loop-hook.d.ts +1 -0
- package/dist/hooks/read-image-resizer/png-chunks.d.ts +6 -0
- package/dist/hooks/read-image-resizer/png-constants.d.ts +1 -0
- package/dist/hooks/read-image-resizer/png-crc.d.ts +1 -0
- package/dist/hooks/read-image-resizer/png-decoder.d.ts +1 -0
- package/dist/hooks/read-image-resizer/png-encoder.d.ts +1 -0
- package/dist/hooks/read-image-resizer/png-filters.d.ts +1 -0
- package/dist/hooks/read-image-resizer/png-ihdr.d.ts +11 -0
- package/dist/hooks/read-image-resizer/png-nearest-neighbor.d.ts +1 -0
- package/dist/hooks/rules-injector/injection-output.d.ts +2 -0
- package/dist/hooks/rules-injector/injection-processor.d.ts +22 -0
- package/dist/hooks/rules-injector/injection-types.d.ts +43 -0
- package/dist/hooks/rules-injector/injector.d.ts +3 -47
- package/dist/hooks/rules-injector/match-decision-cache.d.ts +4 -0
- package/dist/hooks/rules-injector/parsed-rule-cache.d.ts +11 -0
- package/dist/hooks/rules-injector/path-resolution.d.ts +1 -0
- package/dist/hooks/rules-injector/rule-match-reason.d.ts +12 -0
- package/dist/hooks/rules-injector/transcript-hydration.d.ts +13 -2
- package/dist/hooks/runtime-fallback/auto-retry-abort.d.ts +2 -0
- package/dist/hooks/runtime-fallback/auto-retry-agent-context.d.ts +2 -0
- package/dist/hooks/runtime-fallback/auto-retry-cleanup.d.ts +2 -0
- package/dist/hooks/runtime-fallback/auto-retry-dispatch.d.ts +2 -0
- package/dist/hooks/runtime-fallback/auto-retry-metadata.d.ts +9 -0
- package/dist/hooks/runtime-fallback/auto-retry-timeout.d.ts +5 -0
- package/dist/hooks/runtime-fallback/fallback-bootstrap-model.d.ts +1 -1
- package/dist/hooks/runtime-fallback/fallback-state.d.ts +4 -1
- package/dist/hooks/runtime-fallback/normalize-model.d.ts +12 -0
- package/dist/hooks/session-notification-linux.d.ts +3 -0
- package/dist/hooks/session-notification-log.d.ts +2 -0
- package/dist/hooks/session-notification-macos.d.ts +3 -0
- package/dist/hooks/session-notification-platform.d.ts +3 -0
- package/dist/hooks/session-notification-runner.d.ts +9 -0
- package/dist/hooks/session-notification-send.d.ts +3 -0
- package/dist/hooks/session-notification-sender.d.ts +5 -6
- package/dist/hooks/session-notification-sound.d.ts +3 -0
- package/dist/hooks/session-notification-windows.d.ts +3 -0
- package/dist/hooks/session-recovery/error-recovery.d.ts +4 -0
- package/dist/hooks/session-recovery/hook-types.d.ts +22 -0
- package/dist/hooks/session-recovery/hook.d.ts +2 -19
- package/dist/hooks/session-recovery/interrupted-tool-results.d.ts +3 -0
- package/dist/hooks/session-recovery/message-state.d.ts +4 -0
- package/dist/hooks/session-recovery/storage/thinking-strip.d.ts +7 -1
- package/dist/hooks/start-work/context-info-builder.d.ts +9 -9
- package/dist/hooks/start-work/context-info-formatters.d.ts +21 -0
- package/dist/hooks/start-work/explicit-plan-context.d.ts +9 -0
- package/dist/hooks/start-work/plan-discovery-context.d.ts +25 -0
- package/dist/hooks/start-work/plan-selection.d.ts +4 -0
- package/dist/hooks/start-work/work-initializer.d.ts +17 -0
- package/dist/hooks/tool-pair-validator/hook.d.ts +1 -37
- package/dist/hooks/tool-pair-validator/message-transform.d.ts +2 -0
- package/dist/hooks/tool-pair-validator/tool-part-ids.d.ts +6 -0
- package/dist/hooks/tool-pair-validator/tool-result-repair.d.ts +4 -0
- package/dist/hooks/tool-pair-validator/types.d.ts +36 -0
- package/dist/index.js +12708 -9988
- package/dist/oh-my-opencode.schema.json +4 -0
- package/dist/openclaw/reply-listener-poll-loop.d.ts +3 -0
- package/dist/openclaw/reply-listener-signature.d.ts +2 -0
- package/dist/openclaw/reply-listener-sleep.d.ts +1 -0
- package/dist/openclaw/reply-listener-start.d.ts +9 -0
- package/dist/openclaw/reply-listener-status.d.ts +4 -0
- package/dist/openclaw/reply-listener-stop.d.ts +7 -0
- package/dist/openclaw/reply-listener.d.ts +5 -18
- package/dist/openclaw/session-registry-lock.d.ts +2 -0
- package/dist/openclaw/session-registry-paths.d.ts +9 -0
- package/dist/openclaw/session-registry-storage.d.ts +4 -0
- package/dist/openclaw/session-registry-types.d.ts +11 -0
- package/dist/openclaw/session-registry.d.ts +2 -11
- package/dist/plugin/chat-message/loop-commands.d.ts +9 -0
- package/dist/plugin/chat-message/model-cache-warning.d.ts +12 -0
- package/dist/plugin/chat-message/prompt-text.d.ts +2 -0
- package/dist/plugin/chat-message/session-model.d.ts +4 -0
- package/dist/plugin/chat-message/start-work-message.d.ts +5 -0
- package/dist/plugin/chat-message/types.d.ts +67 -0
- package/dist/plugin/chat-message.d.ts +3 -24
- package/dist/plugin/event-error-utils.d.ts +14 -0
- package/dist/plugin/event-hook-dispatcher.d.ts +5 -0
- package/dist/plugin/event-model-fallback-state.d.ts +30 -0
- package/dist/plugin/event-model-fallback.d.ts +39 -0
- package/dist/plugin/event-session-lifecycle.d.ts +49 -0
- package/dist/plugin/event-session-recovery.d.ts +9 -0
- package/dist/plugin/event-team-handlers.d.ts +13 -0
- package/dist/plugin/event-types.d.ts +78 -0
- package/dist/plugin/event.d.ts +3 -12
- package/dist/plugin/hooks/create-core-hooks.d.ts +1 -0
- package/dist/plugin/hooks/create-session-hooks.d.ts +2 -1
- package/dist/plugin/hooks/model-fallback-title-updater.d.ts +8 -0
- package/dist/plugin/session-compacting.d.ts +4 -1
- package/dist/plugin/system-transform.d.ts +1 -1
- package/dist/plugin/tool-execute-after.d.ts +2 -0
- package/dist/plugin/tool-registry-core-tools.d.ts +15 -0
- package/dist/plugin/tool-registry-factories.d.ts +36 -0
- package/dist/plugin/tool-registry-gated-tools.d.ts +16 -0
- package/dist/plugin/tool-registry-team-tools.d.ts +14 -0
- package/dist/plugin/tool-registry-trimming.d.ts +2 -0
- package/dist/plugin/tool-registry.d.ts +3 -38
- package/dist/plugin/ultrawork-db-model-override.d.ts +1 -1
- package/dist/plugin-config/agent-order-warnings.d.ts +1 -0
- package/dist/plugin-config/config-merger.d.ts +2 -0
- package/dist/plugin-config/layered-config-loader.d.ts +2 -0
- package/dist/plugin-config/single-config-loader.d.ts +4 -0
- package/dist/plugin-config.d.ts +3 -5
- package/dist/plugin-handlers/agent-config-assembly.d.ts +19 -0
- package/dist/plugin-handlers/agent-config-finalizer.d.ts +4 -0
- package/dist/plugin-handlers/agent-config-handler.d.ts +2 -11
- package/dist/plugin-handlers/agent-config-types.d.ts +30 -0
- package/dist/plugin-handlers/agent-skill-discovery.d.ts +3 -0
- package/dist/plugin-handlers/agent-source-loader.d.ts +2 -0
- package/dist/plugin-handlers/hook-config-handler.d.ts +0 -3
- package/dist/shared/context-window-usage.d.ts +7 -0
- package/dist/shared/dynamic-truncator-types.d.ts +17 -0
- package/dist/shared/dynamic-truncator.d.ts +8 -23
- package/dist/shared/migration/migrations-sidecar.d.ts +2 -2
- package/dist/shared/migration/model-versions.d.ts +7 -4
- package/dist/shared/model-availability.d.ts +1 -1
- package/dist/shared/opencode-version.d.ts +2 -2
- package/dist/shared/sparkshell-awareness.d.ts +5 -0
- package/dist/shared/spawn-with-windows-hide.d.ts +2 -0
- package/dist/shared/token-limit-truncator.d.ts +2 -0
- package/dist/testing/module-mock-lifecycle.d.ts +8 -0
- package/dist/tools/delegate-task/openai-categories.d.ts +0 -1
- package/dist/tools/delegate-task/subagent-agent-match.d.ts +3 -0
- package/dist/tools/delegate-task/subagent-model-resolution.d.ts +4 -0
- package/dist/tools/delegate-task/subagent-request-preflight.d.ts +3 -0
- package/dist/tools/delegate-task/subagent-resolution-types.d.ts +32 -0
- package/dist/tools/delegate-task/subagent-resolver.d.ts +3 -12
- package/dist/tools/delegate-task/sync-completion-message.d.ts +20 -0
- package/dist/tools/delegate-task/sync-poll-error-recovery.d.ts +1 -0
- package/dist/tools/delegate-task/sync-session-lifecycle.d.ts +12 -0
- package/dist/tools/delegate-task/sync-session-poller.d.ts +2 -0
- package/dist/tools/delegate-task/sync-spawn-reservation.d.ts +10 -0
- package/dist/tools/delegate-task/sync-task-metadata.d.ts +11 -0
- package/dist/tools/delegate-task/sync-task-runner.d.ts +30 -0
- package/dist/tools/delegate-task/sync-task.d.ts +2 -1
- package/dist/tools/hashline-edit/formatter-trigger.d.ts +2 -2
- package/package.json +15 -14
- package/packages/git-bash-mcp/dist/cli.js +29 -12
- package/packages/lsp-tools-mcp/dist/lsp/client-wrapper.d.ts +1 -1
- package/packages/lsp-tools-mcp/dist/lsp/client-wrapper.js +1 -1
- package/packages/lsp-tools-mcp/dist/lsp/config-loader.js +95 -30
- package/packages/lsp-tools-mcp/dist/lsp/server-installation.d.ts +1 -2
- package/packages/lsp-tools-mcp/dist/lsp/server-installation.js +1 -11
- package/packages/lsp-tools-mcp/dist/lsp/transport.d.ts +1 -0
- package/packages/lsp-tools-mcp/dist/lsp/transport.js +5 -10
- package/packages/lsp-tools-mcp/dist/lsp/workspace-edit.d.ts +4 -1
- package/packages/lsp-tools-mcp/dist/lsp/workspace-edit.js +84 -23
- package/packages/lsp-tools-mcp/dist/missing-dependency-result.d.ts +2 -0
- package/packages/lsp-tools-mcp/dist/missing-dependency-result.js +14 -0
- package/packages/lsp-tools-mcp/dist/tools.js +64 -80
- package/packages/lsp-tools-mcp/package.json +4 -4
- package/packages/omo-codex/lazycodex-repository/.github/workflows/pr-source-guidance.yml +36 -0
- package/packages/omo-codex/plugin/.codex-plugin/plugin.json +1 -1
- package/packages/omo-codex/plugin/README.md +3 -1
- package/packages/omo-codex/plugin/components/comment-checker/src/apply-patch.ts +188 -0
- package/packages/omo-codex/plugin/components/comment-checker/src/core-values.ts +1 -0
- package/packages/omo-codex/plugin/components/comment-checker/src/core.ts +15 -361
- package/packages/omo-codex/plugin/components/comment-checker/src/hook-input.ts +19 -0
- package/packages/omo-codex/plugin/components/comment-checker/src/record.ts +11 -0
- package/packages/omo-codex/plugin/components/comment-checker/src/request-extractor.ts +102 -0
- package/packages/omo-codex/plugin/components/comment-checker/src/types.ts +51 -0
- package/packages/omo-codex/plugin/components/comment-checker/test/codex-hook.test.ts +145 -0
- package/packages/omo-codex/plugin/components/comment-checker/test/core.test.ts +200 -0
- package/packages/omo-codex/plugin/components/lsp/CHANGELOG.md +2 -2
- package/packages/omo-codex/plugin/components/rules/bundled-rules/hephaestus.md +11 -5
- package/packages/omo-codex/plugin/components/rules/src/hook-output.ts +11 -1
- package/packages/omo-codex/plugin/components/rules/src/post-compact-budget.ts +0 -1
- package/packages/omo-codex/plugin/components/rules/src/rules/constants.ts +1 -4
- package/packages/omo-codex/plugin/components/rules/src/rules/engine-dynamic-cache.ts +87 -0
- package/packages/omo-codex/plugin/components/rules/src/rules/engine-dynamic-loader.ts +94 -0
- package/packages/omo-codex/plugin/components/rules/src/rules/engine-loader.ts +84 -0
- package/packages/omo-codex/plugin/components/rules/src/rules/engine-paths.ts +103 -0
- package/packages/omo-codex/plugin/components/rules/src/rules/engine-static-loader.ts +43 -0
- package/packages/omo-codex/plugin/components/rules/src/rules/engine-types.ts +45 -0
- package/packages/omo-codex/plugin/components/rules/src/rules/engine.ts +8 -419
- package/packages/omo-codex/plugin/components/rules/src/rules/formatter.ts +39 -13
- package/packages/omo-codex/plugin/components/rules/src/rules/parser-frontmatter.ts +39 -0
- package/packages/omo-codex/plugin/components/rules/src/rules/parser-yaml.ts +271 -0
- package/packages/omo-codex/plugin/components/rules/src/rules/parser.ts +3 -294
- package/packages/omo-codex/plugin/components/rules/src/rules/truncator.ts +17 -0
- package/packages/omo-codex/plugin/components/rules/src/sparkshell-awareness.ts +57 -0
- package/packages/omo-codex/plugin/components/rules/src/static-injection.ts +13 -2
- package/packages/omo-codex/plugin/components/rules/src/transcript-rule-filter.ts +17 -0
- package/packages/omo-codex/plugin/components/rules/test/bundled-rules-priority.test.ts +2 -1
- package/packages/omo-codex/plugin/components/rules/test/bundled-rules.test.ts +26 -11
- package/packages/omo-codex/plugin/components/rules/test/codex-hook-context-pressure.test.ts +104 -138
- package/packages/omo-codex/plugin/components/rules/test/codex-hook-post-compact-budget.test.ts +5 -2
- package/packages/omo-codex/plugin/components/rules/test/codex-hook-post-compact-context.test.ts +12 -5
- package/packages/omo-codex/plugin/components/rules/test/codex-hook.test.ts +10 -4
- package/packages/omo-codex/plugin/components/rules/test/engine.test.ts +65 -3
- package/packages/omo-codex/plugin/components/rules/test/formatter.test.ts +67 -2
- package/packages/omo-codex/plugin/components/rules/test/hook-output.test.ts +16 -0
- package/packages/omo-codex/plugin/components/rules/test/parser.test.ts +153 -0
- package/packages/omo-codex/plugin/components/rules/test/post-compact-budget.test.ts +12 -0
- package/packages/omo-codex/plugin/components/rules/test/sparkshell-awareness.test.ts +236 -0
- package/packages/omo-codex/plugin/components/rules/test/tool-paths.test.ts +28 -50
- package/packages/omo-codex/plugin/components/rules/test/windows-git-bash-bundled-rule.test.ts +6 -3
- package/packages/omo-codex/plugin/components/start-work-continuation/directive.md +13 -6
- package/packages/omo-codex/plugin/components/start-work-continuation/src/codex-hook.ts +21 -0
- package/packages/omo-codex/plugin/components/start-work-continuation/test/codex-hook.test.ts +64 -2
- package/packages/omo-codex/plugin/components/telemetry/README.md +11 -1
- package/packages/omo-codex/plugin/components/telemetry/biome.json +12 -0
- package/packages/omo-codex/plugin/components/telemetry/src/codex-hook.ts +30 -3
- package/packages/omo-codex/plugin/components/telemetry/src/diagnostics.ts +154 -0
- package/packages/omo-codex/plugin/components/telemetry/src/posthog-activity-state.ts +18 -2
- package/packages/omo-codex/plugin/components/telemetry/src/posthog.ts +36 -4
- package/packages/omo-codex/plugin/components/telemetry/test/codex-hook-diagnostics.test.ts +115 -0
- package/packages/omo-codex/plugin/components/telemetry/test/codex-hook.test.ts +16 -25
- package/packages/omo-codex/plugin/components/telemetry/test/diagnostics.test.ts +119 -0
- package/packages/omo-codex/plugin/components/ultrawork/AGENTS.md +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/README.md +5 -5
- package/packages/omo-codex/plugin/components/ultrawork/agents/codex-ultrawork-reviewer.toml +2 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/explorer.toml +1 -0
- package/packages/omo-codex/plugin/components/ultrawork/agents/metis.toml +0 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/momus.toml +0 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/plan.toml +1 -2
- package/packages/omo-codex/plugin/components/ultrawork/directive.md +97 -32
- package/packages/omo-codex/plugin/components/ultrawork/skills/ulw-plan/SKILL.md +65 -0
- package/packages/omo-codex/plugin/components/ultrawork/skills/ulw-plan/agents/openai.yaml +7 -0
- package/packages/omo-codex/plugin/components/ultrawork/skills/ulw-plan/references/full-workflow.md +131 -0
- package/packages/omo-codex/plugin/components/ultrawork/test/codex-hook.test.ts +38 -10
- package/packages/omo-codex/plugin/components/ultrawork/test/directive-contract.test.ts +18 -0
- package/packages/omo-codex/plugin/components/ultrawork/test/package-smoke.test.ts +47 -0
- 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 +12 -8
- package/packages/omo-codex/plugin/components/ulw-loop/skills/ulw-loop/references/full-workflow.md +28 -21
- package/packages/omo-codex/plugin/components/ulw-loop/src/codex-goal-instruction.ts +2 -3
- package/packages/omo-codex/plugin/components/ulw-loop/src/codex-hook.ts +7 -7
- package/packages/omo-codex/plugin/components/ulw-loop/src/command-types.ts +36 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/constants.ts +64 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/domain-types.ts +98 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/plan-crud.ts +17 -2
- package/packages/omo-codex/plugin/components/ulw-loop/src/runtime.ts +22 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/steering-types.ts +69 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/types.ts +5 -277
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-commands.test.ts +35 -13
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-complete-goals.test.ts +52 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-steering.test.ts +67 -111
- package/packages/omo-codex/plugin/components/ulw-loop/test/codex-goal-instruction.test.ts +2 -2
- package/packages/omo-codex/plugin/components/ulw-loop/test/codex-hook.test.ts +31 -2
- package/packages/omo-codex/plugin/components/ulw-loop/test/package-smoke.test.ts +46 -9
- package/packages/omo-codex/plugin/components/ulw-loop/test/steering.test.ts +20 -29
- package/packages/omo-codex/plugin/model-catalog.json +5 -11
- package/packages/omo-codex/plugin/package-lock.json +1 -1
- package/packages/omo-codex/plugin/scripts/auto-update-state.mjs +78 -0
- package/packages/omo-codex/plugin/scripts/auto-update.mjs +166 -76
- package/packages/omo-codex/plugin/scripts/migrate-codex-config/catalog.mjs +71 -0
- package/packages/omo-codex/plugin/scripts/migrate-codex-config/config-paths.mjs +44 -0
- package/packages/omo-codex/plugin/scripts/migrate-codex-config/multi-agent-v2-guard.mjs +40 -0
- package/packages/omo-codex/plugin/scripts/migrate-codex-config/root-settings.mjs +74 -0
- package/packages/omo-codex/plugin/scripts/migrate-codex-config/state.mjs +29 -0
- package/packages/omo-codex/plugin/scripts/migrate-codex-config.mjs +33 -204
- package/packages/omo-codex/plugin/scripts/spawn-command.mjs +11 -0
- package/packages/omo-codex/plugin/scripts/sync-hook-status-messages.mjs +23 -9
- package/packages/omo-codex/plugin/scripts/sync-skills.mjs +131 -28
- package/packages/omo-codex/plugin/skills/debugging/references/methodology/04-oracle-triple.md +3 -3
- package/packages/omo-codex/plugin/skills/git-master/SKILL.md +100 -0
- package/packages/omo-codex/plugin/skills/git-master/agents/openai.yaml +13 -0
- package/packages/omo-codex/plugin/skills/init-deep/SKILL.md +9 -7
- package/packages/omo-codex/plugin/skills/lcx-contribute-bug-fix/SKILL.md +176 -0
- package/packages/omo-codex/plugin/skills/lcx-contribute-bug-fix/agents/openai.yaml +12 -0
- package/packages/omo-codex/plugin/skills/lcx-contribute-bug-fix/scripts/create-pr-body.mjs +107 -0
- package/packages/omo-codex/plugin/skills/lcx-report-bug/SKILL.md +119 -14
- package/packages/omo-codex/plugin/skills/lcx-report-bug/agents/openai.yaml +4 -2
- package/packages/omo-codex/plugin/skills/programming/references/go/concurrency.md +2 -2
- package/packages/omo-codex/plugin/skills/programming/references/python/async-anyio.md +6 -6
- package/packages/omo-codex/plugin/skills/programming/references/python/pydantic-ai.md +12 -12
- package/packages/omo-codex/plugin/skills/programming/references/typescript/backend-hono.md +7 -7
- package/packages/omo-codex/plugin/skills/refactor/SKILL.md +13 -11
- package/packages/omo-codex/plugin/skills/remove-ai-slops/SKILL.md +10 -8
- package/packages/omo-codex/plugin/skills/review-work/SKILL.md +68 -33
- package/packages/omo-codex/plugin/skills/start-work/SKILL.md +86 -22
- package/packages/omo-codex/plugin/skills/ultraresearch/SKILL.md +770 -0
- package/packages/omo-codex/plugin/skills/ulw-loop/SKILL.md +12 -8
- package/packages/omo-codex/plugin/skills/ulw-loop/references/full-workflow.md +28 -21
- package/packages/omo-codex/plugin/skills/ulw-plan/SKILL.md +45 -379
- package/packages/omo-codex/plugin/skills/ulw-plan/agents/openai.yaml +7 -0
- package/packages/omo-codex/plugin/skills/ulw-plan/references/full-workflow.md +131 -0
- package/packages/omo-codex/plugin/skills/visual-qa/SKILL.md +237 -0
- package/packages/omo-codex/plugin/skills/visual-qa/scripts/ansi.ts +17 -0
- package/packages/omo-codex/plugin/skills/visual-qa/scripts/cli.ts +82 -0
- package/packages/omo-codex/plugin/skills/visual-qa/scripts/east-asian-width.ts +72 -0
- package/packages/omo-codex/plugin/skills/visual-qa/scripts/image-diff.ts +109 -0
- package/packages/omo-codex/plugin/skills/visual-qa/scripts/png-crc.ts +27 -0
- package/packages/omo-codex/plugin/skills/visual-qa/scripts/png-decode.ts +206 -0
- package/packages/omo-codex/plugin/skills/visual-qa/scripts/png-synth.ts +57 -0
- package/packages/omo-codex/plugin/skills/visual-qa/scripts/tui-grid.ts +88 -0
- package/packages/omo-codex/plugin/skills/visual-qa/scripts/types.ts +54 -0
- package/packages/omo-codex/plugin/test/aggregate-agents.test.mjs +55 -0
- package/packages/omo-codex/plugin/test/aggregate-build.test.mjs +38 -0
- package/packages/omo-codex/plugin/test/aggregate-hooks.test.mjs +164 -0
- package/packages/omo-codex/plugin/test/aggregate-manifest.test.mjs +73 -0
- package/packages/omo-codex/plugin/test/aggregate-mcp.test.mjs +69 -0
- package/packages/omo-codex/plugin/test/aggregate-model-catalog.test.mjs +53 -0
- package/packages/omo-codex/plugin/test/aggregate-plugin-fixture.mjs +83 -0
- package/packages/omo-codex/plugin/test/aggregate-skills.test.mjs +67 -0
- package/packages/omo-codex/plugin/test/aggregate.test.mjs +2 -514
- package/packages/omo-codex/plugin/test/auto-update-state-persistence.test.mjs +36 -0
- package/packages/omo-codex/plugin/test/auto-update.test.mjs +191 -29
- package/packages/omo-codex/plugin/test/component-bin-names.test.mjs +1 -1
- package/packages/omo-codex/plugin/test/global-review-debug-gate.test.mjs +29 -0
- package/packages/omo-codex/plugin/test/hook-status-message.test.mjs +23 -10
- package/packages/omo-codex/plugin/test/lcx-bug-skills.test.mjs +81 -0
- package/packages/omo-codex/plugin/test/lcx-contribute-bug-fix-template.test.mjs +91 -0
- package/packages/omo-codex/plugin/test/migrate-codex-config.test.mjs +244 -9
- package/packages/omo-codex/plugin/test/node-install-surface.test.mjs +0 -19
- package/packages/omo-codex/plugin/test/start-work-skill.test.mjs +107 -0
- package/packages/omo-codex/plugin/test/subagent-guidance.test.mjs +82 -7
- package/packages/omo-codex/plugin/test/sync-hook-status-messages.test.mjs +58 -6
- package/packages/omo-codex/plugin/test/sync-skills-orchestration.test.mjs +152 -0
- package/packages/omo-codex/plugin/test/sync-skills.test.mjs +158 -50
- package/packages/omo-codex/plugin/test/ulw-plan-skill.test.mjs +43 -0
- package/packages/omo-codex/scripts/install/agent-source-roots.mjs +13 -0
- package/packages/omo-codex/scripts/install/agents.mjs +84 -14
- package/packages/omo-codex/scripts/install/bin-links.mjs +239 -0
- package/packages/omo-codex/scripts/install/cache.mjs +152 -108
- package/packages/omo-codex/scripts/install/cached-marketplace-manifest.mjs +21 -0
- package/packages/omo-codex/scripts/install/cli-args.mjs +39 -2
- package/packages/omo-codex/scripts/install/config.mjs +9 -5
- package/packages/omo-codex/scripts/install/lazycodex-version-stamp.mjs +102 -0
- package/packages/omo-codex/scripts/install/legacy-bins.mjs +9 -1
- package/packages/omo-codex/scripts/install/model-catalog.mjs +9 -1
- package/packages/omo-codex/scripts/install/multi-agent-v2-config.mjs +12 -10
- package/packages/omo-codex/scripts/install/process.mjs +3 -1
- package/packages/omo-codex/scripts/install/project-local-cleanup.mjs +0 -1
- package/packages/omo-codex/scripts/install/snapshot.mjs +0 -1
- package/packages/omo-codex/scripts/install-agent-links.test.mjs +205 -11
- package/packages/omo-codex/scripts/install-bin-links.test.mjs +123 -1
- package/packages/omo-codex/scripts/install-cache-copy.test.mjs +129 -5
- package/packages/omo-codex/scripts/install-cli-args.test.mjs +82 -1
- package/packages/omo-codex/scripts/install-config-preservation.test.mjs +43 -0
- package/packages/omo-codex/scripts/install-config-reasoning.test.mjs +14 -1
- package/packages/omo-codex/scripts/install-config.test.mjs +49 -1
- package/packages/omo-codex/scripts/install-lazycodex-version-stamp.test.mjs +84 -0
- package/packages/omo-codex/scripts/install-local-entrypoint.test.mjs +51 -0
- package/packages/omo-codex/scripts/install-local.mjs +42 -40
- package/packages/omo-codex/scripts/install-local.test.mjs +17 -241
- package/packages/omo-codex/scripts/install-marketplace-cache.test.mjs +162 -0
- package/packages/omo-codex/scripts/install-packaged-local.test.mjs +10 -6
- package/packages/omo-codex/scripts/install-project-local-cleanup.test.mjs +73 -2
- package/packages/omo-codex/scripts/sync-telemetry-component.mjs +1 -0
- package/packages/shared-skills/skills/debugging/references/methodology/04-oracle-triple.md +3 -3
- package/packages/shared-skills/skills/git-master/SKILL.md +100 -0
- package/packages/shared-skills/skills/git-master/agents/openai.yaml +13 -0
- package/packages/shared-skills/skills/lcx-contribute-bug-fix/SKILL.md +176 -0
- package/packages/shared-skills/skills/lcx-contribute-bug-fix/agents/openai.yaml +12 -0
- package/packages/shared-skills/skills/lcx-contribute-bug-fix/scripts/create-pr-body.mjs +107 -0
- package/packages/shared-skills/skills/lcx-report-bug/SKILL.md +119 -14
- package/packages/shared-skills/skills/lcx-report-bug/agents/openai.yaml +4 -2
- package/packages/shared-skills/skills/programming/references/go/concurrency.md +2 -2
- package/packages/shared-skills/skills/programming/references/python/async-anyio.md +6 -6
- package/packages/shared-skills/skills/programming/references/python/pydantic-ai.md +12 -12
- package/packages/shared-skills/skills/programming/references/typescript/backend-hono.md +7 -7
- package/packages/shared-skills/skills/refactor/SKILL.md +4 -4
- package/packages/shared-skills/skills/remove-ai-slops/SKILL.md +1 -1
- package/packages/shared-skills/skills/review-work/SKILL.md +55 -33
- package/packages/shared-skills/skills/start-work/SKILL.md +76 -19
- package/packages/shared-skills/skills/ultraresearch/SKILL.md +770 -0
- package/packages/shared-skills/skills/visual-qa/SKILL.md +219 -0
- package/packages/shared-skills/skills/visual-qa/scripts/ansi.test.ts +45 -0
- package/packages/shared-skills/skills/visual-qa/scripts/ansi.ts +17 -0
- package/packages/shared-skills/skills/visual-qa/scripts/cli.test.ts +73 -0
- package/packages/shared-skills/skills/visual-qa/scripts/cli.ts +82 -0
- package/packages/shared-skills/skills/visual-qa/scripts/east-asian-width.test.ts +60 -0
- package/packages/shared-skills/skills/visual-qa/scripts/east-asian-width.ts +72 -0
- package/packages/shared-skills/skills/visual-qa/scripts/image-diff.test.ts +70 -0
- package/packages/shared-skills/skills/visual-qa/scripts/image-diff.ts +109 -0
- package/packages/shared-skills/skills/visual-qa/scripts/png-crc.ts +27 -0
- package/packages/shared-skills/skills/visual-qa/scripts/png-decode.test.ts +44 -0
- package/packages/shared-skills/skills/visual-qa/scripts/png-decode.ts +206 -0
- package/packages/shared-skills/skills/visual-qa/scripts/png-synth.ts +57 -0
- package/packages/shared-skills/skills/visual-qa/scripts/skill-prompt-contract.test.ts +83 -0
- package/packages/shared-skills/skills/visual-qa/scripts/tui-grid.test.ts +57 -0
- package/packages/shared-skills/skills/visual-qa/scripts/tui-grid.ts +88 -0
- package/packages/shared-skills/skills/visual-qa/scripts/types.ts +54 -0
- package/postinstall.mjs +24 -1
- package/dist/agents/custom-agent-summaries.d.ts +0 -8
- package/dist/agents/hephaestus/gpt-5-3-codex.d.ts +0 -20
- package/dist/agents/prometheus/gemini.d.ts +0 -1
- package/dist/agents/prometheus/gpt.d.ts +0 -1
- package/dist/agents/sisyphus-junior/gpt-5-3-codex.d.ts +0 -8
- package/dist/features/background-agent/session-route.d.ts +0 -12
- package/dist/features/background-agent/spawner/parent-directory-resolver.d.ts +0 -6
- package/dist/features/background-agent/state.d.ts +0 -35
- package/dist/features/claude-tasks/session-storage.d.ts +0 -9
- package/dist/features/mcp-oauth/resource-indicator.d.ts +0 -2
- package/dist/features/mcp-oauth/schema.d.ts +0 -6
- package/dist/features/opencode-skill-loader/async-loader.d.ts +0 -6
- package/dist/features/opencode-skill-loader/blocking.d.ts +0 -2
- package/dist/features/opencode-skill-loader/discover-worker.d.ts +0 -1
- package/dist/hooks/session-recovery/recover-empty-content-message-sdk.d.ts +0 -13
- package/dist/shared/bun-hash-shim.d.ts +0 -1
- package/dist/tools/delegate-task/resolve-call-id.d.ts +0 -2
- package/packages/shared-skills/skills/ulw-plan/SKILL.md +0 -383
- /package/packages/lsp-tools-mcp/dist/lsp/{utils.d.ts → startup-failure.d.ts} +0 -0
- /package/packages/lsp-tools-mcp/dist/lsp/{utils.js → startup-failure.js} +0 -0
|
@@ -18,11 +18,12 @@ You are mid-flight on a Prometheus work plan. The turn just ended without finish
|
|
|
18
18
|
1. Read `{{PLAN_PATH}}` AND `{{LEDGER_PATH}}` first — ground truth for what remains and what evidence has already been recorded. The plan checkbox and the ledger are the only sources of truth; do not trust your own memory of prior turns.
|
|
19
19
|
2. Pick the FIRST unchecked top-level checkbox in `## TODOs` or `## Final Verification Wave`. Ignore nested checkboxes under Acceptance Criteria / Evidence / Definition of Done.
|
|
20
20
|
3. Follow the `start-work` skill in full. The skill is already loaded from your earlier turn — re-read its file at `packages/omo-codex/plugin/skills/start-work/SKILL.md` if you have lost context.
|
|
21
|
-
4. Decompose the checkbox into atomic sub-tasks. Dispatch them in PARALLEL via `spawn_agent` calls in this same response unless a sub-task has a NAMED blocking dependency (input from another sub-task or shared file). Prefer `fork_turns: "none"` unless full history is truly required.
|
|
21
|
+
4. Decompose the checkbox into atomic sub-tasks. Dispatch them in PARALLEL via `spawn_agent` calls in this same response unless a sub-task has a NAMED blocking dependency (input from another sub-task or shared file). Prefer `fork_turns: "none"` unless full history is truly required. Put role and specialty instructions inside `message`; the Codex tool schema only accepts `task_name`, `message`, and `fork_turns`.
|
|
22
22
|
5. Every sub-task message MUST be self-contained and start with `TASK: <imperative assignment>`, then name `DELIVERABLE`, `SCOPE`, and `VERIFY`. State that it is an executable assignment, not a context handoff. It must include all 7 sections and name one Manual-QA channel with its exact tool and exact invocation (the literal `curl` / `send-keys` / `page.click` with concrete inputs and the binary PASS/FAIL observable), plus the applicable ultraqa adversarial classes, a captured artifact, and a cleanup receipt. Channels: HTTP call (`curl -i`); tmux (`send-keys` + `capture-pane`); browser use — use Chrome to drive the page, else download and use agent-browser (https://github.com/vercel-labs/agent-browser); computer use — OS-level GUI automation for a desktop app. Tests are the floor; the channel artifact plus probed adversarial classes are the ceiling. All are required.
|
|
23
|
-
6.
|
|
24
|
-
7.
|
|
25
|
-
8.
|
|
23
|
+
6. Treat every worker DoneClaim as untrusted input. Run independent AdversarialVerify before any checkbox can become FullyDone; `confirmed` is the only pass verdict, while `false-positive`, `needs-fix`, and `needs-human-review` loop back to the executor with exact feedback.
|
|
24
|
+
7. Use `wait_agent` for mailbox signals, not proof of completion. For sub-tasks likely to exceed one wait cycle, require `WORKING: <task> - <current phase>` before long passes and `BLOCKED: <reason>` only when progress stops. A timeout only means no new mailbox update arrived; after a timeout, run a single `list_agents` check for the named child when you need reassurance. If it is running or its latest message is `WORKING:`, treat it as alive. Do not use `list_agents` as a polling loop. Send `TASK STILL ACTIVE: return <deliverable> or BLOCKED: <reason>` only when the child is completed without the deliverable, ack-only, or no longer running. If that followup is still silent or ack-only, record inconclusive, do not count it as pass/review approval, close if safe, and respawn a smaller `fork_turns: "none"` task with the missing deliverable.
|
|
25
|
+
8. After verification of ALL sub-tasks under this checkbox: `apply_patch` the plan to change `- [ ]` → `- [x]`, re-read the plan to confirm the count decreased, append a `task-completed` line to the ledger, then continue.
|
|
26
|
+
9. Do not start fresh on a sub-agent failure. Re-dispatch the same `task_name` with a fix-message: `FAILED: <exact error>` + `Diagnosis: <observation>` + `Fix: <instruction>`.
|
|
26
27
|
|
|
27
28
|
# Hard constraints
|
|
28
29
|
|
|
@@ -34,12 +35,18 @@ You are mid-flight on a Prometheus work plan. The turn just ended without finish
|
|
|
34
35
|
- The worktree path (if set in boulder.json) governs every file edit and command. Do not stray into the main repo.
|
|
35
36
|
- session_ids you write to boulder.json MUST be prefixed `codex:`. Bare ids on read are legacy `opencode:`.
|
|
36
37
|
|
|
38
|
+
# Global Review and Debugging Gate
|
|
39
|
+
|
|
40
|
+
Before completion, run `review-work` and a `debugging` runtime audit. Treat timeout, missing deliverable, ack-only, `BLOCKED:`, and inconclusive review lanes as failures, not progress. Record at least three debugging hypotheses and the runtime evidence that confirms or refutes each one.
|
|
41
|
+
|
|
42
|
+
Do not print `ORCHESTRATION COMPLETE`. Do not create a PR, PR handoff, or branch handoff. Do not write a final completion answer until this gate passes. Always redact secrets, tokens, credentials, auth headers, cookies, env dumps, private logs, and PII from ledgers, PR bodies, and handoffs.
|
|
43
|
+
|
|
37
44
|
# Stop conditions for THIS turn
|
|
38
45
|
|
|
39
46
|
- A top-level checkbox flipped to `- [x]` after the 5-phase QA gate (Phase 1 read, Phase 2 automated, Phase 3 channel scenario, Phase 4 adversarial-class probing, Phase 5 gate decision). Then the Stop hook will re-evaluate; if more checkboxes remain you will be continued again.
|
|
40
|
-
- 3 same-failure cycles on one sub-task → escalate via `spawn_agent(
|
|
47
|
+
- 3 same-failure cycles on one sub-task → escalate via `spawn_agent({"task_name":"failure_escalation_review","message":"TASK: act as a rigorous reviewer. DELIVERABLE: diagnose the repeated sub-task failure and recommend the next safe action. VERIFY: cite the failing evidence.","fork_turns":"none"})` and stop dispatch.
|
|
41
48
|
- Safety boundary (destructive command, secret exfiltration, production write) → stop and surface a safe substitute.
|
|
42
|
-
- All top-level checkboxes `- [x]` AND
|
|
49
|
+
- All top-level checkboxes `- [x]` AND the Global Review and Debugging Gate passed → print the ORCHESTRATION COMPLETE block and end.
|
|
43
50
|
|
|
44
51
|
# Output discipline
|
|
45
52
|
|
|
@@ -6,6 +6,7 @@ import type { ReadonlyFileSystem, StopHookEventName, StopHookOutput, StopInput }
|
|
|
6
6
|
export function runStopHook(input: unknown, fs: ReadonlyFileSystem): string {
|
|
7
7
|
if (!isStopInput(input)) return "";
|
|
8
8
|
if (input.stop_hook_active) return "";
|
|
9
|
+
if (transcriptHasContextPressureMarker(input.transcript_path, fs)) return "";
|
|
9
10
|
const state = readContinuationState(input.cwd, input.session_id, fs);
|
|
10
11
|
if (state === null) return "";
|
|
11
12
|
return JSON.stringify({
|
|
@@ -38,6 +39,26 @@ function renderDirective(state: ContinuationState, sessionId: string): string {
|
|
|
38
39
|
return rendered;
|
|
39
40
|
}
|
|
40
41
|
|
|
42
|
+
const CONTEXT_PRESSURE_MARKERS = [
|
|
43
|
+
"context compacted",
|
|
44
|
+
"context_length_exceeded",
|
|
45
|
+
"skill descriptions were shortened",
|
|
46
|
+
"context_too_large",
|
|
47
|
+
"codex ran out of room in the model's context window",
|
|
48
|
+
"your input exceeds the context window",
|
|
49
|
+
"long threads and multiple compactions",
|
|
50
|
+
] as const;
|
|
51
|
+
|
|
52
|
+
function transcriptHasContextPressureMarker(transcriptPath: string, fs: ReadonlyFileSystem): boolean {
|
|
53
|
+
try {
|
|
54
|
+
const transcript = fs.readFileSync(transcriptPath, "utf8").toLowerCase();
|
|
55
|
+
return CONTEXT_PRESSURE_MARKERS.some((marker) => transcript.includes(marker));
|
|
56
|
+
} catch (error) {
|
|
57
|
+
if (error instanceof Error) return false;
|
|
58
|
+
throw error;
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
|
|
41
62
|
function isStopInput(value: unknown): value is StopInput {
|
|
42
63
|
return (
|
|
43
64
|
isRecord(value) &&
|
package/packages/omo-codex/plugin/components/start-work-continuation/test/codex-hook.test.ts
CHANGED
|
@@ -22,6 +22,21 @@ describe("start-work Stop hook", () => {
|
|
|
22
22
|
expect(output).toBe("");
|
|
23
23
|
});
|
|
24
24
|
|
|
25
|
+
it("#given no boulder state and start work prompt #when stop hook runs #then it stays quiet", () => {
|
|
26
|
+
// given
|
|
27
|
+
const fs = createMemoryFs();
|
|
28
|
+
const input = {
|
|
29
|
+
...createStopInput(),
|
|
30
|
+
last_assistant_message: "I'll start work on this plan now.",
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
// when
|
|
34
|
+
const output = runStopHook(input, fs);
|
|
35
|
+
|
|
36
|
+
// then
|
|
37
|
+
expect(output).toBe("");
|
|
38
|
+
});
|
|
39
|
+
|
|
25
40
|
it("#given active codex work with remaining top-level tasks #when hook runs #then returns block JSON", () => {
|
|
26
41
|
// given
|
|
27
42
|
const fs = createMemoryFs({
|
|
@@ -49,6 +64,38 @@ describe("start-work Stop hook", () => {
|
|
|
49
64
|
expect(parsed.reason).toContain("- Your session id in boulder.json: `codex:sess_abc`");
|
|
50
65
|
});
|
|
51
66
|
|
|
67
|
+
it("#given context-window pressure in transcript #when hook runs #then it does not inject continuation text", () => {
|
|
68
|
+
// given
|
|
69
|
+
const transcriptPath = "/repo/transcript.jsonl";
|
|
70
|
+
const fs = createMemoryFs({
|
|
71
|
+
[BOULDER_PATH]: createBoulderJson({
|
|
72
|
+
sessionIds: ["codex:sess_abc"],
|
|
73
|
+
status: "active",
|
|
74
|
+
}),
|
|
75
|
+
[PLAN_PATH]: ["# Plan", "", "## TODOs", "- [ ] First"].join("\n"),
|
|
76
|
+
[transcriptPath]: [
|
|
77
|
+
JSON.stringify({
|
|
78
|
+
type: "message",
|
|
79
|
+
payload: {
|
|
80
|
+
content: {
|
|
81
|
+
error: {
|
|
82
|
+
code: "context_too_large",
|
|
83
|
+
},
|
|
84
|
+
},
|
|
85
|
+
},
|
|
86
|
+
}),
|
|
87
|
+
"Your input exceeds the context window of this model.",
|
|
88
|
+
"",
|
|
89
|
+
].join("\n"),
|
|
90
|
+
});
|
|
91
|
+
|
|
92
|
+
// when
|
|
93
|
+
const output = runStopHook({ ...createStopInput(), transcript_path: transcriptPath }, fs);
|
|
94
|
+
|
|
95
|
+
// then
|
|
96
|
+
expect(output).toBe("");
|
|
97
|
+
});
|
|
98
|
+
|
|
52
99
|
it("#given active codex work #when continuation directive is emitted #then subagent guidance is reliable", () => {
|
|
53
100
|
// given
|
|
54
101
|
const fs = createMemoryFs({
|
|
@@ -66,9 +113,11 @@ describe("start-work Stop hook", () => {
|
|
|
66
113
|
const parsed = parseBlockOutput(output);
|
|
67
114
|
expect(parsed.reason).toMatch(/TASK:/);
|
|
68
115
|
expect(parsed.reason).toMatch(/fork_turns:\s*"none"/);
|
|
69
|
-
expect(parsed.reason).toMatch(/wait_agent.*
|
|
70
|
-
expect(parsed.reason).toMatch(/
|
|
116
|
+
expect(parsed.reason).toMatch(/wait_agent.*mailbox signals/);
|
|
117
|
+
expect(parsed.reason).toMatch(/TASK STILL ACTIVE/);
|
|
71
118
|
expect(parsed.reason).toMatch(/respawn.*smaller/);
|
|
119
|
+
expect(parsed.reason).toMatch(/WORKING:/);
|
|
120
|
+
expect(parsed.reason).toMatch(/single `list_agents`/);
|
|
72
121
|
});
|
|
73
122
|
|
|
74
123
|
it("#given active work belongs to another harness #when hook runs #then returns empty output", () => {
|
|
@@ -113,6 +162,19 @@ describe("start-work Stop hook", () => {
|
|
|
113
162
|
expect(output).toBe("");
|
|
114
163
|
});
|
|
115
164
|
|
|
165
|
+
it("#given malformed boulder JSON #when hook runs #then returns empty output", () => {
|
|
166
|
+
// given
|
|
167
|
+
const fs = createMemoryFs({
|
|
168
|
+
[BOULDER_PATH]: "{",
|
|
169
|
+
});
|
|
170
|
+
|
|
171
|
+
// when
|
|
172
|
+
const output = runStopHook(createStopInput(), fs);
|
|
173
|
+
|
|
174
|
+
// then
|
|
175
|
+
expect(output).toBe("");
|
|
176
|
+
});
|
|
177
|
+
|
|
116
178
|
it("#given malformed input #when hook runs #then returns empty output", () => {
|
|
117
179
|
// given
|
|
118
180
|
const fs = createMemoryFs();
|
|
@@ -76,7 +76,17 @@ containing `{ "lastActiveDayUTC": "YYYY-MM-DD" }`. If the stored day matches tod
|
|
|
76
76
|
|
|
77
77
|
## Failure Behavior
|
|
78
78
|
|
|
79
|
-
Every telemetry path is wrapped in `try`/`catch`. The hook always exits 0 with no stdout output, even when PostHog construction, capture, or shutdown fails. Codex session startup is never blocked or slowed by telemetry failures.
|
|
79
|
+
Every telemetry path is wrapped in `try`/`catch`. The hook always exits 0 with no stdout or stderr output, even when PostHog construction, capture, or shutdown fails. Codex session startup is never blocked or slowed by telemetry failures.
|
|
80
|
+
|
|
81
|
+
Handled telemetry failures are written only to a local diagnostics file:
|
|
82
|
+
|
|
83
|
+
```
|
|
84
|
+
$XDG_DATA_HOME/omo-codex/telemetry-diagnostics.jsonl
|
|
85
|
+
# or, when XDG_DATA_HOME is unset:
|
|
86
|
+
~/.local/share/omo-codex/telemetry-diagnostics.jsonl
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
The diagnostics file keeps JSONL rows for recent telemetry failures, prunes stale rows during writes, and caps itself at 256 KiB by dropping the oldest complete rows. Diagnostics are never sent to PostHog and do not include prompt contents, transcript contents, raw hostnames, API keys, tokens, or full hook payloads.
|
|
80
90
|
|
|
81
91
|
## Endpoint Overrides
|
|
82
92
|
|
|
@@ -34,6 +34,18 @@
|
|
|
34
34
|
"includes": ["src/**/*.ts", "test/**/*.ts", "vitest.config.ts", "!**/node_modules/**/*", "!**/dist/**/*"]
|
|
35
35
|
},
|
|
36
36
|
"overrides": [
|
|
37
|
+
{
|
|
38
|
+
"includes": [
|
|
39
|
+
"src/atomic-write.ts",
|
|
40
|
+
"src/data-path.ts",
|
|
41
|
+
"src/diagnostics.ts",
|
|
42
|
+
"src/env-flags.ts",
|
|
43
|
+
"src/posthog-activity-state.ts"
|
|
44
|
+
],
|
|
45
|
+
"formatter": {
|
|
46
|
+
"enabled": false
|
|
47
|
+
}
|
|
48
|
+
},
|
|
37
49
|
{
|
|
38
50
|
"includes": ["vitest.config.ts"],
|
|
39
51
|
"linter": {
|
|
@@ -1,3 +1,8 @@
|
|
|
1
|
+
import {
|
|
2
|
+
type TelemetryDiagnosticErrorKind,
|
|
3
|
+
type TelemetryDiagnosticEvent,
|
|
4
|
+
writeTelemetryDiagnostic,
|
|
5
|
+
} from "./diagnostics.js";
|
|
1
6
|
import {
|
|
2
7
|
createPluginPostHog,
|
|
3
8
|
getPostHogDistinctId,
|
|
@@ -22,6 +27,19 @@ export type CodexTelemetryHookOptions = {
|
|
|
22
27
|
|
|
23
28
|
const SESSION_START_REASON: PostHogActivityReason = "session_start";
|
|
24
29
|
|
|
30
|
+
function writeHookDiagnostic(
|
|
31
|
+
event: TelemetryDiagnosticEvent,
|
|
32
|
+
error: unknown,
|
|
33
|
+
errorKind: TelemetryDiagnosticErrorKind,
|
|
34
|
+
): void {
|
|
35
|
+
writeTelemetryDiagnostic({
|
|
36
|
+
event,
|
|
37
|
+
source: "plugin",
|
|
38
|
+
error,
|
|
39
|
+
errorKind,
|
|
40
|
+
});
|
|
41
|
+
}
|
|
42
|
+
|
|
25
43
|
export async function runSessionStartHook(
|
|
26
44
|
_input: CodexSessionStartInput,
|
|
27
45
|
options: CodexTelemetryHookOptions = {},
|
|
@@ -29,10 +47,18 @@ export async function runSessionStartHook(
|
|
|
29
47
|
const createClient = options.createClient ?? createPluginPostHog;
|
|
30
48
|
const getDistinctId = options.getDistinctId ?? getPostHogDistinctId;
|
|
31
49
|
|
|
32
|
-
|
|
50
|
+
let client: PostHogClient;
|
|
51
|
+
try {
|
|
52
|
+
client = await createClient();
|
|
53
|
+
} catch (error) {
|
|
54
|
+
writeHookDiagnostic("telemetry_posthog_init_failed", error, error instanceof Error ? "error" : "non_error");
|
|
55
|
+
return "";
|
|
56
|
+
}
|
|
57
|
+
|
|
33
58
|
try {
|
|
34
59
|
client.trackActive(getDistinctId(), SESSION_START_REASON);
|
|
35
|
-
} catch {
|
|
60
|
+
} catch (error) {
|
|
61
|
+
writeHookDiagnostic("telemetry_capture_failed", error, error instanceof Error ? "error" : "non_error");
|
|
36
62
|
await safeShutdown(client);
|
|
37
63
|
return "";
|
|
38
64
|
}
|
|
@@ -43,7 +69,8 @@ export async function runSessionStartHook(
|
|
|
43
69
|
async function safeShutdown(client: PostHogClient): Promise<void> {
|
|
44
70
|
try {
|
|
45
71
|
await client.shutdown();
|
|
46
|
-
} catch {
|
|
72
|
+
} catch (error) {
|
|
73
|
+
writeHookDiagnostic("telemetry_shutdown_failed", error, error instanceof Error ? "error" : "non_error");
|
|
47
74
|
return;
|
|
48
75
|
}
|
|
49
76
|
}
|
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
import { appendFileSync, existsSync, mkdirSync, readFileSync } from "node:fs"
|
|
2
|
+
import { join } from "node:path"
|
|
3
|
+
|
|
4
|
+
import { writeFileAtomically } from "./atomic-write.js"
|
|
5
|
+
import { getActivityStateDir } from "./data-path.js"
|
|
6
|
+
|
|
7
|
+
export type TelemetryDiagnosticEvent =
|
|
8
|
+
| "telemetry_activity_state_read_failed"
|
|
9
|
+
| "telemetry_activity_state_write_failed"
|
|
10
|
+
| "telemetry_capture_failed"
|
|
11
|
+
| "telemetry_cpu_info_unavailable"
|
|
12
|
+
| "telemetry_posthog_import_failed"
|
|
13
|
+
| "telemetry_posthog_init_failed"
|
|
14
|
+
| "telemetry_shutdown_failed"
|
|
15
|
+
|
|
16
|
+
export type TelemetryDiagnosticSource = "cli" | "install" | "plugin" | "shared"
|
|
17
|
+
|
|
18
|
+
export type TelemetryDiagnosticErrorKind = "error" | "non_error"
|
|
19
|
+
|
|
20
|
+
export type TelemetryDiagnosticInput = {
|
|
21
|
+
readonly event: TelemetryDiagnosticEvent
|
|
22
|
+
readonly source: TelemetryDiagnosticSource
|
|
23
|
+
readonly error?: unknown
|
|
24
|
+
readonly errorKind?: TelemetryDiagnosticErrorKind
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
const DIAGNOSTICS_FILE_NAME = "telemetry-diagnostics.jsonl"
|
|
28
|
+
const DIAGNOSTICS_RETENTION_MS = 7 * 24 * 60 * 60 * 1000
|
|
29
|
+
const DIAGNOSTICS_MAX_BYTES = 256 * 1024
|
|
30
|
+
|
|
31
|
+
export function getTelemetryDiagnosticsFilePath(): string {
|
|
32
|
+
return join(getActivityStateDir(), DIAGNOSTICS_FILE_NAME)
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
export function writeTelemetryDiagnostic(input: TelemetryDiagnosticInput, now: Date = new Date()): void {
|
|
36
|
+
try {
|
|
37
|
+
cleanupTelemetryDiagnostics(now)
|
|
38
|
+
mkdirSync(getActivityStateDir(), { recursive: true })
|
|
39
|
+
appendFileSync(getTelemetryDiagnosticsFilePath(), `${JSON.stringify(toDiagnosticRecord(input, now))}\n`, "utf-8")
|
|
40
|
+
} catch {
|
|
41
|
+
return
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
export function cleanupTelemetryDiagnostics(now: Date = new Date()): void {
|
|
46
|
+
const diagnosticsFilePath = getTelemetryDiagnosticsFilePath()
|
|
47
|
+
if (!existsSync(diagnosticsFilePath)) {
|
|
48
|
+
return
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
try {
|
|
52
|
+
const cutoffMs = now.getTime() - DIAGNOSTICS_RETENTION_MS
|
|
53
|
+
const retainedLines = trimToMaxBytes(
|
|
54
|
+
readFileSync(diagnosticsFilePath, "utf-8")
|
|
55
|
+
.split("\n")
|
|
56
|
+
.filter((line) => shouldRetainLine(line, cutoffMs)),
|
|
57
|
+
)
|
|
58
|
+
writeFileAtomically(diagnosticsFilePath, retainedLines.length === 0 ? "" : `${retainedLines.join("\n")}\n`)
|
|
59
|
+
} catch {
|
|
60
|
+
return
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
function toDiagnosticRecord(
|
|
65
|
+
input: TelemetryDiagnosticInput,
|
|
66
|
+
now: Date,
|
|
67
|
+
): Record<string, string> {
|
|
68
|
+
return {
|
|
69
|
+
timestamp: now.toISOString(),
|
|
70
|
+
event: input.event,
|
|
71
|
+
source: input.source,
|
|
72
|
+
...serializeError(input.error, input.errorKind),
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
function serializeError(
|
|
77
|
+
error: unknown,
|
|
78
|
+
errorKind?: TelemetryDiagnosticErrorKind,
|
|
79
|
+
): Record<string, string> {
|
|
80
|
+
if (error instanceof Error) {
|
|
81
|
+
return {
|
|
82
|
+
error_kind: errorKind ?? "error",
|
|
83
|
+
error_name: error.name,
|
|
84
|
+
error_message: error.message,
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
if (error === undefined) {
|
|
89
|
+
return {}
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
return {
|
|
93
|
+
error_kind: errorKind ?? "non_error",
|
|
94
|
+
error_name: typeof error,
|
|
95
|
+
error_message: String(error),
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
function shouldRetainLine(line: string, cutoffMs: number): boolean {
|
|
100
|
+
if (line.length === 0) {
|
|
101
|
+
return false
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
const parsed = parseDiagnosticLine(line)
|
|
105
|
+
if (parsed === null) {
|
|
106
|
+
return false
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
const timestamp = parsed["timestamp"]
|
|
110
|
+
if (typeof timestamp !== "string") {
|
|
111
|
+
return false
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
const timestampMs = Date.parse(timestamp)
|
|
115
|
+
return Number.isFinite(timestampMs) && timestampMs >= cutoffMs
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
function parseDiagnosticLine(line: string): Record<string, unknown> | null {
|
|
119
|
+
try {
|
|
120
|
+
const parsed: unknown = JSON.parse(line)
|
|
121
|
+
if (!isRecord(parsed)) {
|
|
122
|
+
return null
|
|
123
|
+
}
|
|
124
|
+
return parsed
|
|
125
|
+
} catch {
|
|
126
|
+
return null
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
function isRecord(value: unknown): value is Record<string, unknown> {
|
|
131
|
+
return value !== null && typeof value === "object" && !Array.isArray(value)
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
function trimToMaxBytes(lines: ReadonlyArray<string>): ReadonlyArray<string> {
|
|
135
|
+
const retained: string[] = []
|
|
136
|
+
let totalBytes = 0
|
|
137
|
+
|
|
138
|
+
for (let index = lines.length - 1; index >= 0; index -= 1) {
|
|
139
|
+
const line = lines[index]
|
|
140
|
+
if (line === undefined) {
|
|
141
|
+
continue
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
const lineBytes = Buffer.byteLength(`${line}\n`, "utf-8")
|
|
145
|
+
if (totalBytes + lineBytes > DIAGNOSTICS_MAX_BYTES) {
|
|
146
|
+
break
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
retained.unshift(line)
|
|
150
|
+
totalBytes += lineBytes
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
return retained
|
|
154
|
+
}
|
|
@@ -3,6 +3,7 @@ import { join } from "node:path"
|
|
|
3
3
|
|
|
4
4
|
import { writeFileAtomically } from "./atomic-write.js"
|
|
5
5
|
import { getActivityStateDir } from "./data-path.js"
|
|
6
|
+
import { type TelemetryDiagnosticErrorKind, type TelemetryDiagnosticEvent, writeTelemetryDiagnostic } from "./diagnostics.js"
|
|
6
7
|
|
|
7
8
|
export type PostHogActivityState = {
|
|
8
9
|
readonly lastActiveDayUTC?: string
|
|
@@ -27,6 +28,19 @@ function isPostHogActivityState(value: unknown): value is PostHogActivityState {
|
|
|
27
28
|
return value !== null && typeof value === "object" && !Array.isArray(value)
|
|
28
29
|
}
|
|
29
30
|
|
|
31
|
+
function writeActivityStateDiagnostic(
|
|
32
|
+
event: TelemetryDiagnosticEvent,
|
|
33
|
+
error: unknown,
|
|
34
|
+
errorKind: TelemetryDiagnosticErrorKind,
|
|
35
|
+
): void {
|
|
36
|
+
writeTelemetryDiagnostic({
|
|
37
|
+
event,
|
|
38
|
+
source: "shared",
|
|
39
|
+
error,
|
|
40
|
+
errorKind,
|
|
41
|
+
})
|
|
42
|
+
}
|
|
43
|
+
|
|
30
44
|
function readPostHogActivityState(): PostHogActivityState {
|
|
31
45
|
const stateFilePath = getPostHogActivityStateFilePath()
|
|
32
46
|
|
|
@@ -43,7 +57,8 @@ function readPostHogActivityState(): PostHogActivityState {
|
|
|
43
57
|
}
|
|
44
58
|
|
|
45
59
|
return stateJson
|
|
46
|
-
} catch {
|
|
60
|
+
} catch (error) {
|
|
61
|
+
writeActivityStateDiagnostic("telemetry_activity_state_read_failed", error, error instanceof Error ? "error" : "non_error")
|
|
47
62
|
return {}
|
|
48
63
|
}
|
|
49
64
|
}
|
|
@@ -55,7 +70,8 @@ function writePostHogActivityState(nextState: PostHogActivityState): void {
|
|
|
55
70
|
try {
|
|
56
71
|
mkdirSync(stateDir, { recursive: true })
|
|
57
72
|
writeFileAtomically(stateFilePath, `${JSON.stringify(nextState, null, 2)}\n`)
|
|
58
|
-
} catch {
|
|
73
|
+
} catch (error) {
|
|
74
|
+
writeActivityStateDiagnostic("telemetry_activity_state_write_failed", error, error instanceof Error ? "error" : "non_error")
|
|
59
75
|
return
|
|
60
76
|
}
|
|
61
77
|
}
|
|
@@ -3,6 +3,12 @@ import os from "node:os";
|
|
|
3
3
|
|
|
4
4
|
import type { PostHog } from "posthog-node";
|
|
5
5
|
|
|
6
|
+
import {
|
|
7
|
+
type TelemetryDiagnosticErrorKind,
|
|
8
|
+
type TelemetryDiagnosticEvent,
|
|
9
|
+
type TelemetryDiagnosticSource,
|
|
10
|
+
writeTelemetryDiagnostic,
|
|
11
|
+
} from "./diagnostics.js";
|
|
6
12
|
import { getPostHogApiKey, getPostHogHost, hasPostHogApiKey, shouldDisablePostHog } from "./env-flags.js";
|
|
7
13
|
import { getPostHogActivityCaptureState } from "./posthog-activity-state.js";
|
|
8
14
|
import {
|
|
@@ -44,6 +50,15 @@ function resolveActivityStateProvider(): ActivityStateProvider {
|
|
|
44
50
|
return activityStateProviderOverride ?? getPostHogActivityCaptureState;
|
|
45
51
|
}
|
|
46
52
|
|
|
53
|
+
function writePostHogDiagnostic(
|
|
54
|
+
event: TelemetryDiagnosticEvent,
|
|
55
|
+
source: TelemetryDiagnosticSource,
|
|
56
|
+
error: unknown,
|
|
57
|
+
errorKind: TelemetryDiagnosticErrorKind,
|
|
58
|
+
): void {
|
|
59
|
+
writeTelemetryDiagnostic({ event, source, error, errorKind });
|
|
60
|
+
}
|
|
61
|
+
|
|
47
62
|
function getSafeCpuInfo(): { readonly count: number; readonly model: string | undefined } {
|
|
48
63
|
try {
|
|
49
64
|
const cpuInfo = resolveOsProvider().cpus();
|
|
@@ -51,7 +66,13 @@ function getSafeCpuInfo(): { readonly count: number; readonly model: string | un
|
|
|
51
66
|
count: cpuInfo.length,
|
|
52
67
|
model: cpuInfo[0]?.model,
|
|
53
68
|
};
|
|
54
|
-
} catch {
|
|
69
|
+
} catch (error) {
|
|
70
|
+
writePostHogDiagnostic(
|
|
71
|
+
"telemetry_cpu_info_unavailable",
|
|
72
|
+
"plugin",
|
|
73
|
+
error,
|
|
74
|
+
error instanceof Error ? "error" : "non_error",
|
|
75
|
+
);
|
|
55
76
|
return {
|
|
56
77
|
count: 0,
|
|
57
78
|
model: undefined,
|
|
@@ -96,8 +117,13 @@ export async function createPluginPostHog(): Promise<PostHogClient> {
|
|
|
96
117
|
const module = await import("posthog-node");
|
|
97
118
|
PostHogClientConstructor = module.PostHog;
|
|
98
119
|
} catch (error) {
|
|
99
|
-
|
|
100
|
-
|
|
120
|
+
writePostHogDiagnostic(
|
|
121
|
+
"telemetry_posthog_import_failed",
|
|
122
|
+
"plugin",
|
|
123
|
+
error,
|
|
124
|
+
error instanceof Error ? "error" : "non_error",
|
|
125
|
+
);
|
|
126
|
+
return NO_OP_POSTHOG;
|
|
101
127
|
}
|
|
102
128
|
|
|
103
129
|
let client: PostHog;
|
|
@@ -112,7 +138,13 @@ export async function createPluginPostHog(): Promise<PostHogClient> {
|
|
|
112
138
|
host: getPostHogHost(),
|
|
113
139
|
disableGeoip: false,
|
|
114
140
|
});
|
|
115
|
-
} catch {
|
|
141
|
+
} catch (error) {
|
|
142
|
+
writePostHogDiagnostic(
|
|
143
|
+
"telemetry_posthog_init_failed",
|
|
144
|
+
"plugin",
|
|
145
|
+
error,
|
|
146
|
+
error instanceof Error ? "error" : "non_error",
|
|
147
|
+
);
|
|
116
148
|
return NO_OP_POSTHOG;
|
|
117
149
|
}
|
|
118
150
|
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
import { mkdtempSync, readFileSync, rmSync } from "node:fs";
|
|
2
|
+
import { tmpdir } from "node:os";
|
|
3
|
+
import path from "node:path";
|
|
4
|
+
import { afterEach, describe, expect, it } from "vitest";
|
|
5
|
+
|
|
6
|
+
import { type CodexSessionStartInput, runSessionStartHook } from "../src/codex-hook.js";
|
|
7
|
+
import { getTelemetryDiagnosticsFilePath } from "../src/diagnostics.js";
|
|
8
|
+
import type { PostHogClient } from "../src/posthog.js";
|
|
9
|
+
|
|
10
|
+
const tempDirectories: string[] = [];
|
|
11
|
+
const originalXdgDataHome = process.env["XDG_DATA_HOME"];
|
|
12
|
+
|
|
13
|
+
afterEach(() => {
|
|
14
|
+
if (originalXdgDataHome === undefined) {
|
|
15
|
+
delete process.env["XDG_DATA_HOME"];
|
|
16
|
+
} else {
|
|
17
|
+
process.env["XDG_DATA_HOME"] = originalXdgDataHome;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
for (const directory of tempDirectories.splice(0)) {
|
|
21
|
+
rmSync(directory, { recursive: true, force: true });
|
|
22
|
+
}
|
|
23
|
+
});
|
|
24
|
+
|
|
25
|
+
function makeSessionStartInput(overrides: Partial<CodexSessionStartInput> = {}): CodexSessionStartInput {
|
|
26
|
+
return {
|
|
27
|
+
session_id: "session-123",
|
|
28
|
+
transcript_path: null,
|
|
29
|
+
cwd: "/tmp/project",
|
|
30
|
+
hook_event_name: "SessionStart",
|
|
31
|
+
model: "gpt-5.5",
|
|
32
|
+
permission_mode: "default",
|
|
33
|
+
source: "startup",
|
|
34
|
+
...overrides,
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
function createDiagnosticsDataDir(): string {
|
|
39
|
+
const dataDir = mkdtempSync(path.join(tmpdir(), "codex-telemetry-diagnostics-"));
|
|
40
|
+
tempDirectories.push(dataDir);
|
|
41
|
+
process.env["XDG_DATA_HOME"] = dataDir;
|
|
42
|
+
return dataDir;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
describe("runSessionStartHook diagnostics", () => {
|
|
46
|
+
describe("#given a client whose trackActive throws", () => {
|
|
47
|
+
it("#when invoked #then swallows the error, writes diagnostics, still shuts down, and returns empty string", async () => {
|
|
48
|
+
let shutdownCalls = 0;
|
|
49
|
+
createDiagnosticsDataDir();
|
|
50
|
+
const throwingClient: PostHogClient = {
|
|
51
|
+
trackActive: () => {
|
|
52
|
+
throw new Error("trackActive failed");
|
|
53
|
+
},
|
|
54
|
+
shutdown: async () => {
|
|
55
|
+
shutdownCalls += 1;
|
|
56
|
+
},
|
|
57
|
+
};
|
|
58
|
+
|
|
59
|
+
const output = await runSessionStartHook(makeSessionStartInput(), {
|
|
60
|
+
createClient: () => throwingClient,
|
|
61
|
+
getDistinctId: () => "distinct-id-abc",
|
|
62
|
+
});
|
|
63
|
+
|
|
64
|
+
expect(output).toBe("");
|
|
65
|
+
expect(shutdownCalls).toBe(1);
|
|
66
|
+
const diagnostics = readFileSync(getTelemetryDiagnosticsFilePath(), "utf-8");
|
|
67
|
+
expect(diagnostics).toContain('"event":"telemetry_capture_failed"');
|
|
68
|
+
expect(diagnostics).toContain('"error_message":"trackActive failed"');
|
|
69
|
+
});
|
|
70
|
+
|
|
71
|
+
it("#when invoked with a non-Error throw #then writes diagnostics and still returns empty string", async () => {
|
|
72
|
+
let shutdownCalls = 0;
|
|
73
|
+
const failure = Symbol("trackActive failed");
|
|
74
|
+
createDiagnosticsDataDir();
|
|
75
|
+
const throwingClient: PostHogClient = {
|
|
76
|
+
trackActive: () => {
|
|
77
|
+
throw failure;
|
|
78
|
+
},
|
|
79
|
+
shutdown: async () => {
|
|
80
|
+
shutdownCalls += 1;
|
|
81
|
+
},
|
|
82
|
+
};
|
|
83
|
+
|
|
84
|
+
const output = await runSessionStartHook(makeSessionStartInput(), {
|
|
85
|
+
createClient: () => throwingClient,
|
|
86
|
+
getDistinctId: () => "distinct-id-abc",
|
|
87
|
+
});
|
|
88
|
+
|
|
89
|
+
expect(output).toBe("");
|
|
90
|
+
expect(shutdownCalls).toBe(1);
|
|
91
|
+
const diagnostics = readFileSync(getTelemetryDiagnosticsFilePath(), "utf-8");
|
|
92
|
+
expect(diagnostics).toContain('"event":"telemetry_capture_failed"');
|
|
93
|
+
expect(diagnostics).toContain('"error_name":"symbol"');
|
|
94
|
+
expect(diagnostics).toContain('"error_message":"Symbol(trackActive failed)"');
|
|
95
|
+
});
|
|
96
|
+
});
|
|
97
|
+
|
|
98
|
+
describe("#given a client whose shutdown rejects", () => {
|
|
99
|
+
it("#when invoked #then swallows the rejection and returns empty string", async () => {
|
|
100
|
+
const rejectingClient: PostHogClient = {
|
|
101
|
+
trackActive: () => undefined,
|
|
102
|
+
shutdown: async () => {
|
|
103
|
+
throw new Error("shutdown failed");
|
|
104
|
+
},
|
|
105
|
+
};
|
|
106
|
+
|
|
107
|
+
const output = await runSessionStartHook(makeSessionStartInput(), {
|
|
108
|
+
createClient: () => rejectingClient,
|
|
109
|
+
getDistinctId: () => "distinct-id-abc",
|
|
110
|
+
});
|
|
111
|
+
|
|
112
|
+
expect(output).toBe("");
|
|
113
|
+
});
|
|
114
|
+
});
|
|
115
|
+
});
|