@robinpath/robinpath 0.30.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.
Files changed (65) hide show
  1. package/README.md +856 -0
  2. package/bin/robinpath.js +374 -0
  3. package/dist/classes/ASTSerializer.d.ts +45 -0
  4. package/dist/classes/ExecutionStateTracker.d.ts +30 -0
  5. package/dist/classes/Executor.d.ts +193 -0
  6. package/dist/classes/ExpressionEvaluator.d.ts +20 -0
  7. package/dist/classes/Lexer.d.ts +86 -0
  8. package/dist/classes/Parser.d.ts +71 -0
  9. package/dist/classes/RobinPathThread.d.ts +146 -0
  10. package/dist/classes/TokenStream.d.ts +217 -0
  11. package/dist/classes/code-converter/ASTToCodeConverter.d.ts +178 -0
  12. package/dist/classes/code-converter/LineIndex.d.ts +54 -0
  13. package/dist/classes/code-converter/Printer.d.ts +117 -0
  14. package/dist/classes/code-converter/Writer.d.ts +42 -0
  15. package/dist/classes/code-converter/index.d.ts +8 -0
  16. package/dist/classes/code-converter/types.d.ts +29 -0
  17. package/dist/classes/exceptions.d.ts +26 -0
  18. package/dist/classes/index.d.ts +16 -0
  19. package/dist/index.d.ts +485 -0
  20. package/dist/index.js +13808 -0
  21. package/dist/modules/Array.d.ts +10 -0
  22. package/dist/modules/Core.d.ts +10 -0
  23. package/dist/modules/Dom.d.ts +10 -0
  24. package/dist/modules/Fetch.d.ts +6 -0
  25. package/dist/modules/Json.d.ts +10 -0
  26. package/dist/modules/Math.d.ts +10 -0
  27. package/dist/modules/Object.d.ts +10 -0
  28. package/dist/modules/Random.d.ts +6 -0
  29. package/dist/modules/String.d.ts +10 -0
  30. package/dist/modules/Test.d.ts +10 -0
  31. package/dist/modules/Time.d.ts +10 -0
  32. package/dist/parsers/ArrayLiteralParser.d.ts +17 -0
  33. package/dist/parsers/AssignmentParser.d.ts +37 -0
  34. package/dist/parsers/BracketParser.d.ts +31 -0
  35. package/dist/parsers/BreakParser.d.ts +15 -0
  36. package/dist/parsers/CellBlockParser.d.ts +11 -0
  37. package/dist/parsers/ChunkMarkerParser.d.ts +12 -0
  38. package/dist/parsers/CommandParser.d.ts +56 -0
  39. package/dist/parsers/CommentParser.d.ts +37 -0
  40. package/dist/parsers/ContinueParser.d.ts +15 -0
  41. package/dist/parsers/DecoratorParser.d.ts +29 -0
  42. package/dist/parsers/DefineParser.d.ts +18 -0
  43. package/dist/parsers/EventParser.d.ts +17 -0
  44. package/dist/parsers/ExpressionParser.d.ts +3 -0
  45. package/dist/parsers/FenceClassifier.d.ts +29 -0
  46. package/dist/parsers/ForLoopParser.d.ts +17 -0
  47. package/dist/parsers/IfBlockParser.d.ts +17 -0
  48. package/dist/parsers/ObjectLiteralParser.d.ts +17 -0
  49. package/dist/parsers/ParserUtils.d.ts +15 -0
  50. package/dist/parsers/PromptBlockParser.d.ts +10 -0
  51. package/dist/parsers/ReturnParser.d.ts +16 -0
  52. package/dist/parsers/ScopeParser.d.ts +24 -0
  53. package/dist/parsers/StringTemplateParser.d.ts +31 -0
  54. package/dist/parsers/SubexpressionParser.d.ts +33 -0
  55. package/dist/parsers/TogetherBlockParser.d.ts +18 -0
  56. package/dist/parsers/WithScopeParser.d.ts +24 -0
  57. package/dist/types/Ast.type.d.ts +455 -0
  58. package/dist/types/Environment.type.d.ts +53 -0
  59. package/dist/utils/args.d.ts +24 -0
  60. package/dist/utils/errorFormatter.d.ts +22 -0
  61. package/dist/utils/index.d.ts +8 -0
  62. package/dist/utils/stringParsing.d.ts +41 -0
  63. package/dist/utils/types.d.ts +15 -0
  64. package/dist/utils/valueConversion.d.ts +25 -0
  65. package/package.json +50 -0
