ai-team 1.0.2 → 1.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (63) hide show
  1. package/.agents/teams/web-product/README.md +1 -1
  2. package/.github/workflows/release.yml +40 -0
  3. package/.releaserc.json +34 -0
  4. package/CHANGELOG.md +39 -0
  5. package/README.md +9 -0
  6. package/docs/agents/README.md +2 -1
  7. package/docs/agents/handoffs/REL-NO-IDE-OVERLAYS/backend.md +100 -0
  8. package/docs/agents/handoffs/REL-NO-IDE-OVERLAYS/code-review.md +83 -0
  9. package/docs/agents/handoffs/REL-NO-IDE-OVERLAYS/frontend.md +24 -0
  10. package/docs/agents/handoffs/REL-NO-IDE-OVERLAYS/integration.md +51 -0
  11. package/docs/agents/handoffs/REL-NO-IDE-OVERLAYS/planning-agent.md +51 -0
  12. package/docs/agents/handoffs/REL-NO-IDE-OVERLAYS/qa.md +87 -0
  13. package/docs/agents/handoffs/REL-NO-IDE-OVERLAYS/requirement-analyst.md +75 -0
  14. package/docs/agents/handoffs/REL-SEMVER-AUTOPUBLISH/backend.md +77 -0
  15. package/docs/agents/handoffs/REL-SEMVER-AUTOPUBLISH/code-review.md +80 -0
  16. package/docs/agents/handoffs/REL-SEMVER-AUTOPUBLISH/frontend.md +22 -0
  17. package/docs/agents/handoffs/REL-SEMVER-AUTOPUBLISH/integration.md +65 -0
  18. package/docs/agents/handoffs/REL-SEMVER-AUTOPUBLISH/planning-agent.md +67 -0
  19. package/docs/agents/handoffs/REL-SEMVER-AUTOPUBLISH/qa.md +87 -0
  20. package/docs/agents/handoffs/REL-SEMVER-AUTOPUBLISH/requirement-analyst.md +77 -0
  21. package/docs/agents/knowledge/backend-dev.md +17 -0
  22. package/docs/agents/knowledge/code-reviewer.md +12 -0
  23. package/docs/agents/knowledge/frontend-dev.md +9 -0
  24. package/docs/agents/knowledge/planning-agent.md +32 -0
  25. package/docs/agents/knowledge/requirement-analyst.md +12 -0
  26. package/docs/agents/knowledge/tester.md +12 -0
  27. package/docs/agents/plans/REL-NO-IDE-OVERLAYS/plan.md +106 -0
  28. package/docs/agents/plans/REL-SEMVER-AUTOPUBLISH/plan.md +148 -0
  29. package/docs/cli.md +11 -2
  30. package/docs/plan.md +1 -1
  31. package/package.json +18 -9
  32. package/src/agents/definitions/agent-manager.yaml +2 -2
  33. package/src/agents/generate.js +104 -48
  34. package/src/cli.js +13 -0
  35. package/src/lib/template-registry.js +67 -25
  36. package/templates/bootstrap/{overlays/vscode-copilot/.vscode/mcp.json → base/.agents/mcp/vscode.json} +5 -2
  37. package/templates/bootstrap/base/.agents/teams/web-product/README.md +1 -1
  38. package/templates/bootstrap/manifest.json +5 -6
  39. package/tests/cli.integration.test.js +51 -0
  40. package/tests/sync-engine.test.js +30 -0
  41. package/tests/template-registry.test.js +48 -0
  42. package/templates/bootstrap/overlays/claude-code/.claude/agents/agent-manager.md +0 -153
  43. package/templates/bootstrap/overlays/claude-code/.claude/agents/backend-dev.md +0 -48
  44. package/templates/bootstrap/overlays/claude-code/.claude/agents/cli-dev.md +0 -47
  45. package/templates/bootstrap/overlays/claude-code/.claude/agents/code-reviewer.md +0 -52
  46. package/templates/bootstrap/overlays/claude-code/.claude/agents/documentation-writer.md +0 -56
  47. package/templates/bootstrap/overlays/claude-code/.claude/agents/frontend-dev.md +0 -47
  48. package/templates/bootstrap/overlays/claude-code/.claude/agents/planning-agent.md +0 -51
  49. package/templates/bootstrap/overlays/claude-code/.claude/agents/product-team-orchestrator.md +0 -51
  50. package/templates/bootstrap/overlays/claude-code/.claude/agents/requirement-analyst.md +0 -54
  51. package/templates/bootstrap/overlays/claude-code/.claude/agents/tester.md +0 -58
  52. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/agent-manager.agent.md +0 -164
  53. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/backend-dev.agent.md +0 -67
  54. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/cli-dev.agent.md +0 -57
  55. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/code-reviewer.agent.md +0 -64
  56. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/documentation-writer.agent.md +0 -72
  57. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/frontend-dev.agent.md +0 -66
  58. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/planning-agent.agent.md +0 -70
  59. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/product-team-orchestrator.agent.md +0 -82
  60. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/requirement-analyst.agent.md +0 -65
  61. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/tester-agent.agent.md +0 -69
  62. package/templates/bootstrap/overlays/vscode-copilot/.github/agents/tester.agent.md +0 -80
  63. /package/templates/bootstrap/{overlays/claude-code/.mcp.json → base/.agents/mcp/claude-code.json} +0 -0
