@rely-ai/caliber 0.5.1 → 0.5.3
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/bin.js +169 -64
- package/package.json +1 -1
package/dist/bin.js
CHANGED
|
@@ -3555,10 +3555,10 @@ function checkBonus(dir) {
|
|
|
3555
3555
|
if (settingsContent) {
|
|
3556
3556
|
try {
|
|
3557
3557
|
const settings = JSON.parse(settingsContent);
|
|
3558
|
-
const
|
|
3559
|
-
if (
|
|
3558
|
+
const hooks = settings.hooks;
|
|
3559
|
+
if (hooks && Object.keys(hooks).length > 0) {
|
|
3560
3560
|
hasClaudeHooks = true;
|
|
3561
|
-
hookSources.push(`Claude Code: ${Object.keys(
|
|
3561
|
+
hookSources.push(`Claude Code: ${Object.keys(hooks).join(", ")}`);
|
|
3562
3562
|
}
|
|
3563
3563
|
} catch {
|
|
3564
3564
|
}
|
|
@@ -4935,9 +4935,24 @@ async function recommendCommand(options) {
|
|
|
4935
4935
|
} else {
|
|
4936
4936
|
results = newCandidates.slice(0, 20);
|
|
4937
4937
|
}
|
|
4938
|
-
const
|
|
4938
|
+
const fetchSpinner = ora4("Verifying skill availability...").start();
|
|
4939
|
+
const contentMap = /* @__PURE__ */ new Map();
|
|
4940
|
+
await Promise.all(results.map(async (rec) => {
|
|
4941
|
+
const content = await fetchSkillContent(rec);
|
|
4942
|
+
if (content) contentMap.set(rec.slug, content);
|
|
4943
|
+
}));
|
|
4944
|
+
const available = results.filter((r) => contentMap.has(r.slug));
|
|
4945
|
+
if (!available.length) {
|
|
4946
|
+
fetchSpinner.fail("No installable skills found \u2014 content could not be fetched.");
|
|
4947
|
+
return;
|
|
4948
|
+
}
|
|
4949
|
+
const unavailableCount = results.length - available.length;
|
|
4950
|
+
fetchSpinner.succeed(
|
|
4951
|
+
`${available.length} installable skill${available.length > 1 ? "s" : ""}` + (unavailableCount > 0 ? chalk8.dim(` (${unavailableCount} unavailable)`) : "")
|
|
4952
|
+
);
|
|
4953
|
+
const selected = await interactiveSelect(available);
|
|
4939
4954
|
if (selected?.length) {
|
|
4940
|
-
await installSkills(selected, platforms);
|
|
4955
|
+
await installSkills(selected, platforms, contentMap);
|
|
4941
4956
|
}
|
|
4942
4957
|
}
|
|
4943
4958
|
async function interactiveSelect(recs) {
|
|
@@ -5076,16 +5091,12 @@ async function fetchSkillContent(rec) {
|
|
|
5076
5091
|
}
|
|
5077
5092
|
return null;
|
|
5078
5093
|
}
|
|
5079
|
-
async function installSkills(recs, platforms) {
|
|
5094
|
+
async function installSkills(recs, platforms, contentMap) {
|
|
5080
5095
|
const spinner = ora4(`Installing ${recs.length} skill${recs.length > 1 ? "s" : ""}...`).start();
|
|
5081
5096
|
const installed = [];
|
|
5082
|
-
const warnings = [];
|
|
5083
5097
|
for (const rec of recs) {
|
|
5084
|
-
const content =
|
|
5085
|
-
if (!content)
|
|
5086
|
-
warnings.push(`No content available for ${rec.name}`);
|
|
5087
|
-
continue;
|
|
5088
|
-
}
|
|
5098
|
+
const content = contentMap.get(rec.slug);
|
|
5099
|
+
if (!content) continue;
|
|
5089
5100
|
for (const platform of platforms) {
|
|
5090
5101
|
const skillPath = getSkillPath(platform, rec.slug);
|
|
5091
5102
|
const fullPath = join8(process.cwd(), skillPath);
|
|
@@ -5102,9 +5113,6 @@ async function installSkills(recs, platforms) {
|
|
|
5102
5113
|
} else {
|
|
5103
5114
|
spinner.fail("No skills were installed");
|
|
5104
5115
|
}
|
|
5105
|
-
for (const w of warnings) {
|
|
5106
|
-
console.log(chalk8.yellow(` \u26A0 ${w}`));
|
|
5107
|
-
}
|
|
5108
5116
|
console.log("");
|
|
5109
5117
|
}
|
|
5110
5118
|
function printRecommendations(recs) {
|
|
@@ -5457,60 +5465,162 @@ async function refreshCommand(options) {
|
|
|
5457
5465
|
|
|
5458
5466
|
// src/commands/hooks.ts
|
|
5459
5467
|
import chalk11 from "chalk";
|
|
5460
|
-
|
|
5461
|
-
|
|
5462
|
-
|
|
5463
|
-
|
|
5464
|
-
|
|
5468
|
+
var HOOKS = [
|
|
5469
|
+
{
|
|
5470
|
+
id: "session-end",
|
|
5471
|
+
label: "Claude Code SessionEnd",
|
|
5472
|
+
description: "Auto-refresh CLAUDE.md when a Claude Code session ends",
|
|
5473
|
+
isInstalled: isHookInstalled,
|
|
5474
|
+
install: installHook,
|
|
5475
|
+
remove: removeHook
|
|
5476
|
+
},
|
|
5477
|
+
{
|
|
5478
|
+
id: "pre-commit",
|
|
5479
|
+
label: "Git pre-commit",
|
|
5480
|
+
description: "Auto-refresh CLAUDE.md before each git commit",
|
|
5481
|
+
isInstalled: isPreCommitHookInstalled,
|
|
5482
|
+
install: installPreCommitHook,
|
|
5483
|
+
remove: removePreCommitHook
|
|
5465
5484
|
}
|
|
5466
|
-
|
|
5467
|
-
|
|
5468
|
-
|
|
5469
|
-
|
|
5470
|
-
|
|
5471
|
-
|
|
5472
|
-
|
|
5473
|
-
|
|
5485
|
+
];
|
|
5486
|
+
function printStatus() {
|
|
5487
|
+
console.log(chalk11.bold("\n Hooks\n"));
|
|
5488
|
+
for (const hook of HOOKS) {
|
|
5489
|
+
const installed = hook.isInstalled();
|
|
5490
|
+
const icon = installed ? chalk11.green("\u2713") : chalk11.dim("\u2717");
|
|
5491
|
+
const state = installed ? chalk11.green("enabled") : chalk11.dim("disabled");
|
|
5492
|
+
console.log(` ${icon} ${hook.label.padEnd(26)} ${state}`);
|
|
5493
|
+
console.log(chalk11.dim(` ${hook.description}`));
|
|
5474
5494
|
}
|
|
5475
|
-
console.log(
|
|
5495
|
+
console.log("");
|
|
5476
5496
|
}
|
|
5477
|
-
async function
|
|
5478
|
-
|
|
5479
|
-
|
|
5480
|
-
|
|
5497
|
+
async function hooksCommand(options) {
|
|
5498
|
+
if (options.install) {
|
|
5499
|
+
for (const hook of HOOKS) {
|
|
5500
|
+
const result = hook.install();
|
|
5501
|
+
if (result.alreadyInstalled) {
|
|
5502
|
+
console.log(chalk11.dim(` ${hook.label} already enabled.`));
|
|
5503
|
+
} else {
|
|
5504
|
+
console.log(chalk11.green(" \u2713") + ` ${hook.label} enabled`);
|
|
5505
|
+
}
|
|
5506
|
+
}
|
|
5481
5507
|
return;
|
|
5482
5508
|
}
|
|
5483
|
-
if (
|
|
5484
|
-
|
|
5509
|
+
if (options.remove) {
|
|
5510
|
+
for (const hook of HOOKS) {
|
|
5511
|
+
const result = hook.remove();
|
|
5512
|
+
if (result.notFound) {
|
|
5513
|
+
console.log(chalk11.dim(` ${hook.label} already disabled.`));
|
|
5514
|
+
} else {
|
|
5515
|
+
console.log(chalk11.green(" \u2713") + ` ${hook.label} removed`);
|
|
5516
|
+
}
|
|
5517
|
+
}
|
|
5485
5518
|
return;
|
|
5486
5519
|
}
|
|
5487
|
-
|
|
5488
|
-
|
|
5489
|
-
}
|
|
5490
|
-
async function hooksRemovePrecommitCommand() {
|
|
5491
|
-
const result = removePreCommitHook();
|
|
5492
|
-
if (result.notFound) {
|
|
5493
|
-
console.log(chalk11.dim("Pre-commit hook not found."));
|
|
5520
|
+
if (!process.stdin.isTTY) {
|
|
5521
|
+
printStatus();
|
|
5494
5522
|
return;
|
|
5495
5523
|
}
|
|
5496
|
-
|
|
5497
|
-
|
|
5498
|
-
|
|
5499
|
-
const
|
|
5500
|
-
|
|
5501
|
-
|
|
5502
|
-
|
|
5503
|
-
|
|
5504
|
-
|
|
5505
|
-
|
|
5506
|
-
|
|
5507
|
-
|
|
5508
|
-
|
|
5509
|
-
|
|
5524
|
+
const { stdin, stdout } = process;
|
|
5525
|
+
let cursor = 0;
|
|
5526
|
+
let lineCount = 0;
|
|
5527
|
+
const states = HOOKS.map((h) => h.isInstalled());
|
|
5528
|
+
function render() {
|
|
5529
|
+
const lines = [];
|
|
5530
|
+
lines.push(chalk11.bold(" Hooks"));
|
|
5531
|
+
lines.push("");
|
|
5532
|
+
for (let i = 0; i < HOOKS.length; i++) {
|
|
5533
|
+
const hook = HOOKS[i];
|
|
5534
|
+
const enabled = states[i];
|
|
5535
|
+
const toggle = enabled ? chalk11.green("[on] ") : chalk11.dim("[off]");
|
|
5536
|
+
const ptr = i === cursor ? chalk11.cyan(">") : " ";
|
|
5537
|
+
lines.push(` ${ptr} ${toggle} ${hook.label}`);
|
|
5538
|
+
lines.push(chalk11.dim(` ${hook.description}`));
|
|
5539
|
+
}
|
|
5540
|
+
lines.push("");
|
|
5541
|
+
lines.push(chalk11.dim(" \u2191\u2193 navigate \u23B5 toggle a all on n all off \u23CE apply q cancel"));
|
|
5542
|
+
return lines.join("\n");
|
|
5510
5543
|
}
|
|
5511
|
-
|
|
5512
|
-
|
|
5544
|
+
function draw(initial) {
|
|
5545
|
+
if (!initial && lineCount > 0) {
|
|
5546
|
+
stdout.write(`\x1B[${lineCount}A`);
|
|
5547
|
+
}
|
|
5548
|
+
stdout.write("\x1B[0J");
|
|
5549
|
+
const output = render();
|
|
5550
|
+
stdout.write(output + "\n");
|
|
5551
|
+
lineCount = output.split("\n").length;
|
|
5513
5552
|
}
|
|
5553
|
+
return new Promise((resolve2) => {
|
|
5554
|
+
console.log("");
|
|
5555
|
+
draw(true);
|
|
5556
|
+
stdin.setRawMode(true);
|
|
5557
|
+
stdin.resume();
|
|
5558
|
+
stdin.setEncoding("utf8");
|
|
5559
|
+
function cleanup() {
|
|
5560
|
+
stdin.removeListener("data", onData);
|
|
5561
|
+
stdin.setRawMode(false);
|
|
5562
|
+
stdin.pause();
|
|
5563
|
+
}
|
|
5564
|
+
function apply() {
|
|
5565
|
+
let changed = 0;
|
|
5566
|
+
for (let i = 0; i < HOOKS.length; i++) {
|
|
5567
|
+
const hook = HOOKS[i];
|
|
5568
|
+
const wasInstalled = hook.isInstalled();
|
|
5569
|
+
const wantEnabled = states[i];
|
|
5570
|
+
if (wantEnabled && !wasInstalled) {
|
|
5571
|
+
hook.install();
|
|
5572
|
+
console.log(chalk11.green(" \u2713") + ` ${hook.label} enabled`);
|
|
5573
|
+
changed++;
|
|
5574
|
+
} else if (!wantEnabled && wasInstalled) {
|
|
5575
|
+
hook.remove();
|
|
5576
|
+
console.log(chalk11.green(" \u2713") + ` ${hook.label} disabled`);
|
|
5577
|
+
changed++;
|
|
5578
|
+
}
|
|
5579
|
+
}
|
|
5580
|
+
if (changed === 0) {
|
|
5581
|
+
console.log(chalk11.dim(" No changes."));
|
|
5582
|
+
}
|
|
5583
|
+
console.log("");
|
|
5584
|
+
}
|
|
5585
|
+
function onData(key) {
|
|
5586
|
+
switch (key) {
|
|
5587
|
+
case "\x1B[A":
|
|
5588
|
+
cursor = (cursor - 1 + HOOKS.length) % HOOKS.length;
|
|
5589
|
+
draw(false);
|
|
5590
|
+
break;
|
|
5591
|
+
case "\x1B[B":
|
|
5592
|
+
cursor = (cursor + 1) % HOOKS.length;
|
|
5593
|
+
draw(false);
|
|
5594
|
+
break;
|
|
5595
|
+
case " ":
|
|
5596
|
+
states[cursor] = !states[cursor];
|
|
5597
|
+
draw(false);
|
|
5598
|
+
break;
|
|
5599
|
+
case "a":
|
|
5600
|
+
states.fill(true);
|
|
5601
|
+
draw(false);
|
|
5602
|
+
break;
|
|
5603
|
+
case "n":
|
|
5604
|
+
states.fill(false);
|
|
5605
|
+
draw(false);
|
|
5606
|
+
break;
|
|
5607
|
+
case "\r":
|
|
5608
|
+
case "\n":
|
|
5609
|
+
cleanup();
|
|
5610
|
+
apply();
|
|
5611
|
+
resolve2();
|
|
5612
|
+
break;
|
|
5613
|
+
case "q":
|
|
5614
|
+
case "\x1B":
|
|
5615
|
+
case "":
|
|
5616
|
+
cleanup();
|
|
5617
|
+
console.log(chalk11.dim("\n Cancelled.\n"));
|
|
5618
|
+
resolve2();
|
|
5619
|
+
break;
|
|
5620
|
+
}
|
|
5621
|
+
}
|
|
5622
|
+
stdin.on("data", onData);
|
|
5623
|
+
});
|
|
5514
5624
|
}
|
|
5515
5625
|
|
|
5516
5626
|
// src/commands/config.ts
|
|
@@ -5910,12 +6020,7 @@ program.command("config").description("Configure LLM provider, API key, and mode
|
|
|
5910
6020
|
program.command("recommend").description("Discover and install skill recommendations").option("--generate", "Force fresh recommendation search").action(recommendCommand);
|
|
5911
6021
|
program.command("score").description("Score your current agent config setup (deterministic, no network)").option("--json", "Output as JSON").option("--quiet", "One-line output for scripts/hooks").option("--agent <type>", "Target agent: claude, cursor, or both").action(scoreCommand);
|
|
5912
6022
|
program.command("refresh").description("Update docs based on recent code changes").option("--quiet", "Suppress output (for use in hooks)").option("--dry-run", "Preview changes without writing files").action(refreshCommand);
|
|
5913
|
-
|
|
5914
|
-
hooks.command("install").description("Install Claude Code SessionEnd auto-refresh hook").action(hooksInstallCommand);
|
|
5915
|
-
hooks.command("remove").description("Remove Claude Code SessionEnd auto-refresh hook").action(hooksRemoveCommand);
|
|
5916
|
-
hooks.command("install-precommit").description("Install git pre-commit hook for auto-refresh").action(hooksInstallPrecommitCommand);
|
|
5917
|
-
hooks.command("remove-precommit").description("Remove git pre-commit hook").action(hooksRemovePrecommitCommand);
|
|
5918
|
-
hooks.command("status").description("Check installed hooks status").action(hooksStatusCommand);
|
|
6023
|
+
program.command("hooks").description("Manage auto-refresh hooks (toggle interactively)").option("--install", "Enable all hooks non-interactively").option("--remove", "Disable all hooks non-interactively").action(hooksCommand);
|
|
5919
6024
|
var learn = program.command("learn").description("Session learning \u2014 observe tool usage and extract reusable instructions");
|
|
5920
6025
|
learn.command("observe").description("Record a tool event from stdin (called by hooks)").option("--failure", "Mark event as a tool failure").action(learnObserveCommand);
|
|
5921
6026
|
learn.command("finalize").description("Analyze session events and update CLAUDE.md (called on SessionEnd)").action(learnFinalizeCommand);
|
package/package.json
CHANGED