skild 0.2.7 → 0.2.8
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/index.js +121 -83
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -57,10 +57,10 @@ var logger = {
|
|
|
57
57
|
/**
|
|
58
58
|
* Log a skill entry with status indicator.
|
|
59
59
|
*/
|
|
60
|
-
skillEntry: (name,
|
|
60
|
+
skillEntry: (name, path3, hasSkillMd) => {
|
|
61
61
|
const status = hasSkillMd ? chalk.green("\u2713") : chalk.yellow("\u26A0");
|
|
62
62
|
console.log(` ${status} ${chalk.cyan(name)}`);
|
|
63
|
-
console.log(chalk.dim(` \u2514\u2500 ${
|
|
63
|
+
console.log(chalk.dim(` \u2514\u2500 ${path3}`));
|
|
64
64
|
},
|
|
65
65
|
/**
|
|
66
66
|
* Log installation result details.
|
|
@@ -166,54 +166,122 @@ async function reportDownload(record, registryOverride) {
|
|
|
166
166
|
|
|
167
167
|
// src/commands/list.ts
|
|
168
168
|
import chalk3 from "chalk";
|
|
169
|
-
import fs2 from "fs";
|
|
170
|
-
import path2 from "path";
|
|
171
169
|
import { PLATFORMS, listAllSkills, listSkills } from "@skild/core";
|
|
172
|
-
function
|
|
173
|
-
return
|
|
170
|
+
function isSkillset(skill) {
|
|
171
|
+
return Boolean(skill.record?.skillset || skill.record?.skill?.frontmatter?.skillset);
|
|
174
172
|
}
|
|
175
|
-
function
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
}
|
|
181
|
-
const entries = skills.map((skill) => {
|
|
182
|
-
const displayName = toDisplayName(skill.name, nameToDisplay);
|
|
183
|
-
const flags = [];
|
|
184
|
-
if (skill.record?.skillset || skill.record?.skill?.frontmatter?.skillset) {
|
|
185
|
-
flags.push("skillset");
|
|
186
|
-
}
|
|
187
|
-
if (skill.record?.dependedBy?.length) {
|
|
188
|
-
const dependedBy = skill.record.dependedBy.map((name) => toDisplayName(name, nameToDisplay));
|
|
189
|
-
flags.push(`dep of: ${dependedBy.join(", ")}`);
|
|
190
|
-
}
|
|
191
|
-
return {
|
|
192
|
-
name: displayName,
|
|
193
|
-
installDir: skill.installDir,
|
|
194
|
-
status: skill.hasSkillMd ? "ok" : "warn",
|
|
195
|
-
flags
|
|
196
|
-
};
|
|
197
|
-
});
|
|
173
|
+
function getDisplayName(skill) {
|
|
174
|
+
return skill.record?.canonicalName || skill.record?.skill?.frontmatter?.name || skill.name;
|
|
175
|
+
}
|
|
176
|
+
function buildNameToDisplay(skills) {
|
|
177
|
+
const mapping = /* @__PURE__ */ new Map();
|
|
198
178
|
for (const skill of skills) {
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
179
|
+
mapping.set(skill.name, getDisplayName(skill));
|
|
180
|
+
}
|
|
181
|
+
return mapping;
|
|
182
|
+
}
|
|
183
|
+
function statusIcon(skill) {
|
|
184
|
+
return skill.hasSkillMd ? chalk3.green("\u2713") : chalk3.yellow("\u26A0");
|
|
185
|
+
}
|
|
186
|
+
function missingSkillMdLabel(skill) {
|
|
187
|
+
return skill.hasSkillMd ? "" : chalk3.yellow(" (missing SKILL.md)");
|
|
188
|
+
}
|
|
189
|
+
function formatDepName(dep, nameToDisplay) {
|
|
190
|
+
return dep.canonicalName || nameToDisplay.get(dep.name) || dep.name;
|
|
191
|
+
}
|
|
192
|
+
function summarizeDeps(record) {
|
|
193
|
+
const deps = record?.installedDependencies || [];
|
|
194
|
+
if (deps.length === 0) return null;
|
|
195
|
+
const byType = deps.reduce(
|
|
196
|
+
(acc, d) => {
|
|
197
|
+
acc.total += 1;
|
|
198
|
+
if (d.sourceType === "inline") acc.inline += 1;
|
|
199
|
+
else acc.external += 1;
|
|
200
|
+
acc.bySourceType[d.sourceType] = (acc.bySourceType[d.sourceType] || 0) + 1;
|
|
201
|
+
return acc;
|
|
202
|
+
},
|
|
203
|
+
{ total: 0, inline: 0, external: 0, bySourceType: {} }
|
|
204
|
+
);
|
|
205
|
+
const parts = [];
|
|
206
|
+
if (byType.inline) parts.push(`${byType.inline} inline`);
|
|
207
|
+
const externalParts = Object.entries(byType.bySourceType).filter(([t]) => t !== "inline").sort(([a], [b]) => a.localeCompare(b)).map(([t, c2]) => `${c2} ${t}`);
|
|
208
|
+
if (externalParts.length) parts.push(...externalParts);
|
|
209
|
+
return `deps: ${byType.total}${parts.length ? ` (${parts.join(", ")})` : ""}`;
|
|
210
|
+
}
|
|
211
|
+
function printSkillsetSection(skills, nameToDisplay, options) {
|
|
212
|
+
console.log(chalk3.bold(` Skillsets (${skills.length})`));
|
|
213
|
+
if (skills.length === 0) {
|
|
214
|
+
console.log(chalk3.dim(" (none)"));
|
|
215
|
+
return;
|
|
216
|
+
}
|
|
217
|
+
for (const s of skills) {
|
|
218
|
+
const label = `${chalk3.cyan(getDisplayName(s))}${chalk3.dim(" (skillset)")}${missingSkillMdLabel(s)}`;
|
|
219
|
+
console.log(` ${statusIcon(s)} ${label}`);
|
|
220
|
+
const summary = summarizeDeps(s.record);
|
|
221
|
+
if (summary) console.log(chalk3.dim(` ${summary}`));
|
|
222
|
+
if (options.verbose) {
|
|
223
|
+
const deps = (s.record?.installedDependencies || []).slice().sort((a, b) => a.name.localeCompare(b.name));
|
|
224
|
+
if (deps.length) {
|
|
225
|
+
console.log(chalk3.dim(` includes (${deps.length}):`));
|
|
226
|
+
for (const dep of deps) {
|
|
227
|
+
const depName = formatDepName(dep, nameToDisplay);
|
|
228
|
+
console.log(chalk3.dim(` - ${depName} [${dep.sourceType}]`));
|
|
229
|
+
}
|
|
230
|
+
}
|
|
211
231
|
}
|
|
232
|
+
if (options.paths || !s.hasSkillMd) console.log(chalk3.dim(` path: ${s.installDir}`));
|
|
212
233
|
}
|
|
213
|
-
|
|
234
|
+
}
|
|
235
|
+
function printSkillsSection(skills, options) {
|
|
236
|
+
console.log(chalk3.bold(` Skills (${skills.length})`));
|
|
237
|
+
if (skills.length === 0) {
|
|
238
|
+
console.log(chalk3.dim(" (none)"));
|
|
239
|
+
return;
|
|
240
|
+
}
|
|
241
|
+
for (const s of skills) {
|
|
242
|
+
const label = `${chalk3.cyan(getDisplayName(s))}${missingSkillMdLabel(s)}`;
|
|
243
|
+
console.log(` ${statusIcon(s)} ${label}`);
|
|
244
|
+
if (options.paths || !s.hasSkillMd) console.log(chalk3.dim(` path: ${s.installDir}`));
|
|
245
|
+
}
|
|
246
|
+
}
|
|
247
|
+
function printDependenciesSection(skills, nameToDisplay, options) {
|
|
248
|
+
console.log(chalk3.bold(` Dependencies (${skills.length})`));
|
|
249
|
+
if (skills.length === 0) {
|
|
250
|
+
console.log(chalk3.dim(" (none)"));
|
|
251
|
+
return;
|
|
252
|
+
}
|
|
253
|
+
for (const s of skills) {
|
|
254
|
+
const dependedBy = (s.record?.dependedBy || []).map((name) => nameToDisplay.get(name) || name).sort((a, b) => a.localeCompare(b));
|
|
255
|
+
const requiredBy = dependedBy.length ? chalk3.dim(` \u2190 required by: ${dependedBy.join(", ")}`) : "";
|
|
256
|
+
const label = `${chalk3.cyan(getDisplayName(s))}${missingSkillMdLabel(s)}${requiredBy}`;
|
|
257
|
+
console.log(` ${statusIcon(s)} ${label}`);
|
|
258
|
+
if (options.paths || !s.hasSkillMd) console.log(chalk3.dim(` path: ${s.installDir}`));
|
|
259
|
+
}
|
|
260
|
+
}
|
|
261
|
+
function printPlatform(skills, platform, scope, options) {
|
|
262
|
+
console.log(chalk3.bold(`
|
|
263
|
+
\u{1F4E6} Installed Skills \u2014 ${platform} (${scope})
|
|
264
|
+
`));
|
|
265
|
+
if (skills.length === 0) {
|
|
266
|
+
console.log(chalk3.dim(" No skills installed."));
|
|
267
|
+
console.log(chalk3.dim(` Use ${chalk3.cyan("skild install <source>")} to install a skill.`));
|
|
268
|
+
return;
|
|
269
|
+
}
|
|
270
|
+
const nameToDisplay = buildNameToDisplay(skills);
|
|
271
|
+
const skillsets = skills.filter(isSkillset).sort((a, b) => getDisplayName(a).localeCompare(getDisplayName(b)));
|
|
272
|
+
const dependencies = skills.filter((s) => !isSkillset(s) && Boolean(s.record?.dependedBy?.length)).sort((a, b) => getDisplayName(a).localeCompare(getDisplayName(b)));
|
|
273
|
+
const regular = skills.filter((s) => !isSkillset(s) && !Boolean(s.record?.dependedBy?.length)).sort((a, b) => getDisplayName(a).localeCompare(getDisplayName(b)));
|
|
274
|
+
printSkillsetSection(skillsets, nameToDisplay, options);
|
|
275
|
+
console.log("");
|
|
276
|
+
printSkillsSection(regular, options);
|
|
277
|
+
console.log("");
|
|
278
|
+
printDependenciesSection(dependencies, nameToDisplay, options);
|
|
279
|
+
console.log("");
|
|
214
280
|
}
|
|
215
281
|
async function list(options = {}) {
|
|
216
282
|
const scope = options.local ? "project" : "global";
|
|
283
|
+
const paths = Boolean(options.paths);
|
|
284
|
+
const verbose = Boolean(options.verbose);
|
|
217
285
|
const platform = options.target;
|
|
218
286
|
if (platform) {
|
|
219
287
|
const skills = listSkills({ platform, scope });
|
|
@@ -221,22 +289,7 @@ async function list(options = {}) {
|
|
|
221
289
|
console.log(JSON.stringify(skills, null, 2));
|
|
222
290
|
return;
|
|
223
291
|
}
|
|
224
|
-
|
|
225
|
-
console.log(chalk3.dim("No skills installed."));
|
|
226
|
-
console.log(chalk3.dim(`Use ${chalk3.cyan("skild install <source>")} to install a skill.`));
|
|
227
|
-
return;
|
|
228
|
-
}
|
|
229
|
-
const entries = buildDisplayEntries(skills);
|
|
230
|
-
console.log(chalk3.bold(`
|
|
231
|
-
\u{1F4E6} Installed Skills (${entries.length}) \u2014 ${platform} (${scope}):
|
|
232
|
-
`));
|
|
233
|
-
for (const entry of entries) {
|
|
234
|
-
const status = entry.status === "ok" ? chalk3.green("\u2713") : chalk3.yellow("\u26A0");
|
|
235
|
-
const label = entry.flags.length ? `${entry.name} (${entry.flags.join("; ")})` : entry.name;
|
|
236
|
-
console.log(` ${status} ${chalk3.cyan(label)}`);
|
|
237
|
-
console.log(chalk3.dim(` \u2514\u2500 ${entry.installDir}`));
|
|
238
|
-
}
|
|
239
|
-
console.log("");
|
|
292
|
+
printPlatform(skills, platform, scope, { paths, verbose });
|
|
240
293
|
return;
|
|
241
294
|
}
|
|
242
295
|
const allSkills = listAllSkills({ scope });
|
|
@@ -249,26 +302,11 @@ async function list(options = {}) {
|
|
|
249
302
|
console.log(chalk3.dim(`Use ${chalk3.cyan("skild install <source>")} to install a skill.`));
|
|
250
303
|
return;
|
|
251
304
|
}
|
|
252
|
-
console.log(chalk3.bold(`
|
|
253
|
-
\u{1F4E6} Installed Skills \u2014 all platforms (${scope}):
|
|
254
|
-
`));
|
|
255
305
|
for (const p of PLATFORMS) {
|
|
256
306
|
const platformSkills = allSkills.filter((s) => s.platform === p).sort((a, b) => a.name.localeCompare(b.name));
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
console.log(chalk3.bold(` ${header}`));
|
|
260
|
-
if (entries.length === 0) {
|
|
261
|
-
console.log(chalk3.dim(" (none)"));
|
|
262
|
-
continue;
|
|
263
|
-
}
|
|
264
|
-
for (const entry of entries) {
|
|
265
|
-
const status = entry.status === "ok" ? chalk3.green("\u2713") : chalk3.yellow("\u26A0");
|
|
266
|
-
const label = entry.flags.length ? `${entry.name} (${entry.flags.join("; ")})` : entry.name;
|
|
267
|
-
console.log(` ${status} ${chalk3.cyan(label)}`);
|
|
268
|
-
console.log(chalk3.dim(` \u2514\u2500 ${entry.installDir}`));
|
|
269
|
-
}
|
|
307
|
+
if (platformSkills.length === 0) continue;
|
|
308
|
+
printPlatform(platformSkills, p, scope, { paths, verbose });
|
|
270
309
|
}
|
|
271
|
-
console.log("");
|
|
272
310
|
}
|
|
273
311
|
|
|
274
312
|
// src/commands/info.ts
|
|
@@ -664,9 +702,9 @@ async function whoami() {
|
|
|
664
702
|
}
|
|
665
703
|
|
|
666
704
|
// src/commands/publish.ts
|
|
667
|
-
import
|
|
705
|
+
import fs2 from "fs";
|
|
668
706
|
import os from "os";
|
|
669
|
-
import
|
|
707
|
+
import path2 from "path";
|
|
670
708
|
import crypto from "crypto";
|
|
671
709
|
import * as tar from "tar";
|
|
672
710
|
import chalk13 from "chalk";
|
|
@@ -689,7 +727,7 @@ async function publish(options = {}) {
|
|
|
689
727
|
process.exitCode = 1;
|
|
690
728
|
return;
|
|
691
729
|
}
|
|
692
|
-
const dir =
|
|
730
|
+
const dir = path2.resolve(options.dir || process.cwd());
|
|
693
731
|
const validation = validateSkillDir(dir);
|
|
694
732
|
if (!validation.ok) {
|
|
695
733
|
console.error(chalk13.red("Skill validation failed:"));
|
|
@@ -748,8 +786,8 @@ async function publish(options = {}) {
|
|
|
748
786
|
return;
|
|
749
787
|
}
|
|
750
788
|
const spinner = createSpinner(`Publishing ${chalk13.cyan(`${name}@${version2}`)} to ${chalk13.dim(registry)}...`);
|
|
751
|
-
const tempDir =
|
|
752
|
-
const tarballPath =
|
|
789
|
+
const tempDir = fs2.mkdtempSync(path2.join(os.tmpdir(), "skild-publish-"));
|
|
790
|
+
const tarballPath = path2.join(tempDir, "skill.tgz");
|
|
753
791
|
try {
|
|
754
792
|
await tar.c(
|
|
755
793
|
{
|
|
@@ -761,7 +799,7 @@ async function publish(options = {}) {
|
|
|
761
799
|
},
|
|
762
800
|
["."]
|
|
763
801
|
);
|
|
764
|
-
const buf =
|
|
802
|
+
const buf = fs2.readFileSync(tarballPath);
|
|
765
803
|
const integrity = sha256Hex(buf);
|
|
766
804
|
const form = new FormData();
|
|
767
805
|
form.set("version", version2);
|
|
@@ -805,7 +843,7 @@ async function publish(options = {}) {
|
|
|
805
843
|
console.error(chalk13.red(message));
|
|
806
844
|
process.exitCode = 1;
|
|
807
845
|
} finally {
|
|
808
|
-
|
|
846
|
+
fs2.rmSync(tempDir, { recursive: true, force: true });
|
|
809
847
|
}
|
|
810
848
|
}
|
|
811
849
|
|
|
@@ -850,7 +888,7 @@ program.name("skild").description("The npm for Agent Skills \u2014 Discover, ins
|
|
|
850
888
|
program.command("install <source>").alias("i").description("Install a Skill from a Git URL, degit shorthand, or local directory").option("-t, --target <platform>", `Target platform: ${PLATFORMS2.join(", ")}`, "claude").option("-l, --local", "Install to project-level directory instead of global").option("-f, --force", "Overwrite existing installation").option("--registry <url>", "Registry base URL (default: https://registry.skild.sh)").option("--json", "Output JSON").action(async (source, options) => {
|
|
851
889
|
await install(source, options);
|
|
852
890
|
});
|
|
853
|
-
program.command("list").alias("ls").description("List installed Skills").option("-t, --target <platform>", `Target platform: ${PLATFORMS2.join(", ")} (optional; omit to list all)`).option("-l, --local", "List project-level directory instead of global").option("--json", "Output JSON").action(async (options) => list(options));
|
|
891
|
+
program.command("list").alias("ls").description("List installed Skills").option("-t, --target <platform>", `Target platform: ${PLATFORMS2.join(", ")} (optional; omit to list all)`).option("-l, --local", "List project-level directory instead of global").option("--paths", "Show install paths").option("--verbose", "Show skillset dependency details").option("--json", "Output JSON").action(async (options) => list(options));
|
|
854
892
|
program.command("info <skill>").description("Show installed Skill details").option("-t, --target <platform>", `Target platform: ${PLATFORMS2.join(", ")}`, "claude").option("-l, --local", "Use project-level directory instead of global").option("--json", "Output JSON").action(async (skill, options) => info(skill, options));
|
|
855
893
|
program.command("uninstall <skill>").alias("rm").description("Uninstall a Skill").option("-t, --target <platform>", `Target platform: ${PLATFORMS2.join(", ")}`, "claude").option("-l, --local", "Use project-level directory instead of global").option("-f, --force", "Uninstall even if metadata is missing").option("--with-deps", "Uninstall dependencies that are only required by this skill").action(async (skill, options) => uninstall(skill, options));
|
|
856
894
|
program.command("update [skill]").alias("up").description("Update one or all installed Skills").option("-t, --target <platform>", `Target platform: ${PLATFORMS2.join(", ")}`, "claude").option("-l, --local", "Use project-level directory instead of global").option("--json", "Output JSON").action(async (skill, options) => update(skill, options));
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "skild",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.8",
|
|
4
4
|
"description": "The npm for Agent Skills — Discover, install, manage, and publish AI Agent Skills with ease.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|
|
@@ -37,7 +37,7 @@
|
|
|
37
37
|
"commander": "^12.1.0",
|
|
38
38
|
"ora": "^8.0.1",
|
|
39
39
|
"tar": "^7.4.3",
|
|
40
|
-
"@skild/core": "^0.2.
|
|
40
|
+
"@skild/core": "^0.2.8"
|
|
41
41
|
},
|
|
42
42
|
"devDependencies": {
|
|
43
43
|
"@types/node": "^20.10.0",
|