@@ -0,0 +1,106 @@
1
+ # Implementation Plan — REL-NO-IDE-OVERLAYS
2
+
3
+ Date: 2026-02-23
4
+ Agent: planning-agent
5
+
6
+ ## Closeout Status (2026-02-23)
7
+
8
+ - Lifecycle status: **NOT COMPLETE**
9
+ - QA disposition: **FAIL** with execution checks **BLOCKED**
10
+ - Reason: required command execution evidence is missing for targeted tests, full suite, and CLI parity/drift checks.
11
+ - Required next commands:
12
+ - `node --test tests/template-registry.test.js`
13
+ - `node --test tests/sync-engine.test.js`
14
+ - `node --test tests/cli.integration.test.js`
15
+ - `pnpm test`
16
+ - `node src/cli.js init --target /tmp/rel-no-ide-overlays-vscode --ide vscode --team web-product --include-mcp --yes`
17
+ - `node src/cli.js doctor --target /tmp/rel-no-ide-overlays-vscode`
18
+ - `node src/cli.js init --target /tmp/rel-no-ide-overlays-claude --ide claude-code --team web-product --include-mcp --yes`
19
+ - `node src/cli.js doctor --target /tmp/rel-no-ide-overlays-claude`
20
+ - Edit an installed agent file, then run:
21
+ - `node src/cli.js plan --target <target>`
22
+ - `node src/cli.js update --target <target>`
23
+ - `node src/cli.js update --target <target> --force`
24
+
25
+ ## Objective
26
+
27
+ Remove committed IDE overlay agent files as an operational dependency and move to generation-driven IDE outputs while preserving existing CLI behavior for `init`, `plan`, `update`, and `doctor` across `vscode` and `claude-code`.
28
+
29
+ ## Implementation Approach
30
+
31
+ 1. **Decouple runtime install from committed overlay agent files**
32
+ - Shift agent-content sourcing from `templates/bootstrap/overlays/*/.../agents` to generated-in-memory (or generated-at-build) artifacts derived from `src/agents/definitions/*.yaml`.
33
+ - Keep IDE-specific rendering (filename/frontmatter/body) exactly aligned with current outputs.
34
+ 2. **Retain manifest-driven target mapping for IDE outputs**
35
+ - Keep manifest as authoritative for install target paths and MCP paths, but remove assumptions that agent source files must be present as committed overlay files.
36
+ 3. **Wire generation into template entry collection path**
37
+ - Update template collection flow so `collectTemplateEntries` receives generated agent entries per selected IDE, then feeds unchanged sync conflict/merge logic.
38
+ 4. **Preserve sync semantics and migration compatibility**
39
+ - Ensure `plan`/`update`/`doctor` drift detection and manifest hashing remain deterministic.
40
+ - Keep legacy layout migration behavior untouched unless strictly required for overlay removal.
41
+ 5. **Align docs with architecture change**
42
+ - Update repo docs to describe generation-driven IDE artifacts and remove wording that implies maintained overlay agent files.
43
+
44
+ ## File-Level Change List (implementation phase)
45
+
46
+ 1. `src/agents/generate.js`
47
+ - Refactor from “write directly into overlay directories” script toward reusable generation API consumed by runtime/template registry (CLI-safe import surface).
48
+ - Preserve current render logic for frontmatter/body/file naming parity.
49
+ 2. `src/lib/template-registry.js`
50
+ - Replace direct overlay agent file enumeration with generated IDE agent entries.
51
+ - Keep base assets and MCP handling behavior intact.
52
+ 3. `templates/bootstrap/manifest.json`
53
+ - Remove or simplify overlay metadata that assumes committed overlay agent roots while preserving IDE target path contracts (`.github/agents`, `.claude/agents`, MCP paths).
54
+ 4. `src/lib/sync-engine.js` (if needed only)
55
+ - Minimal compatibility adjustments if manifest shape or entry metadata changes require it.
56
+ 5. `README.md`
57
+ - Update architecture/behavior descriptions to reflect generated IDE agent outputs.
58
+ 6. `docs/cli.md`
59
+ - Update source-of-truth and layout contract language to non-overlay architecture.
60
+ 7. `templates/bootstrap/overlays/**` (agent files only)
61
+ - Remove committed IDE agent files once generation-backed sourcing is in place.
62
+ - Keep MCP template files unless relocated by agreed design.
63
+ 8. `tests/sync-engine.test.js`
64
+ - Update/add assertions proving generated agent entries still map to expected install targets and preserve drift behavior.
65
+ 9. `tests/cli.integration.test.js`
66
+ - Ensure end-to-end `init`/`doctor` still pass for at least one IDE after overlay agent removal.
67
+
68
+ ## Acceptance Checks (clear and testable)
69
+
70
+ 1. **No committed overlay agents required**
71
+ - Repository can remove `templates/bootstrap/overlays/*/*/agents/*` and `pnpm test` still passes.
72
+ 2. **Generated output parity — vscode**
73
+ - `ai-team init --ide vscode --team web-product --yes` installs expected agent files under `.github/agents/*.agent.md` with unchanged naming/frontmatter/body shape.
74
+ 3. **Generated output parity — claude-code**
75
+ - `ai-team init --ide claude-code --team web-product --yes` installs expected agent files under `.claude/agents/*.md` with unchanged naming/frontmatter/body shape.
76
+ 4. **Sync behavior unchanged**
77
+ - After local edit to an installed agent file, `ai-team plan`/`ai-team update` report conflict/skip in safe mode, and `--force` allows overwrite.
78
+ 5. **Doctor behavior unchanged**
79
+ - `ai-team doctor` still reports drift/missing files based on manifest and generated source hashes.
80
+ 6. **MCP path handling retained**
81
+ - `--include-mcp` continues to write `.vscode/mcp.json` for vscode and `.mcp.json` for claude-code with existing merge semantics.
82
+ 7. **Docs aligned**
83
+ - `README.md` and `docs/cli.md` no longer imply committed overlay agent files are maintained sources.
84
+
85
+ ## Rollback / Risk Notes
86
+
87
+ ### Key risks
88
+
89
+ 1. **Hash drift from rendering differences**
90
+ - Small frontmatter or whitespace changes could trigger broad overwrite plans.
91
+ 2. **Manifest/schema compatibility breakage**
92
+ - Aggressive manifest shape changes could break existing installs and `doctor`.
93
+ 3. **IDE path regression**
94
+ - Incorrect mapping could place agents in wrong folders and fail runtime discovery.
95
+
96
+ ### Mitigations
97
+
98
+ 1. Keep rendering logic centralized and re-used across generation + registry paths to avoid parity drift.
99
+ 2. Prefer additive/minimal manifest changes; avoid schema bump unless unavoidable.
100
+ 3. Add fixture/assertion coverage for both IDE target paths and MCP target paths.
101
+
102
+ ### Rollback strategy
103
+
104
+ 1. Revert generation/registry/manifest/doc changes in one commit to restore overlay-file sourcing.
105
+ 2. If released with path regression, ship immediate patch restoring prior target mapping and re-run integration tests.
106
+ 3. If schema changes are introduced, provide explicit compatibility gate or revert schema changes before release.
@@ -0,0 +1,148 @@
1
+ # Implementation Plan — REL-SEMVER-AUTOPUBLISH
2
+
3
+ Date: 2026-02-23
4
+ Agent: planning-agent
5
+
6
+ ## Scope (MVP)
7
+
8
+ Implement minimal semantic version auto-publish for `ai-team` on pushes to `main` using `semantic-release`, with changelog + package version committed back to `main`.
9
+
10
+ ## Exact Files to Change (implementation phase)
11
+
12
+ 1. `package.json`
13
+ - Add release stack devDependencies.
14
+ - Add a release script (`"release": "semantic-release"`) for local/CI consistency.
15
+ 2. `pnpm-lock.yaml`
16
+ - Lockfile update from added devDependencies.
17
+ 3. `.releaserc.json` (new)
18
+ - Define `main` as release branch.
19
+ - Configure semantic-release plugins and plugin order.
20
+ 4. `.github/workflows/release.yml` (new)
21
+ - Push-to-main release workflow with explicit permissions and npm auth.
22
+ 5. `CHANGELOG.md` (new/managed by release process)
23
+ - Created/updated automatically by `@semantic-release/changelog`.
24
+
25
+ ## Dependency Additions (semantic-release stack)
26
+
27
+ Add to `devDependencies` in `package.json`:
28
+
29
+ - `semantic-release`
30
+ - `@semantic-release/commit-analyzer`
31
+ - `@semantic-release/release-notes-generator`
32
+ - `@semantic-release/changelog`
33
+ - `@semantic-release/npm`
34
+ - `@semantic-release/git`
35
+ - `@semantic-release/github`
36
+
37
+ No additional runtime dependencies.
38
+
39
+ ## Semantic-Release Config Approach
40
+
41
+ Use one repo-root config file: `.releaserc.json`.
42
+
43
+ Proposed MVP config:
44
+
45
+ - `branches`: `["main"]`
46
+ - `tagFormat`: `"v${version}"`
47
+ - `plugins` in this order:
48
+ 1. `@semantic-release/commit-analyzer`
49
+ 2. `@semantic-release/release-notes-generator`
50
+ 3. `@semantic-release/changelog` with `changelogFile: "CHANGELOG.md"`
51
+ 4. `@semantic-release/npm` with `npmPublish: true`
52
+ 5. `@semantic-release/github`
53
+ 6. `@semantic-release/git` with assets:
54
+ - `package.json`
55
+ - `pnpm-lock.yaml`
56
+ - `CHANGELOG.md`
57
+ and message pattern:
58
+ - `chore(release): ${nextRelease.version} [skip ci]\n\n${nextRelease.notes}`
59
+
60
+ Why this approach (minimal):
61
+
62
+ - Single declarative config file.
63
+ - Keeps release behavior explicit and reproducible.
64
+ - Ensures changelog/version updates are committed after publish.
65
+
66
+ ## GitHub Actions Workflow Details
67
+
68
+ Workflow file: `.github/workflows/release.yml`
69
+
70
+ Trigger:
71
+
72
+ - `on.push.branches: [main]`
73
+
74
+ Job permissions (explicit):
75
+
76
+ - `contents: write` (tags + release commit + GitHub release)
77
+ - `issues: write` (plugin capability)
78
+ - `pull-requests: write` (plugin capability)
79
+
80
+ Auth and environment:
81
+
82
+ - `GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}`
83
+ - `NPM_TOKEN: ${{ secrets.NPM_TOKEN }}`
84
+ - Add preflight step: fail fast if `NPM_TOKEN` missing.
85
+ - Node setup with npm registry URL and pnpm install using lockfile (`pnpm install --frozen-lockfile`).
86
+
87
+ Minimal job steps:
88
+
89
+ 1. `actions/checkout` with full history (`fetch-depth: 0`)
90
+ 2. `pnpm/action-setup`
91
+ 3. `actions/setup-node` (Node LTS + npm registry)
92
+ 4. Install deps (`pnpm install --frozen-lockfile`)
93
+ 5. Run release (`pnpm release`)
94
+
95
+ ## Step-by-Step Execution Checklist
96
+
97
+ 1. Add release dependencies and script in `package.json`.
98
+ 2. Install deps to update `pnpm-lock.yaml`.
99
+ 3. Add `.releaserc.json` with branch/plugins configuration.
100
+ 4. Add `.github/workflows/release.yml` with trigger/permissions/auth.
101
+ 5. Confirm repository secret `NPM_TOKEN` is configured.
102
+ 6. Merge to `main` with a Conventional Commit (`feat:` or `fix:`) to validate end-to-end.
103
+
104
+ ## Acceptance Checks Mapped to Requirement Criteria
105
+
106
+ 1. **Workflow runs on push to main**
107
+ - Check Actions tab shows `release` workflow for a `main` push.
108
+ 2. **No-op release succeeds when no semver-relevant commits**
109
+ - Push commit such as `docs: ...`; verify workflow exits success with "no release" behavior.
110
+ 3. **Semver-relevant commits publish and create release artifacts**
111
+ - Push `fix:` and verify:
112
+ - computed next version,
113
+ - npm package published,
114
+ - git tag `vX.Y.Z` exists,
115
+ - GitHub release created,
116
+ - commit back to `main` includes `package.json` + `CHANGELOG.md` (+ lockfile if updated).
117
+ 4. **Missing/invalid NPM_TOKEN fails clearly**
118
+ - Temporarily remove/rotate invalid secret in test repo; verify release job fails with explicit auth/preflight error.
119
+ 5. **No manual version bump required**
120
+ - Verify release succeeds from commit messages only without editing `version` manually.
121
+
122
+ ## Rollback / Failure Notes
123
+
124
+ 1. If publish fails before git commit step:
125
+ - Fix token/permissions and rerun workflow; no repo file rollback needed.
126
+ 2. If git release commit is undesirable:
127
+ - Revert release commit on `main` and delete erroneous tag/release in GitHub.
128
+ 3. If wrong version was published to npm:
129
+ - Do **not** unpublish stable versions broadly; publish a corrective next version and document in changelog.
130
+ 4. If semantic-release config causes repeated failures:
131
+ - Revert `.releaserc.json` and `.github/workflows/release.yml` via a single rollback commit to restore previous non-automated state.
132
+
133
+ ## Out-of-Scope Guardrails
134
+
135
+ - No multi-branch channels.
136
+ - No monorepo/workspace release orchestration.
137
+ - No extra CI jobs/quality gates added in this feature.
138
+
139
+ ## Closeout Status (2026-02-23)
140
+
141
+ - **Current state:** **Blocked (QA not approved)**.
142
+ - **Why blocked:** QA handoff reports end-to-end acceptance is blocked by unresolved lockfile integrity and unavailable runtime CI/publish validation in current environment.
143
+ - **Completion criteria to close feature:**
144
+ 1. Regenerate and commit `pnpm-lock.yaml` with full semantic-release dependency resolution.
145
+ 2. Enforce deterministic install in `.github/workflows/release.yml` using `pnpm install --frozen-lockfile`.
146
+ 3. Execute CI validation on `main` for no-op (`docs:`) and release (`fix:`/`feat:`) paths.
147
+ 4. Verify `NPM_TOKEN` secret presence and confirm missing/invalid token failure behavior.
148
+ - **Planning decision:** Do not mark feature complete until QA re-runs and returns APPROVED.
package/docs/cli.md CHANGED
@@ -8,12 +8,13 @@
8
8
  - `ai-team update` — apply bundled template updates with drift protection
