Commit Graph

829 Commits

Author SHA1 Message Date
YeonGyu-Kim aded57ff1f fix(shared): harden ripgrep-cli, zip-extractor, binary-downloader subprocess paths
Same Web-Response-on-Node hazard existed in ripgrep auto-download flow,
zip extraction helpers, and binary downloader streams. Switch to the new
Node-safe reader and ensure no spawn path escapes as unhandledRejection.

Related to #3919.

Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-05-22 20:40:24 +09:00
YeonGyu-Kim 4ea7562f50 feat(shared): add Node-safe process stream reader and search output collector
Introduces:
- src/shared/process-stream-reader.ts: Buffer-concat stream reader compatible with both Bun and Node ChildProcess stdout (replaces Web Response API usage)
- src/tools/shared/search-process-output.ts: structured subprocess output collector with timeout, kill, and rejection cleanup
- bun-spawn-shim hardened: Node path forces windowsHide: true; spawn errors no longer escape as unhandledRejection

Foundation for #3919 fix.

Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-05-22 20:39:52 +09:00
YeonGyu-Kim 2e2e33cfc0 test: fix stale imports after prompt-async-gate and model-core refactors
- prompt-async-gate.test.ts: refactor ced36bffc removed
  promptAsyncAfterSessionIdle in favor of the unified
  dispatchInternalPrompt({ mode: 'async', ... }). One call site at
  line 1441 was left behind. Replace it with the current API and pass
  the explicit dispatchTimeoutMs so the status-timeout semantics are
  preserved. Also switch the surrounding tests to the third-argument
  timeout form so Bun's typings stay happy.
- runtime-model-readers.test.ts: implementation moved to
  packages/model-core during the layering refactor; the orphaned test
  still pointed at './runtime-model-readers'. Switch to the package
  export via getModelCapabilities and keep the modality-reader
  coverage by deriving keys through the package API.
2026-05-22 00:07:46 +09:00
YeonGyu-Kim 9624914c25 test(disabled-providers): drop logger mock to fix global mock-module leakage
mock.restore() in afterAll is global in Bun, so the previous attempt to
satisfy mock-module-lifecycle-audit by pairing mock.module('./logger')
with afterAll(() => mock.restore()) tore down mocks owned by other
tests. Concretely, running this file before src/hooks/runtime-fallback
produced 42 cascading fallback test failures.

The logger mock was decorative - tests do not assert log calls, and the
real logger only writes to oh-my-opencode.log in the OS temp dir. Drop
the mock entirely so the audit has nothing to score and other tests
keep their mocks intact.
2026-05-22 00:07:46 +09:00
YeonGyu-Kim bc0da0fad3 test: fix prometheus-prompt syntax + sync display name casing to lowercase
- prometheus-prompt.test.ts: close missing }) on the OpenSpec expanded
  commands describe block (introduced by d66b6bcbf, parse error).
- agent-sort-shim/agent-config-integration/continuation-injection/
  unstable-agent-babysitter/subagent-resolver/sync-executor/
  resolve-caller-team-lead tests: expect 'Sisyphus - ultraworker'
  (lowercase) to match production after cd39f8858, which lowercased the
  display name to dodge a TUI ZWSP rendering glitch. Legacy uppercase
  inputs that exercise the normalization path are preserved.
- sync-executor.ts + resolve-caller-team-lead.ts: route legacy display
  name inputs through normalizeAgentForPrompt so prompt agent names and
  caller team lead lookups produce the canonical lowercase form.
2026-05-22 00:07:46 +09:00
YeonGyu-Kim edaa95fec0 refactor(model-core): host snapshot fetcher, suggestion parser, and context-limit resolver
Move three pure helpers from src/shared/ into @oh-my-opencode/model-core so the package can stand alone without depending on plugin internals:

