diff --git a/src/cli/agent-help.ts b/src/cli/agent-help.ts index 59fb1a2..8511af1 100644 --- a/src/cli/agent-help.ts +++ b/src/cli/agent-help.ts @@ -72,14 +72,24 @@ function formatForAgent(meta: AgentCommandMeta) { return result; } +/** Maps deprecated command paths to their current canonical equivalents. */ +const commandAliases: Record = { + 'workspace status': 'status', +}; + +function resolveAlias(commandPath: string): string { + return commandAliases[commandPath] ?? commandPath; +} + /** * Look up a meta by the runtime command path (e.g. "skills list"). + * Resolves deprecated aliases (e.g. "workspace status" -> "status"). * Used by index.ts to validate `--json=` against the per-command * allowlist before dispatching. */ export function findMetaByCommand(commandPath: string): AgentCommandMeta | undefined { if (!commandPath) return undefined; - return allCommands.find((c) => c.command === commandPath); + return allCommands.find((c) => c.command === resolveAlias(commandPath)); } export function printAgentHelp(args: string[], version: string): void { @@ -98,16 +108,17 @@ export function printAgentHelp(args: string[], version: string): void { }; console.log(JSON.stringify(tree, null, 2)); } else { + const resolved = resolveAlias(commandPath); // Find exact matching command - const match = allCommands.find(c => c.command === commandPath); + const match = allCommands.find(c => c.command === resolved); if (match) { console.log(JSON.stringify(formatForAgent(match), null, 2)); } else { // Try prefix match for subcommand groups - const matches = allCommands.filter(c => c.command.startsWith(`${commandPath} `)); + const matches = allCommands.filter(c => c.command.startsWith(`${resolved} `)); if (matches.length > 0) { const group = { - name: commandPath, + name: resolved, commands: matches.map(formatForAgent), }; console.log(JSON.stringify(group, null, 2)); diff --git a/tests/unit/cli/agent-help.test.ts b/tests/unit/cli/agent-help.test.ts index db32c58..2c4cef3 100644 --- a/tests/unit/cli/agent-help.test.ts +++ b/tests/unit/cli/agent-help.test.ts @@ -1,5 +1,5 @@ import { describe, test, expect } from 'bun:test'; -import { extractAgentHelpFlag } from '../../../src/cli/agent-help.js'; +import { extractAgentHelpFlag, findMetaByCommand } from '../../../src/cli/agent-help.js'; import { initMeta, syncMeta, statusMeta } from '../../../src/cli/metadata/workspace.js'; import { marketplaceListMeta, @@ -137,3 +137,25 @@ describe('agent command metadata', () => { expect(statusCmd.options).toBeUndefined(); }); }); + +describe('findMetaByCommand', () => { + test('resolves canonical "status" path', () => { + const meta = findMetaByCommand('status'); + expect(meta).toBeDefined(); + expect(meta!.command).toBe('status'); + }); + + test('resolves deprecated "workspace status" alias to status meta', () => { + const meta = findMetaByCommand('workspace status'); + expect(meta).toBeDefined(); + expect(meta!.command).toBe('status'); + }); + + test('returns undefined for unknown command', () => { + expect(findMetaByCommand('workspace frobnicate')).toBeUndefined(); + }); + + test('returns undefined for empty string', () => { + expect(findMetaByCommand('')).toBeUndefined(); + }); +});