clementine-agent 1.0.36 → 1.0.39

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.
@@ -1159,6 +1159,17 @@ function writeCronFileAt(cronFile, parsed, jobs) {
1159
1159
  }
1160
1160
  // ── Express app ──────────────────────────────────────────────────────
1161
1161
  export async function cmdDashboard(opts) {
1162
+ // Ensure BASE_DIR exists before any dashboard-local files (PID file, auth
1163
+ // token) are written. Other CLI commands route through ensureDataHome() in
1164
+ // index.ts, but the dashboard command doesn't — on a truly fresh install
1165
+ // where someone runs `clementine dashboard` before `clementine launch` or
1166
+ // `config setup`, the parent-process writeFileSync(DASHBOARD_PID_FILE)
1167
+ // would ENOENT and the dashboard would die before the browser could see
1168
+ // it. Idempotent, so safe for every invocation.
1169
+ try {
1170
+ mkdirSync(BASE_DIR, { recursive: true });
1171
+ }
1172
+ catch { /* ignore */ }
1162
1173
  // Child process skips the kill step — parent already handled it
1163
1174
  if (!process.env.__CLEM_DASHBOARD_CHILD) {
1164
1175
  const killed = killExistingDashboards();
@@ -9328,7 +9339,7 @@ if('serviceWorker' in navigator){navigator.serviceWorker.getRegistrations().then
9328
9339
  const wmHtml = a.workingMemorySnippet
9329
9340
  ? '<div style="margin-top:8px;padding:8px;background:var(--bg-input);border-radius:6px;font-size:11px;color:var(--text-secondary);overflow:hidden;text-overflow:ellipsis;white-space:nowrap">' + a.workingMemorySnippet + '</div>'
9330
9341
  : '';
9331
- return '<div style="background:var(--bg-card);border:1px solid var(--border);border-radius:12px;padding:16px;cursor:pointer" onclick="showPage(\'team\');setTimeout(()=>selectAgent(\''+a.slug+'\'),100)">' +
9342
+ return '<div style="background:var(--bg-card);border:1px solid var(--border);border-radius:12px;padding:16px;cursor:pointer" onclick="showPage(\\'team\\');setTimeout(()=>selectAgent(\\''+a.slug+'\\'),100)">' +
9332
9343
  '<div style="display:flex;align-items:center;gap:10px;margin-bottom:10px">' +
9333
9344
  '<div style="width:40px;height:40px;border-radius:50%;background:var(--clementine);color:#fff;display:flex;align-items:center;justify-content:center;font-weight:700;font-size:18px">' + avatarLetter + '</div>' +
9334
9345
  '<div><div style="font-weight:600">' + (a.name || a.slug) + '</div>' +
@@ -16480,11 +16491,11 @@ async function applyBrokenJobFix(jobName) {
16480
16491
  return;
16481
16492
  }
16482
16493
  var diffPreview = (dryRes.diff || '(no diff)').slice(0, 1200);
16483
- var msg = 'Apply this fix to ' + jobName + '?\n\n'
16484
- + 'File: ' + (dryRes.file || 'unknown') + '\n'
16485
- + 'Operations: ' + (dryRes.appliedOps || []).length + '\n\n'
16494
+ var msg = 'Apply this fix to ' + jobName + '?\\n\\n'
16495
+ + 'File: ' + (dryRes.file || 'unknown') + '\\n'
16496
+ + 'Operations: ' + (dryRes.appliedOps || []).length + '\\n\\n'
16486
16497
  + diffPreview
16487
- + '\n\nA .bak will be written. The daemon auto-reloads; the next run will be fix-verified.';
16498
+ + '\\n\\nA .bak will be written. The daemon auto-reloads; the next run will be fix-verified.';
16488
16499
  if (!confirm(msg)) return;
16489
16500
 
16490
16501
  var res = await apiJson('POST', '/api/cron/broken-jobs/' + encodeURIComponent(jobName) + '/apply-fix', {});
package/dist/cli/index.js CHANGED
@@ -480,11 +480,10 @@ function cmdDoctor(opts = {}) {
480
480
  console.log(` ${DIM}Running health checks...${fix ? ` (auto-fix enabled)` : ''}${RESET}`);
481
481
  console.log();
482
482
  let issues = 0;
483
- let warnings = 0;
484
483
  let fixed = 0;
485
484
  const isMac = process.platform === 'darwin';
486
485
  const isLinux = process.platform === 'linux';
487
- const hasBrew = isMac && (() => { try {
486
+ let hasBrew = isMac && (() => { try {
488
487
  execSync('which brew', { stdio: 'pipe' });
489
488
  return true;
490
489
  }
@@ -498,9 +497,19 @@ function cmdDoctor(opts = {}) {
498
497
  catch {
499
498
  return false;
500
499
  } })();
501
- // One-liner to install Homebrew on macOS surfaced when brew is missing
502
- // so users have a copy-pasteable fix instead of searching for it.
500
+ // Homebrew official installer. Honors NONINTERACTIVE=1 (set by tryFix) so
501
+ // it won't block on sudo or "Press Return" prompts, though it still needs
502
+ // the password cached or sudoless access. Surfaced as copy-paste guidance
503
+ // when --fix is off.
503
504
  const BREW_INSTALL_CMD = '/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"';
505
+ /** Resolve the current brew binary path after a fresh install. */
506
+ const brewBin = () => {
507
+ for (const p of ['/opt/homebrew/bin/brew', '/usr/local/bin/brew']) {
508
+ if (existsSync(p))
509
+ return p;
510
+ }
511
+ return 'brew';
512
+ };
504
513
  /** Attempt a fix command, return true on success. */
505
514
  function tryFix(label, cmd, opts) {
506
515
  if (!fix)
@@ -575,33 +584,51 @@ function cmdDoctor(opts = {}) {
575
584
  issues++;
576
585
  }
577
586
  }
587
+ // macOS: if Homebrew is missing and --fix is on, install it up front so
588
+ // the subsequent redis-server / libomp checks can auto-resolve. Brew's
589
+ // installer honors NONINTERACTIVE=1 (which tryFix sets), but still needs
590
+ // sudo access — fails gracefully and falls back to copy-paste guidance
591
+ // if sudo isn't available.
592
+ if (isMac && !hasBrew && fix) {
593
+ console.log(` ${RED}FAIL${RESET} Homebrew not installed (required to install graph-memory deps)`);
594
+ if (tryFix('Homebrew', BREW_INSTALL_CMD, { timeout: 600000 })) {
595
+ hasBrew = existsSync('/opt/homebrew/bin/brew') || existsSync('/usr/local/bin/brew');
596
+ }
597
+ if (!hasBrew) {
598
+ console.log(` Install manually, then re-run ${CYAN}clementine doctor --fix${RESET}:`);
599
+ console.log(` ${BREW_INSTALL_CMD}`);
600
+ issues++;
601
+ }
602
+ }
603
+ else if (isMac && !hasBrew) {
604
+ console.log(` ${RED}FAIL${RESET} Homebrew not installed (required to install graph-memory deps)`);
605
+ console.log(` Install it, then run ${CYAN}clementine doctor --fix${RESET}:`);
606
+ console.log(` ${BREW_INSTALL_CMD}`);
607
+ issues++;
608
+ }
578
609
  // FalkorDB graph engine — system dependencies: redis
579
- // Optional at runtime: graph-store.ts degrades gracefully (isAvailable()
580
- // returns false; graph operations become no-ops). Missing deps are a
581
- // warning, not a blocking issue daemon launches fine without them.
610
+ // The knowledge-graph layer is a core memory feature. Missing deps are
611
+ // a blocking issue: the daemon technically launches (graph-store.ts has
612
+ // a no-op degradation path), but memory features the framework depends
613
+ // on are silently absent. Surface it loudly.
582
614
  try {
583
615
  execSync('which redis-server', { stdio: 'pipe' });
584
616
  console.log(` ${GREEN}OK${RESET} redis-server found`);
585
617
  }
586
618
  catch {
587
- console.log(` ${YELLOW}WARN${RESET} redis-server not found (optional enables knowledge graph)`);
588
- const fixCmd = hasBrew ? 'brew install redis' : hasApt ? 'sudo apt-get install -y redis-server' : null;
619
+ console.log(` ${RED}FAIL${RESET} redis-server not found (required for graph memory)`);
620
+ const fixCmd = hasBrew ? `${brewBin()} install redis` : hasApt ? 'sudo apt-get install -y redis-server' : null;
589
621
  if (fixCmd && tryFix('redis-server', fixCmd)) {
590
622
  // fixed
591
623
  }
592
- else if (!fixCmd && fix) {
593
- if (isMac) {
594
- console.log(` ${YELLOW}Homebrew not installed.${RESET} Install it first, then re-run ${CYAN}clementine doctor --fix${RESET}:`);
595
- console.log(` ${BREW_INSTALL_CMD}`);
624
+ else {
625
+ if (isMac && !hasBrew) {
626
+ console.log(` Install Homebrew first (see above), then ${CYAN}clementine doctor --fix${RESET}`);
596
627
  }
597
628
  else {
598
- console.log(` Install redis-server manually (no supported package manager detected)`);
629
+ console.log(` Fix: brew install redis (macOS) or sudo apt install redis-server (Linux)`);
599
630
  }
600
- warnings++;
601
- }
602
- else {
603
- console.log(` Fix: brew install redis (macOS) or sudo apt install redis-server (Linux)`);
604
- warnings++;
631
+ issues++;
605
632
  }
606
633
  }
607
634
  // FalkorDB graph engine — system dependencies: libomp
@@ -615,25 +642,19 @@ function cmdDoctor(opts = {}) {
615
642
  console.log(` ${GREEN}OK${RESET} libomp (OpenMP runtime) found`);
616
643
  }
617
644
  catch {
618
- console.log(` ${YELLOW}WARN${RESET} libomp (OpenMP runtime) not found (optional enables knowledge graph)`);
619
- const fixCmd = hasBrew ? 'brew install libomp' : hasApt ? 'sudo apt-get install -y libomp-dev' : null;
645
+ console.log(` ${RED}FAIL${RESET} libomp (OpenMP runtime) not found (required for graph memory)`);
646
+ const fixCmd = hasBrew ? `${brewBin()} install libomp` : hasApt ? 'sudo apt-get install -y libomp-dev' : null;
620
647
  if (fixCmd && tryFix('libomp', fixCmd)) {
621
648
  // fixed
622
649
  }
623
- else if (!fixCmd && fix) {
624
- if (isMac) {
625
- // Redis check above already printed the brew installer command;
626
- // avoid spamming it twice by just pointing back to that guidance.
627
- console.log(` Install Homebrew (see redis-server WARN above), then ${CYAN}brew install libomp${RESET}`);
650
+ else {
651
+ if (isMac && !hasBrew) {
652
+ console.log(` Install Homebrew first (see above), then ${CYAN}clementine doctor --fix${RESET}`);
628
653
  }
629
654
  else {
630
- console.log(` Install libomp manually (no supported package manager detected)`);
655
+ console.log(` Fix: brew install libomp (macOS) or sudo apt install libomp-dev (Linux)`);
631
656
  }
632
- warnings++;
633
- }
634
- else {
635
- console.log(` Fix: brew install libomp (macOS) or sudo apt install libomp-dev (Linux)`);
636
- warnings++;
657
+ issues++;
637
658
  }
638
659
  }
639
660
  // FalkorDB graph engine — module binaries
@@ -642,11 +663,11 @@ function cmdDoctor(opts = {}) {
642
663
  console.log(` ${GREEN}OK${RESET} FalkorDB graph engine binaries installed`);
643
664
  }
644
665
  catch {
645
- console.log(` ${YELLOW}WARN${RESET} FalkorDB graph engine binaries not available (optional — enables knowledge graph)`);
666
+ console.log(` ${RED}FAIL${RESET} FalkorDB graph engine binaries not available`);
646
667
  if (!tryFix('FalkorDB binaries', `node node_modules/falkordblite/scripts/postinstall.js`, { cwd: PACKAGE_ROOT, timeout: 180000 })) {
647
668
  console.log(` Fix: cd ${PACKAGE_ROOT} && node node_modules/falkordblite/scripts/postinstall.js`);
648
669
  console.log(` ${DIM}(Usually self-heals once redis-server + libomp are installed)${RESET}`);
649
- warnings++;
670
+ issues++;
650
671
  }
651
672
  }
652
673
  // Data home
@@ -848,21 +869,17 @@ function cmdDoctor(opts = {}) {
848
869
  }
849
870
  }
850
871
  console.log();
851
- const warnSuffix = warnings > 0 ? `, ${warnings} warning(s)` : '';
852
- if (issues === 0 && fixed === 0 && warnings === 0) {
872
+ if (issues === 0 && fixed === 0) {
853
873
  console.log(` ${GREEN}All checks passed.${RESET}`);
854
874
  }
855
- else if (issues === 0 && fixed === 0 && warnings > 0) {
856
- console.log(` ${GREEN}Ready to launch.${RESET} ${warnings} optional dependency warning(s) — safe to ignore or install for full experience.`);
857
- }
858
875
  else if (issues === 0 && fixed > 0) {
859
- console.log(` ${GREEN}All issues fixed!${RESET} (${fixed} auto-fixed${warnSuffix})`);
876
+ console.log(` ${GREEN}All issues fixed!${RESET} (${fixed} auto-fixed)`);
860
877
  }
861
878
  else if (fixed > 0) {
862
- console.log(` ${YELLOW}${issues} issue(s) remaining${RESET} (${fixed} auto-fixed${warnSuffix})`);
879
+ console.log(` ${YELLOW}${issues} issue(s) remaining${RESET} (${fixed} auto-fixed)`);
863
880
  }
864
881
  else {
865
- console.log(` ${YELLOW}${issues} issue(s) found${warnSuffix}.${RESET}${!fix ? ` Run ${CYAN}clementine doctor --fix${RESET} to auto-install dependencies.` : ''}`);
882
+ console.log(` ${YELLOW}${issues} issue(s) found.${RESET}${!fix ? ` Run ${CYAN}clementine doctor --fix${RESET} to auto-install dependencies.` : ''}`);
866
883
  }
867
884
  console.log();
868
885
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "clementine-agent",
3
- "version": "1.0.36",
3
+ "version": "1.0.39",
4
4
  "description": "Clementine — Personal AI Assistant (TypeScript)",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",