9
9
  - `ai-team plan` (or `diff`) — dry-run preview
10
10
  - `ai-team doctor` — validate manifest health and local drift
11
+ - `ai-team version` (or `--version`) — print installed CLI version
11
12
 
12
13
  ## Runtime Profile
13
14
 
14
15
  Profile options are selected with flags or interactive prompts:
15
16
 
16
- - `--ide <vscode>`
17
+ - `--ide <vscode|claude-code>`
17
18
  - `--team <web-product>`
18
19
  - `--include-mcp` or `--no-include-mcp`
19
20
  - `--target <path>`
@@ -32,6 +33,13 @@ For `--ide vscode`:
32
33
  - MCP config (optional): `.vscode/mcp.json`
33
34
  - Install manifest: `.agents/manifest.json`
34
35
 
36
+ For `--ide claude-code`:
37
+
38
+ - Shared assets: `.agents/skills/**`, `.agents/teams/web-product/**`
39
+ - Agent entry files (generated install targets): `.claude/agents/*.md`
40
+ - MCP config (optional): `.mcp.json`
41
+ - Install manifest: `.agents/manifest.json`
42
+
35
43
  Customization is project-owned and out-of-band for the CLI:
36
44
 
37
45
  - `.agents/custom/skills/`
@@ -43,7 +51,7 @@ Customization is project-owned and out-of-band for the CLI:
43
51
  `update` runs in safe mode by default:
