indusagi-coding-agent 0.1.23 → 0.1.24
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/CHANGELOG.md +65 -0
- package/README.md +2 -0
- package/dist/cli/args.d.ts +117 -1
- package/dist/cli/args.d.ts.map +1 -1
- package/dist/cli/args.js +221 -52
- package/dist/cli/args.js.map +1 -1
- package/dist/cli/config-selector.d.ts +58 -2
- package/dist/cli/config-selector.d.ts.map +1 -1
- package/dist/cli/config-selector.js +130 -12
- package/dist/cli/config-selector.js.map +1 -1
- package/dist/cli/file-processor.d.ts +70 -2
- package/dist/cli/file-processor.d.ts.map +1 -1
- package/dist/cli/file-processor.js +240 -15
- package/dist/cli/file-processor.js.map +1 -1
- package/dist/cli/list-models.d.ts +63 -3
- package/dist/cli/list-models.d.ts.map +1 -1
- package/dist/cli/list-models.js +202 -27
- package/dist/cli/list-models.js.map +1 -1
- package/dist/cli/login-handler.d.ts +82 -8
- package/dist/cli/login-handler.d.ts.map +1 -1
- package/dist/cli/login-handler.js +410 -77
- package/dist/cli/login-handler.js.map +1 -1
- package/dist/cli/session-picker.d.ts +74 -2
- package/dist/cli/session-picker.d.ts.map +1 -1
- package/dist/cli/session-picker.js +236 -12
- package/dist/cli/session-picker.js.map +1 -1
- package/dist/core/agent-session.d.ts +214 -9
- package/dist/core/agent-session.d.ts.map +1 -1
- package/dist/core/agent-session.js +214 -9
- package/dist/core/agent-session.js.map +1 -1
- package/dist/core/bash-executor.d.ts +302 -12
- package/dist/core/bash-executor.d.ts.map +1 -1
- package/dist/core/bash-executor.js +302 -12
- package/dist/core/bash-executor.js.map +1 -1
- package/dist/core/diagnostics.d.ts +191 -0
- package/dist/core/diagnostics.d.ts.map +1 -1
- package/dist/core/diagnostics.js +142 -0
- package/dist/core/diagnostics.js.map +1 -1
- package/dist/core/event-bus.d.ts +146 -0
- package/dist/core/event-bus.d.ts.map +1 -1
- package/dist/core/event-bus.js +93 -0
- package/dist/core/event-bus.js.map +1 -1
- package/dist/core/export-html/ansi-to-html.d.ts +4 -0
- package/dist/core/export-html/ansi-to-html.d.ts.map +1 -1
- package/dist/core/export-html/ansi-to-html.js +4 -0
- package/dist/core/export-html/ansi-to-html.js.map +1 -1
- package/dist/core/export-html/index.d.ts +128 -0
- package/dist/core/export-html/index.d.ts.map +1 -1
- package/dist/core/export-html/index.js +128 -0
- package/dist/core/export-html/index.js.map +1 -1
- package/dist/core/export-html/tool-renderer.d.ts +4 -0
- package/dist/core/export-html/tool-renderer.d.ts.map +1 -1
- package/dist/core/export-html/tool-renderer.js +4 -0
- package/dist/core/export-html/tool-renderer.js.map +1 -1
- package/dist/core/keybindings.d.ts +142 -0
- package/dist/core/keybindings.d.ts.map +1 -1
- package/dist/core/keybindings.js +142 -0
- package/dist/core/keybindings.js.map +1 -1
- package/dist/core/model-registry.d.ts +98 -1
- package/dist/core/model-registry.d.ts.map +1 -1
- package/dist/core/model-registry.js +98 -1
- package/dist/core/model-registry.js.map +1 -1
- package/dist/core/model-resolver.d.ts +99 -1
- package/dist/core/model-resolver.d.ts.map +1 -1
- package/dist/core/model-resolver.js +99 -1
- package/dist/core/model-resolver.js.map +1 -1
- package/dist/core/prompt-templates.js.map +1 -1
- package/dist/core/session-manager.d.ts +127 -0
- package/dist/core/session-manager.d.ts.map +1 -1
- package/dist/core/session-manager.js +125 -0
- package/dist/core/session-manager.js.map +1 -1
- package/dist/core/skills.js.map +1 -1
- package/dist/core/subagents.js.map +1 -1
- package/dist/core/tools/bash.d.ts +391 -11
- package/dist/core/tools/bash.d.ts.map +1 -1
- package/dist/core/tools/bash.js +269 -2
- package/dist/core/tools/bash.js.map +1 -1
- package/dist/core/tools/edit.d.ts +284 -6
- package/dist/core/tools/edit.d.ts.map +1 -1
- package/dist/core/tools/edit.js +238 -0
- package/dist/core/tools/edit.js.map +1 -1
- package/dist/core/tools/find.d.ts +169 -5
- package/dist/core/tools/find.d.ts.map +1 -1
- package/dist/core/tools/find.js +136 -0
- package/dist/core/tools/find.js.map +1 -1
- package/dist/core/tools/grep.d.ts +285 -5
- package/dist/core/tools/grep.d.ts.map +1 -1
- package/dist/core/tools/grep.js +247 -0
- package/dist/core/tools/grep.js.map +1 -1
- package/dist/core/tools/ls.d.ts +6 -0
- package/dist/core/tools/ls.d.ts.map +1 -1
- package/dist/core/tools/ls.js +6 -0
- package/dist/core/tools/ls.js.map +1 -1
- package/dist/core/tools/read.d.ts +308 -7
- package/dist/core/tools/read.d.ts.map +1 -1
- package/dist/core/tools/read.js +231 -0
- package/dist/core/tools/read.js.map +1 -1
- package/dist/core/tools/webfetch.d.ts +118 -3
- package/dist/core/tools/webfetch.d.ts.map +1 -1
- package/dist/core/tools/webfetch.js +118 -3
- package/dist/core/tools/webfetch.js.map +1 -1
- package/dist/core/tools/websearch.d.ts +130 -3
- package/dist/core/tools/websearch.d.ts.map +1 -1
- package/dist/core/tools/websearch.js +130 -3
- package/dist/core/tools/websearch.js.map +1 -1
- package/dist/core/tools/write.d.ts +251 -5
- package/dist/core/tools/write.d.ts.map +1 -1
- package/dist/core/tools/write.js +210 -0
- package/dist/core/tools/write.js.map +1 -1
- package/dist/modes/interactive/components/assistant-message.d.ts +164 -1
- package/dist/modes/interactive/components/assistant-message.d.ts.map +1 -1
- package/dist/modes/interactive/components/assistant-message.js +164 -1
- package/dist/modes/interactive/components/assistant-message.js.map +1 -1
- package/dist/modes/interactive/components/bash-execution.d.ts +297 -1
- package/dist/modes/interactive/components/bash-execution.d.ts.map +1 -1
- package/dist/modes/interactive/components/bash-execution.js +297 -1
- package/dist/modes/interactive/components/bash-execution.js.map +1 -1
- package/dist/modes/interactive/components/tool-execution.d.ts.map +1 -1
- package/dist/modes/interactive/components/tool-execution.js +251 -1
- package/dist/modes/interactive/components/tool-execution.js.map +1 -1
- package/dist/modes/interactive/components/user-message.d.ts +186 -1
- package/dist/modes/interactive/components/user-message.d.ts.map +1 -1
- package/dist/modes/interactive/components/user-message.js +186 -1
- package/dist/modes/interactive/components/user-message.js.map +1 -1
- package/dist/modes/interactive/interactive-mode.d.ts +1567 -13
- package/dist/modes/interactive/interactive-mode.d.ts.map +1 -1
- package/dist/modes/interactive/interactive-mode.js +1567 -13
- package/dist/modes/interactive/interactive-mode.js.map +1 -1
- package/dist/modes/interactive/theme/theme.d.ts +422 -0
- package/dist/modes/interactive/theme/theme.d.ts.map +1 -1
- package/dist/modes/interactive/theme/theme.js +422 -0
- package/dist/modes/interactive/theme/theme.js.map +1 -1
- package/dist/modes/print-mode.d.ts +538 -5
- package/dist/modes/print-mode.d.ts.map +1 -1
- package/dist/modes/print-mode.js +538 -5
- package/dist/modes/print-mode.js.map +1 -1
- package/dist/modes/rpc/rpc-client.d.ts +921 -8
- package/dist/modes/rpc/rpc-client.d.ts.map +1 -1
- package/dist/modes/rpc/rpc-client.js +921 -8
- package/dist/modes/rpc/rpc-client.js.map +1 -1
- package/dist/modes/rpc/rpc-mode.d.ts +802 -9
- package/dist/modes/rpc/rpc-mode.d.ts.map +1 -1
- package/dist/modes/rpc/rpc-mode.js +802 -9
- package/dist/modes/rpc/rpc-mode.js.map +1 -1
- package/dist/modes/rpc/rpc-types.d.ts +356 -3
- package/dist/modes/rpc/rpc-types.d.ts.map +1 -1
- package/dist/modes/rpc/rpc-types.js +356 -3
- package/dist/modes/rpc/rpc-types.js.map +1 -1
- package/dist/modes/shared.d.ts +386 -0
- package/dist/modes/shared.d.ts.map +1 -0
- package/dist/modes/shared.js +543 -0
- package/dist/modes/shared.js.map +1 -0
- package/dist/utils/array.d.ts +389 -0
- package/dist/utils/array.d.ts.map +1 -0
- package/dist/utils/array.js +585 -0
- package/dist/utils/array.js.map +1 -0
- package/dist/utils/color-formatter.d.ts +318 -0
- package/dist/utils/color-formatter.d.ts.map +1 -0
- package/dist/utils/color-formatter.js +442 -0
- package/dist/utils/color-formatter.js.map +1 -0
- package/dist/utils/data-transformer.d.ts +326 -0
- package/dist/utils/data-transformer.d.ts.map +1 -0
- package/dist/utils/data-transformer.js +512 -0
- package/dist/utils/data-transformer.js.map +1 -0
- package/dist/utils/date-formatter.d.ts +281 -0
- package/dist/utils/date-formatter.d.ts.map +1 -0
- package/dist/utils/date-formatter.js +503 -0
- package/dist/utils/date-formatter.js.map +1 -0
- package/dist/utils/error-handler.d.ts +541 -0
- package/dist/utils/error-handler.d.ts.map +1 -0
- package/dist/utils/error-handler.js +726 -0
- package/dist/utils/error-handler.js.map +1 -0
- package/dist/utils/file-operations.d.ts +297 -0
- package/dist/utils/file-operations.d.ts.map +1 -0
- package/dist/utils/file-operations.js +505 -0
- package/dist/utils/file-operations.js.map +1 -0
- package/dist/utils/frontmatter.d.ts +268 -6
- package/dist/utils/frontmatter.d.ts.map +1 -1
- package/dist/utils/frontmatter.js +500 -21
- package/dist/utils/frontmatter.js.map +1 -1
- package/dist/utils/json-formatter.d.ts +259 -0
- package/dist/utils/json-formatter.d.ts.map +1 -0
- package/dist/utils/json-formatter.js +517 -0
- package/dist/utils/json-formatter.js.map +1 -0
- package/dist/utils/logger.d.ts +176 -0
- package/dist/utils/logger.d.ts.map +1 -0
- package/dist/utils/logger.js +346 -0
- package/dist/utils/logger.js.map +1 -0
- package/dist/utils/markdown-formatter.d.ts +211 -0
- package/dist/utils/markdown-formatter.d.ts.map +1 -0
- package/dist/utils/markdown-formatter.js +482 -0
- package/dist/utils/markdown-formatter.js.map +1 -0
- package/dist/utils/path-validator.d.ts +603 -0
- package/dist/utils/path-validator.d.ts.map +1 -0
- package/dist/utils/path-validator.js +870 -0
- package/dist/utils/path-validator.js.map +1 -0
- package/dist/utils/string-formatter.d.ts +609 -0
- package/dist/utils/string-formatter.d.ts.map +1 -0
- package/dist/utils/string-formatter.js +806 -0
- package/dist/utils/string-formatter.js.map +1 -0
- package/dist/utils/type-guards.d.ts +629 -0
- package/dist/utils/type-guards.d.ts.map +1 -0
- package/dist/utils/type-guards.js +662 -0
- package/dist/utils/type-guards.js.map +1 -0
- package/docs/COMPLETE-GUIDE.md +300 -0
- package/docs/MODES-ARCHITECTURE.md +565 -0
- package/docs/PRINT-MODE-GUIDE.md +456 -0
- package/docs/RPC-GUIDE.md +705 -0
- package/docs/UTILS-IMPLEMENTATION-SUMMARY.md +647 -0
- package/docs/UTILS-MODULE-OVERVIEW.md +1480 -0
- package/docs/UTILS-QA-CHECKLIST.md +1061 -0
- package/docs/UTILS-USAGE-GUIDE.md +1419 -0
- package/package.json +1 -1
|
@@ -0,0 +1,543 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared Utilities for All Execution Modes
|
|
3
|
+
*
|
|
4
|
+
* This module provides common utilities, validators, and formatters used across all three
|
|
5
|
+
* execution modes (interactive, print, RPC).
|
|
6
|
+
*
|
|
7
|
+
* Purpose:
|
|
8
|
+
* --------
|
|
9
|
+
* - Centralize common functionality to avoid duplication
|
|
10
|
+
* - Ensure consistent behavior across modes
|
|
11
|
+
* - Provide standard data transformation and validation
|
|
12
|
+
*
|
|
13
|
+
* Usage by Modes:
|
|
14
|
+
* ---------------
|
|
15
|
+
* INTERACTIVE MODE:
|
|
16
|
+
* - Uses formatDuration for displaying execution times
|
|
17
|
+
* - Uses validatePrompt for user input validation
|
|
18
|
+
* - Uses extractSessionId for session switching
|
|
19
|
+
*
|
|
20
|
+
* PRINT MODE:
|
|
21
|
+
* - Uses createOutputFormatter to format results as JSON/text
|
|
22
|
+
* - Uses escapeJsonString for JSON output
|
|
23
|
+
* - Uses formatErrorMessage for error reporting
|
|
24
|
+
*
|
|
25
|
+
* RPC MODE:
|
|
26
|
+
* - Uses parseSessionPath for session resolution
|
|
27
|
+
* - Uses validatePrompt for incoming RPC requests
|
|
28
|
+
* - Uses escapeJsonString for JSON-RPC responses
|
|
29
|
+
*
|
|
30
|
+
* Architecture:
|
|
31
|
+
* -------------
|
|
32
|
+
* This module acts as a utility facade, providing a single source of truth for:
|
|
33
|
+
* 1. Data transformation (format functions)
|
|
34
|
+
* 2. Input validation (validate functions)
|
|
35
|
+
* 3. Error handling (error formatting)
|
|
36
|
+
* 4. Conversion utilities (token counts, durations)
|
|
37
|
+
*
|
|
38
|
+
* All functions are pure (no side effects) and stateless for maximum reusability.
|
|
39
|
+
*/
|
|
40
|
+
/**
|
|
41
|
+
* Create an output formatter for a specific format type
|
|
42
|
+
*
|
|
43
|
+
* Factory function that returns a formatter implementing the OutputFormatter interface.
|
|
44
|
+
* Each formatter knows how to convert data to its target output format.
|
|
45
|
+
*
|
|
46
|
+
* Formats:
|
|
47
|
+
* - 'json': Outputs JSON lines (each event as a JSON object)
|
|
48
|
+
* - 'text': Outputs human-readable text with formatting
|
|
49
|
+
* - 'compact': Outputs minimal status information
|
|
50
|
+
*
|
|
51
|
+
* Usage:
|
|
52
|
+
* ------
|
|
53
|
+
* PRINT MODE:
|
|
54
|
+
* const formatter = createOutputFormatter('json');
|
|
55
|
+
* console.log(formatter.format(agentResponse));
|
|
56
|
+
* console.error(formatter.formatError(error));
|
|
57
|
+
*
|
|
58
|
+
* @param format - Output format type ('json' | 'text' | 'compact')
|
|
59
|
+
* @returns OutputFormatter instance for the specified format
|
|
60
|
+
*
|
|
61
|
+
* @example
|
|
62
|
+
* // JSON output for event streaming
|
|
63
|
+
* const jsonFormatter = createOutputFormatter('json');
|
|
64
|
+
* process.stdout.write(jsonFormatter.format(event));
|
|
65
|
+
*
|
|
66
|
+
* @example
|
|
67
|
+
* // Text output for human readers
|
|
68
|
+
* const textFormatter = createOutputFormatter('text');
|
|
69
|
+
* process.stdout.write(textFormatter.format(response));
|
|
70
|
+
*
|
|
71
|
+
* @throws Error if format is not recognized
|
|
72
|
+
*/
|
|
73
|
+
export function createOutputFormatter(format) {
|
|
74
|
+
switch (format) {
|
|
75
|
+
case 'json':
|
|
76
|
+
return new JsonFormatter();
|
|
77
|
+
case 'text':
|
|
78
|
+
return new TextFormatter();
|
|
79
|
+
case 'compact':
|
|
80
|
+
return new CompactFormatter();
|
|
81
|
+
default:
|
|
82
|
+
throw new Error(`Unknown output format: ${format}`);
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
/**
|
|
86
|
+
* JSON output formatter - Machine-readable JSON lines format
|
|
87
|
+
* @internal
|
|
88
|
+
*/
|
|
89
|
+
class JsonFormatter {
|
|
90
|
+
format(data) {
|
|
91
|
+
return JSON.stringify(data) + '\n';
|
|
92
|
+
}
|
|
93
|
+
formatError(error) {
|
|
94
|
+
return JSON.stringify({
|
|
95
|
+
type: 'error',
|
|
96
|
+
message: error.message,
|
|
97
|
+
code: error.code,
|
|
98
|
+
stack: process.env.DEBUG ? error.stack : undefined,
|
|
99
|
+
}) + '\n';
|
|
100
|
+
}
|
|
101
|
+
getContentType() {
|
|
102
|
+
return 'application/x-ndjson';
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
/**
|
|
106
|
+
* Text output formatter - Human-readable text format
|
|
107
|
+
* @internal
|
|
108
|
+
*/
|
|
109
|
+
class TextFormatter {
|
|
110
|
+
format(data) {
|
|
111
|
+
if (typeof data === 'string')
|
|
112
|
+
return data + '\n';
|
|
113
|
+
if (typeof data === 'object')
|
|
114
|
+
return JSON.stringify(data, null, 2) + '\n';
|
|
115
|
+
return String(data) + '\n';
|
|
116
|
+
}
|
|
117
|
+
formatError(error) {
|
|
118
|
+
return `ERROR: ${error.message}\n`;
|
|
119
|
+
}
|
|
120
|
+
getContentType() {
|
|
121
|
+
return 'text/plain';
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
/**
|
|
125
|
+
* Compact output formatter - Minimal status output
|
|
126
|
+
* @internal
|
|
127
|
+
*/
|
|
128
|
+
class CompactFormatter {
|
|
129
|
+
format(data) {
|
|
130
|
+
if (typeof data === 'string')
|
|
131
|
+
return data;
|
|
132
|
+
if (typeof data === 'object' && data !== null && 'message' in data) {
|
|
133
|
+
return data.message;
|
|
134
|
+
}
|
|
135
|
+
return String(data);
|
|
136
|
+
}
|
|
137
|
+
formatError(error) {
|
|
138
|
+
return `ERROR: ${error.message}`;
|
|
139
|
+
}
|
|
140
|
+
getContentType() {
|
|
141
|
+
return 'text/plain';
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
/**
|
|
145
|
+
* Parse and validate a session path/ID
|
|
146
|
+
*
|
|
147
|
+
* Extracts and validates session identifiers. Supports multiple formats:
|
|
148
|
+
* - UUID: "550e8400-e29b-41d4-a716-446655440000"
|
|
149
|
+
* - Filename: "session-123.jsonl"
|
|
150
|
+
* - Path: "/home/user/.indusagi/sessions/session-123.jsonl"
|
|
151
|
+
*
|
|
152
|
+
* Returns parsed session ID or throws ValidationError if invalid.
|
|
153
|
+
*
|
|
154
|
+
* Usage:
|
|
155
|
+
* ------
|
|
156
|
+
* RPC MODE:
|
|
157
|
+
* const sessionId = parseSessionPath(request.params.sessionId);
|
|
158
|
+
* const session = sessionManager.load(sessionId);
|
|
159
|
+
*
|
|
160
|
+
* INTERACTIVE MODE:
|
|
161
|
+
* const sessionId = parseSessionPath(userInput);
|
|
162
|
+
* // Used in session switching command
|
|
163
|
+
*
|
|
164
|
+
* @param path - Session ID, filename, or filesystem path
|
|
165
|
+
* @returns Normalized session UUID
|
|
166
|
+
*
|
|
167
|
+
* @example
|
|
168
|
+
* parseSessionPath('550e8400-e29b-41d4-a716-446655440000')
|
|
169
|
+
* // Returns: '550e8400-e29b-41d4-a716-446655440000'
|
|
170
|
+
*
|
|
171
|
+
* @example
|
|
172
|
+
* parseSessionPath('session-123.jsonl')
|
|
173
|
+
* // Returns: 'session-123' (extracts ID from filename)
|
|
174
|
+
*
|
|
175
|
+
* @throws Error if path is empty or invalid format
|
|
176
|
+
*/
|
|
177
|
+
export function parseSessionPath(path) {
|
|
178
|
+
if (!path || typeof path !== 'string') {
|
|
179
|
+
throw new Error('Session path must be a non-empty string');
|
|
180
|
+
}
|
|
181
|
+
// Remove file extensions if present
|
|
182
|
+
let sessionId = path.replace(/\.jsonl?$/, '');
|
|
183
|
+
// Extract from filesystem path
|
|
184
|
+
const match = sessionId.match(/([a-zA-Z0-9\-]+)$/);
|
|
185
|
+
if (match) {
|
|
186
|
+
sessionId = match[1];
|
|
187
|
+
}
|
|
188
|
+
// Validate format (UUID or session-id format)
|
|
189
|
+
if (!/^[a-zA-Z0-9\-]{20,}$/.test(sessionId)) {
|
|
190
|
+
throw new Error(`Invalid session ID format: ${sessionId}`);
|
|
191
|
+
}
|
|
192
|
+
return sessionId;
|
|
193
|
+
}
|
|
194
|
+
/**
|
|
195
|
+
* Validate user input/prompt
|
|
196
|
+
*
|
|
197
|
+
* Checks if a prompt is valid for sending to the agent.
|
|
198
|
+
*
|
|
199
|
+
* Validation rules:
|
|
200
|
+
* - Non-empty (after trimming whitespace)
|
|
201
|
+
* - No longer than 100,000 characters (prevents DOS)
|
|
202
|
+
* - Must be a string
|
|
203
|
+
*
|
|
204
|
+
* Returns ValidationResult with detailed error information if invalid.
|
|
205
|
+
*
|
|
206
|
+
* Usage:
|
|
207
|
+
* ------
|
|
208
|
+
* INTERACTIVE MODE:
|
|
209
|
+
* const result = validatePrompt(userInput);
|
|
210
|
+
* if (!result.valid) {
|
|
211
|
+
* showError(result.error);
|
|
212
|
+
* return;
|
|
213
|
+
* }
|
|
214
|
+
* session.prompt(userInput);
|
|
215
|
+
*
|
|
216
|
+
* RPC MODE:
|
|
217
|
+
* const result = validatePrompt(request.message);
|
|
218
|
+
* if (!result.valid) {
|
|
219
|
+
* return rpcError(-32602, result.error);
|
|
220
|
+
* }
|
|
221
|
+
*
|
|
222
|
+
* @param prompt - User input to validate
|
|
223
|
+
* @returns ValidationResult with valid flag and optional error message
|
|
224
|
+
*
|
|
225
|
+
* @example
|
|
226
|
+
* validatePrompt('What does this code do?')
|
|
227
|
+
* // Returns: { valid: true }
|
|
228
|
+
*
|
|
229
|
+
* @example
|
|
230
|
+
* validatePrompt(' ')
|
|
231
|
+
* // Returns: { valid: false, error: 'Prompt cannot be empty' }
|
|
232
|
+
*
|
|
233
|
+
* @example
|
|
234
|
+
* validatePrompt('x'.repeat(100001))
|
|
235
|
+
* // Returns: { valid: false, error: 'Prompt exceeds maximum length (100000)' }
|
|
236
|
+
*/
|
|
237
|
+
export function validatePrompt(prompt) {
|
|
238
|
+
if (typeof prompt !== 'string') {
|
|
239
|
+
return {
|
|
240
|
+
valid: false,
|
|
241
|
+
error: 'Prompt must be a string',
|
|
242
|
+
details: { received: typeof prompt },
|
|
243
|
+
};
|
|
244
|
+
}
|
|
245
|
+
const trimmed = prompt.trim();
|
|
246
|
+
if (trimmed.length === 0) {
|
|
247
|
+
return {
|
|
248
|
+
valid: false,
|
|
249
|
+
error: 'Prompt cannot be empty',
|
|
250
|
+
};
|
|
251
|
+
}
|
|
252
|
+
const MAX_LENGTH = 100000;
|
|
253
|
+
if (prompt.length > MAX_LENGTH) {
|
|
254
|
+
return {
|
|
255
|
+
valid: false,
|
|
256
|
+
error: `Prompt exceeds maximum length (${MAX_LENGTH})`,
|
|
257
|
+
details: { length: prompt.length, max: MAX_LENGTH },
|
|
258
|
+
};
|
|
259
|
+
}
|
|
260
|
+
return { valid: true };
|
|
261
|
+
}
|
|
262
|
+
/**
|
|
263
|
+
* Format milliseconds to human-readable duration string
|
|
264
|
+
*
|
|
265
|
+
* Converts milliseconds into a readable format like "1h 23m 45s 123ms".
|
|
266
|
+
* Omits zero values and units for brevity.
|
|
267
|
+
*
|
|
268
|
+
* Examples:
|
|
269
|
+
* - 1000 ms → "1s"
|
|
270
|
+
* - 61000 ms → "1m 1s"
|
|
271
|
+
* - 3661000 ms → "1h 1m 1s"
|
|
272
|
+
*
|
|
273
|
+
* Usage:
|
|
274
|
+
* ------
|
|
275
|
+
* INTERACTIVE MODE:
|
|
276
|
+
* const elapsed = Date.now() - startTime;
|
|
277
|
+
* footer.text = `Completed in ${formatDuration(elapsed)}`;
|
|
278
|
+
*
|
|
279
|
+
* PRINT MODE:
|
|
280
|
+
* console.log(`"elapsed_time": "${formatDuration(duration)}"`);
|
|
281
|
+
*
|
|
282
|
+
* @param ms - Duration in milliseconds
|
|
283
|
+
* @returns Formatted duration string
|
|
284
|
+
*
|
|
285
|
+
* @example
|
|
286
|
+
* formatDuration(1234567) // "20m 34s 567ms"
|
|
287
|
+
*
|
|
288
|
+
* @example
|
|
289
|
+
* formatDuration(5000) // "5s"
|
|
290
|
+
*
|
|
291
|
+
* @example
|
|
292
|
+
* formatDuration(0) // "0ms"
|
|
293
|
+
*/
|
|
294
|
+
export function formatDuration(ms) {
|
|
295
|
+
if (ms < 0)
|
|
296
|
+
return '0ms';
|
|
297
|
+
const units = [
|
|
298
|
+
{ name: 'h', ms: 3600000 },
|
|
299
|
+
{ name: 'm', ms: 60000 },
|
|
300
|
+
{ name: 's', ms: 1000 },
|
|
301
|
+
{ name: 'ms', ms: 1 },
|
|
302
|
+
];
|
|
303
|
+
const parts = [];
|
|
304
|
+
let remaining = ms;
|
|
305
|
+
for (const unit of units) {
|
|
306
|
+
if (remaining >= unit.ms) {
|
|
307
|
+
const value = Math.floor(remaining / unit.ms);
|
|
308
|
+
parts.push(`${value}${unit.name}`);
|
|
309
|
+
remaining %= unit.ms;
|
|
310
|
+
}
|
|
311
|
+
}
|
|
312
|
+
return parts.length > 0 ? parts.join(' ') : '0ms';
|
|
313
|
+
}
|
|
314
|
+
/**
|
|
315
|
+
* Format token count with usage estimates
|
|
316
|
+
*
|
|
317
|
+
* Converts a token count into a readable format with estimates of cost/usage:
|
|
318
|
+
* - Shows raw token count
|
|
319
|
+
* - Estimates word count (roughly 0.75 words per token)
|
|
320
|
+
* - Estimates cost at $0.002 per 1000 tokens (GPT-4 average)
|
|
321
|
+
*
|
|
322
|
+
* Useful for displaying resource usage in logs and UI.
|
|
323
|
+
*
|
|
324
|
+
* Usage:
|
|
325
|
+
* ------
|
|
326
|
+
* PRINT MODE:
|
|
327
|
+
* const formatted = formatTokens(response.usage.total_tokens);
|
|
328
|
+
* console.log(`Tokens: ${formatted}`);
|
|
329
|
+
*
|
|
330
|
+
* INTERACTIVE MODE:
|
|
331
|
+
* footer.text = `Tokens: ${formatTokens(totalTokens)}`;
|
|
332
|
+
*
|
|
333
|
+
* @param tokens - Number of tokens used
|
|
334
|
+
* @returns Formatted string with tokens, word estimate, and cost estimate
|
|
335
|
+
*
|
|
336
|
+
* @example
|
|
337
|
+
* formatTokens(1500)
|
|
338
|
+
* // Returns: "1,500 tokens (~1,125 words, ~$0.003 cost)"
|
|
339
|
+
*
|
|
340
|
+
* @example
|
|
341
|
+
* formatTokens(0)
|
|
342
|
+
* // Returns: "0 tokens"
|
|
343
|
+
*/
|
|
344
|
+
export function formatTokens(tokens) {
|
|
345
|
+
if (tokens === 0)
|
|
346
|
+
return '0 tokens';
|
|
347
|
+
const formatted = tokens.toLocaleString();
|
|
348
|
+
const wordEstimate = Math.round(tokens * 0.75);
|
|
349
|
+
const costEstimate = (tokens / 1000) * 0.002;
|
|
350
|
+
return `${formatted} tokens (~${wordEstimate.toLocaleString()} words, ~$${costEstimate.toFixed(3)} cost)`;
|
|
351
|
+
}
|
|
352
|
+
/**
|
|
353
|
+
* Extract session ID from user input
|
|
354
|
+
*
|
|
355
|
+
* Parses user input to extract a session ID. Handles multiple formats:
|
|
356
|
+
* - Direct UUID
|
|
357
|
+
* - Filenames with session ID
|
|
358
|
+
* - Prefixes like "session:uuid"
|
|
359
|
+
*
|
|
360
|
+
* Returns null if no valid session ID found.
|
|
361
|
+
*
|
|
362
|
+
* Usage:
|
|
363
|
+
* ------
|
|
364
|
+
* INTERACTIVE MODE:
|
|
365
|
+
* // User types: "/switch 550e8400-e29b-41d4-a716-446655440000"
|
|
366
|
+
* const sessionId = extractSessionId(userInput);
|
|
367
|
+
* if (sessionId) interactiveMode.switchSession(sessionId);
|
|
368
|
+
*
|
|
369
|
+
* @param input - User input string
|
|
370
|
+
* @returns Session ID if found, null otherwise
|
|
371
|
+
*
|
|
372
|
+
* @example
|
|
373
|
+
* extractSessionId('session:550e8400-e29b-41d4-a716-446655440000')
|
|
374
|
+
* // Returns: '550e8400-e29b-41d4-a716-446655440000'
|
|
375
|
+
*
|
|
376
|
+
* @example
|
|
377
|
+
* extractSessionId('/switch my-session-123')
|
|
378
|
+
* // Returns: 'my-session-123'
|
|
379
|
+
*
|
|
380
|
+
* @example
|
|
381
|
+
* extractSessionId('invalid input')
|
|
382
|
+
* // Returns: null
|
|
383
|
+
*/
|
|
384
|
+
export function extractSessionId(input) {
|
|
385
|
+
if (!input || typeof input !== 'string')
|
|
386
|
+
return null;
|
|
387
|
+
// Try to match UUID directly
|
|
388
|
+
const uuidMatch = input.match(/[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}/i);
|
|
389
|
+
if (uuidMatch)
|
|
390
|
+
return uuidMatch[0];
|
|
391
|
+
// Try to match session:id format
|
|
392
|
+
const prefixMatch = input.match(/session:([a-zA-Z0-9\-]+)/);
|
|
393
|
+
if (prefixMatch)
|
|
394
|
+
return prefixMatch[1];
|
|
395
|
+
// Try to match standalone session ID (alphanumeric with hyphens)
|
|
396
|
+
const idMatch = input.match(/^([a-zA-Z0-9\-]{20,})$/);
|
|
397
|
+
if (idMatch)
|
|
398
|
+
return idMatch[1];
|
|
399
|
+
return null;
|
|
400
|
+
}
|
|
401
|
+
/**
|
|
402
|
+
* Escape string for safe JSON output
|
|
403
|
+
*
|
|
404
|
+
* Properly escapes special characters for JSON strings:
|
|
405
|
+
* - Quotes: " → \"
|
|
406
|
+
* - Backslashes: \ → \\
|
|
407
|
+
* - Newlines: \n, \r, \t etc
|
|
408
|
+
* - Control characters
|
|
409
|
+
*
|
|
410
|
+
* Usage:
|
|
411
|
+
* ------
|
|
412
|
+
* PRINT MODE:
|
|
413
|
+
* const jsonLine = `{"message": "${escapeJsonString(message)}"}`;
|
|
414
|
+
* console.log(jsonLine);
|
|
415
|
+
*
|
|
416
|
+
* RPC MODE:
|
|
417
|
+
* const response = {
|
|
418
|
+
* message: escapeJsonString(plainText)
|
|
419
|
+
* };
|
|
420
|
+
* sendJsonRpc(response);
|
|
421
|
+
*
|
|
422
|
+
* @param str - String to escape
|
|
423
|
+
* @returns Escaped string safe for JSON output
|
|
424
|
+
*
|
|
425
|
+
* @example
|
|
426
|
+
* escapeJsonString('Hello "World"\n')
|
|
427
|
+
* // Returns: 'Hello \"World\"\\n'
|
|
428
|
+
*
|
|
429
|
+
* @example
|
|
430
|
+
* escapeJsonString('Path: C:\\Users\\test')
|
|
431
|
+
* // Returns: 'Path: C:\\\\Users\\\\test'
|
|
432
|
+
*/
|
|
433
|
+
export function escapeJsonString(str) {
|
|
434
|
+
if (typeof str !== 'string')
|
|
435
|
+
return '';
|
|
436
|
+
return str
|
|
437
|
+
.replace(/\\/g, '\\\\')
|
|
438
|
+
.replace(/"/g, '\\"')
|
|
439
|
+
.replace(/\n/g, '\\n')
|
|
440
|
+
.replace(/\r/g, '\\r')
|
|
441
|
+
.replace(/\t/g, '\\t')
|
|
442
|
+
.replace(/\f/g, '\\f')
|
|
443
|
+
.replace(/\b/g, '\\b');
|
|
444
|
+
}
|
|
445
|
+
/**
|
|
446
|
+
* Format error message for display
|
|
447
|
+
*
|
|
448
|
+
* Converts an Error object into a formatted error message suitable for:
|
|
449
|
+
* - Terminal display (interactive mode)
|
|
450
|
+
* - Log output (print mode)
|
|
451
|
+
* - JSON responses (RPC mode)
|
|
452
|
+
*
|
|
453
|
+
* Includes error message, type, and optional stack trace (if DEBUG enabled).
|
|
454
|
+
*
|
|
455
|
+
* Usage:
|
|
456
|
+
* ------
|
|
457
|
+
* INTERACTIVE MODE:
|
|
458
|
+
* try {
|
|
459
|
+
* await session.prompt(input);
|
|
460
|
+
* } catch (error) {
|
|
461
|
+
* displayError(formatErrorMessage(error));
|
|
462
|
+
* }
|
|
463
|
+
*
|
|
464
|
+
* PRINT MODE:
|
|
465
|
+
* process.stderr.write(formatErrorMessage(error));
|
|
466
|
+
* process.exit(1);
|
|
467
|
+
*
|
|
468
|
+
* RPC MODE:
|
|
469
|
+
* catch (error) {
|
|
470
|
+
* response.error = formatErrorMessage(error);
|
|
471
|
+
* }
|
|
472
|
+
*
|
|
473
|
+
* @param error - Error object or string
|
|
474
|
+
* @returns Formatted error message string
|
|
475
|
+
*
|
|
476
|
+
* @example
|
|
477
|
+
* const error = new Error('Invalid session');
|
|
478
|
+
* formatErrorMessage(error)
|
|
479
|
+
* // Returns: 'Error: Invalid session'
|
|
480
|
+
*
|
|
481
|
+
* @example
|
|
482
|
+
* formatErrorMessage('Something went wrong')
|
|
483
|
+
* // Returns: 'Something went wrong'
|
|
484
|
+
*/
|
|
485
|
+
export function formatErrorMessage(error) {
|
|
486
|
+
if (error instanceof Error) {
|
|
487
|
+
let message = `${error.name}: ${error.message}`;
|
|
488
|
+
if (process.env.DEBUG) {
|
|
489
|
+
message += '\n' + (error.stack || '');
|
|
490
|
+
}
|
|
491
|
+
return message;
|
|
492
|
+
}
|
|
493
|
+
if (typeof error === 'string') {
|
|
494
|
+
return error;
|
|
495
|
+
}
|
|
496
|
+
return String(error);
|
|
497
|
+
}
|
|
498
|
+
/**
|
|
499
|
+
* Determine if session should be auto-saved
|
|
500
|
+
*
|
|
501
|
+
* Checks configuration and state to determine whether to automatically persist
|
|
502
|
+
* the session to disk.
|
|
503
|
+
*
|
|
504
|
+
* Auto-save is enabled when:
|
|
505
|
+
* - config.autoSave is true
|
|
506
|
+
* - Session has been modified (dirty flag)
|
|
507
|
+
* - Minimum time interval has passed since last save
|
|
508
|
+
*
|
|
509
|
+
* Usage:
|
|
510
|
+
* ------
|
|
511
|
+
* INTERACTIVE MODE:
|
|
512
|
+
* if (shouldAutoSave(config)) {
|
|
513
|
+
* await sessionManager.save(session);
|
|
514
|
+
* }
|
|
515
|
+
*
|
|
516
|
+
* @param config - Configuration object with autoSave setting
|
|
517
|
+
* @returns Boolean indicating if session should be auto-saved
|
|
518
|
+
*
|
|
519
|
+
* @example
|
|
520
|
+
* const config = { autoSave: true, autoSaveInterval: 30000 };
|
|
521
|
+
* if (shouldAutoSave(config)) {
|
|
522
|
+
* sessionManager.save(currentSession);
|
|
523
|
+
* }
|
|
524
|
+
*/
|
|
525
|
+
export function shouldAutoSave(config) {
|
|
526
|
+
if (!config)
|
|
527
|
+
return false;
|
|
528
|
+
if (typeof config.autoSave !== 'boolean')
|
|
529
|
+
return false;
|
|
530
|
+
return config.autoSave === true;
|
|
531
|
+
}
|
|
532
|
+
export default {
|
|
533
|
+
createOutputFormatter,
|
|
534
|
+
parseSessionPath,
|
|
535
|
+
validatePrompt,
|
|
536
|
+
formatDuration,
|
|
537
|
+
formatTokens,
|
|
538
|
+
extractSessionId,
|
|
539
|
+
escapeJsonString,
|
|
540
|
+
formatErrorMessage,
|
|
541
|
+
shouldAutoSave,
|
|
542
|
+
};
|
|
543
|
+
//# sourceMappingURL=shared.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"shared.js","sourceRoot":"","sources":["../../src/modes/shared.ts"],"names":[],"mappings":"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"}
|