agents-templated 2.2.12 → 2.2.14
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.
- package/README.md +53 -12
- package/bin/cli.js +76 -18
- package/index.js +2 -2
- package/lib/layout.js +27 -3
- package/lib/orchestrator.js +562 -0
- package/lib/workflow.js +472 -3
- package/package.json +1 -1
- package/templates/.claude/agents/README.md +15 -1
- package/templates/.claude/agents/architect.md +79 -106
- package/templates/.claude/agents/backend-specialist.md +79 -0
- package/templates/.claude/agents/build-error-resolver.md +78 -119
- package/templates/.claude/agents/code-reviewer.md +79 -116
- package/templates/.claude/agents/compatibility-checker.md +79 -79
- package/templates/.claude/agents/configuration-validator.md +79 -85
- package/templates/.claude/agents/database-migrator.md +79 -83
- package/templates/.claude/agents/dependency-auditor.md +79 -92
- package/templates/.claude/agents/deployment-specialist.md +91 -0
- package/templates/.claude/agents/doc-updater.md +78 -130
- package/templates/.claude/agents/e2e-runner.md +78 -122
- package/templates/.claude/agents/frontend-specialist.md +79 -0
- package/templates/.claude/agents/load-tester.md +79 -80
- package/templates/.claude/agents/performance-profiler.md +79 -103
- package/templates/.claude/agents/performance-specialist.md +91 -0
- package/templates/.claude/agents/planner.md +81 -87
- package/templates/.claude/agents/qa-specialist.md +92 -0
- package/templates/.claude/agents/refactor-cleaner.md +79 -137
- package/templates/.claude/agents/release-ops-specialist.md +80 -0
- package/templates/.claude/agents/security-reviewer.md +80 -138
- package/templates/.claude/agents/tdd-guide.md +79 -98
- package/templates/.claude/agents/test-data-builder.md +79 -0
- package/templates/CLAUDE.md +7 -0
- package/templates/README.md +37 -9
- package/templates/agent-docs/ARCHITECTURE.md +6 -0
- package/templates/agents/commands/README.md +84 -4
- package/templates/agents/commands/SCHEMA.md +21 -1
- package/templates/agents/commands/test-data.md +56 -0
- package/agents/commands/README.md +0 -64
- package/agents/commands/SCHEMA.md +0 -22
- package/agents/commands/arch-check.md +0 -58
- package/agents/commands/audit.md +0 -58
- package/agents/commands/debug-track.md +0 -58
- package/agents/commands/docs.md +0 -58
- package/agents/commands/fix.md +0 -58
- package/agents/commands/learn-loop.md +0 -58
- package/agents/commands/perf.md +0 -58
- package/agents/commands/plan.md +0 -58
- package/agents/commands/pr.md +0 -58
- package/agents/commands/problem-map.md +0 -58
- package/agents/commands/release-ready.md +0 -58
- package/agents/commands/release.md +0 -58
- package/agents/commands/risk-review.md +0 -58
- package/agents/commands/scope-shape.md +0 -58
- package/agents/commands/task.md +0 -58
- package/agents/commands/test.md +0 -58
- package/agents/commands/ux-bar.md +0 -58
- package/agents/rules/planning.mdc +0 -69
package/README.md
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
[](https://opensource.org/licenses/MIT)
|
|
6
6
|
[](https://github.com/rickandrew2/agents-templated)
|
|
7
7
|
|
|
8
|
-
> **Agents Templated** is a CLI
|
|
8
|
+
> **Agents Templated** is a technology-agnostic CLI that scaffolds the AI development operating layer around your app: policy rules, deterministic command contracts, reusable skills, and compatibility files for Cursor, GitHub Copilot, Claude, and generic agent hosts. It does not scaffold your product framework. It scaffolds how your team and agents plan, build, test, review, and release.
|
|
9
9
|
|
|
10
10
|
---
|
|
11
11
|
|
|
@@ -16,12 +16,28 @@ Most starter templates only create files. This package creates operating rules f
|
|
|
16
16
|
You get:
|
|
17
17
|
|
|
18
18
|
- Multi-agent configuration for Cursor, Copilot, Claude, and generic hosts
|
|
19
|
-
- Deterministic command contracts in
|
|
19
|
+
- Deterministic command contracts in `.claude/commands/`
|
|
20
20
|
- Security-first and testing-first rule baselines
|
|
21
21
|
- Reusable skills and optional subagents
|
|
22
22
|
|
|
23
23
|
Important: this package does not install your framework. It installs the operating layer around your framework.
|
|
24
24
|
|
|
25
|
+
## What Agents Templated Actually Is
|
|
26
|
+
|
|
27
|
+
Agents Templated is a project governance and agent-orchestration scaffold.
|
|
28
|
+
|
|
29
|
+
- It installs a canonical AI policy source (`CLAUDE.md`) and compatibility shims (`AGENTS.MD`, `.github/copilot-instructions.md`, `.cursorrules`).
|
|
30
|
+
- It installs deterministic command contracts in `.claude/commands/` for repeatable specialist workflows.
|
|
31
|
+
- It installs reusable skills in `.github/skills/` and optional subagents in `.claude/agents/`.
|
|
32
|
+
- It installs rule modules in `.claude/rules/` for security, testing, planning, workflows, and guardrails.
|
|
33
|
+
- It includes `validate`, `doctor`, `update`, and `workflow` commands to keep scaffolds healthy over time.
|
|
34
|
+
|
|
35
|
+
What it is not:
|
|
36
|
+
|
|
37
|
+
- Not a framework generator.
|
|
38
|
+
- Not a dependency installer for your app stack.
|
|
39
|
+
- Not a replacement for your application architecture.
|
|
40
|
+
|
|
25
41
|
## 30-Second Start
|
|
26
42
|
|
|
27
43
|
### 1. Install setup
|
|
@@ -161,10 +177,8 @@ your-project/
|
|
|
161
177
|
│ │ ├── system-workflow.md
|
|
162
178
|
│ │ ├── hardening.md
|
|
163
179
|
│ │ └── lessons-learned.md
|
|
164
|
-
│
|
|
165
|
-
│
|
|
166
|
-
├── agents/ # Deterministic command contracts
|
|
167
|
-
│ └── commands/
|
|
180
|
+
│ ├── agents/ # Optional subagents
|
|
181
|
+
│ └── commands/ # Deterministic command contracts
|
|
168
182
|
│ │ ├── SCHEMA.md # Global slash-command response schema
|
|
169
183
|
│ │ ├── plan.md # /plan contract
|
|
170
184
|
│ │ ├── fix.md # /fix contract
|
|
@@ -237,13 +251,31 @@ These commands provide deterministic specialist guidance aligned to the sprint l
|
|
|
237
251
|
| `arch-check` | Architecture Reviewer | Lock architecture and edge-case coverage |
|
|
238
252
|
| `ux-bar` | Design Quality Lead | Raise UX quality before implementation |
|
|
239
253
|
| `debug-track` | Root-Cause Investigator | Reproduce and isolate root cause |
|
|
254
|
+
| `test-data` | Test Data Builder | Prepare deterministic fixtures/seeds for downstream validation |
|
|
240
255
|
| `risk-review` | Release Risk Reviewer | Surface production-risk issues before merge |
|
|
241
256
|
| `perf` | Performance Analyst | Optimize performance and guard against regressions |
|
|
242
257
|
| `release-ready` | Release Coordinator | Prepare release artifacts and final checks |
|
|
243
258
|
| `docs` | Documentation Engineer | Sync docs with shipped behavior |
|
|
244
259
|
| `learn-loop` | Iteration Lead | Capture lessons and next-cycle actions |
|
|
245
260
|
|
|
246
|
-
Each command maps to deterministic contract files in
|
|
261
|
+
Each command maps to deterministic contract files in `.claude/commands/` and uses the schema in `.claude/commands/SCHEMA.md`.
|
|
262
|
+
|
|
263
|
+
### Deprecated Workflow Aliases
|
|
264
|
+
|
|
265
|
+
The CLI keeps selected legacy names as non-breaking redirects with deterministic notices.
|
|
266
|
+
|
|
267
|
+
| Deprecated | Canonical |
|
|
268
|
+
|------------|-----------|
|
|
269
|
+
| `quality-gate` | `risk-review` |
|
|
270
|
+
| `perf-scan` | `perf` |
|
|
271
|
+
| `docs-sync` | `docs` |
|
|
272
|
+
|
|
273
|
+
Migration guidance:
|
|
274
|
+
|
|
275
|
+
- Existing scripts continue to work.
|
|
276
|
+
- Alias invocations print a deprecation warning and redirect deterministically.
|
|
277
|
+
- New automation should use canonical names only.
|
|
278
|
+
- Sunset guidance: deprecated aliases remain supported through v2.x and are scheduled for removal in v3.0.
|
|
247
279
|
|
|
248
280
|
|
|
249
281
|
---
|
|
@@ -361,11 +393,20 @@ Your AI will follow the enterprise patterns automatically!
|
|
|
361
393
|
|
|
362
394
|
| Agent | Responsibility |
|
|
363
395
|
|-------|---------------|
|
|
364
|
-
| **
|
|
365
|
-
| **
|
|
366
|
-
| **
|
|
367
|
-
| **
|
|
368
|
-
| **
|
|
396
|
+
| **backend-specialist** | API, business logic, auth middleware, persistence changes |
|
|
397
|
+
| **frontend-specialist** | UI/UX implementation, accessibility, interaction behavior |
|
|
398
|
+
| **qa-specialist** | Design-mode test planning and validation-mode regression gates |
|
|
399
|
+
| **performance-specialist** | Mode-locked performance profiling and load threshold validation |
|
|
400
|
+
| **test-data-builder** | Deterministic fixtures, seeds, and downstream handoff contracts |
|
|
401
|
+
| **security-reviewer** | Conditional security invocation based on trigger thresholds |
|
|
402
|
+
| **dependency-auditor** | CVE/dependency risk auditing and upgrade hygiene |
|
|
403
|
+
| **deployment-specialist** | Ordered deployment phase contract and rollback readiness |
|
|
404
|
+
|
|
405
|
+
#### Separation-Preservation Sequence Contracts
|
|
406
|
+
|
|
407
|
+
- Backend implementation lane: `backend-specialist -> build-error-resolver -> compatibility-checker`
|
|
408
|
+
- Review/governance lane: `code-reviewer -> dependency-auditor -> doc-updater`
|
|
409
|
+
- Test-data handoff lane: `qa-specialist(mode=design) -> test-data-builder -> qa-specialist(mode=validation) -> e2e-runner -> performance-specialist(mode=load)`
|
|
369
410
|
|
|
370
411
|
**Reference**: [AGENTS.MD](AGENTS.MD)
|
|
371
412
|
|
package/bin/cli.js
CHANGED
|
@@ -10,6 +10,7 @@ const {
|
|
|
10
10
|
LAYOUT,
|
|
11
11
|
resolveRulesDir,
|
|
12
12
|
resolveSkillsDir,
|
|
13
|
+
resolveCommandsDir,
|
|
13
14
|
resolveSubagentsDir,
|
|
14
15
|
hasAnyLayout,
|
|
15
16
|
getLegacyMigrationPlan
|
|
@@ -27,9 +28,14 @@ const {
|
|
|
27
28
|
WORKFLOW_COMMANDS,
|
|
28
29
|
CONTRACT_FILES,
|
|
29
30
|
SPECIALIST_CONTRACT_FILES,
|
|
31
|
+
DEPRECATED_COMMAND_ALIASES,
|
|
30
32
|
formatWorkflowOutput,
|
|
31
33
|
validateWorkflowDefinitions
|
|
32
34
|
} = require('../lib/workflow');
|
|
35
|
+
const {
|
|
36
|
+
WorkflowOrchestrator,
|
|
37
|
+
formatOrchestrationOutput
|
|
38
|
+
} = require('../lib/orchestrator');
|
|
33
39
|
|
|
34
40
|
// Resolve the templates directory - works in both dev and installed contexts
|
|
35
41
|
const getTemplatesDir = () => {
|
|
@@ -141,7 +147,7 @@ program
|
|
|
141
147
|
{ name: 'Documentation files (agent-docs/)', value: 'docs' },
|
|
142
148
|
{ name: 'Agent rules (.claude/rules/*.md)', value: 'rules' },
|
|
143
149
|
{ name: 'Skills (.github/skills/*)', value: 'skills' },
|
|
144
|
-
{ name: 'Command contracts (
|
|
150
|
+
{ name: 'Command contracts (.claude/commands/*.md)', value: 'commands' },
|
|
145
151
|
{ name: 'AI Agent instructions (Cursor, Copilot, Claude, Generic AGENTS)', value: 'github' },
|
|
146
152
|
{ name: 'Agent subagents (.claude/agents/*.md)', value: 'subagents' }
|
|
147
153
|
],
|
|
@@ -205,10 +211,10 @@ program
|
|
|
205
211
|
// Install deterministic command contracts
|
|
206
212
|
if (installAll || choices.includes('commands')) {
|
|
207
213
|
console.log(chalk.yellow('Installing command contracts...'));
|
|
208
|
-
await fs.ensureDir(path.join(targetDir,
|
|
214
|
+
await fs.ensureDir(path.join(targetDir, LAYOUT.canonical.commandsDir));
|
|
209
215
|
await copyDirectory(
|
|
210
216
|
path.join(templateDir, 'agents', 'commands'),
|
|
211
|
-
path.join(targetDir,
|
|
217
|
+
path.join(targetDir, LAYOUT.canonical.commandsDir),
|
|
212
218
|
options.force
|
|
213
219
|
);
|
|
214
220
|
}
|
|
@@ -286,7 +292,7 @@ program
|
|
|
286
292
|
{ name: 'Documentation (agent-docs/)', value: 'docs' },
|
|
287
293
|
{ name: 'Agent Rules (security, testing, database, etc.)', value: 'rules' },
|
|
288
294
|
{ name: 'Skills (reusable agent capabilities)', value: 'skills' },
|
|
289
|
-
{ name: 'Command contracts (
|
|
295
|
+
{ name: 'Command contracts (.claude/commands/*.md)', value: 'commands' },
|
|
290
296
|
{ name: 'AI Agent instructions (Cursor, Copilot, Claude, Generic AGENTS)', value: 'github' },
|
|
291
297
|
{ name: 'Agent subagents (.claude/agents/*.md)', value: 'subagents' }
|
|
292
298
|
],
|
|
@@ -324,7 +330,7 @@ program
|
|
|
324
330
|
{ name: 'Documentation (agent-docs/)', value: 'docs', checked: true },
|
|
325
331
|
{ name: 'Agent Rules (security, testing, database, etc.)', value: 'rules', checked: true },
|
|
326
332
|
{ name: 'Skills (reusable agent capabilities)', value: 'skills', checked: true },
|
|
327
|
-
{ name: 'Command contracts (
|
|
333
|
+
{ name: 'Command contracts (.claude/commands/*.md)', value: 'commands', checked: true },
|
|
328
334
|
{ name: 'AI Agent instructions (Cursor, Copilot, Claude, Generic AGENTS)', value: 'github', checked: true },
|
|
329
335
|
{ name: 'Agent subagents (.claude/agents/*.md)', value: 'subagents', checked: true }
|
|
330
336
|
],
|
|
@@ -390,10 +396,10 @@ program
|
|
|
390
396
|
// Install deterministic command contracts
|
|
391
397
|
if (options.commands) {
|
|
392
398
|
console.log(chalk.yellow('Installing command contracts...'));
|
|
393
|
-
await fs.ensureDir(path.join(targetDir,
|
|
399
|
+
await fs.ensureDir(path.join(targetDir, LAYOUT.canonical.commandsDir));
|
|
394
400
|
await copyDirectory(
|
|
395
401
|
path.join(templateDir, 'agents', 'commands'),
|
|
396
|
-
path.join(targetDir,
|
|
402
|
+
path.join(targetDir, LAYOUT.canonical.commandsDir),
|
|
397
403
|
options.force
|
|
398
404
|
);
|
|
399
405
|
}
|
|
@@ -447,7 +453,7 @@ program
|
|
|
447
453
|
console.log(chalk.yellow('docs') + ' - Documentation files (agent-docs/ directory)');
|
|
448
454
|
console.log(chalk.yellow('rules') + ' - Agent rules (.claude/rules/*.md)');
|
|
449
455
|
console.log(chalk.yellow('skills') + ' - Agent skills (.github/skills/*)');
|
|
450
|
-
console.log(chalk.yellow('commands') + ' - Deterministic command contracts (
|
|
456
|
+
console.log(chalk.yellow('commands') + ' - Deterministic command contracts (.claude/commands/*.md)');
|
|
451
457
|
console.log(chalk.yellow('github') + ' - AI Agent instructions (Cursor, Copilot, Claude, Generic AGENTS)');
|
|
452
458
|
console.log(chalk.yellow('subagents') + ' - Agent subagents (.claude/agents/*.md)');
|
|
453
459
|
console.log(chalk.yellow('all') + ' - All components');
|
|
@@ -542,27 +548,35 @@ program
|
|
|
542
548
|
warnings.push(`⚠ ${LAYOUT.canonical.skillsDir} directory missing - run 'agents-templated init --skills'`);
|
|
543
549
|
}
|
|
544
550
|
|
|
545
|
-
const
|
|
551
|
+
const canonicalCommandsDir = path.join(targetDir, LAYOUT.canonical.commandsDir);
|
|
552
|
+
const legacyCommandsDir = path.join(targetDir, LAYOUT.legacy.commandsDirs[0]);
|
|
553
|
+
const commandsDir = path.join(targetDir, resolveCommandsDir(targetDir));
|
|
554
|
+
|
|
555
|
+
if (!(await fs.pathExists(canonicalCommandsDir)) && await fs.pathExists(legacyCommandsDir)) {
|
|
556
|
+
issues.push(`✗ Legacy command contract layout detected at ${LAYOUT.legacy.commandsDirs[0]} - run 'agents-templated update --all' to migrate`);
|
|
557
|
+
}
|
|
558
|
+
|
|
546
559
|
if (await fs.pathExists(commandsDir)) {
|
|
560
|
+
const relativeCommandsDir = path.relative(targetDir, commandsDir) || LAYOUT.canonical.commandsDir;
|
|
547
561
|
for (const contractFile of CONTRACT_FILES) {
|
|
548
562
|
const contractPath = path.join(commandsDir, contractFile);
|
|
549
563
|
if (await fs.pathExists(contractPath)) {
|
|
550
|
-
passed.push(`✓
|
|
564
|
+
passed.push(`✓ ${relativeCommandsDir}/${contractFile} found`);
|
|
551
565
|
} else {
|
|
552
|
-
warnings.push(`⚠
|
|
566
|
+
warnings.push(`⚠ ${relativeCommandsDir}/${contractFile} missing`);
|
|
553
567
|
}
|
|
554
568
|
}
|
|
555
569
|
|
|
556
570
|
for (const contractFile of SPECIALIST_CONTRACT_FILES) {
|
|
557
571
|
const contractPath = path.join(commandsDir, contractFile);
|
|
558
572
|
if (await fs.pathExists(contractPath)) {
|
|
559
|
-
passed.push(`✓
|
|
573
|
+
passed.push(`✓ ${relativeCommandsDir}/${contractFile} found`);
|
|
560
574
|
} else {
|
|
561
|
-
warnings.push(`⚠
|
|
575
|
+
warnings.push(`⚠ ${relativeCommandsDir}/${contractFile} missing`);
|
|
562
576
|
}
|
|
563
577
|
}
|
|
564
578
|
} else {
|
|
565
|
-
warnings.push(`⚠
|
|
579
|
+
warnings.push(`⚠ ${LAYOUT.canonical.commandsDir} directory missing - run 'agents-templated init --commands'`);
|
|
566
580
|
}
|
|
567
581
|
|
|
568
582
|
// Check subagents
|
|
@@ -786,10 +800,10 @@ async function updateSelectedComponents(targetDir, templateDir, selectedComponen
|
|
|
786
800
|
|
|
787
801
|
if (components.includes('commands')) {
|
|
788
802
|
console.log(chalk.yellow('Updating command contracts...'));
|
|
789
|
-
await fs.ensureDir(path.join(targetDir,
|
|
803
|
+
await fs.ensureDir(path.join(targetDir, LAYOUT.canonical.commandsDir));
|
|
790
804
|
await copyDirectory(
|
|
791
805
|
path.join(templateDir, 'agents', 'commands'),
|
|
792
|
-
path.join(targetDir,
|
|
806
|
+
path.join(targetDir, LAYOUT.canonical.commandsDir),
|
|
793
807
|
overwrite
|
|
794
808
|
);
|
|
795
809
|
}
|
|
@@ -930,8 +944,8 @@ program
|
|
|
930
944
|
{ targetFile: `${LAYOUT.canonical.skillsDir}/error-patterns/SKILL.md`, templateFile: 'agents/skills/error-patterns/SKILL.md', component: 'skills' },
|
|
931
945
|
{ targetFile: `${LAYOUT.canonical.skillsDir}/ui-ux-pro-max/SKILL.md`, templateFile: 'agents/skills/ui-ux-pro-max/SKILL.md', component: 'skills' },
|
|
932
946
|
{ targetFile: `${LAYOUT.canonical.skillsDir}/shadcn-ui/SKILL.md`, templateFile: 'agents/skills/shadcn-ui/SKILL.md', component: 'skills' },
|
|
933
|
-
{ targetFile:
|
|
934
|
-
{ targetFile:
|
|
947
|
+
{ targetFile: `${LAYOUT.canonical.commandsDir}/SCHEMA.md`, templateFile: 'agents/commands/SCHEMA.md', component: 'commands' },
|
|
948
|
+
{ targetFile: `${LAYOUT.canonical.commandsDir}/README.md`, templateFile: 'agents/commands/README.md', component: 'commands' }
|
|
935
949
|
];
|
|
936
950
|
|
|
937
951
|
for (const {targetFile, templateFile, component} of checkFiles) {
|
|
@@ -1109,6 +1123,32 @@ program
|
|
|
1109
1123
|
console.log(chalk.white(' agents-templated problem-map "daily briefing app for founders"\n'));
|
|
1110
1124
|
});
|
|
1111
1125
|
|
|
1126
|
+
program
|
|
1127
|
+
.command('orchestrate [objective...]')
|
|
1128
|
+
.description('Automatically route a high-level objective across specialist subagents')
|
|
1129
|
+
.option('--scenario <id>', 'Force a specific scenario id (feature-delivery, backend-api, frontend-feature, bug-fix, deployment)')
|
|
1130
|
+
.option('--mode <mode>', 'slash-command or slash-command-auto', 'slash-command-auto')
|
|
1131
|
+
.option('--retry-cycle <n>', 'Current retry cycle for refactor-cleaner/build-error-resolver loop control', '0')
|
|
1132
|
+
.option('--json', 'Emit structured JSON only')
|
|
1133
|
+
.action((objective, options) => {
|
|
1134
|
+
const objectiveText = Array.isArray(objective) ? objective.join(' ') : '';
|
|
1135
|
+
const retryCycle = Number.parseInt(options.retryCycle, 10);
|
|
1136
|
+
const orchestrator = new WorkflowOrchestrator();
|
|
1137
|
+
const result = orchestrator.orchestrate({
|
|
1138
|
+
objective: objectiveText,
|
|
1139
|
+
scenarioId: options.scenario,
|
|
1140
|
+
mode: options.mode,
|
|
1141
|
+
retryCycle: Number.isNaN(retryCycle) ? 0 : retryCycle
|
|
1142
|
+
});
|
|
1143
|
+
|
|
1144
|
+
if (options.json) {
|
|
1145
|
+
process.stdout.write(`${JSON.stringify(result, null, 2)}\n`);
|
|
1146
|
+
return;
|
|
1147
|
+
}
|
|
1148
|
+
|
|
1149
|
+
process.stdout.write(formatOrchestrationOutput(result));
|
|
1150
|
+
});
|
|
1151
|
+
|
|
1112
1152
|
for (const workflow of WORKFLOW_COMMANDS) {
|
|
1113
1153
|
program
|
|
1114
1154
|
.command(`${workflow.cli} [objective...]`)
|
|
@@ -1119,6 +1159,24 @@ for (const workflow of WORKFLOW_COMMANDS) {
|
|
|
1119
1159
|
});
|
|
1120
1160
|
}
|
|
1121
1161
|
|
|
1162
|
+
for (const deprecatedAlias of DEPRECATED_COMMAND_ALIASES) {
|
|
1163
|
+
program
|
|
1164
|
+
.command(`${deprecatedAlias.from} [objective...]`)
|
|
1165
|
+
.description(`Deprecated alias for ${deprecatedAlias.to}`)
|
|
1166
|
+
.action((objective) => {
|
|
1167
|
+
const objectiveText = Array.isArray(objective) ? objective.join(' ') : '';
|
|
1168
|
+
const redirectedWorkflow = WORKFLOW_COMMANDS.find((workflow) => workflow.cli === deprecatedAlias.to);
|
|
1169
|
+
|
|
1170
|
+
if (!redirectedWorkflow) {
|
|
1171
|
+
console.error(chalk.red(`Deprecated alias target not found: ${deprecatedAlias.to}`));
|
|
1172
|
+
process.exit(1);
|
|
1173
|
+
}
|
|
1174
|
+
|
|
1175
|
+
console.log(chalk.yellow(`[deprecated] ${deprecatedAlias.notice}`));
|
|
1176
|
+
process.stdout.write(formatWorkflowOutput(redirectedWorkflow, objectiveText));
|
|
1177
|
+
});
|
|
1178
|
+
}
|
|
1179
|
+
|
|
1122
1180
|
program
|
|
1123
1181
|
.command('new-skill <name>')
|
|
1124
1182
|
.description('Scaffold a new skill in .github/skills/<name>/SKILL.md')
|
package/index.js
CHANGED
|
@@ -72,10 +72,10 @@ async function install(targetDir, options = {}) {
|
|
|
72
72
|
|
|
73
73
|
// Deterministic command contracts
|
|
74
74
|
if (installAll || options.commands) {
|
|
75
|
-
await fs.ensureDir(path.join(targetDir,
|
|
75
|
+
await fs.ensureDir(path.join(targetDir, LAYOUT.canonical.commandsDir));
|
|
76
76
|
await copyDirectory(
|
|
77
77
|
path.join(templateDir, 'agents', 'commands'),
|
|
78
|
-
path.join(targetDir,
|
|
78
|
+
path.join(targetDir, LAYOUT.canonical.commandsDir),
|
|
79
79
|
options.force
|
|
80
80
|
);
|
|
81
81
|
}
|
package/lib/layout.js
CHANGED
|
@@ -6,11 +6,13 @@ const LAYOUT = {
|
|
|
6
6
|
docsDir: 'agent-docs',
|
|
7
7
|
rulesDir: '.claude/rules',
|
|
8
8
|
skillsDir: '.github/skills',
|
|
9
|
-
subagentsDir: '.claude/agents'
|
|
9
|
+
subagentsDir: '.claude/agents',
|
|
10
|
+
commandsDir: '.claude/commands'
|
|
10
11
|
},
|
|
11
12
|
legacy: {
|
|
12
13
|
rulesDirs: ['agents/rules'],
|
|
13
|
-
skillsDirs: ['agents/skills']
|
|
14
|
+
skillsDirs: ['agents/skills'],
|
|
15
|
+
commandsDirs: ['agents/commands']
|
|
14
16
|
},
|
|
15
17
|
compatible: {
|
|
16
18
|
rulesDirs: [],
|
|
@@ -45,16 +47,26 @@ function resolveSubagentsDir(baseDir) {
|
|
|
45
47
|
return firstExistingPath(baseDir, candidates) || LAYOUT.canonical.subagentsDir;
|
|
46
48
|
}
|
|
47
49
|
|
|
50
|
+
function resolveCommandsDir(baseDir) {
|
|
51
|
+
const candidates = [
|
|
52
|
+
LAYOUT.canonical.commandsDir,
|
|
53
|
+
...LAYOUT.legacy.commandsDirs
|
|
54
|
+
];
|
|
55
|
+
return firstExistingPath(baseDir, candidates) || LAYOUT.canonical.commandsDir;
|
|
56
|
+
}
|
|
57
|
+
|
|
48
58
|
async function hasAnyLayout(baseDir) {
|
|
49
59
|
const checks = [
|
|
50
60
|
path.join(baseDir, LAYOUT.canonical.rulesDir),
|
|
51
61
|
path.join(baseDir, LAYOUT.canonical.skillsDir),
|
|
52
62
|
path.join(baseDir, LAYOUT.canonical.subagentsDir),
|
|
63
|
+
path.join(baseDir, LAYOUT.canonical.commandsDir),
|
|
53
64
|
path.join(baseDir, 'agents', 'subagents'),
|
|
54
65
|
...LAYOUT.compatible.rulesDirs.map((relPath) => path.join(baseDir, relPath)),
|
|
55
66
|
...LAYOUT.compatible.skillsDirs.map((relPath) => path.join(baseDir, relPath)),
|
|
56
67
|
...LAYOUT.legacy.rulesDirs.map((relPath) => path.join(baseDir, relPath)),
|
|
57
|
-
...LAYOUT.legacy.skillsDirs.map((relPath) => path.join(baseDir, relPath))
|
|
68
|
+
...LAYOUT.legacy.skillsDirs.map((relPath) => path.join(baseDir, relPath)),
|
|
69
|
+
...LAYOUT.legacy.commandsDirs.map((relPath) => path.join(baseDir, relPath))
|
|
58
70
|
];
|
|
59
71
|
|
|
60
72
|
for (const checkPath of checks) {
|
|
@@ -91,6 +103,17 @@ async function getLegacyMigrationPlan(baseDir) {
|
|
|
91
103
|
}
|
|
92
104
|
}
|
|
93
105
|
|
|
106
|
+
for (const relPath of LAYOUT.legacy.commandsDirs) {
|
|
107
|
+
const from = path.join(baseDir, relPath);
|
|
108
|
+
if (await fs.pathExists(from)) {
|
|
109
|
+
plan.push({
|
|
110
|
+
type: 'directory',
|
|
111
|
+
source: relPath,
|
|
112
|
+
target: LAYOUT.canonical.commandsDir
|
|
113
|
+
});
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
|
|
94
117
|
return plan;
|
|
95
118
|
}
|
|
96
119
|
|
|
@@ -98,6 +121,7 @@ module.exports = {
|
|
|
98
121
|
LAYOUT,
|
|
99
122
|
resolveRulesDir,
|
|
100
123
|
resolveSkillsDir,
|
|
124
|
+
resolveCommandsDir,
|
|
101
125
|
resolveSubagentsDir,
|
|
102
126
|
hasAnyLayout,
|
|
103
127
|
getLegacyMigrationPlan
|