@google/adk 0.5.0 → 0.6.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/README.md +1 -1
- package/dist/cjs/a2a/a2a_event.js +53 -26
- package/dist/cjs/a2a/a2a_remote_agent.js +179 -0
- package/dist/cjs/a2a/a2a_remote_agent_run_processor.js +205 -0
- package/dist/cjs/a2a/a2a_remote_agent_utils.js +165 -0
- package/dist/cjs/a2a/agent_card.js +380 -0
- package/dist/cjs/a2a/agent_executor.js +221 -0
- package/dist/cjs/a2a/agent_to_a2a.js +115 -0
- package/dist/cjs/a2a/event_processor_utils.js +180 -0
- package/dist/cjs/a2a/executor_context.js +1 -1
- package/dist/cjs/a2a/metadata_converter_utils.js +1 -0
- package/dist/cjs/a2a/part_converter_utils.js +24 -13
- package/dist/cjs/agents/llm_agent.js +17 -0
- package/dist/cjs/agents/{content_processor_utils.js → processors/content_processor_utils.js} +21 -2
- package/dist/cjs/agents/processors/content_request_processor.js +24 -3
- package/dist/cjs/agents/processors/context_compactor_request_processor.js +61 -0
- package/dist/cjs/agents/processors/instructions_llm_request_processor.js +1 -1
- package/dist/cjs/artifacts/file_artifact_service.js +35 -4
- package/dist/cjs/common.js +37 -0
- package/dist/cjs/context/base_context_compactor.js +27 -0
- package/dist/cjs/context/summarizers/base_summarizer.js +27 -0
- package/dist/cjs/context/summarizers/llm_summarizer.js +93 -0
- package/dist/cjs/context/token_based_context_compactor.js +135 -0
- package/dist/cjs/context/truncating_context_compactor.js +58 -0
- package/dist/cjs/events/compacted_event.js +53 -0
- package/dist/cjs/index.js +38 -14
- package/dist/cjs/index.js.map +4 -4
- package/dist/cjs/memory/in_memory_memory_service.js +1 -1
- package/dist/cjs/runner/runner.js +19 -10
- package/dist/cjs/sessions/db/operations.js +4 -14
- package/dist/cjs/sessions/state.js +2 -2
- package/dist/cjs/tools/agent_tool.js +6 -5
- package/dist/cjs/tools/load_artifacts_tool.js +188 -0
- package/dist/cjs/tools/load_memory_tool.js +107 -0
- package/dist/cjs/tools/preload_memory_tool.js +109 -0
- package/dist/cjs/utils/gemini_schema_util.js +54 -12
- package/dist/cjs/utils/logger.js +1 -0
- package/dist/cjs/version.js +1 -1
- package/dist/esm/a2a/a2a_event.js +52 -26
- package/dist/esm/a2a/a2a_remote_agent.js +153 -0
- package/dist/esm/a2a/a2a_remote_agent_run_processor.js +182 -0
- package/dist/esm/a2a/a2a_remote_agent_utils.js +131 -0
- package/dist/esm/a2a/agent_card.js +340 -0
- package/dist/esm/a2a/agent_executor.js +202 -0
- package/dist/esm/a2a/agent_to_a2a.js +80 -0
- package/dist/esm/a2a/event_processor_utils.js +159 -0
- package/dist/esm/a2a/executor_context.js +1 -1
- package/dist/esm/a2a/metadata_converter_utils.js +1 -0
- package/dist/esm/a2a/part_converter_utils.js +24 -13
- package/dist/esm/agents/llm_agent.js +17 -0
- package/dist/esm/agents/{content_processor_utils.js → processors/content_processor_utils.js} +23 -2
- package/dist/esm/agents/processors/content_request_processor.js +25 -4
- package/dist/esm/agents/processors/context_compactor_request_processor.js +31 -0
- package/dist/esm/agents/processors/instructions_llm_request_processor.js +1 -1
- package/dist/esm/artifacts/file_artifact_service.js +30 -3
- package/dist/esm/common.js +33 -1
- package/dist/esm/context/base_context_compactor.js +5 -0
- package/dist/esm/context/summarizers/base_summarizer.js +5 -0
- package/dist/esm/context/summarizers/llm_summarizer.js +65 -0
- package/dist/esm/context/token_based_context_compactor.js +105 -0
- package/dist/esm/context/truncating_context_compactor.js +28 -0
- package/dist/esm/events/compacted_event.js +22 -0
- package/dist/esm/index.js +38 -14
- package/dist/esm/index.js.map +4 -4
- package/dist/esm/memory/in_memory_memory_service.js +1 -1
- package/dist/esm/runner/runner.js +17 -9
- package/dist/esm/sessions/db/operations.js +4 -14
- package/dist/esm/sessions/state.js +2 -2
- package/dist/esm/tools/agent_tool.js +6 -5
- package/dist/esm/tools/load_artifacts_tool.js +159 -0
- package/dist/esm/tools/load_memory_tool.js +78 -0
- package/dist/esm/tools/preload_memory_tool.js +80 -0
- package/dist/esm/utils/gemini_schema_util.js +54 -12
- package/dist/esm/utils/logger.js +1 -0
- package/dist/esm/version.js +1 -1
- package/dist/types/a2a/a2a_event.d.ts +23 -6
- package/dist/types/a2a/a2a_remote_agent.d.ts +67 -0
- package/dist/types/a2a/a2a_remote_agent_run_processor.d.ts +31 -0
- package/dist/types/a2a/a2a_remote_agent_utils.d.ts +38 -0
- package/dist/types/a2a/agent_card.d.ts +23 -0
- package/dist/types/a2a/agent_executor.d.ts +52 -0
- package/dist/types/a2a/agent_to_a2a.d.ts +45 -0
- package/dist/types/a2a/event_processor_utils.d.ts +24 -0
- package/dist/types/a2a/executor_context.d.ts +1 -1
- package/dist/types/a2a/metadata_converter_utils.d.ts +2 -1
- package/dist/types/agents/llm_agent.d.ts +6 -0
- package/dist/types/agents/loop_agent.d.ts +1 -1
- package/dist/types/agents/{content_processor_utils.d.ts → processors/content_processor_utils.d.ts} +1 -1
- package/dist/types/agents/processors/context_compactor_request_processor.d.ts +22 -0
- package/dist/types/artifacts/file_artifact_service.d.ts +4 -0
- package/dist/types/common.d.ts +16 -1
- package/dist/types/context/base_context_compactor.d.ts +24 -0
- package/dist/types/context/summarizers/base_summarizer.d.ts +19 -0
- package/dist/types/context/summarizers/llm_summarizer.d.ts +23 -0
- package/dist/types/context/token_based_context_compactor.d.ts +33 -0
- package/dist/types/context/truncating_context_compactor.d.ts +24 -0
- package/dist/types/events/compacted_event.d.ts +33 -0
- package/dist/types/index.d.ts +8 -0
- package/dist/types/runner/runner.d.ts +13 -0
- package/dist/types/sessions/db/operations.d.ts +2 -3
- package/dist/types/tools/load_artifacts_tool.d.ts +21 -0
- package/dist/types/tools/load_memory_tool.d.ts +22 -0
- package/dist/types/tools/preload_memory_tool.d.ts +23 -0
- package/dist/types/version.d.ts +1 -1
- package/dist/web/a2a/a2a_event.js +52 -26
- package/dist/web/a2a/a2a_remote_agent.js +184 -0
- package/dist/web/a2a/a2a_remote_agent_run_processor.js +182 -0
- package/dist/web/a2a/a2a_remote_agent_utils.js +131 -0
- package/dist/web/a2a/agent_card.js +340 -0
- package/dist/web/a2a/agent_executor.js +216 -0
- package/dist/web/a2a/agent_to_a2a.js +80 -0
- package/dist/web/a2a/event_processor_utils.js +168 -0
- package/dist/web/a2a/executor_context.js +1 -1
- package/dist/web/a2a/metadata_converter_utils.js +1 -0
- package/dist/web/a2a/part_converter_utils.js +24 -13
- package/dist/web/agents/llm_agent.js +17 -0
- package/dist/web/agents/{content_processor_utils.js → processors/content_processor_utils.js} +22 -2
- package/dist/web/agents/processors/content_request_processor.js +25 -4
- package/dist/web/agents/processors/context_compactor_request_processor.js +49 -0
- package/dist/web/agents/processors/instructions_llm_request_processor.js +1 -1
- package/dist/web/artifacts/file_artifact_service.js +30 -3
- package/dist/web/common.js +33 -1
- package/dist/web/context/base_context_compactor.js +5 -0
- package/dist/web/context/summarizers/base_summarizer.js +5 -0
- package/dist/web/context/summarizers/llm_summarizer.js +74 -0
- package/dist/web/context/token_based_context_compactor.js +105 -0
- package/dist/web/context/truncating_context_compactor.js +28 -0
- package/dist/web/events/compacted_event.js +40 -0
- package/dist/web/index.js +1 -1
- package/dist/web/index.js.map +4 -4
- package/dist/web/memory/in_memory_memory_service.js +1 -1
- package/dist/web/runner/runner.js +17 -9
- package/dist/web/sessions/db/operations.js +4 -14
- package/dist/web/sessions/state.js +2 -2
- package/dist/web/tools/agent_tool.js +6 -5
- package/dist/web/tools/load_artifacts_tool.js +150 -0
- package/dist/web/tools/load_memory_tool.js +77 -0
- package/dist/web/tools/preload_memory_tool.js +75 -0
- package/dist/web/utils/gemini_schema_util.js +85 -12
- package/dist/web/utils/logger.js +1 -0
- package/dist/web/version.js +1 -1
- package/package.json +7 -5
|
@@ -0,0 +1,159 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2026 Google LLC
|
|
4
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
5
|
+
*/
|
|
6
|
+
import { createEventActions } from "../events/event_actions.js";
|
|
7
|
+
import {
|
|
8
|
+
createInputMissingErrorEvent,
|
|
9
|
+
createTaskCompletedEvent,
|
|
10
|
+
createTaskFailedEvent,
|
|
11
|
+
createTaskInputRequiredEvent,
|
|
12
|
+
isInputRequiredTaskStatusUpdateEvent
|
|
13
|
+
} from "./a2a_event.js";
|
|
14
|
+
import {
|
|
15
|
+
getA2AEventMetadata,
|
|
16
|
+
getA2AEventMetadataFromActions,
|
|
17
|
+
getA2ASessionMetadata
|
|
18
|
+
} from "./metadata_converter_utils.js";
|
|
19
|
+
import { toA2AParts, toGenAIParts } from "./part_converter_utils.js";
|
|
20
|
+
function getFinalTaskStatusUpdate(adkEvents, context) {
|
|
21
|
+
var _a, _b;
|
|
22
|
+
const finalEventActions = createEventActions();
|
|
23
|
+
for (const adkEvent of adkEvents) {
|
|
24
|
+
if (adkEvent.errorCode || adkEvent.errorMessage) {
|
|
25
|
+
return createTaskFailedEvent({
|
|
26
|
+
taskId: context.requestContext.taskId,
|
|
27
|
+
contextId: context.requestContext.contextId,
|
|
28
|
+
error: new Error(adkEvent.errorMessage || adkEvent.errorCode),
|
|
29
|
+
metadata: {
|
|
30
|
+
...getA2AEventMetadata(adkEvent, context),
|
|
31
|
+
...getA2AEventMetadataFromActions(finalEventActions)
|
|
32
|
+
}
|
|
33
|
+
});
|
|
34
|
+
}
|
|
35
|
+
finalEventActions.escalate = finalEventActions.escalate || ((_a = adkEvent.actions) == null ? void 0 : _a.escalate);
|
|
36
|
+
if ((_b = adkEvent.actions) == null ? void 0 : _b.transferToAgent) {
|
|
37
|
+
finalEventActions.transferToAgent = adkEvent.actions.transferToAgent;
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
const inputRequiredEvent = scanForInputRequiredEvents(adkEvents, context);
|
|
41
|
+
if (inputRequiredEvent) {
|
|
42
|
+
return {
|
|
43
|
+
...inputRequiredEvent,
|
|
44
|
+
metadata: {
|
|
45
|
+
...inputRequiredEvent.metadata,
|
|
46
|
+
...getA2AEventMetadataFromActions(finalEventActions)
|
|
47
|
+
}
|
|
48
|
+
};
|
|
49
|
+
}
|
|
50
|
+
return createTaskCompletedEvent({
|
|
51
|
+
taskId: context.requestContext.taskId,
|
|
52
|
+
contextId: context.requestContext.contextId,
|
|
53
|
+
metadata: {
|
|
54
|
+
...getA2ASessionMetadata(context),
|
|
55
|
+
...getA2AEventMetadataFromActions(finalEventActions)
|
|
56
|
+
}
|
|
57
|
+
});
|
|
58
|
+
}
|
|
59
|
+
function scanForInputRequiredEvents(adkEvents, context) {
|
|
60
|
+
var _a, _b;
|
|
61
|
+
const inputRequiredParts = [];
|
|
62
|
+
const inputRequiredFunctionCallIds = /* @__PURE__ */ new Set();
|
|
63
|
+
for (const adkEvent of adkEvents) {
|
|
64
|
+
if (!((_b = (_a = adkEvent.content) == null ? void 0 : _a.parts) == null ? void 0 : _b.length)) {
|
|
65
|
+
continue;
|
|
66
|
+
}
|
|
67
|
+
for (const genAIPart of adkEvent.content.parts) {
|
|
68
|
+
const longRunningFunctionCallId = getLongRunnningFunctionCallId(
|
|
69
|
+
genAIPart,
|
|
70
|
+
adkEvent.longRunningToolIds,
|
|
71
|
+
inputRequiredParts
|
|
72
|
+
);
|
|
73
|
+
if (!longRunningFunctionCallId) {
|
|
74
|
+
continue;
|
|
75
|
+
}
|
|
76
|
+
const isAlreadyAdded = inputRequiredFunctionCallIds.has(
|
|
77
|
+
longRunningFunctionCallId
|
|
78
|
+
);
|
|
79
|
+
if (isAlreadyAdded) {
|
|
80
|
+
continue;
|
|
81
|
+
}
|
|
82
|
+
inputRequiredParts.push(genAIPart);
|
|
83
|
+
inputRequiredFunctionCallIds.add(longRunningFunctionCallId);
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
if (inputRequiredParts.length > 0) {
|
|
87
|
+
return createTaskInputRequiredEvent({
|
|
88
|
+
taskId: context.requestContext.taskId,
|
|
89
|
+
contextId: context.requestContext.contextId,
|
|
90
|
+
parts: toA2AParts(inputRequiredParts, [...inputRequiredFunctionCallIds]),
|
|
91
|
+
metadata: getA2ASessionMetadata(context)
|
|
92
|
+
});
|
|
93
|
+
}
|
|
94
|
+
return void 0;
|
|
95
|
+
}
|
|
96
|
+
function getLongRunnningFunctionCallId(genAIPart, longRunningToolIds = [], inputRequiredParts = []) {
|
|
97
|
+
var _a, _b, _c;
|
|
98
|
+
const functionCallId = (_a = genAIPart.functionCall) == null ? void 0 : _a.id;
|
|
99
|
+
const functionResponseId = (_b = genAIPart.functionResponse) == null ? void 0 : _b.id;
|
|
100
|
+
if (!functionCallId && !functionResponseId) {
|
|
101
|
+
return;
|
|
102
|
+
}
|
|
103
|
+
if (functionCallId && longRunningToolIds.includes(functionCallId)) {
|
|
104
|
+
return functionCallId;
|
|
105
|
+
}
|
|
106
|
+
if (functionResponseId && longRunningToolIds.includes(functionResponseId)) {
|
|
107
|
+
return functionResponseId;
|
|
108
|
+
}
|
|
109
|
+
for (const part of inputRequiredParts) {
|
|
110
|
+
if (((_c = part.functionCall) == null ? void 0 : _c.id) === functionResponseId) {
|
|
111
|
+
return functionResponseId;
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
return;
|
|
115
|
+
}
|
|
116
|
+
function getTaskInputRequiredEvent(task, genAIContent) {
|
|
117
|
+
var _a;
|
|
118
|
+
if (!task || !isInputRequiredTaskStatusUpdateEvent(task) || !task.status.message) {
|
|
119
|
+
return void 0;
|
|
120
|
+
}
|
|
121
|
+
const statusMsg = task.status.message;
|
|
122
|
+
const taskParts = toGenAIParts(statusMsg.parts);
|
|
123
|
+
for (const taskPart of taskParts) {
|
|
124
|
+
const functionCallId = (_a = taskPart.functionCall) == null ? void 0 : _a.id;
|
|
125
|
+
if (!functionCallId) {
|
|
126
|
+
continue;
|
|
127
|
+
}
|
|
128
|
+
const hasMatchingResponse = ((genAIContent == null ? void 0 : genAIContent.parts) || []).some(
|
|
129
|
+
(p) => {
|
|
130
|
+
var _a2;
|
|
131
|
+
return ((_a2 = p.functionResponse) == null ? void 0 : _a2.id) === functionCallId;
|
|
132
|
+
}
|
|
133
|
+
);
|
|
134
|
+
if (!hasMatchingResponse) {
|
|
135
|
+
return createInputMissingErrorEvent({
|
|
136
|
+
taskId: task.id,
|
|
137
|
+
contextId: task.contextId,
|
|
138
|
+
parts: [
|
|
139
|
+
...statusMsg.parts.filter((p) => {
|
|
140
|
+
var _a2;
|
|
141
|
+
return !((_a2 = p.metadata) == null ? void 0 : _a2.validation_error);
|
|
142
|
+
}),
|
|
143
|
+
{
|
|
144
|
+
kind: "text",
|
|
145
|
+
text: `No input provided for function call id ${functionCallId}`,
|
|
146
|
+
metadata: {
|
|
147
|
+
validation_error: true
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
]
|
|
151
|
+
});
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
return void 0;
|
|
155
|
+
}
|
|
156
|
+
export {
|
|
157
|
+
getFinalTaskStatusUpdate,
|
|
158
|
+
getTaskInputRequiredEvent
|
|
159
|
+
};
|
|
@@ -25,6 +25,7 @@ var A2AMetadataKeys = ((A2AMetadataKeys2) => {
|
|
|
25
25
|
A2AMetadataKeys2["GROUNDING_METADATA"] = `${ADK_METADATA_KEY_PREFIX}grounding_metadata`;
|
|
26
26
|
A2AMetadataKeys2["USAGE_METADATA"] = `${ADK_METADATA_KEY_PREFIX}usage_metadata`;
|
|
27
27
|
A2AMetadataKeys2["CUSTOM_METADATA"] = `${ADK_METADATA_KEY_PREFIX}custom_metadata`;
|
|
28
|
+
A2AMetadataKeys2["VIDEO_METADATA"] = `${ADK_METADATA_KEY_PREFIX}video_metadata`;
|
|
28
29
|
return A2AMetadataKeys2;
|
|
29
30
|
})(A2AMetadataKeys || {});
|
|
30
31
|
var AdkMetadataKeys = ((AdkMetadataKeys2) => {
|
|
@@ -37,6 +37,10 @@ function toA2ATextPart(part) {
|
|
|
37
37
|
return a2aPart;
|
|
38
38
|
}
|
|
39
39
|
function toA2AFilePart(part) {
|
|
40
|
+
const metadata = {};
|
|
41
|
+
if (part.videoMetadata) {
|
|
42
|
+
metadata[A2AMetadataKeys.VIDEO_METADATA] = part.videoMetadata;
|
|
43
|
+
}
|
|
40
44
|
if (part.fileData) {
|
|
41
45
|
return {
|
|
42
46
|
kind: "file",
|
|
@@ -44,7 +48,7 @@ function toA2AFilePart(part) {
|
|
|
44
48
|
uri: part.fileData.fileUri || "",
|
|
45
49
|
mimeType: part.fileData.mimeType
|
|
46
50
|
},
|
|
47
|
-
metadata
|
|
51
|
+
metadata
|
|
48
52
|
};
|
|
49
53
|
}
|
|
50
54
|
if (part.inlineData) {
|
|
@@ -54,7 +58,7 @@ function toA2AFilePart(part) {
|
|
|
54
58
|
bytes: part.inlineData.data || "",
|
|
55
59
|
mimeType: part.inlineData.mimeType
|
|
56
60
|
},
|
|
57
|
-
metadata
|
|
61
|
+
metadata
|
|
58
62
|
};
|
|
59
63
|
}
|
|
60
64
|
throw new Error(`Not a file part: ${JSON.stringify(part)}`);
|
|
@@ -75,7 +79,11 @@ function toA2ADataPart(part, longRunningToolIDs = []) {
|
|
|
75
79
|
dataPartType = "code_execution_result" /* CODE_EXEC_RESULT */;
|
|
76
80
|
data = part.codeExecutionResult;
|
|
77
81
|
} else {
|
|
78
|
-
|
|
82
|
+
return {
|
|
83
|
+
kind: "data",
|
|
84
|
+
data: {},
|
|
85
|
+
metadata: {}
|
|
86
|
+
};
|
|
79
87
|
}
|
|
80
88
|
const metadata = {
|
|
81
89
|
[A2AMetadataKeys.DATA_PART_TYPE]: dataPartType
|
|
@@ -119,21 +127,24 @@ function toGenAIPartText(a2aPart) {
|
|
|
119
127
|
};
|
|
120
128
|
}
|
|
121
129
|
function toGenAIPartFile(a2aPart) {
|
|
130
|
+
var _a;
|
|
131
|
+
const part = {};
|
|
132
|
+
if ((_a = a2aPart.metadata) == null ? void 0 : _a[A2AMetadataKeys.VIDEO_METADATA]) {
|
|
133
|
+
part.videoMetadata = a2aPart.metadata[A2AMetadataKeys.VIDEO_METADATA];
|
|
134
|
+
}
|
|
122
135
|
if ("bytes" in a2aPart.file) {
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
mimeType: a2aPart.file.mimeType || ""
|
|
127
|
-
}
|
|
136
|
+
part.inlineData = {
|
|
137
|
+
data: a2aPart.file.bytes,
|
|
138
|
+
mimeType: a2aPart.file.mimeType || ""
|
|
128
139
|
};
|
|
140
|
+
return part;
|
|
129
141
|
}
|
|
130
142
|
if ("uri" in a2aPart.file) {
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
mimeType: a2aPart.file.mimeType || ""
|
|
135
|
-
}
|
|
143
|
+
part.fileData = {
|
|
144
|
+
fileUri: a2aPart.file.uri,
|
|
145
|
+
mimeType: a2aPart.file.mimeType || ""
|
|
136
146
|
};
|
|
147
|
+
return part;
|
|
137
148
|
}
|
|
138
149
|
throw new Error(`Not a file part: ${JSON.stringify(a2aPart)}`);
|
|
139
150
|
}
|
|
@@ -34,6 +34,7 @@ import { AGENT_TRANSFER_LLM_REQUEST_PROCESSOR } from "./processors/agent_transfe
|
|
|
34
34
|
import { BASIC_LLM_REQUEST_PROCESSOR } from "./processors/basic_llm_request_processor.js";
|
|
35
35
|
import { CODE_EXECUTION_REQUEST_PROCESSOR } from "./processors/code_execution_request_processor.js";
|
|
36
36
|
import { CONTENT_REQUEST_PROCESSOR } from "./processors/content_request_processor.js";
|
|
37
|
+
import { ContextCompactorRequestProcessor } from "./processors/context_compactor_request_processor.js";
|
|
37
38
|
import { IDENTITY_LLM_REQUEST_PROCESSOR } from "./processors/identity_llm_request_processor.js";
|
|
38
39
|
import { INSTRUCTIONS_LLM_REQUEST_PROCESSOR } from "./processors/instructions_llm_request_processor.js";
|
|
39
40
|
import { REQUEST_CONFIRMATION_LLM_REQUEST_PROCESSOR } from "./processors/request_confirmation_llm_request_processor.js";
|
|
@@ -80,6 +81,22 @@ class LlmAgent extends (_b = BaseAgent, _a = LLM_AGENT_SIGNATURE_SYMBOL, _b) {
|
|
|
80
81
|
CONTENT_REQUEST_PROCESSOR,
|
|
81
82
|
CODE_EXECUTION_REQUEST_PROCESSOR
|
|
82
83
|
];
|
|
84
|
+
if (!config.requestProcessors && config.contextCompactors && config.contextCompactors.length > 0) {
|
|
85
|
+
const contentIndex = this.requestProcessors.indexOf(
|
|
86
|
+
CONTENT_REQUEST_PROCESSOR
|
|
87
|
+
);
|
|
88
|
+
if (contentIndex !== -1) {
|
|
89
|
+
this.requestProcessors.splice(
|
|
90
|
+
contentIndex,
|
|
91
|
+
0,
|
|
92
|
+
new ContextCompactorRequestProcessor(config.contextCompactors)
|
|
93
|
+
);
|
|
94
|
+
} else {
|
|
95
|
+
this.requestProcessors.push(
|
|
96
|
+
new ContextCompactorRequestProcessor(config.contextCompactors)
|
|
97
|
+
);
|
|
98
|
+
}
|
|
99
|
+
}
|
|
83
100
|
this.responseProcessors = (_h = config.responseProcessors) != null ? _h : [];
|
|
84
101
|
const agentTransferDisabled = this.disallowTransferToParent && this.disallowTransferToPeers && !((_i = this.subAgents) == null ? void 0 : _i.length);
|
|
85
102
|
if (!agentTransferDisabled) {
|
package/dist/esm/agents/{content_processor_utils.js → processors/content_processor_utils.js}
RENAMED
|
@@ -3,21 +3,29 @@
|
|
|
3
3
|
* Copyright 2025 Google LLC
|
|
4
4
|
* SPDX-License-Identifier: Apache-2.0
|
|
5
5
|
*/
|
|
6
|
+
import { createUserContent } from "@google/genai";
|
|
6
7
|
import { cloneDeep } from "lodash-es";
|
|
8
|
+
import {
|
|
9
|
+
isCompactedEvent
|
|
10
|
+
} from "../../events/compacted_event.js";
|
|
7
11
|
import {
|
|
8
12
|
createEvent,
|
|
9
13
|
getFunctionCalls,
|
|
10
14
|
getFunctionResponses
|
|
11
|
-
} from "
|
|
15
|
+
} from "../../events/event.js";
|
|
12
16
|
import {
|
|
13
17
|
removeClientFunctionCallId,
|
|
14
18
|
REQUEST_CONFIRMATION_FUNCTION_CALL_NAME,
|
|
15
19
|
REQUEST_EUC_FUNCTION_CALL_NAME
|
|
16
|
-
} from "
|
|
20
|
+
} from "../functions.js";
|
|
17
21
|
function getContents(events, agentName, currentBranch) {
|
|
18
22
|
var _a, _b, _c;
|
|
19
23
|
const filteredEvents = [];
|
|
20
24
|
for (const event of events) {
|
|
25
|
+
if (isCompactedEvent(event)) {
|
|
26
|
+
filteredEvents.push(convertCompactedEvent(event));
|
|
27
|
+
continue;
|
|
28
|
+
}
|
|
21
29
|
if (!((_a = event.content) == null ? void 0 : _a.role) || ((_c = (_b = event.content.parts) == null ? void 0 : _b[0]) == null ? void 0 : _c.text) === "") {
|
|
22
30
|
continue;
|
|
23
31
|
}
|
|
@@ -290,6 +298,19 @@ function safeStringify(obj) {
|
|
|
290
298
|
return String(obj);
|
|
291
299
|
}
|
|
292
300
|
}
|
|
301
|
+
function convertCompactedEvent(event) {
|
|
302
|
+
const content = createUserContent(
|
|
303
|
+
`[Previous Context Summary]:
|
|
304
|
+
${event.compactedContent}`
|
|
305
|
+
);
|
|
306
|
+
return createEvent({
|
|
307
|
+
invocationId: event.invocationId,
|
|
308
|
+
author: "user",
|
|
309
|
+
content,
|
|
310
|
+
branch: event.branch,
|
|
311
|
+
timestamp: event.timestamp
|
|
312
|
+
});
|
|
313
|
+
}
|
|
293
314
|
export {
|
|
294
315
|
getContents,
|
|
295
316
|
getCurrentTurnContents
|
|
@@ -3,11 +3,12 @@
|
|
|
3
3
|
* Copyright 2025 Google LLC
|
|
4
4
|
* SPDX-License-Identifier: Apache-2.0
|
|
5
5
|
*/
|
|
6
|
+
import { isCompactedEvent } from "../../events/compacted_event.js";
|
|
7
|
+
import { isLlmAgent } from "../llm_agent.js";
|
|
6
8
|
import {
|
|
7
9
|
getContents,
|
|
8
10
|
getCurrentTurnContents
|
|
9
|
-
} from "
|
|
10
|
-
import { isLlmAgent } from "../llm_agent.js";
|
|
11
|
+
} from "./content_processor_utils.js";
|
|
11
12
|
class ContentRequestProcessor {
|
|
12
13
|
// eslint-disable-next-line require-yield
|
|
13
14
|
async *runAsync(invocationContext, llmRequest) {
|
|
@@ -15,15 +16,35 @@ class ContentRequestProcessor {
|
|
|
15
16
|
if (!agent || !isLlmAgent(agent)) {
|
|
16
17
|
return;
|
|
17
18
|
}
|
|
19
|
+
let events = invocationContext.session.events;
|
|
20
|
+
const compactedEvents = events.filter(isCompactedEvent);
|
|
21
|
+
const latestCompactedEvent = compactedEvents.length > 0 ? compactedEvents.reduce(
|
|
22
|
+
(latest, current) => current.endTime > latest.endTime ? current : latest
|
|
23
|
+
) : void 0;
|
|
24
|
+
if (latestCompactedEvent) {
|
|
25
|
+
const remainingEvents = events.filter((event) => {
|
|
26
|
+
if (event === latestCompactedEvent) {
|
|
27
|
+
return false;
|
|
28
|
+
}
|
|
29
|
+
if (isCompactedEvent(event)) {
|
|
30
|
+
return false;
|
|
31
|
+
}
|
|
32
|
+
if (event.timestamp <= latestCompactedEvent.endTime) {
|
|
33
|
+
return false;
|
|
34
|
+
}
|
|
35
|
+
return true;
|
|
36
|
+
});
|
|
37
|
+
events = [latestCompactedEvent, ...remainingEvents];
|
|
38
|
+
}
|
|
18
39
|
if (agent.includeContents === "default") {
|
|
19
40
|
llmRequest.contents = getContents(
|
|
20
|
-
|
|
41
|
+
events,
|
|
21
42
|
agent.name,
|
|
22
43
|
invocationContext.branch
|
|
23
44
|
);
|
|
24
45
|
} else {
|
|
25
46
|
llmRequest.contents = getCurrentTurnContents(
|
|
26
|
-
|
|
47
|
+
events,
|
|
27
48
|
agent.name,
|
|
28
49
|
invocationContext.branch
|
|
29
50
|
);
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2026 Google LLC
|
|
4
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
5
|
+
*/
|
|
6
|
+
class ContextCompactorRequestProcessor {
|
|
7
|
+
constructor(compactors) {
|
|
8
|
+
this.compactors = compactors;
|
|
9
|
+
}
|
|
10
|
+
async *runAsync(invocationContext, _llmRequest) {
|
|
11
|
+
for (const compactor of this.compactors) {
|
|
12
|
+
const shouldCompact = await Promise.resolve(
|
|
13
|
+
compactor.shouldCompact(invocationContext)
|
|
14
|
+
);
|
|
15
|
+
if (shouldCompact) {
|
|
16
|
+
const oldEvents = new Set(invocationContext.session.events);
|
|
17
|
+
await Promise.resolve(compactor.compact(invocationContext));
|
|
18
|
+
const newEvents = invocationContext.session.events.filter(
|
|
19
|
+
(e) => !oldEvents.has(e)
|
|
20
|
+
);
|
|
21
|
+
for (const e of newEvents) {
|
|
22
|
+
yield e;
|
|
23
|
+
}
|
|
24
|
+
return;
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
export {
|
|
30
|
+
ContextCompactorRequestProcessor
|
|
31
|
+
};
|
|
@@ -15,7 +15,7 @@ class InstructionsLlmRequestProcessor extends BaseLlmRequestProcessor {
|
|
|
15
15
|
// eslint-disable-next-line require-yield
|
|
16
16
|
async *runAsync(invocationContext, llmRequest) {
|
|
17
17
|
const agent = invocationContext.agent;
|
|
18
|
-
if (!isLlmAgent(agent)
|
|
18
|
+
if (!isLlmAgent(agent)) {
|
|
19
19
|
return;
|
|
20
20
|
}
|
|
21
21
|
const rootAgent = agent.rootAgent;
|
|
@@ -307,8 +307,28 @@ class FileArtifactService {
|
|
|
307
307
|
}
|
|
308
308
|
}
|
|
309
309
|
}
|
|
310
|
+
const SAFE_SEGMENT_RE = /^[a-zA-Z0-9_@-][a-zA-Z0-9_.@-]{0,255}$/;
|
|
311
|
+
function assertSafeSegment(value, label) {
|
|
312
|
+
if (!value || !SAFE_SEGMENT_RE.test(value)) {
|
|
313
|
+
throw new Error(
|
|
314
|
+
`[FileArtifactService] Invalid ${label}: value contains disallowed characters.`
|
|
315
|
+
);
|
|
316
|
+
}
|
|
317
|
+
}
|
|
318
|
+
function assertInsideRoot(resolvedPath, rootDir, label) {
|
|
319
|
+
const root = path.resolve(rootDir);
|
|
320
|
+
const resolved = path.resolve(resolvedPath);
|
|
321
|
+
if (!resolved.startsWith(root + path.sep) && resolved !== root) {
|
|
322
|
+
throw new Error(
|
|
323
|
+
`[FileArtifactService] ${label} escapes storage root. Resolved: ${resolved}, Root: ${root}`
|
|
324
|
+
);
|
|
325
|
+
}
|
|
326
|
+
}
|
|
310
327
|
function getUserRoot(rootDir, userId) {
|
|
311
|
-
|
|
328
|
+
assertSafeSegment(userId, "userId");
|
|
329
|
+
const result = path.join(rootDir, "users", userId);
|
|
330
|
+
assertInsideRoot(result, rootDir, "userRoot");
|
|
331
|
+
return result;
|
|
312
332
|
}
|
|
313
333
|
function isUserScoped(sessionId, filename) {
|
|
314
334
|
return !sessionId || filename.startsWith(USER_NAMESPACE_PREFIX);
|
|
@@ -317,7 +337,10 @@ function getUserArtifactsDir(userRoot) {
|
|
|
317
337
|
return path.join(userRoot, "artifacts");
|
|
318
338
|
}
|
|
319
339
|
function getSessionArtifactsDir(baseRoot, sessionId) {
|
|
320
|
-
|
|
340
|
+
assertSafeSegment(sessionId, "sessionId");
|
|
341
|
+
const result = path.join(baseRoot, "sessions", sessionId, "artifacts");
|
|
342
|
+
assertInsideRoot(result, baseRoot, "sessionArtifactsDir");
|
|
343
|
+
return result;
|
|
321
344
|
}
|
|
322
345
|
function getVersionsDir(artifactDir) {
|
|
323
346
|
return path.join(artifactDir, "versions");
|
|
@@ -447,5 +470,9 @@ function asPosixPath(p) {
|
|
|
447
470
|
return p.split(path.sep).join("/");
|
|
448
471
|
}
|
|
449
472
|
export {
|
|
450
|
-
FileArtifactService
|
|
473
|
+
FileArtifactService,
|
|
474
|
+
assertInsideRoot,
|
|
475
|
+
assertSafeSegment,
|
|
476
|
+
getSessionArtifactsDir,
|
|
477
|
+
getUserRoot
|
|
451
478
|
};
|
package/dist/esm/common.js
CHANGED
|
@@ -16,6 +16,11 @@ import {
|
|
|
16
16
|
BaseLlmRequestProcessor,
|
|
17
17
|
BaseLlmResponseProcessor
|
|
18
18
|
} from "./agents/processors/base_llm_processor.js";
|
|
19
|
+
import {
|
|
20
|
+
CONTENT_REQUEST_PROCESSOR,
|
|
21
|
+
ContentRequestProcessor
|
|
22
|
+
} from "./agents/processors/content_request_processor.js";
|
|
23
|
+
import { ContextCompactorRequestProcessor } from "./agents/processors/context_compactor_request_processor.js";
|
|
19
24
|
import { ReadonlyContext } from "./agents/readonly_context.js";
|
|
20
25
|
import { StreamingMode } from "./agents/run_config.js";
|
|
21
26
|
import { SequentialAgent, isSequentialAgent } from "./agents/sequential_agent.js";
|
|
@@ -23,6 +28,10 @@ import { InMemoryArtifactService } from "./artifacts/in_memory_artifact_service.
|
|
|
23
28
|
import { AuthCredentialTypes } from "./auth/auth_credential.js";
|
|
24
29
|
import { BaseCodeExecutor } from "./code_executors/base_code_executor.js";
|
|
25
30
|
import { BuiltInCodeExecutor } from "./code_executors/built_in_code_executor.js";
|
|
31
|
+
import { LlmSummarizer } from "./context/summarizers/llm_summarizer.js";
|
|
32
|
+
import { TokenBasedContextCompactor } from "./context/token_based_context_compactor.js";
|
|
33
|
+
import { TruncatingContextCompactor } from "./context/truncating_context_compactor.js";
|
|
34
|
+
import { isCompactedEvent } from "./events/compacted_event.js";
|
|
26
35
|
import {
|
|
27
36
|
createEvent,
|
|
28
37
|
getFunctionCalls,
|
|
@@ -53,7 +62,7 @@ import {
|
|
|
53
62
|
getAskUserConfirmationFunctionCalls
|
|
54
63
|
} from "./plugins/security_plugin.js";
|
|
55
64
|
import { InMemoryRunner } from "./runner/in_memory_runner.js";
|
|
56
|
-
import { Runner } from "./runner/runner.js";
|
|
65
|
+
import { Runner, isRunner } from "./runner/runner.js";
|
|
57
66
|
import { BaseSessionService } from "./sessions/base_session_service.js";
|
|
58
67
|
import { InMemorySessionService } from "./sessions/in_memory_session_service.js";
|
|
59
68
|
import { createSession } from "./sessions/session.js";
|
|
@@ -64,7 +73,16 @@ import { BaseToolset, isBaseToolset } from "./tools/base_toolset.js";
|
|
|
64
73
|
import { EXIT_LOOP, ExitLoopTool } from "./tools/exit_loop_tool.js";
|
|
65
74
|
import { FunctionTool, isFunctionTool } from "./tools/function_tool.js";
|
|
66
75
|
import { GOOGLE_SEARCH, GoogleSearchTool } from "./tools/google_search_tool.js";
|
|
76
|
+
import {
|
|
77
|
+
LOAD_ARTIFACTS,
|
|
78
|
+
LoadArtifactsTool
|
|
79
|
+
} from "./tools/load_artifacts_tool.js";
|
|
80
|
+
import { LOAD_MEMORY, LoadMemoryTool } from "./tools/load_memory_tool.js";
|
|
67
81
|
import { LongRunningFunctionTool } from "./tools/long_running_tool.js";
|
|
82
|
+
import {
|
|
83
|
+
PRELOAD_MEMORY,
|
|
84
|
+
PreloadMemoryTool
|
|
85
|
+
} from "./tools/preload_memory_tool.js";
|
|
68
86
|
import { ToolConfirmation } from "./tools/tool_confirmation.js";
|
|
69
87
|
import { LogLevel, getLogger, setLogLevel, setLogger } from "./utils/logger.js";
|
|
70
88
|
import { isGemini2OrAbove } from "./utils/model_name.js";
|
|
@@ -91,7 +109,10 @@ export {
|
|
|
91
109
|
BaseTool,
|
|
92
110
|
BaseToolset,
|
|
93
111
|
BuiltInCodeExecutor,
|
|
112
|
+
CONTENT_REQUEST_PROCESSOR,
|
|
113
|
+
ContentRequestProcessor,
|
|
94
114
|
Context,
|
|
115
|
+
ContextCompactorRequestProcessor,
|
|
95
116
|
EXIT_LOOP,
|
|
96
117
|
EventType,
|
|
97
118
|
ExitLoopTool,
|
|
@@ -107,15 +128,22 @@ export {
|
|
|
107
128
|
InMemorySessionService,
|
|
108
129
|
InvocationContext,
|
|
109
130
|
LLMRegistry,
|
|
131
|
+
LOAD_ARTIFACTS,
|
|
132
|
+
LOAD_MEMORY,
|
|
110
133
|
LiveRequestQueue,
|
|
111
134
|
LlmAgent,
|
|
135
|
+
LlmSummarizer,
|
|
136
|
+
LoadArtifactsTool,
|
|
137
|
+
LoadMemoryTool,
|
|
112
138
|
LogLevel,
|
|
113
139
|
LoggingPlugin,
|
|
114
140
|
LongRunningFunctionTool,
|
|
115
141
|
LoopAgent,
|
|
142
|
+
PRELOAD_MEMORY,
|
|
116
143
|
ParallelAgent,
|
|
117
144
|
PluginManager,
|
|
118
145
|
PolicyOutcome,
|
|
146
|
+
PreloadMemoryTool,
|
|
119
147
|
REQUEST_CONFIRMATION_FUNCTION_CALL_NAME,
|
|
120
148
|
ReadonlyContext,
|
|
121
149
|
Runner,
|
|
@@ -123,7 +151,9 @@ export {
|
|
|
123
151
|
SequentialAgent,
|
|
124
152
|
State,
|
|
125
153
|
StreamingMode,
|
|
154
|
+
TokenBasedContextCompactor,
|
|
126
155
|
ToolConfirmation,
|
|
156
|
+
TruncatingContextCompactor,
|
|
127
157
|
createEvent,
|
|
128
158
|
createEventActions,
|
|
129
159
|
createSession,
|
|
@@ -140,12 +170,14 @@ export {
|
|
|
140
170
|
isBaseLlm,
|
|
141
171
|
isBaseTool,
|
|
142
172
|
isBaseToolset,
|
|
173
|
+
isCompactedEvent,
|
|
143
174
|
isFinalResponse,
|
|
144
175
|
isFunctionTool,
|
|
145
176
|
isGemini2OrAbove,
|
|
146
177
|
isLlmAgent,
|
|
147
178
|
isLoopAgent,
|
|
148
179
|
isParallelAgent,
|
|
180
|
+
isRunner,
|
|
149
181
|
isSequentialAgent,
|
|
150
182
|
setLogLevel,
|
|
151
183
|
setLogger,
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2026 Google LLC
|
|
4
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
5
|
+
*/
|
|
6
|
+
import {
|
|
7
|
+
createCompactedEvent
|
|
8
|
+
} from "../../events/compacted_event.js";
|
|
9
|
+
import { stringifyContent } from "../../events/event.js";
|
|
10
|
+
const DEFAULT_PROMPT = "The following is a conversation history between a user and an AI agent. Please summarize the conversation, focusing on key information and decisions made, as well as any unresolved questions or tasks. The summary should be concise and capture the essence of the interaction.";
|
|
11
|
+
class LlmSummarizer {
|
|
12
|
+
constructor(options) {
|
|
13
|
+
this.llm = options.llm;
|
|
14
|
+
this.prompt = options.prompt || DEFAULT_PROMPT;
|
|
15
|
+
}
|
|
16
|
+
async summarize(events) {
|
|
17
|
+
var _a, _b, _c, _d, _e, _f;
|
|
18
|
+
if (events.length === 0) {
|
|
19
|
+
throw new Error("Cannot summarize an empty list of events.");
|
|
20
|
+
}
|
|
21
|
+
const startTime = events[0].timestamp;
|
|
22
|
+
const endTime = events[events.length - 1].timestamp;
|
|
23
|
+
let formattedEvents = "";
|
|
24
|
+
for (let i = 0; i < events.length; i++) {
|
|
25
|
+
formattedEvents += `[Event ${i + 1} - Author: ${events[i].author}]
|
|
26
|
+
`;
|
|
27
|
+
formattedEvents += `${stringifyContent(events[i])}
|
|
28
|
+
|
|
29
|
+
`;
|
|
30
|
+
}
|
|
31
|
+
const fullPrompt = `${this.prompt}
|
|
32
|
+
|
|
33
|
+
${formattedEvents}`;
|
|
34
|
+
const request = {
|
|
35
|
+
contents: [{ role: "user", parts: [{ text: fullPrompt }] }],
|
|
36
|
+
toolsDict: {},
|
|
37
|
+
liveConnectConfig: {}
|
|
38
|
+
};
|
|
39
|
+
const responseGen = this.llm.generateContentAsync(request, false);
|
|
40
|
+
let compactedContent = "";
|
|
41
|
+
const firstResponse = await responseGen.next();
|
|
42
|
+
if (firstResponse.done || !((_c = (_b = (_a = firstResponse.value.content) == null ? void 0 : _a.parts) == null ? void 0 : _b[0]) == null ? void 0 : _c.text)) {
|
|
43
|
+
throw new Error("LLM failed to return a valid summary.");
|
|
44
|
+
}
|
|
45
|
+
compactedContent += firstResponse.value.content.parts[0].text;
|
|
46
|
+
for await (const chunk of responseGen) {
|
|
47
|
+
if ((_f = (_e = (_d = chunk.content) == null ? void 0 : _d.parts) == null ? void 0 : _e[0]) == null ? void 0 : _f.text) {
|
|
48
|
+
compactedContent += chunk.content.parts[0].text;
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
return createCompactedEvent({
|
|
52
|
+
author: "system",
|
|
53
|
+
content: {
|
|
54
|
+
role: "model",
|
|
55
|
+
parts: [{ text: compactedContent }]
|
|
56
|
+
},
|
|
57
|
+
startTime,
|
|
58
|
+
endTime,
|
|
59
|
+
compactedContent
|
|
60
|
+
});
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
export {
|
|
64
|
+
LlmSummarizer
|
|
65
|
+
};
|