osborn 0.5.2 → 0.5.5
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/.claude/settings.local.json +9 -0
- package/.claude/skills/markdown-to-pdf/SKILL.md +29 -0
- package/.claude/skills/pdf-to-markdown/SKILL.md +28 -0
- package/.claude/skills/playwright-browser/SKILL.md +75 -0
- package/.claude/skills/youtube-transcript/SKILL.md +24 -0
- package/dist/claude-llm.d.ts +29 -1
- package/dist/claude-llm.js +346 -79
- package/dist/config.d.ts +6 -2
- package/dist/config.js +6 -1
- package/dist/fast-brain.d.ts +124 -12
- package/dist/fast-brain.js +1361 -96
- package/dist/index-3-2-26-legacy.d.ts +1 -0
- package/dist/index-3-2-26-legacy.js +2233 -0
- package/dist/index.js +889 -394
- package/dist/jsonl-search.d.ts +66 -0
- package/dist/jsonl-search.js +274 -0
- package/dist/leagcyprompts2.d.ts +0 -0
- package/dist/leagcyprompts2.js +573 -0
- package/dist/pipeline-direct-llm.d.ts +77 -0
- package/dist/pipeline-direct-llm.js +216 -0
- package/dist/pipeline-fastbrain.d.ts +45 -0
- package/dist/pipeline-fastbrain.js +367 -0
- package/dist/prompts-2-25-26.d.ts +0 -0
- package/dist/prompts-2-25-26.js +518 -0
- package/dist/prompts-3-2-26.d.ts +78 -0
- package/dist/prompts-3-2-26.js +1319 -0
- package/dist/prompts.d.ts +83 -8
- package/dist/prompts.js +1990 -374
- package/dist/session-access.d.ts +60 -2
- package/dist/session-access.js +172 -2
- package/dist/summary-index.d.ts +87 -0
- package/dist/summary-index.js +570 -0
- package/dist/turn-detector-shim.d.ts +24 -0
- package/dist/turn-detector-shim.js +83 -0
- package/dist/voice-io.d.ts +9 -3
- package/dist/voice-io.js +39 -20
- package/package.json +18 -11
package/dist/session-access.d.ts
CHANGED
|
@@ -259,6 +259,30 @@ export interface SessionTranscripts {
|
|
|
259
259
|
* @param opts.claudeDir - Override the claude directory path
|
|
260
260
|
*/
|
|
261
261
|
export declare function getSessionPaths(sessionId: string, projectDir: string, opts?: SessionAccessOptions): SessionPaths;
|
|
262
|
+
export interface SubAgentInfo {
|
|
263
|
+
agentId: string;
|
|
264
|
+
description: string;
|
|
265
|
+
status: string;
|
|
266
|
+
agentFile: string;
|
|
267
|
+
agentFileExists: boolean;
|
|
268
|
+
totalTokens: number;
|
|
269
|
+
totalToolUseCount: number;
|
|
270
|
+
durationMs: number;
|
|
271
|
+
}
|
|
272
|
+
/**
|
|
273
|
+
* Find all sub-agents spawned by a session.
|
|
274
|
+
* Extracts agentId from toolUseResult fields in the main JSONL,
|
|
275
|
+
* then checks for corresponding agent-{id}.jsonl files at the project level.
|
|
276
|
+
*
|
|
277
|
+
* Sub-agent files live at: ~/.claude/projects/{slug}/agent-{id}.jsonl
|
|
278
|
+
* (NOT inside the session subdirectory — that's only for the Osborn agent SDK path)
|
|
279
|
+
*/
|
|
280
|
+
export declare function getSessionSubAgents(sessionId: string, projectDir: string, opts?: SessionAccessOptions): SubAgentInfo[];
|
|
281
|
+
/**
|
|
282
|
+
* Get all searchable file paths for a session — main JSONL + all sub-agent JSOLs.
|
|
283
|
+
* This is what the pipeline fast brain should ripgrep across.
|
|
284
|
+
*/
|
|
285
|
+
export declare function getSessionSearchPaths(sessionId: string, projectDir: string, opts?: SessionAccessOptions): string[];
|
|
262
286
|
/**
|
|
263
287
|
* Read raw JSON objects from a JSONL file — no parsing into SessionMessage.
|
|
264
288
|
* Returns the actual JSON as-is so you can inspect the full object shapes.
|
|
@@ -318,9 +342,12 @@ export declare function getSessionPlan(sessionId: string, projectDir: string, op
|
|
|
318
342
|
* Get recent tool use/result pairs from a session.
|
|
319
343
|
* Returns matched pairs of (tool_use → tool_result) in chronological order.
|
|
320
344
|
*
|
|
321
|
-
* @param lastN - Number of recent pairs to return (default: 10)
|
|
345
|
+
* @param lastN - Number of recent pairs to return (default: 10, 0 = all)
|
|
346
|
+
* @param opts.toolNameFilter - Optional: only return results from these tool names (e.g., ['Read', 'WebSearch'])
|
|
322
347
|
*/
|
|
323
|
-
export declare function getRecentToolResults(sessionId: string, projectDir: string, lastN?: number, opts?: SessionAccessOptions
|
|
348
|
+
export declare function getRecentToolResults(sessionId: string, projectDir: string, lastN?: number, opts?: SessionAccessOptions & {
|
|
349
|
+
toolNameFilter?: string[];
|
|
350
|
+
}): ToolResultEntry[];
|
|
324
351
|
/**
|
|
325
352
|
* Watch a session JSONL file for new entries.
|
|
326
353
|
* Calls back with each new parsed entry as it's appended.
|
|
@@ -347,6 +374,37 @@ export declare function getConversationText(sessionId: string, projectDir: strin
|
|
|
347
374
|
role: string;
|
|
348
375
|
text: string;
|
|
349
376
|
}[];
|
|
377
|
+
/**
|
|
378
|
+
* Search the session JSONL for entries matching a keyword (case-insensitive).
|
|
379
|
+
* Searches across text, toolResultContent, toolName, and toolInput.
|
|
380
|
+
* Returns matching entries with 500-char excerpts around the match.
|
|
381
|
+
*
|
|
382
|
+
* @param keyword - The search keyword (case-insensitive)
|
|
383
|
+
* @param opts.maxResults - Maximum number of results to return (default: 20)
|
|
384
|
+
*/
|
|
385
|
+
export declare function searchSessionJsonl(sessionId: string, projectDir: string, keyword: string, opts?: SessionAccessOptions & {
|
|
386
|
+
maxResults?: number;
|
|
387
|
+
}): {
|
|
388
|
+
type: string;
|
|
389
|
+
text: string;
|
|
390
|
+
timestamp?: string;
|
|
391
|
+
}[];
|
|
392
|
+
/**
|
|
393
|
+
* Get session stats: message counts, tool usage breakdown, data sizes.
|
|
394
|
+
* Helps the fast brain decide how much data to read and which tools to query.
|
|
395
|
+
*/
|
|
396
|
+
export declare function getSessionStats(sessionId: string, projectDir: string, opts?: SessionAccessOptions): {
|
|
397
|
+
totalMessages: number;
|
|
398
|
+
userMessages: number;
|
|
399
|
+
assistantMessages: number;
|
|
400
|
+
toolUseCount: number;
|
|
401
|
+
toolResultCount: number;
|
|
402
|
+
toolBreakdown: Record<string, number>;
|
|
403
|
+
subagentCount: number;
|
|
404
|
+
fileSizeBytes: number;
|
|
405
|
+
firstTimestamp?: string;
|
|
406
|
+
lastTimestamp?: string;
|
|
407
|
+
} | null;
|
|
350
408
|
/**
|
|
351
409
|
* Get a quick summary of a session: slug, message count, timestamps, tools used.
|
|
352
410
|
*/
|
package/dist/session-access.js
CHANGED
|
@@ -228,6 +228,80 @@ export function getSessionPaths(sessionId, projectDir, opts) {
|
|
|
228
228
|
exists: existsSync(conversationPath),
|
|
229
229
|
};
|
|
230
230
|
}
|
|
231
|
+
/**
|
|
232
|
+
* Find all sub-agents spawned by a session.
|
|
233
|
+
* Extracts agentId from toolUseResult fields in the main JSONL,
|
|
234
|
+
* then checks for corresponding agent-{id}.jsonl files at the project level.
|
|
235
|
+
*
|
|
236
|
+
* Sub-agent files live at: ~/.claude/projects/{slug}/agent-{id}.jsonl
|
|
237
|
+
* (NOT inside the session subdirectory — that's only for the Osborn agent SDK path)
|
|
238
|
+
*/
|
|
239
|
+
export function getSessionSubAgents(sessionId, projectDir, opts) {
|
|
240
|
+
const claudeDir = resolveClaudeDir(opts);
|
|
241
|
+
const slug = projectPathToSlug(projectDir);
|
|
242
|
+
const projectsDir = join(claudeDir, 'projects', slug);
|
|
243
|
+
const conversationPath = join(projectsDir, `${sessionId}.jsonl`);
|
|
244
|
+
if (!existsSync(conversationPath))
|
|
245
|
+
return [];
|
|
246
|
+
const agents = [];
|
|
247
|
+
const seenIds = new Set();
|
|
248
|
+
try {
|
|
249
|
+
const content = readFileSync(conversationPath, 'utf-8');
|
|
250
|
+
for (const line of content.split('\n')) {
|
|
251
|
+
if (!line.trim())
|
|
252
|
+
continue;
|
|
253
|
+
try {
|
|
254
|
+
const obj = JSON.parse(line);
|
|
255
|
+
const tur = obj.toolUseResult;
|
|
256
|
+
if (tur && typeof tur === 'object' && tur.agentId) {
|
|
257
|
+
const id = tur.agentId;
|
|
258
|
+
if (seenIds.has(id))
|
|
259
|
+
continue;
|
|
260
|
+
seenIds.add(id);
|
|
261
|
+
const agentFile = join(projectsDir, `agent-${id}.jsonl`);
|
|
262
|
+
agents.push({
|
|
263
|
+
agentId: id,
|
|
264
|
+
description: (tur.prompt || '').substring(0, 200),
|
|
265
|
+
status: tur.status || '',
|
|
266
|
+
agentFile,
|
|
267
|
+
agentFileExists: existsSync(agentFile),
|
|
268
|
+
totalTokens: tur.totalTokens || 0,
|
|
269
|
+
totalToolUseCount: tur.totalToolUseCount || 0,
|
|
270
|
+
durationMs: tur.totalDurationMs || 0,
|
|
271
|
+
});
|
|
272
|
+
}
|
|
273
|
+
}
|
|
274
|
+
catch { }
|
|
275
|
+
}
|
|
276
|
+
}
|
|
277
|
+
catch { }
|
|
278
|
+
return agents;
|
|
279
|
+
}
|
|
280
|
+
/**
|
|
281
|
+
* Get all searchable file paths for a session — main JSONL + all sub-agent JSOLs.
|
|
282
|
+
* This is what the pipeline fast brain should ripgrep across.
|
|
283
|
+
*/
|
|
284
|
+
export function getSessionSearchPaths(sessionId, projectDir, opts) {
|
|
285
|
+
const paths = getSessionPaths(sessionId, projectDir, opts);
|
|
286
|
+
const files = [];
|
|
287
|
+
// Main conversation
|
|
288
|
+
if (existsSync(paths.conversation)) {
|
|
289
|
+
files.push(paths.conversation);
|
|
290
|
+
}
|
|
291
|
+
// Sub-agents from session subdirectory (Osborn agent SDK path)
|
|
292
|
+
for (const f of paths.subagents) {
|
|
293
|
+
if (existsSync(f))
|
|
294
|
+
files.push(f);
|
|
295
|
+
}
|
|
296
|
+
// Sub-agents at project level (Claude Code CLI path)
|
|
297
|
+
const agents = getSessionSubAgents(sessionId, projectDir, opts);
|
|
298
|
+
for (const a of agents) {
|
|
299
|
+
if (a.agentFileExists && !files.includes(a.agentFile)) {
|
|
300
|
+
files.push(a.agentFile);
|
|
301
|
+
}
|
|
302
|
+
}
|
|
303
|
+
return files;
|
|
304
|
+
}
|
|
231
305
|
// ============================================================
|
|
232
306
|
// JSONL PARSING
|
|
233
307
|
// ============================================================
|
|
@@ -530,13 +604,15 @@ export function getSessionPlan(sessionId, projectDir, opts) {
|
|
|
530
604
|
* Get recent tool use/result pairs from a session.
|
|
531
605
|
* Returns matched pairs of (tool_use → tool_result) in chronological order.
|
|
532
606
|
*
|
|
533
|
-
* @param lastN - Number of recent pairs to return (default: 10)
|
|
607
|
+
* @param lastN - Number of recent pairs to return (default: 10, 0 = all)
|
|
608
|
+
* @param opts.toolNameFilter - Optional: only return results from these tool names (e.g., ['Read', 'WebSearch'])
|
|
534
609
|
*/
|
|
535
610
|
export function getRecentToolResults(sessionId, projectDir, lastN = 10, opts) {
|
|
536
611
|
const messages = readSessionHistory(sessionId, projectDir, { claudeDir: opts?.claudeDir });
|
|
537
612
|
// Build a map of tool_use by tool ID
|
|
538
613
|
const toolUseMap = new Map();
|
|
539
614
|
const results = [];
|
|
615
|
+
const toolFilter = opts?.toolNameFilter?.map(t => t.toLowerCase());
|
|
540
616
|
for (const msg of messages) {
|
|
541
617
|
if (msg.type === 'tool_use' && msg.toolId) {
|
|
542
618
|
toolUseMap.set(msg.toolId, msg);
|
|
@@ -544,6 +620,10 @@ export function getRecentToolResults(sessionId, projectDir, lastN = 10, opts) {
|
|
|
544
620
|
if (msg.type === 'tool_result' && msg.toolUseId) {
|
|
545
621
|
const toolUse = toolUseMap.get(msg.toolUseId);
|
|
546
622
|
if (toolUse) {
|
|
623
|
+
// Apply tool name filter if provided
|
|
624
|
+
if (toolFilter && !toolFilter.includes(toolUse.toolName.toLowerCase())) {
|
|
625
|
+
continue;
|
|
626
|
+
}
|
|
547
627
|
results.push({
|
|
548
628
|
toolName: toolUse.toolName,
|
|
549
629
|
toolId: toolUse.toolId,
|
|
@@ -555,7 +635,7 @@ export function getRecentToolResults(sessionId, projectDir, lastN = 10, opts) {
|
|
|
555
635
|
}
|
|
556
636
|
}
|
|
557
637
|
}
|
|
558
|
-
return results.slice(-lastN);
|
|
638
|
+
return lastN > 0 ? results.slice(-lastN) : results;
|
|
559
639
|
}
|
|
560
640
|
/**
|
|
561
641
|
* Watch a session JSONL file for new entries.
|
|
@@ -648,6 +728,96 @@ export function getConversationText(sessionId, projectDir, lastN = 30, maxCharsP
|
|
|
648
728
|
}));
|
|
649
729
|
return exchanges.slice(-lastN);
|
|
650
730
|
}
|
|
731
|
+
/**
|
|
732
|
+
* Search the session JSONL for entries matching a keyword (case-insensitive).
|
|
733
|
+
* Searches across text, toolResultContent, toolName, and toolInput.
|
|
734
|
+
* Returns matching entries with 500-char excerpts around the match.
|
|
735
|
+
*
|
|
736
|
+
* @param keyword - The search keyword (case-insensitive)
|
|
737
|
+
* @param opts.maxResults - Maximum number of results to return (default: 20)
|
|
738
|
+
*/
|
|
739
|
+
export function searchSessionJsonl(sessionId, projectDir, keyword, opts) {
|
|
740
|
+
const messages = readSessionHistory(sessionId, projectDir, { claudeDir: opts?.claudeDir });
|
|
741
|
+
const maxResults = opts?.maxResults || 20;
|
|
742
|
+
const results = [];
|
|
743
|
+
const lowerKeyword = keyword.toLowerCase();
|
|
744
|
+
for (const msg of messages) {
|
|
745
|
+
if (results.length >= maxResults)
|
|
746
|
+
break;
|
|
747
|
+
// Search in text content
|
|
748
|
+
if (msg.text && msg.text.toLowerCase().includes(lowerKeyword)) {
|
|
749
|
+
const idx = msg.text.toLowerCase().indexOf(lowerKeyword);
|
|
750
|
+
const start = Math.max(0, idx - 100);
|
|
751
|
+
const end = Math.min(msg.text.length, idx + keyword.length + 400);
|
|
752
|
+
const excerpt = (start > 0 ? '...' : '') + msg.text.substring(start, end) + (end < msg.text.length ? '...' : '');
|
|
753
|
+
results.push({ type: msg.type, text: excerpt, timestamp: msg.timestamp });
|
|
754
|
+
continue;
|
|
755
|
+
}
|
|
756
|
+
// Search in tool result content
|
|
757
|
+
if (msg.toolResultContent && msg.toolResultContent.toLowerCase().includes(lowerKeyword)) {
|
|
758
|
+
const idx = msg.toolResultContent.toLowerCase().indexOf(lowerKeyword);
|
|
759
|
+
const start = Math.max(0, idx - 100);
|
|
760
|
+
const end = Math.min(msg.toolResultContent.length, idx + keyword.length + 400);
|
|
761
|
+
const excerpt = `[tool_result] ` + (start > 0 ? '...' : '') + msg.toolResultContent.substring(start, end) + (end < msg.toolResultContent.length ? '...' : '');
|
|
762
|
+
results.push({ type: msg.type, text: excerpt, timestamp: msg.timestamp });
|
|
763
|
+
continue;
|
|
764
|
+
}
|
|
765
|
+
// Search in tool name
|
|
766
|
+
if (msg.toolName && msg.toolName.toLowerCase().includes(lowerKeyword)) {
|
|
767
|
+
const inputPreview = msg.toolInput ? JSON.stringify(msg.toolInput).substring(0, 200) : '';
|
|
768
|
+
results.push({ type: msg.type, text: `[${msg.toolName}: ${inputPreview}]`, timestamp: msg.timestamp });
|
|
769
|
+
continue;
|
|
770
|
+
}
|
|
771
|
+
// Search in tool input
|
|
772
|
+
if (msg.toolInput) {
|
|
773
|
+
const inputStr = JSON.stringify(msg.toolInput);
|
|
774
|
+
if (inputStr.toLowerCase().includes(lowerKeyword)) {
|
|
775
|
+
results.push({ type: msg.type, text: `[${msg.toolName || 'tool'}: ${inputStr.substring(0, 500)}]`, timestamp: msg.timestamp });
|
|
776
|
+
}
|
|
777
|
+
}
|
|
778
|
+
}
|
|
779
|
+
return results;
|
|
780
|
+
}
|
|
781
|
+
/**
|
|
782
|
+
* Get session stats: message counts, tool usage breakdown, data sizes.
|
|
783
|
+
* Helps the fast brain decide how much data to read and which tools to query.
|
|
784
|
+
*/
|
|
785
|
+
export function getSessionStats(sessionId, projectDir, opts) {
|
|
786
|
+
const paths = getSessionPaths(sessionId, projectDir, opts);
|
|
787
|
+
if (!paths.exists)
|
|
788
|
+
return null;
|
|
789
|
+
const messages = readJsonl(paths.conversation);
|
|
790
|
+
const toolBreakdown = {};
|
|
791
|
+
let userMessages = 0;
|
|
792
|
+
let assistantMessages = 0;
|
|
793
|
+
let toolUseCount = 0;
|
|
794
|
+
let toolResultCount = 0;
|
|
795
|
+
for (const msg of messages) {
|
|
796
|
+
if (msg.type === 'user')
|
|
797
|
+
userMessages++;
|
|
798
|
+
else if (msg.type === 'assistant')
|
|
799
|
+
assistantMessages++;
|
|
800
|
+
else if (msg.type === 'tool_use') {
|
|
801
|
+
toolUseCount++;
|
|
802
|
+
const name = msg.toolName || 'unknown';
|
|
803
|
+
toolBreakdown[name] = (toolBreakdown[name] || 0) + 1;
|
|
804
|
+
}
|
|
805
|
+
else if (msg.type === 'tool_result')
|
|
806
|
+
toolResultCount++;
|
|
807
|
+
}
|
|
808
|
+
return {
|
|
809
|
+
totalMessages: messages.length,
|
|
810
|
+
userMessages,
|
|
811
|
+
assistantMessages,
|
|
812
|
+
toolUseCount,
|
|
813
|
+
toolResultCount,
|
|
814
|
+
toolBreakdown,
|
|
815
|
+
subagentCount: paths.subagents.length,
|
|
816
|
+
fileSizeBytes: existsSync(paths.conversation) ? statSync(paths.conversation).size : 0,
|
|
817
|
+
firstTimestamp: messages.find(m => m.timestamp)?.timestamp,
|
|
818
|
+
lastTimestamp: [...messages].reverse().find(m => m.timestamp)?.timestamp,
|
|
819
|
+
};
|
|
820
|
+
}
|
|
651
821
|
/**
|
|
652
822
|
* Get a quick summary of a session: slug, message count, timestamps, tools used.
|
|
653
823
|
*/
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* summary-index.ts — Builds a compact searchable summary of Claude JSONL sessions
|
|
3
|
+
*
|
|
4
|
+
* Instead of ripgrepping 80MB raw JSONL, we extract one-line summaries per message
|
|
5
|
+
* into a ~1MB plain text file. Ripgrep searches this in <5ms.
|
|
6
|
+
*
|
|
7
|
+
* Format: {lineNum}|{timestamp}|{source}|{msgType}|{summary}
|
|
8
|
+
*
|
|
9
|
+
* No LLM calls — pure heuristic extraction:
|
|
10
|
+
* tool_use → tool name + key params (file path, command, query)
|
|
11
|
+
* tool_result → tool name + first 80 chars of output
|
|
12
|
+
* user → raw text (already short from voice)
|
|
13
|
+
* assistant → first 500 chars of text
|
|
14
|
+
*
|
|
15
|
+
* Per-session index stored at: .osborn/sessions/{sessionId}/.index/search-index.txt
|
|
16
|
+
*/
|
|
17
|
+
export interface IndexEntry {
|
|
18
|
+
lineNum: number;
|
|
19
|
+
byteOffset: number;
|
|
20
|
+
timestamp: string;
|
|
21
|
+
source: string;
|
|
22
|
+
msgType: string;
|
|
23
|
+
summary: string;
|
|
24
|
+
}
|
|
25
|
+
export interface SummaryIndexState {
|
|
26
|
+
indexPath: string;
|
|
27
|
+
metaPath: string;
|
|
28
|
+
main: {
|
|
29
|
+
jsonlPath: string;
|
|
30
|
+
byteOffset: number;
|
|
31
|
+
lineCount: number;
|
|
32
|
+
indexLineCount: number;
|
|
33
|
+
};
|
|
34
|
+
subAgents: Map<string, {
|
|
35
|
+
jsonlPath: string;
|
|
36
|
+
byteOffset: number;
|
|
37
|
+
lineCount: number;
|
|
38
|
+
indexLineCount: number;
|
|
39
|
+
}>;
|
|
40
|
+
toolUseIdMap: Map<string, string>;
|
|
41
|
+
}
|
|
42
|
+
export interface SummaryIndexMeta {
|
|
43
|
+
version: 1;
|
|
44
|
+
sessionId: string;
|
|
45
|
+
createdAt: string;
|
|
46
|
+
updatedAt: string;
|
|
47
|
+
main: {
|
|
48
|
+
jsonlPath: string;
|
|
49
|
+
byteOffset: number;
|
|
50
|
+
lineCount: number;
|
|
51
|
+
indexLineCount: number;
|
|
52
|
+
};
|
|
53
|
+
subAgents: Record<string, {
|
|
54
|
+
jsonlPath: string;
|
|
55
|
+
byteOffset: number;
|
|
56
|
+
lineCount: number;
|
|
57
|
+
indexLineCount: number;
|
|
58
|
+
}>;
|
|
59
|
+
toolUseIdMap: Record<string, string>;
|
|
60
|
+
}
|
|
61
|
+
export interface IndexWatcher {
|
|
62
|
+
stop(): void;
|
|
63
|
+
state: SummaryIndexState;
|
|
64
|
+
}
|
|
65
|
+
/**
|
|
66
|
+
* Build or resume a summary index for a session.
|
|
67
|
+
* Reads main JSONL + all sub-agent JSONLs, extracts summaries.
|
|
68
|
+
* If an existing index with metadata exists, resumes from last byte offset.
|
|
69
|
+
*/
|
|
70
|
+
export declare function buildSummaryIndex(sessionId: string, workingDir: string, sessionBaseDir: string, onProgress?: (msg: string) => void): SummaryIndexState;
|
|
71
|
+
/**
|
|
72
|
+
* Poll-based incremental index updater (10s interval).
|
|
73
|
+
* Checks main JSONL + sub-agents for new content, indexes in one batch.
|
|
74
|
+
* No fs.watch — avoids race conditions with concurrent writers.
|
|
75
|
+
*/
|
|
76
|
+
export declare function startIndexWatcher(sessionId: string, workingDir: string, sessionBaseDir: string, state: SummaryIndexState): IndexWatcher;
|
|
77
|
+
export declare function getIndexPath(sessionId: string, sessionBaseDir: string): string | null;
|
|
78
|
+
/**
|
|
79
|
+
* Given index search results (with byte offsets + source tags),
|
|
80
|
+
* read FULL content from raw JSONL via targeted reads — 0.5ms per result.
|
|
81
|
+
* No readFileSync of the whole file. Strips JSON noise, returns clean text.
|
|
82
|
+
*/
|
|
83
|
+
export declare function readFullContent(results: {
|
|
84
|
+
lineNum: number;
|
|
85
|
+
byteOffset: number;
|
|
86
|
+
source: string;
|
|
87
|
+
}[], sessionId: string, workingDir: string, sessionBaseDir: string, maxCharsPerResult?: number): string[];
|