@axplusb/kepler 2.0.7 → 2.2.0
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/package.json +2 -2
- package/src/config/hook-runner.mjs +100 -0
- package/src/config/memory-loader.mjs +32 -0
- package/src/config/settings-loader.mjs +45 -0
- package/src/core/approval-log.mjs +104 -0
- package/src/core/approval.mjs +164 -24
- package/src/core/context-envelope.mjs +54 -0
- package/src/core/headless.mjs +14 -1
- package/src/core/jsonl-writer.mjs +50 -0
- package/src/core/local-store.mjs +486 -5
- package/src/core/policy-resolver.mjs +156 -0
- package/src/core/project-context-loader.mjs +139 -0
- package/src/core/rate-limit-display.mjs +97 -0
- package/src/core/resume-mode.mjs +154 -0
- package/src/core/risk-tier.mjs +88 -2
- package/src/core/safety.mjs +3 -0
- package/src/core/session-manager.mjs +53 -10
- package/src/core/stream-client.mjs +69 -10
- package/src/core/system-prompt.mjs +6 -1
- package/src/core/tasks.mjs +130 -0
- package/src/core/tool-executor.mjs +72 -6
- package/src/core/trust.mjs +158 -0
- package/src/onboarding/preflight.mjs +27 -11
- package/src/permissions/command-classifier.mjs +78 -0
- package/src/terminal/init.mjs +145 -0
- package/src/terminal/main.mjs +7 -0
- package/src/terminal/repl.mjs +1735 -140
- package/src/tools/bash.mjs +57 -9
- package/src/tools/project-overview.mjs +83 -10
- package/src/ui/approval.mjs +154 -35
- package/src/ui/formatter.mjs +39 -5
- package/src/ui/mission-report.mjs +55 -22
- package/src/ui/slash-commands.mjs +57 -5
- package/src/ui/tool-card.mjs +51 -1
package/src/core/headless.mjs
CHANGED
|
@@ -81,6 +81,7 @@ export async function runHeadless({ instruction, model, timeout = 300, maxCost,
|
|
|
81
81
|
let toolCount = 0;
|
|
82
82
|
let finalContent = '';
|
|
83
83
|
let totalCost = 0;
|
|
84
|
+
let rateLimit = null;
|
|
84
85
|
|
|
85
86
|
// ── Telemetry collectors ──
|
|
86
87
|
const toolCalls = []; // { tool, duration_ms, success }
|
|
@@ -149,7 +150,12 @@ export async function runHeadless({ instruction, model, timeout = 300, maxCost,
|
|
|
149
150
|
if (text) finalContent = text;
|
|
150
151
|
}
|
|
151
152
|
|
|
153
|
+
if (type === 'session_info' && data?.rate_limit) {
|
|
154
|
+
rateLimit = data.rate_limit;
|
|
155
|
+
}
|
|
156
|
+
|
|
152
157
|
if (type === 'complete') {
|
|
158
|
+
if (data?.rate_limit) rateLimit = data.rate_limit;
|
|
153
159
|
totalCost = data?.cost || data?.total_cost || 0;
|
|
154
160
|
if (data?.usage?.total_cost) totalCost = data.usage.total_cost;
|
|
155
161
|
// Capture token usage
|
|
@@ -164,7 +170,13 @@ export async function runHeadless({ instruction, model, timeout = 300, maxCost,
|
|
|
164
170
|
}
|
|
165
171
|
|
|
166
172
|
if (type === 'error') {
|
|
167
|
-
emit({
|
|
173
|
+
emit({
|
|
174
|
+
type: 'error',
|
|
175
|
+
error: data?.message || 'Unknown error',
|
|
176
|
+
code: data?.code,
|
|
177
|
+
retry_after: data?.retry_after,
|
|
178
|
+
rate_limit: data?.rate_limit || null,
|
|
179
|
+
});
|
|
168
180
|
}
|
|
169
181
|
|
|
170
182
|
// ── Cost guard ──
|
|
@@ -202,6 +214,7 @@ export async function runHeadless({ instruction, model, timeout = 300, maxCost,
|
|
|
202
214
|
usage,
|
|
203
215
|
duration_s: Math.round(durationS * 10) / 10,
|
|
204
216
|
cost_usd: totalCost,
|
|
217
|
+
rate_limit: rateLimit,
|
|
205
218
|
model: model || 'default',
|
|
206
219
|
content_length: finalContent.length,
|
|
207
220
|
});
|
|
@@ -40,6 +40,23 @@ function normalizeToolResultContent(output) {
|
|
|
40
40
|
}
|
|
41
41
|
}
|
|
42
42
|
|
|
43
|
+
function sanitizeEventValue(value, depth = 0) {
|
|
44
|
+
if (depth > 8) return '[truncated-depth]';
|
|
45
|
+
if (typeof value === 'string') {
|
|
46
|
+
return value.length > 10000 ? value.slice(0, 10000) + '\n[...truncated...]' : value;
|
|
47
|
+
}
|
|
48
|
+
if (value == null || typeof value === 'number' || typeof value === 'boolean') return value;
|
|
49
|
+
if (Array.isArray(value)) return value.slice(0, 100).map(item => sanitizeEventValue(item, depth + 1));
|
|
50
|
+
if (typeof value === 'object') {
|
|
51
|
+
const out = {};
|
|
52
|
+
for (const [key, item] of Object.entries(value).slice(0, 100)) {
|
|
53
|
+
out[key] = sanitizeEventValue(item, depth + 1);
|
|
54
|
+
}
|
|
55
|
+
return out;
|
|
56
|
+
}
|
|
57
|
+
return String(value);
|
|
58
|
+
}
|
|
59
|
+
|
|
43
60
|
export class JsonlWriter {
|
|
44
61
|
/**
|
|
45
62
|
* @param {string} cwd — project working directory
|
|
@@ -68,6 +85,7 @@ export class JsonlWriter {
|
|
|
68
85
|
this._turnToolResults = []; // [{tool_use_id, content, is_error}, ...]
|
|
69
86
|
this._turnUsage = null;
|
|
70
87
|
this._turnModel = null;
|
|
88
|
+
this._pendingKeplerEvents = [];
|
|
71
89
|
|
|
72
90
|
// Git branch (captured once at construction)
|
|
73
91
|
this._gitBranch = this._detectGitBranch();
|
|
@@ -83,6 +101,11 @@ export class JsonlWriter {
|
|
|
83
101
|
this.sessionId = id;
|
|
84
102
|
this._transcriptPath = path.join(this.projectDir, `${id}.jsonl`);
|
|
85
103
|
this._ready = true;
|
|
104
|
+
if (this._pendingKeplerEvents.length > 0) {
|
|
105
|
+
const pending = this._pendingKeplerEvents;
|
|
106
|
+
this._pendingKeplerEvents = [];
|
|
107
|
+
for (const event of pending) this.writeKeplerEvent(event);
|
|
108
|
+
}
|
|
86
109
|
// Flush any buffered entries now that we have a path
|
|
87
110
|
if (this._buffer.length > 0) this._flush();
|
|
88
111
|
}
|
|
@@ -119,6 +142,33 @@ export class JsonlWriter {
|
|
|
119
142
|
this.lastUuid = uuid;
|
|
120
143
|
}
|
|
121
144
|
|
|
145
|
+
/**
|
|
146
|
+
* Write a Kepler UI/SSE event for exact-ish terminal replay on /resume.
|
|
147
|
+
* This is a Kepler extension; cc-lens readers should ignore unknown types.
|
|
148
|
+
*/
|
|
149
|
+
writeKeplerEvent(event) {
|
|
150
|
+
if (!event || !event.type) return;
|
|
151
|
+
const sanitized = sanitizeEventValue({
|
|
152
|
+
type: event.type,
|
|
153
|
+
data: event.data || {},
|
|
154
|
+
});
|
|
155
|
+
|
|
156
|
+
if (!this.sessionId) {
|
|
157
|
+
this._pendingKeplerEvents.push(sanitized);
|
|
158
|
+
return;
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
const entry = {
|
|
162
|
+
type: 'kepler_event',
|
|
163
|
+
timestamp: new Date().toISOString(),
|
|
164
|
+
cwd: this.cwd,
|
|
165
|
+
sessionId: this.sessionId,
|
|
166
|
+
version: this.version,
|
|
167
|
+
event: sanitized,
|
|
168
|
+
};
|
|
169
|
+
this._appendEntry(entry);
|
|
170
|
+
}
|
|
171
|
+
|
|
122
172
|
/**
|
|
123
173
|
* Accumulate content during streaming (call on content/content_partial events).
|
|
124
174
|
*/
|