Merge remote-tracking branch 'origin/dev' into fix/git-bash-shell-detection-on-windows

# Conflicts:
#	src/shared/shell-env.ts
This commit is contained in:
Zireael
2026-04-18 22:59:25 +02:00
452 changed files with 53406 additions and 41739 deletions
@@ -0,0 +1,7 @@
bun test v1.3.12 (700fc117)
1 pass
3 filtered out
0 fail
1 expect() calls
Ran 1 test across 1 file. [64.00ms]
@@ -0,0 +1,7 @@
bun test v1.3.12 (700fc117)
1 pass
3 filtered out
0 fail
1 expect() calls
Ran 1 test across 1 file. [65.00ms]
@@ -0,0 +1,7 @@
bun test v1.3.12 (700fc117)
1 pass
3 filtered out
0 fail
3 expect() calls
Ran 1 test across 1 file. [69.00ms]
@@ -0,0 +1,7 @@
bun test v1.3.12 (700fc117)
1 pass
3 filtered out
0 fail
12 expect() calls
Ran 1 test across 1 file. [61.00ms]
+10
View File
@@ -0,0 +1,10 @@
## 2026-04-18 Task 2: types module
- `MemberSchema` needs `.strict()` on the base shape so the discriminatedUnion rejects members that mix `category` and `subagent_type`.
- `backendType` and `isActive` defaults are part of the schema contract, so tests should use `toMatchObject` instead of exact object equality.
- The eligibility registry must preserve the plan strings verbatim, especially the hard-reject messages for Momus verification.
## Task 12 learnings
- `git worktree remove` can leave prunable entries behind, so pruning after removal keeps the repo index tidy.
- For testability, a tiny git command runner hook made git-unavailable coverage simpler than mocking Bun directly.
- Detached worktrees need unique temp paths in tests to avoid cross-run collisions.
+4 -4
View File
@@ -1,17 +1,17 @@
# oh-my-opencode — OpenCode Plugin # oh-my-opencode — OpenCode Plugin
**Generated:** 2026-04-11 | **Commit:** f5dc1c0e | **Branch:** dev **Generated:** 2026-04-18 | **Commit:** 2892ca4a | **Branch:** dev
## OVERVIEW ## OVERVIEW
OpenCode plugin (npm: `oh-my-opencode`) extending Claude Code with multi-agent orchestration, 52 lifecycle hooks, 26 tools, skill/command/MCP systems, Hashline edit tool, IntentGate classifier, and Claude Code compatibility. ~1600 TypeScript source files. Dual-published as `oh-my-opencode` + `oh-my-openagent` during transition. OpenCode plugin (npm: `oh-my-opencode`, dual-published as `oh-my-openagent` during transition) extending Claude Code with 11 agents, 52 lifecycle hooks, 26 tools, 3-tier MCP system (built-in + .mcp.json + skill-embedded), Hashline LINE#ID edit tool, IntentGate classifier, and Claude Code compatibility. 1766 TypeScript source files, 377k LOC, 104 barrel index.ts files. Entry: `src/index.ts` → 5-step init (loadConfig → createManagers → createTools → createHooks → createPluginInterface).
## STRUCTURE ## STRUCTURE
``` ```
oh-my-opencode/ oh-my-opencode/
├── src/ ├── src/
│ ├── index.ts # Plugin entry: loadConfig → createManagers → createTools → createHooks → createPluginInterface │ ├── index.ts # Plugin entry: default export `pluginModule`, shape `{ id, server }`
│ ├── plugin-config.ts # JSONC multi-level config: user → project → defaults (Zod v4) │ ├── plugin-config.ts # JSONC multi-level config: user → project → defaults (Zod v4)
│ ├── agents/ # 11 agents (Sisyphus, Hephaestus, Oracle, Librarian, Explore, Atlas, Prometheus, Metis, Momus, Multimodal-Looker, Sisyphus-Junior) │ ├── agents/ # 11 agents (Sisyphus, Hephaestus, Oracle, Librarian, Explore, Atlas, Prometheus, Metis, Momus, Multimodal-Looker, Sisyphus-Junior)
│ ├── hooks/ # 52 lifecycle hooks across dedicated modules and standalone files │ ├── hooks/ # 52 lifecycle hooks across dedicated modules and standalone files
@@ -33,7 +33,7 @@ oh-my-opencode/
## INITIALIZATION FLOW ## INITIALIZATION FLOW
``` ```
OhMyOpenCodePlugin(ctx) pluginModule.server(input, options)
├─→ loadPluginConfig() # JSONC parse → project/user merge → Zod validate → migrate ├─→ loadPluginConfig() # JSONC parse → project/user merge → Zod validate → migrate
├─→ createManagers() # TmuxSessionManager, BackgroundManager, SkillMcpManager, ConfigHandler ├─→ createManagers() # TmuxSessionManager, BackgroundManager, SkillMcpManager, ConfigHandler
├─→ createTools() # SkillContext + AvailableCategories + ToolRegistry (26 tools) ├─→ createTools() # SkillContext + AvailableCategories + ToolRegistry (26 tools)
+6 -7
View File
@@ -56,8 +56,7 @@ If English isn't your first language, don't worry! We value your contributions r
### Prerequisites ### Prerequisites
- **Bun** (latest version) - The only supported package manager - **Bun** (latest version) - The only supported package manager
- **TypeScript 5.7.3+** - For type checking and declarations - **TypeScript** - Strict mode for type checking and declarations
- **OpenCode 1.0.150+** - For testing the plugin
### Development Setup ### Development Setup
@@ -110,17 +109,17 @@ After making changes, you can test your local build in OpenCode:
``` ```
oh-my-opencode/ oh-my-opencode/
├── src/ ├── src/
│ ├── index.ts # Plugin entry (OhMyOpenCodePlugin) │ ├── index.ts # Plugin entry (V1 PluginModule, default export)
│ ├── plugin-config.ts # JSONC multi-level config (Zod v4) │ ├── plugin-config.ts # JSONC multi-level config (Zod v4)
│ ├── agents/ # 11 agents (Sisyphus, Hephaestus, Oracle, Librarian, Explore, Atlas, Prometheus, Metis, Momus, Multimodal-Looker, Sisyphus-Junior) │ ├── agents/ # 11 agents (Sisyphus, Hephaestus, Oracle, Librarian, Explore, Atlas, Prometheus, Metis, Momus, Multimodal-Looker, Sisyphus-Junior)
│ ├── hooks/ # Lifecycle hooks for orchestration, recovery, UX, and context management │ ├── hooks/ # 52 lifecycle hooks across 55 dedicated modules
│ ├── tools/ # 26 tools across 15 directories │ ├── tools/ # 26 tools across 16 directories
│ ├── mcp/ # 3 built-in remote MCPs (websearch, context7, grep_app) │ ├── mcp/ # 3 built-in remote MCPs (websearch, context7, grep_app)
│ ├── features/ # 19 feature modules (background-agent, skill-loader, tmux, MCP-OAuth, etc.) │ ├── features/ # 19 feature modules (background-agent, skill-loader, tmux, MCP-OAuth, etc.)
│ ├── config/ # Zod v4 schema system │ ├── config/ # Zod v4 schema system
│ ├── shared/ # Cross-cutting utilities │ ├── shared/ # Cross-cutting utilities
│ ├── cli/ # CLI: install, run, doctor, mcp-oauth (Commander.js) │ ├── cli/ # CLI: install, run, doctor, mcp-oauth (Commander.js)
│ ├── plugin/ # 8 OpenCode hook handlers + hook composition │ ├── plugin/ # 10 OpenCode hook handlers + 52 hook composition
│ └── plugin-handlers/ # 6-phase config loading pipeline │ └── plugin-handlers/ # 6-phase config loading pipeline
├── packages/ # Monorepo: comment-checker, opencode-sdk ├── packages/ # Monorepo: comment-checker, opencode-sdk
└── dist/ # Build output (ESM + .d.ts) └── dist/ # Build output (ESM + .d.ts)
@@ -184,7 +183,7 @@ import type { AgentConfig } from "./types";
export const myAgent: AgentConfig = { export const myAgent: AgentConfig = {
name: "my-agent", name: "my-agent",
model: "anthropic/claude-opus-4-6", model: "anthropic/claude-opus-4-7",
description: "Description of what this agent does", description: "Description of what this agent does",
prompt: `Your agent's system prompt here`, prompt: `Your agent's system prompt here`,
temperature: 0.1, temperature: 0.1,
+6 -2
View File
@@ -115,6 +115,10 @@ https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/do
curl -s https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/docs/guide/installation.md curl -s https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/docs/guide/installation.md
``` ```
**注記**: 公開されているパッケージおよびバイナリ名は `oh-my-opencode` を使用してください。`opencode.json` 内では、互換性レイヤーがプラグインエントリ `oh-my-openagent` を優先しますが、従来の `oh-my-opencode` エントリも警告付きで読み込まれます。プラグイン設定ファイルは依然として `oh-my-opencode.json` または `oh-my-opencode.jsonc` を使用するのが一般的で、移行期間中は従来のファイル名と改名後のファイル名の両方が認識されます。
匿名のテレメトリは、インストールとランタイムの信頼性向上のためにデフォルトで有効になっています。これは PostHog を使用し、生のホスト名ではなくハッシュ化されたインストール識別子を使用します。無効化するには `OMO_SEND_ANONYMOUS_TELEMETRY=0` または `OMO_DISABLE_POSTHOG=1` を設定してください。[プライバシーポリシー](docs/legal/privacy-policy.md)と[利用規約](docs/legal/terms-of-service.md)をご覧ください。
--- ---
## このREADMEをスキップする ## このREADMEをスキップする
@@ -166,11 +170,11 @@ Read this and tell me why it's not just another boilerplate: https://raw.githubu
<td align="center"><img src=".github/assets/hephaestus.png" height="300" /></td> <td align="center"><img src=".github/assets/hephaestus.png" height="300" /></td>
</tr></table> </tr></table>
**Sisyphus** (`claude-opus-4-6` / **`kimi-k2.5`** / **`glm-5`**) はあなたのメインのオーケストレーターです。計画を立て、専門家に委任し、攻撃的な並列実行でタスクを完了まで推進します。途中で投げ出すことはありません。 **Sisyphus** (`claude-opus-4-7` / **`kimi-k2.5`** / **`glm-5`**) はあなたのメインのオーケストレーターです。計画を立て、専門家に委任し、攻撃的な並列実行でタスクを完了まで推進します。途中で投げ出すことはありません。
**Hephaestus** (`gpt-5.4`) はあなたの自律的なディープワーカーです。レシピではなく、目標を与えてください。手取り足取り教えなくても、コードベースを探索し、パターンを研究し、端から端まで実行します。*正当なる職人 (The Legitimate Craftsman).* **Hephaestus** (`gpt-5.4`) はあなたの自律的なディープワーカーです。レシピではなく、目標を与えてください。手取り足取り教えなくても、コードベースを探索し、パターンを研究し、端から端まで実行します。*正当なる職人 (The Legitimate Craftsman).*
**Prometheus** (`claude-opus-4-6` / **`kimi-k2.5`** / **`glm-5`**) はあなたの戦略プランナーです。インタビューモードで動作し、コードに触れる前に質問をしてスコープを特定し、詳細な計画を構築します。 **Prometheus** (`claude-opus-4-7` / **`kimi-k2.5`** / **`glm-5`**) はあなたの戦略プランナーです。インタビューモードで動作し、コードに触れる前に質問をしてスコープを特定し、詳細な計画を構築します。
すべてのエージェントは、それぞれのモデルの強みに合わせてチューニングされています。手動でモデルを切り替える必要はありません。[詳しくはこちら →](docs/guide/overview.md) すべてのエージェントは、それぞれのモデルの強みに合わせてチューニングされています。手動でモデルを切り替える必要はありません。[詳しくはこちら →](docs/guide/overview.md)
+6 -2
View File
@@ -109,6 +109,10 @@ https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/do
curl -s https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/docs/guide/installation.md curl -s https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/docs/guide/installation.md
``` ```
**참고**: 배포된 패키지와 바이너리 이름은 `oh-my-opencode`를 사용하세요. `opencode.json` 내부에서는 호환성 레이어가 이제 플러그인 엔트리 `oh-my-openagent`를 우선시하며, 레거시 `oh-my-opencode` 엔트리는 경고와 함께 여전히 로드됩니다. 플러그인 설정 파일은 여전히 일반적으로 `oh-my-opencode.json` 또는 `oh-my-opencode.jsonc`를 사용하며, 전환 기간 동안 레거시와 변경된 basename 모두 인식됩니다.
익명 텔레메트리는 설치 및 런타임 안정성 개선을 위해 기본적으로 활성화되어 있습니다. PostHog를 사용하며 해시된 설치 식별자를 사용하고 원시 호스트명은 절대 사용하지 않습니다. `OMO_SEND_ANONYMOUS_TELEMETRY=0` 또는 `OMO_DISABLE_POSTHOG=1`로 비활성화할 수 있습니다. [개인정보처리방침](docs/legal/privacy-policy.md)과 [서비스 이용약관](docs/legal/terms-of-service.md)을 참조하세요.
--- ---
## 이 README 건너뛰기 ## 이 README 건너뛰기
@@ -160,11 +164,11 @@ Read this and tell me why it's not just another boilerplate: https://raw.githubu
<td align="center"><img src=".github/assets/hephaestus.png" height="300" /></td> <td align="center"><img src=".github/assets/hephaestus.png" height="300" /></td>
</tr></table> </tr></table>
**Sisyphus** (`claude-opus-4-6` / **`kimi-k2.5`** / **`glm-5`**)는 당신의 메인 오케스트레이터입니다. 공격적인 병렬 실행으로 계획을 세우고, 전문가들에게 위임하며, 완료될 때까지 밀어붙입니다. 중간에 포기하는 법이 없습니다. **Sisyphus** (`claude-opus-4-7` / **`kimi-k2.5`** / **`glm-5`**)는 당신의 메인 오케스트레이터입니다. 공격적인 병렬 실행으로 계획을 세우고, 전문가들에게 위임하며, 완료될 때까지 밀어붙입니다. 중간에 포기하는 법이 없습니다.
**Hephaestus** (`gpt-5.4`)는 당신의 자율 딥 워커입니다. 레시피가 아니라 목표를 주세요. 베이비시터 없이 알아서 코드베이스를 탐색하고, 패턴을 연구하며, 끝에서 끝까지 전부 해냅니다. *진정한 장인(The Legitimate Craftsman).* **Hephaestus** (`gpt-5.4`)는 당신의 자율 딥 워커입니다. 레시피가 아니라 목표를 주세요. 베이비시터 없이 알아서 코드베이스를 탐색하고, 패턴을 연구하며, 끝에서 끝까지 전부 해냅니다. *진정한 장인(The Legitimate Craftsman).*
**Prometheus** (`claude-opus-4-6` / **`kimi-k2.5`** / **`glm-5`**)는 당신의 전략 플래너입니다. 인터뷰 모드로 작동합니다. 코드 한 줄 만지기 전에 질문을 던져 스코프를 파악하고 상세한 계획부터 세웁니다. **Prometheus** (`claude-opus-4-7` / **`kimi-k2.5`** / **`glm-5`**)는 당신의 전략 플래너입니다. 인터뷰 모드로 작동합니다. 코드 한 줄 만지기 전에 질문을 던져 스코프를 파악하고 상세한 계획부터 세웁니다.
모든 에이전트는 해당 모델의 특장점에 맞춰 튜닝되어 있습니다. 수동으로 모델 바꿔가며 뻘짓하지 마세요. [더 알아보기 →](docs/guide/overview.md) 모든 에이전트는 해당 모델의 특장점에 맞춰 튜닝되어 있습니다. 수동으로 모델 바꿔가며 뻘짓하지 마세요. [더 알아보기 →](docs/guide/overview.md)
+2 -2
View File
@@ -166,11 +166,11 @@ Even only with following subscriptions, ultrawork will work well (this project i
<td align="center"><img src=".github/assets/hephaestus.png" height="300" /></td> <td align="center"><img src=".github/assets/hephaestus.png" height="300" /></td>
</tr></table> </tr></table>
**Sisyphus** (`claude-opus-4-6` / **`kimi-k2.5`** / **`glm-5`** ) is your main orchestrator. He plans, delegates to specialists, and drives tasks to completion with aggressive parallel execution. He does not stop halfway. **Sisyphus** (`claude-opus-4-7` / **`kimi-k2.5`** / **`glm-5`** ) is your main orchestrator. He plans, delegates to specialists, and drives tasks to completion with aggressive parallel execution. He does not stop halfway.
**Hephaestus** (`gpt-5.4`) is your autonomous deep worker. Give him a goal, not a recipe. He explores the codebase, researches patterns, and executes end-to-end without hand-holding. *The Legitimate Craftsman.* **Hephaestus** (`gpt-5.4`) is your autonomous deep worker. Give him a goal, not a recipe. He explores the codebase, researches patterns, and executes end-to-end without hand-holding. *The Legitimate Craftsman.*
**Prometheus** (`claude-opus-4-6` / **`kimi-k2.5`** / **`glm-5`** ) is your strategic planner. Interview mode: it questions, identifies scope, and builds a detailed plan before a single line of code is touched. **Prometheus** (`claude-opus-4-7` / **`kimi-k2.5`** / **`glm-5`** ) is your strategic planner. Interview mode: it questions, identifies scope, and builds a detailed plan before a single line of code is touched.
Every agent is tuned to its model's specific strengths. No manual model-juggling. [Learn more →](docs/guide/overview.md) Every agent is tuned to its model's specific strengths. No manual model-juggling. [Learn more →](docs/guide/overview.md)
+6 -2
View File
@@ -101,6 +101,10 @@ https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/do
curl -s https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/docs/guide/installation.md curl -s https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/docs/guide/installation.md
``` ```
**Примечание**: Используйте опубликованное имя пакета и бинарника `oh-my-opencode`. Внутри `opencode.json` слой совместимости теперь предпочитает точку входа плагина `oh-my-openagent`, в то время как устаревшие записи `oh-my-opencode` все еще загружаются с предупреждением. Файлы конфигурации плагина по-прежнему часто используют `oh-my-opencode.json` или `oh-my-opencode.jsonc`, и как устаревшие, так и переименованные базовые имена распознаются во время переходного периода.
Анонимная телеметрия включена по умолчанию для улучшения надежности установки и работы. Она использует PostHog с хешированным идентификатором установки, никогда не используя исходное имя хоста, и может быть отключена с помощью `OMO_SEND_ANONYMOUS_TELEMETRY=0` или `OMO_DISABLE_POSTHOG=1`. См. [Политику конфиденциальности](docs/legal/privacy-policy.md) и [Условия обслуживания](docs/legal/terms-of-service.md).
------ ------
## Пропустите этот README ## Пропустите этот README
@@ -150,11 +154,11 @@ Read this and tell me why it's not just another boilerplate: https://raw.githubu
<table><tr> <td align="center"><img src=".github/assets/sisyphus.png" height="300" /></td> <td align="center"><img src=".github/assets/hephaestus.png" height="300" /></td> </tr></table> <table><tr> <td align="center"><img src=".github/assets/sisyphus.png" height="300" /></td> <td align="center"><img src=".github/assets/hephaestus.png" height="300" /></td> </tr></table>
**Sisyphus** (`claude-opus-4-6` / **`kimi-k2.5`** / **`glm-5`**) — главный оркестратор. Он планирует, делегирует задачи специалистам и доводит их до завершения с агрессивным параллельным выполнением. Он не останавливается на полпути. **Sisyphus** (`claude-opus-4-7` / **`kimi-k2.5`** / **`glm-5`**) — главный оркестратор. Он планирует, делегирует задачи специалистам и доводит их до завершения с агрессивным параллельным выполнением. Он не останавливается на полпути.
**Hephaestus** (`gpt-5.4`) — автономный глубокий исполнитель. Дайте ему цель, а не рецепт. Он исследует кодовую базу, изучает паттерны и выполняет задачи сквозным образом без лишних подсказок. *Законный Мастер.* **Hephaestus** (`gpt-5.4`) — автономный глубокий исполнитель. Дайте ему цель, а не рецепт. Он исследует кодовую базу, изучает паттерны и выполняет задачи сквозным образом без лишних подсказок. *Законный Мастер.*
**Prometheus** (`claude-opus-4-6` / **`kimi-k2.5`** / **`glm-5`**) — стратегический планировщик. Режим интервью: задаёт вопросы, определяет объём работ и формирует детальный план до того, как написана хотя бы одна строка кода. **Prometheus** (`claude-opus-4-7` / **`kimi-k2.5`** / **`glm-5`**) — стратегический планировщик. Режим интервью: задаёт вопросы, определяет объём работ и формирует детальный план до того, как написана хотя бы одна строка кода.
Каждый агент настроен под сильные стороны своей модели. Никакого ручного переключения между моделями. Подробнее → Каждый агент настроен под сильные стороны своей модели. Никакого ручного переключения между моделями. Подробнее →
+6 -2
View File
@@ -116,6 +116,10 @@ https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/do
curl -s https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/docs/guide/installation.md curl -s https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/docs/guide/installation.md
``` ```
**注意**:请使用已发布的包名和二进制名 `oh-my-opencode`。在 `opencode.json` 中,兼容性层现在优先使用插件入口 `oh-my-openagent`,而旧的 `oh-my-opencode` 条目仍会加载并显示警告。插件配置文件通常仍使用 `oh-my-opencode.json``oh-my-opencode.jsonc`,在过渡期间新旧两种文件名都会被识别。
匿名遥测默认开启,用于帮助提升安装和运行时的可靠性。它使用 PostHog,并采用哈希化的安装标识符,绝不会使用原始主机名,可通过 `OMO_SEND_ANONYMOUS_TELEMETRY=0``OMO_DISABLE_POSTHOG=1` 禁用。详见 [隐私政策](docs/legal/privacy-policy.md) 和 [服务条款](docs/legal/terms-of-service.md)。
--- ---
## 跳过这个 README 吧 ## 跳过这个 README 吧
@@ -167,11 +171,11 @@ Read this and tell me why it's not just another boilerplate: https://raw.githubu
<td align="center"><img src=".github/assets/hephaestus.png" height="300" /></td> <td align="center"><img src=".github/assets/hephaestus.png" height="300" /></td>
</tr></table> </tr></table>
**Sisyphus** (`claude-opus-4-6` / **`kimi-k2.5`** / **`glm-5`**) 是你的主指挥官。他负责制定计划、分配任务给专家团队,并以极其激进的并行策略推动任务直至完成。他从不半途而废。 **Sisyphus** (`claude-opus-4-7` / **`kimi-k2.5`** / **`glm-5`**) 是你的主指挥官。他负责制定计划、分配任务给专家团队,并以极其激进的并行策略推动任务直至完成。他从不半途而废。
**Hephaestus** (`gpt-5.4`) 是你的自主深度工作者。你只需要给他目标,不要给他具体做法。他会自动探索代码库模式,从头到尾独立执行任务,绝不会中途要你当保姆。*名副其实的正牌工匠。* **Hephaestus** (`gpt-5.4`) 是你的自主深度工作者。你只需要给他目标,不要给他具体做法。他会自动探索代码库模式,从头到尾独立执行任务,绝不会中途要你当保姆。*名副其实的正牌工匠。*
**Prometheus** (`claude-opus-4-6` / **`kimi-k2.5`** / **`glm-5`**) 是你的战略规划师。他通过访谈模式,在动一行代码之前,先通过提问确定范围并构建详尽的执行计划。 **Prometheus** (`claude-opus-4-7` / **`kimi-k2.5`** / **`glm-5`**) 是你的战略规划师。他通过访谈模式,在动一行代码之前,先通过提问确定范围并构建详尽的执行计划。
每一个 Agent 都针对其底层模型的特点进行了专门调优。你无需手动来回切换模型。[阅读背景设定了解更多 →](docs/guide/overview.md) 每一个 Agent 都针对其底层模型的特点进行了专门调优。你无需手动来回切换模型。[阅读背景设定了解更多 →](docs/guide/overview.md)
+7 -5
View File
@@ -14,6 +14,13 @@
"default_run_agent": { "default_run_agent": {
"type": "string" "type": "string"
}, },
"agent_definitions": {
"type": "array",
"items": {
"type": "string",
"minLength": 1
}
},
"disabled_mcps": { "disabled_mcps": {
"type": "array", "type": "array",
"items": { "items": {
@@ -5666,11 +5673,6 @@
"minimum": 1, "minimum": 1,
"maximum": 9007199254740991 "maximum": 9007199254740991
}, },
"maxDescendants": {
"type": "integer",
"minimum": 1,
"maximum": 9007199254740991
},
"staleTimeoutMs": { "staleTimeoutMs": {
"type": "number", "type": "number",
"minimum": 60000 "minimum": 60000
+26 -23
View File
@@ -21,26 +21,29 @@
"picomatch": "^4.0.2", "picomatch": "^4.0.2",
"posthog-node": "^5.29.2", "posthog-node": "^5.29.2",
"vscode-jsonrpc": "^8.2.0", "vscode-jsonrpc": "^8.2.0",
"zod": "^4.3.0",
}, },
"devDependencies": { "devDependencies": {
"@types/js-yaml": "^4.0.9", "@types/js-yaml": "^4.0.9",
"@types/picomatch": "^3.0.2", "@types/picomatch": "^3.0.2",
"bun-types": "1.3.11", "bun-types": "1.3.11",
"typescript": "^5.7.3", "typescript": "^5.7.3",
"zod": "^4.3.0",
}, },
"optionalDependencies": { "optionalDependencies": {
"oh-my-opencode-darwin-arm64": "3.17.0", "oh-my-opencode-darwin-arm64": "3.17.4",
"oh-my-opencode-darwin-x64": "3.17.0", "oh-my-opencode-darwin-x64": "3.17.4",
"oh-my-opencode-darwin-x64-baseline": "3.17.0", "oh-my-opencode-darwin-x64-baseline": "3.17.4",
"oh-my-opencode-linux-arm64": "3.17.0", "oh-my-opencode-linux-arm64": "3.17.4",
"oh-my-opencode-linux-arm64-musl": "3.17.0", "oh-my-opencode-linux-arm64-musl": "3.17.4",
"oh-my-opencode-linux-x64": "3.17.0", "oh-my-opencode-linux-x64": "3.17.4",
"oh-my-opencode-linux-x64-baseline": "3.17.0", "oh-my-opencode-linux-x64-baseline": "3.17.4",
"oh-my-opencode-linux-x64-musl": "3.17.0", "oh-my-opencode-linux-x64-musl": "3.17.4",
"oh-my-opencode-linux-x64-musl-baseline": "3.17.0", "oh-my-opencode-linux-x64-musl-baseline": "3.17.4",
"oh-my-opencode-windows-x64": "3.17.0", "oh-my-opencode-windows-x64": "3.17.4",
"oh-my-opencode-windows-x64-baseline": "3.17.0", "oh-my-opencode-windows-x64-baseline": "3.17.4",
},
"peerDependencies": {
"zod": "^4.0.0",
}, },
}, },
}, },
@@ -238,27 +241,27 @@
"object-inspect": ["object-inspect@1.13.4", "", {}, "sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew=="], "object-inspect": ["object-inspect@1.13.4", "", {}, "sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew=="],
"oh-my-opencode-darwin-arm64": ["oh-my-opencode-darwin-arm64@3.17.0", "", { "os": "darwin", "cpu": "arm64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-d8VHKSjR4gWwQ7rvYn2bU+v+I3KlcgqGc0R38WCn4ZiyfTJECcOVzhOVKt4hKfJgbH2uNjpJ5eM41jPP6oJRjA=="], "oh-my-opencode-darwin-arm64": ["oh-my-opencode-darwin-arm64@3.17.4", "", { "os": "darwin", "cpu": "arm64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-N135KhfHom/qiP3lgMHfY8DvRNVyOzZMuUs6p6uYTekLduSg3i72Pnc2WyNTZEKFX2yehaLjC5ireY8SnRCbdg=="],
"oh-my-opencode-darwin-x64": ["oh-my-opencode-darwin-x64@3.17.0", "", { "os": "darwin", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-m4ir/TpacyobUFQ9xcKHq1Tn4JLHvwrOWmoJk59VQPDMUIaGWhfafgBuRFFKIkXIXRKBP1pEnV+PYGolPRBUGg=="], "oh-my-opencode-darwin-x64": ["oh-my-opencode-darwin-x64@3.17.4", "", { "os": "darwin", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-LSh5o4oC7ItuIoqd7s1UCAVZ5I7JftEBgeLoatUeto/8by1O6MYvm12ljjP8HIXLsnfi3nJfipqLyXAiiHDHPQ=="],
"oh-my-opencode-darwin-x64-baseline": ["oh-my-opencode-darwin-x64-baseline@3.17.0", "", { "os": "darwin", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-ej4XZdt3aRpUL3mSIp5SHRDmoTdeojdgkxqF5s/6Gv79NomCIhQLNVs6yRhUihrWkVwclAkKXHM6+UkGNbWQQw=="], "oh-my-opencode-darwin-x64-baseline": ["oh-my-opencode-darwin-x64-baseline@3.17.4", "", { "os": "darwin", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-caGra13pBdRoV/jCdRWZNeu8XUHUgIxBVn9guAJfT9bZ7AoBurqwO0wgJHUFghOydTdFxPBOGbSOYzJY3Hco5Q=="],
"oh-my-opencode-linux-arm64": ["oh-my-opencode-linux-arm64@3.17.0", "", { "os": "linux", "cpu": "arm64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-xww4j2wRwxA0M7YpM5DT9ZScEajW9aDr5+NNoIqJQwIRCkKShmDvyhxbi/zTXLiyhu0HNySoLfN5iqfhIvNl9w=="], "oh-my-opencode-linux-arm64": ["oh-my-opencode-linux-arm64@3.17.4", "", { "os": "linux", "cpu": "arm64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-P9BAlcybNmJn7ZEq4pKI/qeeP6eUJd0/M/unP+FCjKJE/UwY0YJTYS/Jf9PPZbLCgwbJErPglZe2Ku6t/NXAxQ=="],
"oh-my-opencode-linux-arm64-musl": ["oh-my-opencode-linux-arm64-musl@3.17.0", "", { "os": "linux", "cpu": "arm64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-oR0EwN9jbhshhdomnV9zv5KNfsv0LWP3G21yhBkTPc2DtzUPQ0WEhG0qgbVPV8z9rq3HsB/L0CIg+/D/CGavPQ=="], "oh-my-opencode-linux-arm64-musl": ["oh-my-opencode-linux-arm64-musl@3.17.4", "", { "os": "linux", "cpu": "arm64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-F7HNYc/DygFsrraMbvXSQjb16NnC9EgtBsbWgHNkRm6UbxVHkWGIuVdHFEUJ1CqHPm2C/9xIuKJ5jiZrtEXqaA=="],
"oh-my-opencode-linux-x64": ["oh-my-opencode-linux-x64@3.17.0", "", { "os": "linux", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-9uNbkDhJIsaTCxF+A0KOUxES0vasw+8LD9uEdN0BBgjtvQZ67XaHsPUZkSGBYzeTJgJVOImq/fwzINhqxfXahw=="], "oh-my-opencode-linux-x64": ["oh-my-opencode-linux-x64@3.17.4", "", { "os": "linux", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-WgDiowJBI7nXxqFZDo3FbR0lRkxURrFbBjDVfpqj7jxRQfUrVtwedNjkgxCF8eBOQwoBrijTmxG40GiF4z219g=="],
"oh-my-opencode-linux-x64-baseline": ["oh-my-opencode-linux-x64-baseline@3.17.0", "", { "os": "linux", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-FaWPECkzdnT5CkHPgWsMbpsXK8vC+YgqxmBJ5SdwRb8aeRk0+ySF96dTp4rz6xkegmkwC7XXfmmW5bu9yQjzyg=="], "oh-my-opencode-linux-x64-baseline": ["oh-my-opencode-linux-x64-baseline@3.17.4", "", { "os": "linux", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-BVJR1qiFe1WykrTBGYmd9XT387yR6VY8jupS/Pu0pqamRYBjeSlER4HQjOcrMY1XHJ/ygsspOcaWKJbSQ8Wcvw=="],
"oh-my-opencode-linux-x64-musl": ["oh-my-opencode-linux-x64-musl@3.17.0", "", { "os": "linux", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-JHEIjWvhB0Z5kHNhXirTsW7YzTb4IbV//LVCmQuhpoyDC7GeN3Wka3OPSBnTgnqw1SMvm0c6G7gNvDqeZNgzUg=="], "oh-my-opencode-linux-x64-musl": ["oh-my-opencode-linux-x64-musl@3.17.4", "", { "os": "linux", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-qbLyLSc6bMAys6AwQnD4a3PR9KJNSDaMvA9DA9ARz9+yZ1tb7aA2JdEA24xAoxwct7k2EzxnQI+gssJJM4VUoQ=="],
"oh-my-opencode-linux-x64-musl-baseline": ["oh-my-opencode-linux-x64-musl-baseline@3.17.0", "", { "os": "linux", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-WxwUW0VWDle78U0xtF7lrcYUWB6EXf+lLBZJue3HWS4wpyTAYlynGgnZJCnG0l8bc9RLJIe4VvvmiZSFuxNIEg=="], "oh-my-opencode-linux-x64-musl-baseline": ["oh-my-opencode-linux-x64-musl-baseline@3.17.4", "", { "os": "linux", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode" } }, "sha512-ETqpbPN4HHc0wKfNSeAI2f0NE4nzUq+x85APomPRitVfTPxjdZbQd0TSc0O85vjT+kWj6cXjnHtviHB2BtxHog=="],
"oh-my-opencode-windows-x64": ["oh-my-opencode-windows-x64@3.17.0", "", { "os": "win32", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode.exe" } }, "sha512-XnIR++Kw1s+5MOZLqoBTCWyYaXT03JAR+5/7zYU1b5JEbQuM5L/zKXjUScXnVUHMkqtYpxUZLE7Nk6ldUyWNaA=="], "oh-my-opencode-windows-x64": ["oh-my-opencode-windows-x64@3.17.4", "", { "os": "win32", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode.exe" } }, "sha512-RC34rbTJGtJeOvp2WTY4ZgVmtkjrduVmXCVMcIdgvQ53yNmNqx79nDITm9FVBA8Id02AHJbYmXGxKvr+XpHbNA=="],
"oh-my-opencode-windows-x64-baseline": ["oh-my-opencode-windows-x64-baseline@3.17.0", "", { "os": "win32", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode.exe" } }, "sha512-wyv/OHC/SrJVYGWMu9wD7+PUcmp87v38zBgMduqOn5PIUkmwIPOXF7tOdPeIQsch3/m/CK01RuZJ8NHAMA0bGA=="], "oh-my-opencode-windows-x64-baseline": ["oh-my-opencode-windows-x64-baseline@3.17.4", "", { "os": "win32", "cpu": "x64", "bin": { "oh-my-opencode": "bin/oh-my-opencode.exe" } }, "sha512-pi43bhDpt6l1fnxkqYYkWCsec1RNxsWL7FZDXoLOGJq/0y3bobWiTNDhbEWNr+uJvOrMs/Sv3qpF1TmYeTvdiA=="],
"on-finished": ["on-finished@2.4.1", "", { "dependencies": { "ee-first": "1.1.1" } }, "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg=="], "on-finished": ["on-finished@2.4.1", "", { "dependencies": { "ee-first": "1.1.1" } }, "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg=="],
+1 -1
View File
@@ -8,7 +8,7 @@
// Primary orchestrator: aggressive parallel delegation // Primary orchestrator: aggressive parallel delegation
"sisyphus": { "sisyphus": {
"model": "kimi-for-coding/k2p5", "model": "kimi-for-coding/k2p5",
"ultrawork": { "model": "anthropic/claude-opus-4-6", "variant": "max" }, "ultrawork": { "model": "anthropic/claude-opus-4-7", "variant": "max" },
"prompt_append": "Delegate heavily to hephaestus for implementation. Parallelize exploration.", "prompt_append": "Delegate heavily to hephaestus for implementation. Parallelize exploration.",
}, },
+3 -3
View File
@@ -7,8 +7,8 @@
"agents": { "agents": {
// Main orchestrator: handles delegation and drives tasks to completion // Main orchestrator: handles delegation and drives tasks to completion
"sisyphus": { "sisyphus": {
"model": "anthropic/claude-opus-4-6", "model": "anthropic/claude-opus-4-7",
"ultrawork": { "model": "anthropic/claude-opus-4-6", "variant": "max" }, "ultrawork": { "model": "anthropic/claude-opus-4-7", "variant": "max" },
}, },
// Deep autonomous worker: end-to-end implementation // Deep autonomous worker: end-to-end implementation
@@ -50,7 +50,7 @@
"categories": { "categories": {
"quick": { "model": "opencode/gpt-5-nano" }, "quick": { "model": "opencode/gpt-5-nano" },
"unspecified-low": { "model": "anthropic/claude-sonnet-4-6" }, "unspecified-low": { "model": "anthropic/claude-sonnet-4-6" },
"unspecified-high": { "model": "anthropic/claude-opus-4-6", "variant": "max" }, "unspecified-high": { "model": "anthropic/claude-opus-4-7", "variant": "max" },
"writing": { "model": "google/gemini-3-flash" }, "writing": { "model": "google/gemini-3-flash" },
"visual-engineering": { "model": "google/gemini-3.1-pro", "variant": "high" }, "visual-engineering": { "model": "google/gemini-3.1-pro", "variant": "high" },
"deep": { "model": "openai/gpt-5.4" }, "deep": { "model": "openai/gpt-5.4" },
+5 -5
View File
@@ -7,8 +7,8 @@
"agents": { "agents": {
// Orchestrator: delegates to planning agents first // Orchestrator: delegates to planning agents first
"sisyphus": { "sisyphus": {
"model": "anthropic/claude-opus-4-6", "model": "anthropic/claude-opus-4-7",
"ultrawork": { "model": "anthropic/claude-opus-4-6", "variant": "max" }, "ultrawork": { "model": "anthropic/claude-opus-4-7", "variant": "max" },
"prompt_append": "Always consult prometheus and atlas for planning. Never rush to implementation.", "prompt_append": "Always consult prometheus and atlas for planning. Never rush to implementation.",
}, },
@@ -20,7 +20,7 @@
// Primary planner: deep interview mode // Primary planner: deep interview mode
"prometheus": { "prometheus": {
"model": "anthropic/claude-opus-4-6", "model": "anthropic/claude-opus-4-7",
"thinking": { "type": "enabled", "budgetTokens": 160000 }, "thinking": { "type": "enabled", "budgetTokens": 160000 },
"prompt_append": "Interview extensively. Question assumptions. Build exhaustive plans with milestones, risks, and contingencies. Use deep & quick agents heavily in parallel for research.", "prompt_append": "Interview extensively. Question assumptions. Build exhaustive plans with milestones, risks, and contingencies. Use deep & quick agents heavily in parallel for research.",
}, },
@@ -43,7 +43,7 @@
// Plan review and refinement: heavily utilized // Plan review and refinement: heavily utilized
"metis": { "metis": {
"model": "anthropic/claude-opus-4-6", "model": "anthropic/claude-opus-4-7",
"prompt_append": "Critically evaluate plans. Identify gaps, risks, and improvements. Be thorough.", "prompt_append": "Critically evaluate plans. Identify gaps, risks, and improvements. Be thorough.",
}, },
@@ -98,7 +98,7 @@
"openai": 3, "openai": 3,
}, },
"modelConcurrency": { "modelConcurrency": {
"anthropic/claude-opus-4-6": 2, "anthropic/claude-opus-4-7": 2,
"openai/gpt-5.4": 2, "openai/gpt-5.4": 2,
}, },
}, },
+27 -23
View File
@@ -64,8 +64,8 @@ These agents have Claude-optimized prompts — long, detailed, mechanics-driven.
| Agent | Role | Fallback Chain | Notes | | Agent | Role | Fallback Chain | Notes |
| ------------ | ----------------- | -------------------------------------- | ------------------------------------------------------------------------------------------------- | | ------------ | ----------------- | -------------------------------------- | ------------------------------------------------------------------------------------------------- |
| **Sisyphus** | Main orchestrator | anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → opencode-go/kimi-k2.5 → kimi-for-coding/k2p5 → opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix/kimi-k2.5 → openai\|github-copilot\|opencode/gpt-5.4 (medium) → zai-coding-plan\|opencode/glm-5 → opencode/big-pickle | Exact runtime chain from `src/shared/model-requirements.ts`. | | **Sisyphus** | Main orchestrator | anthropic\|github-copilot\|opencode\|vercel/claude-opus-4-7 (max) → opencode-go\|vercel/kimi-k2.5 → kimi-for-coding/k2p5 → opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix\|vercel/kimi-k2.5 → openai\|github-copilot\|opencode\|vercel/gpt-5.4 (medium) → zai-coding-plan\|opencode\|vercel/glm-5 → opencode/big-pickle | Exact runtime chain from `src/shared/model-requirements.ts`. |
| **Metis** | Plan gap analyzer | anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → openai\|github-copilot\|opencode/gpt-5.4 (high) → opencode-go/glm-5 → kimi-for-coding/k2p5 | Exact runtime chain from `src/shared/model-requirements.ts`. | | **Metis** | Plan gap analyzer | anthropic\|github-copilot\|opencode\|vercel/claude-opus-4-7 (max) → openai\|github-copilot\|opencode\|vercel/gpt-5.4 (high) → opencode-go\|vercel/glm-5 → kimi-for-coding/k2p5 | Exact runtime chain from `src/shared/model-requirements.ts`. |
### Dual-Prompt Agents → Claude preferred, GPT supported ### Dual-Prompt Agents → Claude preferred, GPT supported
@@ -73,8 +73,8 @@ These agents ship separate prompts for Claude and GPT families. They auto-detect
| Agent | Role | Fallback Chain | Notes | | Agent | Role | Fallback Chain | Notes |
| -------------- | ----------------- | -------------------------------------- | -------------------------------------------------------------------- | | -------------- | ----------------- | -------------------------------------- | -------------------------------------------------------------------- |
| **Prometheus** | Strategic planner | anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → openai\|github-copilot\|opencode/gpt-5.4 (high) → opencode-go/glm-5 → google\|github-copilot\|opencode/gemini-3.1-pro | Exact runtime chain from `src/shared/model-requirements.ts`. | | **Prometheus** | Strategic planner | anthropic\|github-copilot\|opencode\|vercel/claude-opus-4-7 (max) → openai\|github-copilot\|opencode\|vercel/gpt-5.4 (high) → opencode-go\|vercel/glm-5 → google\|github-copilot\|opencode\|vercel/gemini-3.1-pro | Exact runtime chain from `src/shared/model-requirements.ts`. |
| **Atlas** | Todo orchestrator | anthropic\|github-copilot\|opencode/claude-sonnet-4-6 → opencode-go/kimi-k2.5 → openai\|github-copilot\|opencode/gpt-5.4 (medium) → opencode-go/minimax-m2.7 | Exact runtime chain from `src/shared/model-requirements.ts`. | | **Atlas** | Todo orchestrator | anthropic\|github-copilot\|opencode\|vercel/claude-sonnet-4-6 → opencode-go\|vercel/kimi-k2.5 → openai\|github-copilot\|opencode\|vercel/gpt-5.4 (medium) → opencode-go\|vercel/minimax-m2.7 | Exact runtime chain from `src/shared/model-requirements.ts`. |
### Deep Specialists → GPT ### Deep Specialists → GPT
@@ -82,9 +82,9 @@ These agents are built for GPT's principle-driven style. Their prompts assume au
| Agent | Role | Fallback Chain | Notes | | Agent | Role | Fallback Chain | Notes |
| -------------- | ----------------------- | -------------------------------------- | ------------------------------------------------ | | -------------- | ----------------------- | -------------------------------------- | ------------------------------------------------ |
| **Hephaestus** | Autonomous deep worker | GPT-5.4 (medium) | Requires a GPT-capable provider. The craftsman. | | **Hephaestus** | Autonomous deep worker | openai\|github-copilot\|venice\|opencode\|vercel/gpt-5.4 (medium) | Single-entry chain. Requires one of those providers. The craftsman. |
| **Oracle** | Architecture consultant | openai\|github-copilot\|opencode/gpt-5.4 (high) → google\|github-copilot\|opencode/gemini-3.1-pro (high) → anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → opencode-go/glm-5 | Exact runtime chain from `src/shared/model-requirements.ts`. | | **Oracle** | Architecture consultant | openai\|github-copilot\|opencode\|vercel/gpt-5.4 (high) → google\|github-copilot\|opencode\|vercel/gemini-3.1-pro (high) → anthropic\|github-copilot\|opencode\|vercel/claude-opus-4-7 (max) → opencode-go\|vercel/glm-5 | Exact runtime chain from `src/shared/model-requirements.ts`. |
| **Momus** | Ruthless reviewer | openai\|github-copilot\|opencode/gpt-5.4 (xhigh) → anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → google\|github-copilot\|opencode/gemini-3.1-pro (high) → opencode-go/glm-5 | Exact runtime chain from `src/shared/model-requirements.ts`. | | **Momus** | Ruthless reviewer | openai\|github-copilot\|opencode\|vercel/gpt-5.4 (xhigh) → anthropic\|github-copilot\|opencode\|vercel/claude-opus-4-7 (max) → google\|github-copilot\|opencode\|vercel/gemini-3.1-pro (high) → opencode-go\|vercel/glm-5 | Exact runtime chain from `src/shared/model-requirements.ts`. |
### Utility Runners → Speed over Intelligence ### Utility Runners → Speed over Intelligence
@@ -92,10 +92,10 @@ These agents do grep, search, and retrieval. They intentionally use the fastest,
| Agent | Role | Fallback Chain | Notes | | Agent | Role | Fallback Chain | Notes |
| --------------------- | ------------------ | ---------------------------------------------- | ----------------------------------------------------- | | --------------------- | ------------------ | ---------------------------------------------- | ----------------------------------------------------- |
| **Explore** | Fast codebase grep | github-copilot\|xai/grok-code-fast-1 → opencode-go/minimax-m2.7-highspeed → opencode/minimax-m2.7 → anthropic\|opencode/claude-haiku-4-5 → opencode/gpt-5-nano | Exact runtime chain from `src/shared/model-requirements.ts`. | | **Explore** | Fast codebase grep | github-copilot\|xai\|vercel/grok-code-fast-1 → opencode-go\|vercel/minimax-m2.7-highspeed → opencode\|vercel/minimax-m2.7 → anthropic\|opencode\|vercel/claude-haiku-4-5 → opencode\|vercel/gpt-5-nano | Exact runtime chain from `src/shared/model-requirements.ts`. |
| **Librarian** | Docs/code search | opencode-go/minimax-m2.7 → opencode/minimax-m2.7-highspeed → anthropic\|opencode/claude-haiku-4-5 → opencode/gpt-5-nano | Exact runtime chain from `src/shared/model-requirements.ts`. | | **Librarian** | Docs/code search | opencode-go\|vercel/minimax-m2.7 → opencode\|vercel/minimax-m2.7-highspeed → anthropic\|opencode\|vercel/claude-haiku-4-5 → opencode\|vercel/gpt-5-nano | Exact runtime chain from `src/shared/model-requirements.ts`. |
| **Multimodal Looker** | Vision/screenshots | openai\|opencode/gpt-5.4 (medium) → opencode-go/kimi-k2.5 → zai-coding-plan/glm-4.6v → openai\|github-copilot\|opencode/gpt-5-nano | Exact runtime chain from `src/shared/model-requirements.ts`. | | **Multimodal Looker** | Vision/screenshots | openai\|opencode\|vercel/gpt-5.4 (medium) → opencode-go\|vercel/kimi-k2.5 → zai-coding-plan\|vercel/glm-4.6v → openai\|github-copilot\|opencode\|vercel/gpt-5-nano | Exact runtime chain from `src/shared/model-requirements.ts`. |
| **Sisyphus-Junior** | Category executor | anthropic\|github-copilot\|opencode/claude-sonnet-4-6 → opencode-go/kimi-k2.5 → openai\|github-copilot\|opencode/gpt-5.4 (medium) → opencode-go/minimax-m2.7 → opencode/big-pickle | Exact runtime chain from `src/shared/model-requirements.ts`. | | **Sisyphus-Junior** | Category executor | anthropic\|github-copilot\|opencode\|vercel/claude-sonnet-4-6 → opencode-go\|vercel/kimi-k2.5 → openai\|github-copilot\|opencode\|vercel/gpt-5.4 (medium) → opencode-go\|vercel/minimax-m2.7 → opencode/big-pickle | Exact runtime chain from `src/shared/model-requirements.ts`. |
--- ---
@@ -107,7 +107,7 @@ Communicative, instruction-following, structured output. Best for agents that ne
| Model | Strengths | | Model | Strengths |
| --------------------- | ---------------------------------------------------------------------------- | | --------------------- | ---------------------------------------------------------------------------- |
| **Claude Opus 4.6** | Best overall. Highest compliance with complex prompts. Default for Sisyphus. | | **Claude Opus 4.7** | Best overall. Highest compliance with complex prompts. Default for Sisyphus. |
| **Claude Sonnet 4.6** | Faster, cheaper. Good balance for everyday tasks. | | **Claude Sonnet 4.6** | Faster, cheaper. Good balance for everyday tasks. |
| **Claude Haiku 4.5** | Fast and cheap. Good for quick tasks and utility work. | | **Claude Haiku 4.5** | Fast and cheap. Good for quick tasks and utility work. |
| **Kimi K2.5** | Behaves very similarly to Claude. Great all-rounder at lower cost. | | **Kimi K2.5** | Behaves very similarly to Claude. Great all-rounder at lower cost. |
@@ -169,17 +169,21 @@ When agents delegate work, they don't pick a model name — they pick a **catego
| Category | When Used | Fallback Chain | | Category | When Used | Fallback Chain |
| -------------------- | -------------------------- | -------------------------------------------- | | -------------------- | -------------------------- | -------------------------------------------- |
| `visual-engineering` | Frontend, UI, CSS, design | google\|github-copilot\|opencode/gemini-3.1-pro (high) → zai-coding-plan\|opencode/glm-5 → anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → opencode-go/glm-5 → kimi-for-coding/k2p5 | | `visual-engineering` | Frontend, UI, CSS, design | google\|github-copilot\|opencode\|vercel/gemini-3.1-pro (high) → zai-coding-plan\|opencode\|vercel/glm-5 → anthropic\|github-copilot\|opencode\|vercel/claude-opus-4-7 (max) → opencode-go\|vercel/glm-5 → kimi-for-coding/k2p5 |
| `ultrabrain` | Maximum reasoning needed | openai\|opencode/gpt-5.4 (xhigh) → google\|github-copilot\|opencode/gemini-3.1-pro (high) → anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → opencode-go/glm-5 | | `ultrabrain` | Maximum reasoning needed | openai\|opencode\|vercel/gpt-5.4 (xhigh) → google\|github-copilot\|opencode\|vercel/gemini-3.1-pro (high) → anthropic\|github-copilot\|opencode\|vercel/claude-opus-4-7 (max) → opencode-go\|vercel/glm-5 |
| `deep` | Deep coding, complex logic | openai\|github-copilot\|venice\|opencode/gpt-5.4 (medium) → anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → google\|github-copilot\|opencode/gemini-3.1-pro (high) | | `deep` | Deep coding, complex logic | openai\|github-copilot\|venice\|opencode\|vercel/gpt-5.4 (medium) → anthropic\|github-copilot\|opencode\|vercel/claude-opus-4-7 (max) → google\|github-copilot\|opencode\|vercel/gemini-3.1-pro (high) |
| `artistry` | Creative, novel approaches | google\|github-copilot\|opencode/gemini-3.1-pro (high) → anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → openai\|github-copilot\|opencode/gpt-5.4 | | `artistry` | Creative, novel approaches | google\|github-copilot\|opencode\|vercel/gemini-3.1-pro (high) → anthropic\|github-copilot\|opencode\|vercel/claude-opus-4-7 (max) → openai\|github-copilot\|opencode\|vercel/gpt-5.4 |
| `quick` | Simple, fast tasks | openai\|github-copilot\|opencode/gpt-5.4-mini → anthropic\|github-copilot\|opencode/claude-haiku-4-5 → google\|github-copilot\|opencode/gemini-3-flash → opencode-go/minimax-m2.7 → opencode/gpt-5-nano | | `quick` | Simple, fast tasks | openai\|github-copilot\|opencode\|vercel/gpt-5.4-mini → anthropic\|github-copilot\|opencode\|vercel/claude-haiku-4-5 → google\|github-copilot\|opencode\|vercel/gemini-3-flash → opencode-go\|vercel/minimax-m2.7 → opencode\|vercel/gpt-5-nano |
| `unspecified-high` | General complex work | anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → openai\|github-copilot\|opencode/gpt-5.4 (high) → zai-coding-plan\|opencode/glm-5 → kimi-for-coding/k2p5 → opencode-go/glm-5 → opencode/kimi-k2.5 → opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix/kimi-k2.5 | | `unspecified-high` | General complex work | anthropic\|github-copilot\|opencode\|vercel/claude-opus-4-7 (max) → openai\|github-copilot\|opencode\|vercel/gpt-5.4 (high) → zai-coding-plan\|opencode\|vercel/glm-5 → kimi-for-coding/k2p5 → opencode-go\|vercel/glm-5 → opencode\|vercel/kimi-k2.5 → opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix\|vercel/kimi-k2.5 |
| `unspecified-low` | General standard work | anthropic\|github-copilot\|opencode/claude-sonnet-4-6 → openai\|opencode/gpt-5.3-codex (medium) → opencode-go/kimi-k2.5 → google\|github-copilot\|opencode/gemini-3-flash → opencode-go/minimax-m2.7 | | `unspecified-low` | General standard work | anthropic\|github-copilot\|opencode\|vercel/claude-sonnet-4-6 → openai\|opencode\|vercel/gpt-5.3-codex (medium) → opencode-go\|vercel/kimi-k2.5 → google\|github-copilot\|opencode\|vercel/gemini-3-flash → opencode-go\|vercel/minimax-m2.7 |
| `writing` | Text, docs, prose | google\|github-copilot\|opencode/gemini-3-flash → opencode-go/kimi-k2.5 → anthropic\|github-copilot\|opencode/claude-sonnet-4-6 → opencode-go/minimax-m2.7 | | `writing` | Text, docs, prose | google\|github-copilot\|opencode\|vercel/gemini-3-flash → opencode-go\|vercel/kimi-k2.5 → anthropic\|github-copilot\|opencode\|vercel/claude-sonnet-4-6 → opencode-go\|vercel/minimax-m2.7 |
See the [Orchestration System Guide](./orchestration.md) for how agents dispatch tasks to categories. See the [Orchestration System Guide](./orchestration.md) for how agents dispatch tasks to categories.
### Vercel AI Gateway fallback coverage
`src/shared/model-requirements.ts` now includes `vercel` on nearly every gateway-compatible fallback entry across both agent and category chains. Treat it as a universal extra provider path for the listed model IDs, not as a different model family. If a row above shows `|vercel` in the provider set, that is the current source-of-truth runtime fallback, not a docs-only convenience alias.
--- ---
## Customization ## Customization
@@ -194,7 +198,7 @@ See the [Orchestration System Guide](./orchestration.md) for how agents dispatch
// Main orchestrator: Claude Opus or Kimi K2.5 work best // Main orchestrator: Claude Opus or Kimi K2.5 work best
"sisyphus": { "sisyphus": {
"model": "kimi-for-coding/k2p5", "model": "kimi-for-coding/k2p5",
"ultrawork": { "model": "anthropic/claude-opus-4-6", "variant": "max" }, "ultrawork": { "model": "anthropic/claude-opus-4-7", "variant": "max" },
}, },
// Research agents: cheaper models are fine // Research agents: cheaper models are fine
@@ -213,7 +217,7 @@ See the [Orchestration System Guide](./orchestration.md) for how agents dispatch
"categories": { "categories": {
"quick": { "model": "opencode/gpt-5-nano" }, "quick": { "model": "opencode/gpt-5-nano" },
"unspecified-low": { "model": "anthropic/claude-sonnet-4-6" }, "unspecified-low": { "model": "anthropic/claude-sonnet-4-6" },
"unspecified-high": { "model": "anthropic/claude-opus-4-6", "variant": "max" }, "unspecified-high": { "model": "anthropic/claude-opus-4-7", "variant": "max" },
"visual-engineering": { "visual-engineering": {
"model": "google/gemini-3.1-pro", "model": "google/gemini-3.1-pro",
"variant": "high", "variant": "high",
@@ -230,7 +234,7 @@ See the [Orchestration System Guide](./orchestration.md) for how agents dispatch
"zai-coding-plan": 10, "zai-coding-plan": 10,
}, },
"modelConcurrency": { "modelConcurrency": {
"anthropic/claude-opus-4-6": 2, "anthropic/claude-opus-4-7": 2,
"opencode/gpt-5-nano": 20, "opencode/gpt-5-nano": 20,
}, },
}, },
+20 -13
View File
@@ -14,8 +14,7 @@ https://raw.githubusercontent.com/code-yeongyu/oh-my-openagent/refs/heads/dev/do
Run the interactive installer: Run the interactive installer:
```bash ```bash
bunx oh-my-opencode install # recommended bunx oh-my-opencode install
npx oh-my-opencode install # alternative
``` ```
> **Note**: The CLI ships with standalone binaries for all major platforms. No runtime (Bun/Node.js) is required for CLI execution after installation. > **Note**: The CLI ships with standalone binaries for all major platforms. No runtime (Bun/Node.js) is required for CLI execution after installation.
@@ -77,6 +76,14 @@ Ask the user these questions to determine CLI options:
- If **yes**`--opencode-go=yes` - If **yes**`--opencode-go=yes`
- If **no**`--opencode-go=no` (default) - If **no**`--opencode-go=no` (default)
8. **Do you have a Kimi for Coding subscription?**
- If **yes**`--kimi-for-coding=yes`
- If **no**`--kimi-for-coding=no` (default)
9. **Do you use Vercel AI Gateway?**
- If **yes**`--vercel-ai-gateway=yes`
- If **no**`--vercel-ai-gateway=no` (default)
**Provider selection is agent-specific.** The installer and runtime do not use one single global provider priority. Each agent resolves against its own fallback chain. **Provider selection is agent-specific.** The installer and runtime do not use one single global provider priority. Each agent resolves against its own fallback chain.
MUST STRONGLY WARNING, WHEN USER SAID THEY DON'T HAVE CLAUDE SUBSCRIPTION, SISYPHUS AGENT MIGHT NOT WORK IDEALLY. MUST STRONGLY WARNING, WHEN USER SAID THEY DON'T HAVE CLAUDE SUBSCRIPTION, SISYPHUS AGENT MIGHT NOT WORK IDEALLY.
@@ -100,7 +107,7 @@ Spawn a subagent to handle installation and report back - to save context.
Based on user's answers, run the CLI installer with appropriate flags: Based on user's answers, run the CLI installer with appropriate flags:
```bash ```bash
bunx oh-my-opencode install --no-tui --claude=<yes|no|max20> --gemini=<yes|no> --copilot=<yes|no> [--openai=<yes|no>] [--opencode-go=<yes|no>] [--opencode-zen=<yes|no>] [--zai-coding-plan=<yes|no>] bunx oh-my-opencode install --no-tui --claude=<yes|no|max20> --gemini=<yes|no> --copilot=<yes|no> [--openai=<yes|no>] [--opencode-go=<yes|no>] [--opencode-zen=<yes|no>] [--zai-coding-plan=<yes|no>] [--kimi-for-coding=<yes|no>] [--vercel-ai-gateway=<yes|no>] [--skip-auth]
``` ```
**Examples:** **Examples:**
@@ -218,7 +225,7 @@ When GitHub Copilot is the best available provider, install-time defaults are ag
| Agent | Model | | Agent | Model |
| ------------- | ---------------------------------- | | ------------- | ---------------------------------- |
| **Sisyphus** | `github-copilot/claude-opus-4.6` | | **Sisyphus** | `github-copilot/claude-opus-4.7` |
| **Oracle** | `github-copilot/gpt-5.4` | | **Oracle** | `github-copilot/gpt-5.4` |
| **Explore** | `github-copilot/grok-code-fast-1` | | **Explore** | `github-copilot/grok-code-fast-1` |
| **Atlas** | `github-copilot/claude-sonnet-4.6` | | **Atlas** | `github-copilot/claude-sonnet-4.6` |
@@ -240,13 +247,13 @@ If Z.ai is your main provider, the most important fallbacks are:
#### OpenCode Zen #### OpenCode Zen
OpenCode Zen provides access to `opencode/` prefixed models including `opencode/claude-opus-4-6`, `opencode/gpt-5.4`, `opencode/gpt-5.3-codex`, `opencode/gpt-5-nano`, `opencode/glm-5`, `opencode/big-pickle`, `opencode/minimax-m2.7`, and `opencode/minimax-m2.7-highspeed`. OpenCode Zen provides access to `opencode/` prefixed models including `opencode/claude-opus-4-7`, `opencode/gpt-5.4`, `opencode/gpt-5.3-codex`, `opencode/gpt-5-nano`, `opencode/glm-5`, `opencode/big-pickle`, `opencode/minimax-m2.7`, and `opencode/minimax-m2.7-highspeed`.
When OpenCode Zen is the best available provider, these are the most relevant source-backed examples: When OpenCode Zen is the best available provider, these are the most relevant source-backed examples:
| Agent | Model | | Agent | Model |
| ------------- | ---------------------------------------------------- | | ------------- | ---------------------------------------------------- |
| **Sisyphus** | `opencode/claude-opus-4-6` | | **Sisyphus** | `opencode/claude-opus-4-7` |
| **Oracle** | `opencode/gpt-5.4` | | **Oracle** | `opencode/gpt-5.4` |
| **Explore** | `opencode/minimax-m2.7` | | **Explore** | `opencode/minimax-m2.7` |
@@ -280,7 +287,7 @@ Not all models behave the same way. Understanding which models are "similar" hel
| Model | Provider(s) | Notes | | Model | Provider(s) | Notes |
| ------------------------ | ----------------------------------- | ----------------------------------------------------------------------- | | ------------------------ | ----------------------------------- | ----------------------------------------------------------------------- |
| **Claude Opus 4.6** | anthropic, github-copilot, opencode | Best overall. Default for Sisyphus. | | **Claude Opus 4.7** | anthropic, github-copilot, opencode | Best overall. Default for Sisyphus. |
| **Claude Sonnet 4.6** | anthropic, github-copilot, opencode | Faster, cheaper. Good balance. | | **Claude Sonnet 4.6** | anthropic, github-copilot, opencode | Faster, cheaper. Good balance. |
| **Claude Haiku 4.5** | anthropic, opencode | Fast and cheap. Good for quick tasks. | | **Claude Haiku 4.5** | anthropic, opencode | Fast and cheap. Good for quick tasks. |
| **Kimi K2.5** | kimi-for-coding, opencode-go, opencode, moonshotai, moonshotai-cn, firmware, ollama-cloud, aihubmix | Behaves very similarly to Claude. Great all-rounder that appears in several orchestration fallback chains. | | **Kimi K2.5** | kimi-for-coding, opencode-go, opencode, moonshotai, moonshotai-cn, firmware, ollama-cloud, aihubmix | Behaves very similarly to Claude. Great all-rounder that appears in several orchestration fallback chains. |
@@ -323,8 +330,8 @@ Based on your subscriptions, here's how the agents were configured:
| Agent | Role | Default Chain | What It Does | | Agent | Role | Default Chain | What It Does |
| ------------ | ---------------- | ----------------------------------------------- | ---------------------------------------------------------------------------------------- | | ------------ | ---------------- | ----------------------------------------------- | ---------------------------------------------------------------------------------------- |
| **Sisyphus** | Main ultraworker | anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → opencode-go/kimi-k2.5 → kimi-for-coding/k2p5 → opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix/kimi-k2.5 → openai\|github-copilot\|opencode/gpt-5.4 (medium) → zai-coding-plan\|opencode/glm-5 → opencode/big-pickle | Primary coding agent. Exact runtime chain from `src/shared/model-requirements.ts`. | | **Sisyphus** | Main ultraworker | anthropic\|github-copilot\|opencode/claude-opus-4-7 (max) → opencode-go/kimi-k2.5 → kimi-for-coding/k2p5 → opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix/kimi-k2.5 → openai\|github-copilot\|opencode/gpt-5.4 (medium) → zai-coding-plan\|opencode/glm-5 → opencode/big-pickle | Primary coding agent. Exact runtime chain from `src/shared/model-requirements.ts`. |
| **Metis** | Plan review | anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → openai\|github-copilot\|opencode/gpt-5.4 (high) → opencode-go/glm-5 → kimi-for-coding/k2p5 | Reviews Prometheus plans for gaps. Exact runtime chain from `src/shared/model-requirements.ts`. | | **Metis** | Plan review | anthropic\|github-copilot\|opencode/claude-opus-4-7 (max) → openai\|github-copilot\|opencode/gpt-5.4 (high) → opencode-go/glm-5 → kimi-for-coding/k2p5 | Reviews Prometheus plans for gaps. Exact runtime chain from `src/shared/model-requirements.ts`. |
**Dual-Prompt Agents** (auto-switch between Claude and GPT prompts): **Dual-Prompt Agents** (auto-switch between Claude and GPT prompts):
@@ -334,7 +341,7 @@ Priority: **Claude > GPT > Claude-like models**
| Agent | Role | Default Chain | GPT Prompt? | | Agent | Role | Default Chain | GPT Prompt? |
| -------------- | ----------------- | ---------------------------------------------------------- | ---------------------------------------------------------------- | | -------------- | ----------------- | ---------------------------------------------------------- | ---------------------------------------------------------------- |
| **Prometheus** | Strategic planner | anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → openai\|github-copilot\|opencode/gpt-5.4 (high) → opencode-go/glm-5 → google\|github-copilot\|opencode/gemini-3.1-pro | Yes — XML-tagged, principle-driven (~300 lines vs ~1,100 Claude) | | **Prometheus** | Strategic planner | anthropic\|github-copilot\|opencode/claude-opus-4-7 (max) → openai\|github-copilot\|opencode/gpt-5.4 (high) → opencode-go/glm-5 → google\|github-copilot\|opencode/gemini-3.1-pro | Yes — XML-tagged, principle-driven (~300 lines vs ~1,100 Claude) |
| **Atlas** | Todo orchestrator | anthropic\|github-copilot\|opencode/claude-sonnet-4-6 → opencode-go/kimi-k2.5 → openai\|github-copilot\|opencode/gpt-5.4 (medium) → opencode-go/minimax-m2.7 | Yes - GPT-optimized todo management | | **Atlas** | Todo orchestrator | anthropic\|github-copilot\|opencode/claude-sonnet-4-6 → opencode-go/kimi-k2.5 → openai\|github-copilot\|opencode/gpt-5.4 (medium) → opencode-go/minimax-m2.7 | Yes - GPT-optimized todo management |
**GPT-Native Agents** (built for GPT, don't override to Claude): **GPT-Native Agents** (built for GPT, don't override to Claude):
@@ -342,8 +349,8 @@ Priority: **Claude > GPT > Claude-like models**
| Agent | Role | Default Chain | Notes | | Agent | Role | Default Chain | Notes |
| -------------- | ---------------------- | -------------------------------------- | ------------------------------------------------------ | | -------------- | ---------------------- | -------------------------------------- | ------------------------------------------------------ |
| **Hephaestus** | Deep autonomous worker | GPT-5.4 (medium) only | "Codex on steroids." No fallback. Requires GPT access. | | **Hephaestus** | Deep autonomous worker | GPT-5.4 (medium) only | "Codex on steroids." No fallback. Requires GPT access. |
| **Oracle** | Architecture/debugging | openai\|github-copilot\|opencode/gpt-5.4 (high) → google\|github-copilot\|opencode/gemini-3.1-pro (high) → anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → opencode-go/glm-5 | High-IQ strategic backup. GPT preferred. | | **Oracle** | Architecture/debugging | openai\|github-copilot\|opencode/gpt-5.4 (high) → google\|github-copilot\|opencode/gemini-3.1-pro (high) → anthropic\|github-copilot\|opencode/claude-opus-4-7 (max) → opencode-go/glm-5 | High-IQ strategic backup. GPT preferred. |
| **Momus** | High-accuracy reviewer | openai\|github-copilot\|opencode/gpt-5.4 (xhigh) → anthropic\|github-copilot\|opencode/claude-opus-4-6 (max) → google\|github-copilot\|opencode/gemini-3.1-pro (high) → opencode-go/glm-5 | Verification agent. GPT preferred. | | **Momus** | High-accuracy reviewer | openai\|github-copilot\|opencode/gpt-5.4 (xhigh) → anthropic\|github-copilot\|opencode/claude-opus-4-7 (max) → google\|github-copilot\|opencode/gemini-3.1-pro (high) → opencode-go/glm-5 | Verification agent. GPT preferred. |
**Utility Agents** (speed over intelligence): **Utility Agents** (speed over intelligence):
@@ -456,7 +463,7 @@ gh api --silent --method PUT /user/starred/code-yeongyu/oh-my-openagent >/dev/nu
Tell the user of following: Tell the user of following:
1. **Sisyphus agent strongly recommends Opus 4.6 model. Using other models may result in significantly degraded experience.** 1. **Sisyphus agent strongly recommends Opus 4.7 model. Using other models may result in significantly degraded experience.**
2. **Feeling lazy?** Just include `ultrawork` (or `ulw`) in your prompt. That's it. The agent figures out the rest. 2. **Feeling lazy?** Just include `ultrawork` (or `ulw`) in your prompt. That's it. The agent figures out the rest.
+32 -29
View File
@@ -15,6 +15,7 @@ Oh My OpenAgent's orchestration system transforms a simple AI agent into a coord
**Decision Flow:** **Decision Flow:**
``` ```
Is it a quick fix or simple task? Is it a quick fix or simple task?
└─ YES → Just prompt normally └─ YES → Just prompt normally
└─ NO → Is explaining the full context tedious? └─ NO → Is explaining the full context tedious?
@@ -34,21 +35,21 @@ The orchestration system uses a three-layer architecture that solves context ove
flowchart TB flowchart TB
subgraph Planning["Planning Layer (Human + Prometheus)"] subgraph Planning["Planning Layer (Human + Prometheus)"]
User[(" User")] User[(" User")]
Prometheus[" Prometheus<br/>(Planner)<br/>Claude Opus 4.6"] Prometheus[" Prometheus<br/>(Planner)<br/>claude-opus-4-7 / gpt-5.4 / glm-5"]
Metis[" Metis<br/>(Consultant)<br/>Claude Opus 4.6"] Metis[" Metis<br/>(Consultant)<br/>claude-opus-4-7 / gpt-5.4 / glm-5"]
Momus[" Momus<br/>(Reviewer)<br/>GPT-5.4"] Momus[" Momus<br/>(Reviewer)<br/>gpt-5.4 / claude-opus-4-7 / gemini-3.1-pro / glm-5"]
end end
subgraph Execution["Execution Layer (Orchestrator)"] subgraph Execution["Execution Layer (Orchestrator)"]
Orchestrator[" Atlas<br/>(Conductor)<br/>Claude Sonnet 4.6"] Orchestrator[" Atlas<br/>(Conductor)<br/>claude-sonnet-4-6 / kimi-k2.5 / gpt-5.4 / minimax-m2.7"]
end end
subgraph Workers["Worker Layer (Specialized Agents)"] subgraph Workers["Worker Layer (Specialized Agents)"]
Junior[" Sisyphus-Junior<br/>(Task Executor)<br/>Claude Sonnet 4.6"] Junior[" Sisyphus-Junior<br/>(Task Executor)<br/>claude-sonnet-4-6 / kimi-k2.5 / gpt-5.4 / minimax-m2.7"]
Oracle[" Oracle<br/>(Architecture)<br/>GPT-5.4"] Oracle[" Oracle<br/>(Architecture)<br/>gpt-5.4 / gemini-3.1-pro / claude-opus-4-7 / glm-5"]
Explore[" Explore<br/>(Codebase Grep)<br/>Grok Code"] Explore[" Explore<br/>(Codebase Grep)<br/>grok-code-fast-1 / minimax-m2.7-highspeed / claude-haiku-4-5"]
Librarian[" Librarian<br/>(Docs/OSS)<br/>Gemini 3 Flash"] Librarian[" Librarian<br/>(Docs/OSS)<br/>minimax-m2.7 / minimax-m2.7-highspeed / claude-haiku-4-5"]
Frontend[" Frontend<br/>(UI/UX)<br/>Gemini 3.1 Pro"] Frontend[" visual-engineering<br/>(category + frontend-ui-ux)<br/>gemini-3.1-pro / glm-5 / claude-opus-4-7"]
end end
User -->|"Describe work"| Prometheus User -->|"Describe work"| Prometheus
@@ -61,11 +62,11 @@ flowchart TB
User -->|"/start-work"| Orchestrator User -->|"/start-work"| Orchestrator
Plan -->|"Read"| Orchestrator Plan -->|"Read"| Orchestrator
Orchestrator -->|"task(category)"| Junior Orchestrator -->|"task(category=deep/quick/unspecified-*)"| Junior
Orchestrator -->|"task(agent)"| Oracle Orchestrator -->|"call_omo_agent(subagent_type=oracle)"| Oracle
Orchestrator -->|"task(agent)"| Explore Orchestrator -->|"call_omo_agent(subagent_type=explore)"| Explore
Orchestrator -->|"task(agent)"| Librarian Orchestrator -->|"call_omo_agent(subagent_type=librarian)"| Librarian
Orchestrator -->|"task(agent)"| Frontend Orchestrator -->|"task(category=visual-engineering, load_skills=[frontend-ui-ux])"| Frontend
Junior -->|"Results + Learnings"| Orchestrator Junior -->|"Results + Learnings"| Orchestrator
Oracle -->|"Advice"| Orchestrator Oracle -->|"Advice"| Orchestrator
@@ -74,6 +75,8 @@ flowchart TB
Frontend -->|"UI code"| Orchestrator Frontend -->|"UI code"| Orchestrator
``` ```
Model labels above show the current fallback stacks from `src/shared/model-requirements.ts`, not marketing names.
--- ---
## Planning: Prometheus + Metis + Momus ## Planning: Prometheus + Metis + Momus
@@ -240,7 +243,7 @@ Junior is the workhorse that actually writes code. Key characteristics:
- **Verified**: Must pass lsp_diagnostics before completion - **Verified**: Must pass lsp_diagnostics before completion
- **Constrained**: Cannot modify plan files (READ-ONLY) - **Constrained**: Cannot modify plan files (READ-ONLY)
**Why Sonnet is Sufficient:** **Why the fallback chain is sufficient:**
Junior doesn't need to be the smartest - it needs to be reliable. With: Junior doesn't need to be the smartest - it needs to be reliable. With:
@@ -249,7 +252,7 @@ Junior doesn't need to be the smartest - it needs to be reliable. With:
3. Clear MUST DO / MUST NOT DO constraints 3. Clear MUST DO / MUST NOT DO constraints
4. Verification requirements 4. Verification requirements
Even a mid-tier model executes precisely. The intelligence is in the **system**, not individual agents. Even a mid-tier execution model works when the harness is strict. The current fallback order is `claude-sonnet-4-6``kimi-k2.5``gpt-5.4``minimax-m2.7``big-pickle`. The intelligence is in the **system**, not a single worker model.
### System Reminder Mechanism ### System Reminder Mechanism
@@ -279,7 +282,7 @@ This "boulder pushing" mechanism is why the system is named after Sisyphus.
```typescript ```typescript
// OLD: Model name creates distributional bias // OLD: Model name creates distributional bias
task({ agent: "gpt-5.4", prompt: "..." }); // Model knows its limitations task({ agent: "gpt-5.4", prompt: "..." }); // Model knows its limitations
task({ agent: "claude-opus-4.6", prompt: "..." }); // Different self-perception task({ agent: "claude-opus-4-7", prompt: "..." }); // Different self-perception
``` ```
**The Solution: Semantic Categories:** **The Solution: Semantic Categories:**
@@ -293,16 +296,16 @@ task({ category: "quick", prompt: "..." }); // "Just get it done fast"
### Built-in Categories ### Built-in Categories
| Category | Model | When to Use | | Category | Default config | Runtime fallback order | When to Use |
| -------------------- | ---------------------- | ----------------------------------------------------------- | | -------------------- | ------------------------------- | -------------------------------------------------------------------------------------- | ----------------------------------------------------------- |
| `visual-engineering` | Gemini 3.1 Pro | Frontend, UI/UX, design, styling, animation | | `visual-engineering` | `google/gemini-3.1-pro high` | `gemini-3.1-pro``glm-5``claude-opus-4-7``glm-5``k2p5` | Frontend, UI/UX, design, styling, animation |
| `ultrabrain` | GPT-5.4 (xhigh) | Deep logical reasoning, complex architecture decisions | | `ultrabrain` | `openai/gpt-5.4 xhigh` | `gpt-5.4``gemini-3.1-pro``claude-opus-4-7``glm-5` | Deep logical reasoning, complex architecture decisions |
| `artistry` | Gemini 3.1 Pro (high) | Highly creative or artistic tasks, novel ideas | | `deep` | `openai/gpt-5.4 medium` | `gpt-5.4``claude-opus-4-7``gemini-3.1-pro` | Goal-oriented autonomous problem-solving, thorough research |
| `quick` | GPT-5.4 Mini | Trivial tasks - single file changes, typo fixes | | `artistry` | `google/gemini-3.1-pro high` | `gemini-3.1-pro``claude-opus-4-7``gpt-5.4` | Highly creative or artistic tasks, novel ideas |
| `deep` | GPT-5.4 (medium) | Goal-oriented autonomous problem-solving, thorough research | | `quick` | `openai/gpt-5.4-mini` | `gpt-5.4-mini``claude-haiku-4-5``gemini-3-flash``minimax-m2.7``gpt-5-nano` | Trivial tasks, single file changes, typo fixes |
| `unspecified-low` | Claude Sonnet 4.6 | Tasks that don't fit other categories, low effort | | `unspecified-low` | `anthropic/claude-sonnet-4-6` | `claude-sonnet-4-6``gpt-5.3-codex``kimi-k2.5``gemini-3-flash``minimax-m2.7` | Tasks that don't fit other categories, low effort |
| `unspecified-high` | Claude Opus 4.6 (max) | Tasks that don't fit other categories, high effort | | `unspecified-high` | `anthropic/claude-opus-4-7 max` | `claude-opus-4-7``gpt-5.4``glm-5``k2p5``kimi-k2.5` | Tasks that don't fit other categories, high effort |
| `writing` | Gemini 3 Flash | Documentation, prose, technical writing | | `writing` | `kimi-for-coding/k2p5` | `gemini-3-flash``kimi-k2.5``claude-sonnet-4-6``minimax-m2.7` | Documentation, prose, technical writing |
### Skills: Domain-Specific Instructions ### Skills: Domain-Specific Instructions
@@ -317,7 +320,7 @@ task(
); );
task( task(
(category = "general"), (category = "deep"),
(load_skills = ["playwright"]), // Adds browser automation expertise (load_skills = ["playwright"]), // Adds browser automation expertise
(prompt = "..."), (prompt = "..."),
); );
@@ -420,7 +423,7 @@ Atlas is automatically activated when you run `/start-work`. You don't need to m
| Aspect | Hephaestus | Sisyphus + `ulw` / `ultrawork` | | Aspect | Hephaestus | Sisyphus + `ulw` / `ultrawork` |
| --------------- | ------------------------------------------ | ---------------------------------------------------- | | --------------- | ------------------------------------------ | ---------------------------------------------------- |
| **Model** | GPT-5.4 (medium reasoning) | Claude Opus 4.6 / GPT-5.4 / GLM 5 depending on setup | | **Model** | `gpt-5.4` (`medium`) | `claude-opus-4-7` / `kimi-k2.5` / `gpt-5.4` / `glm-5` depending on setup |
| **Approach** | Autonomous deep worker | Keyword-activated ultrawork mode | | **Approach** | Autonomous deep worker | Keyword-activated ultrawork mode |
| **Best For** | Complex architectural work, deep reasoning | General complex tasks, "just do it" scenarios | | **Best For** | Complex architectural work, deep reasoning | General complex tasks, "just do it" scenarios |
| **Planning** | Self-plans during execution | Uses Prometheus plans if available | | **Planning** | Self-plans during execution | Uses Prometheus plans if available |
+25 -14
View File
@@ -66,7 +66,7 @@ User Request
└─→ [Category-based agents] — Specialized by task type └─→ [Category-based agents] — Specialized by task type
``` ```
When Sisyphus delegates to a subagent, it doesn't pick a model name. It picks a **category**`visual-engineering`, `ultrabrain`, `quick`, `deep`. The category automatically maps to the right model. You touch nothing. When Sisyphus delegates to a subagent, it doesn't pick a model name. It picks a **category**`visual-engineering`, `ultrabrain`, `deep`, `artistry`, `quick`, `unspecified-low`, `unspecified-high`, `writing`. The category automatically maps to the right model. You touch nothing.
For a deep dive into how agents collaborate, see the [Orchestration System Guide](./orchestration.md). For a deep dive into how agents collaborate, see the [Orchestration System Guide](./orchestration.md).
@@ -82,12 +82,11 @@ Sisyphus is your main orchestrator. He plans, delegates to specialists, and driv
**Recommended models:** **Recommended models:**
- **Claude Opus 4.6** — Best overall experience. Sisyphus was built with Claude-optimized prompts. - **Claude Opus 4.7** — Best overall experience. Sisyphus was built with Claude-optimized prompts.
- **Claude Sonnet 4.6** — Good balance of capability and cost.
- **Kimi K2.5** — Great Claude-like alternative. Many users run this combo exclusively. - **Kimi K2.5** — Great Claude-like alternative. Many users run this combo exclusively.
- **GLM 5** — Solid option, especially via Z.ai. - **GLM 5** — Solid option, especially via Z.ai.
Sisyphus still works best on Claude-family models, Kimi, and GLM. GPT-5.4 now has a dedicated prompt path, but older GPT models are still a poor fit and should route to Hephaestus instead. Sisyphus works best on Claude Opus 4.7, Kimi K2.5, and GLM 5. GPT-5.4 now has a dedicated prompt path, but older GPT models are still a poor fit and should route to Hephaestus instead.
### Hephaestus: The Legitimate Craftsman ### Hephaestus: The Legitimate Craftsman
@@ -101,7 +100,7 @@ Use Hephaestus when you need deep architectural reasoning, complex debugging acr
- **Multi-model orchestration.** Pure Codex is single-model. OmO routes different tasks to different models automatically. GPT for deep reasoning. Gemini for frontend. GPT-5.4 Mini for speed. The right brain for the right job. - **Multi-model orchestration.** Pure Codex is single-model. OmO routes different tasks to different models automatically. GPT for deep reasoning. Gemini for frontend. GPT-5.4 Mini for speed. The right brain for the right job.
- **Background agents.** Fire 5+ agents in parallel. Something Codex simply cannot do. While one agent writes code, another researches patterns, another checks documentation. Like a real dev team. - **Background agents.** Fire 5+ agents in parallel. Something Codex simply cannot do. While one agent writes code, another researches patterns, another checks documentation. Like a real dev team.
- **Category system.** Tasks are routed by intent, not model name. `visual-engineering` gets Gemini. `ultrabrain` gets GPT-5.4. `quick` gets GPT-5.4 Mini. No manual juggling. - **Category system.** Tasks are routed by intent, not model name. `visual-engineering` gets Gemini. `ultrabrain` gets GPT-5.4 xhigh. `deep` gets GPT-5.4. `artistry` gets Gemini. `quick` gets GPT-5.4 Mini. `unspecified-low` gets fast cheap models. `unspecified-high` gets Claude Opus. `writing` gets prose-optimized models. No manual juggling.
- **Accumulated wisdom.** Subagents learn from previous results. Conventions discovered in task 1 are passed to task 5. Mistakes made early aren't repeated. The system gets smarter as it works. - **Accumulated wisdom.** Subagents learn from previous results. Conventions discovered in task 1 are passed to task 5. Mistakes made early aren't repeated. The system gets smarter as it works.
### Prometheus: The Strategic Planner ### Prometheus: The Strategic Planner
@@ -174,7 +173,7 @@ You can override specific agents or categories in your config:
// Main orchestrator: Claude Opus or Kimi K2.5 work best // Main orchestrator: Claude Opus or Kimi K2.5 work best
"sisyphus": { "sisyphus": {
"model": "kimi-for-coding/k2p5", "model": "kimi-for-coding/k2p5",
"ultrawork": { "model": "anthropic/claude-opus-4-6", "variant": "max" }, "ultrawork": { "model": "anthropic/claude-opus-4-7", "variant": "max" },
}, },
// Research agents: cheaper models are fine // Research agents: cheaper models are fine
@@ -186,20 +185,32 @@ You can override specific agents or categories in your config:
}, },
"categories": { "categories": {
// Frontend work: Gemini dominates visual tasks // Frontend/UI work: Gemini dominates visual tasks
"visual-engineering": { "visual-engineering": {
"model": "google/gemini-3.1-pro", "model": "google/gemini-3.1-pro",
"variant": "high", "variant": "high",
}, },
// General high-effort work // Hard logic and architecture: GPT-5.4 xhigh
"unspecified-high": { "model": "anthropic/claude-opus-4-6", "variant": "max" }, "ultrabrain": { "model": "openai/gpt-5.4", "variant": "xhigh" },
// Quick tasks: use GPT-5.4-mini (fast and cheap) // Autonomous research and execution
"deep": { "model": "openai/gpt-5.4", "variant": "high" },
// Creative and design work
"artistry": { "model": "google/gemini-3.1-pro", "variant": "high" },
// Quick tasks: fast and cheap
"quick": { "model": "openai/gpt-5.4-mini" }, "quick": { "model": "openai/gpt-5.4-mini" },
// Deep reasoning: GPT-5.4 // Low-effort fallback: cheapest available
"ultrabrain": { "model": "openai/gpt-5.4", "variant": "xhigh" }, "unspecified-low": { "model": "openai/gpt-5.4-mini" },
// High-effort fallback: best available
"unspecified-high": { "model": "anthropic/claude-opus-4-7", "variant": "max" },
// Prose and documentation
"writing": { "model": "anthropic/claude-opus-4-7", "variant": "high" },
}, },
} }
``` ```
@@ -208,14 +219,14 @@ You can override specific agents or categories in your config:
**Claude-like models** (instruction-following, structured output): **Claude-like models** (instruction-following, structured output):
- Claude Opus 4.6, Claude Sonnet 4.6, Claude Haiku 4.5 - Claude Opus 4.7, Claude Haiku 4.5
- Kimi K2.5 — behaves very similarly to Claude - Kimi K2.5 — behaves very similarly to Claude
- GLM 5 — Claude-like behavior, good for broad tasks - GLM 5 — Claude-like behavior, good for broad tasks
**GPT models** (explicit reasoning, principle-driven): **GPT models** (explicit reasoning, principle-driven):
- GPT-5.4 — deep coding powerhouse, required for Hephaestus and default for Oracle - GPT-5.4 — deep coding powerhouse, required for Hephaestus and default for Oracle
- GPT-5-Nano — ultra-cheap, fast utility tasks - GPT-5.4 Mini — fast and cheap utility tasks
**Different-behavior models**: **Different-behavior models**:
+1
View File
@@ -57,6 +57,7 @@ bunx oh-my-opencode install
| `--zai-coding-plan <no\|yes>` | Z.ai Coding Plan subscription | | `--zai-coding-plan <no\|yes>` | Z.ai Coding Plan subscription |
| `--kimi-for-coding <no\|yes>` | Kimi for Coding subscription | | `--kimi-for-coding <no\|yes>` | Kimi for Coding subscription |
| `--opencode-go <no\|yes>` | OpenCode Go subscription | | `--opencode-go <no\|yes>` | OpenCode Go subscription |
| `--vercel-ai-gateway <no\|yes>` | Vercel AI Gateway: no, yes (default: no) |
| `--skip-auth` | Skip authentication setup hints | | `--skip-auth` | Skip authentication setup hints |
Anonymous telemetry uses PostHog with a hashed installation identifier. Disable it with `OMO_SEND_ANONYMOUS_TELEMETRY=0` or `OMO_DISABLE_POSTHOG=1`. See [Privacy Policy](../legal/privacy-policy.md). Anonymous telemetry uses PostHog with a hashed installation identifier. Disable it with `OMO_SEND_ANONYMOUS_TELEMETRY=0` or `OMO_DISABLE_POSTHOG=1`. See [Privacy Policy](../legal/privacy-policy.md).
+21 -21
View File
@@ -78,7 +78,7 @@ Here's a practical starting configuration:
// Main orchestrator: Claude Opus or Kimi K2.5 work best // Main orchestrator: Claude Opus or Kimi K2.5 work best
"sisyphus": { "sisyphus": {
"model": "kimi-for-coding/k2p5", "model": "kimi-for-coding/k2p5",
"ultrawork": { "model": "anthropic/claude-opus-4-6", "variant": "max" }, "ultrawork": { "model": "anthropic/claude-opus-4-7", "variant": "max" },
}, },
// Research agents: cheap fast models are fine // Research agents: cheap fast models are fine
@@ -102,7 +102,7 @@ Here's a practical starting configuration:
"unspecified-low": { "model": "anthropic/claude-sonnet-4-6" }, "unspecified-low": { "model": "anthropic/claude-sonnet-4-6" },
// unspecified-high - complex work // unspecified-high - complex work
"unspecified-high": { "model": "anthropic/claude-opus-4-6", "variant": "max" }, "unspecified-high": { "model": "anthropic/claude-opus-4-7", "variant": "max" },
// writing - docs/prose // writing - docs/prose
"writing": { "model": "google/gemini-3-flash" }, "writing": { "model": "google/gemini-3-flash" },
@@ -130,7 +130,7 @@ Here's a practical starting configuration:
"zai-coding-plan": 10, "zai-coding-plan": 10,
}, },
"modelConcurrency": { "modelConcurrency": {
"anthropic/claude-opus-4-6": 2, "anthropic/claude-opus-4-7": 2,
"opencode/gpt-5-nano": 20, "opencode/gpt-5-nano": 20,
}, },
}, },
@@ -146,7 +146,7 @@ Here's a practical starting configuration:
### Agents ### Agents
Override built-in agent settings. Available agents: `sisyphus`, `hephaestus`, `prometheus`, `oracle`, `librarian`, `explore`, `multimodal-looker`, `metis`, `momus`, `atlas`. Override built-in agent settings. Available agents: `sisyphus`, `hephaestus`, `prometheus`, `oracle`, `librarian`, `explore`, `multimodal-looker`, `metis`, `momus`, `atlas`, `sisyphus-junior`.
```json ```json
{ {
@@ -229,7 +229,7 @@ Control what tools an agent can use:
{ {
"agents": { "agents": {
"sisyphus": { "sisyphus": {
"model": "anthropic/claude-opus-4-6", "model": "anthropic/claude-opus-4-7",
"fallback_models": [ "fallback_models": [
// Simple string fallback // Simple string fallback
"openai/gpt-5.4", "openai/gpt-5.4",
@@ -293,7 +293,7 @@ Domain-specific model delegation used by the `task()` tool. When Sisyphus delega
| `artistry` | `google/gemini-3.1-pro` (high) | Creative/unconventional approaches | | `artistry` | `google/gemini-3.1-pro` (high) | Creative/unconventional approaches |
| `quick` | `openai/gpt-5.4-mini` | Trivial tasks, typo fixes, single-file changes | | `quick` | `openai/gpt-5.4-mini` | Trivial tasks, typo fixes, single-file changes |
| `unspecified-low` | `anthropic/claude-sonnet-4-6` | General tasks, low effort | | `unspecified-low` | `anthropic/claude-sonnet-4-6` | General tasks, low effort |
| `unspecified-high` | `anthropic/claude-opus-4-6` (max) | General tasks, high effort | | `unspecified-high` | `anthropic/claude-opus-4-7` (max) | General tasks, high effort |
| `writing` | `google/gemini-3-flash` | Documentation, prose, technical writing | | `writing` | `google/gemini-3-flash` | Documentation, prose, technical writing |
> **Note**: Built-in defaults only apply if the category is present in your config. Otherwise the system default model is used. > **Note**: Built-in defaults only apply if the category is present in your config. Otherwise the system default model is used.
@@ -355,28 +355,28 @@ Capability data comes from provider runtime metadata first. OmO also ships bundl
| Agent | Default Model | Provider Priority | | Agent | Default Model | Provider Priority |
| --------------------- | ------------------- | ---------------------------------------------------------------------------- | | --------------------- | ------------------- | ---------------------------------------------------------------------------- |
| **Sisyphus** | `claude-opus-4-6` | `anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``opencode-go/kimi-k2.5``kimi-for-coding/k2p5``opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix/kimi-k2.5``openai\|github-copilot\|opencode/gpt-5.4 (medium)``zai-coding-plan\|opencode/glm-5``opencode/big-pickle` | | **Sisyphus** | `claude-opus-4-7` | `anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``opencode-go/kimi-k2.5``kimi-for-coding/k2p5``opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix/kimi-k2.5``openai\|github-copilot\|opencode/gpt-5.4 (medium)``zai-coding-plan\|opencode/glm-5``opencode/big-pickle` |
| **Hephaestus** | `gpt-5.4` | `gpt-5.4 (medium)` | | **Hephaestus** | `gpt-5.4` | `gpt-5.4 (medium)` |
| **oracle** | `gpt-5.4` | `openai\|github-copilot\|opencode/gpt-5.4 (high)``google\|github-copilot\|opencode/gemini-3.1-pro (high)``anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``opencode-go/glm-5` | | **oracle** | `gpt-5.4` | `openai\|github-copilot\|opencode/gpt-5.4 (high)``google\|github-copilot\|opencode/gemini-3.1-pro (high)``anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``opencode-go/glm-5` |
| **librarian** | `minimax-m2.7` | `opencode-go/minimax-m2.7``opencode/minimax-m2.7-highspeed``anthropic\|opencode/claude-haiku-4-5``opencode/gpt-5-nano` | | **librarian** | `minimax-m2.7` | `opencode-go/minimax-m2.7``opencode/minimax-m2.7-highspeed``anthropic\|opencode/claude-haiku-4-5``opencode/gpt-5-nano` |
| **explore** | `grok-code-fast-1` | `github-copilot\|xai/grok-code-fast-1``opencode-go/minimax-m2.7-highspeed``opencode/minimax-m2.7``anthropic\|opencode/claude-haiku-4-5``opencode/gpt-5-nano` | | **explore** | `grok-code-fast-1` | `github-copilot\|xai/grok-code-fast-1``opencode-go/minimax-m2.7-highspeed``opencode/minimax-m2.7``anthropic\|opencode/claude-haiku-4-5``opencode/gpt-5-nano` |
| **multimodal-looker** | `gpt-5.4` | `openai\|opencode/gpt-5.4 (medium)``opencode-go/kimi-k2.5``zai-coding-plan/glm-4.6v``openai\|github-copilot\|opencode/gpt-5-nano` | | **multimodal-looker** | `gpt-5.4` | `openai\|opencode/gpt-5.4 (medium)``opencode-go/kimi-k2.5``zai-coding-plan/glm-4.6v``openai\|github-copilot\|opencode/gpt-5-nano` |
| **Prometheus** | `claude-opus-4-6` | `anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``openai\|github-copilot\|opencode/gpt-5.4 (high)``opencode-go/glm-5``google\|github-copilot\|opencode/gemini-3.1-pro` | | **Prometheus** | `claude-opus-4-7` | `anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``openai\|github-copilot\|opencode/gpt-5.4 (high)``opencode-go/glm-5``google\|github-copilot\|opencode/gemini-3.1-pro` |
| **Metis** | `claude-opus-4-6` | `anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``openai\|github-copilot\|opencode/gpt-5.4 (high)``opencode-go/glm-5``kimi-for-coding/k2p5` | | **Metis** | `claude-opus-4-7` | `anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``openai\|github-copilot\|opencode/gpt-5.4 (high)``opencode-go/glm-5``kimi-for-coding/k2p5` |
| **Momus** | `gpt-5.4` | `openai\|github-copilot\|opencode/gpt-5.4 (xhigh)``anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``google\|github-copilot\|opencode/gemini-3.1-pro (high)``opencode-go/glm-5` | | **Momus** | `gpt-5.4` | `openai\|github-copilot\|opencode/gpt-5.4 (xhigh)``anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``google\|github-copilot\|opencode/gemini-3.1-pro (high)``opencode-go/glm-5` |
| **Atlas** | `claude-sonnet-4-6` | `anthropic\|github-copilot\|opencode/claude-sonnet-4-6``opencode-go/kimi-k2.5``openai\|github-copilot\|opencode/gpt-5.4 (medium)``opencode-go/minimax-m2.7` | | **Atlas** | `claude-sonnet-4-6` | `anthropic\|github-copilot\|opencode/claude-sonnet-4-6``opencode-go/kimi-k2.5``openai\|github-copilot\|opencode/gpt-5.4 (medium)``opencode-go/minimax-m2.7` |
#### Category Provider Chains #### Category Provider Chains
| Category | Default Model | Provider Priority | | Category | Default Model | Provider Priority |
| ---------------------- | ------------------- | -------------------------------------------------------------- | | ---------------------- | ------------------- | -------------------------------------------------------------- |
| **visual-engineering** | `gemini-3.1-pro` | `google\|github-copilot\|opencode/gemini-3.1-pro (high)``zai-coding-plan\|opencode/glm-5``anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``opencode-go/glm-5``kimi-for-coding/k2p5` | | **visual-engineering** | `gemini-3.1-pro` | `google\|github-copilot\|opencode/gemini-3.1-pro (high)``zai-coding-plan\|opencode/glm-5``anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``opencode-go/glm-5``kimi-for-coding/k2p5` |
| **ultrabrain** | `gpt-5.4` | `openai\|opencode/gpt-5.4 (xhigh)``google\|github-copilot\|opencode/gemini-3.1-pro (high)``anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``opencode-go/glm-5` | | **ultrabrain** | `gpt-5.4` | `openai\|opencode/gpt-5.4 (xhigh)``google\|github-copilot\|opencode/gemini-3.1-pro (high)``anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``opencode-go/glm-5` |
| **deep** | `gpt-5.4` | `openai\|github-copilot\|venice\|opencode/gpt-5.4 (medium)``anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``google\|github-copilot\|opencode/gemini-3.1-pro (high)` | | **deep** | `gpt-5.4` | `openai\|github-copilot\|venice\|opencode/gpt-5.4 (medium)``anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``google\|github-copilot\|opencode/gemini-3.1-pro (high)` |
| **artistry** | `gemini-3.1-pro` | `google\|github-copilot\|opencode/gemini-3.1-pro (high)``anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``openai\|github-copilot\|opencode/gpt-5.4` | | **artistry** | `gemini-3.1-pro` | `google\|github-copilot\|opencode/gemini-3.1-pro (high)``anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``openai\|github-copilot\|opencode/gpt-5.4` |
| **quick** | `gpt-5.4-mini` | `openai\|github-copilot\|opencode/gpt-5.4-mini``anthropic\|github-copilot\|opencode/claude-haiku-4-5``google\|github-copilot\|opencode/gemini-3-flash``opencode-go/minimax-m2.7``opencode/gpt-5-nano` | | **quick** | `gpt-5.4-mini` | `openai\|github-copilot\|opencode/gpt-5.4-mini``anthropic\|github-copilot\|opencode/claude-haiku-4-5``google\|github-copilot\|opencode/gemini-3-flash``opencode-go/minimax-m2.7``opencode/gpt-5-nano` |
| **unspecified-low** | `claude-sonnet-4-6` | `anthropic\|github-copilot\|opencode/claude-sonnet-4-6``openai\|opencode/gpt-5.3-codex (medium)``opencode-go/kimi-k2.5``google\|github-copilot\|opencode/gemini-3-flash``opencode-go/minimax-m2.7` | | **unspecified-low** | `claude-sonnet-4-6` | `anthropic\|github-copilot\|opencode/claude-sonnet-4-6``openai\|opencode/gpt-5.3-codex (medium)``opencode-go/kimi-k2.5``google\|github-copilot\|opencode/gemini-3-flash``opencode-go/minimax-m2.7` |
| **unspecified-high** | `claude-opus-4-6` | `anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``openai\|github-copilot\|opencode/gpt-5.4 (high)``zai-coding-plan\|opencode/glm-5``kimi-for-coding/k2p5``opencode-go/glm-5``opencode/kimi-k2.5``opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix/kimi-k2.5` | | **unspecified-high** | `claude-opus-4-7` | `anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``openai\|github-copilot\|opencode/gpt-5.4 (high)``zai-coding-plan\|opencode/glm-5``kimi-for-coding/k2p5``opencode-go/glm-5``opencode/kimi-k2.5``opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix/kimi-k2.5` |
| **writing** | `gemini-3-flash` | `google\|github-copilot\|opencode/gemini-3-flash``opencode-go/kimi-k2.5``anthropic\|github-copilot\|opencode/claude-sonnet-4-6``opencode-go/minimax-m2.7` | | **writing** | `gemini-3-flash` | `google\|github-copilot\|opencode/gemini-3-flash``opencode-go/kimi-k2.5``anthropic\|github-copilot\|opencode/claude-sonnet-4-6``opencode-go/minimax-m2.7` |
Run `bunx oh-my-opencode doctor --verbose` to see effective model resolution for your config. Run `bunx oh-my-opencode doctor --verbose` to see effective model resolution for your config.
@@ -395,7 +395,7 @@ Control parallel agent execution and concurrency limits.
"defaultConcurrency": 5, "defaultConcurrency": 5,
"staleTimeoutMs": 180000, "staleTimeoutMs": 180000,
"providerConcurrency": { "anthropic": 3, "openai": 5, "google": 10 }, "providerConcurrency": { "anthropic": 3, "openai": 5, "google": 10 },
"modelConcurrency": { "anthropic/claude-opus-4-6": 2 } "modelConcurrency": { "anthropic/claude-opus-4-7": 2 }
} }
} }
``` ```
@@ -678,7 +678,7 @@ Define `fallback_models` per agent or category:
{ {
"agents": { "agents": {
"sisyphus": { "sisyphus": {
"model": "anthropic/claude-opus-4-6", "model": "anthropic/claude-opus-4-7",
"fallback_models": [ "fallback_models": [
"openai/gpt-5.4", "openai/gpt-5.4",
{ {
@@ -697,7 +697,7 @@ Define `fallback_models` per agent or category:
{ {
"agents": { "agents": {
"sisyphus": { "sisyphus": {
"model": "anthropic/claude-opus-4-6", "model": "anthropic/claude-opus-4-7",
"fallback_models": [ "fallback_models": [
"openai/gpt-5.4", "openai/gpt-5.4",
{ {
@@ -798,7 +798,7 @@ Mix string entries and object entries when only some fallback models need specia
{ {
"agents": { "agents": {
"sisyphus": { "sisyphus": {
"model": "anthropic/claude-opus-4-6", "model": "anthropic/claude-opus-4-7",
"fallback_models": [ "fallback_models": [
"openai/gpt-5.4", "openai/gpt-5.4",
{ {
@@ -832,7 +832,7 @@ Mix string entries and object entries when only some fallback models need specia
"maxTokens": 12000 "maxTokens": 12000
}, },
{ {
"model": "anthropic/claude-opus-4-6", "model": "anthropic/claude-opus-4-7",
"variant": "max", "variant": "max",
"temperature": 0.2 "temperature": 0.2
}, },
+10 -9
View File
@@ -10,9 +10,9 @@ Core-agent tab cycling is deterministic via injected runtime order field. The fi
| Agent | Model | Purpose | | Agent | Model | Purpose |
| --------------------- | ------------------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | --------------------- | ------------------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **Sisyphus** | `claude-opus-4-6` | The default orchestrator. Plans, delegates, and executes complex tasks using specialized subagents with aggressive parallel execution. Todo-driven workflow with extended thinking (32k budget). Fallback: `opencode-go/kimi-k2.5``kimi-for-coding/k2p5``opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix/kimi-k2.5``openai\|github-copilot\|opencode/gpt-5.4 (medium)``zai-coding-plan\|opencode/glm-5``opencode/big-pickle`. | | **Sisyphus** | `claude-opus-4-7` | The default orchestrator. Plans, delegates, and executes complex tasks using specialized subagents with aggressive parallel execution. Todo-driven workflow with extended thinking (32k budget). Fallback: `opencode-go/kimi-k2.5``kimi-for-coding/k2p5``opencode\|moonshotai\|moonshotai-cn\|firmware\|ollama-cloud\|aihubmix/kimi-k2.5``openai\|github-copilot\|opencode/gpt-5.4 (medium)``zai-coding-plan\|opencode/glm-5``opencode/big-pickle`. |
| **Hephaestus** | `gpt-5.4` | The Legitimate Craftsman. Autonomous deep worker inspired by AmpCode's deep mode. Goal-oriented execution with thorough research before action. Explores codebase patterns, completes tasks end-to-end without premature stopping. Named after the Greek god of forge and craftsmanship. Requires a GPT-capable provider. | | **Hephaestus** | `gpt-5.4` | The Legitimate Craftsman. Autonomous deep worker inspired by AmpCode's deep mode. Goal-oriented execution with thorough research before action. Explores codebase patterns, completes tasks end-to-end without premature stopping. Named after the Greek god of forge and craftsmanship. Requires a GPT-capable provider. |
| **Oracle** | `gpt-5.4` | Architecture decisions, code review, debugging. Read-only consultation with stellar logical reasoning and deep analysis. Inspired by AmpCode. Fallback: `google\|github-copilot\|opencode/gemini-3.1-pro (high)``anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``opencode-go/glm-5`. | | **Oracle** | `gpt-5.4` | Architecture decisions, code review, debugging. Read-only consultation with stellar logical reasoning and deep analysis. Inspired by AmpCode. Fallback: `google\|github-copilot\|opencode/gemini-3.1-pro (high)``anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``opencode-go/glm-5`. |
| **Librarian** | `minimax-m2.7` | Multi-repo analysis, documentation lookup, OSS implementation examples. Deep codebase understanding with evidence-based answers. Fallback: `opencode/minimax-m2.7-highspeed``anthropic\|opencode/claude-haiku-4-5``opencode/gpt-5-nano`. | | **Librarian** | `minimax-m2.7` | Multi-repo analysis, documentation lookup, OSS implementation examples. Deep codebase understanding with evidence-based answers. Fallback: `opencode/minimax-m2.7-highspeed``anthropic\|opencode/claude-haiku-4-5``opencode/gpt-5-nano`. |
| **Explore** | `grok-code-fast-1` | Fast codebase exploration and contextual grep. Fallback: `opencode-go/minimax-m2.7-highspeed``opencode/minimax-m2.7``anthropic\|opencode/claude-haiku-4-5``opencode/gpt-5-nano`. | | **Explore** | `grok-code-fast-1` | Fast codebase exploration and contextual grep. Fallback: `opencode-go/minimax-m2.7-highspeed``opencode/minimax-m2.7``anthropic\|opencode/claude-haiku-4-5``opencode/gpt-5-nano`. |
| **Multimodal-Looker** | `gpt-5.4` | Visual content specialist. Analyzes PDFs, images, diagrams to extract information. Fallback: `opencode-go/kimi-k2.5``zai-coding-plan/glm-4.6v``openai\|github-copilot\|opencode/gpt-5-nano`. | | **Multimodal-Looker** | `gpt-5.4` | Visual content specialist. Analyzes PDFs, images, diagrams to extract information. Fallback: `opencode-go/kimi-k2.5``zai-coding-plan/glm-4.6v``openai\|github-copilot\|opencode/gpt-5-nano`. |
@@ -20,9 +20,9 @@ Core-agent tab cycling is deterministic via injected runtime order field. The fi
| Agent | Model | Purpose | | Agent | Model | Purpose |
| -------------- | ----------------- | -------------------------------------------------------------------------------------------------------------------------------------------------- | | -------------- | ----------------- | -------------------------------------------------------------------------------------------------------------------------------------------------- |
| **Prometheus** | `claude-opus-4-6` | Strategic planner with interview mode. Creates detailed work plans through iterative questioning. Fallback: `openai\|github-copilot\|opencode/gpt-5.4 (high)``opencode-go/glm-5``google\|github-copilot\|opencode/gemini-3.1-pro`. | | **Prometheus** | `claude-opus-4-7` | Strategic planner with interview mode. Creates detailed work plans through iterative questioning. Fallback: `openai\|github-copilot\|opencode/gpt-5.4 (high)``opencode-go/glm-5``google\|github-copilot\|opencode/gemini-3.1-pro`. |
| **Metis** | `claude-opus-4-6` | Plan consultant — pre-planning analysis. Identifies hidden intentions, ambiguities, and AI failure points. Fallback: `openai\|github-copilot\|opencode/gpt-5.4 (high)``opencode-go/glm-5``kimi-for-coding/k2p5`. | | **Metis** | `claude-opus-4-7` | Plan consultant — pre-planning analysis. Identifies hidden intentions, ambiguities, and AI failure points. Fallback: `openai\|github-copilot\|opencode/gpt-5.4 (high)``opencode-go/glm-5``kimi-for-coding/k2p5`. |
| **Momus** | `gpt-5.4` | Plan reviewer — validates plans against clarity, verifiability, and completeness standards. Fallback: `anthropic\|github-copilot\|opencode/claude-opus-4-6 (max)``google\|github-copilot\|opencode/gemini-3.1-pro (high)``opencode-go/glm-5`. | | **Momus** | `gpt-5.4` | Plan reviewer — validates plans against clarity, verifiability, and completeness standards. Fallback: `anthropic\|github-copilot\|opencode/claude-opus-4-7 (max)``google\|github-copilot\|opencode/gemini-3.1-pro (high)``opencode-go/glm-5`. |
### Orchestration Agents ### Orchestration Agents
@@ -115,7 +115,7 @@ By combining these two concepts, you can generate optimal agents through `task`.
| `artistry` | `google/gemini-3.1-pro` (high) | Highly creative/artistic tasks, novel ideas | | `artistry` | `google/gemini-3.1-pro` (high) | Highly creative/artistic tasks, novel ideas |
| `quick` | `openai/gpt-5.4-mini` | Trivial tasks - single file changes, typo fixes, simple modifications | | `quick` | `openai/gpt-5.4-mini` | Trivial tasks - single file changes, typo fixes, simple modifications |
| `unspecified-low` | `anthropic/claude-sonnet-4-6` | Tasks that don't fit other categories, low effort required | | `unspecified-low` | `anthropic/claude-sonnet-4-6` | Tasks that don't fit other categories, low effort required |
| `unspecified-high` | `anthropic/claude-opus-4-6` (max) | Tasks that don't fit other categories, high effort required | | `unspecified-high` | `anthropic/claude-opus-4-7` (max) | Tasks that don't fit other categories, high effort required |
| `writing` | `google/gemini-3-flash` | Documentation, prose, technical writing | | `writing` | `google/gemini-3-flash` | Documentation, prose, technical writing |
### Usage ### Usage
@@ -138,7 +138,7 @@ You can define custom categories in your plugin config file. During the rename t
| Field | Type | Description | | Field | Type | Description |
| ------------------- | ------- | --------------------------------------------------------------------------- | | ------------------- | ------- | --------------------------------------------------------------------------- |
| `description` | string | Human-readable description of the category's purpose. Shown in task prompt. | | `description` | string | Human-readable description of the category's purpose. Shown in task prompt. |
| `model` | string | AI model ID to use (e.g., `anthropic/claude-opus-4-6`) | | `model` | string | AI model ID to use (e.g., `anthropic/claude-opus-4-7`) |
| `variant` | string | Model variant (e.g., `max`, `xhigh`) | | `variant` | string | Model variant (e.g., `max`, `xhigh`) |
| `temperature` | number | Creativity level (0.0 ~ 2.0). Lower is more deterministic. | | `temperature` | number | Creativity level (0.0 ~ 2.0). Lower is more deterministic. |
| `top_p` | number | Nucleus sampling parameter (0.0 ~ 1.0) | | `top_p` | number | Nucleus sampling parameter (0.0 ~ 1.0) |
@@ -170,7 +170,7 @@ You can define custom categories in your plugin config file. During the rename t
// 3. Configure thinking model and restrict tools // 3. Configure thinking model and restrict tools
"deep-reasoning": { "deep-reasoning": {
"model": "anthropic/claude-opus-4-6", "model": "anthropic/claude-opus-4-7",
"thinking": { "thinking": {
"type": "enabled", "type": "enabled",
"budgetTokens": 32000, "budgetTokens": 32000,
@@ -269,10 +269,11 @@ Skills provide specialized workflows with embedded MCP servers and detailed inst
| ------------------ | ------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | ------------------ | ------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **git-master** | commit, rebase, squash, "who wrote", "when was X added" | Git expert. Detects commit styles, splits atomic commits, formulates rebase strategies. Three specializations: Commit Architect (atomic commits, dependency ordering, style detection), Rebase Surgeon (history rewriting, conflict resolution, branch cleanup), History Archaeologist (finding when/where specific changes were introduced). | | **git-master** | commit, rebase, squash, "who wrote", "when was X added" | Git expert. Detects commit styles, splits atomic commits, formulates rebase strategies. Three specializations: Commit Architect (atomic commits, dependency ordering, style detection), Rebase Surgeon (history rewriting, conflict resolution, branch cleanup), History Archaeologist (finding when/where specific changes were introduced). |
| **playwright** | Browser tasks, testing, screenshots | Browser automation via Playwright MCP. MUST USE for browser verification, browsing, web scraping, testing, and screenshots. | | **playwright** | Browser tasks, testing, screenshots | Browser automation via Playwright MCP. MUST USE for browser verification, browsing, web scraping, testing, and screenshots. |
| **playwright-cli** | Browser tasks on Playwright CLI | Browser automation through the Playwright CLI integration. Useful when direct CLI scripting is preferred over MCP. |
| **agent-browser** | Browser tasks on agent-browser | Browser automation via the `agent-browser` CLI. Covers navigation, snapshots, screenshots, network inspection, and scripted interactions. | | **agent-browser** | Browser tasks on agent-browser | Browser automation via the `agent-browser` CLI. Covers navigation, snapshots, screenshots, network inspection, and scripted interactions. |
| **dev-browser** | Stateful browser scripting | Browser automation with persistent page state for iterative workflows and authenticated sessions. | | **dev-browser** | Stateful browser scripting | Browser automation with persistent page state for iterative workflows and authenticated sessions. |
| **frontend-ui-ux** | UI/UX tasks, styling | Designer-turned-developer persona. Crafts stunning UI/UX even without design mockups. Emphasizes bold aesthetic direction, distinctive typography, cohesive color palettes. | | **frontend-ui-ux** | UI/UX tasks, styling | Designer-turned-developer persona. Crafts stunning UI/UX even without design mockups. Emphasizes bold aesthetic direction, distinctive typography, cohesive color palettes. |
| **review-work** | "review work", "review my work", "QA my work" | Post-implementation review orchestrator. Launches 5 parallel background sub-agents for comprehensive review: goal verification, code quality, security, hands-on QA, and context mining. All must pass for review to pass. |
| **ai-slop-remover**| "remove AI slop", "de-AI", "humanize" | Removes AI-generated code smells from files while preserving functionality. Identifies and eliminates verbose comments, redundant error handling, over-engineered patterns, and generic AI phrasing. |
#### git-master Core Principles #### git-master Core Principles
+2 -2
View File
@@ -67,7 +67,7 @@ The proper fix requires Claude Code SDK to:
3. Merge `tool_calls` from multiple lines 3. Merge `tool_calls` from multiple lines
4. Return a single merged response 4. Return a single merged response
**Tracking**: https://github.com/code-yeongyu/oh-my-openagent/issues/1124 **Tracking**: https://github.com/code-yeongyu/oh-my-openagent/issues/1124 (closed - documented workaround)
## Workaround Implementation ## Workaround Implementation
@@ -114,7 +114,7 @@ curl -s http://localhost:11434/api/chat \
## Related Issues ## Related Issues
- **oh-my-openagent**: https://github.com/code-yeongyu/oh-my-openagent/issues/1124 - **oh-my-openagent**: https://github.com/code-yeongyu/oh-my-openagent/issues/1124 (closed - workaround documented)
- **Ollama API Docs**: https://github.com/ollama/ollama/blob/main/docs/api.md - **Ollama API Docs**: https://github.com/ollama/ollama/blob/main/docs/api.md
## Getting Help ## Getting Help
+22 -18
View File
@@ -1,12 +1,13 @@
{ {
"name": "oh-my-opencode", "name": "oh-my-opencode",
"version": "3.17.0", "version": "3.17.4",
"description": "The Best AI Agent Harness - Batteries-Included OpenCode Plugin with Multi-Model Orchestration, Parallel Background Agents, and Crafted LSP/AST Tools", "description": "The Best AI Agent Harness - Batteries-Included OpenCode Plugin with Multi-Model Orchestration, Parallel Background Agents, and Crafted LSP/AST Tools",
"main": "./dist/index.js", "main": "./dist/index.js",
"types": "dist/index.d.ts", "types": "dist/index.d.ts",
"type": "module", "type": "module",
"bin": { "bin": {
"oh-my-opencode": "bin/oh-my-opencode.js" "oh-my-opencode": "bin/oh-my-opencode.js",
"oh-my-openagent": "bin/oh-my-opencode.js"
}, },
"files": [ "files": [
"dist", "dist",
@@ -21,7 +22,7 @@
"./schema.json": "./dist/oh-my-opencode.schema.json" "./schema.json": "./dist/oh-my-opencode.schema.json"
}, },
"scripts": { "scripts": {
"build": "bun build src/index.ts --outdir dist --target bun --format esm --external @ast-grep/napi && tsc --emitDeclarationOnly && bun build src/cli/index.ts --outdir dist/cli --target bun --format esm --external @ast-grep/napi && bun run build:schema", "build": "bun build src/index.ts --outdir dist --target bun --format esm --external @ast-grep/napi --external zod && tsc --emitDeclarationOnly && bun build src/cli/index.ts --outdir dist/cli --target bun --format esm --external @ast-grep/napi && bun run build:schema",
"build:all": "bun run build && bun run build:binaries", "build:all": "bun run build && bun run build:binaries",
"build:binaries": "bun run script/build-binaries.ts", "build:binaries": "bun run script/build-binaries.ts",
"build:schema": "bun run script/build-schema.ts", "build:schema": "bun run script/build-schema.ts",
@@ -69,32 +70,35 @@
"picocolors": "^1.1.1", "picocolors": "^1.1.1",
"picomatch": "^4.0.2", "picomatch": "^4.0.2",
"posthog-node": "^5.29.2", "posthog-node": "^5.29.2",
"vscode-jsonrpc": "^8.2.0", "vscode-jsonrpc": "^8.2.0"
"zod": "^4.3.0"
}, },
"devDependencies": { "devDependencies": {
"@types/js-yaml": "^4.0.9", "@types/js-yaml": "^4.0.9",
"@types/picomatch": "^3.0.2", "@types/picomatch": "^3.0.2",
"bun-types": "1.3.11", "bun-types": "1.3.11",
"typescript": "^5.7.3" "typescript": "^5.7.3",
"zod": "^4.3.0"
}, },
"optionalDependencies": { "optionalDependencies": {
"oh-my-opencode-darwin-arm64": "3.17.0", "oh-my-opencode-darwin-arm64": "3.17.4",
"oh-my-opencode-darwin-x64": "3.17.0", "oh-my-opencode-darwin-x64": "3.17.4",
"oh-my-opencode-darwin-x64-baseline": "3.17.0", "oh-my-opencode-darwin-x64-baseline": "3.17.4",
"oh-my-opencode-linux-arm64": "3.17.0", "oh-my-opencode-linux-arm64": "3.17.4",
"oh-my-opencode-linux-arm64-musl": "3.17.0", "oh-my-opencode-linux-arm64-musl": "3.17.4",
"oh-my-opencode-linux-x64": "3.17.0", "oh-my-opencode-linux-x64": "3.17.4",
"oh-my-opencode-linux-x64-baseline": "3.17.0", "oh-my-opencode-linux-x64-baseline": "3.17.4",
"oh-my-opencode-linux-x64-musl": "3.17.0", "oh-my-opencode-linux-x64-musl": "3.17.4",
"oh-my-opencode-linux-x64-musl-baseline": "3.17.0", "oh-my-opencode-linux-x64-musl-baseline": "3.17.4",
"oh-my-opencode-windows-x64": "3.17.0", "oh-my-opencode-windows-x64": "3.17.4",
"oh-my-opencode-windows-x64-baseline": "3.17.0" "oh-my-opencode-windows-x64-baseline": "3.17.4"
}, },
"overrides": {}, "overrides": {},
"trustedDependencies": [ "trustedDependencies": [
"@ast-grep/cli", "@ast-grep/cli",
"@ast-grep/napi", "@ast-grep/napi",
"@code-yeongyu/comment-checker" "@code-yeongyu/comment-checker"
] ],
"peerDependencies": {
"zod": "^4.0.0"
}
} }
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-darwin-arm64", "name": "oh-my-opencode-darwin-arm64",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (darwin-arm64)", "description": "Platform-specific binary for oh-my-opencode (darwin-arm64)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-darwin-x64-baseline", "name": "oh-my-opencode-darwin-x64-baseline",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (darwin-x64-baseline, no AVX2)", "description": "Platform-specific binary for oh-my-opencode (darwin-x64-baseline, no AVX2)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-darwin-x64", "name": "oh-my-opencode-darwin-x64",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (darwin-x64)", "description": "Platform-specific binary for oh-my-opencode (darwin-x64)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-linux-arm64-musl", "name": "oh-my-opencode-linux-arm64-musl",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (linux-arm64-musl)", "description": "Platform-specific binary for oh-my-opencode (linux-arm64-musl)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-linux-arm64", "name": "oh-my-opencode-linux-arm64",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (linux-arm64)", "description": "Platform-specific binary for oh-my-opencode (linux-arm64)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-linux-x64-baseline", "name": "oh-my-opencode-linux-x64-baseline",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (linux-x64-baseline, no AVX2)", "description": "Platform-specific binary for oh-my-opencode (linux-x64-baseline, no AVX2)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-linux-x64-musl-baseline", "name": "oh-my-opencode-linux-x64-musl-baseline",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (linux-x64-musl-baseline, no AVX2)", "description": "Platform-specific binary for oh-my-opencode (linux-x64-musl-baseline, no AVX2)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-linux-x64-musl", "name": "oh-my-opencode-linux-x64-musl",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (linux-x64-musl)", "description": "Platform-specific binary for oh-my-opencode (linux-x64-musl)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-linux-x64", "name": "oh-my-opencode-linux-x64",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (linux-x64)", "description": "Platform-specific binary for oh-my-opencode (linux-x64)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-windows-x64-baseline", "name": "oh-my-opencode-windows-x64-baseline",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (windows-x64-baseline, no AVX2)", "description": "Platform-specific binary for oh-my-opencode (windows-x64-baseline, no AVX2)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "oh-my-opencode-windows-x64", "name": "oh-my-opencode-windows-x64",
"version": "3.17.0", "version": "3.17.4",
"description": "Platform-specific binary for oh-my-opencode (windows-x64)", "description": "Platform-specific binary for oh-my-opencode (windows-x64)",
"license": "MIT", "license": "MIT",
"repository": { "repository": {
+136
View File
@@ -2743,6 +2743,142 @@
"created_at": "2026-04-12T01:51:16Z", "created_at": "2026-04-12T01:51:16Z",
"repoId": 1108837393, "repoId": 1108837393,
"pullRequestNo": 3358 "pullRequestNo": 3358
},
{
"name": "Zireael",
"id": 3856578,
"comment_id": 4232913324,
"created_at": "2026-04-12T22:50:13Z",
"repoId": 1108837393,
"pullRequestNo": 3370
},
{
"name": "FuDesign2008",
"id": 908026,
"comment_id": 4232932576,
"created_at": "2026-04-12T23:02:42Z",
"repoId": 1108837393,
"pullRequestNo": 3371
},
{
"name": "matchai",
"id": 4658208,
"comment_id": 4233389606,
"created_at": "2026-04-13T02:27:55Z",
"repoId": 1108837393,
"pullRequestNo": 3376
},
{
"name": "mauriciozaffari",
"id": 26127,
"comment_id": 4238234599,
"created_at": "2026-04-13T17:07:26Z",
"repoId": 1108837393,
"pullRequestNo": 3398
},
{
"name": "kywoo26",
"id": 63901518,
"comment_id": 4238559975,
"created_at": "2026-04-13T18:04:07Z",
"repoId": 1108837393,
"pullRequestNo": 3402
},
{
"name": "garnetlyx",
"id": 12513503,
"comment_id": 4240950163,
"created_at": "2026-04-14T02:37:06Z",
"repoId": 1108837393,
"pullRequestNo": 3409
},
{
"name": "lightrabbit",
"id": 1521765,
"comment_id": 4242277206,
"created_at": "2026-04-14T08:13:57Z",
"repoId": 1108837393,
"pullRequestNo": 3415
},
{
"name": "fr1sk",
"id": 15851195,
"comment_id": 4243608500,
"created_at": "2026-04-14T11:45:25Z",
"repoId": 1108837393,
"pullRequestNo": 3419
},
{
"name": "grandmaster451",
"id": 90475406,
"comment_id": 4243713991,
"created_at": "2026-04-14T12:03:48Z",
"repoId": 1108837393,
"pullRequestNo": 3420
},
{
"name": "kithawk",
"id": 12224006,
"comment_id": 4245479006,
"created_at": "2026-04-14T16:19:42Z",
"repoId": 1108837393,
"pullRequestNo": 3428
},
{
"name": "orbisai0security",
"id": 242526317,
"comment_id": 4249340916,
"created_at": "2026-04-15T05:03:42Z",
"repoId": 1108837393,
"pullRequestNo": 3440
},
{
"name": "CHLK",
"id": 30882682,
"comment_id": 4252344048,
"created_at": "2026-04-15T13:10:30Z",
"repoId": 1108837393,
"pullRequestNo": 3455
},
{
"name": "omer-koren",
"id": 54630488,
"comment_id": 4257838546,
"created_at": "2026-04-16T06:34:57Z",
"repoId": 1108837393,
"pullRequestNo": 3470
},
{
"name": "EnochLi15",
"id": 38340798,
"comment_id": 4259785224,
"created_at": "2026-04-16T11:45:01Z",
"repoId": 1108837393,
"pullRequestNo": 3473
},
{
"name": "Disaster-Terminator",
"id": 47147571,
"comment_id": 4272328109,
"created_at": "2026-04-18T01:42:07Z",
"repoId": 1108837393,
"pullRequestNo": 3497
},
{
"name": "Netzhangheng",
"id": 25896014,
"comment_id": 4272702675,
"created_at": "2026-04-18T04:24:37Z",
"repoId": 1108837393,
"pullRequestNo": 3499
},
{
"name": "andomeder",
"id": 33397443,
"comment_id": 4273945668,
"created_at": "2026-04-18T14:55:50Z",
"repoId": 1108837393,
"pullRequestNo": 3514
} }
] ]
} }
+2 -2
View File
@@ -1,6 +1,6 @@
# src/ — Plugin Source # src/ — Plugin Source
**Generated:** 2026-04-11 **Generated:** 2026-04-18
## OVERVIEW ## OVERVIEW
@@ -10,7 +10,7 @@ Entry point `index.ts` orchestrates 5-step initialization: loadConfig → create
| File | Purpose | | File | Purpose |
|------|---------| |------|---------|
| `index.ts` | Plugin entry, exports `OhMyOpenCodePlugin` | | `index.ts` | Plugin entry, default-exports `pluginModule: PluginModule` with `{ id, server }` |
| `plugin-config.ts` | JSONC parse, multi-level merge, Zod v4 validation | | `plugin-config.ts` | JSONC parse, multi-level merge, Zod v4 validation |
| `create-managers.ts` | TmuxSessionManager, BackgroundManager, SkillMcpManager, ConfigHandler | | `create-managers.ts` | TmuxSessionManager, BackgroundManager, SkillMcpManager, ConfigHandler |
| `create-tools.ts` | SkillContext + AvailableCategories + ToolRegistry (26 tools) | | `create-tools.ts` | SkillContext + AvailableCategories + ToolRegistry (26 tools) |
@@ -0,0 +1 @@
# fixture root
@@ -0,0 +1 @@
# fixture package
@@ -0,0 +1 @@
export const file16 = 16
@@ -0,0 +1 @@
export const file17 = 17
@@ -0,0 +1 @@
export const file18 = 18
@@ -0,0 +1 @@
export const file19 = 19
@@ -0,0 +1 @@
export const file20 = 20
@@ -0,0 +1 @@
# fixture src
@@ -0,0 +1 @@
export const file01 = 1
@@ -0,0 +1 @@
export const file02 = 2
@@ -0,0 +1 @@
export const file03 = 3
@@ -0,0 +1 @@
export const file04 = 4
@@ -0,0 +1 @@
export const file05 = 5
@@ -0,0 +1 @@
export const file06 = 6
@@ -0,0 +1 @@
export const file07 = 7
@@ -0,0 +1 @@
export const file08 = 8
@@ -0,0 +1 @@
export const file09 = 9
@@ -0,0 +1 @@
export const file10 = 10
@@ -0,0 +1 @@
export const file11 = 11
@@ -0,0 +1 @@
export const file12 = 12
@@ -0,0 +1 @@
export const file13 = 13
@@ -0,0 +1 @@
export const file14 = 14
@@ -0,0 +1 @@
export const file15 = 15
+121
View File
@@ -0,0 +1,121 @@
import { cpSync, mkdirSync, mkdtempSync, rmSync } from "node:fs"
import { tmpdir } from "node:os"
import { join } from "node:path"
import type { PluginInput } from "@opencode-ai/plugin"
import { createOpencodeClient } from "@opencode-ai/sdk"
import { describe, expect, it } from "bun:test"
type InitMetrics = {
coldMs: number
warmMs: [number, number]
medianMs: number
}
function getMedian(values: number[]): number {
const sorted = [...values].sort((left, right) => left - right)
return sorted[Math.floor(sorted.length / 2)] ?? 0
}
function createPluginInput(directory: string): PluginInput {
const client = createOpencodeClient({ directory })
return {
client,
project: {
id: `perf-${Date.now()}`,
worktree: directory,
time: { created: Date.now() },
},
directory,
worktree: directory,
serverUrl: new URL("http://localhost"),
$: Bun.$,
}
}
async function importFreshPluginModule(): Promise<(typeof import("../../index"))["default"]> {
const token = `${Date.now()}-${Math.random()}`
return (await import(`../../index?perf=${token}`)).default
}
async function measureInitMetrics(directory: string): Promise<InitMetrics> {
const pluginModule = await importFreshPluginModule()
const measurements: number[] = []
for (let index = 0; index < 3; index += 1) {
const input = createPluginInput(directory)
const start = performance.now()
await pluginModule.server(input, {})
measurements.push(performance.now() - start)
}
return {
coldMs: measurements[0] ?? 0,
warmMs: [measurements[1] ?? 0, measurements[2] ?? 0],
medianMs: getMedian(measurements),
}
}
async function measureScenario(
label: string,
populateDirectory: (directory: string) => void,
): Promise<InitMetrics> {
const rootDirectory = mkdtempSync(join(tmpdir(), "perf-d09-"))
const projectDirectory = join(rootDirectory, label)
const configDirectory = join(rootDirectory, "opencode-config")
const previousConfigDirectory = process.env.OPENCODE_CONFIG_DIR
mkdirSync(configDirectory, { recursive: true })
process.env.OPENCODE_CONFIG_DIR = configDirectory
try {
populateDirectory(projectDirectory)
return await measureInitMetrics(projectDirectory)
} finally {
if (previousConfigDirectory === undefined) {
delete process.env.OPENCODE_CONFIG_DIR
} else {
process.env.OPENCODE_CONFIG_DIR = previousConfigDirectory
}
rmSync(rootDirectory, { recursive: true, force: true })
}
}
function logMetrics(label: string, metrics: InitMetrics): void {
console.info(
`${label}: cold=${metrics.coldMs.toFixed(1)}ms warm=[${metrics.warmMs.map((value) => value.toFixed(1)).join(", ")}] median=${metrics.medianMs.toFixed(1)}ms`,
)
}
describe("plugin init performance", () => {
it("stays within the empty project init budget", async () => {
// given
const metrics = await measureScenario("empty-project", (directory) => {
mkdirSync(directory, { recursive: true })
})
// when
logMetrics("empty-project", metrics)
// then
// regression budget
expect(metrics.medianMs).toBeLessThan(500)
})
it("stays within the in-tree fixture init budget", async () => {
// given
const fixtureDirectory = new URL("./fixtures/in-tree/", import.meta.url)
const metrics = await measureScenario("in-tree-fixture", (directory) => {
cpSync(fixtureDirectory, directory, { recursive: true })
})
// when
logMetrics("in-tree-fixture", metrics)
// then
// regression budget
expect(metrics.medianMs).toBeLessThan(700)
})
})
+6 -6
View File
@@ -1,6 +1,6 @@
# src/agents/ — 11 Agent Definitions # src/agents/ — 11 Agent Definitions
**Generated:** 2026-04-11 **Generated:** 2026-04-18
## OVERVIEW ## OVERVIEW
@@ -10,16 +10,16 @@ Agent factories following `createXXXAgent(model) → AgentConfig` pattern. Each
| Agent | Model | Temp | Mode | Fallback Chain | Purpose | | Agent | Model | Temp | Mode | Fallback Chain | Purpose |
|-------|-------|------|------|----------------|---------| |-------|-------|------|------|----------------|---------|
| **Sisyphus** | claude-opus-4-6 max | 0.1 | all | k2p5 -> kimi-k2.5 -> gpt-5.4 medium -> glm-5 -> big-pickle | Main orchestrator, plans + delegates | | **Sisyphus** | claude-opus-4-7 max | 0.1 | all | k2p5 -> kimi-k2.5 -> gpt-5.4 medium -> glm-5 -> big-pickle | Main orchestrator, plans + delegates |
| **Hephaestus** | gpt-5.4 medium | 0.1 | all | — | Autonomous deep worker | | **Hephaestus** | gpt-5.4 medium | 0.1 | all | — | Autonomous deep worker |
| **Oracle** | gpt-5.4 high | 0.1 | subagent | gemini-3.1-pro high -> claude-opus-4-6 max | Read-only consultation | | **Oracle** | gpt-5.4 high | 0.1 | subagent | gemini-3.1-pro high -> claude-opus-4-7 max | Read-only consultation |
| **Librarian** | minimax-m2.7 | 0.1 | subagent | minimax-m2.7-highspeed -> claude-haiku-4-5 -> gpt-5-nano | External docs/code search | | **Librarian** | minimax-m2.7 | 0.1 | subagent | minimax-m2.7-highspeed -> claude-haiku-4-5 -> gpt-5-nano | External docs/code search |
| **Explore** | grok-code-fast-1 | 0.1 | subagent | minimax-m2.7-highspeed -> minimax-m2.7 -> claude-haiku-4-5 -> gpt-5-nano | Contextual grep | | **Explore** | grok-code-fast-1 | 0.1 | subagent | minimax-m2.7-highspeed -> minimax-m2.7 -> claude-haiku-4-5 -> gpt-5-nano | Contextual grep |
| **Multimodal-Looker** | gpt-5.3-codex medium | 0.1 | subagent | k2p5 -> gemini-3-flash -> glm-4.6v -> gpt-5-nano | PDF/image analysis | | **Multimodal-Looker** | gpt-5.3-codex medium | 0.1 | subagent | k2p5 -> gemini-3-flash -> glm-4.6v -> gpt-5-nano | PDF/image analysis |
| **Metis** | claude-opus-4-6 max | **0.3** | subagent | gpt-5.4 high -> gemini-3.1-pro high | Pre-planning consultant | | **Metis** | claude-opus-4-7 max | **0.3** | subagent | gpt-5.4 high -> gemini-3.1-pro high | Pre-planning consultant |
| **Momus** | gpt-5.4 xhigh | 0.1 | subagent | claude-opus-4-6 max -> gemini-3.1-pro high | Plan reviewer | | **Momus** | gpt-5.4 xhigh | 0.1 | subagent | claude-opus-4-7 max -> gemini-3.1-pro high | Plan reviewer |
| **Atlas** | claude-sonnet-4-6 | 0.1 | primary | gpt-5.4 medium | Todo-list orchestrator | | **Atlas** | claude-sonnet-4-6 | 0.1 | primary | gpt-5.4 medium | Todo-list orchestrator |
| **Prometheus** | claude-opus-4-6 max | 0.1 | — | internal planner | Strategic planner (internal) | | **Prometheus** | claude-opus-4-7 max | 0.1 | — | internal planner | Strategic planner (internal) |
| **Sisyphus-Junior** | claude-sonnet-4-6 | 0.1 | all | user-configurable | Category-spawned executor | | **Sisyphus-Junior** | claude-sonnet-4-6 | 0.1 | all | user-configurable | Category-spawned executor |
## TOOL RESTRICTIONS ## TOOL RESTRICTIONS
+4 -4
View File
@@ -57,7 +57,7 @@ describe("Sisyphus prompt identity", () => {
describe("#given a Sisyphus agent created with default model", () => { describe("#given a Sisyphus agent created with default model", () => {
describe("#when checking the prompt", () => { describe("#when checking the prompt", () => {
it("#then contains the agent identity section with override directive", () => { it("#then contains the agent identity section with override directive", () => {
const config = createSisyphusAgent("anthropic/claude-opus-4-6") const config = createSisyphusAgent("anthropic/claude-opus-4-7")
expect(config.prompt).toContain("<agent-identity>") expect(config.prompt).toContain("<agent-identity>")
expect(config.prompt).toContain("Sisyphus") expect(config.prompt).toContain("Sisyphus")
@@ -65,7 +65,7 @@ describe("Sisyphus prompt identity", () => {
}) })
it("#then identity section appears before the Role section", () => { it("#then identity section appears before the Role section", () => {
const config = createSisyphusAgent("anthropic/claude-opus-4-6") const config = createSisyphusAgent("anthropic/claude-opus-4-7")
const prompt = config.prompt ?? "" const prompt = config.prompt ?? ""
const identityIndex = prompt.indexOf("<agent-identity>") const identityIndex = prompt.indexOf("<agent-identity>")
const roleIndex = prompt.indexOf("<Role>") const roleIndex = prompt.indexOf("<Role>")
@@ -115,7 +115,7 @@ describe("Agent identity preservation through overrides", () => {
describe("#given a Sisyphus agent with prompt_append override", () => { describe("#given a Sisyphus agent with prompt_append override", () => {
describe("#when merging the override", () => { describe("#when merging the override", () => {
it("#then identity section is preserved in the merged prompt", () => { it("#then identity section is preserved in the merged prompt", () => {
const baseConfig = createSisyphusAgent("anthropic/claude-opus-4-6") const baseConfig = createSisyphusAgent("anthropic/claude-opus-4-7")
const merged = mergeAgentConfig(baseConfig, { prompt_append: "Extra instructions here" }) const merged = mergeAgentConfig(baseConfig, { prompt_append: "Extra instructions here" })
expect(merged.prompt).toContain("<agent-identity>") expect(merged.prompt).toContain("<agent-identity>")
@@ -129,7 +129,7 @@ describe("Agent identity preservation through overrides", () => {
describe("#given a Sisyphus agent with model override only", () => { describe("#given a Sisyphus agent with model override only", () => {
describe("#when merging the override", () => { describe("#when merging the override", () => {
it("#then identity section is preserved unchanged", () => { it("#then identity section is preserved unchanged", () => {
const baseConfig = createSisyphusAgent("anthropic/claude-opus-4-6") const baseConfig = createSisyphusAgent("anthropic/claude-opus-4-7")
const merged = mergeAgentConfig(baseConfig, { model: "openai/gpt-5.4" }) const merged = mergeAgentConfig(baseConfig, { model: "openai/gpt-5.4" })
expect(merged.prompt).toContain("<agent-identity>") expect(merged.prompt).toContain("<agent-identity>")
+6 -6
View File
@@ -150,16 +150,16 @@ task(
### 3.5 Handle Failures (USE RESUME) ### 3.5 Handle Failures (USE RESUME)
**CRITICAL: When re-delegating, ALWAYS use \`session_id\` parameter.** **CRITICAL: When re-delegating, ALWAYS use \`task_id\` parameter.**
Every \`task()\` output includes a session_id. STORE IT. Every \`task()\` output includes a task_id. STORE IT.
If task fails: If task fails:
1. Identify what went wrong 1. Identify what went wrong
2. **Resume the SAME session** - subagent has full context already: 2. **Resume the SAME session** - subagent has full context already:
\`\`\`typescript \`\`\`typescript
task( task(
session_id="ses_xyz789", // Session from failed task task_id="ses_xyz789", // Task ID from failed task
load_skills=[...], load_skills=[...],
prompt="FAILED: {error}. Fix by: {specific instruction}" prompt="FAILED: {error}. Fix by: {specific instruction}"
) )
@@ -167,7 +167,7 @@ If task fails:
3. Maximum 3 retry attempts with the SAME session 3. Maximum 3 retry attempts with the SAME session
4. If blocked after 3 attempts: Document and continue to independent tasks 4. If blocked after 3 attempts: Document and continue to independent tasks
**Why session_id is MANDATORY for failures:** **Why task_id is MANDATORY for failures:**
- Subagent already read all files, knows the context - Subagent already read all files, knows the context
- No repeated exploration = 70%+ token savings - No repeated exploration = 70%+ token savings
- Subagent knows what approaches already failed - Subagent knows what approaches already failed
@@ -292,6 +292,6 @@ export const DEFAULT_ATLAS_CRITICAL_RULES = `<critical_overrides>
- Pass inherited wisdom to every subagent - Pass inherited wisdom to every subagent
- Parallelize independent tasks - Parallelize independent tasks
- Verify with your own tools - Verify with your own tools
- **Store session_id from every delegation output** - **Store task_id from every delegation output**
- **Use \`session_id="{session_id}"\` for retries, fixes, and follow-ups** - **Use \`task_id="{task_id}"\` for retries, fixes, and follow-ups**
</critical_overrides>` </critical_overrides>`
+2 -2
View File
@@ -164,10 +164,10 @@ Count remaining **top-level task** checkboxes. Ignore nested verification/eviden
### 3.5 Handle Failures ### 3.5 Handle Failures
**CRITICAL: Use \`session_id\` for retries.** **CRITICAL: Use \`task_id\` for retries.**
\`\`\`typescript \`\`\`typescript
task(session_id="ses_xyz789", load_skills=[...], prompt="FAILED: {error}. Fix by: {instruction}") task(task_id="ses_xyz789", load_skills=[...], prompt="FAILED: {error}. Fix by: {instruction}")
\`\`\` \`\`\`
- Maximum 3 retries per task - Maximum 3 retries per task
+2 -2
View File
@@ -169,10 +169,10 @@ Count remaining **top-level task** checkboxes. Ignore nested verification/eviden
### 3.5 Handle Failures ### 3.5 Handle Failures
**CRITICAL: Use \`session_id\` for retries.** **CRITICAL: Use \`task_id\` for retries.**
\`\`\`typescript \`\`\`typescript
task(session_id="ses_xyz789", load_skills=[...], prompt="FAILED: {error}. Fix by: {instruction}") task(task_id="ses_xyz789", load_skills=[...], prompt="FAILED: {error}. Fix by: {instruction}")
\`\`\` \`\`\`
- Maximum 3 retries per task - Maximum 3 retries per task
@@ -43,7 +43,7 @@ describe("maybeCreateSisyphusConfig", () => {
// given // given
const agentOverrides: AgentOverrides = { const agentOverrides: AgentOverrides = {
sisyphus: { sisyphus: {
model: "anthropic/claude-opus-4-6", model: "anthropic/claude-opus-4-7",
permission: { permission: {
apply_patch: "allow", apply_patch: "allow",
}, },
@@ -55,8 +55,8 @@ describe("maybeCreateSisyphusConfig", () => {
const config = maybeCreateSisyphusConfig({ const config = maybeCreateSisyphusConfig({
disabledAgents: [], disabledAgents: [],
agentOverrides, agentOverrides,
availableModels: new Set(["anthropic/claude-opus-4-6"]), availableModels: new Set(["anthropic/claude-opus-4-7"]),
systemDefaultModel: "anthropic/claude-opus-4-6", systemDefaultModel: "anthropic/claude-opus-4-7",
isFirstRunNoCache: false, isFirstRunNoCache: false,
availableAgents: [], availableAgents: [],
availableSkills: [], availableSkills: [],
@@ -67,7 +67,7 @@ describe("maybeCreateSisyphusConfig", () => {
// then // then
expect(config).toBeDefined(); expect(config).toBeDefined();
expect(config?.model).toBe("anthropic/claude-opus-4-6"); expect(config?.model).toBe("anthropic/claude-opus-4-7");
// Claude models should allow the user override // Claude models should allow the user override
expect(config?.permission).toHaveProperty("apply_patch", "allow"); expect(config?.permission).toHaveProperty("apply_patch", "allow");
}); });
@@ -2,13 +2,13 @@ import { describe, expect, spyOn, test } from "bun:test"
import { createBuiltinAgents } from "./builtin-agents" import { createBuiltinAgents } from "./builtin-agents"
import * as shared from "../shared" import * as shared from "../shared"
const TEST_DEFAULT_MODEL = "anthropic/claude-opus-4-6" const TEST_DEFAULT_MODEL = "anthropic/claude-opus-4-7"
describe("createBuiltinAgents custom agent visibility", () => { describe("createBuiltinAgents custom agent visibility", () => {
test("#given runtime custom agents #when orchestrator prompts are built #then custom agents are not advertised for automatic delegation", async () => { test("#given runtime custom agents #when orchestrator prompts are built #then custom agents are not advertised for automatic delegation", async () => {
//#given //#given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6", "openai/gpt-5.4"]) new Set(["anthropic/claude-opus-4-7", "openai/gpt-5.4"])
) )
try { try {
+1 -1
View File
@@ -182,7 +182,7 @@ Multi-step task? **ALWAYS consult Plan Agent first.** Do NOT start implementatio
- Single-file fix or trivial change proceed directly - Single-file fix or trivial change proceed directly
- Anything else (2+ steps, unclear scope, architecture) \`task(subagent_type="plan", ...)\` FIRST - Anything else (2+ steps, unclear scope, architecture) \`task(subagent_type="plan", ...)\` FIRST
- Use \`session_id\` to resume the same Plan Agent - ask follow-up questions aggressively - Use \`task_id\` to resume the same Plan Agent - ask follow-up questions aggressively
- If ANY part of the task is ambiguous, ask Plan Agent before guessing - If ANY part of the task is ambiguous, ask Plan Agent before guessing
Plan Agent returns a structured work breakdown with parallel execution opportunities. Follow it.` Plan Agent returns a structured work breakdown with parallel execution opportunities. Follow it.`
@@ -211,7 +211,7 @@ describe("buildParallelDelegationSection", () => {
it("#given Claude model #when building #then returns empty", () => { it("#given Claude model #when building #then returns empty", () => {
//#given //#given
const model = "anthropic/claude-opus-4-6" const model = "anthropic/claude-opus-4-7"
const categories = [deepCategory] const categories = [deepCategory]
//#when //#when
@@ -244,7 +244,7 @@ describe("buildNonClaudePlannerSection", () => {
//#then //#then
expect(result).toContain("Plan Agent") expect(result).toContain("Plan Agent")
expect(result).toContain("session_id") expect(result).toContain("task_id")
expect(result).toContain("Multi-step") expect(result).toContain("Multi-step")
}) })
+4 -7
View File
@@ -25,13 +25,10 @@ export const EXPLORE_PROMPT_METADATA: AgentPromptMetadata = {
} }
export function createExploreAgent(model: string): AgentConfig { export function createExploreAgent(model: string): AgentConfig {
const restrictions = createAgentToolRestrictions([ const restrictions = createAgentToolRestrictions(
"write", ["write", "edit", "apply_patch", "task", "call_omo_agent"],
"edit", ["lsp_symbols", "lsp_goto_definition", "lsp_find_references", "lsp_diagnostics", "ast_grep_search"],
"apply_patch", )
"task",
"call_omo_agent",
])
return { return {
description: description:
+8 -8
View File
@@ -56,7 +56,7 @@ describe("getHephaestusPromptSource", () => {
test("returns 'gpt' for non-GPT models and undefined", () => { test("returns 'gpt' for non-GPT models and undefined", () => {
// given // given
const model1 = "anthropic/claude-opus-4-6"; const model1 = "anthropic/claude-opus-4-7";
const model2 = undefined; const model2 = undefined;
// when // when
@@ -124,7 +124,7 @@ describe("getHephaestusPrompt", () => {
test("Claude model returns generic GPT prompt (Hephaestus default)", () => { test("Claude model returns generic GPT prompt (Hephaestus default)", () => {
// given // given
const model = "anthropic/claude-opus-4-6"; const model = "anthropic/claude-opus-4-7";
// when // when
const prompt = getHephaestusPrompt(model); const prompt = getHephaestusPrompt(model);
@@ -149,7 +149,7 @@ describe("getHephaestusPrompt", () => {
test("useTaskSystem=false includes Todo Discipline for Claude models", () => { test("useTaskSystem=false includes Todo Discipline for Claude models", () => {
// given // given
const model = "anthropic/claude-opus-4-6"; const model = "anthropic/claude-opus-4-7";
// when // when
const prompt = getHephaestusPrompt(model, false); const prompt = getHephaestusPrompt(model, false);
@@ -239,7 +239,7 @@ describe("createHephaestusAgent", () => {
// given // given
const gpt54Model = "openai/gpt-5.4"; const gpt54Model = "openai/gpt-5.4";
const gptGenericModel = "openai/gpt-4o"; const gptGenericModel = "openai/gpt-4o";
const claudeModel = "anthropic/claude-opus-4-6"; const claudeModel = "anthropic/claude-opus-4-7";
// when // when
const gpt54Config = createHephaestusAgent(gpt54Model); const gpt54Config = createHephaestusAgent(gpt54Model);
@@ -322,7 +322,7 @@ describe("maybeCreateHephaestusConfig GPT apply_patch guard", () => {
// given // given
const agentOverrides: AgentOverrides = { const agentOverrides: AgentOverrides = {
hephaestus: { hephaestus: {
model: "anthropic/claude-opus-4-6", model: "anthropic/claude-opus-4-7",
permission: { permission: {
apply_patch: "allow", apply_patch: "allow",
}, },
@@ -334,8 +334,8 @@ describe("maybeCreateHephaestusConfig GPT apply_patch guard", () => {
const config = maybeCreateHephaestusConfig({ const config = maybeCreateHephaestusConfig({
disabledAgents: [], disabledAgents: [],
agentOverrides, agentOverrides,
availableModels: new Set(["anthropic/claude-opus-4-6"]), availableModels: new Set(["anthropic/claude-opus-4-7"]),
systemDefaultModel: "anthropic/claude-opus-4-6", systemDefaultModel: "anthropic/claude-opus-4-7",
isFirstRunNoCache: false, isFirstRunNoCache: false,
availableAgents: [], availableAgents: [],
availableSkills: [], availableSkills: [],
@@ -346,7 +346,7 @@ describe("maybeCreateHephaestusConfig GPT apply_patch guard", () => {
// then // then
expect(config).toBeDefined(); expect(config).toBeDefined();
expect(config?.model).toBe("anthropic/claude-opus-4-6"); expect(config?.model).toBe("anthropic/claude-opus-4-7");
expect(config?.permission).toHaveProperty("apply_patch", "allow"); expect(config?.permission).toHaveProperty("apply_patch", "allow");
}); });
}); });
+3 -3
View File
@@ -409,9 +409,9 @@ After delegation, ALWAYS verify: works as expected? follows codebase pattern? MU
Every \`task()\` output includes a session_id. **USE IT for follow-ups.** Every \`task()\` output includes a session_id. **USE IT for follow-ups.**
- **Task failed/incomplete** - \`session_id="{id}", prompt="Fix: {error}"\` - **Task failed/incomplete** - \`task_id="{id}", prompt="Fix: {error}"\`
- **Follow-up on result** - \`session_id="{id}", prompt="Also: {question}"\` - **Follow-up on result** - \`task_id="{id}", prompt="Also: {question}"\`
- **Verification failed** - \`session_id="{id}", prompt="Failed: {error}. Fix."\` - **Verification failed** - \`task_id="{id}", prompt="Failed: {error}. Fix."\`
${ ${
oracleSection oracleSection
+4 -4
View File
@@ -312,10 +312,10 @@ Every delegation prompt needs these 6 sections:
After delegation, verify by reading every file the subagent touched. Check: works as expected? follows codebase pattern? Do not trust self-reports. After delegation, verify by reading every file the subagent touched. Check: works as expected? follows codebase pattern? Do not trust self-reports.
<session_continuity> <session_continuity>
Every \`task()\` returns a session_id. Use it for all follow-ups: Every \`task()\` returns a task_id. Use it for all follow-ups:
- Task failed/incomplete: \`session_id="{id}", prompt="Fix: {error}"\` - Task failed/incomplete: \`task_id="{id}", prompt="Fix: {error}"\`
- Follow-up on result: \`session_id="{id}", prompt="Also: {question}"\` - Follow-up on result: \`task_id="{id}", prompt="Also: {question}"\`
- Verification failed: \`session_id="{id}", prompt="Failed: {error}. Fix."\` - Verification failed: \`task_id="{id}", prompt="Failed: {error}. Fix."\`
This preserves full context, avoids repeated exploration, saves 70%+ tokens. This preserves full context, avoids repeated exploration, saves 70%+ tokens.
</session_continuity> </session_continuity>
+4 -4
View File
@@ -277,11 +277,11 @@ After delegation, ALWAYS verify: works as expected? follows codebase pattern? MU
### Session Continuity ### Session Continuity
Every \`task()\` output includes a session_id. **USE IT for follow-ups.** Every \`task()\` output includes a task_id. **USE IT for follow-ups.**
- **Task failed/incomplete** - \`session_id="{id}", prompt="Fix: {error}"\` - **Task failed/incomplete** - \`task_id="{id}", prompt="Fix: {error}"\`
- **Follow-up on result** - \`session_id="{id}", prompt="Also: {question}"\` - **Follow-up on result** - \`task_id="{id}", prompt="Also: {question}"\`
- **Verification failed** - \`session_id="{id}", prompt="Failed: {error}. Fix."\` - **Verification failed** - \`task_id="{id}", prompt="Failed: {error}. Fix."\`
${ ${
oracleSection oracleSection
+8 -8
View File
@@ -317,15 +317,15 @@ AFTER THE WORK YOU DELEGATED SEEMS DONE, ALWAYS VERIFY THE RESULTS AS FOLLOWING:
### Session Continuity (MANDATORY) ### Session Continuity (MANDATORY)
Every \`task()\` output includes a session_id. **USE IT.** Every \`task()\` output includes a task_id. **USE IT.**
**ALWAYS continue when:** **ALWAYS continue when:**
- Task failed/incomplete \`session_id=\"{session_id}\", prompt=\"Fix: {specific error}\"\` - Task failed/incomplete \`task_id=\"{task_id}\", prompt=\"Fix: {specific error}\"\`
- Follow-up question on result \`session_id=\"{session_id}\", prompt=\"Also: {question}\"\` - Follow-up question on result \`task_id=\"{task_id}\", prompt=\"Also: {question}\"\`
- Multi-turn with same agent \`session_id=\"{session_id}\"\` - NEVER start fresh - Multi-turn with same agent \`task_id=\"{task_id}\"\` - NEVER start fresh
- Verification failed \`session_id=\"{session_id}\", prompt=\"Failed verification: {error}. Fix.\"\` - Verification failed \`task_id=\"{task_id}\", prompt=\"Failed verification: {error}. Fix.\"\`
**Why session_id is CRITICAL:** **Why task_id is CRITICAL:**
- Subagent has FULL conversation context preserved - Subagent has FULL conversation context preserved
- No repeated file reads, exploration, or setup - No repeated file reads, exploration, or setup
- Saves 70%+ tokens on follow-ups - Saves 70%+ tokens on follow-ups
@@ -336,10 +336,10 @@ Every \`task()\` output includes a session_id. **USE IT.**
task(category="quick", load_skills=[], run_in_background=false, description="Fix type error", prompt="Fix the type error in auth.ts...") task(category="quick", load_skills=[], run_in_background=false, description="Fix type error", prompt="Fix the type error in auth.ts...")
// CORRECT: Resume preserves everything // CORRECT: Resume preserves everything
task(session_id="ses_abc123", load_skills=[], run_in_background=false, description="Fix type error", prompt="Fix: Type error on line 42") task(task_id="ses_abc123", load_skills=[], run_in_background=false, description="Fix type error", prompt="Fix: Type error on line 42")
\`\`\` \`\`\`
**After EVERY delegation, STORE the session_id for potential continuation.** **After EVERY delegation, STORE the task_id for potential continuation.**
### Code Changes: ### Code Changes:
- Match existing patterns (if codebase is disciplined) - Match existing patterns (if codebase is disciplined)
+8 -8
View File
@@ -389,15 +389,15 @@ AFTER THE WORK YOU DELEGATED SEEMS DONE, ALWAYS VERIFY THE RESULTS AS FOLLOWING:
### Session Continuity (MANDATORY) ### Session Continuity (MANDATORY)
Every \`task()\` output includes a session_id. **USE IT.** Every \`task()\` output includes a task_id. **USE IT.**
**ALWAYS continue when:** **ALWAYS continue when:**
- Task failed/incomplete \`session_id="{session_id}", prompt="Fix: {specific error}"\` - Task failed/incomplete \`task_id="{task_id}", prompt="Fix: {specific error}"\`
- Follow-up question on result \`session_id="{session_id}", prompt="Also: {question}"\` - Follow-up question on result \`task_id="{task_id}", prompt="Also: {question}"\`
- Multi-turn with same agent \`session_id="{session_id}"\` - NEVER start fresh - Multi-turn with same agent \`task_id="{task_id}"\` - NEVER start fresh
- Verification failed \`session_id="{session_id}", prompt="Failed verification: {error}. Fix."\` - Verification failed \`task_id="{task_id}", prompt="Failed verification: {error}. Fix."\`
**Why session_id is CRITICAL:** **Why task_id is CRITICAL:**
- Subagent has FULL conversation context preserved - Subagent has FULL conversation context preserved
- No repeated file reads, exploration, or setup - No repeated file reads, exploration, or setup
- Saves 70%+ tokens on follow-ups - Saves 70%+ tokens on follow-ups
@@ -408,10 +408,10 @@ Every \`task()\` output includes a session_id. **USE IT.**
task(category="quick", load_skills=[], run_in_background=false, description="Fix type error", prompt="Fix the type error in auth.ts...") task(category="quick", load_skills=[], run_in_background=false, description="Fix type error", prompt="Fix the type error in auth.ts...")
// CORRECT: Resume preserves everything // CORRECT: Resume preserves everything
task(session_id="ses_abc123", load_skills=[], run_in_background=false, description="Fix type error", prompt="Fix: Type error on line 42") task(task_id="ses_abc123", load_skills=[], run_in_background=false, description="Fix type error", prompt="Fix: Type error on line 42")
\`\`\` \`\`\`
**After EVERY delegation, STORE the session_id for potential continuation.** **After EVERY delegation, STORE the task_id for potential continuation.**
### Code Changes: ### Code Changes:
- Match existing patterns (if codebase is disciplined) - Match existing patterns (if codebase is disciplined)
+4 -4
View File
@@ -387,10 +387,10 @@ Post-delegation: delegation never substitutes for verification. Always run \`<ve
### Session continuity ### Session continuity
Every \`task()\` returns a session_id. Use it for all follow-ups: Every \`task()\` returns a task_id. Use it for all follow-ups:
- Failed/incomplete \`session_id="{id}", prompt="Fix: {specific error}"\` - Failed/incomplete \`task_id="{id}", prompt="Fix: {specific error}"\`
- Follow-up \`session_id="{id}", prompt="Also: {question}"\` - Follow-up \`task_id="{id}", prompt="Also: {question}"\`
- Multi-turn always \`session_id\`, never start fresh - Multi-turn always \`task_id\`, never start fresh
This preserves full context, avoids repeated exploration, saves 70%+ tokens. This preserves full context, avoids repeated exploration, saves 70%+ tokens.
+7 -7
View File
@@ -18,7 +18,7 @@ describe("isGpt5_4Model", () => {
}); });
test("does not match non-GPT models", () => { test("does not match non-GPT models", () => {
expect(isGpt5_4Model("anthropic/claude-opus-4-6")).toBe(false); expect(isGpt5_4Model("anthropic/claude-opus-4-7")).toBe(false);
expect(isGpt5_4Model("google/gemini-3.1-pro")).toBe(false); expect(isGpt5_4Model("google/gemini-3.1-pro")).toBe(false);
expect(isGpt5_4Model("openai/o1")).toBe(false); expect(isGpt5_4Model("openai/o1")).toBe(false);
}); });
@@ -64,7 +64,7 @@ describe("isGptModel", () => {
}); });
test("claude models are not gpt", () => { test("claude models are not gpt", () => {
expect(isGptModel("anthropic/claude-opus-4-6")).toBe(false); expect(isGptModel("anthropic/claude-opus-4-7")).toBe(false);
expect(isGptModel("anthropic/claude-sonnet-4-6")).toBe(false); expect(isGptModel("anthropic/claude-sonnet-4-6")).toBe(false);
expect(isGptModel("litellm/anthropic.claude-opus-4-5")).toBe(false); expect(isGptModel("litellm/anthropic.claude-opus-4-5")).toBe(false);
}); });
@@ -75,7 +75,7 @@ describe("isGptModel", () => {
}); });
test("opencode provider is not gpt", () => { test("opencode provider is not gpt", () => {
expect(isGptModel("opencode/claude-opus-4-6")).toBe(false); expect(isGptModel("opencode/claude-opus-4-7")).toBe(false);
}); });
}); });
@@ -95,7 +95,7 @@ describe("isMiniMaxModel", () => {
test("does not match non-minimax models", () => { test("does not match non-minimax models", () => {
expect(isMiniMaxModel("openai/gpt-5.4")).toBe(false); expect(isMiniMaxModel("openai/gpt-5.4")).toBe(false);
expect(isMiniMaxModel("anthropic/claude-opus-4-6")).toBe(false); expect(isMiniMaxModel("anthropic/claude-opus-4-7")).toBe(false);
expect(isMiniMaxModel("google/gemini-3.1-pro")).toBe(false); expect(isMiniMaxModel("google/gemini-3.1-pro")).toBe(false);
expect(isMiniMaxModel("opencode-go/kimi-k2.5")).toBe(false); expect(isMiniMaxModel("opencode-go/kimi-k2.5")).toBe(false);
}); });
@@ -116,7 +116,7 @@ describe("isGlmModel", () => {
test("#given non-GLM models #then returns false", () => { test("#given non-GLM models #then returns false", () => {
expect(isGlmModel("openai/gpt-5.4")).toBe(false); expect(isGlmModel("openai/gpt-5.4")).toBe(false);
expect(isGlmModel("anthropic/claude-opus-4-6")).toBe(false); expect(isGlmModel("anthropic/claude-opus-4-7")).toBe(false);
expect(isGlmModel("google/gemini-3.1-pro")).toBe(false); expect(isGlmModel("google/gemini-3.1-pro")).toBe(false);
}); });
}); });
@@ -156,11 +156,11 @@ describe("isGeminiModel", () => {
}); });
test("#given claude models #then returns false", () => { test("#given claude models #then returns false", () => {
expect(isGeminiModel("anthropic/claude-opus-4-6")).toBe(false); expect(isGeminiModel("anthropic/claude-opus-4-7")).toBe(false);
expect(isGeminiModel("anthropic/claude-sonnet-4-6")).toBe(false); expect(isGeminiModel("anthropic/claude-sonnet-4-6")).toBe(false);
}); });
test("#given opencode provider #then returns false", () => { test("#given opencode provider #then returns false", () => {
expect(isGeminiModel("opencode/claude-opus-4-6")).toBe(false); expect(isGeminiModel("opencode/claude-opus-4-7")).toBe(false);
}); });
}); });
+23 -23
View File
@@ -7,7 +7,7 @@ import * as connectedProvidersCache from "../shared/connected-providers-cache"
import * as modelAvailability from "../shared/model-availability" import * as modelAvailability from "../shared/model-availability"
import * as shared from "../shared" import * as shared from "../shared"
const TEST_DEFAULT_MODEL = "anthropic/claude-opus-4-6" const TEST_DEFAULT_MODEL = "anthropic/claude-opus-4-7"
let createBuiltinAgents: (typeof import("./builtin-agents"))["createBuiltinAgents"] let createBuiltinAgents: (typeof import("./builtin-agents"))["createBuiltinAgents"]
async function importFreshBuiltinAgentsModule(): Promise<typeof import("./builtin-agents")> { async function importFreshBuiltinAgentsModule(): Promise<typeof import("./builtin-agents")> {
@@ -32,7 +32,7 @@ describe("createBuiltinAgents with model overrides", () => {
// #given // #given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set([ new Set([
"anthropic/claude-opus-4-6", "anthropic/claude-opus-4-7",
"kimi-for-coding/k2p5", "kimi-for-coding/k2p5",
"opencode/kimi-k2.5-free", "opencode/kimi-k2.5-free",
"zai-coding-plan/glm-5", "zai-coding-plan/glm-5",
@@ -45,7 +45,7 @@ describe("createBuiltinAgents with model overrides", () => {
const agents = await createBuiltinAgents([], {}, undefined, TEST_DEFAULT_MODEL, undefined, undefined, [], {}) const agents = await createBuiltinAgents([], {}, undefined, TEST_DEFAULT_MODEL, undefined, undefined, [], {})
// #then // #then
expect(agents.sisyphus.model).toBe("anthropic/claude-opus-4-6") expect(agents.sisyphus.model).toBe("anthropic/claude-opus-4-7")
expect(agents.sisyphus.thinking).toEqual({ type: "enabled", budgetTokens: 32000 }) expect(agents.sisyphus.thinking).toEqual({ type: "enabled", budgetTokens: 32000 })
expect(agents.sisyphus.reasoningEffort).toBeUndefined() expect(agents.sisyphus.reasoningEffort).toBeUndefined()
} finally { } finally {
@@ -170,7 +170,7 @@ describe("createBuiltinAgents with model overrides", () => {
test("Sisyphus is created on first run when no availableModels or cache exist", async () => { test("Sisyphus is created on first run when no availableModels or cache exist", async () => {
// #given // #given
const systemDefaultModel = "anthropic/claude-opus-4-6" const systemDefaultModel = "anthropic/claude-opus-4-7"
const cacheSpy = spyOn(connectedProvidersCache, "readConnectedProvidersCache").mockReturnValue(null) const cacheSpy = spyOn(connectedProvidersCache, "readConnectedProvidersCache").mockReturnValue(null)
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(new Set()) const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(new Set())
@@ -180,7 +180,7 @@ describe("createBuiltinAgents with model overrides", () => {
// #then // #then
expect(agents.sisyphus).toBeDefined() expect(agents.sisyphus).toBeDefined()
expect(agents.sisyphus.model).toBe("anthropic/claude-opus-4.6") expect(agents.sisyphus.model).toBe("anthropic/claude-opus-4.7")
} finally { } finally {
cacheSpy.mockRestore() cacheSpy.mockRestore()
fetchSpy.mockRestore() fetchSpy.mockRestore()
@@ -299,7 +299,7 @@ describe("createBuiltinAgents with model overrides", () => {
// #given // #given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set([ new Set([
"anthropic/claude-opus-4-6", "anthropic/claude-opus-4-7",
"kimi-for-coding/k2p5", "kimi-for-coding/k2p5",
"opencode/kimi-k2.5-free", "opencode/kimi-k2.5-free",
"zai-coding-plan/glm-5", "zai-coding-plan/glm-5",
@@ -341,7 +341,7 @@ describe("createBuiltinAgents with model overrides", () => {
test("excludes hidden custom agents from orchestrator prompts", async () => { test("excludes hidden custom agents from orchestrator prompts", async () => {
// #given // #given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6", "openai/gpt-5.4"]) new Set(["anthropic/claude-opus-4-7", "openai/gpt-5.4"])
) )
const customAgentSummaries = [ const customAgentSummaries = [
@@ -377,7 +377,7 @@ describe("createBuiltinAgents with model overrides", () => {
test("excludes disabled custom agents from orchestrator prompts", async () => { test("excludes disabled custom agents from orchestrator prompts", async () => {
// #given // #given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6", "openai/gpt-5.4"]) new Set(["anthropic/claude-opus-4-7", "openai/gpt-5.4"])
) )
const customAgentSummaries = [ const customAgentSummaries = [
@@ -413,7 +413,7 @@ describe("createBuiltinAgents with model overrides", () => {
test("excludes custom agents when disabledAgents contains their name (case-insensitive)", async () => { test("excludes custom agents when disabledAgents contains their name (case-insensitive)", async () => {
// #given // #given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6", "openai/gpt-5.4"]) new Set(["anthropic/claude-opus-4-7", "openai/gpt-5.4"])
) )
const disabledAgents = ["ReSeArChEr"] const disabledAgents = ["ReSeArChEr"]
@@ -449,7 +449,7 @@ describe("createBuiltinAgents with model overrides", () => {
test("does not advertise duplicate custom agents case-insensitively", async () => { test("does not advertise duplicate custom agents case-insensitively", async () => {
// #given // #given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6", "openai/gpt-5.4"]) new Set(["anthropic/claude-opus-4-7", "openai/gpt-5.4"])
) )
const customAgentSummaries = [ const customAgentSummaries = [
@@ -481,7 +481,7 @@ describe("createBuiltinAgents with model overrides", () => {
test("does not surface custom agent strings in orchestrator prompts", async () => { test("does not surface custom agent strings in orchestrator prompts", async () => {
// #given // #given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6", "openai/gpt-5.4"]) new Set(["anthropic/claude-opus-4-7", "openai/gpt-5.4"])
) )
const customAgentSummaries = [ const customAgentSummaries = [
@@ -555,7 +555,7 @@ describe("createBuiltinAgents without systemDefaultModel", () => {
]) ])
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set([ new Set([
"anthropic/claude-opus-4-6", "anthropic/claude-opus-4-7",
"kimi-for-coding/k2p5", "kimi-for-coding/k2p5",
"opencode/kimi-k2.5-free", "opencode/kimi-k2.5-free",
"zai-coding-plan/glm-5", "zai-coding-plan/glm-5",
@@ -569,7 +569,7 @@ describe("createBuiltinAgents without systemDefaultModel", () => {
// #then // #then
expect(agents.sisyphus).toBeDefined() expect(agents.sisyphus).toBeDefined()
expect(agents.sisyphus.model).toBe("anthropic/claude-opus-4-6") expect(agents.sisyphus.model).toBe("anthropic/claude-opus-4-7")
} finally { } finally {
cacheSpy.mockRestore() cacheSpy.mockRestore()
fetchSpy.mockRestore() fetchSpy.mockRestore()
@@ -590,7 +590,7 @@ describe("createBuiltinAgents with requiresProvider gating (hephaestus)", () =>
const providers = options?.connectedProviders ?? [] const providers = options?.connectedProviders ?? []
return providers.includes("openai") return providers.includes("openai")
? new Set(["openai/gpt-5.3-codex"]) ? new Set(["openai/gpt-5.3-codex"])
: new Set(["anthropic/claude-opus-4-6"]) : new Set(["anthropic/claude-opus-4-7"])
}) })
try { try {
@@ -609,7 +609,7 @@ describe("createBuiltinAgents with requiresProvider gating (hephaestus)", () =>
test("hephaestus is not created when no required provider is connected", async () => { test("hephaestus is not created when no required provider is connected", async () => {
// #given - only anthropic models available, not in hephaestus requiresProvider // #given - only anthropic models available, not in hephaestus requiresProvider
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6"]) new Set(["anthropic/claude-opus-4-7"])
) )
const cacheSpy = spyOn(connectedProvidersCache, "readConnectedProvidersCache").mockReturnValue(["anthropic"]) const cacheSpy = spyOn(connectedProvidersCache, "readConnectedProvidersCache").mockReturnValue(["anthropic"])
@@ -699,10 +699,10 @@ describe("createBuiltinAgents with requiresProvider gating (hephaestus)", () =>
test("hephaestus is created when explicit config provided even if provider unavailable", async () => { test("hephaestus is created when explicit config provided even if provider unavailable", async () => {
// #given // #given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6"]) new Set(["anthropic/claude-opus-4-7"])
) )
const overrides = { const overrides = {
hephaestus: { model: "anthropic/claude-opus-4-6" }, hephaestus: { model: "anthropic/claude-opus-4-7" },
} }
try { try {
@@ -781,7 +781,7 @@ describe("Sisyphus and Librarian environment context toggle", () => {
beforeEach(() => { beforeEach(() => {
fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6", "google/gemini-3-flash"]) new Set(["anthropic/claude-opus-4-7", "google/gemini-3-flash"])
) )
}) })
@@ -840,7 +840,7 @@ describe("Atlas is unaffected by environment context toggle", () => {
beforeEach(() => { beforeEach(() => {
fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6", "openai/gpt-5.4"]) new Set(["anthropic/claude-opus-4-7", "openai/gpt-5.4"])
) )
}) })
@@ -893,7 +893,7 @@ describe("createBuiltinAgents with requiresAnyModel gating (sisyphus)", () => {
test("sisyphus is created when at least one fallback model is available", async () => { test("sisyphus is created when at least one fallback model is available", async () => {
// #given // #given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue( const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(
new Set(["anthropic/claude-opus-4-6"]) new Set(["anthropic/claude-opus-4-7"])
) )
try { try {
@@ -918,7 +918,7 @@ describe("createBuiltinAgents with requiresAnyModel gating (sisyphus)", () => {
// #then // #then
expect(agents.sisyphus).toBeDefined() expect(agents.sisyphus).toBeDefined()
expect(agents.sisyphus.model).toBe("anthropic/claude-opus-4.6") expect(agents.sisyphus.model).toBe("anthropic/claude-opus-4.7")
} finally { } finally {
cacheSpy.mockRestore() cacheSpy.mockRestore()
fetchSpy.mockRestore() fetchSpy.mockRestore()
@@ -929,7 +929,7 @@ describe("createBuiltinAgents with requiresAnyModel gating (sisyphus)", () => {
// #given // #given
const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(new Set()) const fetchSpy = spyOn(shared, "fetchAvailableModels").mockResolvedValue(new Set())
const overrides = { const overrides = {
sisyphus: { model: "anthropic/claude-opus-4-6" }, sisyphus: { model: "anthropic/claude-opus-4-7" },
} }
try { try {
@@ -1039,7 +1039,7 @@ describe("createBuiltinAgents with requiresAnyModel gating (sisyphus)", () => {
describe("buildAgent with category and skills", () => { describe("buildAgent with category and skills", () => {
const { buildAgent } = require("./agent-builder") const { buildAgent } = require("./agent-builder")
const TEST_MODEL = "anthropic/claude-opus-4-6" const TEST_MODEL = "anthropic/claude-opus-4-7"
beforeEach(() => { beforeEach(() => {
clearSkillCache() clearSkillCache()
+1 -1
View File
@@ -1,6 +1,6 @@
# src/cli/ — CLI: install, run, doctor, mcp-oauth # src/cli/ — CLI: install, run, doctor, mcp-oauth
**Generated:** 2026-04-11 **Generated:** 2026-04-18
## OVERVIEW ## OVERVIEW
File diff suppressed because it is too large Load Diff
+1
View File
@@ -22,6 +22,7 @@ describe("runCliInstaller telemetry isolation", () => {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
}), }),
spyOn(configManager, "isOpenCodeInstalled").mockResolvedValue(true), spyOn(configManager, "isOpenCodeInstalled").mockResolvedValue(true),
spyOn(configManager, "getOpenCodeVersion").mockResolvedValue("1.4.0"), spyOn(configManager, "getOpenCodeVersion").mockResolvedValue("1.4.0"),
+2
View File
@@ -37,6 +37,7 @@ describe("runCliInstaller", () => {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
}), }),
spyOn(configManager, "isOpenCodeInstalled").mockResolvedValue(true), spyOn(configManager, "isOpenCodeInstalled").mockResolvedValue(true),
spyOn(configManager, "getOpenCodeVersion").mockResolvedValue("1.3.9"), spyOn(configManager, "getOpenCodeVersion").mockResolvedValue("1.3.9"),
@@ -83,6 +84,7 @@ describe("runCliInstaller", () => {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
}), }),
spyOn(configManager, "isOpenCodeInstalled").mockResolvedValue(true), spyOn(configManager, "isOpenCodeInstalled").mockResolvedValue(true),
spyOn(configManager, "getOpenCodeVersion").mockResolvedValue("1.4.0"), spyOn(configManager, "getOpenCodeVersion").mockResolvedValue("1.4.0"),
+2 -1
View File
@@ -138,7 +138,8 @@ export async function runCliInstaller(args: InstallArgs, version: string): Promi
!config.hasOpenAI && !config.hasOpenAI &&
!config.hasGemini && !config.hasGemini &&
!config.hasCopilot && !config.hasCopilot &&
!config.hasOpencodeZen !config.hasOpencodeZen &&
!config.hasVercelAiGateway
) { ) {
printWarning("No model providers configured. Using opencode/big-pickle as fallback.") printWarning("No model providers configured. Using opencode/big-pickle as fallback.")
} }
+6 -3
View File
@@ -33,6 +33,7 @@ program
.option("--zai-coding-plan <value>", "Z.ai Coding Plan subscription: no, yes (default: no)") .option("--zai-coding-plan <value>", "Z.ai Coding Plan subscription: no, yes (default: no)")
.option("--kimi-for-coding <value>", "Kimi For Coding subscription: no, yes (default: no)") .option("--kimi-for-coding <value>", "Kimi For Coding subscription: no, yes (default: no)")
.option("--opencode-go <value>", "OpenCode Go subscription: no, yes (default: no)") .option("--opencode-go <value>", "OpenCode Go subscription: no, yes (default: no)")
.option("--vercel-ai-gateway <value>", "Vercel AI Gateway: no, yes (default: no)")
.option("--skip-auth", "Skip authentication setup hints") .option("--skip-auth", "Skip authentication setup hints")
.addHelpText("after", ` .addHelpText("after", `
Examples: Examples:
@@ -40,14 +41,15 @@ Examples:
$ bunx oh-my-opencode install --no-tui --claude=max20 --openai=yes --gemini=yes --copilot=no $ bunx oh-my-opencode install --no-tui --claude=max20 --openai=yes --gemini=yes --copilot=no
$ bunx oh-my-opencode install --no-tui --claude=no --gemini=no --copilot=yes --opencode-zen=yes $ bunx oh-my-opencode install --no-tui --claude=no --gemini=no --copilot=yes --opencode-zen=yes
Model Providers (Priority: Native > Copilot > OpenCode Zen > Z.ai > Kimi): Model Providers (Priority: Native > Copilot > OpenCode Zen > Z.ai > Kimi > Vercel):
Claude Native anthropic/ models (Opus, Sonnet, Haiku) Claude Native anthropic/ models (Opus, Sonnet, Haiku)
OpenAI Native openai/ models (GPT-5.4 for Oracle) OpenAI Native openai/ models (GPT-5.4 for Oracle)
Gemini Native google/ models (Gemini 3.1 Pro, Flash) Gemini Native google/ models (Gemini 3.1 Pro, Flash)
Copilot github-copilot/ models (fallback) Copilot github-copilot/ models (fallback)
OpenCode Zen opencode/ models (opencode/claude-opus-4-6, etc.) OpenCode Zen opencode/ models (opencode/claude-opus-4-7, etc.)
Z.ai zai-coding-plan/glm-5 (visual-engineering fallback) Z.ai zai-coding-plan/glm-5 (visual-engineering fallback)
Kimi kimi-for-coding/k2p5 (Sisyphus/Prometheus fallback) Kimi kimi-for-coding/k2p5 (Sisyphus/Prometheus fallback)
Vercel vercel/ models (universal proxy, always last fallback)
`) `)
.action(async (options) => { .action(async (options) => {
const args: InstallArgs = { const args: InstallArgs = {
@@ -60,6 +62,7 @@ Model Providers (Priority: Native > Copilot > OpenCode Zen > Z.ai > Kimi):
zaiCodingPlan: options.zaiCodingPlan, zaiCodingPlan: options.zaiCodingPlan,
kimiForCoding: options.kimiForCoding, kimiForCoding: options.kimiForCoding,
opencodeGo: options.opencodeGo, opencodeGo: options.opencodeGo,
vercelAiGateway: options.vercelAiGateway,
skipAuth: options.skipAuth ?? false, skipAuth: options.skipAuth ?? false,
} }
const exitCode = await install(args) const exitCode = await install(args)
@@ -12,6 +12,7 @@ function detectProvidersFromOmoConfig(): {
hasZaiCodingPlan: boolean hasZaiCodingPlan: boolean
hasKimiForCoding: boolean hasKimiForCoding: boolean
hasOpencodeGo: boolean hasOpencodeGo: boolean
hasVercelAiGateway: boolean
} { } {
const omoConfigPath = getOmoConfigPath() const omoConfigPath = getOmoConfigPath()
if (!existsSync(omoConfigPath)) { if (!existsSync(omoConfigPath)) {
@@ -21,6 +22,7 @@ function detectProvidersFromOmoConfig(): {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
} }
@@ -34,6 +36,7 @@ function detectProvidersFromOmoConfig(): {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
} }
@@ -43,8 +46,9 @@ function detectProvidersFromOmoConfig(): {
const hasZaiCodingPlan = configStr.includes('"zai-coding-plan/') const hasZaiCodingPlan = configStr.includes('"zai-coding-plan/')
const hasKimiForCoding = configStr.includes('"kimi-for-coding/') const hasKimiForCoding = configStr.includes('"kimi-for-coding/')
const hasOpencodeGo = configStr.includes('"opencode-go/') const hasOpencodeGo = configStr.includes('"opencode-go/')
const hasVercelAiGateway = configStr.includes('"vercel/')
return { hasOpenAI, hasOpencodeZen, hasZaiCodingPlan, hasKimiForCoding, hasOpencodeGo } return { hasOpenAI, hasOpencodeZen, hasZaiCodingPlan, hasKimiForCoding, hasOpencodeGo, hasVercelAiGateway }
} catch { } catch {
return { return {
hasOpenAI: true, hasOpenAI: true,
@@ -52,6 +56,7 @@ function detectProvidersFromOmoConfig(): {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
} }
} }
@@ -78,6 +83,7 @@ export function detectCurrentConfig(): DetectedConfig {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
const { format, path } = detectConfigFormat() const { format, path } = detectConfigFormat()
@@ -106,12 +112,13 @@ export function detectCurrentConfig(): DetectedConfig {
const providers = openCodeConfig.provider as Record<string, unknown> | undefined const providers = openCodeConfig.provider as Record<string, unknown> | undefined
result.hasGemini = providers ? "google" in providers : false result.hasGemini = providers ? "google" in providers : false
const { hasOpenAI, hasOpencodeZen, hasZaiCodingPlan, hasKimiForCoding, hasOpencodeGo } = detectProvidersFromOmoConfig() const { hasOpenAI, hasOpencodeZen, hasZaiCodingPlan, hasKimiForCoding, hasOpencodeGo, hasVercelAiGateway } = detectProvidersFromOmoConfig()
result.hasOpenAI = hasOpenAI result.hasOpenAI = hasOpenAI
result.hasOpencodeZen = hasOpencodeZen result.hasOpencodeZen = hasOpencodeZen
result.hasZaiCodingPlan = hasZaiCodingPlan result.hasZaiCodingPlan = hasZaiCodingPlan
result.hasKimiForCoding = hasKimiForCoding result.hasKimiForCoding = hasKimiForCoding
result.hasOpencodeGo = hasOpencodeGo result.hasOpencodeGo = hasOpencodeGo
result.hasVercelAiGateway = hasVercelAiGateway
return result return result
} }
@@ -18,6 +18,7 @@ describe("generateOmoConfig - model fallback system", () => {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
//#when //#when
@@ -25,8 +26,8 @@ describe("generateOmoConfig - model fallback system", () => {
//#then //#then
expect([ expect([
"github-copilot/claude-opus-4.6", "github-copilot/claude-opus-4.7",
"github-copilot/claude-opus-4-6", "github-copilot/claude-opus-4-7",
]).toContain((result.agents as Record<string, { model: string }>).sisyphus.model) ]).toContain((result.agents as Record<string, { model: string }>).sisyphus.model)
}) })
@@ -42,6 +43,7 @@ describe("generateOmoConfig - model fallback system", () => {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
//#when //#when
@@ -64,6 +66,7 @@ describe("generateOmoConfig - model fallback system", () => {
hasZaiCodingPlan: true, hasZaiCodingPlan: true,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
//#when //#when
@@ -71,7 +74,7 @@ describe("generateOmoConfig - model fallback system", () => {
//#then //#then
expect((result.agents as Record<string, { model: string }>).librarian.model).toBe("zai-coding-plan/glm-4.7") expect((result.agents as Record<string, { model: string }>).librarian.model).toBe("zai-coding-plan/glm-4.7")
expect((result.agents as Record<string, { model: string }>).sisyphus.model).toBe("anthropic/claude-opus-4-6") expect((result.agents as Record<string, { model: string }>).sisyphus.model).toBe("anthropic/claude-opus-4-7")
}) })
test("uses native OpenAI models when only ChatGPT available", () => { test("uses native OpenAI models when only ChatGPT available", () => {
@@ -86,6 +89,7 @@ describe("generateOmoConfig - model fallback system", () => {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
//#when //#when
@@ -110,6 +114,7 @@ describe("generateOmoConfig - model fallback system", () => {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
//#when //#when
@@ -126,7 +131,7 @@ describe("generateOmoConfig - model fallback system", () => {
}> }>
//#then //#then
expect(agents.sisyphus.model).toBe("anthropic/claude-opus-4-6") expect(agents.sisyphus.model).toBe("anthropic/claude-opus-4-7")
expect(agents.sisyphus.fallback_models).toEqual([ expect(agents.sisyphus.fallback_models).toEqual([
{ {
model: "openai/gpt-5.4", model: "openai/gpt-5.4",
@@ -136,7 +141,7 @@ describe("generateOmoConfig - model fallback system", () => {
expect(categories.deep.model).toBe("openai/gpt-5.4") expect(categories.deep.model).toBe("openai/gpt-5.4")
expect(categories.deep.fallback_models).toEqual([ expect(categories.deep.fallback_models).toEqual([
{ {
model: "anthropic/claude-opus-4-6", model: "anthropic/claude-opus-4-7",
variant: "max", variant: "max",
}, },
]) ])
@@ -154,6 +159,7 @@ describe("generateOmoConfig - model fallback system", () => {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
//#when //#when
@@ -175,6 +181,7 @@ describe("generateOmoConfig - model fallback system", () => {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
//#when //#when
@@ -20,6 +20,7 @@ const installConfig: InstallConfig = {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
} }
function getRecord(value: unknown): Record<string, unknown> { function getRecord(value: unknown): Record<string, unknown> {
+82
View File
@@ -0,0 +1,82 @@
# src/cli/doctor/ — Health Diagnostics (25 Check Files)
**Generated:** 2026-04-18
## OVERVIEW
`bunx oh-my-opencode doctor` — parallel diagnostic checks across 4 categories (System, Config, Tools, Models). Catches broken installs, config typos, missing dependencies, provider misconfigurations before they become runtime errors.
## COMMAND FLAGS
```bash
bunx oh-my-opencode doctor # Full diagnostics (all 4 categories)
bunx oh-my-opencode doctor --status # Compact dashboard (status only)
bunx oh-my-opencode doctor --verbose # Deep details (model resolution traces)
bunx oh-my-opencode doctor --json # Machine-readable output
```
## CHECK CATEGORIES
| Category | File | Validates |
|----------|------|-----------|
| **SYSTEM** | `checks/system.ts` | OpenCode binary found + version ≥1.0.150, plugin registered in opencode.json, loaded plugin version matches installed |
| **CONFIG** | `checks/config.ts` | JSONC validity, Zod schema passes, no unknown keys, model override syntax correct |
| **TOOLS** | `checks/tools.ts` | AST-Grep CLI + NAPI, comment-checker binary, LSP servers reachable, GitHub CLI auth, built-in MCP reachability |
| **MODELS** | `checks/model-resolution.ts` | models.json cache exists, per-agent fallback resolution, category overrides valid, provider availability |
## SUPPORTING CHECK FILES (25 total)
```
checks/
├── index.ts # Registration
├── system.ts # Main System aggregator
├── system-binary.ts # OpenCode binary discovery (PATH + desktop app)
├── system-plugin.ts # opencode.json plugin entry detection
├── system-loaded-version.ts # Cache vs npm latest
├── config.ts # Main Config aggregator
├── tools.ts # Main Tools aggregator
├── dependencies.ts # AST-Grep CLI/NAPI + comment-checker presence
├── tools-gh.ts # gh cli install + auth status
├── tools-lsp.ts # LSP server enumeration
├── tools-mcp.ts # Built-in + user MCP reachability
├── model-resolution.ts # Main Models aggregator
├── model-resolution-cache.ts # models.json presence + freshness
├── model-resolution-config.ts # oh-my-opencode.jsonc parse
├── model-resolution-effective-model.ts # Per-agent fallback chain trace
├── model-resolution-variant.ts # Model variant (max, high, medium) handling
├── model-resolution-details.ts # Verbose output formatter
└── model-resolution-types.ts # Shared types
```
## EXECUTION FLOW
```
doctor command
→ runner.ts: parallel check execution with 30s per-check timeout
→ checks/index.ts registers all 4 category checks
→ each check returns: { status: "ok" | "warn" | "error", detail: string }
→ formatter.ts: render to stdout (text/status/json)
→ exit code: 0 (all ok) | 1 (errors) | 2 (warnings only)
```
## KEY FILES
| File | Purpose |
|------|---------|
| `index.ts` | CLI command entry, flag parsing |
| `runner.ts` | Parallel `Promise.allSettled()` orchestration, 30s timeout per check |
| `formatter.ts` | Pretty printing: colored status, hierarchical output |
| `types.ts` | `DoctorCheck`, `CheckResult`, `DoctorReport` types |
## HOW TO ADD A CHECK
1. Create `src/cli/doctor/checks/{name}.ts` exporting check function matching `DoctorCheck`
2. Register in `checks/index.ts`
3. Category-level aggregator (system/config/tools/model-resolution) invokes it
4. Return `{ status, detail }` — no throws, all errors caught by runner
## EXIT CODES
- `0`: All checks passed (or only info messages)
- `1`: One or more errors — plugin will likely not work
- `2`: Warnings only — plugin works with degraded features
@@ -34,7 +34,7 @@ describe("loadAvailableModelsFromCache", () => {
join(tempDir, "cache", "opencode", "models.json"), join(tempDir, "cache", "opencode", "models.json"),
JSON.stringify({ JSON.stringify({
openai: { models: { "gpt-5.4": {} } }, openai: { models: { "gpt-5.4": {} } },
anthropic: { models: { "claude-opus-4-6": {}, "claude-sonnet-4-6": {} } }, anthropic: { models: { "claude-opus-4-7": {}, "claude-sonnet-4-6": {} } },
}) })
) )
@@ -14,7 +14,7 @@ describe("model-resolution check", () => {
// then: Should have agent entries // then: Should have agent entries
const sisyphus = info.agents.find((a) => a.name === "sisyphus") const sisyphus = info.agents.find((a) => a.name === "sisyphus")
expect(sisyphus).toBeDefined() expect(sisyphus).toBeDefined()
expect(sisyphus!.requirement.fallbackChain[0]?.model).toBe("claude-opus-4-6") expect(sisyphus!.requirement.fallbackChain[0]?.model).toBe("claude-opus-4-7")
expect(sisyphus!.requirement.fallbackChain[0]?.providers).toContain("anthropic") expect(sisyphus!.requirement.fallbackChain[0]?.providers).toContain("anthropic")
}) })
@@ -42,7 +42,7 @@ describe("model-resolution check", () => {
// given: User has override for oracle agent // given: User has override for oracle agent
const mockConfig = { const mockConfig = {
agents: { agents: {
oracle: { model: "anthropic/claude-opus-4-6" }, oracle: { model: "anthropic/claude-opus-4-7" },
}, },
} }
@@ -51,8 +51,8 @@ describe("model-resolution check", () => {
// then: Oracle should show the override // then: Oracle should show the override
const oracle = info.agents.find((a) => a.name === "oracle") const oracle = info.agents.find((a) => a.name === "oracle")
expect(oracle).toBeDefined() expect(oracle).toBeDefined()
expect(oracle!.userOverride).toBe("anthropic/claude-opus-4-6") expect(oracle!.userOverride).toBe("anthropic/claude-opus-4-7")
expect(oracle!.effectiveResolution).toBe("User override: anthropic/claude-opus-4-6") expect(oracle!.effectiveResolution).toBe("User override: anthropic/claude-opus-4-7")
}) })
it("shows user override for category when configured", async () => { it("shows user override for category when configured", async () => {
@@ -169,13 +169,13 @@ describe("model-resolution check", () => {
const info = getModelResolutionInfoWithOverrides({ const info = getModelResolutionInfoWithOverrides({
agents: { agents: {
oracle: { model: "anthropic/claude-opus-4-6-thinking" }, oracle: { model: "anthropic/claude-opus-4-7-thinking" },
}, },
}) })
const oracle = info.agents.find((agent) => agent.name === "oracle") const oracle = info.agents.find((agent) => agent.name === "oracle")
expect(oracle).toBeDefined() expect(oracle).toBeDefined()
expect(oracle!.effectiveModel).toBe("anthropic/claude-opus-4-6-thinking") expect(oracle!.effectiveModel).toBe("anthropic/claude-opus-4-7-thinking")
expect(oracle!.capabilityDiagnostics).toMatchObject({ expect(oracle!.capabilityDiagnostics).toMatchObject({
resolutionMode: "alias-backed", resolutionMode: "alias-backed",
canonicalization: { canonicalization: {
+8
View File
@@ -40,6 +40,7 @@ export function formatConfigSummary(config: InstallConfig): string {
lines.push(formatProvider("OpenCode Zen", config.hasOpencodeZen, "opencode/ models")) lines.push(formatProvider("OpenCode Zen", config.hasOpencodeZen, "opencode/ models"))
lines.push(formatProvider("Z.ai Coding Plan", config.hasZaiCodingPlan, "Librarian/Multimodal")) lines.push(formatProvider("Z.ai Coding Plan", config.hasZaiCodingPlan, "Librarian/Multimodal"))
lines.push(formatProvider("Kimi For Coding", config.hasKimiForCoding, "Sisyphus/Prometheus fallback")) lines.push(formatProvider("Kimi For Coding", config.hasKimiForCoding, "Sisyphus/Prometheus fallback"))
lines.push(formatProvider("Vercel AI Gateway", config.hasVercelAiGateway, "universal proxy"))
lines.push("") lines.push("")
lines.push(color.dim("─".repeat(40))) lines.push(color.dim("─".repeat(40)))
@@ -153,6 +154,10 @@ export function validateNonTuiArgs(args: InstallArgs): { valid: boolean; errors:
errors.push(`Invalid --kimi-for-coding value: ${args.kimiForCoding} (expected: no, yes)`) errors.push(`Invalid --kimi-for-coding value: ${args.kimiForCoding} (expected: no, yes)`)
} }
if (args.vercelAiGateway !== undefined && !["no", "yes"].includes(args.vercelAiGateway)) {
errors.push(`Invalid --vercel-ai-gateway value: ${args.vercelAiGateway} (expected: no, yes)`)
}
return { valid: errors.length === 0, errors } return { valid: errors.length === 0, errors }
} }
@@ -167,6 +172,7 @@ export function argsToConfig(args: InstallArgs): InstallConfig {
hasZaiCodingPlan: args.zaiCodingPlan === "yes", hasZaiCodingPlan: args.zaiCodingPlan === "yes",
hasKimiForCoding: args.kimiForCoding === "yes", hasKimiForCoding: args.kimiForCoding === "yes",
hasOpencodeGo: args.opencodeGo === "yes", hasOpencodeGo: args.opencodeGo === "yes",
hasVercelAiGateway: args.vercelAiGateway === "yes",
} }
} }
@@ -179,6 +185,7 @@ export function detectedToInitialValues(detected: DetectedConfig): {
zaiCodingPlan: BooleanArg zaiCodingPlan: BooleanArg
kimiForCoding: BooleanArg kimiForCoding: BooleanArg
opencodeGo: BooleanArg opencodeGo: BooleanArg
vercelAiGateway: BooleanArg
} { } {
let claude: ClaudeSubscription = "no" let claude: ClaudeSubscription = "no"
if (detected.hasClaude) { if (detected.hasClaude) {
@@ -194,5 +201,6 @@ kimiForCoding: BooleanArg
zaiCodingPlan: detected.hasZaiCodingPlan ? "yes" : "no", zaiCodingPlan: detected.hasZaiCodingPlan ? "yes" : "no",
kimiForCoding: detected.hasKimiForCoding ? "yes" : "no", kimiForCoding: detected.hasKimiForCoding ? "yes" : "no",
opencodeGo: detected.hasOpencodeGo ? "yes" : "no", opencodeGo: detected.hasOpencodeGo ? "yes" : "no",
vercelAiGateway: detected.hasVercelAiGateway ? "yes" : "no",
} }
} }
+1
View File
@@ -11,6 +11,7 @@ export interface ProviderAvailability {
zai: boolean zai: boolean
kimiForCoding: boolean kimiForCoding: boolean
opencodeGo: boolean opencodeGo: boolean
vercelAiGateway: boolean
isMaxPlan: boolean isMaxPlan: boolean
} }
+73 -8
View File
@@ -16,6 +16,7 @@ function createConfig(overrides: Partial<InstallConfig> = {}): InstallConfig {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
...overrides, ...overrides,
} }
} }
@@ -380,7 +381,7 @@ describe("generateModelConfig", () => {
const result = generateModelConfig(config) const result = generateModelConfig(config)
// #then // #then
expect(result.agents?.sisyphus?.model).toBe("anthropic/claude-opus-4.6") expect(result.agents?.sisyphus?.model).toBe("anthropic/claude-opus-4-7")
}) })
test("Sisyphus is created when multiple fallback providers are available", () => { test("Sisyphus is created when multiple fallback providers are available", () => {
@@ -397,7 +398,7 @@ describe("generateModelConfig", () => {
const result = generateModelConfig(config) const result = generateModelConfig(config)
// #then // #then
expect(result.agents?.sisyphus?.model).toBe("anthropic/claude-opus-4.6") expect(result.agents?.sisyphus?.model).toBe("anthropic/claude-opus-4-7")
}) })
test("Sisyphus resolves to gpt-5.4 medium when only OpenAI is available", () => { test("Sisyphus resolves to gpt-5.4 medium when only OpenAI is available", () => {
@@ -572,13 +573,9 @@ describe("generateModelConfig", () => {
// #when generateModelConfig is called // #when generateModelConfig is called
const result = generateModelConfig(config) const result = generateModelConfig(config)
// #then explore should not have fallback_models (only one chain entry matches) // #then explore should not have fallback_models (only one distinct chain entry matches)
expect(result.agents?.explore?.model).toBe("anthropic/claude-haiku-4-5") expect(result.agents?.explore?.model).toBe("anthropic/claude-haiku-4-5")
expect(result.agents?.explore?.fallback_models).toEqual([ expect(result.agents?.explore?.fallback_models).toBeUndefined()
{
model: "anthropic/claude-haiku-4.5",
},
])
}) })
test("librarian includes fallback_models when opencode-go and Claude are both available", () => { test("librarian includes fallback_models when opencode-go and Claude are both available", () => {
@@ -607,6 +604,74 @@ describe("generateModelConfig", () => {
}) })
}) })
describe("Vercel AI Gateway provider", () => {
test("uses vercel/ model strings when only Vercel AI Gateway is available", () => {
// #given only Vercel AI Gateway is available
const config = createConfig({ hasVercelAiGateway: true })
// #when generateModelConfig is called
const result = generateModelConfig(config)
// #then should use vercel/<sub-provider>/<model> format
expect(result).toMatchSnapshot()
})
test("uses vercel/ model strings with isMax20 flag", () => {
// #given Vercel AI Gateway is available with Max 20 plan
const config = createConfig({ hasVercelAiGateway: true, isMax20: true })
// #when generateModelConfig is called
const result = generateModelConfig(config)
// #then should use higher capability models via gateway
expect(result).toMatchSnapshot()
})
test("explore uses vercel/minimax/minimax-m2.7-highspeed when only gateway available", () => {
// #given only Vercel AI Gateway is available
const config = createConfig({ hasVercelAiGateway: true })
// #when generateModelConfig is called
const result = generateModelConfig(config)
// #then explore should use gateway-routed minimax (preferred over claude-haiku)
expect(result.agents?.explore?.model).toBe("vercel/minimax/minimax-m2.7-highspeed")
})
test("librarian uses vercel/minimax/minimax-m2.7 when only gateway available", () => {
// #given only Vercel AI Gateway is available
const config = createConfig({ hasVercelAiGateway: true })
// #when generateModelConfig is called
const result = generateModelConfig(config)
// #then librarian should use gateway-routed minimax (preferred over claude-haiku)
expect(result.agents?.librarian?.model).toBe("vercel/minimax/minimax-m2.7")
})
test("Hephaestus is created when only Vercel AI Gateway is available", () => {
// #given only Vercel AI Gateway is available
const config = createConfig({ hasVercelAiGateway: true })
// #when generateModelConfig is called
const result = generateModelConfig(config)
// #then hephaestus should be created with gateway-routed gpt-5.4
expect(result.agents?.hephaestus?.model).toBe("vercel/openai/gpt-5.4")
})
test("native providers take priority over gateway", () => {
// #given Claude and Vercel AI Gateway are both available
const config = createConfig({ hasClaude: true, hasVercelAiGateway: true })
// #when generateModelConfig is called
const result = generateModelConfig(config)
// #then should prefer native anthropic over gateway
expect(result.agents?.sisyphus?.model).toBe("anthropic/claude-opus-4-7")
})
})
describe("schema URL", () => { describe("schema URL", () => {
test("always includes correct schema URL", () => { test("always includes correct schema URL", () => {
// #given any config // #given any config
+6 -1
View File
@@ -105,7 +105,8 @@ export function generateModelConfig(config: InstallConfig): GeneratedOmoConfig {
avail.copilot || avail.copilot ||
avail.zai || avail.zai ||
avail.kimiForCoding || avail.kimiForCoding ||
avail.opencodeGo avail.opencodeGo ||
avail.vercelAiGateway
if (!hasAnyProvider) { if (!hasAnyProvider) {
return { return {
$schema: SCHEMA_URL, $schema: SCHEMA_URL,
@@ -130,6 +131,8 @@ export function generateModelConfig(config: InstallConfig): GeneratedOmoConfig {
agentConfig = { model: "opencode-go/minimax-m2.7" } agentConfig = { model: "opencode-go/minimax-m2.7" }
} else if (avail.zai) { } else if (avail.zai) {
agentConfig = { model: ZAI_MODEL } agentConfig = { model: ZAI_MODEL }
} else if (avail.vercelAiGateway) {
agentConfig = { model: "vercel/minimax/minimax-m2.7" }
} }
if (agentConfig) { if (agentConfig) {
agents[role] = attachAllFallbackModels(agentConfig, req.fallbackChain, avail) agents[role] = attachAllFallbackModels(agentConfig, req.fallbackChain, avail)
@@ -147,6 +150,8 @@ export function generateModelConfig(config: InstallConfig): GeneratedOmoConfig {
agentConfig = { model: "opencode-go/minimax-m2.7" } agentConfig = { model: "opencode-go/minimax-m2.7" }
} else if (avail.copilot) { } else if (avail.copilot) {
agentConfig = { model: "github-copilot/gpt-5-mini" } agentConfig = { model: "github-copilot/gpt-5-mini" }
} else if (avail.vercelAiGateway) {
agentConfig = { model: "vercel/minimax/minimax-m2.7-highspeed" }
} else { } else {
agentConfig = { model: "opencode/gpt-5-nano" } agentConfig = { model: "opencode/gpt-5-nano" }
} }
@@ -14,6 +14,7 @@ function createConfig(overrides: Partial<InstallConfig> = {}): InstallConfig {
hasZaiCodingPlan: false, hasZaiCodingPlan: false,
hasKimiForCoding: false, hasKimiForCoding: false,
hasOpencodeGo: false, hasOpencodeGo: false,
hasVercelAiGateway: false,
...overrides, ...overrides,
} }
} }
+2
View File
@@ -13,6 +13,7 @@ export function toProviderAvailability(config: InstallConfig): ProviderAvailabil
zai: config.hasZaiCodingPlan, zai: config.hasZaiCodingPlan,
kimiForCoding: config.hasKimiForCoding, kimiForCoding: config.hasKimiForCoding,
opencodeGo: config.hasOpencodeGo, opencodeGo: config.hasOpencodeGo,
vercelAiGateway: config.hasVercelAiGateway,
isMaxPlan: config.isMax20, isMaxPlan: config.isMax20,
} }
} }
@@ -27,6 +28,7 @@ export function isProviderAvailable(provider: string, availability: ProviderAvai
"zai-coding-plan": availability.zai, "zai-coding-plan": availability.zai,
"kimi-for-coding": availability.kimiForCoding, "kimi-for-coding": availability.kimiForCoding,
"opencode-go": availability.opencodeGo, "opencode-go": availability.opencodeGo,
vercel: availability.vercelAiGateway,
} }
return mapping[provider] ?? false return mapping[provider] ?? false
} }

Some files were not shown because too many files have changed in this diff Show More