@cogitator-ai/self-modifying 17.0.16 → 17.0.18
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/LICENSE +21 -0
- package/dist/architecture-evolution/capability-analyzer.d.ts.map +1 -1
- package/dist/architecture-evolution/capability-analyzer.js +6 -3
- package/dist/architecture-evolution/capability-analyzer.js.map +1 -1
- package/dist/architecture-evolution/evolution-strategy.d.ts.map +1 -1
- package/dist/architecture-evolution/evolution-strategy.js +4 -2
- package/dist/architecture-evolution/evolution-strategy.js.map +1 -1
- package/dist/architecture-evolution/parameter-optimizer.d.ts.map +1 -1
- package/dist/architecture-evolution/parameter-optimizer.js +32 -9
- package/dist/architecture-evolution/parameter-optimizer.js.map +1 -1
- package/dist/architecture-evolution/prompts.d.ts.map +1 -1
- package/dist/architecture-evolution/prompts.js +42 -4
- package/dist/architecture-evolution/prompts.js.map +1 -1
- package/dist/constraints/modification-validator.d.ts.map +1 -1
- package/dist/constraints/modification-validator.js +16 -5
- package/dist/constraints/modification-validator.js.map +1 -1
- package/dist/constraints/rollback-manager.d.ts +1 -0
- package/dist/constraints/rollback-manager.d.ts.map +1 -1
- package/dist/constraints/rollback-manager.js +25 -1
- package/dist/constraints/rollback-manager.js.map +1 -1
- package/dist/events/event-emitter.d.ts +0 -1
- package/dist/events/event-emitter.d.ts.map +1 -1
- package/dist/events/event-emitter.js +6 -10
- package/dist/events/event-emitter.js.map +1 -1
- package/dist/meta-reasoning/meta-reasoner.d.ts +1 -1
- package/dist/meta-reasoning/meta-reasoner.d.ts.map +1 -1
- package/dist/meta-reasoning/meta-reasoner.js +22 -13
- package/dist/meta-reasoning/meta-reasoner.js.map +1 -1
- package/dist/meta-reasoning/observation-collector.d.ts.map +1 -1
- package/dist/meta-reasoning/observation-collector.js +6 -2
- package/dist/meta-reasoning/observation-collector.js.map +1 -1
- package/dist/meta-reasoning/prompts.d.ts.map +1 -1
- package/dist/meta-reasoning/prompts.js +5 -38
- package/dist/meta-reasoning/prompts.js.map +1 -1
- package/dist/meta-reasoning/strategy-selector.d.ts.map +1 -1
- package/dist/meta-reasoning/strategy-selector.js +6 -0
- package/dist/meta-reasoning/strategy-selector.js.map +1 -1
- package/dist/self-modifying-agent.d.ts +8 -1
- package/dist/self-modifying-agent.d.ts.map +1 -1
- package/dist/self-modifying-agent.js +108 -14
- package/dist/self-modifying-agent.js.map +1 -1
- package/dist/tool-generation/gap-analyzer.d.ts.map +1 -1
- package/dist/tool-generation/gap-analyzer.js +3 -2
- package/dist/tool-generation/gap-analyzer.js.map +1 -1
- package/dist/tool-generation/generated-tool-store.d.ts.map +1 -1
- package/dist/tool-generation/generated-tool-store.js +90 -10
- package/dist/tool-generation/generated-tool-store.js.map +1 -1
- package/dist/tool-generation/index.d.ts +1 -1
- package/dist/tool-generation/index.d.ts.map +1 -1
- package/dist/tool-generation/index.js +1 -1
- package/dist/tool-generation/index.js.map +1 -1
- package/dist/tool-generation/prompts.d.ts +3 -3
- package/dist/tool-generation/prompts.d.ts.map +1 -1
- package/dist/tool-generation/prompts.js +65 -12
- package/dist/tool-generation/prompts.js.map +1 -1
- package/dist/tool-generation/tool-generator.d.ts +1 -1
- package/dist/tool-generation/tool-generator.d.ts.map +1 -1
- package/dist/tool-generation/tool-generator.js +55 -3
- package/dist/tool-generation/tool-generator.js.map +1 -1
- package/dist/tool-generation/tool-sandbox.d.ts +2 -6
- package/dist/tool-generation/tool-sandbox.d.ts.map +1 -1
- package/dist/tool-generation/tool-sandbox.js +220 -130
- package/dist/tool-generation/tool-sandbox.js.map +1 -1
- package/dist/tool-generation/tool-validator.d.ts +1 -0
- package/dist/tool-generation/tool-validator.d.ts.map +1 -1
- package/dist/tool-generation/tool-validator.js +48 -1
- package/dist/tool-generation/tool-validator.js.map +1 -1
- package/dist/utils/index.d.ts.map +1 -1
- package/dist/utils/index.js +30 -5
- package/dist/utils/index.js.map +1 -1
- package/package.json +14 -14
- package/src/__tests__/self-modifying-agent.test.ts +42 -10
- package/src/architecture-evolution/capability-analyzer.ts +7 -4
- package/src/architecture-evolution/evolution-strategy.ts +5 -2
- package/src/architecture-evolution/parameter-optimizer.ts +39 -15
- package/src/architecture-evolution/prompts.ts +48 -4
- package/src/constraints/modification-validator.ts +19 -8
- package/src/constraints/rollback-manager.ts +20 -1
- package/src/events/event-emitter.ts +6 -15
- package/src/meta-reasoning/meta-reasoner.ts +22 -15
- package/src/meta-reasoning/observation-collector.ts +6 -2
- package/src/meta-reasoning/prompts.ts +5 -44
- package/src/meta-reasoning/strategy-selector.ts +6 -0
- package/src/self-modifying-agent.ts +123 -14
- package/src/tool-generation/gap-analyzer.ts +3 -2
- package/src/tool-generation/generated-tool-store.ts +97 -10
- package/src/tool-generation/index.ts +1 -1
- package/src/tool-generation/prompts.ts +81 -12
- package/src/tool-generation/tool-generator.ts +71 -3
- package/src/tool-generation/tool-sandbox.ts +241 -170
- package/src/tool-generation/tool-validator.ts +51 -1
- package/src/utils/index.ts +29 -5
package/dist/utils/index.js
CHANGED
|
@@ -6,9 +6,34 @@ export function extractJson(text) {
|
|
|
6
6
|
if (codeBlockMatch) {
|
|
7
7
|
cleaned = codeBlockMatch[1].trim();
|
|
8
8
|
}
|
|
9
|
-
const
|
|
10
|
-
|
|
9
|
+
const objectStart = cleaned.indexOf('{');
|
|
10
|
+
const arrayStart = cleaned.indexOf('[');
|
|
11
|
+
let start;
|
|
12
|
+
let open;
|
|
13
|
+
let close;
|
|
14
|
+
if (objectStart === -1 && arrayStart === -1) {
|
|
11
15
|
return null;
|
|
16
|
+
}
|
|
17
|
+
else if (objectStart === -1) {
|
|
18
|
+
start = arrayStart;
|
|
19
|
+
open = '[';
|
|
20
|
+
close = ']';
|
|
21
|
+
}
|
|
22
|
+
else if (arrayStart === -1) {
|
|
23
|
+
start = objectStart;
|
|
24
|
+
open = '{';
|
|
25
|
+
close = '}';
|
|
26
|
+
}
|
|
27
|
+
else if (objectStart < arrayStart) {
|
|
28
|
+
start = objectStart;
|
|
29
|
+
open = '{';
|
|
30
|
+
close = '}';
|
|
31
|
+
}
|
|
32
|
+
else {
|
|
33
|
+
start = arrayStart;
|
|
34
|
+
open = '[';
|
|
35
|
+
close = ']';
|
|
36
|
+
}
|
|
12
37
|
let depth = 0;
|
|
13
38
|
let inString = false;
|
|
14
39
|
let escape = false;
|
|
@@ -28,9 +53,9 @@ export function extractJson(text) {
|
|
|
28
53
|
}
|
|
29
54
|
if (inString)
|
|
30
55
|
continue;
|
|
31
|
-
if (ch ===
|
|
56
|
+
if (ch === open)
|
|
32
57
|
depth++;
|
|
33
|
-
else if (ch ===
|
|
58
|
+
else if (ch === close) {
|
|
34
59
|
depth--;
|
|
35
60
|
if (depth === 0) {
|
|
36
61
|
return cleaned.slice(start, i + 1);
|
|
@@ -40,7 +65,7 @@ export function extractJson(text) {
|
|
|
40
65
|
if (depth > 0) {
|
|
41
66
|
let repaired = cleaned.slice(start);
|
|
42
67
|
repaired = repaired.replace(/,\s*$/, '');
|
|
43
|
-
repaired +=
|
|
68
|
+
repaired += close.repeat(depth);
|
|
44
69
|
try {
|
|
45
70
|
JSON.parse(repaired);
|
|
46
71
|
return repaired;
|
package/dist/utils/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/utils/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAEvC,MAAM,UAAU,WAAW,CAAC,IAAY;IACtC,IAAI,OAAO,GAAG,IAAI,CAAC;IAEnB,MAAM,cAAc,GAAG,iCAAiC,CAAC;IACzD,MAAM,cAAc,GAAG,cAAc,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;IACpD,IAAI,cAAc,EAAE,CAAC;QACnB,OAAO,GAAG,cAAc,CAAC,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC;IACrC,CAAC;IAED,MAAM,
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/utils/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAEvC,MAAM,UAAU,WAAW,CAAC,IAAY;IACtC,IAAI,OAAO,GAAG,IAAI,CAAC;IAEnB,MAAM,cAAc,GAAG,iCAAiC,CAAC;IACzD,MAAM,cAAc,GAAG,cAAc,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;IACpD,IAAI,cAAc,EAAE,CAAC;QACnB,OAAO,GAAG,cAAc,CAAC,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC;IACrC,CAAC;IAED,MAAM,WAAW,GAAG,OAAO,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;IACzC,MAAM,UAAU,GAAG,OAAO,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;IAExC,IAAI,KAAa,CAAC;IAClB,IAAI,IAAY,CAAC;IACjB,IAAI,KAAa,CAAC;IAElB,IAAI,WAAW,KAAK,CAAC,CAAC,IAAI,UAAU,KAAK,CAAC,CAAC,EAAE,CAAC;QAC5C,OAAO,IAAI,CAAC;IACd,CAAC;SAAM,IAAI,WAAW,KAAK,CAAC,CAAC,EAAE,CAAC;QAC9B,KAAK,GAAG,UAAU,CAAC;QACnB,IAAI,GAAG,GAAG,CAAC;QACX,KAAK,GAAG,GAAG,CAAC;IACd,CAAC;SAAM,IAAI,UAAU,KAAK,CAAC,CAAC,EAAE,CAAC;QAC7B,KAAK,GAAG,WAAW,CAAC;QACpB,IAAI,GAAG,GAAG,CAAC;QACX,KAAK,GAAG,GAAG,CAAC;IACd,CAAC;SAAM,IAAI,WAAW,GAAG,UAAU,EAAE,CAAC;QACpC,KAAK,GAAG,WAAW,CAAC;QACpB,IAAI,GAAG,GAAG,CAAC;QACX,KAAK,GAAG,GAAG,CAAC;IACd,CAAC;SAAM,CAAC;QACN,KAAK,GAAG,UAAU,CAAC;QACnB,IAAI,GAAG,GAAG,CAAC;QACX,KAAK,GAAG,GAAG,CAAC;IACd,CAAC;IAED,IAAI,KAAK,GAAG,CAAC,CAAC;IACd,IAAI,QAAQ,GAAG,KAAK,CAAC;IACrB,IAAI,MAAM,GAAG,KAAK,CAAC;IAEnB,KAAK,IAAI,CAAC,GAAG,KAAK,EAAE,CAAC,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE,CAAC;QAC5C,MAAM,EAAE,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;QAEtB,IAAI,MAAM,EAAE,CAAC;YACX,MAAM,GAAG,KAAK,CAAC;YACf,SAAS;QACX,CAAC;QAED,IAAI,EAAE,KAAK,IAAI,IAAI,QAAQ,EAAE,CAAC;YAC5B,MAAM,GAAG,IAAI,CAAC;YACd,SAAS;QACX,CAAC;QAED,IAAI,EAAE,KAAK,GAAG,EAAE,CAAC;YACf,QAAQ,GAAG,CAAC,QAAQ,CAAC;YACrB,SAAS;QACX,CAAC;QAED,IAAI,QAAQ;YAAE,SAAS;QAEvB,IAAI,EAAE,KAAK,IAAI;YAAE,KAAK,EAAE,CAAC;aACpB,IAAI,EAAE,KAAK,KAAK,EAAE,CAAC;YACtB,KAAK,EAAE,CAAC;YACR,IAAI,KAAK,KAAK,CAAC,EAAE,CAAC;gBAChB,OAAO,OAAO,CAAC,KAAK,CAAC,KAAK,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;YACrC,CAAC;QACH,CAAC;IACH,CAAC;IAED,IAAI,KAAK,GAAG,CAAC,EAAE,CAAC;QACd,IAAI,QAAQ,GAAG,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;QACpC,QAAQ,GAAG,QAAQ,CAAC,OAAO,CAAC,OAAO,EAAE,EAAE,CAAC,CAAC;QACzC,QAAQ,IAAI,KAAK,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;QAChC,IAAI,CAAC;YACH,IAAI,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC;YACrB,OAAO,QAAQ,CAAC;QAClB,CAAC;QAAC,MAAM,CAAC;YACP,OAAO,IAAI,CAAC;QACd,CAAC;IACH,CAAC;IAED,OAAO,IAAI,CAAC;AACd,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@cogitator-ai/self-modifying",
|
|
3
|
-
"version": "17.0.
|
|
3
|
+
"version": "17.0.18",
|
|
4
4
|
"description": "Self-modifying agent capabilities for Cogitator - tool generation, meta-reasoning, architecture evolution",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|
|
@@ -16,22 +16,14 @@
|
|
|
16
16
|
"dist",
|
|
17
17
|
"src"
|
|
18
18
|
],
|
|
19
|
-
"scripts": {
|
|
20
|
-
"build": "tsc",
|
|
21
|
-
"dev": "tsc --watch",
|
|
22
|
-
"test": "vitest run",
|
|
23
|
-
"test:watch": "vitest",
|
|
24
|
-
"lint": "eslint src --ext .ts",
|
|
25
|
-
"typecheck": "tsc --noEmit"
|
|
26
|
-
},
|
|
27
19
|
"dependencies": {
|
|
28
|
-
"@cogitator-ai/types": "workspace:*",
|
|
29
20
|
"nanoid": "^5.0.4",
|
|
30
|
-
"zod": "^4.3.6"
|
|
21
|
+
"zod": "^4.3.6",
|
|
22
|
+
"@cogitator-ai/types": "0.22.3"
|
|
31
23
|
},
|
|
32
24
|
"peerDependencies": {
|
|
33
|
-
"@cogitator-ai/core": "
|
|
34
|
-
"@cogitator-ai/neuro-symbolic": "
|
|
25
|
+
"@cogitator-ai/core": "0.19.4",
|
|
26
|
+
"@cogitator-ai/neuro-symbolic": "15.1.16"
|
|
35
27
|
},
|
|
36
28
|
"peerDependenciesMeta": {
|
|
37
29
|
"@cogitator-ai/neuro-symbolic": {
|
|
@@ -61,5 +53,13 @@
|
|
|
61
53
|
"publishConfig": {
|
|
62
54
|
"registry": "https://npm.pkg.github.com",
|
|
63
55
|
"access": "public"
|
|
56
|
+
},
|
|
57
|
+
"scripts": {
|
|
58
|
+
"build": "tsc",
|
|
59
|
+
"dev": "tsc --watch",
|
|
60
|
+
"test": "vitest run",
|
|
61
|
+
"test:watch": "vitest",
|
|
62
|
+
"lint": "eslint src --ext .ts",
|
|
63
|
+
"typecheck": "tsc --noEmit"
|
|
64
64
|
}
|
|
65
|
-
}
|
|
65
|
+
}
|
|
@@ -46,7 +46,11 @@ describe('SelfModifyingAgent tool execution', () => {
|
|
|
46
46
|
.mockResolvedValueOnce(
|
|
47
47
|
chatResponse('', [{ id: 'call_1', name: 'calculator', arguments: { input: '6*7' } }])
|
|
48
48
|
)
|
|
49
|
-
.mockResolvedValueOnce(
|
|
49
|
+
.mockResolvedValueOnce(
|
|
50
|
+
chatResponse(
|
|
51
|
+
'The answer to your calculation is 42. I used the calculator tool to compute 6 times 7.'
|
|
52
|
+
)
|
|
53
|
+
),
|
|
50
54
|
};
|
|
51
55
|
|
|
52
56
|
const agent = createMockAgent([calculator]);
|
|
@@ -63,7 +67,9 @@ describe('SelfModifyingAgent tool execution', () => {
|
|
|
63
67
|
|
|
64
68
|
const result = await selfMod.run('What is 6 times 7?');
|
|
65
69
|
|
|
66
|
-
expect(result.output).toBe(
|
|
70
|
+
expect(result.output).toBe(
|
|
71
|
+
'The answer to your calculation is 42. I used the calculator tool to compute 6 times 7.'
|
|
72
|
+
);
|
|
67
73
|
expect(calculator.execute).toHaveBeenCalledOnce();
|
|
68
74
|
expect(calculator.execute).toHaveBeenCalledWith(
|
|
69
75
|
{ input: '6*7' },
|
|
@@ -89,7 +95,11 @@ describe('SelfModifyingAgent tool execution', () => {
|
|
|
89
95
|
.mockResolvedValueOnce(
|
|
90
96
|
chatResponse('', [{ id: 'call_2', name: 'format', arguments: { input: 'found it' } }])
|
|
91
97
|
)
|
|
92
|
-
.mockResolvedValueOnce(
|
|
98
|
+
.mockResolvedValueOnce(
|
|
99
|
+
chatResponse(
|
|
100
|
+
'Here is your formatted result. I searched for the information and then formatted it for you.'
|
|
101
|
+
)
|
|
102
|
+
),
|
|
93
103
|
};
|
|
94
104
|
|
|
95
105
|
const agent = createMockAgent([search, format]);
|
|
@@ -106,7 +116,9 @@ describe('SelfModifyingAgent tool execution', () => {
|
|
|
106
116
|
|
|
107
117
|
const result = await selfMod.run('Search and format');
|
|
108
118
|
|
|
109
|
-
expect(result.output).toBe(
|
|
119
|
+
expect(result.output).toBe(
|
|
120
|
+
'Here is your formatted result. I searched for the information and then formatted it for you.'
|
|
121
|
+
);
|
|
110
122
|
expect(search.execute).toHaveBeenCalledOnce();
|
|
111
123
|
expect(format.execute).toHaveBeenCalledOnce();
|
|
112
124
|
expect(vi.mocked(mockLLM.chat!)).toHaveBeenCalledTimes(3);
|
|
@@ -122,7 +134,11 @@ describe('SelfModifyingAgent tool execution', () => {
|
|
|
122
134
|
.mockResolvedValueOnce(
|
|
123
135
|
chatResponse('', [{ id: 'call_1', name: 'broken', arguments: { input: 'test' } }])
|
|
124
136
|
)
|
|
125
|
-
.mockResolvedValueOnce(
|
|
137
|
+
.mockResolvedValueOnce(
|
|
138
|
+
chatResponse(
|
|
139
|
+
'The tool failed but I can still help you with your request. Let me try a different approach.'
|
|
140
|
+
)
|
|
141
|
+
),
|
|
126
142
|
};
|
|
127
143
|
|
|
128
144
|
const agent = createMockAgent([failTool]);
|
|
@@ -139,7 +155,9 @@ describe('SelfModifyingAgent tool execution', () => {
|
|
|
139
155
|
|
|
140
156
|
const result = await selfMod.run('Use the broken tool');
|
|
141
157
|
|
|
142
|
-
expect(result.output).toBe(
|
|
158
|
+
expect(result.output).toBe(
|
|
159
|
+
'The tool failed but I can still help you with your request. Let me try a different approach.'
|
|
160
|
+
);
|
|
143
161
|
const secondCall = vi.mocked(mockLLM.chat!).mock.calls[1][0];
|
|
144
162
|
const toolMsg = secondCall.messages.find((m: { role: string }) => m.role === 'tool');
|
|
145
163
|
expect(toolMsg?.content).toContain('tool crashed');
|
|
@@ -152,7 +170,11 @@ describe('SelfModifyingAgent tool execution', () => {
|
|
|
152
170
|
.mockResolvedValueOnce(
|
|
153
171
|
chatResponse('', [{ id: 'call_1', name: 'nonexistent', arguments: { input: 'x' } }])
|
|
154
172
|
)
|
|
155
|
-
.mockResolvedValueOnce(
|
|
173
|
+
.mockResolvedValueOnce(
|
|
174
|
+
chatResponse(
|
|
175
|
+
'I could not find that tool in my available tools. Let me try to help you without it.'
|
|
176
|
+
)
|
|
177
|
+
),
|
|
156
178
|
};
|
|
157
179
|
|
|
158
180
|
const agent = createMockAgent([]);
|
|
@@ -169,7 +191,9 @@ describe('SelfModifyingAgent tool execution', () => {
|
|
|
169
191
|
|
|
170
192
|
const result = await selfMod.run('Call a tool');
|
|
171
193
|
|
|
172
|
-
expect(result.output).toBe(
|
|
194
|
+
expect(result.output).toBe(
|
|
195
|
+
'I could not find that tool in my available tools. Let me try to help you without it.'
|
|
196
|
+
);
|
|
173
197
|
const secondCall = vi.mocked(mockLLM.chat!).mock.calls[1][0];
|
|
174
198
|
const toolMsg = secondCall.messages.find((m: { role: string }) => m.role === 'tool');
|
|
175
199
|
expect(toolMsg?.content).toContain('not found');
|
|
@@ -177,7 +201,13 @@ describe('SelfModifyingAgent tool execution', () => {
|
|
|
177
201
|
|
|
178
202
|
it('works without any tools (no tools passed to LLM)', async () => {
|
|
179
203
|
const mockLLM: Partial<LLMBackend> = {
|
|
180
|
-
chat: vi
|
|
204
|
+
chat: vi
|
|
205
|
+
.fn()
|
|
206
|
+
.mockResolvedValueOnce(
|
|
207
|
+
chatResponse(
|
|
208
|
+
'Hello world! I am a test assistant and I am here to help you with your questions.'
|
|
209
|
+
)
|
|
210
|
+
),
|
|
181
211
|
};
|
|
182
212
|
|
|
183
213
|
const agent = createMockAgent([]);
|
|
@@ -194,7 +224,9 @@ describe('SelfModifyingAgent tool execution', () => {
|
|
|
194
224
|
|
|
195
225
|
const result = await selfMod.run('Just say hi');
|
|
196
226
|
|
|
197
|
-
expect(result.output).toBe(
|
|
227
|
+
expect(result.output).toBe(
|
|
228
|
+
'Hello world! I am a test assistant and I am here to help you with your questions.'
|
|
229
|
+
);
|
|
198
230
|
const chatCall = vi.mocked(mockLLM.chat!).mock.calls[0][0];
|
|
199
231
|
expect(chatCall.tools).toBeUndefined();
|
|
200
232
|
});
|
|
@@ -121,6 +121,7 @@ const COMPLEXITY_INDICATORS = {
|
|
|
121
121
|
simple: ['explain', 'define', 'list', 'describe', 'show'],
|
|
122
122
|
moderate: ['compare', 'analyze', 'summarize', 'evaluate', 'implement'],
|
|
123
123
|
complex: ['design', 'architect', 'optimize', 'comprehensive', 'detailed'],
|
|
124
|
+
expert: ['expert', 'advanced', 'specialized', 'intricate', 'sophisticated'],
|
|
124
125
|
extreme: ['novel', 'research', 'breakthrough', 'state-of-the-art', 'cutting-edge'],
|
|
125
126
|
};
|
|
126
127
|
|
|
@@ -237,6 +238,8 @@ export class CapabilityAnalyzer {
|
|
|
237
238
|
domain,
|
|
238
239
|
estimatedTokens: this.estimateTokens(wordCount, complexity),
|
|
239
240
|
requiresTools: toolAnalysis.requiresTools,
|
|
241
|
+
requiresReasoning: domain === 'reasoning' || domain === 'coding',
|
|
242
|
+
requiresCreativity: domain === 'creative',
|
|
240
243
|
toolIntensity: toolAnalysis.intensity,
|
|
241
244
|
reasoningDepth: this.estimateReasoningDepth(complexity, domain),
|
|
242
245
|
creativityLevel:
|
|
@@ -375,10 +378,6 @@ export class CapabilityAnalyzer {
|
|
|
375
378
|
domain: TaskProfile['domain'],
|
|
376
379
|
task: string
|
|
377
380
|
): TaskProfile['accuracyRequirement'] {
|
|
378
|
-
if (domain === 'coding' || domain === 'factual') {
|
|
379
|
-
return 'high';
|
|
380
|
-
}
|
|
381
|
-
|
|
382
381
|
const criticalIndicators = ['critical', 'exact', 'precise', 'must be correct', 'no errors'];
|
|
383
382
|
for (const indicator of criticalIndicators) {
|
|
384
383
|
if (task.includes(indicator)) {
|
|
@@ -386,6 +385,10 @@ export class CapabilityAnalyzer {
|
|
|
386
385
|
}
|
|
387
386
|
}
|
|
388
387
|
|
|
388
|
+
if (domain === 'coding' || domain === 'factual') {
|
|
389
|
+
return 'high';
|
|
390
|
+
}
|
|
391
|
+
|
|
389
392
|
const approximateIndicators = ['rough', 'approximate', 'estimate', 'about', 'roughly'];
|
|
390
393
|
for (const indicator of approximateIndicators) {
|
|
391
394
|
if (task.includes(indicator)) {
|
|
@@ -152,8 +152,9 @@ export class EvolutionStrategy {
|
|
|
152
152
|
|
|
153
153
|
const d = shape - 1 / 3;
|
|
154
154
|
const c = 1 / Math.sqrt(9 * d);
|
|
155
|
+
const maxIterations = 1000;
|
|
155
156
|
|
|
156
|
-
|
|
157
|
+
for (let i = 0; i < maxIterations; i++) {
|
|
157
158
|
let x: number;
|
|
158
159
|
let v: number;
|
|
159
160
|
|
|
@@ -173,6 +174,8 @@ export class EvolutionStrategy {
|
|
|
173
174
|
return d * v;
|
|
174
175
|
}
|
|
175
176
|
}
|
|
177
|
+
|
|
178
|
+
return d;
|
|
176
179
|
}
|
|
177
180
|
|
|
178
181
|
private sampleNormal(): number {
|
|
@@ -202,7 +205,7 @@ export class EvolutionStrategy {
|
|
|
202
205
|
(this.strategy.explorationConstant ?? 2) / Math.sqrt(this.totalSelections)
|
|
203
206
|
);
|
|
204
207
|
case 'thompson_sampling':
|
|
205
|
-
return 0.
|
|
208
|
+
return Math.max(0.05, 1 / Math.sqrt(this.totalSelections + 1));
|
|
206
209
|
default:
|
|
207
210
|
return 0.1;
|
|
208
211
|
}
|
|
@@ -82,11 +82,20 @@ export class ParameterOptimizer {
|
|
|
82
82
|
|
|
83
83
|
const mergedConfig = this.mergeConfigs(this.baseConfig, selection.candidate.config);
|
|
84
84
|
|
|
85
|
+
const bestEvaluated = this.candidates
|
|
86
|
+
.filter((c) => c.evaluationCount > 0)
|
|
87
|
+
.sort((a, b) => b.score - a.score)[0];
|
|
88
|
+
|
|
89
|
+
const shouldAdopt =
|
|
90
|
+
!bestEvaluated ||
|
|
91
|
+
selection.candidate.id === bestEvaluated.id ||
|
|
92
|
+
selection.score >= bestEvaluated.score * 0.9;
|
|
93
|
+
|
|
85
94
|
return {
|
|
86
95
|
recommendedConfig: mergedConfig,
|
|
87
96
|
candidate: selection.candidate,
|
|
88
97
|
metrics: this.calculateMetrics(),
|
|
89
|
-
shouldAdopt
|
|
98
|
+
shouldAdopt,
|
|
90
99
|
confidence: selection.score,
|
|
91
100
|
reasoning: selection.reasoning,
|
|
92
101
|
};
|
|
@@ -247,23 +256,20 @@ export class ParameterOptimizer {
|
|
|
247
256
|
const mutated = { ...config };
|
|
248
257
|
const mutationRate = 0.3;
|
|
249
258
|
|
|
250
|
-
if (Math.random() < mutationRate
|
|
251
|
-
mutated.temperature
|
|
252
|
-
|
|
253
|
-
Math.min(2, mutated.temperature + (Math.random() - 0.5) * 0.3)
|
|
254
|
-
);
|
|
259
|
+
if (Math.random() < mutationRate) {
|
|
260
|
+
const base = mutated.temperature ?? this.baseConfig.temperature;
|
|
261
|
+
mutated.temperature = Math.max(0, Math.min(2, base + (Math.random() - 0.5) * 0.3));
|
|
255
262
|
}
|
|
256
263
|
|
|
257
|
-
if (Math.random() < mutationRate
|
|
264
|
+
if (Math.random() < mutationRate) {
|
|
265
|
+
const base = mutated.maxTokens ?? this.baseConfig.maxTokens;
|
|
258
266
|
const delta = Math.floor((Math.random() - 0.5) * 1000);
|
|
259
|
-
mutated.maxTokens = Math.max(100, Math.min(32000,
|
|
267
|
+
mutated.maxTokens = Math.max(100, Math.min(32000, base + delta));
|
|
260
268
|
}
|
|
261
269
|
|
|
262
|
-
if (Math.random() < mutationRate
|
|
263
|
-
mutated.reflectionDepth
|
|
264
|
-
|
|
265
|
-
Math.min(5, mutated.reflectionDepth + Math.round(Math.random() * 2 - 1))
|
|
266
|
-
);
|
|
270
|
+
if (Math.random() < mutationRate) {
|
|
271
|
+
const base = mutated.reflectionDepth ?? this.baseConfig.reflectionDepth;
|
|
272
|
+
mutated.reflectionDepth = Math.max(0, Math.min(5, base + Math.round(Math.random() * 2 - 1)));
|
|
267
273
|
}
|
|
268
274
|
|
|
269
275
|
return mutated;
|
|
@@ -316,12 +322,16 @@ export class ParameterOptimizer {
|
|
|
316
322
|
}
|
|
317
323
|
|
|
318
324
|
private shouldEvolve(): boolean {
|
|
319
|
-
const
|
|
325
|
+
const evaluatedCandidates = this.candidates.filter((c) => c.evaluationCount > 0);
|
|
326
|
+
if (evaluatedCandidates.length === 0) return false;
|
|
327
|
+
|
|
328
|
+
const minEvaluations = evaluatedCandidates.reduce(
|
|
320
329
|
(min, c) => Math.min(min, c.evaluationCount),
|
|
321
330
|
Infinity
|
|
322
331
|
);
|
|
323
332
|
|
|
324
|
-
|
|
333
|
+
const minRequired = this.config.minEvaluationsBeforeEvolution ?? 3;
|
|
334
|
+
if (minEvaluations < minRequired) return false;
|
|
325
335
|
|
|
326
336
|
const evaluationsSinceEvolution = this.history.filter(
|
|
327
337
|
(h) => h.timestamp > this.getLastEvolutionTime()
|
|
@@ -418,6 +428,20 @@ export class ParameterOptimizer {
|
|
|
418
428
|
fields++;
|
|
419
429
|
}
|
|
420
430
|
|
|
431
|
+
if (
|
|
432
|
+
a.toolStrategy !== undefined &&
|
|
433
|
+
b.toolStrategy !== undefined &&
|
|
434
|
+
a.toolStrategy !== b.toolStrategy
|
|
435
|
+
) {
|
|
436
|
+
distance += 1;
|
|
437
|
+
fields++;
|
|
438
|
+
}
|
|
439
|
+
|
|
440
|
+
if (a.reflectionDepth !== undefined && b.reflectionDepth !== undefined) {
|
|
441
|
+
distance += Math.abs(a.reflectionDepth - b.reflectionDepth) / 5;
|
|
442
|
+
fields++;
|
|
443
|
+
}
|
|
444
|
+
|
|
421
445
|
return fields > 0 ? distance / fields : 0;
|
|
422
446
|
}
|
|
423
447
|
|
|
@@ -37,10 +37,12 @@ ${contextSection}
|
|
|
37
37
|
|
|
38
38
|
Respond with a JSON object:
|
|
39
39
|
{
|
|
40
|
-
"complexity": "trivial" | "simple" | "moderate" | "complex" | "extreme",
|
|
40
|
+
"complexity": "trivial" | "simple" | "moderate" | "complex" | "expert" | "extreme",
|
|
41
41
|
"domain": "general" | "coding" | "reasoning" | "creative" | "factual" | "conversational",
|
|
42
42
|
"estimatedTokens": number,
|
|
43
43
|
"requiresTools": boolean,
|
|
44
|
+
"requiresReasoning": boolean,
|
|
45
|
+
"requiresCreativity": boolean,
|
|
44
46
|
"toolIntensity": "none" | "light" | "moderate" | "heavy",
|
|
45
47
|
"reasoningDepth": "shallow" | "moderate" | "deep" | "exhaustive",
|
|
46
48
|
"creativityLevel": "low" | "moderate" | "high",
|
|
@@ -152,6 +154,8 @@ export function parseTaskProfileResponse(response: string): TaskProfile | null {
|
|
|
152
154
|
domain: parsed.domain || 'general',
|
|
153
155
|
estimatedTokens: parsed.estimatedTokens || 1000,
|
|
154
156
|
requiresTools: Boolean(parsed.requiresTools),
|
|
157
|
+
requiresReasoning: Boolean(parsed.requiresReasoning),
|
|
158
|
+
requiresCreativity: Boolean(parsed.requiresCreativity),
|
|
155
159
|
toolIntensity: parsed.toolIntensity || 'none',
|
|
156
160
|
reasoningDepth: parsed.reasoningDepth || 'moderate',
|
|
157
161
|
creativityLevel: parsed.creativityLevel || 'moderate',
|
|
@@ -164,11 +168,11 @@ export function parseTaskProfileResponse(response: string): TaskProfile | null {
|
|
|
164
168
|
}
|
|
165
169
|
|
|
166
170
|
export function parseCandidateGenerationResponse(response: string): EvolutionCandidate[] {
|
|
167
|
-
const
|
|
168
|
-
if (!
|
|
171
|
+
const json = extractJsonArray(response);
|
|
172
|
+
if (!json) return [];
|
|
169
173
|
|
|
170
174
|
try {
|
|
171
|
-
const parsed = JSON.parse(
|
|
175
|
+
const parsed = JSON.parse(json);
|
|
172
176
|
if (!Array.isArray(parsed)) return [];
|
|
173
177
|
|
|
174
178
|
return parsed
|
|
@@ -214,3 +218,43 @@ export function parsePerformanceAnalysisResponse(response: string): {
|
|
|
214
218
|
return null;
|
|
215
219
|
}
|
|
216
220
|
}
|
|
221
|
+
|
|
222
|
+
function extractJsonArray(text: string): string | null {
|
|
223
|
+
const start = text.indexOf('[');
|
|
224
|
+
if (start === -1) return null;
|
|
225
|
+
|
|
226
|
+
let depth = 0;
|
|
227
|
+
let inString = false;
|
|
228
|
+
let escape = false;
|
|
229
|
+
|
|
230
|
+
for (let i = start; i < text.length; i++) {
|
|
231
|
+
const ch = text[i];
|
|
232
|
+
|
|
233
|
+
if (escape) {
|
|
234
|
+
escape = false;
|
|
235
|
+
continue;
|
|
236
|
+
}
|
|
237
|
+
|
|
238
|
+
if (ch === '\\' && inString) {
|
|
239
|
+
escape = true;
|
|
240
|
+
continue;
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
if (ch === '"') {
|
|
244
|
+
inString = !inString;
|
|
245
|
+
continue;
|
|
246
|
+
}
|
|
247
|
+
|
|
248
|
+
if (inString) continue;
|
|
249
|
+
|
|
250
|
+
if (ch === '[' || ch === '{') depth++;
|
|
251
|
+
else if (ch === ']' || ch === '}') {
|
|
252
|
+
depth--;
|
|
253
|
+
if (depth === 0) {
|
|
254
|
+
return text.slice(start, i + 1);
|
|
255
|
+
}
|
|
256
|
+
}
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
return null;
|
|
260
|
+
}
|
|
@@ -92,10 +92,21 @@ export class ModificationValidator {
|
|
|
92
92
|
return this.evaluateExpression(rule, request.payload as Record<string, unknown>);
|
|
93
93
|
}
|
|
94
94
|
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
)
|
|
95
|
+
const context = request.payload as Record<string, unknown>;
|
|
96
|
+
const checks: boolean[] = [];
|
|
97
|
+
|
|
98
|
+
if (rule.expression) {
|
|
99
|
+
checks.push(this.evaluateExpression(rule.expression, context));
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
if (rule.pattern) {
|
|
103
|
+
const subject = JSON.stringify(request.changes ?? request.payload ?? '');
|
|
104
|
+
checks.push(rule.pattern.test(subject));
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
if (checks.length === 0) return false;
|
|
108
|
+
|
|
109
|
+
return checks.every(Boolean);
|
|
99
110
|
}
|
|
100
111
|
|
|
101
112
|
private evaluateExpression(expression: string, context: Record<string, unknown>): boolean {
|
|
@@ -181,7 +192,7 @@ export class ModificationValidator {
|
|
|
181
192
|
): Promise<ConstraintCheckResult[]> {
|
|
182
193
|
const results: ConstraintCheckResult[] = [];
|
|
183
194
|
|
|
184
|
-
if (request.type !== 'tool_generation') {
|
|
195
|
+
if (request.type !== 'tool_generation' && request.type !== 'tool_creation') {
|
|
185
196
|
return results;
|
|
186
197
|
}
|
|
187
198
|
|
|
@@ -239,7 +250,7 @@ export class ModificationValidator {
|
|
|
239
250
|
|
|
240
251
|
if (
|
|
241
252
|
constraint.maxTokensPerRun &&
|
|
242
|
-
payload.tokensUsed &&
|
|
253
|
+
payload.tokensUsed != null &&
|
|
243
254
|
payload.tokensUsed > constraint.maxTokensPerRun
|
|
244
255
|
) {
|
|
245
256
|
satisfied = false;
|
|
@@ -249,7 +260,7 @@ export class ModificationValidator {
|
|
|
249
260
|
if (
|
|
250
261
|
satisfied &&
|
|
251
262
|
constraint.maxCostPerRun &&
|
|
252
|
-
payload.cost &&
|
|
263
|
+
payload.cost != null &&
|
|
253
264
|
payload.cost > constraint.maxCostPerRun
|
|
254
265
|
) {
|
|
255
266
|
satisfied = false;
|
|
@@ -259,7 +270,7 @@ export class ModificationValidator {
|
|
|
259
270
|
if (
|
|
260
271
|
satisfied &&
|
|
261
272
|
constraint.maxToolsActive &&
|
|
262
|
-
payload.activeTools &&
|
|
273
|
+
payload.activeTools != null &&
|
|
263
274
|
payload.activeTools > constraint.maxToolsActive
|
|
264
275
|
) {
|
|
265
276
|
satisfied = false;
|
|
@@ -119,11 +119,30 @@ export class RollbackManager {
|
|
|
119
119
|
if (!checkpoint) return null;
|
|
120
120
|
|
|
121
121
|
return {
|
|
122
|
-
agentConfig: checkpoint.agentConfig
|
|
122
|
+
agentConfig: this.toAgentConfig(checkpoint.agentConfig),
|
|
123
123
|
tools: checkpoint.tools.map((t) => ({ ...t })),
|
|
124
124
|
};
|
|
125
125
|
}
|
|
126
126
|
|
|
127
|
+
private toAgentConfig(record: Record<string, unknown>): AgentConfig {
|
|
128
|
+
const config: AgentConfig = {
|
|
129
|
+
name: typeof record.name === 'string' ? record.name : 'agent',
|
|
130
|
+
model: typeof record.model === 'string' ? record.model : 'default',
|
|
131
|
+
instructions: typeof record.instructions === 'string' ? record.instructions : '',
|
|
132
|
+
};
|
|
133
|
+
|
|
134
|
+
if (typeof record.id === 'string') config.id = record.id;
|
|
135
|
+
if (typeof record.description === 'string') config.description = record.description;
|
|
136
|
+
if (typeof record.provider === 'string') config.provider = record.provider;
|
|
137
|
+
if (typeof record.temperature === 'number') config.temperature = record.temperature;
|
|
138
|
+
if (typeof record.topP === 'number') config.topP = record.topP;
|
|
139
|
+
if (typeof record.maxTokens === 'number') config.maxTokens = record.maxTokens;
|
|
140
|
+
if (typeof record.maxIterations === 'number') config.maxIterations = record.maxIterations;
|
|
141
|
+
if (typeof record.timeout === 'number') config.timeout = record.timeout;
|
|
142
|
+
|
|
143
|
+
return config;
|
|
144
|
+
}
|
|
145
|
+
|
|
127
146
|
async rollbackToLatest(
|
|
128
147
|
agentId: string
|
|
129
148
|
): Promise<{ agentConfig: AgentConfig; tools: Tool[] } | null> {
|
|
@@ -30,7 +30,7 @@ export class SelfModifyingEventEmitter {
|
|
|
30
30
|
...(wildcardHandlers ? [...wildcardHandlers] : []),
|
|
31
31
|
];
|
|
32
32
|
|
|
33
|
-
await Promise.allSettled(
|
|
33
|
+
const results = await Promise.allSettled(
|
|
34
34
|
allHandlers.map((h) => {
|
|
35
35
|
try {
|
|
36
36
|
return Promise.resolve(h(event));
|
|
@@ -39,21 +39,12 @@ export class SelfModifyingEventEmitter {
|
|
|
39
39
|
}
|
|
40
40
|
})
|
|
41
41
|
);
|
|
42
|
-
}
|
|
43
42
|
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
): SelfModifyingEvent {
|
|
50
|
-
return {
|
|
51
|
-
type,
|
|
52
|
-
runId,
|
|
53
|
-
agentId,
|
|
54
|
-
timestamp: new Date(),
|
|
55
|
-
data,
|
|
56
|
-
};
|
|
43
|
+
for (const result of results) {
|
|
44
|
+
if (result.status === 'rejected') {
|
|
45
|
+
console.error(`[self-modifying] event handler for "${event.type}" failed:`, result.reason);
|
|
46
|
+
}
|
|
47
|
+
}
|
|
57
48
|
}
|
|
58
49
|
|
|
59
50
|
removeAllListeners(event?: SelfModifyingEventType | '*'): void {
|