skild 0.2.2 → 0.2.4
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 +90 -32
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -7,7 +7,7 @@ import { createRequire } from "module";
|
|
|
7
7
|
|
|
8
8
|
// src/commands/install.ts
|
|
9
9
|
import chalk2 from "chalk";
|
|
10
|
-
import { fetchWithTimeout, installRegistrySkill, installSkill, resolveRegistryUrl, SkildError } from "@skild/core";
|
|
10
|
+
import { fetchWithTimeout, installRegistrySkill, installSkill, loadRegistryAuth, resolveRegistryUrl, SkildError } from "@skild/core";
|
|
11
11
|
|
|
12
12
|
// src/utils/logger.ts
|
|
13
13
|
import chalk from "chalk";
|
|
@@ -55,10 +55,10 @@ var logger = {
|
|
|
55
55
|
/**
|
|
56
56
|
* Log a skill entry with status indicator.
|
|
57
57
|
*/
|
|
58
|
-
skillEntry: (name,
|
|
58
|
+
skillEntry: (name, path3, hasSkillMd) => {
|
|
59
59
|
const status = hasSkillMd ? chalk.green("\u2713") : chalk.yellow("\u26A0");
|
|
60
60
|
console.log(` ${status} ${chalk.cyan(name)}`);
|
|
61
|
-
console.log(chalk.dim(` \u2514\u2500 ${
|
|
61
|
+
console.log(chalk.dim(` \u2514\u2500 ${path3}`));
|
|
62
62
|
},
|
|
63
63
|
/**
|
|
64
64
|
* Log installation result details.
|
|
@@ -73,12 +73,14 @@ var logger = {
|
|
|
73
73
|
async function install(source, options = {}) {
|
|
74
74
|
const platform = options.target || "claude";
|
|
75
75
|
const scope = options.local ? "project" : "global";
|
|
76
|
+
const auth = loadRegistryAuth();
|
|
77
|
+
const registryUrlForDeps = options.registry || auth?.registryUrl;
|
|
76
78
|
const spinner = createSpinner(`Installing ${chalk2.cyan(source)} to ${chalk2.dim(platform)} (${scope})...`);
|
|
77
79
|
try {
|
|
78
80
|
const record = source.trim().startsWith("@") && source.includes("/") ? await installRegistrySkill(
|
|
79
|
-
{ spec: source, registryUrl:
|
|
81
|
+
{ spec: source, registryUrl: registryUrlForDeps },
|
|
80
82
|
{ platform, scope, force: Boolean(options.force) }
|
|
81
|
-
) : await installSkill({ source }, { platform, scope, force: Boolean(options.force) });
|
|
83
|
+
) : await installSkill({ source }, { platform, scope, force: Boolean(options.force), registryUrl: registryUrlForDeps });
|
|
82
84
|
const displayName = record.canonicalName || record.name;
|
|
83
85
|
spinner.succeed(`Installed ${chalk2.green(displayName)} to ${chalk2.dim(record.installDir)}`);
|
|
84
86
|
if (options.json) {
|
|
@@ -95,7 +97,7 @@ async function install(source, options = {}) {
|
|
|
95
97
|
} else if (record.skill?.validation?.ok) {
|
|
96
98
|
logger.installDetail(`Validation: ${chalk2.green("ok")}`);
|
|
97
99
|
}
|
|
98
|
-
void reportDownload(record,
|
|
100
|
+
void reportDownload(record, registryUrlForDeps);
|
|
99
101
|
} catch (error) {
|
|
100
102
|
spinner.fail(`Failed to install ${chalk2.red(source)}`);
|
|
101
103
|
const message = error instanceof SkildError ? error.message : error instanceof Error ? error.message : String(error);
|
|
@@ -136,7 +138,52 @@ async function reportDownload(record, registryOverride) {
|
|
|
136
138
|
|
|
137
139
|
// src/commands/list.ts
|
|
138
140
|
import chalk3 from "chalk";
|
|
141
|
+
import fs from "fs";
|
|
142
|
+
import path from "path";
|
|
139
143
|
import { PLATFORMS, listAllSkills, listSkills } from "@skild/core";
|
|
144
|
+
function toDisplayName(name, mapping) {
|
|
145
|
+
return mapping.get(name) || name;
|
|
146
|
+
}
|
|
147
|
+
function buildDisplayEntries(skills) {
|
|
148
|
+
const nameToDisplay = /* @__PURE__ */ new Map();
|
|
149
|
+
for (const skill of skills) {
|
|
150
|
+
const displayName = skill.record?.canonicalName || skill.name;
|
|
151
|
+
nameToDisplay.set(skill.name, displayName);
|
|
152
|
+
}
|
|
153
|
+
const entries = skills.map((skill) => {
|
|
154
|
+
const displayName = toDisplayName(skill.name, nameToDisplay);
|
|
155
|
+
const flags = [];
|
|
156
|
+
if (skill.record?.skillset || skill.record?.skill?.frontmatter?.skillset) {
|
|
157
|
+
flags.push("skillset");
|
|
158
|
+
}
|
|
159
|
+
if (skill.record?.dependedBy?.length) {
|
|
160
|
+
const dependedBy = skill.record.dependedBy.map((name) => toDisplayName(name, nameToDisplay));
|
|
161
|
+
flags.push(`dep of: ${dependedBy.join(", ")}`);
|
|
162
|
+
}
|
|
163
|
+
return {
|
|
164
|
+
name: displayName,
|
|
165
|
+
installDir: skill.installDir,
|
|
166
|
+
status: skill.hasSkillMd ? "ok" : "warn",
|
|
167
|
+
flags
|
|
168
|
+
};
|
|
169
|
+
});
|
|
170
|
+
for (const skill of skills) {
|
|
171
|
+
const inlineDeps = skill.record?.installedDependencies?.filter((dep) => dep.sourceType === "inline") || [];
|
|
172
|
+
if (!inlineDeps.length) continue;
|
|
173
|
+
const ownerName = toDisplayName(skill.name, nameToDisplay);
|
|
174
|
+
for (const dep of inlineDeps) {
|
|
175
|
+
const inlineDir = dep.inlinePath ? path.join(skill.installDir, dep.inlinePath) : path.join(skill.installDir, dep.name);
|
|
176
|
+
const hasSkillMd = fs.existsSync(path.join(inlineDir, "SKILL.md"));
|
|
177
|
+
entries.push({
|
|
178
|
+
name: dep.name,
|
|
179
|
+
installDir: inlineDir,
|
|
180
|
+
status: hasSkillMd ? "ok" : "warn",
|
|
181
|
+
flags: [`dep of: ${ownerName}`]
|
|
182
|
+
});
|
|
183
|
+
}
|
|
184
|
+
}
|
|
185
|
+
return entries;
|
|
186
|
+
}
|
|
140
187
|
async function list(options = {}) {
|
|
141
188
|
const scope = options.local ? "project" : "global";
|
|
142
189
|
const platform = options.target;
|
|
@@ -151,14 +198,15 @@ async function list(options = {}) {
|
|
|
151
198
|
console.log(chalk3.dim(`Use ${chalk3.cyan("skild install <source>")} to install a skill.`));
|
|
152
199
|
return;
|
|
153
200
|
}
|
|
201
|
+
const entries = buildDisplayEntries(skills);
|
|
154
202
|
console.log(chalk3.bold(`
|
|
155
|
-
\u{1F4E6} Installed Skills (${
|
|
203
|
+
\u{1F4E6} Installed Skills (${entries.length}) \u2014 ${platform} (${scope}):
|
|
156
204
|
`));
|
|
157
|
-
for (const
|
|
158
|
-
const status =
|
|
159
|
-
const
|
|
160
|
-
console.log(` ${status} ${chalk3.cyan(
|
|
161
|
-
console.log(chalk3.dim(` \u2514\u2500 ${
|
|
205
|
+
for (const entry of entries) {
|
|
206
|
+
const status = entry.status === "ok" ? chalk3.green("\u2713") : chalk3.yellow("\u26A0");
|
|
207
|
+
const label = entry.flags.length ? `${entry.name} (${entry.flags.join("; ")})` : entry.name;
|
|
208
|
+
console.log(` ${status} ${chalk3.cyan(label)}`);
|
|
209
|
+
console.log(chalk3.dim(` \u2514\u2500 ${entry.installDir}`));
|
|
162
210
|
}
|
|
163
211
|
console.log("");
|
|
164
212
|
return;
|
|
@@ -178,17 +226,18 @@ async function list(options = {}) {
|
|
|
178
226
|
`));
|
|
179
227
|
for (const p of PLATFORMS) {
|
|
180
228
|
const platformSkills = allSkills.filter((s) => s.platform === p).sort((a, b) => a.name.localeCompare(b.name));
|
|
181
|
-
const
|
|
229
|
+
const entries = buildDisplayEntries(platformSkills);
|
|
230
|
+
const header = `${p} (${entries.length})`;
|
|
182
231
|
console.log(chalk3.bold(` ${header}`));
|
|
183
|
-
if (
|
|
232
|
+
if (entries.length === 0) {
|
|
184
233
|
console.log(chalk3.dim(" (none)"));
|
|
185
234
|
continue;
|
|
186
235
|
}
|
|
187
|
-
for (const
|
|
188
|
-
const status =
|
|
189
|
-
const
|
|
190
|
-
console.log(` ${status} ${chalk3.cyan(
|
|
191
|
-
console.log(chalk3.dim(` \u2514\u2500 ${
|
|
236
|
+
for (const entry of entries) {
|
|
237
|
+
const status = entry.status === "ok" ? chalk3.green("\u2713") : chalk3.yellow("\u26A0");
|
|
238
|
+
const label = entry.flags.length ? `${entry.name} (${entry.flags.join("; ")})` : entry.name;
|
|
239
|
+
console.log(` ${status} ${chalk3.cyan(label)}`);
|
|
240
|
+
console.log(chalk3.dim(` \u2514\u2500 ${entry.installDir}`));
|
|
192
241
|
}
|
|
193
242
|
}
|
|
194
243
|
console.log("");
|
|
@@ -246,7 +295,12 @@ async function uninstall(skill, options = {}) {
|
|
|
246
295
|
const resolvedName = canonical.startsWith("@") && canonical.includes("/") ? canonicalNameToInstallDirName2(canonical) : canonical;
|
|
247
296
|
const spinner = createSpinner(`Uninstalling ${chalk5.cyan(canonical)} from ${chalk5.dim(platform)} (${scope})...`);
|
|
248
297
|
try {
|
|
249
|
-
uninstallSkill(resolvedName, {
|
|
298
|
+
uninstallSkill(resolvedName, {
|
|
299
|
+
platform,
|
|
300
|
+
scope,
|
|
301
|
+
allowMissingMetadata: Boolean(options.force),
|
|
302
|
+
withDeps: Boolean(options.withDeps)
|
|
303
|
+
});
|
|
250
304
|
spinner.succeed(`Uninstalled ${chalk5.green(canonical)}`);
|
|
251
305
|
} catch (error) {
|
|
252
306
|
spinner.fail(`Failed to uninstall ${chalk5.red(canonical)}`);
|
|
@@ -500,9 +554,9 @@ async function logout() {
|
|
|
500
554
|
|
|
501
555
|
// src/commands/whoami.ts
|
|
502
556
|
import chalk12 from "chalk";
|
|
503
|
-
import { fetchWithTimeout as fetchWithTimeout4, loadRegistryAuth, resolveRegistryUrl as resolveRegistryUrl4, SkildError as SkildError8 } from "@skild/core";
|
|
557
|
+
import { fetchWithTimeout as fetchWithTimeout4, loadRegistryAuth as loadRegistryAuth2, resolveRegistryUrl as resolveRegistryUrl4, SkildError as SkildError8 } from "@skild/core";
|
|
504
558
|
async function whoami() {
|
|
505
|
-
const auth =
|
|
559
|
+
const auth = loadRegistryAuth2();
|
|
506
560
|
if (!auth) {
|
|
507
561
|
console.error(chalk12.red("Not logged in. Run `skild login` first."));
|
|
508
562
|
process.exitCode = 1;
|
|
@@ -532,13 +586,13 @@ async function whoami() {
|
|
|
532
586
|
}
|
|
533
587
|
|
|
534
588
|
// src/commands/publish.ts
|
|
535
|
-
import
|
|
589
|
+
import fs2 from "fs";
|
|
536
590
|
import os from "os";
|
|
537
|
-
import
|
|
591
|
+
import path2 from "path";
|
|
538
592
|
import crypto from "crypto";
|
|
539
593
|
import * as tar from "tar";
|
|
540
594
|
import chalk13 from "chalk";
|
|
541
|
-
import { fetchWithTimeout as fetchWithTimeout5, loadRegistryAuth as
|
|
595
|
+
import { fetchWithTimeout as fetchWithTimeout5, loadRegistryAuth as loadRegistryAuth3, resolveRegistryUrl as resolveRegistryUrl5, SkildError as SkildError9, splitCanonicalName, validateSkillDir } from "@skild/core";
|
|
542
596
|
function sha256Hex(buf) {
|
|
543
597
|
const h = crypto.createHash("sha256");
|
|
544
598
|
h.update(buf);
|
|
@@ -549,7 +603,7 @@ function parseTargets(raw) {
|
|
|
549
603
|
return raw.split(",").map((s) => s.trim()).filter(Boolean);
|
|
550
604
|
}
|
|
551
605
|
async function publish(options = {}) {
|
|
552
|
-
const auth =
|
|
606
|
+
const auth = loadRegistryAuth3();
|
|
553
607
|
const registry = resolveRegistryUrl5(options.registry || auth?.registryUrl);
|
|
554
608
|
const token = auth?.token;
|
|
555
609
|
if (!token) {
|
|
@@ -557,7 +611,7 @@ async function publish(options = {}) {
|
|
|
557
611
|
process.exitCode = 1;
|
|
558
612
|
return;
|
|
559
613
|
}
|
|
560
|
-
const dir =
|
|
614
|
+
const dir = path2.resolve(options.dir || process.cwd());
|
|
561
615
|
const validation = validateSkillDir(dir);
|
|
562
616
|
if (!validation.ok) {
|
|
563
617
|
console.error(chalk13.red("Skill validation failed:"));
|
|
@@ -571,6 +625,8 @@ async function publish(options = {}) {
|
|
|
571
625
|
const description = (options.description || fm.description || "").trim();
|
|
572
626
|
const tag = (options.tag || "latest").trim() || "latest";
|
|
573
627
|
const targets = parseTargets(options.targets);
|
|
628
|
+
const skillset = fm.skillset === true;
|
|
629
|
+
const dependencies = Array.isArray(fm.dependencies) ? fm.dependencies : [];
|
|
574
630
|
if (!name) {
|
|
575
631
|
console.error(chalk13.red("Missing name. Provide SKILL.md frontmatter.name or --name."));
|
|
576
632
|
process.exitCode = 1;
|
|
@@ -614,8 +670,8 @@ async function publish(options = {}) {
|
|
|
614
670
|
return;
|
|
615
671
|
}
|
|
616
672
|
const spinner = createSpinner(`Publishing ${chalk13.cyan(`${name}@${version2}`)} to ${chalk13.dim(registry)}...`);
|
|
617
|
-
const tempDir =
|
|
618
|
-
const tarballPath =
|
|
673
|
+
const tempDir = fs2.mkdtempSync(path2.join(os.tmpdir(), "skild-publish-"));
|
|
674
|
+
const tarballPath = path2.join(tempDir, "skill.tgz");
|
|
619
675
|
try {
|
|
620
676
|
await tar.c(
|
|
621
677
|
{
|
|
@@ -627,13 +683,15 @@ async function publish(options = {}) {
|
|
|
627
683
|
},
|
|
628
684
|
["."]
|
|
629
685
|
);
|
|
630
|
-
const buf =
|
|
686
|
+
const buf = fs2.readFileSync(tarballPath);
|
|
631
687
|
const integrity = sha256Hex(buf);
|
|
632
688
|
const form = new FormData();
|
|
633
689
|
form.set("version", version2);
|
|
634
690
|
form.set("description", description);
|
|
635
691
|
form.set("targets", JSON.stringify(targets));
|
|
636
692
|
form.set("tag", tag);
|
|
693
|
+
form.set("skillset", skillset ? "true" : "false");
|
|
694
|
+
form.set("dependencies", JSON.stringify(dependencies));
|
|
637
695
|
form.append("tarball", new Blob([buf], { type: "application/gzip" }), "skill.tgz");
|
|
638
696
|
const { scope, name: skillName } = splitCanonicalName(name);
|
|
639
697
|
const res = await fetchWithTimeout5(
|
|
@@ -669,7 +727,7 @@ async function publish(options = {}) {
|
|
|
669
727
|
console.error(chalk13.red(message));
|
|
670
728
|
process.exitCode = 1;
|
|
671
729
|
} finally {
|
|
672
|
-
|
|
730
|
+
fs2.rmSync(tempDir, { recursive: true, force: true });
|
|
673
731
|
}
|
|
674
732
|
}
|
|
675
733
|
|
|
@@ -716,7 +774,7 @@ program.command("install <source>").alias("i").description("Install a Skill from
|
|
|
716
774
|
});
|
|
717
775
|
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));
|
|
718
776
|
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));
|
|
719
|
-
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").action(async (skill, options) => uninstall(skill, options));
|
|
777
|
+
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));
|
|
720
778
|
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));
|
|
721
779
|
program.command("validate [target]").alias("v").description("Validate a Skill folder (path) or an installed Skill name").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 (target, options) => validate(target, options));
|
|
722
780
|
program.command("init <name>").description("Create a new Skill project").option("--dir <path>", "Target directory (defaults to <name>)").option("--description <text>", "Skill description").option("-f, --force", "Overwrite target directory if it exists").action(async (name, options) => init(name, options));
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "skild",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.4",
|
|
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.4"
|
|
41
41
|
},
|
|
42
42
|
"devDependencies": {
|
|
43
43
|
"@types/node": "^20.10.0",
|