44
52
 
45
53
  - copy-tracked files changed locally are skipped and reported as conflicts
46
- - JSON assets (`.vscode/mcp.json`) use structured merge
54
+ - JSON assets (`.vscode/mcp.json` / `.mcp.json`) use structured merge
47
55
  - `--force` allows overwrite behavior for copy-tracked conflicts
48
56
 
49
57
  ## Versioning Flow
@@ -52,6 +60,7 @@ Template source of truth:
52
60
 
53
61
  - Agent templates: `src/agents/definitions/*.yaml`
54
62
  - Template pack metadata and path resolution: `templates/bootstrap/manifest.json`
63
+ - Runtime accepts both `packs.ide` (current) and `packs.overlays` (legacy compatibility shim) in the template manifest.
55
64
  - `templateVersion` is copied into installed `.agents/manifest.json`
56
65
  - `update` compares installed template version and bundled template version
57
66
  - change risk should be documented by version in release notes/changelog
package/docs/plan.md CHANGED
@@ -10,7 +10,7 @@ Build a Node CLI that installs and updates agent template assets from this repo
10
10
 
11
11
  - Agent template definitions live under `src/agents/definitions/*.yaml`.
12
12
  - Platform-neutral base templates live under `templates/bootstrap/base/.agents/**`.
13
- - VSCode/Copilot overlay templates live under `templates/bootstrap/overlays/vscode-copilot/**`.
13
+ - IDE-specific agent files are rendered from definitions at runtime and can be preview-generated under `templates/bootstrap/base/.agents/generated/agents/**`.
14
14
  - Template source metadata lives in `templates/bootstrap/manifest.json` and includes semantic `templateVersion`.