@@ -0,0 +1,485 @@
1
+ import { extractNamedArgs, Value, AttributePathSegment } from './utils';
2
+ import { RobinPathThread, ExecutionStateTracker, ExecutionLog } from './classes';
3
+ import { Statement, Arg, DefineFunction, OnBlock } from './types/Ast.type';
4
+ /**
5
+ * RobinPath Interpreter
6
+ *
7
+ * See README.md for full documentation and usage examples.
8
+ */
9
+ export declare const ROBINPATH_VERSION = "0.30.0";
10
+ export interface ModuleAdapter {
11
+ name: string;
12
+ functions: Record<string, BuiltinHandler>;
13
+ functionMetadata: Record<string, FunctionMetadata>;
14
+ moduleMetadata: ModuleMetadata;
15
+ global?: boolean;
16
+ }
17
+ export { Parser, Printer, LineIndexImpl } from './classes';
18
+ export type { PrintContext, LineIndex } from './classes';
19
+ export { formatErrorWithContext, createErrorWithContext } from './utils';
20
+ export type { ExecutionLog, ExecutionStepInfo, LogCallback } from './classes';
21
+ export type { Value, AttributePathSegment };
22
+ export type { Statement, Arg, CommandCall, Assignment, ShorthandAssignment, InlineIf, IfBlock, IfTrue, IfFalse, DefineFunction, ScopeBlock, TogetherBlock, ForLoop, ReturnStatement, BreakStatement, OnBlock, CommentStatement, ChunkMarkerStatement, CellBlock, PromptBlockStatement, CommentWithPosition, CodePosition, DecoratorCall, } from './types/Ast.type';
23
+ export type BuiltinCallback = (callbackArgs: Value[]) => Promise<Value> | Value | null;
24
+ export type BuiltinHandler = (args: Value[], callback?: BuiltinCallback | null) => Promise<Value> | Value | null;
25
+ export type DecoratorHandler = (targetName: string, func: DefineFunction | null, originalArgs: Value[], decoratorArgs: Value[], originalDecoratorArgs?: Arg[]) => Promise<Value[] | Value | null | undefined>;
26
+ export type ParseDecoratorHandler = (targetName: string, func: DefineFunction | null, decoratorArgs: Arg[], environment: Environment) => Promise<void> | void;
27
+ export interface Environment {
28
+ variables: Map<string, Value>;
29
+ functions: Map<string, DefineFunction>;
30
+ builtins: Map<string, BuiltinHandler>;
31
+ decorators: Map<string, DecoratorHandler>;
32
+ parseDecorators: Map<string, ParseDecoratorHandler>;
33
+ metadata: Map<string, FunctionMetadata>;
34
+ moduleMetadata: Map<string, ModuleMetadata>;
35
+ currentModule: string | null;
36
+ variableMetadata: Map<string, Map<string, Value>>;
37
+ functionMetadata: Map<string, Map<string, Value>>;
38
+ constants: Set<string>;
39
+ eventHandlers: Map<string, OnBlock[]>;
40
+ stateTracker?: ExecutionStateTracker;
41
+ }
42
+ export interface Frame {
43
+ locals: Map<string, Value>;
44
+ lastValue: Value;
45
+ isFunctionFrame?: boolean;
46
+ forgotten?: Set<string>;
47
+ isIsolatedScope?: boolean;
48
+ }
49
+ export { extractNamedArgs };
50
+ export type DataType = "string" | "number" | "boolean" | "object" | "array" | "null" | "any";
51
+ export type FormInputType = "text" | "number" | "textarea" | "select" | "checkbox" | "radio" | "date" | "datetime" | "file" | "json" | "code" | "varname";
52
+ export interface ParameterMetadata {
53
+ name: string;
54
+ label?: string;
55
+ dataType: DataType;
56
+ description: string;
57
+ formInputType: FormInputType;
58
+ required?: boolean;
59
+ defaultValue?: Value;
60
+ allowedTypes?: string[];
61
+ children?: ParameterMetadata;
62
+ }
63
+ export interface FunctionMetadata {
64
+ description: string;
65
+ parameters: ParameterMetadata[];
66
+ returnType: DataType;
67
+ returnDescription: string;
68
+ example?: string;
69
+ }
70
+ export interface ModuleMetadata {
71
+ description: string;
72
+ methods: string[];
73
+ author?: string;
74
+ category?: string;
75
+ doc_url?: string;
76
+ }
77
+ export declare class RobinPath {
78
+ private static versionLogged;
79
+ private environment;
80
+ private persistentExecutor;
81
+ private lastExecutor;
82
+ private activeExecutor;
83
+ private threads;
84
+ private currentThread;
85
+ private threadControl;
86
+ private replBuffer;
87
+ private astToCodeConverter;
88
+ private serializer;
89
+ private stateTracker;
90
+ constructor(options?: {
91
+ threadControl?: boolean;
92
+ });
93
+ /**
94
+ * Get execution steps from the last execution
95
+ */
96
+ getExecutionSteps(): import('./classes').ExecutionStepInfo[];
97
+ /**
98
+ * Get execution logs from the last execution
99
+ */
100
+ getExecutionLogs(): ExecutionLog[];
101
+ /**
102
+ * Set a callback for real-time log notifications
103
+ * The callback is called immediately when a log is added during execution
104
+ */
105
+ setLogCallback(callback: ((log: ExecutionLog) => void) | null): void;
106
+ /**
107
+ * Clear execution state
108
+ */
109
+ clearExecutionState(): void;
110
+ /**
111
+ * Native modules registry
112
+ * Add new modules here to auto-load them
113
+ */
114
+ private static readonly NATIVE_MODULES;
115
+ /**
116
+ * Load a single module using the adapter pattern
117
+ */
118
+ private loadModule;
119
+ /**
120
+ * Load all native modules
121
+ */
122
+ private loadNativeModules;
123
+ /**
124
+ * Register a builtin function
125
+ */
126
+ registerBuiltin(name: string, handler: BuiltinHandler): void;
127
+ /**
128
+ * Register a runtime decorator function that can be used to modify function calls at execution time
129
+ * Runtime decorators execute during function execution and can modify arguments or behavior
130
+ * Decorators are only available via API registration, not in scripts
131
+ * @param name Decorator name (without @ prefix)
132
+ * @param handler Decorator handler function
133
+ */
134
+ registerDecorator(name: string, handler: DecoratorHandler): void;
135
+ /**
136
+ * Register a parse-time decorator function that executes during parsing
137
+ * Parse decorators inject metadata into AST nodes (def, on, var, const)
138
+ * They run during parsing, not execution, and work with AST arguments
139
+ * @param name Decorator name (without @ prefix)
140
+ * @param handler Parse decorator handler function
141
+ */
142
+ registerParseDecorator(name: string, handler: ParseDecoratorHandler): void;
143
+ /**
144
+ * Register built-in parse-time decorators (@desc/@description, @title, @param, @arg, @required)
145
+ * These decorators execute during parsing and inject metadata into AST nodes
146
+ */
147
+ private registerBuiltinDecorators;
148
+ /**
149
+ * Register a module with multiple functions
150
+ * @example
151
+ * rp.registerModule('fs', {
152
+ * read: (args) => { ... },
153
+ * write: (args) => { ... }
154
+ * });
155
+ */
156
+ registerModule(moduleName: string, functions: Record<string, BuiltinHandler>): void;
157
+ /**
158
+ * Register a module function (e.g., 'fs.read')
159
+ */
160
+ registerModuleFunction(module: string, func: string, handler: BuiltinHandler): void;
161
+ /**
162
+ * Register an external class constructor (e.g., 'Client', 'Database')
163
+ */
164
+ registerConstructor(name: string, handler: BuiltinHandler): void;
165
+ /**
166
+ * Register metadata for a module with multiple functions
167
+ * @example
168
+ * rp.registerModuleMeta('fs', {
169
+ * read: {
170
+ * description: 'Reads a file from the filesystem',
171
+ * parameters: [
172
+ * {
173
+ * name: 'filename',
174
+ * dataType: 'string',
175
+ * description: 'Path to the file to read',
176
+ * formInputType: 'text',
177
+ * required: true
178
+ * }
179
+ * ],
180
+ * returnType: 'string',
181
+ * returnDescription: 'Contents of the file'
182
+ * },
183
+ * write: {
184
+ * description: 'Writes content to a file',
185
+ * parameters: [
186
+ * {
187
+ * name: 'filename',
188
+ * dataType: 'string',
189
+ * description: 'Path to the file to write',
190
+ * formInputType: 'text',
191
+ * required: true
192
+ * },
193
+ * {
194
+ * name: 'content',
195
+ * dataType: 'string',
196
+ * description: 'Content to write to the file',
197
+ * formInputType: 'textarea',
198
+ * required: true
199
+ * }
200
+ * ],
201
+ * returnType: 'boolean',
202
+ * returnDescription: 'True if write was successful'
203
+ * }
204
+ * });
205
+ */
206
+ registerModuleMeta(moduleName: string, functions: Record<string, FunctionMetadata>): void;
207
+ /**
208
+ * Register metadata for a single module function (e.g., 'fs.read')
209
+ * @example
210
+ * rp.registerModuleFunctionMeta('fs', 'read', {
211
+ * description: 'Reads a file from the filesystem',
212
+ * parameters: [
213
+ * {
214
+ * name: 'filename',
215
+ * dataType: 'string',
216
+ * description: 'Path to the file to read',
217
+ * formInputType: 'text',
218
+ * required: true
219
+ * }
220
+ * ],
221
+ * returnType: 'string',
222
+ * returnDescription: 'Contents of the file'
223
+ * });
224
+ */
225
+ registerModuleFunctionMeta(module: string, func: string, metadata: FunctionMetadata): void;
226
+ /**
227
+ * Get metadata for a function (builtin or module function)
228
+ * Returns null if no metadata is registered
229
+ */
230
+ getFunctionMetadata(functionName: string): FunctionMetadata | null;
231
+ /**
232
+ * Get all registered function metadata
233
+ */
234
+ getAllFunctionMetadata(): Map<string, FunctionMetadata>;
235
+ /**
236
+ * Register module-level metadata (description and list of methods)
237
+ * @example
238
+ * rp.registerModuleInfo('fs', {
239
+ * description: 'File system operations for reading and writing files',
240
+ * methods: ['read', 'write', 'exists', 'delete']
241
+ * });
242
+ */
243
+ registerModuleInfo(moduleName: string, metadata: ModuleMetadata): void;
244
+ /**
245
+ * Get module metadata (description and methods list)
246
+ * Returns null if no metadata is registered
247
+ */
248
+ getModuleInfo(moduleName: string): ModuleMetadata | null;
249
+ /**
250
+ * Get all registered module metadata
251
+ */
252
+ getAllModuleInfo(): Map<string, ModuleMetadata>;
253
+ /**
254
+ * Get syntax context for available commands
255
+ * Determines what commands are valid based on the current syntax position
256
+ */
257
+ private getSyntaxContext;
258
+ /**
259
+ * Get all available commands, modules, and functions
260
+ * Returns a structured object with categories, each containing objects with:
261
+ * - name: The command/function name
262
+ * - type: The type (native, builtin, module, moduleFunction, userFunction)
263
+ * - description: Description if available
264
+ *
265
+ * @param context Optional syntax context to filter commands based on what's valid next
266
+ */
267
+ getAvailableCommands(context?: {
268
+ inIfBlock?: boolean;
269
+ inDefBlock?: boolean;
270
+ afterIf?: boolean;
271
+ afterDef?: boolean;
272
+ afterElseif?: boolean;
273
+ }): {
274
+ native: Array<{
275
+ name: string;
276
+ type: string;
277
+ description: string;
278
+ }>;
279
+ builtin: Array<{
280
+ name: string;
281
+ type: string;
282
+ description: string;
283
+ }>;
284
+ modules: Array<{
285
+ name: string;
286
+ type: string;
287
+ description: string;
288
+ author?: string;
289
+ category?: string;
290
+ }>;
291
+ moduleFunctions: Array<{
292
+ name: string;
293
+ type: string;
294
+ description: string;
295
+ }>;
296
+ userFunctions: Array<{
297
+ name: string;
298
+ type: string;
299
+ description: string;
300
+ }>;
301
+ };
302
+ /**
303
+ * Check if a script needs more input (incomplete block)
304
+ * Returns { needsMore: true, waitingFor: 'endif' | 'enddef' | 'endfor' | 'enddo' | 'endon' | 'subexpr' | 'paren' | 'object' | 'array' } if incomplete,
305
+ * or { needsMore: false } if complete.
306
+ */
307
+ needsMoreInput(script: string): Promise<{
308
+ needsMore: boolean;
309
+ waitingFor?: "endif" | "enddef" | "endfor" | "enddo" | "endon" | "subexpr" | "paren" | "object" | "array";
310
+ }>;
311
+ /**
312
+ * Get the AST without execution state
313
+ * Returns a JSON-serializable AST array
314
+ *
315
+ * Note: This method only parses the script, it does not execute it.
316
+ */
317
+ getAST(script: string): Promise<any[]>;
318
+ /**
319
+ * Get extracted function definitions (def/enddef blocks) from a script
320
+ * Returns a JSON-serializable array of function definitions
321
+ *
322
+ * Note: This method only parses the script, it does not execute it.
323
+ */
324
+ getExtractedFunctions(script: string): Promise<any[]>;
325
+ /**
326
+ * Serialize a statement to JSON
327
+ * @param stmt The statement to serialize
328
+ * @param currentModuleContext Optional module context
329
+ * @param lastValue Optional execution state
330
+ * @param nodeKey Optional node key
331
+ */
332
+ private serializeStatement;
333
+ /**
334
+ * Get the complete structure of the script in a tree format
335
+ * Includes main body, functions, event handlers, and variables
336
+ */
337
+ getScriptStructure(script: string): Promise<any>;
338
+ /**
339
+ * Get extracted variables from the script (parsed, not executed)
340
+ * Returns variable names with optional description and initial value
341
+ */
342
+ getExtractedVariables(script: string): Promise<Array<{
343
+ name: string;
344
+ description?: string;
345
+ initialValue?: any;
346
+ }>>;
347
+ /**
348
+ * Update source code based on AST changes
349
+ * Uses precise character-level positions (codePos.startRow/startCol/endRow/endCol) to update code
350
+ * Nested nodes are reconstructed as part of their parent's code
351
+ * @param originalScript The original source code
352
+ * @param ast The modified AST array (top-level nodes only)
353
+ * @returns Updated source code
354
+ */
355
+ updateCodeFromAST(originalScript: string, ast: any[]): Promise<string>;
356
+ /**
357
+ * Reconstruct code from an AST node
358
+ * @param node The AST node (serialized)
359
+ * @param indentLevel Indentation level for nested code
360
+ * @returns Reconstructed code string, or null if cannot be reconstructed
361
+ */
362
+ reconstructCodeFromASTNode(node: any, indentLevel?: number): string | null;
363
+ /**
364
+ * Execute a RobinPath script
365
+ */
366
+ executeScript(script: string): Promise<Value>;
367
+ /**
368
+ * Execute a single line (for REPL)
369
+ * Uses a persistent executor to maintain state ($, variables) between calls.
370
+ * Functions and builtins persist across calls.
371
+ */
372
+ executeLine(line: string): Promise<Value>;
373
+ /**
374
+ * Get the last value ($)
375
+ * Returns the value from the most recent execution (script or REPL line).
376
+ */
377
+ getLastValue(): Value;
378
+ /**
379
+ * REPL-friendly execution that supports multi-line blocks (if/def/for and $( ... )).
380
+ *
381
+ * Usage pattern:
382
+ * - Call this for every user-entered line.
383
+ * - If done === false, keep collecting lines.
384
+ * - When done === true, value is the execution result and the buffer is cleared.
385
+ */
386
+ executeReplLine(line: string): Promise<{
387
+ done: boolean;
388
+ value: Value | null;
389
+ waitingFor?: string;
390
+ }>;
391
+ /**
392
+ * Generate a UUID v4
393
+ */
394
+ private generateUUID;
395
+ /**
396
+ * Create a new thread/session.
397
+ * Each thread has its own variables, functions, and $,
398
+ * but shares builtins and metadata with the root interpreter.
399
+ *
400
+ * @param id Optional thread ID. If not provided, a UUID will be generated.
401
+ * @returns The created thread
402
+ *
403
+ * @example
404
+ * const rp = new RobinPath();
405
+ * const thread = rp.createThread('my-thread');
406
+ * await thread.executeScript('math.add 5 5');
407
+ * console.log(thread.getLastValue()); // 10
408
+ */
409
+ createThread(id?: string): RobinPathThread;
410
+ /**
411
+ * Get a thread by ID
412
+ */
413
+ getThread(id: string): RobinPathThread | null;
414
+ /**
415
+ * List all threads with their IDs
416
+ */
417
+ listThreads(): Array<{
418
+ id: string;
419
+ isCurrent: boolean;
420
+ }>;
421
+ /**
422
+ * Switch to a different thread
423
+ */
424
+ useThread(id: string): void;
425
+ /**
426
+ * Get the current thread
427
+ */
428
+ getCurrentThread(): RobinPathThread | null;
429
+ /**
430
+ * Check if thread control is enabled
431
+ */
432
+ isThreadControlEnabled(): boolean;
433
+ /**
434
+ * Close a thread by ID
435
+ * If the closed thread is the current thread, currentThread is set to null
436
+ */
437
+ closeThread(id: string): void;
438
+ /**
439
+ * Trigger an event, executing all registered event handlers for the event name
440
+ * @param eventName The name of the event to trigger
441
+ * @param args Arguments to pass to event handlers (available as $1, $2, $3, etc.)
442
+ * @returns Promise that resolves when all handlers have executed
443
+ */
444
+ trigger(eventName: string, ...args: Value[]): Promise<void>;
445
+ /**
446
+ * Get all event handlers (onBlocks) registered in the environment
447
+ * @returns Map of event name to array of OnBlock handlers
448
+ */
449
+ getEventHandlers(): Map<string, OnBlock[]>;
450
+ /**
451
+ * Get all event handlers as a flat array
452
+ * @returns Array of all OnBlock handlers
453
+ */
454
+ getAllEventHandlers(): OnBlock[];
455
+ /**
456
+ * Get event handlers as serialized AST
457
+ * @returns Array of serialized event handler AST nodes
458
+ */
459
+ getEventAST(): any[];
460
+ /**
461
+ * Get a variable value
462
+ */
463
+ getVariable(name: string): Value;
464
+ /**
465
+ * Set a variable value (for external use)
466
+ */
467
+ setVariable(name: string, value: Value): void;
468
+ /**
469
+ * Get all variables as a plain object
470
+ */
471
+ getVariableState(): Record<string, Value>;
472
+ /**
473
+ * Get the next statement index that would execute after a given statement.
474
+ * This method analyzes the AST structure to determine execution flow.
475
+ *
476
+ * @param statements The array of all statements
477
+ * @param currentIndex The index of the current statement
478
+ * @param context Optional context for conditional branches (which branch was taken)
479
+ * @returns The index of the next statement to execute, or -1 if execution ends
480
+ */
481
+ getNextStatementIndex(statements: Statement[], currentIndex: number, context?: {
482
+ ifBlockBranch?: "then" | "elseif" | "else" | null;
483
+ forLoopIteration?: number;
484
+ }): number;
485
+ }