@bradygaster/squad-cli 0.9.4 → 0.9.5-insider.2
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/dist/cli/commands/preset.d.ts +24 -0
- package/dist/cli/commands/preset.d.ts.map +1 -0
- package/dist/cli/commands/preset.js +352 -0
- package/dist/cli/commands/preset.js.map +1 -0
- package/dist/cli-entry.js +45 -6
- package/dist/cli-entry.js.map +1 -1
- package/package.json +4 -4
- package/dist/cli/commands/skill.d.ts +0 -31
- package/dist/cli/commands/skill.d.ts.map +0 -1
- package/dist/cli/commands/skill.js +0 -497
- package/dist/cli/commands/skill.js.map +0 -1
- package/dist/cli/commands/watch/agent-spawn.d.ts +0 -62
- package/dist/cli/commands/watch/agent-spawn.d.ts.map +0 -1
- package/dist/cli/commands/watch/agent-spawn.js +0 -127
- package/dist/cli/commands/watch/agent-spawn.js.map +0 -1
|
@@ -1,497 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Skill command — APM (Agent Package Manager) integration
|
|
3
|
-
*
|
|
4
|
-
* squad skill publish [<name>] — export a skill to APM format
|
|
5
|
-
* squad skill install <name> — install a skill from APM registry
|
|
6
|
-
* squad skill list — list installed skills
|
|
7
|
-
*
|
|
8
|
-
* APM is package.json for AI agent context: https://github.com/microsoft/apm
|
|
9
|
-
*/
|
|
10
|
-
import { readFile, writeFile, mkdir, readdir } from 'node:fs/promises';
|
|
11
|
-
import { existsSync } from 'node:fs';
|
|
12
|
-
import { join, basename } from 'node:path';
|
|
13
|
-
import { execFile } from 'node:child_process';
|
|
14
|
-
import { promisify } from 'node:util';
|
|
15
|
-
import { success, warn, info, DIM, BOLD, RESET } from '../core/output.js';
|
|
16
|
-
import { fatal } from '../core/errors.js';
|
|
17
|
-
import { detectSquadDir } from '../core/detect-squad-dir.js';
|
|
18
|
-
import { ghAvailable } from '../core/gh-cli.js';
|
|
19
|
-
const IS_WINDOWS = process.platform === 'win32';
|
|
20
|
-
const execFileAsync = promisify(execFile);
|
|
21
|
-
// ── Helpers ───────────────────────────────────────────────────────────────────
|
|
22
|
-
/** Parse `---\nkey: value\n---` front-matter from a Markdown file. */
|
|
23
|
-
function parseFrontMatter(content) {
|
|
24
|
-
const match = content.match(/^---\r?\n([\s\S]*?)\r?\n---/);
|
|
25
|
-
if (!match)
|
|
26
|
-
return {};
|
|
27
|
-
const result = {};
|
|
28
|
-
for (const line of match[1].split('\n')) {
|
|
29
|
-
const colon = line.indexOf(':');
|
|
30
|
-
if (colon === -1)
|
|
31
|
-
continue;
|
|
32
|
-
const key = line.slice(0, colon).trim();
|
|
33
|
-
const value = line.slice(colon + 1).trim().replace(/^["']|["']$/g, '');
|
|
34
|
-
result[key] = value;
|
|
35
|
-
}
|
|
36
|
-
return result;
|
|
37
|
-
}
|
|
38
|
-
/** Read the project name from package.json, falling back to directory name. */
|
|
39
|
-
async function readProjectName(dest) {
|
|
40
|
-
const pkgPath = join(dest, 'package.json');
|
|
41
|
-
if (existsSync(pkgPath)) {
|
|
42
|
-
try {
|
|
43
|
-
const pkg = JSON.parse(await readFile(pkgPath, 'utf8'));
|
|
44
|
-
if (typeof pkg.name === 'string' && pkg.name)
|
|
45
|
-
return pkg.name;
|
|
46
|
-
}
|
|
47
|
-
catch {
|
|
48
|
-
// ignore
|
|
49
|
-
}
|
|
50
|
-
}
|
|
51
|
-
return basename(dest);
|
|
52
|
-
}
|
|
53
|
-
/**
|
|
54
|
-
* Resolve the skills directory, preferring .copilot/skills/ over .squad/skills/.
|
|
55
|
-
* Returns { dir, relPrefix } where relPrefix is the display path (e.g. '.copilot/skills').
|
|
56
|
-
*/
|
|
57
|
-
function resolveSkillsDir(dest) {
|
|
58
|
-
const copilotSkills = join(dest, '.copilot', 'skills');
|
|
59
|
-
if (existsSync(copilotSkills)) {
|
|
60
|
-
return { dir: copilotSkills, relPrefix: '.copilot/skills' };
|
|
61
|
-
}
|
|
62
|
-
const squadDirInfo = detectSquadDir(dest);
|
|
63
|
-
const squadSkills = join(squadDirInfo.path, 'skills');
|
|
64
|
-
if (existsSync(squadSkills)) {
|
|
65
|
-
return { dir: squadSkills, relPrefix: `${squadDirInfo.name}/skills` };
|
|
66
|
-
}
|
|
67
|
-
// Default to .copilot/skills/ for new installs
|
|
68
|
-
return { dir: copilotSkills, relPrefix: '.copilot/skills' };
|
|
69
|
-
}
|
|
70
|
-
/** Collect all skills from the skills directory. */
|
|
71
|
-
async function collectSkills(skillsDir, relPrefix) {
|
|
72
|
-
if (!existsSync(skillsDir))
|
|
73
|
-
return [];
|
|
74
|
-
const skills = [];
|
|
75
|
-
try {
|
|
76
|
-
const entries = await readdir(skillsDir);
|
|
77
|
-
for (const entry of entries) {
|
|
78
|
-
const skillFile = join(skillsDir, entry, 'skill.md');
|
|
79
|
-
if (!existsSync(skillFile))
|
|
80
|
-
continue;
|
|
81
|
-
const content = await readFile(skillFile, 'utf8');
|
|
82
|
-
const fm = parseFrontMatter(content);
|
|
83
|
-
skills.push({
|
|
84
|
-
name: fm['name'] ?? entry,
|
|
85
|
-
description: fm['description'],
|
|
86
|
-
path: `${relPrefix}/${entry}/skill.md`,
|
|
87
|
-
version: fm['version'],
|
|
88
|
-
source: fm['source'],
|
|
89
|
-
});
|
|
90
|
-
}
|
|
91
|
-
}
|
|
92
|
-
catch {
|
|
93
|
-
// ignore read errors
|
|
94
|
-
}
|
|
95
|
-
return skills;
|
|
96
|
-
}
|
|
97
|
-
// ── Sub-commands ──────────────────────────────────────────────────────────────
|
|
98
|
-
/**
|
|
99
|
-
* squad skill publish [<name>]
|
|
100
|
-
*
|
|
101
|
-
* Exports a skill (or all skills) to APM-compatible format.
|
|
102
|
-
* Creates/updates apm.yml at the project root.
|
|
103
|
-
*/
|
|
104
|
-
async function publish(dest, skillName) {
|
|
105
|
-
const { dir: skillsDir, relPrefix } = resolveSkillsDir(dest);
|
|
106
|
-
if (!existsSync(skillsDir)) {
|
|
107
|
-
fatal('No skills directory found. Create .copilot/skills/ first.');
|
|
108
|
-
}
|
|
109
|
-
const projectName = await readProjectName(dest);
|
|
110
|
-
if (skillName) {
|
|
111
|
-
// Publish a single named skill
|
|
112
|
-
const skillFile = join(skillsDir, skillName, 'skill.md');
|
|
113
|
-
if (!existsSync(skillFile)) {
|
|
114
|
-
fatal(`Skill '${skillName}' not found at ${relPrefix}/${skillName}/skill.md`);
|
|
115
|
-
}
|
|
116
|
-
const content = await readFile(skillFile, 'utf8');
|
|
117
|
-
const fm = parseFrontMatter(content);
|
|
118
|
-
// Build the skill's own apm.yml inside its directory
|
|
119
|
-
const apmSkillPath = join(skillsDir, skillName, 'apm.yml');
|
|
120
|
-
const skillApm = [
|
|
121
|
-
`name: ${fm['name'] ?? skillName}`,
|
|
122
|
-
`version: ${fm['version'] ?? '1.0.0'}`,
|
|
123
|
-
fm['description'] ? `description: "${fm['description']}"` : null,
|
|
124
|
-
``,
|
|
125
|
-
`skills:`,
|
|
126
|
-
` - name: ${fm['name'] ?? skillName}`,
|
|
127
|
-
` path: skill.md`,
|
|
128
|
-
fm['description'] ? ` description: "${fm['description']}"` : null,
|
|
129
|
-
]
|
|
130
|
-
.filter(l => l !== null)
|
|
131
|
-
.join('\n');
|
|
132
|
-
await writeFile(apmSkillPath, skillApm + '\n', 'utf8');
|
|
133
|
-
success(`Published skill '${skillName}' to ${relPrefix}/${skillName}/apm.yml`);
|
|
134
|
-
info(`${DIM}APM format ready — push to GitHub to share via APM registry${RESET}`);
|
|
135
|
-
return;
|
|
136
|
-
}
|
|
137
|
-
// Publish all skills → update project-level apm.yml
|
|
138
|
-
const skills = await collectSkills(skillsDir, relPrefix);
|
|
139
|
-
const apmPath = join(dest, 'apm.yml');
|
|
140
|
-
// Read existing apm.yml to preserve manually-added fields
|
|
141
|
-
let existing = {};
|
|
142
|
-
if (existsSync(apmPath)) {
|
|
143
|
-
try {
|
|
144
|
-
// Simple YAML parse — only top-level fields we care about
|
|
145
|
-
const raw = await readFile(apmPath, 'utf8');
|
|
146
|
-
if (raw.includes('instructions:')) {
|
|
147
|
-
// Preserve instructions block (just keep existing file, re-emit skills section)
|
|
148
|
-
info(`${DIM}Updating skills section in existing apm.yml${RESET}`);
|
|
149
|
-
}
|
|
150
|
-
existing = { name: projectName };
|
|
151
|
-
}
|
|
152
|
-
catch {
|
|
153
|
-
existing = {};
|
|
154
|
-
}
|
|
155
|
-
}
|
|
156
|
-
const lines = [
|
|
157
|
-
`# apm.yml — Agent Package Manager manifest`,
|
|
158
|
-
`# See: https://github.com/microsoft/apm`,
|
|
159
|
-
``,
|
|
160
|
-
`name: ${existing.name ?? projectName}`,
|
|
161
|
-
`version: 1.0.0`,
|
|
162
|
-
``,
|
|
163
|
-
`# Skills exported from ${relPrefix}/`,
|
|
164
|
-
`skills:`,
|
|
165
|
-
...skills.map(s => [
|
|
166
|
-
` - name: ${s.name}`,
|
|
167
|
-
s.description ? ` description: "${s.description}"` : null,
|
|
168
|
-
` path: ${s.path}`,
|
|
169
|
-
s.version ? ` version: ${s.version}` : null,
|
|
170
|
-
]
|
|
171
|
-
.filter(l => l !== null)
|
|
172
|
-
.join('\n')),
|
|
173
|
-
``,
|
|
174
|
-
`# Instruction files deployed by 'apm install'`,
|
|
175
|
-
`instructions:`,
|
|
176
|
-
` - path: .squad/copilot-instructions.md`,
|
|
177
|
-
` target: .github/copilot-instructions.md`,
|
|
178
|
-
``,
|
|
179
|
-
`# Prompts deployed by 'apm install'`,
|
|
180
|
-
`prompts:`,
|
|
181
|
-
` - path: ${relPrefix}/*/skill.md`,
|
|
182
|
-
` target: .github/prompts/`,
|
|
183
|
-
];
|
|
184
|
-
await writeFile(apmPath, lines.join('\n') + '\n', 'utf8');
|
|
185
|
-
if (skills.length > 0) {
|
|
186
|
-
success(`Published ${skills.length} skill(s) to apm.yml`);
|
|
187
|
-
for (const s of skills) {
|
|
188
|
-
info(` ${DIM}• ${s.name}${RESET}`);
|
|
189
|
-
}
|
|
190
|
-
}
|
|
191
|
-
else {
|
|
192
|
-
success(`Created apm.yml (no skills found yet — add skills to ${relPrefix}/)`);
|
|
193
|
-
}
|
|
194
|
-
info(`${DIM}Run 'apm publish' to push to the APM registry${RESET}`);
|
|
195
|
-
}
|
|
196
|
-
/**
|
|
197
|
-
* squad skill install <source>
|
|
198
|
-
*
|
|
199
|
-
* Installs a skill from an APM source.
|
|
200
|
-
* Source formats:
|
|
201
|
-
* owner/repo — install all skills from a GitHub repo
|
|
202
|
-
* owner/repo/skill-name — install a specific skill
|
|
203
|
-
* https://... — URL to a raw skill.md
|
|
204
|
-
*/
|
|
205
|
-
async function install(dest, source) {
|
|
206
|
-
if (!source) {
|
|
207
|
-
fatal('Usage: squad skill install <owner/repo>[/<skill-name>] | <url>');
|
|
208
|
-
}
|
|
209
|
-
const { dir: skillsDir, relPrefix } = resolveSkillsDir(dest);
|
|
210
|
-
if (!existsSync(skillsDir)) {
|
|
211
|
-
await mkdir(skillsDir, { recursive: true });
|
|
212
|
-
}
|
|
213
|
-
// URL-based install
|
|
214
|
-
if (source.startsWith('http://') || source.startsWith('https://')) {
|
|
215
|
-
await installFromUrl(source, skillsDir, relPrefix);
|
|
216
|
-
return;
|
|
217
|
-
}
|
|
218
|
-
// GitHub-based: owner/repo or owner/repo/skill-name
|
|
219
|
-
const parts = source.split('/');
|
|
220
|
-
if (parts.length < 2) {
|
|
221
|
-
fatal('Invalid source. Use: owner/repo, owner/repo/skill-name, or a URL');
|
|
222
|
-
}
|
|
223
|
-
const owner = parts[0];
|
|
224
|
-
const repo = parts[1];
|
|
225
|
-
const skillFilter = parts.length >= 3 ? parts.slice(2).join('/') : undefined;
|
|
226
|
-
if (!(await ghAvailable())) {
|
|
227
|
-
fatal('GitHub CLI (gh) is required for APM install. Install from https://cli.github.com/');
|
|
228
|
-
}
|
|
229
|
-
info(`${DIM}Fetching skill(s) from ${owner}/${repo}...${RESET}`);
|
|
230
|
-
// Try to find skills via gh api — look for apm.yml or .copilot/skills/
|
|
231
|
-
await installFromGitHub(owner, repo, skillFilter, skillsDir, dest);
|
|
232
|
-
}
|
|
233
|
-
async function installFromUrl(url, skillsDir, relPrefix) {
|
|
234
|
-
let content;
|
|
235
|
-
try {
|
|
236
|
-
// Node 18+ has built-in fetch
|
|
237
|
-
const res = await fetch(url);
|
|
238
|
-
if (!res.ok) {
|
|
239
|
-
fatal(`Failed to fetch ${url}: ${res.status} ${res.statusText}`);
|
|
240
|
-
}
|
|
241
|
-
content = await res.text();
|
|
242
|
-
}
|
|
243
|
-
catch (err) {
|
|
244
|
-
fatal(`Failed to fetch ${url}: ${err.message}`);
|
|
245
|
-
return;
|
|
246
|
-
}
|
|
247
|
-
// Derive skill name from URL
|
|
248
|
-
const urlName = url
|
|
249
|
-
.split('/')
|
|
250
|
-
.filter(Boolean)
|
|
251
|
-
.slice(-2, -1)[0] ??
|
|
252
|
-
'imported-skill';
|
|
253
|
-
const skillName = urlName.replace(/[^a-z0-9-_]/gi, '-').toLowerCase();
|
|
254
|
-
const skillDir = join(skillsDir, skillName);
|
|
255
|
-
await mkdir(skillDir, { recursive: true });
|
|
256
|
-
await writeFile(join(skillDir, 'skill.md'), content, 'utf8');
|
|
257
|
-
success(`Installed skill '${skillName}' from URL`);
|
|
258
|
-
info(` ${DIM}Location: ${relPrefix}/${skillName}/skill.md${RESET}`);
|
|
259
|
-
}
|
|
260
|
-
async function installFromGitHub(owner, repo, skillFilter, skillsDir, dest) {
|
|
261
|
-
// First, try to read the apm.yml from the repo to discover skills
|
|
262
|
-
let apmContent = null;
|
|
263
|
-
try {
|
|
264
|
-
const { stdout } = await execFileAsync('gh', [
|
|
265
|
-
'api',
|
|
266
|
-
`repos/${owner}/${repo}/contents/apm.yml`,
|
|
267
|
-
'--jq', '.content',
|
|
268
|
-
], { shell: IS_WINDOWS });
|
|
269
|
-
apmContent = Buffer.from(stdout.trim(), 'base64').toString('utf8');
|
|
270
|
-
}
|
|
271
|
-
catch {
|
|
272
|
-
// No apm.yml — fall back to scanning skills directories
|
|
273
|
-
}
|
|
274
|
-
if (!apmContent) {
|
|
275
|
-
// Fall back: try skills directories via API
|
|
276
|
-
await installSkillsFromSquadDir(owner, repo, skillFilter, skillsDir);
|
|
277
|
-
return;
|
|
278
|
-
}
|
|
279
|
-
// Parse the apm.yml to find skill paths
|
|
280
|
-
const skillPaths = [];
|
|
281
|
-
const lines = apmContent.split('\n');
|
|
282
|
-
let inSkills = false;
|
|
283
|
-
let currentSkill = {};
|
|
284
|
-
for (const line of lines) {
|
|
285
|
-
if (line.trim() === 'skills:') {
|
|
286
|
-
inSkills = true;
|
|
287
|
-
continue;
|
|
288
|
-
}
|
|
289
|
-
if (inSkills && line.match(/^[a-z]/i) && !line.startsWith(' ')) {
|
|
290
|
-
// New top-level key — exit skills section
|
|
291
|
-
if (currentSkill.name && currentSkill.path)
|
|
292
|
-
skillPaths.push(currentSkill);
|
|
293
|
-
currentSkill = {};
|
|
294
|
-
inSkills = false;
|
|
295
|
-
}
|
|
296
|
-
if (inSkills) {
|
|
297
|
-
const nameMatch = line.match(/^\s+- name:\s*(.+)$/);
|
|
298
|
-
const pathMatch = line.match(/^\s+path:\s*(.+)$/);
|
|
299
|
-
if (nameMatch) {
|
|
300
|
-
if (currentSkill.name && currentSkill.path)
|
|
301
|
-
skillPaths.push(currentSkill);
|
|
302
|
-
currentSkill = { name: nameMatch[1].trim() };
|
|
303
|
-
}
|
|
304
|
-
if (pathMatch)
|
|
305
|
-
currentSkill.path = pathMatch[1].trim();
|
|
306
|
-
}
|
|
307
|
-
}
|
|
308
|
-
if (currentSkill.name && currentSkill.path)
|
|
309
|
-
skillPaths.push(currentSkill);
|
|
310
|
-
// Filter by skill name if specified
|
|
311
|
-
const toInstall = skillFilter
|
|
312
|
-
? skillPaths.filter(s => s.name === skillFilter || s.path.includes(skillFilter))
|
|
313
|
-
: skillPaths;
|
|
314
|
-
if (toInstall.length === 0) {
|
|
315
|
-
if (skillFilter) {
|
|
316
|
-
fatal(`Skill '${skillFilter}' not found in ${owner}/${repo}'s apm.yml`);
|
|
317
|
-
}
|
|
318
|
-
else {
|
|
319
|
-
warn(`No skills declared in ${owner}/${repo}'s apm.yml`);
|
|
320
|
-
return;
|
|
321
|
-
}
|
|
322
|
-
}
|
|
323
|
-
let installed = 0;
|
|
324
|
-
for (const skill of toInstall) {
|
|
325
|
-
try {
|
|
326
|
-
const { stdout: rawContent } = await execFileAsync('gh', [
|
|
327
|
-
'api',
|
|
328
|
-
`repos/${owner}/${repo}/contents/${skill.path}`,
|
|
329
|
-
'--jq', '.content',
|
|
330
|
-
], { shell: IS_WINDOWS });
|
|
331
|
-
const content = Buffer.from(rawContent.trim(), 'base64').toString('utf8');
|
|
332
|
-
const skillDir = join(skillsDir, skill.name);
|
|
333
|
-
await mkdir(skillDir, { recursive: true });
|
|
334
|
-
await writeFile(join(skillDir, 'skill.md'), content, 'utf8');
|
|
335
|
-
// Write a source metadata file so we can track origin
|
|
336
|
-
const meta = {
|
|
337
|
-
source: `${owner}/${repo}`,
|
|
338
|
-
path: skill.path,
|
|
339
|
-
installed_at: new Date().toISOString(),
|
|
340
|
-
};
|
|
341
|
-
await writeFile(join(skillDir, '.apm-source.json'), JSON.stringify(meta, null, 2) + '\n', 'utf8');
|
|
342
|
-
success(`Installed skill '${skill.name}'`);
|
|
343
|
-
info(` ${DIM}Source: ${owner}/${repo}${skill.path}${RESET}`);
|
|
344
|
-
installed++;
|
|
345
|
-
}
|
|
346
|
-
catch (err) {
|
|
347
|
-
warn(`Failed to install '${skill.name}': ${err.message}`);
|
|
348
|
-
}
|
|
349
|
-
}
|
|
350
|
-
if (installed > 0) {
|
|
351
|
-
info(`\n${DIM}Run 'squad skill publish' to refresh apm.yml with newly installed skills${RESET}`);
|
|
352
|
-
}
|
|
353
|
-
}
|
|
354
|
-
async function installSkillsFromSquadDir(owner, repo, skillFilter, skillsDir) {
|
|
355
|
-
// Try .copilot/skills/ (standard) then .squad/skills/ (legacy) then bare skills/
|
|
356
|
-
const candidates = ['.copilot/skills', '.squad/skills', 'skills'];
|
|
357
|
-
let entries = [];
|
|
358
|
-
for (const candidate of candidates) {
|
|
359
|
-
try {
|
|
360
|
-
const { stdout } = await execFileAsync('gh', [
|
|
361
|
-
'api',
|
|
362
|
-
`repos/${owner}/${repo}/contents/${candidate}`,
|
|
363
|
-
'--jq', '[.[] | {name: .name, path: .path, type: .type}]',
|
|
364
|
-
], { shell: IS_WINDOWS });
|
|
365
|
-
entries = JSON.parse(stdout);
|
|
366
|
-
break;
|
|
367
|
-
}
|
|
368
|
-
catch {
|
|
369
|
-
continue;
|
|
370
|
-
}
|
|
371
|
-
}
|
|
372
|
-
if (entries.length === 0) {
|
|
373
|
-
fatal(`No skills directory found in ${owner}/${repo}. The repo may not use APM or Squad conventions.`);
|
|
374
|
-
}
|
|
375
|
-
const dirs = entries.filter(e => e.type === 'dir');
|
|
376
|
-
const toInstall = skillFilter ? dirs.filter(d => d.name === skillFilter) : dirs;
|
|
377
|
-
if (toInstall.length === 0) {
|
|
378
|
-
if (skillFilter) {
|
|
379
|
-
fatal(`Skill '${skillFilter}' not found in ${owner}/${repo}`);
|
|
380
|
-
}
|
|
381
|
-
else {
|
|
382
|
-
warn(`No skill directories found in ${owner}/${repo}`);
|
|
383
|
-
return;
|
|
384
|
-
}
|
|
385
|
-
}
|
|
386
|
-
let installed = 0;
|
|
387
|
-
for (const dir of toInstall) {
|
|
388
|
-
const skillFilePath = `${dir.path}/skill.md`;
|
|
389
|
-
try {
|
|
390
|
-
const { stdout: rawContent } = await execFileAsync('gh', [
|
|
391
|
-
'api',
|
|
392
|
-
`repos/${owner}/${repo}/contents/${skillFilePath}`,
|
|
393
|
-
'--jq', '.content',
|
|
394
|
-
], { shell: IS_WINDOWS });
|
|
395
|
-
const content = Buffer.from(rawContent.trim(), 'base64').toString('utf8');
|
|
396
|
-
const skillDir = join(skillsDir, dir.name);
|
|
397
|
-
await mkdir(skillDir, { recursive: true });
|
|
398
|
-
await writeFile(join(skillDir, 'skill.md'), content, 'utf8');
|
|
399
|
-
const meta = {
|
|
400
|
-
source: `${owner}/${repo}`,
|
|
401
|
-
path: skillFilePath,
|
|
402
|
-
installed_at: new Date().toISOString(),
|
|
403
|
-
};
|
|
404
|
-
await writeFile(join(skillDir, '.apm-source.json'), JSON.stringify(meta, null, 2) + '\n', 'utf8');
|
|
405
|
-
success(`Installed skill '${dir.name}'`);
|
|
406
|
-
info(` ${DIM}Source: ${owner}/${repo}/${skillFilePath}${RESET}`);
|
|
407
|
-
installed++;
|
|
408
|
-
}
|
|
409
|
-
catch {
|
|
410
|
-
warn(`Skipped '${dir.name}' — no skill.md found`);
|
|
411
|
-
}
|
|
412
|
-
}
|
|
413
|
-
if (installed > 0) {
|
|
414
|
-
info(`\n${DIM}Run 'squad skill publish' to refresh apm.yml${RESET}`);
|
|
415
|
-
}
|
|
416
|
-
}
|
|
417
|
-
/**
|
|
418
|
-
* squad skill list
|
|
419
|
-
*
|
|
420
|
-
* Lists installed skills from .copilot/skills/ (or legacy .squad/skills/).
|
|
421
|
-
*/
|
|
422
|
-
async function listSkills(dest) {
|
|
423
|
-
const { dir: skillsDir, relPrefix } = resolveSkillsDir(dest);
|
|
424
|
-
if (!existsSync(skillsDir)) {
|
|
425
|
-
info('No skills directory found. Run "squad init" first or create .copilot/skills/');
|
|
426
|
-
return;
|
|
427
|
-
}
|
|
428
|
-
const skills = await collectSkills(skillsDir, relPrefix);
|
|
429
|
-
if (skills.length === 0) {
|
|
430
|
-
info(`${DIM}No skills installed yet.${RESET}`);
|
|
431
|
-
info(`Install a skill: squad skill install <owner/repo>`);
|
|
432
|
-
return;
|
|
433
|
-
}
|
|
434
|
-
console.log(`\n${BOLD}Installed Skills${RESET}\n`);
|
|
435
|
-
for (const skill of skills) {
|
|
436
|
-
const metaPath = join(skillsDir, skill.name, '.apm-source.json');
|
|
437
|
-
let sourceNote = '';
|
|
438
|
-
if (existsSync(metaPath)) {
|
|
439
|
-
try {
|
|
440
|
-
const meta = JSON.parse(await readFile(metaPath, 'utf8'));
|
|
441
|
-
sourceNote = ` ${DIM}(from ${meta.source})${RESET}`;
|
|
442
|
-
}
|
|
443
|
-
catch {
|
|
444
|
-
// ignore
|
|
445
|
-
}
|
|
446
|
-
}
|
|
447
|
-
console.log(` ${BOLD}${skill.name}${RESET}${sourceNote}`);
|
|
448
|
-
if (skill.description) {
|
|
449
|
-
console.log(` ${DIM}${skill.description}${RESET}`);
|
|
450
|
-
}
|
|
451
|
-
}
|
|
452
|
-
console.log();
|
|
453
|
-
}
|
|
454
|
-
// ── Main export ───────────────────────────────────────────────────────────────
|
|
455
|
-
/**
|
|
456
|
-
* Entry point for `squad skill` command.
|
|
457
|
-
*
|
|
458
|
-
* @param dest - Working directory (usually process.cwd())
|
|
459
|
-
* @param args - Remaining args after `squad skill`
|
|
460
|
-
*/
|
|
461
|
-
export async function runSkill(dest, args) {
|
|
462
|
-
const subCmd = args[0];
|
|
463
|
-
if (!subCmd || subCmd === 'help' || subCmd === '--help') {
|
|
464
|
-
console.log(`\n${BOLD}squad skill${RESET} — APM (Agent Package Manager) integration\n`);
|
|
465
|
-
console.log(`Usage:`);
|
|
466
|
-
console.log(` squad skill publish [<skill-name>] Export skill(s) to APM format (apm.yml)`);
|
|
467
|
-
console.log(` squad skill install <source> Install from APM registry`);
|
|
468
|
-
console.log(` squad skill list List installed skills`);
|
|
469
|
-
console.log(`\nInstall sources:`);
|
|
470
|
-
console.log(` owner/repo All skills from a GitHub repo`);
|
|
471
|
-
console.log(` owner/repo/skill-name A specific skill from a GitHub repo`);
|
|
472
|
-
console.log(` https://... A direct URL to a skill.md file`);
|
|
473
|
-
console.log(`\nAPM registry: https://github.com/microsoft/apm\n`);
|
|
474
|
-
return;
|
|
475
|
-
}
|
|
476
|
-
switch (subCmd) {
|
|
477
|
-
case 'publish': {
|
|
478
|
-
const skillName = args[1];
|
|
479
|
-
await publish(dest, skillName);
|
|
480
|
-
break;
|
|
481
|
-
}
|
|
482
|
-
case 'install': {
|
|
483
|
-
const source = args[1];
|
|
484
|
-
if (!source) {
|
|
485
|
-
fatal('Usage: squad skill install <owner/repo>[/<skill-name>] | <url>');
|
|
486
|
-
}
|
|
487
|
-
await install(dest, source);
|
|
488
|
-
break;
|
|
489
|
-
}
|
|
490
|
-
case 'list':
|
|
491
|
-
await listSkills(dest);
|
|
492
|
-
break;
|
|
493
|
-
default:
|
|
494
|
-
fatal(`Unknown skill subcommand: ${subCmd}\nRun 'squad skill help' for usage.`);
|
|
495
|
-
}
|
|
496
|
-
}
|
|
497
|
-
//# sourceMappingURL=skill.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"skill.js","sourceRoot":"","sources":["../../../src/cli/commands/skill.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,62 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Shared agent spawn utilities for watch capabilities.
|
|
3
|
-
*
|
|
4
|
-
* Centralises `buildAgentCommand()` and `spawnWithTimeout()` so every
|
|
5
|
-
* capability uses the same logic, respects `agentCmd` from config,
|
|
6
|
-
* and works on Windows (shell: true when win32).
|
|
7
|
-
*
|
|
8
|
-
* @see https://github.com/bradygaster/squad/issues/920
|
|
9
|
-
* @see https://github.com/bradygaster/squad/issues/923
|
|
10
|
-
*/
|
|
11
|
-
import type { WatchContext } from './types.js';
|
|
12
|
-
/** True when running on Windows — used to gate `shell: true`. */
|
|
13
|
-
export declare const IS_WINDOWS: boolean;
|
|
14
|
-
/**
|
|
15
|
-
* Detect which copilot CLI is available at runtime.
|
|
16
|
-
*
|
|
17
|
-
* Tries standalone `copilot` first (modern default). If that fails,
|
|
18
|
-
* falls back to `gh copilot` (legacy). The result is cached for the
|
|
19
|
-
* lifetime of the process so we only shell-out once.
|
|
20
|
-
*
|
|
21
|
-
* @returns `{ cmd, cmdPrefix }` — e.g. `{ cmd: 'copilot', cmdPrefix: [] }`
|
|
22
|
-
* or `{ cmd: 'gh', cmdPrefix: ['copilot'] }`.
|
|
23
|
-
*/
|
|
24
|
-
export declare function resolveCopilotCmd(): {
|
|
25
|
-
cmd: string;
|
|
26
|
-
cmdPrefix: string[];
|
|
27
|
-
};
|
|
28
|
-
/**
|
|
29
|
-
* Reset the cached copilot detection. Exported for testing only.
|
|
30
|
-
* @internal
|
|
31
|
-
*/
|
|
32
|
-
export declare function _resetCopilotDetection(): void;
|
|
33
|
-
/**
|
|
34
|
-
* Build the command + args array for an agent invocation.
|
|
35
|
-
*
|
|
36
|
-
* Resolution order:
|
|
37
|
-
* 1. `context.agentCmd` (explicit override from config / CLI)
|
|
38
|
-
* 2. Runtime detection via `resolveCopilotCmd()`:
|
|
39
|
-
* - standalone `copilot` if available on PATH
|
|
40
|
-
* - `gh copilot` as fallback
|
|
41
|
-
*/
|
|
42
|
-
export declare function buildAgentCommand(prompt: string, context: WatchContext): {
|
|
43
|
-
cmd: string;
|
|
44
|
-
args: string[];
|
|
45
|
-
};
|
|
46
|
-
/**
|
|
47
|
-
* Spawn an agent command with a timeout.
|
|
48
|
-
*
|
|
49
|
-
* Uses `shell: true` on Windows so that `.cmd`/`.bat` wrappers and
|
|
50
|
-
* PATH resolution work correctly.
|
|
51
|
-
*/
|
|
52
|
-
export declare function spawnWithTimeout(cmd: string, args: string[], cwd: string, timeoutMs: number): Promise<void>;
|
|
53
|
-
/**
|
|
54
|
-
* Spawn an agent command with a timeout, resolving with success/error
|
|
55
|
-
* instead of rejecting. Used by execute and wave-dispatch where the
|
|
56
|
-
* caller wants to handle failure without try/catch.
|
|
57
|
-
*/
|
|
58
|
-
export declare function spawnAgent(cmd: string, args: string[], cwd: string, timeoutMs: number): Promise<{
|
|
59
|
-
success: boolean;
|
|
60
|
-
error?: string;
|
|
61
|
-
}>;
|
|
62
|
-
//# sourceMappingURL=agent-spawn.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"agent-spawn.d.ts","sourceRoot":"","sources":["../../../../src/cli/commands/watch/agent-spawn.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAGH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAE/C,iEAAiE;AACjE,eAAO,MAAM,UAAU,SAA+B,CAAC;AAQvD;;;;;;;;;GASG;AACH,wBAAgB,iBAAiB,IAAI;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,SAAS,EAAE,MAAM,EAAE,CAAA;CAAE,CAgBxE;AAED;;;GAGG;AACH,wBAAgB,sBAAsB,IAAI,IAAI,CAE7C;AAED;;;;;;;;GAQG;AACH,wBAAgB,iBAAiB,CAC/B,MAAM,EAAE,MAAM,EACd,OAAO,EAAE,YAAY,GACpB;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,EAAE,CAAA;CAAE,CAejC;AAED;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAC9B,GAAG,EAAE,MAAM,EACX,IAAI,EAAE,MAAM,EAAE,EACd,GAAG,EAAE,MAAM,EACX,SAAS,EAAE,MAAM,GAChB,OAAO,CAAC,IAAI,CAAC,CAoBf;AAED;;;;GAIG;AACH,wBAAgB,UAAU,CACxB,GAAG,EAAE,MAAM,EACX,IAAI,EAAE,MAAM,EAAE,EACd,GAAG,EAAE,MAAM,EACX,SAAS,EAAE,MAAM,GAChB,OAAO,CAAC;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CAsB/C"}
|