15
15
 
16
16
  ### Downstream install contract (`--ide vscode`)
package/package.json CHANGED
@@ -1,29 +1,38 @@
1
1
  {
2
2
  "name": "ai-team",
3
- "version": "1.0.2",
3
+ "version": "1.2.0",
4
4
  "description": "AI agent team management CLI tool",
5
5
  "type": "module",
6
6
  "main": "src/cli.js",
7
7
  "bin": {
8
8
  "ai-team": "src/cli.js"
9
9
  },
10
+ "scripts": {
11
+ "test": "node --test",
12
+ "ai-team": "node ./src/cli.js",
13
+ "release": "semantic-release"
14
+ },
10
15
  "keywords": [],
11
16
  "author": "",
12
17
  "license": "ISC",
13
18
  "publishConfig": {
14
19
  "access": "public"
15
20
  },
21
+ "packageManager": "pnpm@10.28.1",
16
22
  "dependencies": {
17
- "@inquirer/prompts": "^8.2.1",
23
+ "@inquirer/prompts": "^8.3.0",
18
24
  "chalk": "^5.6.2",
25
+ "mustache": "^4.2.0",
19
26
  "ora": "^9.3.0",
20
- "yaml": "^2.8.1"
27
+ "yaml": "^2.8.2"
21
28
  },
22
29
  "devDependencies": {
23
- "mustache": "^4.2.0"
24
- },
25
- "scripts": {
26
- "test": "node --test",
27
- "ai-team": "node ./src/cli.js"
30
+ "@semantic-release/changelog": "^6.0.3",
31
+ "@semantic-release/commit-analyzer": "^13.0.1",
32
+ "@semantic-release/git": "^10.0.1",
33
+ "@semantic-release/github": "^11.0.6",
34
+ "@semantic-release/npm": "^13.1.4",
35
+ "@semantic-release/release-notes-generator": "^14.1.0",
36
+ "semantic-release": "^25.0.3"
28
37
  }
29
- }
38
+ }
@@ -34,7 +34,7 @@ body: |
34
34
 