- buildModelCapabilitiesSnapshotFromModelsDev + fetchModelCapabilitiesSnapshot (models.dev normalization)
- parseModelSuggestion (cross-provider ProviderModelNotFoundError suggestion extraction)
- resolveActualContextLimit (Anthropic GA 1M context override)

Split provider-model-id-transform into two variants exposed by model-core:

- transformModelForProvider keeps the runtime dash to dot Anthropic rewrite used by the SDK
- transformModelForProviderDisplay preserves hyphenated Anthropic IDs so the installer writes registry-compatible model strings, fixing the ProviderModelNotFoundError fresh installs hit when the dotted form leaks into the config

src/shared/* and src/cli/provider-model-id-transform.ts collapse to re-export shims that point at the new core modules. Stale src/shared/{known-variants,model-capability-aliases,model-capability-guardrails,model-capability-heuristics}.ts re-export files plus the duplicated context-limit-resolver test are removed in favor of the canonical model-core copies.

Tests: bun test packages/model-core src/shared/model-capabilities-cache.test.ts src/cli/provider-model-id-transform.test.ts
2026-05-21 16:19:38 +09:00
YeonGyu-Kim d78ebc1280 Merge pull request #3370 from Zireael/fix/git-bash-shell-detection-on-windows
fix: detect Git Bash/WSL/MSYS2 shell on Windows (non-interactive-env hook)
2026-05-21 12:58:48 +09:00
YeonGyu-Kim 6678c2ae04 Merge pull request #3884 from leeyazhou/i18n
feat(i18n): add toast i18n with en/zh locale and plugin config support
2026-05-21 12:58:45 +09:00
YeonGyu-Kim c5f8fd4060 Merge pull request #4031 from PeterPonyu/feat/config-disabled-providers
feat(config): add disabled_providers schema + helper
2026-05-21 12:58:42 +09:00
YeonGyu-Kim 9cca6848c9 Merge pull request #4081 from PeterPonyu/feat/4004-agent-display-name-i18n
feat(agents): support per-agent displayName for i18n (#4004)
2026-05-21 12:58:21 +09:00
YeonGyu-Kim ba5bc0ef4f Merge pull request #4092 from code-yeongyu/fix/status-timeout-hang
fix(shared): add timeout to isSessionActive to prevent infinite hang
2026-05-21 12:58:14 +09:00
YeonGyu-Kim bd61479315 Merge pull request #4227 from code-yeongyu/fix/post-4106-cleanup-20260521
fix: clean up post-4106 prompt gate artifacts
2026-05-21 12:53:17 +09:00
YeonGyu-Kim f6a2ff3541 test(coupling-audit): allowlist dual-runtime spawn shims 2026-05-21 12:50:10 +09:00
YeonGyu-Kim e15461febc refactor(model-core): inject bundled capabilities snapshot from harness
- remove bundled snapshot dependency on src/generated in model-core

- make shared harness provide runtime bundled snapshot

- update guardrail and capability tests to pass explicit snapshot

Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-05-21 12:50:10 +09:00
YeonGyu-Kim 2462d7af29 refactor(model-core): remove src back-imports via core utilities and adapter
- move fuzzyMatchModel and transformModelForProvider into model-core

- replace connected-providers re-export with adapter contract

- route shared wrappers through model-core exports

Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-05-21 12:50:10 +09:00
YeonGyu-Kim 819bf0d11f chore: update meta-audits + add opencode coupling grep gate 2026-05-21 12:50:10 +09:00
YeonGyu-Kim 2748009ff2 refactor(packages): extract model-core package 2026-05-21 12:49:50 +09:00
YeonGyu-Kim a5c1d71001 refactor(packages): extract utils package 2026-05-21 12:48:43 +09:00
YeonGyu-Kim ced36bffc1 refactor: split prompt async gate modules
Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-05-21 12:00:01 +09:00
YeonGyu-Kim db4c9f49e3 Merge pull request #3316 from ahuangsnail/fix/max-output-tokens-zero-fallback
fix: treat zero limit.output as unknown to enable fallback to bundled…
2026-05-21 00:59:05 +09:00
YeonGyu-Kim d0719ff7b7 Merge pull request #3875 from jollyxenon/fix/3846-opencode-config-dir-additive
fix(config): align OPENCODE_CONFIG_DIR with additive OpenCode semantics
2026-05-21 00:48:00 +09:00
YeonGyu-Kim b18963b0a9 Merge pull request #3868 from MoerAI/fix/openai-server-error-retryable
fix(model-error-classifier): mark OpenAI server_error patterns as retryable (fixes #3799)
2026-05-21 00:46:16 +09:00
YeonGyu-Kim 7651c856aa Merge pull request #3944 from survivor998/fix/ultraworker-display-name-zwsp
fix(display): lowercase ultraworker to avoid ZWSP rendering glitch
2026-05-21 00:45:07 +09:00
YeonGyu-Kim aa3187bfbb Merge pull request #4180 from JacobZyy/fix/plugin-hooks-merge 2026-05-21 00:14:58 +09:00
YeonGyu-Kim 12ed091e93 Merge pull request #4101 from sjawhar/fix/modalities-object-shape
fix(model-capabilities): handle object-shaped modalities in readModalityKeys
2026-05-21 00:10:29 +09:00
JacobZyy 33f121b113 fix: add PATH to restricted hook env, protect HOME/CLAUDE_PROJECT_DIR from allowlist override, reset plugin hooks state in tests
- P1: When allowedEnvVars is provided, PATH was missing from the base
  restricted env, causing non-builtin commands to fail at exec time
- P2: Allowlisted HOME/CLAUDE_PROJECT_DIR could overwrite normalized
  values from getHomeDirectory()/cwd with ambient process.env values
- P2: Test suite mutated shared pluginHooksState singleton without
  resetting it in afterEach, causing cross-test state leaks
2026-05-20 22:49:05 +08:00
YeonGyu-Kim 791825fc20 Merge pull request #4153 from MoerAI/fix/fallback-model-string-guard
fix(shared,delegate-task,claude-code-agent-loader): guard model parsers against non-string input (fixes #4145)
2026-05-20 23:40:33 +09:00
JacobZyy 0a20844bd4 fix: address PR #4180 review - security, typing, and test coverage
- Apply mcp_env_allowlist to plugin hooks: intersect HTTP allowedEnvVars
  with MCP allowlist, set command allowedEnvVars to full MCP allowlist
- Scrub process.env in executeHookCommand when allowedEnvVars provided
- Add PluginHooksState class with per-directory Map storage
- Add PluginHooksConfig interface for typed boundary layer
- Pass directory context through hook-config-handler
- Add 16 tests across 4 files (40 assertions) covering allowlist
  filtering, env scrubbing, directory isolation, and edge cases
- Remove unnecessary 'as' type assertions, use discriminated union
  narrowing instead
2026-05-20 22:30:25 +08:00
YeonGyu-Kim 32f0e1e0af Merge pull request #4186 from lang-911/feat/grok-reasoning-effort
fix(model-heuristics): register Grok family so reasoningEffort survives on @ai-sdk/openai
2026-05-20 22:05:22 +09:00
MoerAI c85d2f9bc8 fix(model-error-classifier): mark OpenAI server_error patterns as retryable (fixes #3799)
OpenAI streaming responses can surface mid-stream errors with type
'server_error' or with the prose message 'An error occurred while processing
your request'. Neither matched any entry in RETRYABLE_MESSAGE_PATTERNS, so
shouldRetryError returned false and the runtime-fallback / fallback-retry
code paths skipped retry. The result was that GPT-5.5 subagent (and main)
turns silently stalled until the stale timeout fired.

The maintainer's diagnosis on issue #3799 explicitly recommends adding
these two patterns to model-error-classifier.ts; this commit does exactly
that and adds two regression tests covering the JSON envelope and the
prose form.
2026-05-20 19:11:54 +09:00
YeonGyu-Kim 330e437f08 docs(agents): regenerate hierarchical AGENTS.md for 2026-05-20
Sync the AGENTS.md hierarchy to current code state:

Drift fixes in 11 existing files
- Root: 2026-05-20 commit 39aadbf9f, ~2167 TS files, 120 barrel index.ts,
  57 src/hooks dirs, 297 (179 non-test) src/shared files, 11 OpenCode hook
  handlers in plugin-interface.ts, packages list adds ast-grep-mcp + rules-core,
  first-prompt-watchdog 206 LOC, parent-wake-notifier 587 LOC
- src/AGENTS.md: file counts, plugin-interface handler count
- src/shared/AGENTS.md: title + counts 278/170 -> 297/179
- src/hooks/AGENTS.md: 57 dirs, note unwired WIP (task-reminder,
  hashline-edit-diff-enhancer)
- src/features/AGENTS.md: module map with NON-TEST counts + sub-AGENTS.md
  column, 7 modules without sub-doc
- src/features/background-agent/AGENTS.md: add 12 newer files (parent-wake-
  notifier 587 LOC, loop-detector, error-classifier, fallback-retry-handler,
  process-cleanup, subagent-spawn-limits, session-status-classifier,
  compaction-aware-message-resolver, etc.)
- src/plugin/AGENTS.md: 11 handlers, add system-transform.ts + command-
  execute-before.ts + build-team-idle-wake-hint-client.ts
- src/config/AGENTS.md: note schema/internal/permission.ts
- src/cli/AGENTS.md: 8 commands including 'version'
- src/plugin-handlers/AGENTS.md, packages/web/AGENTS.md: date bump

New AGENTS.md in 4 directories
- packages/AGENTS.md: index of 15 packages (11 platform binaries + 2 MCP
  packages + rules-core + web), role map, conventions
- docs/AGENTS.md: WHERE TO LOOK table for 19 docs across 6 subdirs
- .opencode/AGENTS.md: 5 skills + 4 slash commands + relationship to .agents/
- .agents/AGENTS.md: superset migration target (9 skills + 4 commands)
2026-05-20 17:18:44 +09:00
YeonGyu-Kim f8f4b572dc fix(runtime-fallback,prompt-gate): recognize all OpenCode progress event shapes and boolean/completed finish markers
Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-05-20 13:12:06 +09:00
YeonGyu-Kim d3e218f912 fix(prompt): treat post-dispatch failures as accepted 2026-05-20 11:42:32 +09:00
Sami Jawhar 94e71936fb fix(model-capabilities): handle object-shaped modalities in readModalityKeys 2026-05-19 12:24:59 +00:00
YeonGyu-Kim b2918fd4db fix(team-mode): close peer message delivery races 2026-05-19 19:18:13 +09:00
YeonGyu-Kim bcea4a9d28 fix(prompt-gate): harden sync and team prompt dispatch 2026-05-19 19:18:13 +09:00
YeonGyu-Kim 1492bffd20 fix(prompt-gate): harden internal prompt dispatch 2026-05-19 19:18:13 +09:00
lang-911 8b097f2c3b fix(model-heuristics): register Grok family with reasoningEffort support
Grok model IDs (e.g. `grok-4.3`, `grok-3-mini`) were missing from `HEURISTIC_MODEL_FAMILY_REGISTRY`, so `resolveCompatibleModelSettings` returned an "unknown family" result for them.

The `chat.params` hook treats unknown families as "no reasoning support" and deletes `output.options.reasoningEffort` before the request leaves the plugin, so users routing Grok via OpenAI-compatible endpoints never saw their reasoning effort forwarded — even with `forceReasoning: true`.

Add a `grok` family entry that includes any model ID containing "grok", exposes `low | medium | high` variants, and sets `reasoningEfforts` so the heuristic surfaces the same capability flag used by the `chat.params` hook. Extend the family table-driven test in `model-settings-compatibility.test.ts` to cover `grok-4.3`.
2026-05-19 02:44:38 -07:00
leeyazhou 9dc9d77904 feat(i18n): add toast i18n with en/zh locale and plugin config support
- Add src/locales/ with en baseline and zh overrides (Partial<Record> fallback)
- Add src/shared/i18n.ts with initI18n/t/setLocale/getLocale (LANG env auto-detect)
- Add I18nConfigSchema with locale field to plugin config
- Internationalize 13 hardcoded strings in task-toast-manager
- Add 18 unit tests for i18n module
- Pin manager tests to en locale for determinism
2026-05-19 14:31:13 +08:00
YeonGyu-Kim bb75751410 fix(babysitter): avoid double prompt gate 2026-05-19 13:48:55 +09:00
YeonGyu-Kim e57bac3b6b fix(prompt-retry): preserve async holds without blocking validation fallbacks 2026-05-19 13:48:33 +09:00
YeonGyu-Kim 98c3fee181 fix(prompt-gate): detect finish-only tool waits 2026-05-19 13:16:39 +09:00
YeonGyu-Kim dfc2e8e4ae fix(prompt-retry): preserve peer prompt reservations 2026-05-19 13:16:39 +09:00
YeonGyu-Kim f5f358ab9d fix(prompt-gate): ignore internal user tails in tool waits 2026-05-19 13:16:39 +09:00
YeonGyu-Kim 90b3f4ac96 test: harden workspace package assumptions
Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-05-18 21:28:12 +09:00
YeonGyu-Kim c9a3c34a29 test: stabilize dependency verification
Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-05-18 20:55:33 +09:00
MoerAI ae0c106ed4 fix(shared,delegate-task,claude-code-agent-loader): guard model parsers against non-string input (fixes #4145)
After the 4.2.0 unified-dispatch refactor (a42f894f / df198d8b / fee515c5 / 989ab717 / dd3fecaf / 1bbe065c / 12bd6580), at least one caller in the new prompt-async-gate path forwards a FallbackModelObject (or some other non-string shape) into parsers that statically claim 'model: string'. The downstream .trim() call then throws 'model.trim is not a function', which rejects the session.processor promise and surfaces as 'Aborted process' + UI 'interrupted'. The issue (#4145) reports this aborts 90% of subagent dispatches across every provider on 4.2.0 + opencode 1.15.4.

This patch adds a 'typeof x !== "string"' runtime guard at the four parser entrypoints called from the dispatch path:

- src/shared/fallback-chain-from-models.ts :: parseVariantFromModel, parseFallbackModelEntry

- src/tools/delegate-task/model-string-parser.ts :: parseVariantFromModelID, parseModelString

- src/shared/model-string-parser.ts (duplicate file with same API) :: parseVariantFromModelID, parseModelString

- src/features/claude-code-agent-loader/claude-model-mapper.ts :: mapClaudeModelString

Each parser now returns undefined / { modelID: "" } for non-string input instead of throwing. This unblocks subagent dispatch and leaves the underlying caller bug for a follow-up.

Regression coverage: three new tests in src/shared/fallback-chain-from-models.test.ts pin the non-string behavior (object, null/undefined, number). Existing 38 tests still pass. Total: 41/41 green, typecheck clean.
2026-05-18 19:22:33 +09:00
YeonGyu-Kim c712b71d9a test(tmux): isolate pane close logic tests 2026-05-18 14:46:10 +09:00
YeonGyu-Kim 66cb72b831 fix(prompt-gate): bind session messages receiver 2026-05-18 14:22:58 +09:00
YeonGyu-Kim b2961409b7 test(shell-env): add csh/tcsh detection and buildEnvPrefix coverage
Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-05-18 14:04:17 +09:00