prior-cli 1.5.4 → 1.5.6

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.
Files changed (2) hide show
  1. package/bin/prior.js +89 -1
  2. package/package.json +1 -1
package/bin/prior.js CHANGED
@@ -669,7 +669,7 @@ async function startChat(opts = {}) {
669
669
  console.log(c.ok(' ◉') + c.muted(' Agent mode ') + c.dim('· file web shell image prior-network'));
670
670
 
671
671
  console.log(DIVIDER);
672
- console.log(c.muted(' /help /clear /censored /uncensored /exit'));
672
+ console.log(c.muted(' /help /clear /compact /censored /uncensored /exit'));
673
673
  console.log(DIVIDER);
674
674
  console.log('');
675
675
 
@@ -686,6 +686,7 @@ async function startChat(opts = {}) {
686
686
  readline.emitKeypressEvents(process.stdin, rl);
687
687
 
688
688
  const SLASH_CMDS = [
689
+ { cmd: '/compact', desc: 'Compact conversation to save context' },
689
690
  { cmd: '/help', desc: 'Show help' },
690
691
  { cmd: '/clear', desc: 'Clear screen' },
691
692
  { cmd: '/censored', desc: 'Load standard model (qwen)' },
@@ -1037,9 +1038,96 @@ Keep it under 350 words. Write prior.md now.`;
1037
1038
  return loop();
1038
1039
  }
1039
1040
 
1041
+ case '/compact': {
1042
+ if (chatHistory.length === 0) {
1043
+ console.log(c.muted(' Nothing to compact yet.\n'));
1044
+ return loop();
1045
+ }
1046
+ const msgsBefore = chatHistory.length;
1047
+ const tokensBefore = chatHistory.reduce((n, m) => n + (m.content?.length || 0), 0);
1048
+
1049
+ // Animation frames while waiting
1050
+ const FRAMES = ['⠋','⠙','⠹','⠸','⠼','⠴','⠦','⠧','⠇','⠏'];
1051
+ const steps = [
1052
+ 'analyzing conversation…',
1053
+ 'identifying key context…',
1054
+ 'building summary…',
1055
+ 'compressing history…',
1056
+ ];
1057
+ let fi = 0; let si = 0;
1058
+ process.stdout.write('\n');
1059
+ const animTimer = setInterval(() => {
1060
+ process.stdout.clearLine(0);
1061
+ process.stdout.cursorTo(0);
1062
+ if (fi % 8 === 0 && si < steps.length - 1) si++;
1063
+ process.stdout.write(` ${c.brand(FRAMES[fi % FRAMES.length])} ${c.dim(steps[si])}`);
1064
+ fi++;
1065
+ }, 100);
1066
+
1067
+ try {
1068
+ const compactPrompt = [
1069
+ ...chatHistory,
1070
+ {
1071
+ role: 'user',
1072
+ content: `Please produce a compact summary of our conversation so far. Structure it as:
1073
+
1074
+ **What we were doing:** (1-2 sentences on the task/goal)
1075
+ **Key decisions made:** (bullet points)
1076
+ **Important context:** (facts, file paths, code details worth remembering)
1077
+ **Current state:** (where things stand right now)
1078
+
1079
+ Be concise but thorough — this summary replaces the full history to save context.`,
1080
+ },
1081
+ ];
1082
+
1083
+ const token = require('../lib/config').getToken();
1084
+ const res = await fetch('https://prior.ngrok.app/cli-backend/api/infer', {
1085
+ method: 'POST',
1086
+ headers: { 'Content-Type': 'application/json' },
1087
+ body: JSON.stringify({ messages: compactPrompt, model: currentModel, token, cwd: process.cwd() }),
1088
+ timeout: 120000,
1089
+ });
1090
+ if (!res.ok) throw new Error(`HTTP ${res.status}`);
1091
+ const data = await res.json();
1092
+ const summary = data.content?.trim() || '';
1093
+
1094
+ clearInterval(animTimer);
1095
+ process.stdout.clearLine(0);
1096
+ process.stdout.cursorTo(0);
1097
+
1098
+ if (!summary) throw new Error('Empty summary returned');
1099
+
1100
+ // Replace history with single compact message
1101
+ chatHistory.length = 0;
1102
+ chatHistory.push({ role: 'user', content: '[Conversation compacted]' });
1103
+ chatHistory.push({ role: 'assistant', content: summary });
1104
+
1105
+ const tokensAfter = summary.length;
1106
+ const saved = Math.round((1 - tokensAfter / tokensBefore) * 100);
1107
+
1108
+ process.stdout.write(` ${c.ok('✓')} ${c.bold('Compacted')} ${c.dim(`${msgsBefore} messages → 1 summary · ~${saved}% smaller`)}\n\n`);
1109
+
1110
+ // Draw summary box
1111
+ const summaryLines = summary.split('\n');
1112
+ process.stdout.write(c.muted(' ┌─────────────────────────────────────\n'));
1113
+ for (const line of summaryLines) {
1114
+ process.stdout.write(c.muted(' │ ') + c.dim(line) + '\n');
1115
+ }
1116
+ process.stdout.write(c.muted(' └─────────────────────────────────────\n\n'));
1117
+
1118
+ } catch (err) {
1119
+ clearInterval(animTimer);
1120
+ process.stdout.clearLine(0);
1121
+ process.stdout.cursorTo(0);
1122
+ console.error(c.err(` ✗ Compact failed: ${err.message}\n`));
1123
+ }
1124
+ return loop();
1125
+ }
1126
+
1040
1127
  case '/help':
1041
1128
  console.log('');
1042
1129
  console.log(c.bold(' Commands'));
1130
+ console.log(c.muted(' /compact ') + 'Compact conversation to save context');
1043
1131
  console.log(c.muted(' /clear ') + 'Clear screen');
1044
1132
  console.log(c.muted(' /censored ') + 'Load standard model (qwen)');
1045
1133
  console.log(c.muted(' /uncensored ') + 'Load uncensored model (dolphin)');
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "prior-cli",
3
- "version": "1.5.4",
3
+ "version": "1.5.6",
4
4
  "description": "Prior Network AI — command-line interface",
5
5
  "bin": {
6
6
  "prior": "bin/prior.js"