@aigne/core 0.4.205-0 → 0.4.205-1
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/lib/cjs/agent.js +60 -0
- package/lib/cjs/definitions/data-type-schema.js +46 -0
- package/lib/cjs/definitions/memory.js +21 -0
- package/lib/cjs/function-agent.js +1 -1
- package/lib/cjs/function-runner.js +2 -2
- package/lib/cjs/index.js +1 -1
- package/lib/cjs/llm-agent.js +19 -126
- package/lib/cjs/llm-decision-agent.js +40 -33
- package/lib/cjs/llm-model.js +2 -2
- package/lib/cjs/local-function-agent.js +11 -9
- package/lib/cjs/pipeline-agent.js +2 -4
- package/lib/cjs/runnable.js +3 -1
- package/lib/cjs/tsconfig.tsbuildinfo +1 -1
- package/lib/cjs/utils/message-utils.js +62 -0
- package/lib/cjs/utils/nullable.js +2 -0
- package/lib/cjs/utils/ordered-map.js +12 -0
- package/lib/cjs/utils/stream-utils.js +43 -5
- package/lib/esm/agent.js +53 -0
- package/lib/esm/definitions/data-type-schema.js +43 -0
- package/lib/esm/definitions/memory.js +18 -0
- package/lib/esm/function-agent.js +1 -1
- package/lib/esm/function-runner.js +2 -2
- package/lib/esm/index.js +1 -1
- package/lib/esm/llm-agent.js +21 -125
- package/lib/esm/llm-decision-agent.js +41 -34
- package/lib/esm/llm-model.js +2 -2
- package/lib/esm/local-function-agent.js +11 -9
- package/lib/esm/pipeline-agent.js +2 -4
- package/lib/esm/runnable.js +3 -1
- package/lib/esm/tsconfig.tsbuildinfo +1 -1
- package/lib/esm/utils/message-utils.js +57 -0
- package/lib/esm/utils/nullable.js +1 -0
- package/lib/esm/utils/ordered-map.js +12 -0
- package/lib/esm/utils/stream-utils.js +42 -5
- package/lib/types/agent.d.ts +42 -0
- package/lib/types/definitions/data-type-schema.d.ts +40 -0
- package/lib/types/definitions/memory.d.ts +40 -0
- package/lib/types/function-agent.d.ts +1 -1
- package/lib/types/function-runner.d.ts +2 -1
- package/lib/types/index.d.ts +1 -1
- package/lib/types/llm-agent.d.ts +34 -63
- package/lib/types/llm-decision-agent.d.ts +54 -30
- package/lib/types/llm-model.d.ts +2 -1
- package/lib/types/local-function-agent.d.ts +50 -19
- package/lib/types/memorable.d.ts +2 -1
- package/lib/types/pipeline-agent.d.ts +2 -3
- package/lib/types/runnable.d.ts +8 -2
- package/lib/types/tsconfig.tsbuildinfo +1 -1
- package/lib/types/utils/message-utils.d.ts +18 -0
- package/lib/types/utils/nullable.d.ts +7 -0
- package/lib/types/utils/ordered-map.d.ts +3 -0
- package/lib/types/utils/stream-utils.d.ts +12 -1
- package/lib/types/utils/union.d.ts +1 -1
- package/package.json +1 -1
package/lib/cjs/agent.js
ADDED
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.Agent = void 0;
|
|
7
|
+
const logger_1 = __importDefault(require("./logger"));
|
|
8
|
+
const runnable_1 = require("./runnable");
|
|
9
|
+
const utils_1 = require("./utils");
|
|
10
|
+
class Agent extends runnable_1.Runnable {
|
|
11
|
+
async getMemoryQuery(input, query) {
|
|
12
|
+
if (query?.from === 'variable') {
|
|
13
|
+
const i = utils_1.OrderedRecord.find(this.definition.inputs, (i) => i.id === query.fromVariableId);
|
|
14
|
+
if (!i)
|
|
15
|
+
throw new Error(`Input variable ${query.fromVariableId} not found`);
|
|
16
|
+
const value = input[i.name];
|
|
17
|
+
return (0, utils_1.renderMessage)('{{value}}', { value });
|
|
18
|
+
}
|
|
19
|
+
return Object.entries(input)
|
|
20
|
+
.map(([key, value]) => `${key} ${value}`)
|
|
21
|
+
.join('\n');
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* Load memories that are defined in the agent definition.
|
|
25
|
+
* @param input The agent input.
|
|
26
|
+
* @param context The AIGNE context.
|
|
27
|
+
* @returns A dictionary of memories, where the key is the memory name and the value is an array of memory items.
|
|
28
|
+
*/
|
|
29
|
+
async loadMemories(input, context) {
|
|
30
|
+
const { memories } = this.definition;
|
|
31
|
+
const { userId, sessionId } = context?.state ?? {};
|
|
32
|
+
return Object.fromEntries((await Promise.all(utils_1.OrderedRecord.map(memories, async ({ name, memory, query, options }) => {
|
|
33
|
+
if (!name || !memory)
|
|
34
|
+
return null;
|
|
35
|
+
const q = await this.getMemoryQuery(input, query);
|
|
36
|
+
const { results: memories } = await memory.search(q, { ...options, userId, sessionId });
|
|
37
|
+
return [name, memories];
|
|
38
|
+
}))).filter(utils_1.isNonNullable));
|
|
39
|
+
}
|
|
40
|
+
/**
|
|
41
|
+
* Update memories by user messages and assistant responses.
|
|
42
|
+
* @param messages Messages to be added to memories.
|
|
43
|
+
*/
|
|
44
|
+
async updateMemories(messages) {
|
|
45
|
+
const { memories } = this.definition;
|
|
46
|
+
const { userId, sessionId } = this.context?.state ?? {};
|
|
47
|
+
await Promise.all(utils_1.OrderedRecord.map(memories, async ({ memory }) => {
|
|
48
|
+
if (!memory) {
|
|
49
|
+
logger_1.default.warn(`Memory is not defined in agent ${this.name || this.id}`);
|
|
50
|
+
return;
|
|
51
|
+
}
|
|
52
|
+
return await memory.add(messages, { userId, sessionId });
|
|
53
|
+
}));
|
|
54
|
+
}
|
|
55
|
+
async run(input, options) {
|
|
56
|
+
const memories = await this.loadMemories(input, this.context);
|
|
57
|
+
return this.process(input, { ...options, memories });
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
exports.Agent = Agent;
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.schemaToDataType = schemaToDataType;
|
|
4
|
+
const nanoid_1 = require("nanoid");
|
|
5
|
+
const utils_1 = require("../utils");
|
|
6
|
+
function schemaToDataType(dataType) {
|
|
7
|
+
return utils_1.OrderedRecord.fromArray(Object.entries(dataType).map(([name, schema]) => {
|
|
8
|
+
const base = {
|
|
9
|
+
...schema,
|
|
10
|
+
id: (0, nanoid_1.nanoid)(),
|
|
11
|
+
name,
|
|
12
|
+
};
|
|
13
|
+
switch (schema.type) {
|
|
14
|
+
case 'string':
|
|
15
|
+
return {
|
|
16
|
+
...base,
|
|
17
|
+
type: 'string',
|
|
18
|
+
};
|
|
19
|
+
case 'number':
|
|
20
|
+
return {
|
|
21
|
+
...base,
|
|
22
|
+
type: 'number',
|
|
23
|
+
};
|
|
24
|
+
case 'boolean':
|
|
25
|
+
return {
|
|
26
|
+
...base,
|
|
27
|
+
type: 'boolean',
|
|
28
|
+
};
|
|
29
|
+
case 'object':
|
|
30
|
+
return {
|
|
31
|
+
...base,
|
|
32
|
+
type: 'object',
|
|
33
|
+
properties: schemaToDataType(schema.properties),
|
|
34
|
+
};
|
|
35
|
+
case 'array':
|
|
36
|
+
return {
|
|
37
|
+
...base,
|
|
38
|
+
type: 'array',
|
|
39
|
+
items: utils_1.OrderedRecord.find(schemaToDataType({ items: schema.items }), (i) => i.name === 'items'),
|
|
40
|
+
};
|
|
41
|
+
default: {
|
|
42
|
+
throw new Error(`Unknown data type: ${schema.type}`);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
}));
|
|
46
|
+
}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.toRunnableMemories = toRunnableMemories;
|
|
4
|
+
const nanoid_1 = require("nanoid");
|
|
5
|
+
const utils_1 = require("../utils");
|
|
6
|
+
function toRunnableMemories(agentName, inputs, memories) {
|
|
7
|
+
return utils_1.OrderedRecord.fromArray(Object.entries(memories).map(([name, { memory, query, options }]) => {
|
|
8
|
+
const queryFromVariable = query?.fromVariable
|
|
9
|
+
? utils_1.OrderedRecord.find(inputs, (j) => j.name === query.fromVariable)
|
|
10
|
+
: null;
|
|
11
|
+
if (query?.fromVariable && !queryFromVariable)
|
|
12
|
+
throw new Error(`LLMAgent ${agentName} -> Memory ${name} -> Query variable ${query.fromVariable.toString()} not found`);
|
|
13
|
+
return {
|
|
14
|
+
id: name || (0, nanoid_1.nanoid)(),
|
|
15
|
+
name: name,
|
|
16
|
+
memory: memory,
|
|
17
|
+
query: queryFromVariable ? { from: 'variable', fromVariableId: queryFromVariable.id } : undefined,
|
|
18
|
+
options,
|
|
19
|
+
};
|
|
20
|
+
}));
|
|
21
|
+
}
|
|
@@ -18,7 +18,7 @@ exports.createFunctionAgentDefinition = createFunctionAgentDefinition;
|
|
|
18
18
|
const nanoid_1 = require("nanoid");
|
|
19
19
|
const tsyringe_1 = require("tsyringe");
|
|
20
20
|
const constants_1 = require("./constants");
|
|
21
|
-
const data_type_schema_1 = require("./data-type-schema");
|
|
21
|
+
const data_type_schema_1 = require("./definitions/data-type-schema");
|
|
22
22
|
const function_runner_1 = require("./function-runner");
|
|
23
23
|
const runnable_1 = require("./runnable");
|
|
24
24
|
const utils_1 = require("./utils");
|
|
@@ -4,7 +4,7 @@ exports.FunctionRunner = void 0;
|
|
|
4
4
|
const runnable_1 = require("./runnable");
|
|
5
5
|
const utils_1 = require("./utils");
|
|
6
6
|
class FunctionRunner extends runnable_1.Runnable {
|
|
7
|
-
constructor() {
|
|
7
|
+
constructor(context) {
|
|
8
8
|
super({
|
|
9
9
|
id: 'function_runner',
|
|
10
10
|
type: 'function_runner',
|
|
@@ -23,7 +23,7 @@ class FunctionRunner extends runnable_1.Runnable {
|
|
|
23
23
|
type: 'object',
|
|
24
24
|
},
|
|
25
25
|
]),
|
|
26
|
-
});
|
|
26
|
+
}, context);
|
|
27
27
|
}
|
|
28
28
|
}
|
|
29
29
|
exports.FunctionRunner = FunctionRunner;
|
package/lib/cjs/index.js
CHANGED
|
@@ -17,7 +17,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
17
17
|
__exportStar(require("./utils"), exports);
|
|
18
18
|
__exportStar(require("./constants"), exports);
|
|
19
19
|
__exportStar(require("./data-type"), exports);
|
|
20
|
-
__exportStar(require("./data-type-schema"), exports);
|
|
20
|
+
__exportStar(require("./definitions/data-type-schema"), exports);
|
|
21
21
|
__exportStar(require("./context"), exports);
|
|
22
22
|
__exportStar(require("./runnable"), exports);
|
|
23
23
|
__exportStar(require("./pipeline-agent"), exports);
|
package/lib/cjs/llm-agent.js
CHANGED
|
@@ -11,45 +11,39 @@ var __metadata = (this && this.__metadata) || function (k, v) {
|
|
|
11
11
|
var __param = (this && this.__param) || function (paramIndex, decorator) {
|
|
12
12
|
return function (target, key) { decorator(target, key, paramIndex); }
|
|
13
13
|
};
|
|
14
|
-
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
15
|
-
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
16
|
-
};
|
|
17
14
|
var LLMAgent_1;
|
|
18
15
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
19
16
|
exports.LLMAgent = void 0;
|
|
20
17
|
exports.createLLMAgentDefinition = createLLMAgentDefinition;
|
|
21
|
-
const remove_1 = __importDefault(require("lodash/remove"));
|
|
22
18
|
const nanoid_1 = require("nanoid");
|
|
23
19
|
const tsyringe_1 = require("tsyringe");
|
|
20
|
+
const agent_1 = require("./agent");
|
|
24
21
|
const constants_1 = require("./constants");
|
|
25
|
-
const data_type_schema_1 = require("./data-type-schema");
|
|
22
|
+
const data_type_schema_1 = require("./definitions/data-type-schema");
|
|
23
|
+
const memory_1 = require("./definitions/memory");
|
|
26
24
|
const llm_model_1 = require("./llm-model");
|
|
27
|
-
const logger_1 = __importDefault(require("./logger"));
|
|
28
|
-
const runnable_1 = require("./runnable");
|
|
29
25
|
const utils_1 = require("./utils");
|
|
30
26
|
const message_utils_1 = require("./utils/message-utils");
|
|
31
27
|
const mustache_utils_1 = require("./utils/mustache-utils");
|
|
32
28
|
const ordered_map_1 = require("./utils/ordered-map");
|
|
33
29
|
const structured_output_schema_1 = require("./utils/structured-output-schema");
|
|
34
|
-
let LLMAgent = LLMAgent_1 = class LLMAgent extends
|
|
30
|
+
let LLMAgent = LLMAgent_1 = class LLMAgent extends agent_1.Agent {
|
|
35
31
|
definition;
|
|
36
32
|
model;
|
|
37
|
-
context;
|
|
38
33
|
static create(options) {
|
|
39
34
|
const definition = createLLMAgentDefinition(options);
|
|
40
35
|
return new LLMAgent_1(definition);
|
|
41
36
|
}
|
|
42
|
-
constructor(definition,
|
|
43
|
-
super(definition);
|
|
37
|
+
constructor(definition, context, model) {
|
|
38
|
+
super(definition, context);
|
|
44
39
|
this.definition = definition;
|
|
45
40
|
this.model = model;
|
|
46
|
-
this.context = context;
|
|
47
41
|
}
|
|
48
|
-
async
|
|
42
|
+
async process(input, options) {
|
|
49
43
|
const { definition, model } = this;
|
|
50
44
|
if (!model)
|
|
51
45
|
throw new Error('LLM model is required');
|
|
52
|
-
const { originalMessages, messagesWithMemory } =
|
|
46
|
+
const { originalMessages, messagesWithMemory } = (0, message_utils_1.prepareMessages)(definition, input, options.memories);
|
|
53
47
|
const llmInputs = {
|
|
54
48
|
messages: messagesWithMemory,
|
|
55
49
|
modelOptions: definition.modelOptions,
|
|
@@ -95,35 +89,6 @@ let LLMAgent = LLMAgent_1 = class LLMAgent extends runnable_1.Runnable {
|
|
|
95
89
|
await updateMemories($text, json);
|
|
96
90
|
return { $text, ...json };
|
|
97
91
|
}
|
|
98
|
-
async prepareMessages(input) {
|
|
99
|
-
const { definition } = this;
|
|
100
|
-
const originalMessages = ordered_map_1.OrderedRecord.toArray(definition.messages).map(({ role, content }) => ({
|
|
101
|
-
role,
|
|
102
|
-
// TODO: support use memory variables in message content
|
|
103
|
-
content: typeof content === 'string' ? (0, mustache_utils_1.renderMessage)(content, input) : content,
|
|
104
|
-
}));
|
|
105
|
-
if (!originalMessages.length)
|
|
106
|
-
throw new Error('Messages are required');
|
|
107
|
-
const { primaryMemory, memory } = await this.getMemories(input);
|
|
108
|
-
let messagesWithMemory = [...originalMessages];
|
|
109
|
-
// Add memory to a system message
|
|
110
|
-
if (memory) {
|
|
111
|
-
const message = {
|
|
112
|
-
role: 'system',
|
|
113
|
-
content: `\
|
|
114
|
-
Here are the memories about the user:
|
|
115
|
-
${memory}
|
|
116
|
-
`,
|
|
117
|
-
};
|
|
118
|
-
const lastSystemMessageIndex = messagesWithMemory.findLastIndex((i) => i.role === 'assistant');
|
|
119
|
-
messagesWithMemory.splice(lastSystemMessageIndex + 1, 0, message);
|
|
120
|
-
}
|
|
121
|
-
// Add primary memory to messages
|
|
122
|
-
if (primaryMemory.length)
|
|
123
|
-
messagesWithMemory = (0, message_utils_1.mergeHistoryMessages)(messagesWithMemory, primaryMemory);
|
|
124
|
-
// TODO: support comment/image for messages
|
|
125
|
-
return { originalMessages, messagesWithMemory };
|
|
126
|
-
}
|
|
127
92
|
async runWithStructuredOutput(llmInputs) {
|
|
128
93
|
const jsonOutputs = ordered_map_1.OrderedRecord.filter(this.definition.outputs, (i) => i.name !== constants_1.StreamTextOutputName // ignore `$text` output
|
|
129
94
|
);
|
|
@@ -156,74 +121,14 @@ let LLMAgent = LLMAgent_1 = class LLMAgent extends runnable_1.Runnable {
|
|
|
156
121
|
throw new Error('LLM model is required');
|
|
157
122
|
return model.run(llmInputs, { stream: true });
|
|
158
123
|
}
|
|
159
|
-
async getMemoryQuery(input, query) {
|
|
160
|
-
if (query?.from === 'variable') {
|
|
161
|
-
const i = ordered_map_1.OrderedRecord.find(this.definition.inputs, (i) => i.id === query.fromVariableId);
|
|
162
|
-
if (!i)
|
|
163
|
-
throw new Error(`Input variable ${query.fromVariableId} not found`);
|
|
164
|
-
const value = input[i.name];
|
|
165
|
-
return (0, mustache_utils_1.renderMessage)('{{value}}', { value });
|
|
166
|
-
}
|
|
167
|
-
return Object.entries(input)
|
|
168
|
-
.map(([key, value]) => `${key} ${value}`)
|
|
169
|
-
.join('\n');
|
|
170
|
-
}
|
|
171
|
-
async getMemories(input) {
|
|
172
|
-
const { memories } = this.definition;
|
|
173
|
-
const { userId, sessionId } = this.context?.state ?? {};
|
|
174
|
-
const list = (await Promise.all(ordered_map_1.OrderedRecord.map(memories, async ({ id, memory, query, options }) => {
|
|
175
|
-
if (!memory) {
|
|
176
|
-
logger_1.default.warn(`Memory is not defined in agent ${this.name || this.id}`);
|
|
177
|
-
return null;
|
|
178
|
-
}
|
|
179
|
-
const q = await this.getMemoryQuery(input, query);
|
|
180
|
-
const { results: memories } = await memory.search(q, { ...options, userId, sessionId });
|
|
181
|
-
return { id, memories };
|
|
182
|
-
}))).filter(utils_1.isNonNullable);
|
|
183
|
-
const primary = (0, remove_1.default)(list, (i) => i.id === this.definition.primaryMemoryId)[0]?.memories || [];
|
|
184
|
-
const primaryMemory = primary
|
|
185
|
-
.map((i) => {
|
|
186
|
-
const content = (0, mustache_utils_1.renderMessage)('{{memory}}', { memory: i.memory }).trim();
|
|
187
|
-
const role = ['user', 'assistant'].includes(i.metadata.role) ? i.metadata.role : undefined;
|
|
188
|
-
if (!role || !content)
|
|
189
|
-
return null;
|
|
190
|
-
return { role, content };
|
|
191
|
-
})
|
|
192
|
-
.filter(utils_1.isNonNullable);
|
|
193
|
-
const memory = list
|
|
194
|
-
.map((i) => i.memories
|
|
195
|
-
.map((j) => (0, mustache_utils_1.renderMessage)('{{memory}}\n{{metadata}}', j).trim() || null)
|
|
196
|
-
.filter(utils_1.isNonNullable)
|
|
197
|
-
.join('\n'))
|
|
198
|
-
.join('\n');
|
|
199
|
-
return {
|
|
200
|
-
primaryMemory,
|
|
201
|
-
memory,
|
|
202
|
-
};
|
|
203
|
-
}
|
|
204
|
-
/**
|
|
205
|
-
* Update memories by user messages and assistant responses.
|
|
206
|
-
* @param messages Messages to be added to memories.
|
|
207
|
-
*/
|
|
208
|
-
async updateMemories(messages) {
|
|
209
|
-
const { memories } = this.definition;
|
|
210
|
-
const { userId, sessionId } = this.context?.state ?? {};
|
|
211
|
-
await Promise.all(ordered_map_1.OrderedRecord.map(memories, async ({ memory }) => {
|
|
212
|
-
if (!memory) {
|
|
213
|
-
logger_1.default.warn(`Memory is not defined in agent ${this.name || this.id}`);
|
|
214
|
-
return;
|
|
215
|
-
}
|
|
216
|
-
return await memory.add(messages, { userId, sessionId });
|
|
217
|
-
}));
|
|
218
|
-
}
|
|
219
124
|
};
|
|
220
125
|
exports.LLMAgent = LLMAgent;
|
|
221
126
|
exports.LLMAgent = LLMAgent = LLMAgent_1 = __decorate([
|
|
222
127
|
(0, tsyringe_1.injectable)(),
|
|
223
128
|
__param(0, (0, tsyringe_1.inject)(constants_1.TYPES.definition)),
|
|
224
|
-
__param(1, (0, tsyringe_1.inject)(constants_1.TYPES.
|
|
225
|
-
__param(2, (0, tsyringe_1.inject)(constants_1.TYPES.
|
|
226
|
-
__metadata("design:paramtypes", [Object, llm_model_1.LLMModel
|
|
129
|
+
__param(1, (0, tsyringe_1.inject)(constants_1.TYPES.context)),
|
|
130
|
+
__param(2, (0, tsyringe_1.inject)(constants_1.TYPES.llmModel)),
|
|
131
|
+
__metadata("design:paramtypes", [Object, Object, llm_model_1.LLMModel])
|
|
227
132
|
], LLMAgent);
|
|
228
133
|
/**
|
|
229
134
|
* Create LLMAgent definition.
|
|
@@ -232,27 +137,15 @@ exports.LLMAgent = LLMAgent = LLMAgent_1 = __decorate([
|
|
|
232
137
|
*/
|
|
233
138
|
function createLLMAgentDefinition(options) {
|
|
234
139
|
const agentId = options.name || (0, nanoid_1.nanoid)();
|
|
235
|
-
const primaryMemories = options.memories?.filter((i) => i.primary);
|
|
236
|
-
if (primaryMemories && primaryMemories.length > 1) {
|
|
237
|
-
throw new Error('Only one primary memory is allowed');
|
|
238
|
-
}
|
|
239
140
|
const inputs = (0, data_type_schema_1.schemaToDataType)(options.inputs);
|
|
240
141
|
const outputs = (0, data_type_schema_1.schemaToDataType)(options.outputs);
|
|
241
|
-
const memories =
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
return {
|
|
249
|
-
id: name || (0, nanoid_1.nanoid)(),
|
|
250
|
-
name: name,
|
|
251
|
-
memory: memory,
|
|
252
|
-
query: queryFromVariable ? { from: 'variable', fromVariableId: queryFromVariable.id } : undefined,
|
|
253
|
-
options,
|
|
254
|
-
};
|
|
255
|
-
}));
|
|
142
|
+
const memories = (0, memory_1.toRunnableMemories)(agentId, inputs, options.memories ?? {});
|
|
143
|
+
const primaryMemoryNames = Object.entries(options.memories ?? {})
|
|
144
|
+
.filter(([, i]) => i.primary)
|
|
145
|
+
.map(([name]) => name);
|
|
146
|
+
if (primaryMemoryNames && primaryMemoryNames.length > 1) {
|
|
147
|
+
throw new Error('Only one primary memory is allowed');
|
|
148
|
+
}
|
|
256
149
|
const messages = ordered_map_1.OrderedRecord.fromArray(options.messages?.map((i) => ({
|
|
257
150
|
id: (0, nanoid_1.nanoid)(),
|
|
258
151
|
role: i.role,
|
|
@@ -264,7 +157,7 @@ function createLLMAgentDefinition(options) {
|
|
|
264
157
|
type: 'llm_agent',
|
|
265
158
|
inputs,
|
|
266
159
|
outputs,
|
|
267
|
-
primaryMemoryId:
|
|
160
|
+
primaryMemoryId: primaryMemoryNames?.at(0),
|
|
268
161
|
memories,
|
|
269
162
|
modelOptions: options.modelOptions,
|
|
270
163
|
messages,
|
|
@@ -17,33 +17,31 @@ exports.LLMDecisionAgent = void 0;
|
|
|
17
17
|
exports.createLLMDecisionAgentDefinition = createLLMDecisionAgentDefinition;
|
|
18
18
|
const nanoid_1 = require("nanoid");
|
|
19
19
|
const tsyringe_1 = require("tsyringe");
|
|
20
|
+
const agent_1 = require("./agent");
|
|
20
21
|
const constants_1 = require("./constants");
|
|
22
|
+
const memory_1 = require("./definitions/memory");
|
|
21
23
|
const llm_model_1 = require("./llm-model");
|
|
22
|
-
const runnable_1 = require("./runnable");
|
|
23
24
|
const utils_1 = require("./utils");
|
|
24
|
-
|
|
25
|
+
const message_utils_1 = require("./utils/message-utils");
|
|
26
|
+
let LLMDecisionAgent = LLMDecisionAgent_1 = class LLMDecisionAgent extends agent_1.Agent {
|
|
25
27
|
definition;
|
|
26
28
|
model;
|
|
27
|
-
context;
|
|
28
29
|
static create(options) {
|
|
29
30
|
const definition = createLLMDecisionAgentDefinition(options);
|
|
30
31
|
return new LLMDecisionAgent_1(definition);
|
|
31
32
|
}
|
|
32
|
-
constructor(definition,
|
|
33
|
-
super(definition);
|
|
33
|
+
constructor(definition, context, model) {
|
|
34
|
+
super(definition, context);
|
|
34
35
|
this.definition = definition;
|
|
35
36
|
this.model = model;
|
|
36
|
-
this.context = context;
|
|
37
37
|
}
|
|
38
|
-
async
|
|
38
|
+
async process(input, options) {
|
|
39
39
|
const { definition, context, model } = this;
|
|
40
40
|
if (!model)
|
|
41
41
|
throw new Error('LLM model is required');
|
|
42
42
|
if (!context)
|
|
43
43
|
throw new Error('Context is required');
|
|
44
|
-
const
|
|
45
|
-
if (!messages.length)
|
|
46
|
-
throw new Error('Messages are required');
|
|
44
|
+
const { originalMessages, messagesWithMemory } = (0, message_utils_1.prepareMessages)(definition, input, options.memories);
|
|
47
45
|
const cases = await Promise.all(utils_1.OrderedRecord.map(definition.cases, async (t) => {
|
|
48
46
|
if (!t.runnable?.id)
|
|
49
47
|
throw new Error('Runnable is required');
|
|
@@ -52,13 +50,10 @@ let LLMDecisionAgent = LLMDecisionAgent_1 = class LLMDecisionAgent extends runna
|
|
|
52
50
|
const name = t.name || runnable.name;
|
|
53
51
|
if (!name)
|
|
54
52
|
throw new Error('Case name is required');
|
|
55
|
-
return { name, description: t.description, runnable
|
|
53
|
+
return { name, description: t.description, runnable };
|
|
56
54
|
}));
|
|
57
55
|
const llmInputs = {
|
|
58
|
-
messages:
|
|
59
|
-
role,
|
|
60
|
-
content: typeof content === 'string' ? (0, utils_1.renderMessage)(content, input) : content,
|
|
61
|
-
})),
|
|
56
|
+
messages: messagesWithMemory,
|
|
62
57
|
modelOptions: definition.modelOptions,
|
|
63
58
|
tools: cases.map((t) => {
|
|
64
59
|
// TODO: auto generate parameters by llm model if needed
|
|
@@ -82,40 +77,52 @@ let LLMDecisionAgent = LLMDecisionAgent_1 = class LLMDecisionAgent extends runna
|
|
|
82
77
|
if (!caseToCall)
|
|
83
78
|
throw new Error('Case not found');
|
|
84
79
|
// TODO: check result structure and omit undefined values
|
|
85
|
-
|
|
80
|
+
const output = (await caseToCall.runnable.run(input, options));
|
|
81
|
+
return (0, utils_1.extractOutputsFromRunnableOutput)(output, ({ $text, ...json }) => this.updateMemories([
|
|
82
|
+
...originalMessages,
|
|
83
|
+
{ role: 'assistant', content: (0, utils_1.renderMessage)('{{$text}}\n{{json}}', { $text, json }).trim() },
|
|
84
|
+
]));
|
|
86
85
|
}
|
|
87
86
|
};
|
|
88
87
|
exports.LLMDecisionAgent = LLMDecisionAgent;
|
|
89
88
|
exports.LLMDecisionAgent = LLMDecisionAgent = LLMDecisionAgent_1 = __decorate([
|
|
90
89
|
(0, tsyringe_1.injectable)(),
|
|
91
90
|
__param(0, (0, tsyringe_1.inject)(constants_1.TYPES.definition)),
|
|
92
|
-
__param(1, (0, tsyringe_1.inject)(constants_1.TYPES.
|
|
93
|
-
__param(2, (0, tsyringe_1.inject)(constants_1.TYPES.
|
|
94
|
-
__metadata("design:paramtypes", [Object, llm_model_1.LLMModel
|
|
91
|
+
__param(1, (0, tsyringe_1.inject)(constants_1.TYPES.context)),
|
|
92
|
+
__param(2, (0, tsyringe_1.inject)(constants_1.TYPES.llmModel)),
|
|
93
|
+
__metadata("design:paramtypes", [Object, Object, llm_model_1.LLMModel])
|
|
95
94
|
], LLMDecisionAgent);
|
|
96
95
|
function createLLMDecisionAgentDefinition(options) {
|
|
97
|
-
const
|
|
98
|
-
|
|
99
|
-
id: (0, nanoid_1.nanoid)(),
|
|
100
|
-
role: 'system',
|
|
101
|
-
content: options.messages,
|
|
102
|
-
},
|
|
103
|
-
]);
|
|
104
|
-
const cases = utils_1.OrderedRecord.fromArray(options.cases.map((c) => ({
|
|
96
|
+
const agentId = options.name || (0, nanoid_1.nanoid)();
|
|
97
|
+
const cases = utils_1.OrderedRecord.fromArray(Object.entries(options.cases).map(([name, c]) => ({
|
|
105
98
|
id: (0, nanoid_1.nanoid)(),
|
|
106
|
-
name:
|
|
99
|
+
name: name || c.runnable.name,
|
|
107
100
|
description: c.description,
|
|
108
101
|
runnable: { id: c.runnable.id },
|
|
109
102
|
})));
|
|
103
|
+
const inputs = utils_1.OrderedRecord.merge(...Object.values(options.cases).map((i) => i.runnable.definition.inputs));
|
|
104
|
+
const outputs = utils_1.OrderedRecord.fromArray(utils_1.OrderedRecord.map(utils_1.OrderedRecord.merge(...Object.values(options.cases).map((i) => i.runnable.definition.outputs)), (o) => ({ ...o, required: false })));
|
|
105
|
+
const memories = (0, memory_1.toRunnableMemories)(agentId, inputs, options.memories ?? {});
|
|
106
|
+
const primaryMemoryNames = Object.entries(options.memories ?? {})
|
|
107
|
+
.filter(([, i]) => i.primary)
|
|
108
|
+
.map(([name]) => name);
|
|
109
|
+
if (primaryMemoryNames && primaryMemoryNames.length > 1) {
|
|
110
|
+
throw new Error('Only one primary memory is allowed');
|
|
111
|
+
}
|
|
112
|
+
const messages = utils_1.OrderedRecord.fromArray(options.messages?.map((i) => ({
|
|
113
|
+
id: (0, nanoid_1.nanoid)(),
|
|
114
|
+
role: i.role,
|
|
115
|
+
content: i.content,
|
|
116
|
+
})));
|
|
110
117
|
return {
|
|
111
|
-
id:
|
|
118
|
+
id: agentId,
|
|
112
119
|
name: options.name,
|
|
113
120
|
type: 'llm_decision_agent',
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
// TODO: decision agent outputs should be the union of all case outputs
|
|
117
|
-
outputs: utils_1.OrderedRecord.fromArray([]),
|
|
121
|
+
inputs,
|
|
122
|
+
outputs,
|
|
118
123
|
messages,
|
|
124
|
+
primaryMemoryId: primaryMemoryNames?.at(0),
|
|
125
|
+
memories,
|
|
119
126
|
modelOptions: options.modelOptions,
|
|
120
127
|
cases,
|
|
121
128
|
};
|
package/lib/cjs/llm-model.js
CHANGED
|
@@ -4,7 +4,7 @@ exports.LLMModel = void 0;
|
|
|
4
4
|
const runnable_1 = require("./runnable");
|
|
5
5
|
const utils_1 = require("./utils");
|
|
6
6
|
class LLMModel extends runnable_1.Runnable {
|
|
7
|
-
constructor() {
|
|
7
|
+
constructor(context) {
|
|
8
8
|
super({
|
|
9
9
|
id: 'llm_model',
|
|
10
10
|
type: 'llm_model',
|
|
@@ -21,7 +21,7 @@ class LLMModel extends runnable_1.Runnable {
|
|
|
21
21
|
{ id: '$text', name: '$text', type: 'string' },
|
|
22
22
|
{ id: 'toolCalls', name: 'toolCalls', type: 'object' },
|
|
23
23
|
]),
|
|
24
|
-
});
|
|
24
|
+
}, context);
|
|
25
25
|
}
|
|
26
26
|
}
|
|
27
27
|
exports.LLMModel = LLMModel;
|
|
@@ -17,29 +17,28 @@ exports.LocalFunctionAgent = void 0;
|
|
|
17
17
|
exports.createLocalFunctionAgentDefinition = createLocalFunctionAgentDefinition;
|
|
18
18
|
const nanoid_1 = require("nanoid");
|
|
19
19
|
const tsyringe_1 = require("tsyringe");
|
|
20
|
+
const agent_1 = require("./agent");
|
|
20
21
|
const constants_1 = require("./constants");
|
|
21
|
-
const data_type_schema_1 = require("./data-type-schema");
|
|
22
|
-
const
|
|
22
|
+
const data_type_schema_1 = require("./definitions/data-type-schema");
|
|
23
|
+
const memory_1 = require("./definitions/memory");
|
|
23
24
|
const utils_1 = require("./utils");
|
|
24
|
-
let LocalFunctionAgent = LocalFunctionAgent_1 = class LocalFunctionAgent extends
|
|
25
|
+
let LocalFunctionAgent = LocalFunctionAgent_1 = class LocalFunctionAgent extends agent_1.Agent {
|
|
25
26
|
definition;
|
|
26
|
-
context;
|
|
27
27
|
static create(options) {
|
|
28
28
|
const definition = createLocalFunctionAgentDefinition(options);
|
|
29
29
|
return new LocalFunctionAgent_1(definition);
|
|
30
30
|
}
|
|
31
31
|
constructor(definition, context) {
|
|
32
|
-
super(definition);
|
|
32
|
+
super(definition, context);
|
|
33
33
|
this.definition = definition;
|
|
34
|
-
this.context = context;
|
|
35
34
|
}
|
|
36
|
-
async
|
|
35
|
+
async process(input, options) {
|
|
37
36
|
const { definition: { function: func }, context, } = this;
|
|
38
37
|
if (!func)
|
|
39
38
|
throw new Error('Function is required');
|
|
40
39
|
if (!context)
|
|
41
40
|
throw new Error('Context is required');
|
|
42
|
-
const result =
|
|
41
|
+
const result = await func(input, { context, memories: options.memories });
|
|
43
42
|
// TODO: validate the result against the definition.outputs
|
|
44
43
|
return options?.stream
|
|
45
44
|
? result instanceof ReadableStream
|
|
@@ -58,14 +57,17 @@ exports.LocalFunctionAgent = LocalFunctionAgent = LocalFunctionAgent_1 = __decor
|
|
|
58
57
|
__metadata("design:paramtypes", [Object, Object])
|
|
59
58
|
], LocalFunctionAgent);
|
|
60
59
|
function createLocalFunctionAgentDefinition(options) {
|
|
60
|
+
const agentId = options.name || (0, nanoid_1.nanoid)();
|
|
61
61
|
const inputs = (0, data_type_schema_1.schemaToDataType)(options.inputs);
|
|
62
62
|
const outputs = (0, data_type_schema_1.schemaToDataType)(options.outputs);
|
|
63
|
+
const memories = (0, memory_1.toRunnableMemories)(agentId, inputs, options.memories || {});
|
|
63
64
|
return {
|
|
64
|
-
id:
|
|
65
|
+
id: agentId,
|
|
65
66
|
name: options.name,
|
|
66
67
|
type: 'local_function_agent',
|
|
67
68
|
inputs,
|
|
68
69
|
outputs,
|
|
70
|
+
memories,
|
|
69
71
|
function: options.function,
|
|
70
72
|
};
|
|
71
73
|
}
|
|
@@ -22,7 +22,7 @@ const lodash_1 = require("lodash");
|
|
|
22
22
|
const nanoid_1 = require("nanoid");
|
|
23
23
|
const tsyringe_1 = require("tsyringe");
|
|
24
24
|
const constants_1 = require("./constants");
|
|
25
|
-
const data_type_schema_1 = require("./data-type-schema");
|
|
25
|
+
const data_type_schema_1 = require("./definitions/data-type-schema");
|
|
26
26
|
const logger_1 = __importDefault(require("./logger"));
|
|
27
27
|
const runnable_1 = require("./runnable");
|
|
28
28
|
const utils_1 = require("./utils");
|
|
@@ -30,15 +30,13 @@ const is_non_nullable_1 = require("./utils/is-non-nullable");
|
|
|
30
30
|
const ordered_map_1 = require("./utils/ordered-map");
|
|
31
31
|
let PipelineAgent = PipelineAgent_1 = class PipelineAgent extends runnable_1.Runnable {
|
|
32
32
|
definition;
|
|
33
|
-
context;
|
|
34
33
|
static create(options) {
|
|
35
34
|
const definition = createPipelineAgentDefinition(options);
|
|
36
35
|
return new PipelineAgent_1(definition);
|
|
37
36
|
}
|
|
38
37
|
constructor(definition, context) {
|
|
39
|
-
super(definition);
|
|
38
|
+
super(definition, context);
|
|
40
39
|
this.definition = definition;
|
|
41
|
-
this.context = context;
|
|
42
40
|
}
|
|
43
41
|
async run(input, options) {
|
|
44
42
|
// TODO: validate the input against the definition
|
package/lib/cjs/runnable.js
CHANGED
|
@@ -6,8 +6,10 @@ exports.isRunnableResponseError = isRunnableResponseError;
|
|
|
6
6
|
const ordered_map_1 = require("./utils/ordered-map");
|
|
7
7
|
class Runnable {
|
|
8
8
|
definition;
|
|
9
|
-
|
|
9
|
+
context;
|
|
10
|
+
constructor(definition, context) {
|
|
10
11
|
this.definition = definition;
|
|
12
|
+
this.context = context;
|
|
11
13
|
this.inputs = Object.fromEntries(ordered_map_1.OrderedRecord.map(definition.inputs, (i) => [i.name || i.id, i]));
|
|
12
14
|
this.outputs = Object.fromEntries(ordered_map_1.OrderedRecord.map(definition.outputs, (i) => [i.name || i.id, i]));
|
|
13
15
|
}
|