Repository navigation
fix: tolerate hosts without ctx.permission.rules on session.create - #43
abcdef8751 wants to merge 1 commit into
Conversation
opencode 2.0.27+ no longer exposes permission.rules on the plugin context (the permission domain is request/reply/list/get/asked only). The V2 client called it unconditionally after every session.create, so team_spawn crashed for every teammate. Feature-detect the method: the re-assert was already best-effort (the create-input permissions are still applied), so skip it cleanly when the host lacks it. Covered by a regression test. Resolves an upstream OQ (V2-rules) blocking all spawns on current hosts.
|
Confirmed working on OpenCode 2.0.32 (Windows, Node/Electron desktop + CLI). Repro of the 0.18.0 bug: every team_spawn fails with 'ctx.permission.rules is not a function' (same as issue #40), tripping the spawn circuit breaker. Important discovery: applying this PR only to dist/ is NOT enough — OpenCode 2.0.x loads the plugin from src/index.ts and transpiles TypeScript at load time (verified via server logs: 'loading plugin ... entrypoint=file:///.../src/index.ts'). After patching src/v2-client.ts with the exact guard from this PR, spawn works again end-to-end: 2 teammates spawned with explicit models (opencode/deepseek-v4.1-flash-free and opencode/nemotron-3.5-super-vl-free), completed, and shut down cleanly. Suggestion: merge quickly and consider publishing 0.18.1+ so Desktop/CLI 2.0.27+ users don't have to hand-patch their npm cache (which gets wiped on plugin reinstall). Thanks for the plugin! |
…, read-only agents (#46) fixes the `team_spawn` crash + silent worktree failure from #40 on opencode 2.0.19+, plus the stuff that still stops teammates from working after that. ## vs #41 / #43 both guard `ctx.permission.rules`, #41 also validates `depends_on`. this does both, plus: ▸ **worktree root cause**: #41 adds a warning but couldn't find why `worktree.create` made nothing. 2.0.19+ worktree endpoints need a `projectID`. ensemble never sent one → creation failed → everyone shared the base tree. now passes `ctx.location.project.id` to create/list/remove/refresh ▸ **detached worktrees (2.0.32+)**: opencode now does `git worktree add --detach` (`packages/core/src/git.ts`). teammate commits land on a detached HEAD → `team_merge`: "not something we can merge". if the new worktree has no branch, ensemble creates it ▸ **edits stuck on approval**: v2 checks in-location files as relative paths, so `edit <worktree>/** allow` never matched → ask nobody answers. worktree teammates also get `edit * allow`. outside-the-worktree stays behind `external_directory` ▸ **read-only detection**: was name-only (`plan`, `explore`). custom reviewers got a worktree + `shell * allow`. now reads the agent's own rules via `agent.get`, names as fallback not touched: the 4th #40 thing (notifications redelivered after purge). on `permission.rules`: since 2.0.19 core merges session rules *after* agent rules (`merge(agent, session)`, last match wins), so the `session.create` permissions already win. skipping `rules()` when it's gone loses nothing. ## verification ✓ `bun run typecheck` clean ✓ `bun test` 857 pass / 0 fail (new: projectID pass-through, detached naming, read-only from rules, `edit *`, unknown `depends_on`) ✓ `bun run lint` only pre-existing warnings ✓ live on **2.0.24 + 2.0.32**: ``` team_create → team_spawn(build, worktree) → own worktree + branch → commit → team_shutdown → team_merge ✓ → team_cleanup ``` ✗ not verified: subagent-mode teammates (`explore` etc.) on opencode's free `big-pickle`. they get "free tier can only be used from within OpenCode", built-ins too, so it looks like a host/provider thing, not ensemble. 🤖 Generated with [Claude Code](https://claude.com/claude-code) https://claude.ai/code/session_01GUtz6gBn7rhXaufK97d8cm --------- Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>
|
Closing as superseded — thank you for the report-quality guard work. All three open PRs (#41, #43, #46) fixed the same broken |
Problem
team_spawn(and any path callingclient.session.createwith permissions) crashes on current OpenCode hosts:opencode 2.0.27+ no longer exposes
permission.ruleson the plugin context — the permission domain is nowrequest/reply/list/get/askedonly. This is theOQ-V2-rulescall site: it was spike-verified against 2.0.3, and every spawn on newer hosts throws.Repro:
team_create+team_spawnon opencode v2.0.27 → spawn fails before the teammate session is usable.Fix
Feature-detect the method in
src/v2-client.ts:rules()call was already best-effort — the permission rules are shipped in thesession.createinput (permissions: [...]), and the post-create re-assert was only re-applying them after agent rules ran.rules(), skip it cleanly instead of throwing. Fail-open: create proceeds with the permissions that the host does honor.Testing
test/v2-client.test.ts):session.createwith a permission-lesspermissiondomain still succeeds, still ships the rules in the create input, and never calls the absentrules().rules()path test unchanged and still passing.bun run typecheck✅ ·bun test851 passing ✅ ·bun run build✅Note: this was also verified live — spawned two teammates on opencode v2.0.27, both ran their full team-messaging flow and shut down cleanly.