lua-cli 3.0.0-alpha.1 → 3.0.0-alpha.4
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/dist/api/job.api.service.d.ts +16 -7
- package/dist/api/job.api.service.js +21 -5
- package/dist/api/postprocessor.api.service.d.ts +61 -1
- package/dist/api/postprocessor.api.service.js +35 -0
- package/dist/api/preprocessor.api.service.d.ts +61 -1
- package/dist/api/preprocessor.api.service.js +35 -0
- package/dist/api-exports.d.ts +26 -6
- package/dist/api-exports.js +42 -29
- package/dist/commands/chat.js +32 -5
- package/dist/commands/compile.js +16 -2
- package/dist/commands/dev.js +23 -2
- package/dist/commands/push.js +5 -3
- package/dist/commands/test.js +18 -2
- package/dist/common/job.instance.d.ts +3 -0
- package/dist/common/job.instance.js +8 -0
- package/dist/config/constants.d.ts +6 -5
- package/dist/config/constants.js +12 -10
- package/dist/interfaces/chat.d.ts +30 -1
- package/dist/interfaces/jobs.d.ts +21 -0
- package/dist/types/skill.d.ts +75 -56
- package/dist/types/skill.js +53 -59
- package/dist/utils/bundling.d.ts +13 -4
- package/dist/utils/bundling.js +83 -26
- package/dist/utils/compile.js +27 -6
- package/dist/utils/dev-api.d.ts +42 -2
- package/dist/utils/dev-api.js +177 -4
- package/dist/utils/dev-server.d.ts +1 -1
- package/dist/utils/dev-server.js +4 -4
- package/dist/utils/dynamic-job-bundler.d.ts +17 -0
- package/dist/utils/dynamic-job-bundler.js +143 -0
- package/dist/utils/pre-bundle-jobs.d.ts +26 -0
- package/dist/utils/pre-bundle-jobs.js +176 -0
- package/dist/utils/sandbox-storage.d.ts +48 -0
- package/dist/utils/sandbox-storage.js +114 -0
- package/dist/utils/sandbox.d.ts +2 -2
- package/dist/utils/sandbox.js +23 -7
- package/package.json +1 -1
- package/template/lua.skill.yaml +47 -0
- package/template/package-lock.json +10505 -0
- package/template/package.json +2 -1
- package/template/src/index.ts +65 -3
- package/template/src/tools/CreateInlineJob.ts +42 -0
- package/API_REFERENCE.md +0 -1408
- package/CHANGELOG.md +0 -236
- package/CLI_REFERENCE.md +0 -908
- package/GETTING_STARTED.md +0 -1040
- package/INSTANCE_TYPES.md +0 -1158
- package/README.md +0 -865
- package/TEMPLATE_GUIDE.md +0 -1398
- package/USER_DATA_INSTANCE.md +0 -621
- package/template/AGENT_CONFIGURATION.md +0 -251
- package/template/COMPLEX_JOB_EXAMPLES.md +0 -795
- package/template/DYNAMIC_JOB_CREATION.md +0 -371
- package/template/TOOL_EXAMPLES.md +0 -655
- package/template/WEBHOOKS_JOBS_QUICKSTART.md +0 -318
- package/template/WEBHOOK_JOB_EXAMPLES.md +0 -817
- package/template/src/index-agent-example.ts +0 -201
- package/template/src/postprocessors/ResponseFormatter.ts +0 -151
- package/template/src/preprocessors/MessageFilter.ts +0 -91
package/dist/types/skill.js
CHANGED
|
@@ -283,21 +283,6 @@ export class LuaJob {
|
|
|
283
283
|
getMetadata() {
|
|
284
284
|
return this.metadata;
|
|
285
285
|
}
|
|
286
|
-
/**
|
|
287
|
-
* Executes the job.
|
|
288
|
-
* This is called by the scheduler at the appropriate time.
|
|
289
|
-
*
|
|
290
|
-
* @returns Promise resolving to job execution result
|
|
291
|
-
*
|
|
292
|
-
* @example
|
|
293
|
-
* ```typescript
|
|
294
|
-
* const result = await job.execute();
|
|
295
|
-
* console.log('Job completed:', result);
|
|
296
|
-
* ```
|
|
297
|
-
*/
|
|
298
|
-
async execute() {
|
|
299
|
-
return this.executeFunction();
|
|
300
|
-
}
|
|
301
286
|
}
|
|
302
287
|
/**
|
|
303
288
|
* Lua Webhook class.
|
|
@@ -330,19 +315,19 @@ export class LuaJob {
|
|
|
330
315
|
* email: z.string().email(),
|
|
331
316
|
* name: z.string()
|
|
332
317
|
* }),
|
|
333
|
-
* execute: async (
|
|
318
|
+
* execute: async (query, headers, body) => {
|
|
334
319
|
* // Process the webhook...
|
|
335
320
|
* console.log('New user:', body.email);
|
|
336
321
|
* return { success: true, userId: body.userId };
|
|
337
322
|
* }
|
|
338
323
|
* });
|
|
339
324
|
*
|
|
340
|
-
* // Execute the webhook with validated
|
|
341
|
-
* const result = await webhook.execute(
|
|
342
|
-
*
|
|
343
|
-
*
|
|
344
|
-
*
|
|
345
|
-
*
|
|
325
|
+
* // Execute the webhook with validated inputs
|
|
326
|
+
* const result = await webhook.execute(
|
|
327
|
+
* { source: 'mobile' },
|
|
328
|
+
* { 'x-api-key': 'secret-key' },
|
|
329
|
+
* { userId: '123', email: 'user@example.com', name: 'John' }
|
|
330
|
+
* );
|
|
346
331
|
* ```
|
|
347
332
|
*/
|
|
348
333
|
export class LuaWebhook {
|
|
@@ -398,81 +383,82 @@ export class LuaWebhook {
|
|
|
398
383
|
* Validates query parameters, headers, and body against their respective schemas
|
|
399
384
|
* before executing the webhook function.
|
|
400
385
|
*
|
|
401
|
-
* @param
|
|
402
|
-
* @param
|
|
403
|
-
* @param
|
|
404
|
-
* @param input.body - Request body
|
|
386
|
+
* @param query - Query parameters object
|
|
387
|
+
* @param headers - Headers object
|
|
388
|
+
* @param body - Request body
|
|
405
389
|
* @returns Promise resolving to webhook execution result
|
|
406
390
|
* @throws Error if validation fails for any input
|
|
407
391
|
*
|
|
408
392
|
* @example
|
|
409
393
|
* ```typescript
|
|
410
|
-
* const result = await webhook.execute(
|
|
411
|
-
*
|
|
412
|
-
*
|
|
413
|
-
*
|
|
414
|
-
*
|
|
394
|
+
* const result = await webhook.execute(
|
|
395
|
+
* { limit: '10' },
|
|
396
|
+
* { 'x-api-key': 'secret' },
|
|
397
|
+
* { data: 'value' }
|
|
398
|
+
* );
|
|
415
399
|
* ```
|
|
416
400
|
*/
|
|
417
|
-
async execute(
|
|
418
|
-
|
|
401
|
+
async execute(query, headers, body) {
|
|
402
|
+
let validatedQuery = query;
|
|
403
|
+
let validatedHeaders = headers;
|
|
404
|
+
let validatedBody = body;
|
|
419
405
|
// Validate query parameters if schema is provided
|
|
420
406
|
if (this.querySchema) {
|
|
421
407
|
try {
|
|
422
|
-
|
|
408
|
+
validatedQuery = this.querySchema.parse(query || {});
|
|
423
409
|
}
|
|
424
410
|
catch (error) {
|
|
425
411
|
throw new Error(`Query parameter validation failed: ${error}`);
|
|
426
412
|
}
|
|
427
413
|
}
|
|
428
|
-
else {
|
|
429
|
-
validatedInput.query = input.query;
|
|
430
|
-
}
|
|
431
414
|
// Validate headers if schema is provided
|
|
432
415
|
if (this.headerSchema) {
|
|
433
416
|
try {
|
|
434
|
-
|
|
417
|
+
validatedHeaders = this.headerSchema.parse(headers || {});
|
|
435
418
|
}
|
|
436
419
|
catch (error) {
|
|
437
420
|
throw new Error(`Header validation failed: ${error}`);
|
|
438
421
|
}
|
|
439
422
|
}
|
|
440
|
-
else {
|
|
441
|
-
validatedInput.headers = input.headers;
|
|
442
|
-
}
|
|
443
423
|
// Validate body if schema is provided
|
|
444
424
|
if (this.bodySchema) {
|
|
445
425
|
try {
|
|
446
|
-
|
|
426
|
+
validatedBody = this.bodySchema.parse(body);
|
|
447
427
|
}
|
|
448
428
|
catch (error) {
|
|
449
429
|
throw new Error(`Body validation failed: ${error}`);
|
|
450
430
|
}
|
|
451
431
|
}
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
}
|
|
455
|
-
// Execute the webhook function with validated input
|
|
456
|
-
return this.executeFunction(validatedInput);
|
|
432
|
+
// Execute the webhook function with validated inputs as separate parameters
|
|
433
|
+
return this.executeFunction(validatedQuery, validatedHeaders, validatedBody);
|
|
457
434
|
}
|
|
458
435
|
}
|
|
459
436
|
/**
|
|
460
437
|
* PreProcessor class.
|
|
461
438
|
* Processes user messages before they reach the agent.
|
|
439
|
+
* Can handle rich content (text, images, files).
|
|
462
440
|
*
|
|
463
441
|
* @example
|
|
464
442
|
* ```typescript
|
|
465
|
-
* const
|
|
466
|
-
* name: '
|
|
443
|
+
* const contentFilter = new PreProcessor({
|
|
444
|
+
* name: 'content-filter',
|
|
467
445
|
* version: '1.0.0',
|
|
468
|
-
* description: '
|
|
469
|
-
* context: '
|
|
470
|
-
* execute: async (user,
|
|
471
|
-
*
|
|
472
|
-
*
|
|
473
|
-
*
|
|
474
|
-
*
|
|
475
|
-
*
|
|
446
|
+
* description: 'Filters and processes message content',
|
|
447
|
+
* context: 'Filters spam, validates images, and adds context',
|
|
448
|
+
* execute: async (user, messages, channel) => {
|
|
449
|
+
* // Process each message
|
|
450
|
+
* return messages.map(msg => {
|
|
451
|
+
* if (msg.type === 'text') {
|
|
452
|
+
* // Filter spam from text
|
|
453
|
+
* const filtered = msg.text.replace(/spam/gi, '[filtered]');
|
|
454
|
+
* return { type: 'text', text: filtered };
|
|
455
|
+
* }
|
|
456
|
+
* if (msg.type === 'image') {
|
|
457
|
+
* // Could validate image, add watermark, etc.
|
|
458
|
+
* return msg;
|
|
459
|
+
* }
|
|
460
|
+
* return msg;
|
|
461
|
+
* });
|
|
476
462
|
* }
|
|
477
463
|
* });
|
|
478
464
|
* ```
|
|
@@ -483,6 +469,7 @@ export class PreProcessor {
|
|
|
483
469
|
this.version = config.version || '1.0.0';
|
|
484
470
|
this.description = config.description;
|
|
485
471
|
this.context = config.context;
|
|
472
|
+
this.asyncMode = config.async ?? false; // Default to synchronous
|
|
486
473
|
this.executeFunction = config.execute;
|
|
487
474
|
}
|
|
488
475
|
getName() {
|
|
@@ -497,8 +484,11 @@ export class PreProcessor {
|
|
|
497
484
|
getContext() {
|
|
498
485
|
return this.context;
|
|
499
486
|
}
|
|
500
|
-
|
|
501
|
-
return this.
|
|
487
|
+
getAsync() {
|
|
488
|
+
return this.asyncMode;
|
|
489
|
+
}
|
|
490
|
+
async execute(user, messages, channel) {
|
|
491
|
+
return this.executeFunction(user, messages, channel);
|
|
502
492
|
}
|
|
503
493
|
}
|
|
504
494
|
/**
|
|
@@ -524,6 +514,7 @@ export class PostProcessor {
|
|
|
524
514
|
this.version = config.version || '1.0.0';
|
|
525
515
|
this.description = config.description;
|
|
526
516
|
this.context = config.context;
|
|
517
|
+
this.asyncMode = config.async ?? false; // Default to synchronous
|
|
527
518
|
this.executeFunction = config.execute;
|
|
528
519
|
}
|
|
529
520
|
getName() {
|
|
@@ -538,6 +529,9 @@ export class PostProcessor {
|
|
|
538
529
|
getContext() {
|
|
539
530
|
return this.context;
|
|
540
531
|
}
|
|
532
|
+
getAsync() {
|
|
533
|
+
return this.asyncMode;
|
|
534
|
+
}
|
|
541
535
|
async execute(user, message, response, channel) {
|
|
542
536
|
return this.executeFunction(user, message, response, channel);
|
|
543
537
|
}
|
package/dist/utils/bundling.d.ts
CHANGED
|
@@ -2,8 +2,15 @@
|
|
|
2
2
|
* Bundling Utilities
|
|
3
3
|
* Handles esbuild bundling of tools and main index
|
|
4
4
|
*/
|
|
5
|
+
import { Plugin } from "esbuild";
|
|
5
6
|
import { Project } from "ts-morph";
|
|
6
7
|
import { ToolInfo } from '../interfaces/compile.js';
|
|
8
|
+
/**
|
|
9
|
+
* esbuild plugin to inject sandbox globals instead of requiring lua-cli
|
|
10
|
+
* This removes require("lua-cli") statements and injects the global API objects
|
|
11
|
+
* that are available in the sandbox (Products, User, Data, Baskets, Orders, Webhooks, Jobs)
|
|
12
|
+
*/
|
|
13
|
+
export declare const sandboxGlobalsPlugin: Plugin;
|
|
7
14
|
/**
|
|
8
15
|
* Bundles a tool's TypeScript code into a standalone JavaScript file.
|
|
9
16
|
* Uses esbuild to:
|
|
@@ -16,7 +23,7 @@ import { ToolInfo } from '../interfaces/compile.js';
|
|
|
16
23
|
* @param tool - The tool to bundle
|
|
17
24
|
* @param distDir - The distribution directory for output
|
|
18
25
|
*/
|
|
19
|
-
export declare function bundleTool(tool: ToolInfo, distDir: string): Promise<void>;
|
|
26
|
+
export declare function bundleTool(tool: ToolInfo, distDir: string, modifiedSource?: string): Promise<void>;
|
|
20
27
|
/**
|
|
21
28
|
* Bundles the main index.ts file into a standalone JavaScript file.
|
|
22
29
|
* This creates the entry point for the skill.
|
|
@@ -57,10 +64,12 @@ export declare function bundlePostProcessor(postprocessor: any, indexFile: any,
|
|
|
57
64
|
* Extracts execute code and input schema from a tool.
|
|
58
65
|
* This function:
|
|
59
66
|
* 1. Reads the bundled tool code
|
|
60
|
-
* 2.
|
|
61
|
-
* 3.
|
|
67
|
+
* 2. Detects and bundles any Jobs.create() calls within execute
|
|
68
|
+
* 3. Extracts the execute function
|
|
69
|
+
* 4. Converts Zod schema to JSON Schema format
|
|
62
70
|
*
|
|
63
71
|
* @param tool - The tool to extract metadata from (mutated with executeCode and inputSchema)
|
|
64
72
|
* @param project - The ts-morph Project instance for AST analysis
|
|
73
|
+
* @param distDir - Distribution directory for bundling nested jobs
|
|
65
74
|
*/
|
|
66
|
-
export declare function extractExecuteCode(tool: ToolInfo, project: Project): Promise<void>;
|
|
75
|
+
export declare function extractExecuteCode(tool: ToolInfo, project: Project, distDir?: string): Promise<void>;
|
package/dist/utils/bundling.js
CHANGED
|
@@ -8,13 +8,34 @@ import { build } from "esbuild";
|
|
|
8
8
|
import { Project, Node } from "ts-morph";
|
|
9
9
|
import { writeProgress } from "./cli.js";
|
|
10
10
|
import { COMPILE_DIRS, COMPILE_FILES, ESBUILD_TOOL_CONFIG, ESBUILD_INDEX_CONFIG, DEFAULT_INPUT_SCHEMA, } from '../config/compile.constants.js';
|
|
11
|
-
import { wrapToolForVM, createExecuteFunction, evaluateZodSchemaToJsonSchema
|
|
11
|
+
import { wrapToolForVM, createExecuteFunction, evaluateZodSchemaToJsonSchema } from './compile.js';
|
|
12
|
+
/**
|
|
13
|
+
* Helper function to remove lua-cli and api-exports imports from source code.
|
|
14
|
+
* Used when bundling via stdin or temp files where the plugin can't process them.
|
|
15
|
+
*/
|
|
16
|
+
function stripLuaCliImports(sourceCode) {
|
|
17
|
+
return sourceCode
|
|
18
|
+
// Remove api-exports imports
|
|
19
|
+
.replace(/import\s+{([^}]+)}\s+from\s+["'][^"']*api-exports["'];?/g, '// api-exports imports removed - using sandbox globals')
|
|
20
|
+
// Remove lua-cli imports
|
|
21
|
+
.replace(/import\s+{([^}]+)}\s+from\s+["']lua-cli["'];?/g, '// lua-cli imports removed - using sandbox globals')
|
|
22
|
+
// Remove lua-cli/skill imports (but keep LuaTool, etc. for type checking in temp files)
|
|
23
|
+
.replace(/import\s+{([^}]+)}\s+from\s+["']lua-cli\/skill["'];?/g, (match, imports) => {
|
|
24
|
+
// Keep only LuaTool, LuaWebhook, LuaJob types for temp files
|
|
25
|
+
const typeImports = imports.split(',')
|
|
26
|
+
.map((imp) => imp.trim())
|
|
27
|
+
.filter((imp) => /^(LuaTool|LuaWebhook|LuaJob|LuaPreProcessor|LuaPostProcessor)$/.test(imp));
|
|
28
|
+
return typeImports.length > 0
|
|
29
|
+
? `// lua-cli/skill imports removed - using sandbox globals (types kept for compilation)`
|
|
30
|
+
: '// lua-cli/skill imports removed - using sandbox globals';
|
|
31
|
+
});
|
|
32
|
+
}
|
|
12
33
|
/**
|
|
13
34
|
* esbuild plugin to inject sandbox globals instead of requiring lua-cli
|
|
14
35
|
* This removes require("lua-cli") statements and injects the global API objects
|
|
15
36
|
* that are available in the sandbox (Products, User, Data, Baskets, Orders, Webhooks, Jobs)
|
|
16
37
|
*/
|
|
17
|
-
const sandboxGlobalsPlugin = {
|
|
38
|
+
export const sandboxGlobalsPlugin = {
|
|
18
39
|
name: 'sandbox-globals',
|
|
19
40
|
setup(build) {
|
|
20
41
|
// Only process user files, not node_modules
|
|
@@ -24,12 +45,18 @@ const sandboxGlobalsPlugin = {
|
|
|
24
45
|
return null;
|
|
25
46
|
}
|
|
26
47
|
const contents = await fs.promises.readFile(args.path, 'utf8');
|
|
27
|
-
// Only transform files that import from lua-cli
|
|
28
|
-
if (!contents.includes('lua-cli')) {
|
|
48
|
+
// Only transform files that import from lua-cli or api-exports
|
|
49
|
+
if (!contents.includes('lua-cli') && !contents.includes('api-exports')) {
|
|
29
50
|
return null;
|
|
30
51
|
}
|
|
31
52
|
// Replace lua-cli imports with global references
|
|
32
53
|
let transformedContents = contents;
|
|
54
|
+
// Replace named imports from api-exports (e.g., ../../../dist/api-exports)
|
|
55
|
+
// Match: import { Jobs, Products, etc. } from "../../../dist/api-exports"
|
|
56
|
+
transformedContents = transformedContents.replace(/import\s+{([^}]+)}\s+from\s+["'][^"']*api-exports["'];?/g, (match, imports) => {
|
|
57
|
+
// Just remove the import, globals will be available in sandbox
|
|
58
|
+
return '// api-exports imports removed - using sandbox globals';
|
|
59
|
+
});
|
|
33
60
|
// Replace named imports from lua-cli
|
|
34
61
|
// Match: import { Products, User, Data, etc. } from "lua-cli"
|
|
35
62
|
transformedContents = transformedContents.replace(/import\s+{([^}]+)}\s+from\s+["']lua-cli["'];?/g, (match, imports) => {
|
|
@@ -83,12 +110,13 @@ const sandboxGlobalsPlugin = {
|
|
|
83
110
|
* @param tool - The tool to bundle
|
|
84
111
|
* @param distDir - The distribution directory for output
|
|
85
112
|
*/
|
|
86
|
-
export async function bundleTool(tool, distDir) {
|
|
113
|
+
export async function bundleTool(tool, distDir, modifiedSource) {
|
|
87
114
|
writeProgress(`📦 Bundling ${tool.className}...`);
|
|
88
115
|
try {
|
|
89
116
|
const outputPath = path.join(distDir, COMPILE_DIRS.TOOLS, `${tool.className}.js`);
|
|
90
117
|
let entryPoint = tool.filePath;
|
|
91
118
|
let tempFile = null;
|
|
119
|
+
// Note: modifiedSource is handled via stdin below, no temp file needed
|
|
92
120
|
// Check if tool is inline (in index.ts or src/index.ts)
|
|
93
121
|
const isInlineInIndex = tool.filePath.endsWith('index.ts') || tool.filePath.endsWith('index.tsx');
|
|
94
122
|
if (isInlineInIndex) {
|
|
@@ -121,12 +149,30 @@ export async function bundleTool(tool, distDir) {
|
|
|
121
149
|
entryPoint = tempFile;
|
|
122
150
|
}
|
|
123
151
|
}
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
152
|
+
// Use stdin for modified source to preserve import resolution
|
|
153
|
+
if (modifiedSource && !isInlineInIndex) {
|
|
154
|
+
// Remove api-exports and lua-cli imports (they're available in sandbox)
|
|
155
|
+
const transformedSource = stripLuaCliImports(modifiedSource);
|
|
156
|
+
await build({
|
|
157
|
+
...ESBUILD_TOOL_CONFIG,
|
|
158
|
+
stdin: {
|
|
159
|
+
contents: transformedSource,
|
|
160
|
+
resolveDir: path.dirname(tool.filePath),
|
|
161
|
+
sourcefile: tool.filePath,
|
|
162
|
+
loader: 'ts',
|
|
163
|
+
},
|
|
164
|
+
outfile: outputPath,
|
|
165
|
+
plugins: [sandboxGlobalsPlugin],
|
|
166
|
+
});
|
|
167
|
+
}
|
|
168
|
+
else {
|
|
169
|
+
await build({
|
|
170
|
+
...ESBUILD_TOOL_CONFIG,
|
|
171
|
+
entryPoints: [entryPoint],
|
|
172
|
+
outfile: outputPath,
|
|
173
|
+
plugins: [sandboxGlobalsPlugin],
|
|
174
|
+
});
|
|
175
|
+
}
|
|
130
176
|
// Wrap the bundled code for VM execution environment
|
|
131
177
|
await wrapToolForVM(outputPath, tool);
|
|
132
178
|
// Clean up temp file if created
|
|
@@ -303,10 +349,10 @@ async function bundleAndCompressWebhookCode(executeFunction, webhookName, distDi
|
|
|
303
349
|
const tempOutput = path.join(tempDir, `${webhookName}-webhook.js`);
|
|
304
350
|
try {
|
|
305
351
|
// Write execute function as a module export
|
|
306
|
-
const moduleCode = `
|
|
352
|
+
const moduleCode = stripLuaCliImports(`
|
|
307
353
|
// Webhook execute function for ${webhookName}
|
|
308
354
|
export default ${executeFunction};
|
|
309
|
-
|
|
355
|
+
`);
|
|
310
356
|
fs.writeFileSync(tempFile, moduleCode);
|
|
311
357
|
// Bundle with esbuild
|
|
312
358
|
await build({
|
|
@@ -323,8 +369,7 @@ export default ${executeFunction};
|
|
|
323
369
|
// Read bundled code
|
|
324
370
|
let bundledCode = fs.readFileSync(tempOutput, 'utf8');
|
|
325
371
|
// Wrap for webhook VM execution (similar to tools)
|
|
326
|
-
const wrappedCode = `(async (
|
|
327
|
-
const { query, headers, body } = input;
|
|
372
|
+
const wrappedCode = `(async (query, headers, body) => {
|
|
328
373
|
|
|
329
374
|
// Execute the bundled webhook code
|
|
330
375
|
${bundledCode}
|
|
@@ -332,8 +377,8 @@ export default ${executeFunction};
|
|
|
332
377
|
// Get the execute function from exports
|
|
333
378
|
const executeFunction = module.exports.default || module.exports;
|
|
334
379
|
|
|
335
|
-
// Execute with
|
|
336
|
-
return await executeFunction(
|
|
380
|
+
// Execute with three separate parameters (not an object)
|
|
381
|
+
return await executeFunction(query, headers, body);
|
|
337
382
|
})`;
|
|
338
383
|
// Compress the wrapped code
|
|
339
384
|
const compressed = compressCode(wrappedCode);
|
|
@@ -472,10 +517,10 @@ async function bundleAndCompressJobCode(executeFunction, jobName, distDir) {
|
|
|
472
517
|
const tempOutput = path.join(tempDir, `${jobName}-job.js`);
|
|
473
518
|
try {
|
|
474
519
|
// Write execute function as a module export
|
|
475
|
-
const moduleCode = `
|
|
520
|
+
const moduleCode = stripLuaCliImports(`
|
|
476
521
|
// Job execute function for ${jobName}
|
|
477
522
|
export default ${executeFunction};
|
|
478
|
-
|
|
523
|
+
`);
|
|
479
524
|
fs.writeFileSync(tempFile, moduleCode);
|
|
480
525
|
// Bundle with esbuild
|
|
481
526
|
await build({
|
|
@@ -597,7 +642,11 @@ export async function bundlePreProcessor(preprocessor, indexFile, distDir, proje
|
|
|
597
642
|
compressedCode = await bundleAndCompressProcessorCode(executeFunction, preprocessor.name, 'pre', distDir);
|
|
598
643
|
}
|
|
599
644
|
return {
|
|
600
|
-
|
|
645
|
+
name: preprocessor.name,
|
|
646
|
+
version: preprocessor.version,
|
|
647
|
+
description: preprocessor.description,
|
|
648
|
+
context: preprocessor.context,
|
|
649
|
+
async: preprocessor.async === true ? true : false, // Explicitly set boolean
|
|
601
650
|
executeFunction,
|
|
602
651
|
code: compressedCode
|
|
603
652
|
};
|
|
@@ -675,7 +724,11 @@ export async function bundlePostProcessor(postprocessor, indexFile, distDir, pro
|
|
|
675
724
|
compressedCode = await bundleAndCompressProcessorCode(executeFunction, postprocessor.name, 'post', distDir);
|
|
676
725
|
}
|
|
677
726
|
return {
|
|
678
|
-
|
|
727
|
+
name: postprocessor.name,
|
|
728
|
+
version: postprocessor.version,
|
|
729
|
+
description: postprocessor.description,
|
|
730
|
+
context: postprocessor.context,
|
|
731
|
+
async: postprocessor.async === true ? true : false, // Explicitly set boolean
|
|
679
732
|
executeFunction,
|
|
680
733
|
code: compressedCode
|
|
681
734
|
};
|
|
@@ -699,10 +752,10 @@ async function bundleAndCompressProcessorCode(executeFunction, processorName, ty
|
|
|
699
752
|
try {
|
|
700
753
|
// Processor execute functions receive: (user, message, [response], channel)
|
|
701
754
|
const paramList = type === 'pre' ? 'user, message, channel' : 'user, message, response, channel';
|
|
702
|
-
const moduleCode = `
|
|
755
|
+
const moduleCode = stripLuaCliImports(`
|
|
703
756
|
// ${type === 'pre' ? 'Pre' : 'Post'}Processor execute function for ${processorName}
|
|
704
757
|
export default ${executeFunction};
|
|
705
|
-
|
|
758
|
+
`);
|
|
706
759
|
fs.writeFileSync(tempFile, moduleCode);
|
|
707
760
|
await build({
|
|
708
761
|
entryPoints: [tempFile],
|
|
@@ -751,13 +804,15 @@ export default ${executeFunction};
|
|
|
751
804
|
* Extracts execute code and input schema from a tool.
|
|
752
805
|
* This function:
|
|
753
806
|
* 1. Reads the bundled tool code
|
|
754
|
-
* 2.
|
|
755
|
-
* 3.
|
|
807
|
+
* 2. Detects and bundles any Jobs.create() calls within execute
|
|
808
|
+
* 3. Extracts the execute function
|
|
809
|
+
* 4. Converts Zod schema to JSON Schema format
|
|
756
810
|
*
|
|
757
811
|
* @param tool - The tool to extract metadata from (mutated with executeCode and inputSchema)
|
|
758
812
|
* @param project - The ts-morph Project instance for AST analysis
|
|
813
|
+
* @param distDir - Distribution directory for bundling nested jobs
|
|
759
814
|
*/
|
|
760
|
-
export async function extractExecuteCode(tool, project) {
|
|
815
|
+
export async function extractExecuteCode(tool, project, distDir) {
|
|
761
816
|
try {
|
|
762
817
|
const toolSourceFile = project.getSourceFile(tool.filePath);
|
|
763
818
|
if (!toolSourceFile) {
|
|
@@ -793,6 +848,8 @@ export async function extractExecuteCode(tool, project) {
|
|
|
793
848
|
}
|
|
794
849
|
// Extract execute code from bundled file
|
|
795
850
|
tool.executeCode = extractExecuteCodeFromBundledFile(tool);
|
|
851
|
+
// NOTE: Dynamic job bundling moved to source-level processing
|
|
852
|
+
// Attempting to extract from minified bundled code is too fragile
|
|
796
853
|
// Extract and convert input schema
|
|
797
854
|
tool.inputSchema = await extractInputSchema(classDecl, tool);
|
|
798
855
|
}
|
package/dist/utils/compile.js
CHANGED
|
@@ -423,6 +423,7 @@ export function extractPreProcessorsMetadata(indexFile) {
|
|
|
423
423
|
let version = '';
|
|
424
424
|
let description = '';
|
|
425
425
|
let context = '';
|
|
426
|
+
let asyncMode = false;
|
|
426
427
|
configObj.getProperties().forEach((prop) => {
|
|
427
428
|
if (Node.isPropertyAssignment(prop)) {
|
|
428
429
|
const propName = prop.getName();
|
|
@@ -439,6 +440,11 @@ export function extractPreProcessorsMetadata(indexFile) {
|
|
|
439
440
|
else if (propName === 'context' && value) {
|
|
440
441
|
context = value.getText().replace(/['"]/g, '');
|
|
441
442
|
}
|
|
443
|
+
else if (propName === 'async' && value) {
|
|
444
|
+
// Properly extract boolean value by checking node kind
|
|
445
|
+
const nodeKind = value.getKind();
|
|
446
|
+
asyncMode = nodeKind === 110; // TrueKeyword = 110, FalseKeyword = 95
|
|
447
|
+
}
|
|
442
448
|
}
|
|
443
449
|
});
|
|
444
450
|
if (name) {
|
|
@@ -446,7 +452,8 @@ export function extractPreProcessorsMetadata(indexFile) {
|
|
|
446
452
|
name,
|
|
447
453
|
version: version || '1.0.0',
|
|
448
454
|
description,
|
|
449
|
-
context
|
|
455
|
+
context,
|
|
456
|
+
async: asyncMode
|
|
450
457
|
});
|
|
451
458
|
}
|
|
452
459
|
}
|
|
@@ -472,6 +479,7 @@ export function extractPostProcessorsMetadata(indexFile) {
|
|
|
472
479
|
let version = '';
|
|
473
480
|
let description = '';
|
|
474
481
|
let context = '';
|
|
482
|
+
let asyncMode = false;
|
|
475
483
|
configObj.getProperties().forEach((prop) => {
|
|
476
484
|
if (Node.isPropertyAssignment(prop)) {
|
|
477
485
|
const propName = prop.getName();
|
|
@@ -488,6 +496,11 @@ export function extractPostProcessorsMetadata(indexFile) {
|
|
|
488
496
|
else if (propName === 'context' && value) {
|
|
489
497
|
context = value.getText().replace(/['"]/g, '');
|
|
490
498
|
}
|
|
499
|
+
else if (propName === 'async' && value) {
|
|
500
|
+
// Properly extract boolean value by checking node kind
|
|
501
|
+
const nodeKind = value.getKind();
|
|
502
|
+
asyncMode = nodeKind === 110; // TrueKeyword = 110, FalseKeyword = 95
|
|
503
|
+
}
|
|
491
504
|
}
|
|
492
505
|
});
|
|
493
506
|
if (name) {
|
|
@@ -495,7 +508,8 @@ export function extractPostProcessorsMetadata(indexFile) {
|
|
|
495
508
|
name,
|
|
496
509
|
version: version || '1.0.0',
|
|
497
510
|
description,
|
|
498
|
-
context
|
|
511
|
+
context,
|
|
512
|
+
async: asyncMode
|
|
499
513
|
});
|
|
500
514
|
}
|
|
501
515
|
}
|
|
@@ -674,10 +688,12 @@ function extractValueFromNode(node) {
|
|
|
674
688
|
if (Node.isNumericLiteral(node)) {
|
|
675
689
|
return node.getLiteralValue();
|
|
676
690
|
}
|
|
677
|
-
// Boolean literal
|
|
678
|
-
|
|
679
|
-
|
|
680
|
-
|
|
691
|
+
// Boolean literal (TrueKeyword = 110, FalseKeyword = 95)
|
|
692
|
+
const nodeKind = node.getKind();
|
|
693
|
+
if (nodeKind === 110)
|
|
694
|
+
return true; // TrueKeyword
|
|
695
|
+
if (nodeKind === 95)
|
|
696
|
+
return false; // FalseKeyword
|
|
681
697
|
// New expression (for tools: [new ToolClass()])
|
|
682
698
|
// Extract just the class name for compatibility with buildSkillsArray
|
|
683
699
|
if (Node.isNewExpression(node)) {
|
|
@@ -699,6 +715,11 @@ function extractValueFromNode(node) {
|
|
|
699
715
|
// Template literal or other complex expressions
|
|
700
716
|
// For persona, context, etc. that might be multiline
|
|
701
717
|
const text = node.getText();
|
|
718
|
+
// Handle boolean strings (fallback if node kind check didn't catch it)
|
|
719
|
+
if (text === 'true')
|
|
720
|
+
return true;
|
|
721
|
+
if (text === 'false')
|
|
722
|
+
return false;
|
|
702
723
|
// If it starts with a quote, remove quotes
|
|
703
724
|
if ((text.startsWith('"') && text.endsWith('"')) ||
|
|
704
725
|
(text.startsWith("'") && text.endsWith("'")) ||
|
package/dist/utils/dev-api.d.ts
CHANGED
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
*/
|
|
5
5
|
import { DevVersionResponse, UpdateDevVersionResponse, SandboxIdsMap } from '../interfaces/dev.js';
|
|
6
6
|
/**
|
|
7
|
-
* Sends a chat message to the API with skill
|
|
7
|
+
* Sends a chat message to the API with skill and processor overrides for sandbox testing.
|
|
8
8
|
*
|
|
9
9
|
* @param apiKey - User's API key
|
|
10
10
|
* @param agentId - Agent ID
|
|
@@ -13,9 +13,10 @@ import { DevVersionResponse, UpdateDevVersionResponse, SandboxIdsMap } from '../
|
|
|
13
13
|
* @param message - Message to send
|
|
14
14
|
* @param persona - Optional persona override
|
|
15
15
|
* @param deployData - Deploy data containing all skills
|
|
16
|
+
* @param config - Optional config for processor overrides
|
|
16
17
|
* @returns The chat response text or null if failed
|
|
17
18
|
*/
|
|
18
|
-
export declare function sendChatMessage(apiKey: string, agentId: string, skillId: string, sandboxId: string, message: string, persona: string | undefined, deployData: any): Promise<string | null>;
|
|
19
|
+
export declare function sendChatMessage(apiKey: string, agentId: string, skillId: string, sandboxId: string, message: string, persona: string | undefined, deployData: any, config?: any): Promise<string | null>;
|
|
19
20
|
/**
|
|
20
21
|
* Updates an existing sandbox version.
|
|
21
22
|
*
|
|
@@ -59,3 +60,42 @@ export declare function pushSingleSkillToSandbox(apiKey: string, agentId: string
|
|
|
59
60
|
* @returns Map of skill names to their sandbox IDs
|
|
60
61
|
*/
|
|
61
62
|
export declare function pushSkillsToSandbox(apiKey: string, agentId: string, deployData: any, isInitial?: boolean): Promise<SandboxIdsMap>;
|
|
63
|
+
/**
|
|
64
|
+
* Pushes a single preprocessor to the sandbox.
|
|
65
|
+
* Attempts to update existing sandbox version, creates new one if update fails.
|
|
66
|
+
*
|
|
67
|
+
* @param apiKey - User's API key
|
|
68
|
+
* @param agentId - Agent ID
|
|
69
|
+
* @param preprocessorId - PreProcessor ID
|
|
70
|
+
* @param preprocessorData - PreProcessor data to push
|
|
71
|
+
* @param isInitial - Whether this is the initial push (affects logging)
|
|
72
|
+
* @returns True if successful, false otherwise
|
|
73
|
+
*/
|
|
74
|
+
export declare function pushSinglePreProcessorToSandbox(apiKey: string, agentId: string, preprocessorId: string, preprocessorData: any, isInitial?: boolean): Promise<boolean>;
|
|
75
|
+
/**
|
|
76
|
+
* Pushes a single postprocessor to the sandbox.
|
|
77
|
+
* Attempts to update existing sandbox version, creates new one if update fails.
|
|
78
|
+
*
|
|
79
|
+
* @param apiKey - User's API key
|
|
80
|
+
* @param agentId - Agent ID
|
|
81
|
+
* @param postprocessorId - PostProcessor ID
|
|
82
|
+
* @param postprocessorData - PostProcessor data to push
|
|
83
|
+
* @param isInitial - Whether this is the initial push (affects logging)
|
|
84
|
+
* @returns True if successful, false otherwise
|
|
85
|
+
*/
|
|
86
|
+
export declare function pushSinglePostProcessorToSandbox(apiKey: string, agentId: string, postprocessorId: string, postprocessorData: any, isInitial?: boolean): Promise<boolean>;
|
|
87
|
+
/**
|
|
88
|
+
* Pushes preprocessors and postprocessors to sandbox.
|
|
89
|
+
*
|
|
90
|
+
* @param apiKey - User's API key
|
|
91
|
+
* @param agentId - Agent ID
|
|
92
|
+
* @param config - Configuration with preprocessors and postprocessors
|
|
93
|
+
* @param bundledPreProcessors - Bundled preprocessor data from compilation
|
|
94
|
+
* @param bundledPostProcessors - Bundled postprocessor data from compilation
|
|
95
|
+
* @param isInitial - Whether this is the initial push
|
|
96
|
+
* @returns Object with counts of pushed processors
|
|
97
|
+
*/
|
|
98
|
+
export declare function pushProcessorsToSandbox(apiKey: string, agentId: string, config: any, bundledPreProcessors: any[], bundledPostProcessors: any[], isInitial?: boolean): Promise<{
|
|
99
|
+
preprocessors: number;
|
|
100
|
+
postprocessors: number;
|
|
101
|
+
}>;
|