From b555d46a4a0e83f8573e3c8b6776c23d8c72b9e2 Mon Sep 17 00:00:00 2001 From: Javier Gomez <113129149+Javierg9n4@users.noreply.github.com> Date: Tue, 9 Sep 2025 19:11:33 +0200 Subject: [PATCH] feat: add OpenCode integration implementation plan for BMAD-METHOD --- ...pencode-integration-implementation-plan.md | 165 ++++++++++++++++++ docs/opencode-integration-plan.md | 152 ++++++++++++++++ 2 files changed, 317 insertions(+) create mode 100644 docs/opencode-integration-implementation-plan.md create mode 100644 docs/opencode-integration-plan.md diff --git a/docs/opencode-integration-implementation-plan.md b/docs/opencode-integration-implementation-plan.md new file mode 100644 index 00000000..b065ff00 --- /dev/null +++ b/docs/opencode-integration-implementation-plan.md @@ -0,0 +1,165 @@ +# OpenCode Integration Implementation Plan (Single PR, Small Commits) + +This document describes how we’ll implement the OpenCode (SST) integration for BMAD-METHOD in a single PR composed of small, focused commits that comply with the repository’s CONTRIBUTING guidelines. + +## Scope and Constraints + +- JSON-only project-level integration (no Markdown generation). +- Existing project `opencode.json(c)`: + - Only add BMAD `agent` and `command` entries. + - Ensure `instructions` includes a single entry: `.bmad-core/core-config.yaml`. + - Do not modify other top-level fields (e.g., `theme`, `model`, `small_model`, `permission`). +- No project `opencode.json(c)`: + - Create a minimal `opencode.jsonc` with `$schema`, `instructions: [".bmad-core/core-config.yaml"]`, and `agent`/`command` populated. + - Intentionally omit top-level `theme`, `model`, `small_model`, and `permission` to avoid overriding a global config. +- Idempotent behavior: safe re-runs; no duplication; preserve user entries and JSONC comments. +- Path mapping: Source is `bmad-core/...` in this repo; installed project references must use `.bmad-core/...` with POSIX-style `./`-prefixed relative paths. + +## Single-PR Strategy + +- Base branch: `next` (per CONTRIBUTING recommendations for new features). +- One PR containing ~6–9 small commits; each commit is independently reviewable and keeps the PR within the 200–400 LOC ideal (max 800 LOC). +- Each commit runs the standard validation: `npm run pre-release` (or at minimum `npm run format:check` and `npm run lint`). + +## Commit-by-Commit Plan + +1. docs(opencode): add implementation plan (this file) + +- Goal: Check in the execution plan to guide the PR. +- Files: `docs/opencode-integration-implementation-plan.md` +- Validation: `npm run format:check` and `npm run lint` + +2. feat(installer): register opencode target (metadata only) + +- Goal: Add `opencode` to installer config (no runtime behavior yet). +- Files: `tools/installer/config/install.config.yaml` +- Validation: `npm run lint` + +3. chore(deps): add JSONC support for config IO + +- Goal: Add dependency to parse/write JSONC while preserving comments. +- Choice: `comment-json` (parse + stringify with comments) +- Files: `package.json` (+ lockfile updates by package manager) +- Validation: install completes; `npm run lint` + +4. feat(installer): scaffold opencode handler (detect-only) + +- Goal: Wire `case 'opencode'` and add `setupOpenCode()` with dry-run detection/logging (no write operations yet). +- Files: `tools/installer/lib/ide-setup.js` +- Validation: run the installer in a test repo; verify it detects an existing or missing config and exits without modifications. + +5. feat(installer): minimal config creation/merge (instructions only) + +- Goal: + - If config exists: ensure `instructions` contains `.bmad-core/core-config.yaml` (append once). + - If config is missing: create minimal `opencode.jsonc` with `$schema` and `instructions` only (empty `agent` and `command`). +- Files: `tools/installer/lib/ide-setup.js` (and optional `tools/installer/lib/opencode-config.js` helper) +- Validation: re-run safely; confirm idempotence. + +6. feat(installer): add agent mapping + merge + +- Goal: Map BMAD agents (core + expansions) to OpenCode `agent` entries with: + - `description`, `mode`, `prompt: {file:...}`, default `tools`/`permission` by role. + - Optional name prefix `bmad-`. +- Files: `tools/installer/lib/ide-setup.js` (and optional `tools/installer/lib/opencode-map.js` helper) +- Validation: verify agents are added once; re-run remains stable. + +7. feat(installer): add command mapping + merge + +- Goal: Map BMAD tasks to OpenCode `command` entries: + - `template`: `{file:...}` (standardize on `{file:...}`; do not mix with `@file`). + - `description` and optional `agent` per task. +- Files: `tools/installer/lib/ide-setup.js` +- Validation: verify commands are added once; re-run remains stable. + +8. feat(installer): polish UX (prefix prompt + summary) + +- Goal: Add a prompt to apply `bmad-` prefix to names; output a concise summary of added/updated/skipped entries and config path. +- Files: `tools/installer/lib/ide-setup.js` +- Validation: manual smoke in a test repo with and without pre-existing config. + +9. docs(opencode): user guide update (JSON-only usage) + +- Goal: Add a short OpenCode section in `docs/user-guide.md` describing usage and re-run behavior. +- Files: `docs/user-guide.md` +- Validation: `npm run format:check` and `npm run lint` + +## Technical Details & Contracts + +- Config detection order: `opencode.jsonc` → `opencode.json` → create `opencode.jsonc`. +- JSONC parsing/writing: use `comment-json` to preserve comments where present. +- Existing config path: + - Only modify `instructions` (append `.bmad-core/core-config.yaml` if missing), `agent`, and `command` sections. + - Never change top-level `theme`, `model`, `small_model`, or `permission`. +- New config path: + - Create minimal file with `$schema`, `instructions`, `agent`, and `command`. + - Exclude top-level `theme`, `model`, `small_model`, `permission`. +- Agent defaults (examples): + - dev/build-like: `tools: { write: true, edit: true, bash: true }`, `permission: { edit: "allow", bash: "ask" }` + - pm/analyst/plan: `tools: { write: false, edit: false, bash: false }`, `permission: { edit: "deny", bash: "deny" }` + - qa: `tools: { write: true, edit: true, bash: false }`, `permission: { edit: "ask", bash: "deny" }` +- Commands: `template` references to BMAD tasks via `{file:...}` or `@file` strings; optional `agent` per task. +- Commands: `template` references use `{file:...}` consistently; optional `agent` per task (explicit where sensible). +- Prefix: Optional `bmad-` applied consistently to agent and command keys to avoid collisions. +- Idempotence: Re-runs should not duplicate or clobber user-defined entries; only update BMAD-managed keys. +- Mode values: restrict to `primary` and `subagent` unless spec confirms more. +- Default tools: minimal `{ write, edit, bash }` to avoid schema drift; extend later if needed. + +### Collision strategy and BMAD-managed detection + +- Collision handling (when prefix is off): + - If an unprefixed key exists and is not BMAD-managed → skip and warn; suggest `--prefix bmad-`. + - If a key is BMAD-managed → update idempotently. +- BMAD-managed detection: + - Agent with `prompt` pointing into `.bmad-core/agents` or `.bmad-core/expansion-packs/.../agents`. + - Command with `template` pointing into `.bmad-core/tasks` or `.bmad-core/expansion-packs/.../tasks`. + +## Minimal JSONC Example (New Project Config) + +```jsonc +{ + "$schema": "https://opencode.ai/config.json", + "instructions": [".bmad-core/core-config.yaml"], + "agent": { + "dev": { + "description": "Product development / implementation agent", + "mode": "primary", + "prompt": "{file:./.bmad-core/agents/dev.md}", + "tools": { "write": true, "edit": true, "bash": true }, + "permission": { "edit": "allow", "bash": "ask" }, + }, + }, + "command": { + "test-design": { + "description": "Design tests based on the test levels framework", + "agent": "qa", + "template": "{file:./.bmad-core/tasks/test-design.md}", + }, + }, +} +``` + +## Validation & QA + +- Automated (prefer Bun, npm fallback): + - `bun run format:check` (or `npm run format:check`) + - `bun run lint` (or `npm run lint`) + - Optionally `bun run pre-release` (or `npm run pre-release`) +- Manual smoke (in a temp repo): + - With no `opencode.json(c)`: creates minimal JSONC, adds agents/commands. + - With an existing `opencode.jsonc`: merges agents/commands and appends `.bmad-core/core-config.yaml` to `instructions` if missing; preserves other top-level fields and comments. + - Re-run: no duplicates; only new/changed BMAD entries update. + +## Acceptance Criteria + +- Selecting `Opencode` integrates BMAD agents/commands into project-level `opencode.json(c)` or creates a minimal `opencode.jsonc`. +- Existing configs are preserved; only `instructions`, `agent`, and `command` are touched. +- Minimal new config contains only: `$schema`, `instructions`, `agent`, `command` (no theme/model/permission at top level). +- Idempotent behavior and expansion pack support are verified. +- User guide updated with JSON-only usage and re-run behavior. + +## Out of Scope (Future) + +- Markdown-based agent/command generation. +- Advanced provider-specific model settings at top-level. +- Force-overwrite behavior for colliding user-owned keys. diff --git a/docs/opencode-integration-plan.md b/docs/opencode-integration-plan.md new file mode 100644 index 00000000..017244fc --- /dev/null +++ b/docs/opencode-integration-plan.md @@ -0,0 +1,152 @@ +# BMAD-METHOD × OpenCode (SST) Integration Plan (JSON-only) + +This plan delivers first-class OpenCode CLI/TUI integration for BMAD-METHOD using a project-level `opencode.json`/`opencode.jsonc` — no Markdown generation fallback. It mirrors our Codex integration goals and prioritizes file references to BMAD sources so updates flow automatically. + +## Objectives + +- Generate/merge a project-level OpenCode config with BMAD agents and commands. +- Use file references (`{file:...}` and `@file`) to avoid duplicating BMAD content. +- Support all relevant agent/command options in OpenCode JSON. +- Be idempotent and non-destructive when a project already has `opencode.json(c)`. +- Minimize name collisions; optionally prefix names with `bmad-`. + +## References + +- Config: https://opencode.ai/docs/config/ +- Agents: https://opencode.ai/docs/agents/#configure +- Commands: https://opencode.ai/docs/commands/ + +## High-Level Approach + +1. Add a new IDE target `opencode` in the installer. +2. Detect an existing project-level `opencode.jsonc` or `opencode.json`; if none, create `opencode.jsonc`. +3. Merge BMAD agents and commands into the config using file references to BMAD source files. +4. Preserve user entries; only add or update BMAD-managed keys. +5. Support expansion packs using the same mapping and relative path logic. + +## Path mapping (source → installed) + +- Source in this repo: `bmad-core/...` and `expansion-packs/...`. +- Installed in a user project: `.bmad-core/...` and `.bmad-core/expansion-packs/...`. +- All `opencode.json(c)` references must target the installed `.bmad-core/...` paths and be POSIX-style, `./`-prefixed relative to the project root. + +## Mapping BMAD → OpenCode (JSON-only) + +- Agents (from `.bmad-core/agents/*.md` and expansion packs) → `agent` entries: + - Key: agent ID (optionally with prefix, e.g., `bmad-dev`). + - Fields supported: + - `description`: from BMAD YAML `whenToUse` or a generated fallback. + - `mode`: `primary` | `subagent` (map core roles to `primary`, specialists to `subagent`). + - `prompt`: `{file:./relative/path/to/.bmad-core/agents/{agent}.md}` (or expansion path). + - Optional: `model`, `temperature`. + - `tools`: conservative defaults `{ write: true, edit: true, bash: true }` (add more later as needed). + - `permission`: `{ edit: allow|ask|deny, bash: allow|ask|deny|{pattern map}, webfetch: allow|ask|deny }`. + - Provider-specific options pass through unchanged. + +- Commands (from `.bmad-core/tasks/*.md`, `common/tasks/*.md`, and expansion tasks) → `command` entries: + - Key: task ID (optionally with prefix, e.g., `bmad-test-design`). + - Fields supported: + - `template`: `{file:./relative/path/to/task.md}` (use `{file:...}` consistently). + - `description`: from the task’s heading/summary or a generated fallback. + - `agent`: optional; set explicitly where sensible (e.g., `dev`, `pm`, `qa`). If omitted, OpenCode’s default applies. + - `model`: optional override per command. + +## Project Config Creation/Merge Strategy + +- Detection order: `opencode.jsonc` → `opencode.json` → create `opencode.jsonc`. +- `$schema`: `https://opencode.ai/config.json`. +- Existing project config present: + - Only add BMAD `agent` and `command` entries. + - Ensure `instructions` includes the single entry: `.bmad-core/core-config.yaml` (append if missing). + - Do not add or modify other top-level fields (e.g., `theme`, `model`, `small_model`, `permission`). + - Idempotent: preserve user entries and comments; never remove non-BMAD entries. +- No project config present: + - Create a minimal `opencode.jsonc` containing: + - `$schema`: `https://opencode.ai/config.json` + - `instructions`: [ ".bmad-core/core-config.yaml" ] + - `agent`: { ...BMAD agents... } + - `command`: { ...BMAD commands... } + - Intentionally do NOT set `theme`, `model`, `small_model`, or `permission` here to avoid overriding a global configuration. + - Paths must be relative to the project root. + +## Defaults for Tools & Permissions + +- dev/build-like agents: `tools: { write: true, edit: true, bash: true }`, `permission: { edit: "allow", bash: "ask" }`. +- pm/analyst/plan: `tools: { write: false, edit: false, bash: false }`, `permission: { edit: "deny", bash: "deny" }`. +- qa: `tools: { write: true, edit: true, bash: false }`, `permission: { edit: "ask", bash: "deny" }`. +- reviewer/read-only: `tools: { write: false, edit: false, bash: false }`, `permission: { edit: "deny", bash: "deny" }`. + +## Installer UX & Flow + +- When `opencode` is selected: + - Detect `opencode.jsonc` or `opencode.json` at project root. + - If config exists: add BMAD `agent`/`command` and ensure `.bmad-core/core-config.yaml` is present in `instructions` (no other top-level changes). + - If config does not exist: create minimal `opencode.jsonc` with `$schema`, `instructions: [".bmad-core/core-config.yaml"]`, `agent`, and `command`. + - Ask: “Prefix agent/command names with `bmad-`?” (default: off). + - Output a summary of added/updated/skipped entries and the config file path. + +## Implementation Plan (code) + +1. Config entry: add `opencode` to `tools/installer/config/install.config.yaml` with a brief description. +2. Switch wiring: in `tools/installer/lib/ide-setup.js`, add `case 'opencode': return this.setupOpenCode(installDir, selectedAgent, { prefix });`. +3. Implement `setupOpenCode(installDir, selectedAgent, { prefix })`: + - Resolve project root, detect existing OpenCode config file. + - Parse with a JSONC-capable parser (e.g., `jsonc-parser` or `comment-json`). + - Build BMAD agent and command maps using existing helpers (agents/tasks from core + expansion packs). + - Apply defaults (tools/permissions) by agent category. + - Merge into `agent`/`command` sections (idempotent, preserve user entries). + - Write back preserving comments/format when possible. +4. Docs: update `docs/user-guide.md` with an OpenCode section describing usage in JSON mode and re-run behavior. +5. Optional: add npm script if `package.json` exists: `"bmad:opencode": "bmad-method install -f -i opencode"`. + +## JSONC Example (minimal project-level config) + +```jsonc +{ + "$schema": "https://opencode.ai/config.json", + "instructions": [ ".bmad-core/core-config.yaml" ], + "agent": { + "dev": { + "description": "Product development / implementation agent", + "mode": "primary", + "prompt": "{file:./.bmad-core/agents/dev.md}", + "tools": { "write": true, "edit": true, "bash": true }, + "permission": { "edit": "allow", "bash": "ask" } + }, + "pm": { + "description": "Product management and planning agent", + "mode": "primary", + "prompt": "{file:./.bmad-core/agents/pm.md}", + "tools": { "write": false, "edit": false, "bash": false }, + "permission": { "edit": "deny", "bash": "deny" } + } + }, + "command": { + "review-changes": { + "description": "Review recent changes", + "agent": "dev", + "template": "{file:./.bmad-core/tasks/review-changes.md}" + }, + "test-design": { + "description": "Design tests based on the test levels framework", + "agent": "qa", + "template": "{file:./.bmad-core/tasks/test-design.md}" + } + } +} + +## Name collisions and BMAD-managed detection + +- Collision handling (when prefix is off): + - If an unprefixed key exists and is not BMAD-managed → skip and report a collision; suggest re-run with `--prefix bmad-`. + - If a key is BMAD-managed → update it idempotently. +- BMAD-managed detection heuristics: + - Agent with `prompt` referencing `.bmad-core/agents` or `.bmad-core/expansion-packs/.../agents`. + - Command with `template` referencing `.bmad-core/tasks` or `.bmad-core/expansion-packs/.../tasks`. + +## Acceptance Criteria + +- Selecting `Opencode` merges BMAD agents/commands into a project’s `opencode.json(c)` or creates a new `opencode.jsonc`. +- Agents reference BMAD agent files via `prompt: {file:...}`; commands reference tasks via `template`. +- Doc updates describe how to use the integration and how it behaves on updates. +```