skillops-cli 1.3.6 → 1.3.7
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.js +89 -21
- package/dist/index.d.ts +8 -3
- package/dist/index.js +85 -19
- package/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -10,7 +10,7 @@ import YAML6 from "yaml";
|
|
|
10
10
|
import fs from "fs";
|
|
11
11
|
import YAML from "yaml";
|
|
12
12
|
import { z } from "zod";
|
|
13
|
-
var SKILLOPS_VERSION = "1.3.
|
|
13
|
+
var SKILLOPS_VERSION = "1.3.7";
|
|
14
14
|
var SKILL_NAME_REGEX = /^[a-z0-9]+(?:-[a-z0-9]+)*$/;
|
|
15
15
|
var SEMVER_REGEX = /^\d+\.\d+\.\d+$/;
|
|
16
16
|
var FRONTMATTER_REGEX = /^---\r?\n([\s\S]*?)\r?\n---\r?\n?([\s\S]*)$/;
|
|
@@ -5412,6 +5412,9 @@ function optionMatchesQuery(opt, rawQuery) {
|
|
|
5412
5412
|
if (!q) {
|
|
5413
5413
|
return true;
|
|
5414
5414
|
}
|
|
5415
|
+
if (opt.isSelectAll) {
|
|
5416
|
+
return false;
|
|
5417
|
+
}
|
|
5415
5418
|
return opt.label.toLowerCase().includes(q) || opt.value.toLowerCase().includes(q) || (opt.hint ?? "").toLowerCase().includes(q);
|
|
5416
5419
|
}
|
|
5417
5420
|
function getFilteredTabOptions(state, tab = state.activeTab) {
|
|
@@ -5419,16 +5422,47 @@ function getFilteredTabOptions(state, tab = state.activeTab) {
|
|
|
5419
5422
|
(opt) => optionMatchesTab(opt, tab) && optionMatchesQuery(opt, state.searchQuery)
|
|
5420
5423
|
);
|
|
5421
5424
|
}
|
|
5422
|
-
function createMultiSelectState(options) {
|
|
5425
|
+
function createMultiSelectState(options, stateOptions = {}) {
|
|
5426
|
+
let finalOptions = options;
|
|
5427
|
+
if (stateOptions.showSelectAll && !options.some((opt) => opt.isSelectAll === true)) {
|
|
5428
|
+
const skillItems = options.filter((opt) => optionMatchesTab(opt, "skill"));
|
|
5429
|
+
const agentItems = options.filter((opt) => optionMatchesTab(opt, "agent"));
|
|
5430
|
+
const withAll = [];
|
|
5431
|
+
if (skillItems.length > 0) {
|
|
5432
|
+
withAll.push({
|
|
5433
|
+
value: "__all_skills__",
|
|
5434
|
+
label: "[ALL] Select all Skills",
|
|
5435
|
+
kind: "skill",
|
|
5436
|
+
tab: "skill",
|
|
5437
|
+
isSelectAll: true,
|
|
5438
|
+
hint: `Select or deselect all ${skillItems.length} Skills in this tab`
|
|
5439
|
+
});
|
|
5440
|
+
withAll.push(...skillItems);
|
|
5441
|
+
}
|
|
5442
|
+
if (agentItems.length > 0) {
|
|
5443
|
+
withAll.push({
|
|
5444
|
+
value: "__all_agents__",
|
|
5445
|
+
label: "[ALL] Select all Agents",
|
|
5446
|
+
kind: "agent",
|
|
5447
|
+
tab: "agent",
|
|
5448
|
+
isSelectAll: true,
|
|
5449
|
+
hint: `Select or deselect all ${agentItems.length} Agents in this tab`
|
|
5450
|
+
});
|
|
5451
|
+
withAll.push(...agentItems);
|
|
5452
|
+
}
|
|
5453
|
+
if (withAll.length > 0) {
|
|
5454
|
+
finalOptions = withAll;
|
|
5455
|
+
}
|
|
5456
|
+
}
|
|
5423
5457
|
const initial = /* @__PURE__ */ new Set();
|
|
5424
|
-
for (const opt of
|
|
5425
|
-
if (opt.initialSelected) {
|
|
5458
|
+
for (const opt of finalOptions) {
|
|
5459
|
+
if (opt.initialSelected && !opt.isSelectAll) {
|
|
5426
5460
|
initial.add(opt.value);
|
|
5427
5461
|
}
|
|
5428
5462
|
}
|
|
5429
|
-
const hasSkills =
|
|
5463
|
+
const hasSkills = finalOptions.some((opt) => optionMatchesTab(opt, "skill"));
|
|
5430
5464
|
return {
|
|
5431
|
-
options,
|
|
5465
|
+
options: finalOptions,
|
|
5432
5466
|
activeTab: hasSkills ? "skill" : "agent",
|
|
5433
5467
|
cursor: 0,
|
|
5434
5468
|
selected: initial,
|
|
@@ -5518,6 +5552,29 @@ function applyMultiSelectKey(state, key, options = {}) {
|
|
|
5518
5552
|
if (!currentOpt) {
|
|
5519
5553
|
return state;
|
|
5520
5554
|
}
|
|
5555
|
+
if (currentOpt.isSelectAll) {
|
|
5556
|
+
const realVisible = visible.filter((opt) => !opt.isSelectAll);
|
|
5557
|
+
if (realVisible.length === 0) {
|
|
5558
|
+
return state;
|
|
5559
|
+
}
|
|
5560
|
+
const allTabSelected = realVisible.every(
|
|
5561
|
+
(opt) => state.selected.has(opt.value)
|
|
5562
|
+
);
|
|
5563
|
+
const nextSelected2 = new Set(state.selected);
|
|
5564
|
+
if (allTabSelected) {
|
|
5565
|
+
for (const opt of realVisible) {
|
|
5566
|
+
nextSelected2.delete(opt.value);
|
|
5567
|
+
}
|
|
5568
|
+
} else {
|
|
5569
|
+
for (const opt of realVisible) {
|
|
5570
|
+
nextSelected2.add(opt.value);
|
|
5571
|
+
}
|
|
5572
|
+
}
|
|
5573
|
+
return {
|
|
5574
|
+
...state,
|
|
5575
|
+
selected: nextSelected2
|
|
5576
|
+
};
|
|
5577
|
+
}
|
|
5521
5578
|
const nextSelected = new Set(state.selected);
|
|
5522
5579
|
if (nextSelected.has(currentOpt.value)) {
|
|
5523
5580
|
nextSelected.delete(currentOpt.value);
|
|
@@ -5581,19 +5638,20 @@ function applyMultiSelectKey(state, key, options = {}) {
|
|
|
5581
5638
|
};
|
|
5582
5639
|
}
|
|
5583
5640
|
if (key === "a" || key === "A") {
|
|
5584
|
-
|
|
5641
|
+
const realVisible = visible.filter((opt) => !opt.isSelectAll);
|
|
5642
|
+
if (realVisible.length === 0) {
|
|
5585
5643
|
return state;
|
|
5586
5644
|
}
|
|
5587
|
-
const allTabSelected =
|
|
5645
|
+
const allTabSelected = realVisible.every(
|
|
5588
5646
|
(opt) => state.selected.has(opt.value)
|
|
5589
5647
|
);
|
|
5590
5648
|
const nextSelected = new Set(state.selected);
|
|
5591
5649
|
if (allTabSelected) {
|
|
5592
|
-
for (const opt of
|
|
5650
|
+
for (const opt of realVisible) {
|
|
5593
5651
|
nextSelected.delete(opt.value);
|
|
5594
5652
|
}
|
|
5595
5653
|
} else {
|
|
5596
|
-
for (const opt of
|
|
5654
|
+
for (const opt of realVisible) {
|
|
5597
5655
|
nextSelected.add(opt.value);
|
|
5598
5656
|
}
|
|
5599
5657
|
}
|
|
@@ -5608,15 +5666,19 @@ function renderMultiSelectFrame(title, state, options = {}) {
|
|
|
5608
5666
|
const c = options.colorEnabled;
|
|
5609
5667
|
const bar = style.dim("\u2502", c);
|
|
5610
5668
|
const maxVisible = options.maxVisible ?? 10;
|
|
5611
|
-
const
|
|
5669
|
+
const realOptions = state.options.filter((o) => !o.isSelectAll);
|
|
5670
|
+
const totalSkills = realOptions.filter(
|
|
5612
5671
|
(o) => optionMatchesTab(o, "skill")
|
|
5613
5672
|
).length;
|
|
5614
|
-
const totalAgents =
|
|
5673
|
+
const totalAgents = realOptions.filter(
|
|
5615
5674
|
(o) => optionMatchesTab(o, "agent")
|
|
5616
5675
|
).length;
|
|
5617
5676
|
const filteredSkills = getFilteredTabOptions(state, "skill");
|
|
5618
5677
|
const filteredAgents = getFilteredTabOptions(state, "agent");
|
|
5678
|
+
const realFilteredSkills = filteredSkills.filter((o) => !o.isSelectAll);
|
|
5679
|
+
const realFilteredAgents = filteredAgents.filter((o) => !o.isSelectAll);
|
|
5619
5680
|
const visible = state.activeTab === "skill" ? filteredSkills : filteredAgents;
|
|
5681
|
+
const realVisible = state.activeTab === "skill" ? realFilteredSkills : realFilteredAgents;
|
|
5620
5682
|
const total = visible.length;
|
|
5621
5683
|
const skillTabTitle = options.tabLabels?.skill ?? "Skills";
|
|
5622
5684
|
const agentTabTitle = options.tabLabels?.agent ?? "Agents";
|
|
@@ -5631,8 +5693,8 @@ function renderMultiSelectFrame(title, state, options = {}) {
|
|
|
5631
5693
|
}
|
|
5632
5694
|
lines.push(instructions, bar);
|
|
5633
5695
|
const hasQuery = state.searchQuery.length > 0;
|
|
5634
|
-
const skillCountStr = hasQuery ? `${
|
|
5635
|
-
const agentCountStr = hasQuery ? `${
|
|
5696
|
+
const skillCountStr = hasQuery ? `${realFilteredSkills.length}/${totalSkills}` : `${totalSkills}`;
|
|
5697
|
+
const agentCountStr = hasQuery ? `${realFilteredAgents.length}/${totalAgents}` : `${totalAgents}`;
|
|
5636
5698
|
const skillTabLabel = state.activeTab === "skill" ? style.bold(
|
|
5637
5699
|
style.cyan(`[ \u25C6 ${skillTabTitle} (${skillCountStr}) ]`, c),
|
|
5638
5700
|
c
|
|
@@ -5671,9 +5733,11 @@ function renderMultiSelectFrame(title, state, options = {}) {
|
|
|
5671
5733
|
const opt = visible[i];
|
|
5672
5734
|
if (!opt) continue;
|
|
5673
5735
|
const isCurrent = i === state.cursor;
|
|
5674
|
-
const
|
|
5736
|
+
const allRealSelected = realVisible.length > 0 && realVisible.every((o) => state.selected.has(o.value));
|
|
5737
|
+
const someRealSelected = realVisible.some((o) => state.selected.has(o.value)) && !allRealSelected;
|
|
5738
|
+
const isChecked = opt.isSelectAll ? allRealSelected : state.selected.has(opt.value);
|
|
5675
5739
|
const pointer = isCurrent ? style.cyan("\u276F", c) : " ";
|
|
5676
|
-
const checkbox = isChecked ? style.green("\u25C9", c) : style.dim("\u25EF", c);
|
|
5740
|
+
const checkbox = isChecked ? style.green("\u25C9", c) : opt.isSelectAll && someRealSelected ? style.cyan("\u25D0", c) : style.dim("\u25EF", c);
|
|
5677
5741
|
const labelRaw = opt.label.length > maxLabelCols ? `${opt.label.slice(0, maxLabelCols - 1)}\u2026` : opt.label;
|
|
5678
5742
|
const labelPadded = padVisible(labelRaw, maxLabelCols + 1, "left");
|
|
5679
5743
|
const styledLabel = isCurrent ? style.bold(labelPadded, c) : isChecked ? style.green(labelPadded, c) : labelPadded;
|
|
@@ -5691,10 +5755,10 @@ function renderMultiSelectFrame(title, state, options = {}) {
|
|
|
5691
5755
|
}
|
|
5692
5756
|
}
|
|
5693
5757
|
lines.push(bar);
|
|
5694
|
-
const selectedSkillsCount =
|
|
5758
|
+
const selectedSkillsCount = realOptions.filter(
|
|
5695
5759
|
(o) => optionMatchesTab(o, "skill") && state.selected.has(o.value)
|
|
5696
5760
|
).length;
|
|
5697
|
-
const selectedAgentsCount =
|
|
5761
|
+
const selectedAgentsCount = realOptions.filter(
|
|
5698
5762
|
(o) => optionMatchesTab(o, "agent") && state.selected.has(o.value)
|
|
5699
5763
|
).length;
|
|
5700
5764
|
const currentOptLabel = visible[state.cursor]?.label ?? "";
|
|
@@ -5711,7 +5775,9 @@ async function runMultiSelectPrompt(title, options, renderOpts = {}) {
|
|
|
5711
5775
|
if (!process.stdin.isTTY || !process.stdout.isTTY) {
|
|
5712
5776
|
return null;
|
|
5713
5777
|
}
|
|
5714
|
-
let state = createMultiSelectState(options
|
|
5778
|
+
let state = createMultiSelectState(options, {
|
|
5779
|
+
showSelectAll: renderOpts.showSelectAll
|
|
5780
|
+
});
|
|
5715
5781
|
let renderedLineCount = 0;
|
|
5716
5782
|
const render = () => {
|
|
5717
5783
|
const frame = renderMultiSelectFrame(title, state, renderOpts);
|
|
@@ -7478,7 +7544,8 @@ async function runCliInteractive(argv) {
|
|
|
7478
7544
|
const options = buildInteractiveCatalogOptions(catalogDir);
|
|
7479
7545
|
const step2Title = !explicitTargetsArg ? "SkillOps \u2014 Step 2/2: Select Skills & Agents to Import" : "SkillOps \u2014 Select Skills & Agents to Import";
|
|
7480
7546
|
const selected = await runMultiSelectPrompt(step2Title, options, {
|
|
7481
|
-
targetHint: targets.join(", ")
|
|
7547
|
+
targetHint: targets.join(", "),
|
|
7548
|
+
showSelectAll: true
|
|
7482
7549
|
});
|
|
7483
7550
|
if (!selected || selected.length === 0) {
|
|
7484
7551
|
process.stdout.write("No Skills or Agents selected.\n");
|
|
@@ -7529,7 +7596,8 @@ async function runCliInteractive(argv) {
|
|
|
7529
7596
|
installedOptions,
|
|
7530
7597
|
{
|
|
7531
7598
|
submitActionLabel: "remove",
|
|
7532
|
-
targetHint: targets ? targets.join(", ") : void 0
|
|
7599
|
+
targetHint: targets ? targets.join(", ") : void 0,
|
|
7600
|
+
showSelectAll: true
|
|
7533
7601
|
}
|
|
7534
7602
|
);
|
|
7535
7603
|
if (!selected || selected.length === 0) {
|
package/dist/index.d.ts
CHANGED
|
@@ -8,7 +8,7 @@ import { z } from 'zod';
|
|
|
8
8
|
* telemetry and Multi-Runtime Transpilation lockfiles.
|
|
9
9
|
*/
|
|
10
10
|
|
|
11
|
-
declare const SKILLOPS_VERSION = "1.3.
|
|
11
|
+
declare const SKILLOPS_VERSION = "1.3.7";
|
|
12
12
|
/**
|
|
13
13
|
* Count whitespace-delimited words in text.
|
|
14
14
|
*/
|
|
@@ -2190,6 +2190,10 @@ interface MultiSelectOption {
|
|
|
2190
2190
|
readonly tab?: MultiSelectTab;
|
|
2191
2191
|
readonly hint?: string;
|
|
2192
2192
|
readonly initialSelected?: boolean;
|
|
2193
|
+
readonly isSelectAll?: boolean;
|
|
2194
|
+
}
|
|
2195
|
+
interface CreateMultiSelectStateOptions {
|
|
2196
|
+
readonly showSelectAll?: boolean;
|
|
2193
2197
|
}
|
|
2194
2198
|
interface MultiSelectState {
|
|
2195
2199
|
readonly options: readonly MultiSelectOption[];
|
|
@@ -2212,6 +2216,7 @@ interface RenderMultiSelectOptions {
|
|
|
2212
2216
|
};
|
|
2213
2217
|
readonly submitActionLabel?: string;
|
|
2214
2218
|
readonly selectCursorOnEmptySubmit?: boolean;
|
|
2219
|
+
readonly showSelectAll?: boolean;
|
|
2215
2220
|
readonly maxVisible?: number;
|
|
2216
2221
|
readonly colorEnabled?: boolean;
|
|
2217
2222
|
}
|
|
@@ -2222,7 +2227,7 @@ declare function getFilteredTabOptions(state: MultiSelectState, tab?: MultiSelec
|
|
|
2222
2227
|
/**
|
|
2223
2228
|
* Initialize a deterministic multi-select state from a list of options.
|
|
2224
2229
|
*/
|
|
2225
|
-
declare function createMultiSelectState(options: readonly MultiSelectOption[]): MultiSelectState;
|
|
2230
|
+
declare function createMultiSelectState(options: readonly MultiSelectOption[], stateOptions?: CreateMultiSelectStateOptions): MultiSelectState;
|
|
2226
2231
|
/**
|
|
2227
2232
|
* Pure state reducer for keyboard input in the tabbed + searchable multi-select TUI.
|
|
2228
2233
|
*/
|
|
@@ -2356,4 +2361,4 @@ declare const DEFAULT_VALID_COMMANDS: readonly string[];
|
|
|
2356
2361
|
*/
|
|
2357
2362
|
declare function suggestCommand(unknownCommand: string, validCommands?: readonly string[]): string | null;
|
|
2358
2363
|
|
|
2359
|
-
export { ALL_RUNTIME_TARGETS, type AddOptions, type AnalyzeTokenEconomyOptions, type ApplyMultiSelectKeyOptions, type AuditCatalogOptions, type BadgeType, type BenchmarkArm, BenchmarkArmSchema, type BenchmarkDelta, BenchmarkDeltaSchema, type BoxOptions, COMMAND_HELP_SPECS, CORE_RUNTIME_TARGETS, type CatalogEvalSummary, CatalogEvalSummarySchema, type CatalogItemInfo, type CatalogSearchMatch, type CatalogSearchReport, type CatalogTokenBudgetSummary, type CatalogTrack, CatalogTrackSchema, type CleanOptions, type CollisionPair, CollisionPairSchema, type CollisionReport, CollisionReportSchema, type CollisionSeverity, CollisionSeveritySchema, type ColorOverrideOptions, type CommandHelpSpec, type CommandOptionSpec, DEFAULT_VALID_COMMANDS, type DiagnoseRepositoryOptions, type DoctorCheckItem, type DoctorReport, type EvalAssertion, EvalAssertionSchema, type EvalCase, EvalCaseSchema, ExitCode, type ExitCodeValue, type HarnessCategory, type HarnessInspectionEntry, type HarnessInspectionReport, type HarnessSkillFormat, type JsonRpcRequest, type JsonRpcResponse, type LoadedSkillOpsConfigResult, type LockfileArtifactDiagnostic, type McpConfigAction, type McpServerContext, type McpSetupOptions, type McpSetupReport, type MultiSelectOption, type MultiSelectState, type MultiSelectTab, type NextStepHint, type ParseSkillOptions, type ParsedSkillDirectory, type ParsedSubagentFile, type QuickstartOptions, type QuickstartReport, RUNTIME_HARNESS_SPECS, type RemoveOptions, type RenderMultiSelectOptions, RepoFingerprinter, type RepoProfile, RepoProfileSchema, type RouteOptions, type RoutedBundle, RoutedBundleSchema, type RoutingSignals, RoutingSignalsSchema, type RuntimeHarnessSpec, type RuntimeTarget, RuntimeTargetSchema, SKILLOPS_VERSION, type ScaffoldOptions, type ScaffoldResult, type ScoredSkill, ScoredSkillSchema, type ScriptEntrypoint, ScriptEntrypointSchema, type SkillBenchmark, SkillBenchmarkSchema, type SkillEntrypoints, SkillEntrypointsSchema, type SkillEvalSuite, SkillEvalSuiteSchema, type SkillManifest, type SkillManifestInput, SkillManifestSchema, type SkillOpsConfig, SkillOpsConfigSchema, type SkillOpsDetectedStackConfig, SkillOpsDetectedStackConfigSchema, type SkillOpsTokenEconomyConfig, SkillOpsTokenEconomyConfigSchema, type SkillTokenBudgetAudit, type SkippedSkill, SkippedSkillSchema, type SubagentManifest, SubagentManifestSchema, type SubagentTokenBudgetAudit, type SyncLockEntry, SyncLockEntrySchema, type SyncLockfile, SyncLockfileSchema, type SyncOptions, type SyncReport, SyncReportSchema, type SyncedArtifact, SyncedArtifactSchema, type TableOptions, type TokenBarOptions, type TokenEconomyReport, TokenEconomyReportSchema, type TokenFileCategory, TokenFileCategorySchema, type TokenFileEntry, TokenFileEntrySchema, type TokenWasteHotspot, TokenWasteHotspotSchema, addSkillOrSubagent, analyzeRepoTokenEconomy, applyMultiSelectKey, auditCatalog, auditCatalogTokenBudgets, auditSkillTokenBudget, auditSubagentTokenBudget, classifyCollisionSeverity, cleanSyncedArtifacts, compileSkillBundle, computeCollisionMatrix, computeFeatureCosine, computeIdfWeights, computeSha256, countWords, createCollisionPair, createCollisionReport, createMultiSelectState, createSkillManifest, createSubagentManifest, detectInstalledHarnesses, diagnoseRepository, discoverSkillDirectories, discoverSubagentFiles, estimateTokenCount, evaluateCatalog, evaluateSkillDirectory, extractSkillFeatures, findCommandHelpSpec, fingerprintRepository, formatBadge, formatCatalogItemInfo, formatCatalogSearchReport, formatDoctorReport, formatEvalSummary, formatHarnessInspectionReport, formatMcpSetupReport, formatQuickstartReport, formatRoutedBundle, formatScaffoldReport, formatSyncReport, formatTokenEconomyReport, getFilteredTabOptions, handleMcpJsonRpcRequest, inspectCatalogItem, inspectHarnesses, isColorEnabled, levenshteinDistance, loadSkillOpsConfig, normalizePackageName, padVisible, parseSkillDirectory, parseSkillMdFile, parseSubagentFile, parseSubagentMdFile, removeSkillOrSubagent, renderAiUsageGuide, renderBox, renderCodexAgentsIndex, renderCommandHelp, renderGlobalHelp, renderHeaderBanner, renderMultiSelectFrame, renderNextSteps, renderProgressBar, renderSectionHeader, renderStep, renderTable, renderTokenBar, resolveRuntimeTargets, routeRepository, runMultiSelectPrompt, runQuickstart, scaffoldFrameworkItem, scoreSkillAgainstProfile, searchCatalog, setupMcpForHarnesses, splitFrontmatter, startMcpStdioServer, stripAnsi, stripCodexAgentsBlock, stripNegativeTriggerClauses, style, suggestCommand, syncRepository, tokenizeRoutingText, visibleLength };
|
|
2364
|
+
export { ALL_RUNTIME_TARGETS, type AddOptions, type AnalyzeTokenEconomyOptions, type ApplyMultiSelectKeyOptions, type AuditCatalogOptions, type BadgeType, type BenchmarkArm, BenchmarkArmSchema, type BenchmarkDelta, BenchmarkDeltaSchema, type BoxOptions, COMMAND_HELP_SPECS, CORE_RUNTIME_TARGETS, type CatalogEvalSummary, CatalogEvalSummarySchema, type CatalogItemInfo, type CatalogSearchMatch, type CatalogSearchReport, type CatalogTokenBudgetSummary, type CatalogTrack, CatalogTrackSchema, type CleanOptions, type CollisionPair, CollisionPairSchema, type CollisionReport, CollisionReportSchema, type CollisionSeverity, CollisionSeveritySchema, type ColorOverrideOptions, type CommandHelpSpec, type CommandOptionSpec, type CreateMultiSelectStateOptions, DEFAULT_VALID_COMMANDS, type DiagnoseRepositoryOptions, type DoctorCheckItem, type DoctorReport, type EvalAssertion, EvalAssertionSchema, type EvalCase, EvalCaseSchema, ExitCode, type ExitCodeValue, type HarnessCategory, type HarnessInspectionEntry, type HarnessInspectionReport, type HarnessSkillFormat, type JsonRpcRequest, type JsonRpcResponse, type LoadedSkillOpsConfigResult, type LockfileArtifactDiagnostic, type McpConfigAction, type McpServerContext, type McpSetupOptions, type McpSetupReport, type MultiSelectOption, type MultiSelectState, type MultiSelectTab, type NextStepHint, type ParseSkillOptions, type ParsedSkillDirectory, type ParsedSubagentFile, type QuickstartOptions, type QuickstartReport, RUNTIME_HARNESS_SPECS, type RemoveOptions, type RenderMultiSelectOptions, RepoFingerprinter, type RepoProfile, RepoProfileSchema, type RouteOptions, type RoutedBundle, RoutedBundleSchema, type RoutingSignals, RoutingSignalsSchema, type RuntimeHarnessSpec, type RuntimeTarget, RuntimeTargetSchema, SKILLOPS_VERSION, type ScaffoldOptions, type ScaffoldResult, type ScoredSkill, ScoredSkillSchema, type ScriptEntrypoint, ScriptEntrypointSchema, type SkillBenchmark, SkillBenchmarkSchema, type SkillEntrypoints, SkillEntrypointsSchema, type SkillEvalSuite, SkillEvalSuiteSchema, type SkillManifest, type SkillManifestInput, SkillManifestSchema, type SkillOpsConfig, SkillOpsConfigSchema, type SkillOpsDetectedStackConfig, SkillOpsDetectedStackConfigSchema, type SkillOpsTokenEconomyConfig, SkillOpsTokenEconomyConfigSchema, type SkillTokenBudgetAudit, type SkippedSkill, SkippedSkillSchema, type SubagentManifest, SubagentManifestSchema, type SubagentTokenBudgetAudit, type SyncLockEntry, SyncLockEntrySchema, type SyncLockfile, SyncLockfileSchema, type SyncOptions, type SyncReport, SyncReportSchema, type SyncedArtifact, SyncedArtifactSchema, type TableOptions, type TokenBarOptions, type TokenEconomyReport, TokenEconomyReportSchema, type TokenFileCategory, TokenFileCategorySchema, type TokenFileEntry, TokenFileEntrySchema, type TokenWasteHotspot, TokenWasteHotspotSchema, addSkillOrSubagent, analyzeRepoTokenEconomy, applyMultiSelectKey, auditCatalog, auditCatalogTokenBudgets, auditSkillTokenBudget, auditSubagentTokenBudget, classifyCollisionSeverity, cleanSyncedArtifacts, compileSkillBundle, computeCollisionMatrix, computeFeatureCosine, computeIdfWeights, computeSha256, countWords, createCollisionPair, createCollisionReport, createMultiSelectState, createSkillManifest, createSubagentManifest, detectInstalledHarnesses, diagnoseRepository, discoverSkillDirectories, discoverSubagentFiles, estimateTokenCount, evaluateCatalog, evaluateSkillDirectory, extractSkillFeatures, findCommandHelpSpec, fingerprintRepository, formatBadge, formatCatalogItemInfo, formatCatalogSearchReport, formatDoctorReport, formatEvalSummary, formatHarnessInspectionReport, formatMcpSetupReport, formatQuickstartReport, formatRoutedBundle, formatScaffoldReport, formatSyncReport, formatTokenEconomyReport, getFilteredTabOptions, handleMcpJsonRpcRequest, inspectCatalogItem, inspectHarnesses, isColorEnabled, levenshteinDistance, loadSkillOpsConfig, normalizePackageName, padVisible, parseSkillDirectory, parseSkillMdFile, parseSubagentFile, parseSubagentMdFile, removeSkillOrSubagent, renderAiUsageGuide, renderBox, renderCodexAgentsIndex, renderCommandHelp, renderGlobalHelp, renderHeaderBanner, renderMultiSelectFrame, renderNextSteps, renderProgressBar, renderSectionHeader, renderStep, renderTable, renderTokenBar, resolveRuntimeTargets, routeRepository, runMultiSelectPrompt, runQuickstart, scaffoldFrameworkItem, scoreSkillAgainstProfile, searchCatalog, setupMcpForHarnesses, splitFrontmatter, startMcpStdioServer, stripAnsi, stripCodexAgentsBlock, stripNegativeTriggerClauses, style, suggestCommand, syncRepository, tokenizeRoutingText, visibleLength };
|
package/dist/index.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
import fs from "fs";
|
|
3
3
|
import YAML from "yaml";
|
|
4
4
|
import { z } from "zod";
|
|
5
|
-
var SKILLOPS_VERSION = "1.3.
|
|
5
|
+
var SKILLOPS_VERSION = "1.3.7";
|
|
6
6
|
var SKILL_NAME_REGEX = /^[a-z0-9]+(?:-[a-z0-9]+)*$/;
|
|
7
7
|
var SEMVER_REGEX = /^\d+\.\d+\.\d+$/;
|
|
8
8
|
var FRONTMATTER_REGEX = /^---\r?\n([\s\S]*?)\r?\n---\r?\n?([\s\S]*)$/;
|
|
@@ -5430,6 +5430,9 @@ function optionMatchesQuery(opt, rawQuery) {
|
|
|
5430
5430
|
if (!q) {
|
|
5431
5431
|
return true;
|
|
5432
5432
|
}
|
|
5433
|
+
if (opt.isSelectAll) {
|
|
5434
|
+
return false;
|
|
5435
|
+
}
|
|
5433
5436
|
return opt.label.toLowerCase().includes(q) || opt.value.toLowerCase().includes(q) || (opt.hint ?? "").toLowerCase().includes(q);
|
|
5434
5437
|
}
|
|
5435
5438
|
function getFilteredTabOptions(state, tab = state.activeTab) {
|
|
@@ -5437,16 +5440,47 @@ function getFilteredTabOptions(state, tab = state.activeTab) {
|
|
|
5437
5440
|
(opt) => optionMatchesTab(opt, tab) && optionMatchesQuery(opt, state.searchQuery)
|
|
5438
5441
|
);
|
|
5439
5442
|
}
|
|
5440
|
-
function createMultiSelectState(options) {
|
|
5443
|
+
function createMultiSelectState(options, stateOptions = {}) {
|
|
5444
|
+
let finalOptions = options;
|
|
5445
|
+
if (stateOptions.showSelectAll && !options.some((opt) => opt.isSelectAll === true)) {
|
|
5446
|
+
const skillItems = options.filter((opt) => optionMatchesTab(opt, "skill"));
|
|
5447
|
+
const agentItems = options.filter((opt) => optionMatchesTab(opt, "agent"));
|
|
5448
|
+
const withAll = [];
|
|
5449
|
+
if (skillItems.length > 0) {
|
|
5450
|
+
withAll.push({
|
|
5451
|
+
value: "__all_skills__",
|
|
5452
|
+
label: "[ALL] Select all Skills",
|
|
5453
|
+
kind: "skill",
|
|
5454
|
+
tab: "skill",
|
|
5455
|
+
isSelectAll: true,
|
|
5456
|
+
hint: `Select or deselect all ${skillItems.length} Skills in this tab`
|
|
5457
|
+
});
|
|
5458
|
+
withAll.push(...skillItems);
|
|
5459
|
+
}
|
|
5460
|
+
if (agentItems.length > 0) {
|
|
5461
|
+
withAll.push({
|
|
5462
|
+
value: "__all_agents__",
|
|
5463
|
+
label: "[ALL] Select all Agents",
|
|
5464
|
+
kind: "agent",
|
|
5465
|
+
tab: "agent",
|
|
5466
|
+
isSelectAll: true,
|
|
5467
|
+
hint: `Select or deselect all ${agentItems.length} Agents in this tab`
|
|
5468
|
+
});
|
|
5469
|
+
withAll.push(...agentItems);
|
|
5470
|
+
}
|
|
5471
|
+
if (withAll.length > 0) {
|
|
5472
|
+
finalOptions = withAll;
|
|
5473
|
+
}
|
|
5474
|
+
}
|
|
5441
5475
|
const initial = /* @__PURE__ */ new Set();
|
|
5442
|
-
for (const opt of
|
|
5443
|
-
if (opt.initialSelected) {
|
|
5476
|
+
for (const opt of finalOptions) {
|
|
5477
|
+
if (opt.initialSelected && !opt.isSelectAll) {
|
|
5444
5478
|
initial.add(opt.value);
|
|
5445
5479
|
}
|
|
5446
5480
|
}
|
|
5447
|
-
const hasSkills =
|
|
5481
|
+
const hasSkills = finalOptions.some((opt) => optionMatchesTab(opt, "skill"));
|
|
5448
5482
|
return {
|
|
5449
|
-
options,
|
|
5483
|
+
options: finalOptions,
|
|
5450
5484
|
activeTab: hasSkills ? "skill" : "agent",
|
|
5451
5485
|
cursor: 0,
|
|
5452
5486
|
selected: initial,
|
|
@@ -5536,6 +5570,29 @@ function applyMultiSelectKey(state, key, options = {}) {
|
|
|
5536
5570
|
if (!currentOpt) {
|
|
5537
5571
|
return state;
|
|
5538
5572
|
}
|
|
5573
|
+
if (currentOpt.isSelectAll) {
|
|
5574
|
+
const realVisible = visible.filter((opt) => !opt.isSelectAll);
|
|
5575
|
+
if (realVisible.length === 0) {
|
|
5576
|
+
return state;
|
|
5577
|
+
}
|
|
5578
|
+
const allTabSelected = realVisible.every(
|
|
5579
|
+
(opt) => state.selected.has(opt.value)
|
|
5580
|
+
);
|
|
5581
|
+
const nextSelected2 = new Set(state.selected);
|
|
5582
|
+
if (allTabSelected) {
|
|
5583
|
+
for (const opt of realVisible) {
|
|
5584
|
+
nextSelected2.delete(opt.value);
|
|
5585
|
+
}
|
|
5586
|
+
} else {
|
|
5587
|
+
for (const opt of realVisible) {
|
|
5588
|
+
nextSelected2.add(opt.value);
|
|
5589
|
+
}
|
|
5590
|
+
}
|
|
5591
|
+
return {
|
|
5592
|
+
...state,
|
|
5593
|
+
selected: nextSelected2
|
|
5594
|
+
};
|
|
5595
|
+
}
|
|
5539
5596
|
const nextSelected = new Set(state.selected);
|
|
5540
5597
|
if (nextSelected.has(currentOpt.value)) {
|
|
5541
5598
|
nextSelected.delete(currentOpt.value);
|
|
@@ -5599,19 +5656,20 @@ function applyMultiSelectKey(state, key, options = {}) {
|
|
|
5599
5656
|
};
|
|
5600
5657
|
}
|
|
5601
5658
|
if (key === "a" || key === "A") {
|
|
5602
|
-
|
|
5659
|
+
const realVisible = visible.filter((opt) => !opt.isSelectAll);
|
|
5660
|
+
if (realVisible.length === 0) {
|
|
5603
5661
|
return state;
|
|
5604
5662
|
}
|
|
5605
|
-
const allTabSelected =
|
|
5663
|
+
const allTabSelected = realVisible.every(
|
|
5606
5664
|
(opt) => state.selected.has(opt.value)
|
|
5607
5665
|
);
|
|
5608
5666
|
const nextSelected = new Set(state.selected);
|
|
5609
5667
|
if (allTabSelected) {
|
|
5610
|
-
for (const opt of
|
|
5668
|
+
for (const opt of realVisible) {
|
|
5611
5669
|
nextSelected.delete(opt.value);
|
|
5612
5670
|
}
|
|
5613
5671
|
} else {
|
|
5614
|
-
for (const opt of
|
|
5672
|
+
for (const opt of realVisible) {
|
|
5615
5673
|
nextSelected.add(opt.value);
|
|
5616
5674
|
}
|
|
5617
5675
|
}
|
|
@@ -5626,15 +5684,19 @@ function renderMultiSelectFrame(title, state, options = {}) {
|
|
|
5626
5684
|
const c = options.colorEnabled;
|
|
5627
5685
|
const bar = style.dim("\u2502", c);
|
|
5628
5686
|
const maxVisible = options.maxVisible ?? 10;
|
|
5629
|
-
const
|
|
5687
|
+
const realOptions = state.options.filter((o) => !o.isSelectAll);
|
|
5688
|
+
const totalSkills = realOptions.filter(
|
|
5630
5689
|
(o) => optionMatchesTab(o, "skill")
|
|
5631
5690
|
).length;
|
|
5632
|
-
const totalAgents =
|
|
5691
|
+
const totalAgents = realOptions.filter(
|
|
5633
5692
|
(o) => optionMatchesTab(o, "agent")
|
|
5634
5693
|
).length;
|
|
5635
5694
|
const filteredSkills = getFilteredTabOptions(state, "skill");
|
|
5636
5695
|
const filteredAgents = getFilteredTabOptions(state, "agent");
|
|
5696
|
+
const realFilteredSkills = filteredSkills.filter((o) => !o.isSelectAll);
|
|
5697
|
+
const realFilteredAgents = filteredAgents.filter((o) => !o.isSelectAll);
|
|
5637
5698
|
const visible = state.activeTab === "skill" ? filteredSkills : filteredAgents;
|
|
5699
|
+
const realVisible = state.activeTab === "skill" ? realFilteredSkills : realFilteredAgents;
|
|
5638
5700
|
const total = visible.length;
|
|
5639
5701
|
const skillTabTitle = options.tabLabels?.skill ?? "Skills";
|
|
5640
5702
|
const agentTabTitle = options.tabLabels?.agent ?? "Agents";
|
|
@@ -5649,8 +5711,8 @@ function renderMultiSelectFrame(title, state, options = {}) {
|
|
|
5649
5711
|
}
|
|
5650
5712
|
lines.push(instructions, bar);
|
|
5651
5713
|
const hasQuery = state.searchQuery.length > 0;
|
|
5652
|
-
const skillCountStr = hasQuery ? `${
|
|
5653
|
-
const agentCountStr = hasQuery ? `${
|
|
5714
|
+
const skillCountStr = hasQuery ? `${realFilteredSkills.length}/${totalSkills}` : `${totalSkills}`;
|
|
5715
|
+
const agentCountStr = hasQuery ? `${realFilteredAgents.length}/${totalAgents}` : `${totalAgents}`;
|
|
5654
5716
|
const skillTabLabel = state.activeTab === "skill" ? style.bold(
|
|
5655
5717
|
style.cyan(`[ \u25C6 ${skillTabTitle} (${skillCountStr}) ]`, c),
|
|
5656
5718
|
c
|
|
@@ -5689,9 +5751,11 @@ function renderMultiSelectFrame(title, state, options = {}) {
|
|
|
5689
5751
|
const opt = visible[i];
|
|
5690
5752
|
if (!opt) continue;
|
|
5691
5753
|
const isCurrent = i === state.cursor;
|
|
5692
|
-
const
|
|
5754
|
+
const allRealSelected = realVisible.length > 0 && realVisible.every((o) => state.selected.has(o.value));
|
|
5755
|
+
const someRealSelected = realVisible.some((o) => state.selected.has(o.value)) && !allRealSelected;
|
|
5756
|
+
const isChecked = opt.isSelectAll ? allRealSelected : state.selected.has(opt.value);
|
|
5693
5757
|
const pointer = isCurrent ? style.cyan("\u276F", c) : " ";
|
|
5694
|
-
const checkbox = isChecked ? style.green("\u25C9", c) : style.dim("\u25EF", c);
|
|
5758
|
+
const checkbox = isChecked ? style.green("\u25C9", c) : opt.isSelectAll && someRealSelected ? style.cyan("\u25D0", c) : style.dim("\u25EF", c);
|
|
5695
5759
|
const labelRaw = opt.label.length > maxLabelCols ? `${opt.label.slice(0, maxLabelCols - 1)}\u2026` : opt.label;
|
|
5696
5760
|
const labelPadded = padVisible(labelRaw, maxLabelCols + 1, "left");
|
|
5697
5761
|
const styledLabel = isCurrent ? style.bold(labelPadded, c) : isChecked ? style.green(labelPadded, c) : labelPadded;
|
|
@@ -5709,10 +5773,10 @@ function renderMultiSelectFrame(title, state, options = {}) {
|
|
|
5709
5773
|
}
|
|
5710
5774
|
}
|
|
5711
5775
|
lines.push(bar);
|
|
5712
|
-
const selectedSkillsCount =
|
|
5776
|
+
const selectedSkillsCount = realOptions.filter(
|
|
5713
5777
|
(o) => optionMatchesTab(o, "skill") && state.selected.has(o.value)
|
|
5714
5778
|
).length;
|
|
5715
|
-
const selectedAgentsCount =
|
|
5779
|
+
const selectedAgentsCount = realOptions.filter(
|
|
5716
5780
|
(o) => optionMatchesTab(o, "agent") && state.selected.has(o.value)
|
|
5717
5781
|
).length;
|
|
5718
5782
|
const currentOptLabel = visible[state.cursor]?.label ?? "";
|
|
@@ -5729,7 +5793,9 @@ async function runMultiSelectPrompt(title, options, renderOpts = {}) {
|
|
|
5729
5793
|
if (!process.stdin.isTTY || !process.stdout.isTTY) {
|
|
5730
5794
|
return null;
|
|
5731
5795
|
}
|
|
5732
|
-
let state = createMultiSelectState(options
|
|
5796
|
+
let state = createMultiSelectState(options, {
|
|
5797
|
+
showSelectAll: renderOpts.showSelectAll
|
|
5798
|
+
});
|
|
5733
5799
|
let renderedLineCount = 0;
|
|
5734
5800
|
const render = () => {
|
|
5735
5801
|
const frame = renderMultiSelectFrame(title, state, renderOpts);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "skillops-cli",
|
|
3
|
-
"version": "1.3.
|
|
3
|
+
"version": "1.3.7",
|
|
4
4
|
"description": "SkillOps — The Zero-API Framework & Benchmark-Verified Library for High-End AI Coding Skills & Context-Isolated Subagents with Universal Top-28 AI Agent Transpilation & Token Economy Auditing.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|