35
35
  - Analyze requirements for new or changed agent roles.
36
36
  - Create or update source agent definitions in `src/agents/definitions/*.yaml`.
37
- - Regenerate agent overlay files from definitions after changes.
37
+ - Regenerate agent files from definitions after changes.
38
38
  - Ensure agents are properly integrated with existing skills and workflows.
39
39
  - Update team documentation to reflect the agent structure.
40
40
  - Execute the `adopt` command to tailor the agent setup for the current project.
@@ -42,7 +42,7 @@ body: |
42
42
  ## Deliverables
43
43
 
44
44
  - New or updated definition file in `src/agents/definitions/*.yaml`
45
- - Regenerated overlay files under `templates/bootstrap/overlays/**`
45
+ - Regenerated files under `templates/bootstrap/base/.agents/generated/agents/**`
46
46
  - Updates to `.agents/teams/web-product/README.md` listing the new agent
47
47
  - Updates to `docs/agents/README.md` if workflow changes are significant
48
48
 
@@ -3,8 +3,17 @@ import path from "node:path";
3
3
  import { fileURLToPath } from "node:url";
4
4
  import Mustache from "mustache";
5
5
  import YAML from "yaml";
6
+ import { hashText } from "../lib/hash.js";
6
7
 
7
- const IDE_KEYS = ["vscode", "claude"];
8
+ const IDE_TEMPLATE_KEYS = {
9
+ vscode: "vscode",
10
+ "vscode-copilot": "vscode",
11
+ copilot: "vscode",
12
+ claude: "claude",
13
+ "claude-code": "claude",
14
+ };
15
+
16
+ const DEFAULT_SOURCE_PATH_PREFIX = ".generated/agents";
8
17
 
9
18
  const __filename = fileURLToPath(import.meta.url);
10
19
  const __dirname = path.dirname(__filename);
@@ -12,6 +21,18 @@ const repoRoot = path.resolve(__dirname, "../..");
12
21
 
13
22
  const definitionsDir = path.join(repoRoot, "src/agents/definitions");
14
23
  const manifestPath = path.join(repoRoot, "templates/bootstrap/manifest.json");
