@cogitator-ai/self-modifying 17.0.10 → 17.0.13
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/architecture-evolution/capability-analyzer.d.ts +2 -0
- package/dist/architecture-evolution/capability-analyzer.d.ts.map +1 -1
- package/dist/architecture-evolution/capability-analyzer.js +3 -1
- package/dist/architecture-evolution/capability-analyzer.js.map +1 -1
- package/dist/architecture-evolution/parameter-optimizer.d.ts +2 -0
- package/dist/architecture-evolution/parameter-optimizer.d.ts.map +1 -1
- package/dist/architecture-evolution/parameter-optimizer.js +4 -1
- package/dist/architecture-evolution/parameter-optimizer.js.map +1 -1
- package/dist/self-modifying-agent.d.ts +1 -0
- package/dist/self-modifying-agent.d.ts.map +1 -1
- package/dist/self-modifying-agent.js +81 -16
- package/dist/self-modifying-agent.js.map +1 -1
- package/dist/tool-generation/gap-analyzer.d.ts +2 -0
- package/dist/tool-generation/gap-analyzer.d.ts.map +1 -1
- package/dist/tool-generation/gap-analyzer.js +3 -1
- package/dist/tool-generation/gap-analyzer.js.map +1 -1
- package/dist/tool-generation/prompts.d.ts +1 -1
- package/dist/tool-generation/prompts.d.ts.map +1 -1
- package/dist/tool-generation/prompts.js +16 -12
- package/dist/tool-generation/prompts.js.map +1 -1
- package/dist/tool-generation/tool-generator.d.ts +2 -0
- package/dist/tool-generation/tool-generator.d.ts.map +1 -1
- package/dist/tool-generation/tool-generator.js +4 -1
- package/dist/tool-generation/tool-generator.js.map +1 -1
- package/dist/tool-generation/tool-validator.d.ts +2 -0
- package/dist/tool-generation/tool-validator.d.ts.map +1 -1
- package/dist/tool-generation/tool-validator.js +3 -4
- package/dist/tool-generation/tool-validator.js.map +1 -1
- package/package.json +1 -1
- package/src/__tests__/self-modifying-agent.test.ts +197 -0
- package/src/architecture-evolution/capability-analyzer.ts +4 -1
- package/src/architecture-evolution/parameter-optimizer.ts +5 -1
- package/src/self-modifying-agent.ts +90 -16
- package/src/tool-generation/gap-analyzer.ts +4 -1
- package/src/tool-generation/prompts.ts +16 -12
- package/src/tool-generation/tool-generator.ts +5 -1
- package/src/tool-generation/tool-validator.ts +4 -6
|
@@ -11,6 +11,9 @@ import type {
|
|
|
11
11
|
ModificationCheckpoint,
|
|
12
12
|
SelfModifyingEvent,
|
|
13
13
|
CapabilityGap,
|
|
14
|
+
Message,
|
|
15
|
+
ToolSchema,
|
|
16
|
+
ToolContext,
|
|
14
17
|
} from '@cogitator-ai/types';
|
|
15
18
|
|
|
16
19
|
import { SelfModifyingEventEmitter } from './events';
|
|
@@ -67,18 +70,19 @@ export class SelfModifyingAgent {
|
|
|
67
70
|
this.config = this.mergeConfig(options.config);
|
|
68
71
|
|
|
69
72
|
const toolGenConfig = this.config.toolGeneration;
|
|
70
|
-
|
|
71
|
-
this.
|
|
73
|
+
const agentModel = this.agent.model;
|
|
74
|
+
this.gapAnalyzer = new GapAnalyzer({ llm: this.llm, config: toolGenConfig, model: agentModel });
|
|
75
|
+
this.toolGenerator = new ToolGenerator({ llm: this.llm, config: toolGenConfig, model: agentModel });
|
|
72
76
|
this.toolStore = new InMemoryGeneratedToolStore();
|
|
73
77
|
|
|
74
78
|
this.metaReasoner = new MetaReasoner({
|
|
75
79
|
llm: this.llm,
|
|
76
|
-
model: 'default',
|
|
80
|
+
model: agentModel ?? 'default',
|
|
77
81
|
config: this.config.metaReasoning,
|
|
78
82
|
});
|
|
79
83
|
|
|
80
84
|
const baseArchConfig: ArchitectureConfig = {
|
|
81
|
-
model: 'default',
|
|
85
|
+
model: agentModel ?? 'default',
|
|
82
86
|
temperature: 0.7,
|
|
83
87
|
maxTokens: 4096,
|
|
84
88
|
toolStrategy: 'sequential',
|
|
@@ -89,11 +93,13 @@ export class SelfModifyingAgent {
|
|
|
89
93
|
llm: this.llm,
|
|
90
94
|
config: this.config.architectureEvolution,
|
|
91
95
|
baseConfig: baseArchConfig,
|
|
96
|
+
model: agentModel,
|
|
92
97
|
});
|
|
93
98
|
|
|
94
99
|
this.capabilityAnalyzer = new CapabilityAnalyzer({
|
|
95
100
|
llm: this.llm,
|
|
96
101
|
enableLLMAnalysis: true,
|
|
102
|
+
model: agentModel,
|
|
97
103
|
});
|
|
98
104
|
|
|
99
105
|
this.modificationValidator = new ModificationValidator({
|
|
@@ -372,11 +378,8 @@ export class SelfModifyingAgent {
|
|
|
372
378
|
reflective: { mode: 'reflective', temperature: 0.4, depth: 3 },
|
|
373
379
|
exploratory: { mode: 'exploratory', temperature: 0.7, depth: 2 },
|
|
374
380
|
},
|
|
375
|
-
maxAssessmentsPerRun: 5,
|
|
376
|
-
maxAdaptationsPerRun: 3,
|
|
377
381
|
maxMetaAssessments: 5,
|
|
378
382
|
maxAdaptations: 3,
|
|
379
|
-
assessmentCooldown: 10000,
|
|
380
383
|
metaAssessmentCooldown: 10000,
|
|
381
384
|
adaptationCooldown: 15000,
|
|
382
385
|
triggers: ['on_failure', 'on_low_confidence', 'periodic'],
|
|
@@ -598,19 +601,90 @@ export class SelfModifyingAgent {
|
|
|
598
601
|
}
|
|
599
602
|
|
|
600
603
|
private async executeAgentStep(input: string): Promise<string> {
|
|
601
|
-
const
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
606
|
-
|
|
607
|
-
|
|
608
|
-
|
|
604
|
+
const tools = this.currentContext?.tools ?? [];
|
|
605
|
+
const toolSchemas = this.buildToolSchemas(tools);
|
|
606
|
+
const toolMap = new Map<string, Tool>();
|
|
607
|
+
for (const t of tools) {
|
|
608
|
+
toolMap.set(t.name, t);
|
|
609
|
+
}
|
|
610
|
+
|
|
611
|
+
const model = this.currentContext?.currentConfig.model ?? this.agent.model ?? 'default';
|
|
612
|
+
const messages: Message[] = [
|
|
613
|
+
...(this.agent.instructions
|
|
614
|
+
? [{ role: 'system' as const, content: this.agent.instructions }]
|
|
615
|
+
: []),
|
|
616
|
+
{ role: 'user' as const, content: input },
|
|
617
|
+
];
|
|
618
|
+
|
|
619
|
+
const maxToolRounds = 10;
|
|
620
|
+
for (let round = 0; round < maxToolRounds; round++) {
|
|
621
|
+
const response = await this.llm.chat({
|
|
622
|
+
model,
|
|
623
|
+
messages,
|
|
624
|
+
tools: toolSchemas.length > 0 ? toolSchemas : undefined,
|
|
625
|
+
temperature: this.currentContext?.currentConfig.temperature,
|
|
626
|
+
maxTokens: this.currentContext?.currentConfig.maxTokens,
|
|
627
|
+
});
|
|
628
|
+
|
|
629
|
+
if (response.finishReason !== 'tool_calls' || !response.toolCalls?.length) {
|
|
630
|
+
return response.content;
|
|
631
|
+
}
|
|
632
|
+
|
|
633
|
+
messages.push({
|
|
634
|
+
role: 'assistant',
|
|
635
|
+
content: response.content,
|
|
636
|
+
toolCalls: response.toolCalls,
|
|
637
|
+
} as Message);
|
|
638
|
+
|
|
639
|
+
for (const toolCall of response.toolCalls) {
|
|
640
|
+
const t = toolMap.get(toolCall.name);
|
|
641
|
+
let result: unknown;
|
|
642
|
+
|
|
643
|
+
if (!t) {
|
|
644
|
+
result = { error: `Tool "${toolCall.name}" not found` };
|
|
645
|
+
} else {
|
|
646
|
+
try {
|
|
647
|
+
const ctx: ToolContext = {
|
|
648
|
+
agentId: this.agent.name || 'self-modifying',
|
|
649
|
+
runId: this.currentContext?.runId || 'unknown',
|
|
650
|
+
signal: AbortSignal.timeout(30_000),
|
|
651
|
+
};
|
|
652
|
+
result = await t.execute(toolCall.arguments, ctx);
|
|
653
|
+
} catch (err) {
|
|
654
|
+
result = { error: err instanceof Error ? err.message : String(err) };
|
|
655
|
+
}
|
|
656
|
+
}
|
|
657
|
+
|
|
658
|
+
messages.push({
|
|
659
|
+
role: 'tool' as const,
|
|
660
|
+
content: typeof result === 'string' ? result : JSON.stringify(result),
|
|
661
|
+
toolCallId: toolCall.id,
|
|
662
|
+
name: toolCall.name,
|
|
663
|
+
});
|
|
664
|
+
}
|
|
665
|
+
}
|
|
666
|
+
|
|
667
|
+
const finalResponse = await this.llm.chat({
|
|
668
|
+
model,
|
|
669
|
+
messages,
|
|
609
670
|
temperature: this.currentContext?.currentConfig.temperature,
|
|
610
671
|
maxTokens: this.currentContext?.currentConfig.maxTokens,
|
|
611
672
|
});
|
|
673
|
+
return finalResponse.content;
|
|
674
|
+
}
|
|
612
675
|
|
|
613
|
-
|
|
676
|
+
private buildToolSchemas(tools: Tool[]): ToolSchema[] {
|
|
677
|
+
return tools
|
|
678
|
+
.map((t) => {
|
|
679
|
+
if (typeof t.toJSON === 'function') {
|
|
680
|
+
return t.toJSON() as ToolSchema;
|
|
681
|
+
}
|
|
682
|
+
return {
|
|
683
|
+
name: t.name,
|
|
684
|
+
description: t.description,
|
|
685
|
+
parameters: { type: 'object' as const, properties: {} },
|
|
686
|
+
};
|
|
687
|
+
});
|
|
614
688
|
}
|
|
615
689
|
|
|
616
690
|
private estimateConfidence(output: string): number {
|
|
@@ -10,16 +10,19 @@ import { buildGapAnalysisPrompt, parseGapAnalysisResponse } from './prompts';
|
|
|
10
10
|
export interface GapAnalyzerOptions {
|
|
11
11
|
llm: LLMBackend;
|
|
12
12
|
config: ToolSelfGenerationConfig;
|
|
13
|
+
model?: string;
|
|
13
14
|
}
|
|
14
15
|
|
|
15
16
|
export class GapAnalyzer {
|
|
16
17
|
private readonly llm: LLMBackend;
|
|
17
18
|
private readonly config: ToolSelfGenerationConfig;
|
|
19
|
+
private readonly model: string;
|
|
18
20
|
private readonly analysisCache = new Map<string, GapAnalysisResult>();
|
|
19
21
|
|
|
20
22
|
constructor(options: GapAnalyzerOptions) {
|
|
21
23
|
this.llm = options.llm;
|
|
22
24
|
this.config = options.config;
|
|
25
|
+
this.model = options.model ?? 'default';
|
|
23
26
|
}
|
|
24
27
|
|
|
25
28
|
async analyze(
|
|
@@ -233,6 +236,6 @@ Consider tool composition before suggesting new tools.`,
|
|
|
233
236
|
if (this.llm.complete) {
|
|
234
237
|
return this.llm.complete({ messages, temperature });
|
|
235
238
|
}
|
|
236
|
-
return this.llm.chat({ model:
|
|
239
|
+
return this.llm.chat({ model: this.model, messages, temperature });
|
|
237
240
|
}
|
|
238
241
|
}
|
|
@@ -1,23 +1,24 @@
|
|
|
1
1
|
import type { CapabilityGap, GeneratedTool, ToolValidationResult } from '@cogitator-ai/types';
|
|
2
2
|
import { extractJson } from '../utils';
|
|
3
3
|
|
|
4
|
-
export const TOOL_GENERATION_SYSTEM_PROMPT = `You are an expert
|
|
5
|
-
Your task is to generate safe, efficient
|
|
4
|
+
export const TOOL_GENERATION_SYSTEM_PROMPT = `You are an expert JavaScript developer specializing in creating tools for AI agents.
|
|
5
|
+
Your task is to generate safe, efficient tool implementations.
|
|
6
6
|
|
|
7
7
|
CRITICAL CONSTRAINTS:
|
|
8
|
-
1. Generate ONLY
|
|
9
|
-
2.
|
|
10
|
-
3.
|
|
11
|
-
4.
|
|
12
|
-
5.
|
|
13
|
-
6.
|
|
8
|
+
1. Generate ONLY plain JavaScript (ES2020+) - NO TypeScript syntax, NO type annotations, NO interfaces
|
|
9
|
+
2. No external dependencies - only built-in globals (Math, JSON, Date, Array, Object, String, Number, Boolean, RegExp, Map, Set, Error)
|
|
10
|
+
3. All generated code must be self-contained
|
|
11
|
+
4. Never generate code that accesses file system, network, or system resources
|
|
12
|
+
5. Always include proper error handling with try-catch
|
|
13
|
+
6. The implementation MUST define an async function called "execute" that takes a params object and returns a result
|
|
14
|
+
7. Do NOT use: eval, Function, import, require, process, global, fetch, setTimeout, setInterval, constructor
|
|
14
15
|
|
|
15
16
|
OUTPUT FORMAT:
|
|
16
17
|
Return a JSON object with:
|
|
17
18
|
{
|
|
18
19
|
"name": "tool_name",
|
|
19
20
|
"description": "Clear description of what the tool does",
|
|
20
|
-
"implementation": "
|
|
21
|
+
"implementation": "async function execute(params) { ... }",
|
|
21
22
|
"parameters": { "type": "object", "properties": {...}, "required": [...] },
|
|
22
23
|
"reasoning": "Why this implementation was chosen"
|
|
23
24
|
}`;
|
|
@@ -92,7 +93,7 @@ export function buildToolGenerationPrompt(
|
|
|
92
93
|
const security = constraints?.securityLevel || 'strict';
|
|
93
94
|
const maxLines = constraints?.maxLines || 100;
|
|
94
95
|
|
|
95
|
-
return `Generate a
|
|
96
|
+
return `Generate a plain JavaScript tool implementation for the following capability gap.
|
|
96
97
|
|
|
97
98
|
CAPABILITY GAP:
|
|
98
99
|
- Description: ${gap.description}
|
|
@@ -106,6 +107,8 @@ ${existingTools.map((t) => `- ${t.name}: ${t.description}`).join('\n')}
|
|
|
106
107
|
CONSTRAINTS:
|
|
107
108
|
- Maximum ${maxLines} lines of code
|
|
108
109
|
- Security level: ${security}
|
|
110
|
+
- MUST use plain JavaScript (ES2020+), NO TypeScript syntax, NO type annotations, NO interfaces
|
|
111
|
+
- The "implementation" field must define an async function called "execute" that takes a plain object "params"
|
|
109
112
|
${securityRules[security]}
|
|
110
113
|
${constraints?.allowedModules ? `- Allowed modules: ${constraints.allowedModules.join(', ')}` : ''}
|
|
111
114
|
|
|
@@ -113,7 +116,7 @@ Generate a complete, self-contained tool following this exact structure:
|
|
|
113
116
|
{
|
|
114
117
|
"name": "${gap.suggestedToolName}",
|
|
115
118
|
"description": "Clear description",
|
|
116
|
-
"implementation": "async function execute(params
|
|
119
|
+
"implementation": "async function execute(params) { ... }",
|
|
117
120
|
"parameters": {
|
|
118
121
|
"type": "object",
|
|
119
122
|
"properties": { ... },
|
|
@@ -190,11 +193,12 @@ SUGGESTIONS:
|
|
|
190
193
|
${validationResult.suggestions.map((s, idx) => `${idx + 1}. ${s}`).join('\n')}
|
|
191
194
|
|
|
192
195
|
Generate an improved implementation that addresses ALL issues.
|
|
196
|
+
IMPORTANT: Use plain JavaScript only (NO TypeScript, NO type annotations). The execute function signature must be: async function execute(params) { ... }
|
|
193
197
|
Respond with the same JSON format as before:
|
|
194
198
|
{
|
|
195
199
|
"name": "${tool.name}",
|
|
196
200
|
"description": "Updated description if needed",
|
|
197
|
-
"implementation": "
|
|
201
|
+
"implementation": "async function execute(params) { ... }",
|
|
198
202
|
"parameters": { ... },
|
|
199
203
|
"reasoning": "What was changed and why"
|
|
200
204
|
}`;
|
|
@@ -19,6 +19,7 @@ import {
|
|
|
19
19
|
export interface ToolGeneratorOptions {
|
|
20
20
|
llm: LLMBackend;
|
|
21
21
|
config: ToolSelfGenerationConfig;
|
|
22
|
+
model?: string;
|
|
22
23
|
}
|
|
23
24
|
|
|
24
25
|
export interface GenerationResult {
|
|
@@ -32,15 +33,18 @@ export interface GenerationResult {
|
|
|
32
33
|
export class ToolGenerator {
|
|
33
34
|
private readonly llm: LLMBackend;
|
|
34
35
|
private readonly config: ToolSelfGenerationConfig;
|
|
36
|
+
private readonly model: string;
|
|
35
37
|
private readonly validator: ToolValidator;
|
|
36
38
|
private readonly sandbox: ToolSandbox;
|
|
37
39
|
|
|
38
40
|
constructor(options: ToolGeneratorOptions) {
|
|
39
41
|
this.llm = options.llm;
|
|
40
42
|
this.config = options.config;
|
|
43
|
+
this.model = options.model ?? 'default';
|
|
41
44
|
this.validator = new ToolValidator({
|
|
42
45
|
llm: options.llm,
|
|
43
46
|
config: options.config,
|
|
47
|
+
model: options.model,
|
|
44
48
|
});
|
|
45
49
|
this.sandbox = new ToolSandbox(options.config.sandboxConfig);
|
|
46
50
|
}
|
|
@@ -240,6 +244,6 @@ export class ToolGenerator {
|
|
|
240
244
|
if (this.llm.complete) {
|
|
241
245
|
return this.llm.complete({ messages, temperature });
|
|
242
246
|
}
|
|
243
|
-
return this.llm.chat({ model:
|
|
247
|
+
return this.llm.chat({ model: this.model, messages, temperature });
|
|
244
248
|
}
|
|
245
249
|
}
|
|
@@ -10,6 +10,7 @@ import { buildToolValidationPrompt, parseValidationResponse } from './prompts';
|
|
|
10
10
|
export interface ToolValidatorOptions {
|
|
11
11
|
llm?: LLMBackend;
|
|
12
12
|
config: ToolSelfGenerationConfig;
|
|
13
|
+
model?: string;
|
|
13
14
|
}
|
|
14
15
|
|
|
15
16
|
interface ValidationRule {
|
|
@@ -141,12 +142,14 @@ const STATIC_VALIDATION_RULES: ValidationRule[] = [
|
|
|
141
142
|
export class ToolValidator {
|
|
142
143
|
private readonly llm?: LLMBackend;
|
|
143
144
|
private readonly config: ToolSelfGenerationConfig;
|
|
145
|
+
private readonly model: string;
|
|
144
146
|
private readonly sandbox: ToolSandbox;
|
|
145
147
|
private readonly customRules: ValidationRule[] = [];
|
|
146
148
|
|
|
147
149
|
constructor(options: ToolValidatorOptions) {
|
|
148
150
|
this.llm = options.llm;
|
|
149
151
|
this.config = options.config;
|
|
152
|
+
this.model = options.model ?? 'default';
|
|
150
153
|
this.sandbox = new ToolSandbox(options.config.sandboxConfig);
|
|
151
154
|
}
|
|
152
155
|
|
|
@@ -303,11 +306,6 @@ Be thorough but practical - focus on real issues.`,
|
|
|
303
306
|
validInput[key] = this.generateSampleValue(schema.type, schema.default);
|
|
304
307
|
}
|
|
305
308
|
testCases.push({ input: validInput });
|
|
306
|
-
|
|
307
|
-
const required = params.required as string[] | undefined;
|
|
308
|
-
testCases.push({ input: {}, shouldThrow: (required?.length ?? 0) > 0 });
|
|
309
|
-
|
|
310
|
-
testCases.push({ input: null, shouldThrow: true });
|
|
311
309
|
}
|
|
312
310
|
|
|
313
311
|
return testCases;
|
|
@@ -364,6 +362,6 @@ Be thorough but practical - focus on real issues.`,
|
|
|
364
362
|
if (this.llm.complete) {
|
|
365
363
|
return this.llm.complete({ messages, temperature });
|
|
366
364
|
}
|
|
367
|
-
return this.llm.chat({ model:
|
|
365
|
+
return this.llm.chat({ model: this.model, messages, temperature });
|
|
368
366
|
}
|
|
369
367
|
}
|