24
+ const generatedRoot = path.join(
25
+ repoRoot,
26
+ "templates/bootstrap/base/.agents/generated/agents",
27
+ );
28
+
29
+ const normalizeIdeKey = (ide) => {
30
+ const normalized = IDE_TEMPLATE_KEYS[ide];
31
+ if (!normalized) {
32
+ throw new Error(`Unsupported IDE key: ${ide}`);
33
+ }
34
+ return normalized;
35
+ };
15
36
 
16
37
  const pickByIde = (value, ide) => {
17
38
  if (value && typeof value === "object" && !Array.isArray(value)) {
@@ -103,34 +124,20 @@ const loadManifest = async () => {
103
124
  return JSON.parse(raw);
104
125
  };
105
126
 
106
- const getOverlayPaths = (manifest) => {
107
- const templateRoot = path.join(repoRoot, "templates/bootstrap");
108
- const overlays = manifest.packs?.overlays || {};
109
- const vscodeOverlay = overlays.vscode;
110
- const claudeOverlay = overlays["claude-code"];
127
+ const getManifestIdePacks = (manifest) => {
128
+ const idePacks = manifest?.packs?.ide;
129
+ if (idePacks && typeof idePacks === "object") {
130
+ return idePacks;
131
+ }
111
132
 
112
- if (!vscodeOverlay || !claudeOverlay) {
113
- throw new Error("Missing overlay configuration for vscode or claude-code.");
133
+ const legacyOverlayPacks = manifest?.packs?.overlays;
134
+ if (legacyOverlayPacks && typeof legacyOverlayPacks === "object") {
135
+ return legacyOverlayPacks;
114
136
  }
115
137
 
116
- return {
117
- vscode: {
118
- outputDir: path.join(
119
- templateRoot,
120
- vscodeOverlay.root,
121
- vscodeOverlay.agents,
122
- ),
123
- agentDir: vscodeOverlay.agents,
124
- },
125
- claude: {
126
- outputDir: path.join(
127
- templateRoot,
128
- claudeOverlay.root,
129
- claudeOverlay.agents,
130
- ),
131
- agentDir: claudeOverlay.agents,
132
- },
133
- };
138
+ throw new Error(
139
+ "Missing packs.ide (or legacy packs.overlays) configuration in template manifest.",
140
+ );
134
141
  };
135
142
 
136
143
  const getBody = (definition, ide) => {
@@ -140,17 +147,17 @@ const getBody = (definition, ide) => {
140
147
  return pickByIde(definition.body, ide);
141
148
  };
142
149
 
143
- const getTemplateVariables = (definition, ide, overlay) => {
150
+ const getTemplateVariables = (definition, ide, config) => {
144
151
  const baseName = definition.filename || definition.name;
145
152
  return {
146
- agentDir: overlay.agentDir,
153
+ agentDir: config.agents,
147
154
  agentFileExt: ide === "vscode" ? "agent.md" : "md",
148
155
  agentName: definition.name,
149
156
  agentFileName: baseName,
150
157
  };
151
158
  };
152
159
 
153
- const generateForIde = async (definition, ide, overlay) => {
160
+ const renderAgentDefinition = ({ definition, ide, config }) => {
154
161
  const rawBody = getBody(definition, ide);
155
162
  if (!rawBody) {
156
163
  throw new Error(`Missing body for ${definition.name} (${ide}).`);
@@ -158,18 +165,15 @@ const generateForIde = async (definition, ide, overlay) => {
158
165
 
159
166
  const frontmatter = buildFrontmatter(definition, ide);
160
167
  const fileName = resolveFileName(definition, ide);
161
- const variables = getTemplateVariables(definition, ide, overlay);
168
+ const variables = getTemplateVariables(definition, ide, config);
162
169
  const body = Mustache.render(rawBody, variables);
163
- const content = `${formatFrontmatter(frontmatter)}${body.trimEnd()}\n`;
164
- const outputPath = path.join(overlay.outputDir, fileName);
165
-
166
- await mkdir(path.dirname(outputPath), { recursive: true });
167
- await writeFile(outputPath, content, "utf8");
168
-
169
- return outputPath;
170
+ return {
171
+ fileName,
172
+ content: `${formatFrontmatter(frontmatter)}${body.trimEnd()}\n`,
173
+ };
170
174
  };
171
175
 
172
- const loadDefinitions = async () => {
176
+ export const loadDefinitions = async () => {
173
177
  const entries = await readdir(definitionsDir, { withFileTypes: true });
174
178
  const definitionFiles = entries
175
179
  .filter((entry) => entry.isFile())
@@ -191,23 +195,75 @@ const loadDefinitions = async () => {
191
195
  return definitions;
192
196
  };
193
197
 
194
- const main = async () => {
195
- const manifest = await loadManifest();
196
- const outputDirs = getOverlayPaths(manifest);
198
+ function normalizeIdeConfig(ideConfig, ideKey) {
199
+ if (!ideConfig || typeof ideConfig !== "object") {
200
+ throw new Error(`Missing IDE configuration for ${ideKey}.`);
201
+ }
202
+
203
+ if (!ideConfig.agents) {
204
+ throw new Error(`Missing agents path for ${ideKey}.`);
205
+ }
206
+
207
+ return ideConfig;
208
+ }
209
+
210
+ export async function generateAgentEntriesForIde({
211
+ ide,
212
+ config,
213
+ sourcePathPrefix = DEFAULT_SOURCE_PATH_PREFIX,
214
+ }) {
215
+ const templateIde = normalizeIdeKey(ide);
216
+ const sourcePathIde = templateIde === "vscode" ? "vscode" : "claude-code";
217
+ const ideConfig = normalizeIdeConfig(config, ide);
197
218
  const definitions = await loadDefinitions();
198
219
 
220
+ return definitions.map(({ definition }) => {
221
+ const { fileName, content } = renderAgentDefinition({
222
+ definition,
223
+ ide: templateIde,
224
+ config: ideConfig,
225
+ });
226
+
227
+ return {
228
+ sourcePath: path.posix.join(sourcePathPrefix, sourcePathIde, fileName),
229
+ targetPath: path.posix.join(ideConfig.agents, fileName),
230
+ mode: "copy",
231
+ sourceHash: hashText(content),
232
+ sourceContent: content,
233
+ };
234
+ });
235
+ }
236
+
237
+ async function writeGeneratedFiles(manifest) {
238
+ const ideConfigs = getManifestIdePacks(manifest);
239
+
199
240
  const outputs = [];
200
- for (const { definition } of definitions) {
201
- for (const ide of IDE_KEYS) {
202
- const outputPath = await generateForIde(definition, ide, outputDirs[ide]);
241
+ for (const [ide, config] of Object.entries(ideConfigs)) {
242
+ const entries = await generateAgentEntriesForIde({ ide, config });
243
+ const outputDir = path.join(generatedRoot, ide);
244
+ await mkdir(outputDir, { recursive: true });
245
+
246
+ for (const entry of entries) {
247
+ const fileName = path.basename(entry.targetPath);
248
+ const outputPath = path.join(outputDir, fileName);
249
+ await writeFile(outputPath, entry.sourceContent, "utf8");
203
250
  outputs.push(outputPath);
204
251
  }
205
252
  }
206
253
 
254
+ return outputs;
255
+ }
256
+
257
+ const main = async () => {
258
+ const manifest = await loadManifest();
259
+ const outputs = await writeGeneratedFiles(manifest);
260
+
207
261
  console.log(`Generated ${outputs.length} agent files.`);
208
262
  };
209
263
 
210
- main().catch((error) => {
211
- console.error(error);
212
- process.exitCode = 1;
213
- });
264
+ if (process.argv[1] && path.resolve(process.argv[1]) === __filename) {
265
+ main().catch((error) => {
266
+ console.error(error);
267
+ process.exitCode = 1;
268
+ });
269
+ }
package/src/cli.js CHANGED
@@ -19,8 +19,10 @@ Commands:
19
19
  plan Dry-run preview of changes
20
20
  diff Alias of plan
21
21
  doctor Validate install health and report drift
22
+ version Print installed CLI version
22
23
 
23
24
  Options:
25
+ -v, --version Print installed CLI version
24
26
  --ide <vscode|claude-code>
25
27
  --team <web-product>
26
28
  --target <path> Default: current directory
@@ -33,6 +35,12 @@ Options:
33
35
  `);
34
36
  }
35
37
 
38
+ async function printVersion() {
39
+ const packageJsonPath = new URL("../package.json", import.meta.url);
40
+ const packageJson = JSON.parse(await fs.readFile(packageJsonPath, "utf8"));
41
+ console.log(packageJson.version);
42
+ }
43
+
36
44
  function createSpinner(values, text) {
37
45
  const canUseSpinner = !values.json && process.stdout.isTTY;
38
46
  return ora({ text, isEnabled: canUseSpinner }).start();
@@ -272,6 +280,11 @@ function asJson(values, payload) {
272
280
 
273
281
  async function run() {
274
282
  const [, , commandArg] = process.argv;
283
+ if (["version", "--version", "-v"].includes(commandArg)) {
284
+ await printVersion();
285
+ process.exit(0);
286
+ }
287
+
275
288
  const command = commandArg === "diff" ? "plan" : commandArg;
276
289
 
277
290
  if (!command || ["-h", "--help", "help"].includes(command)) {