@google/adk 1.4.0 → 1.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cjs/a2a/a2a_remote_agent.js +12 -2
- package/dist/cjs/a2a/agent_to_a2a.js +18 -3
- package/dist/cjs/a2a/auth.js +65 -0
- package/dist/cjs/a2a/event_converter_utils.js +47 -18
- package/dist/cjs/a2a/metadata_converter_utils.js +1 -1
- package/dist/cjs/agents/base_agent.js +39 -0
- package/dist/cjs/agents/functions.js +26 -28
- package/dist/cjs/agents/llm_agent.js +4 -2
- package/dist/cjs/agents/loop_agent.js +15 -3
- package/dist/cjs/agents/processors/basic_llm_request_processor.js +3 -2
- package/dist/cjs/agents/processors/content_processor_utils.js +2 -1
- package/dist/cjs/agents/processors/content_request_processor.js +2 -21
- package/dist/cjs/agents/processors/instructions_llm_request_processor.js +3 -1
- package/dist/cjs/agents/routed_agent.js +31 -0
- package/dist/cjs/agents/run_config.js +3 -2
- package/dist/cjs/artifacts/in_memory_artifact_service.js +17 -9
- package/dist/cjs/auth/credential_service/in_memory_credential_service.js +14 -3
- package/dist/cjs/code_executors/unsafe_local_code_executor.js +23 -12
- package/dist/cjs/common.js +35 -0
- package/dist/cjs/context/agent_controlled_context_compactor.js +2 -11
- package/dist/cjs/context/anchored_context_compactor.js +127 -0
- package/dist/cjs/context/compaction_utils.js +64 -0
- package/dist/cjs/context/token_based_context_compactor.js +13 -44
- package/dist/cjs/events/compacted_event.js +9 -3
- package/dist/cjs/events/event.js +28 -0
- package/dist/cjs/index.js +7 -0
- package/dist/cjs/integrations/agent_registry/agent_registry_mcp_toolset.js +9 -1
- package/dist/cjs/memory/in_memory_memory_service.js +13 -2
- package/dist/cjs/memory/vertex_ai_memory_bank_service.js +3 -0
- package/dist/cjs/plugins/base_plugin.js +4 -2
- package/dist/cjs/plugins/global_instruction_plugin.js +97 -0
- package/dist/cjs/runner/runner.js +69 -23
- package/dist/cjs/sessions/base_session_service.js +8 -3
- package/dist/cjs/sessions/in_memory_session_service.js +8 -8
- package/dist/cjs/sessions/vertex_ai_session_service.js +22 -10
- package/dist/cjs/skills/loader.js +40 -6
- package/dist/cjs/tools/enterprise_web_search_tool.js +81 -0
- package/dist/cjs/tools/example_tool.js +68 -0
- package/dist/cjs/tools/get_user_choice_tool.js +53 -0
- package/dist/cjs/tools/load_web_page.js +250 -0
- package/dist/cjs/tools/mcp/load_mcp_resource_tool.js +140 -0
- package/dist/cjs/tools/mcp/mcp_session_manager.js +35 -21
- package/dist/cjs/tools/mcp/mcp_toolset.js +63 -0
- package/dist/cjs/tools/openapi_tool/openapi_spec_parser/tool_auth_handler.js +13 -10
- package/dist/cjs/tools/request_input_tool.js +54 -0
- package/dist/cjs/tools/skill/run_skill_inline_script_tool.js +54 -4
- package/dist/cjs/tools/skill/skill_toolset.js +4 -2
- package/dist/cjs/utils/branch_trie.js +41 -0
- package/dist/cjs/utils/crypto_shim.js +43 -0
- package/dist/cjs/utils/env_aware_utils.js +15 -13
- package/dist/cjs/utils/error_utils.js +120 -0
- package/dist/cjs/utils/file_utils.js +5 -2
- package/dist/cjs/utils/output_schema_utils.js +43 -0
- package/dist/cjs/utils/streaming_utils.js +5 -5
- package/dist/cjs/utils/vertex_ai_utils.js +3 -0
- package/dist/cjs/version.js +1 -1
- package/dist/esm/a2a/a2a_remote_agent.js +12 -2
- package/dist/esm/a2a/agent_to_a2a.js +18 -3
- package/dist/esm/a2a/auth.js +37 -0
- package/dist/esm/a2a/event_converter_utils.js +47 -18
- package/dist/esm/a2a/metadata_converter_utils.js +1 -1
- package/dist/esm/agents/base_agent.js +39 -0
- package/dist/esm/agents/functions.js +27 -24
- package/dist/esm/agents/llm_agent.js +6 -4
- package/dist/esm/agents/loop_agent.js +15 -3
- package/dist/esm/agents/processors/basic_llm_request_processor.js +3 -2
- package/dist/esm/agents/processors/content_processor_utils.js +2 -1
- package/dist/esm/agents/processors/content_request_processor.js +2 -21
- package/dist/esm/agents/processors/instructions_llm_request_processor.js +3 -1
- package/dist/esm/agents/routed_agent.js +31 -0
- package/dist/esm/agents/run_config.js +3 -2
- package/dist/esm/artifacts/in_memory_artifact_service.js +17 -9
- package/dist/esm/auth/credential_service/in_memory_credential_service.js +14 -3
- package/dist/esm/code_executors/unsafe_local_code_executor.js +22 -11
- package/dist/esm/common.js +29 -1
- package/dist/esm/context/agent_controlled_context_compactor.js +2 -11
- package/dist/esm/context/anchored_context_compactor.js +99 -0
- package/dist/esm/context/compaction_utils.js +38 -0
- package/dist/esm/context/token_based_context_compactor.js +16 -44
- package/dist/esm/events/compacted_event.js +7 -2
- package/dist/esm/events/event.js +24 -0
- package/dist/esm/index.js +8 -1
- package/dist/esm/integrations/agent_registry/agent_registry_mcp_toolset.js +9 -1
- package/dist/esm/memory/in_memory_memory_service.js +13 -2
- package/dist/esm/memory/vertex_ai_memory_bank_service.js +7 -1
- package/dist/esm/plugins/base_plugin.js +4 -2
- package/dist/esm/plugins/global_instruction_plugin.js +69 -0
- package/dist/esm/runner/runner.js +69 -23
- package/dist/esm/sessions/base_session_service.js +8 -3
- package/dist/esm/sessions/in_memory_session_service.js +8 -8
- package/dist/esm/sessions/vertex_ai_session_service.js +26 -11
- package/dist/esm/skills/loader.js +40 -6
- package/dist/esm/tools/enterprise_web_search_tool.js +55 -0
- package/dist/esm/tools/example_tool.js +42 -0
- package/dist/esm/tools/get_user_choice_tool.js +25 -0
- package/dist/esm/tools/load_web_page.js +221 -0
- package/dist/esm/tools/mcp/load_mcp_resource_tool.js +114 -0
- package/dist/esm/tools/mcp/mcp_session_manager.js +35 -21
- package/dist/esm/tools/mcp/mcp_toolset.js +63 -0
- package/dist/esm/tools/openapi_tool/openapi_spec_parser/tool_auth_handler.js +13 -10
- package/dist/esm/tools/request_input_tool.js +26 -0
- package/dist/esm/tools/skill/run_skill_inline_script_tool.js +53 -4
- package/dist/esm/tools/skill/skill_toolset.js +4 -2
- package/dist/esm/utils/branch_trie.js +13 -0
- package/dist/esm/utils/crypto_shim.js +15 -0
- package/dist/esm/utils/env_aware_utils.js +15 -13
- package/dist/esm/utils/error_utils.js +92 -0
- package/dist/esm/utils/file_utils.js +5 -2
- package/dist/esm/utils/output_schema_utils.js +15 -0
- package/dist/esm/utils/streaming_utils.js +1 -1
- package/dist/esm/utils/vertex_ai_utils.js +2 -0
- package/dist/esm/version.js +1 -1
- package/dist/types/a2a/a2a_remote_agent.d.ts +5 -1
- package/dist/types/a2a/agent_to_a2a.d.ts +38 -0
- package/dist/types/a2a/auth.d.ts +30 -0
- package/dist/types/a2a/event_converter_utils.d.ts +4 -1
- package/dist/types/agents/base_agent.d.ts +29 -1
- package/dist/types/agents/functions.d.ts +1 -9
- package/dist/types/agents/llm_agent.d.ts +5 -1
- package/dist/types/agents/loop_agent.d.ts +2 -2
- package/dist/types/agents/routed_agent.d.ts +24 -1
- package/dist/types/agents/run_config.d.ts +1 -1
- package/dist/types/auth/credential_service/in_memory_credential_service.d.ts +11 -0
- package/dist/types/code_executors/unsafe_local_code_executor.d.ts +5 -1
- package/dist/types/common.d.ts +11 -2
- package/dist/types/context/agent_controlled_context_compactor.d.ts +0 -1
- package/dist/types/context/anchored_context_compactor.d.ts +35 -0
- package/dist/types/context/compaction_utils.d.ts +23 -0
- package/dist/types/context/token_based_context_compactor.d.ts +0 -1
- package/dist/types/events/compacted_event.d.ts +10 -0
- package/dist/types/events/event.d.ts +13 -0
- package/dist/types/index.d.ts +5 -3
- package/dist/types/memory/in_memory_memory_service.d.ts +11 -0
- package/dist/types/plugins/base_plugin.d.ts +4 -2
- package/dist/types/plugins/global_instruction_plugin.d.ts +38 -0
- package/dist/types/runner/runner.d.ts +1 -1
- package/dist/types/sessions/base_session_service.d.ts +8 -0
- package/dist/types/sessions/in_memory_session_service.d.ts +9 -0
- package/dist/types/sessions/vertex_ai_session_service.d.ts +19 -1
- package/dist/types/skills/loader.d.ts +5 -0
- package/dist/types/tools/enterprise_web_search_tool.d.ts +26 -0
- package/dist/types/tools/example_tool.d.ts +21 -0
- package/dist/types/tools/get_user_choice_tool.d.ts +14 -0
- package/dist/types/tools/load_web_page.d.ts +33 -0
- package/dist/types/tools/mcp/load_mcp_resource_tool.d.ts +26 -0
- package/dist/types/tools/mcp/mcp_toolset.d.ts +27 -0
- package/dist/types/tools/request_input_tool.d.ts +15 -0
- package/dist/types/tools/skill/run_skill_inline_script_tool.d.ts +25 -0
- package/dist/types/tools/skill/skill_toolset.d.ts +9 -0
- package/dist/types/utils/branch_trie.d.ts +14 -0
- package/dist/types/utils/crypto_shim.d.ts +16 -0
- package/dist/types/utils/env_aware_utils.d.ts +23 -0
- package/dist/types/utils/error_utils.d.ts +18 -0
- package/dist/types/utils/output_schema_utils.d.ts +18 -0
- package/dist/types/utils/vertex_ai_utils.d.ts +1 -0
- package/dist/types/version.d.ts +1 -1
- package/dist/web/a2a/a2a_remote_agent.js +12 -2
- package/dist/web/a2a/agent_to_a2a.js +18 -3
- package/dist/web/a2a/auth.js +37 -0
- package/dist/web/a2a/event_converter_utils.js +47 -18
- package/dist/web/a2a/metadata_converter_utils.js +1 -1
- package/dist/web/agents/base_agent.js +39 -0
- package/dist/web/agents/functions.js +27 -24
- package/dist/web/agents/llm_agent.js +6 -4
- package/dist/web/agents/loop_agent.js +27 -3
- package/dist/web/agents/processors/basic_llm_request_processor.js +3 -2
- package/dist/web/agents/processors/content_processor_utils.js +2 -1
- package/dist/web/agents/processors/content_request_processor.js +2 -21
- package/dist/web/agents/processors/instructions_llm_request_processor.js +3 -1
- package/dist/web/agents/routed_agent.js +31 -0
- package/dist/web/agents/run_config.js +8 -3
- package/dist/web/artifacts/in_memory_artifact_service.js +17 -9
- package/dist/web/auth/credential_service/in_memory_credential_service.js +14 -3
- package/dist/web/code_executors/unsafe_local_code_executor.js +22 -11
- package/dist/web/common.js +29 -1
- package/dist/web/context/agent_controlled_context_compactor.js +2 -11
- package/dist/web/context/anchored_context_compactor.js +117 -0
- package/dist/web/context/compaction_utils.js +38 -0
- package/dist/web/context/token_based_context_compactor.js +16 -44
- package/dist/web/events/compacted_event.js +7 -2
- package/dist/web/events/event.js +24 -0
- package/dist/web/index.js +8 -1
- package/dist/web/integrations/agent_registry/agent_registry_mcp_toolset.js +9 -1
- package/dist/web/memory/in_memory_memory_service.js +13 -2
- package/dist/web/memory/vertex_ai_memory_bank_service.js +7 -1
- package/dist/web/plugins/base_plugin.js +4 -2
- package/dist/web/plugins/global_instruction_plugin.js +67 -0
- package/dist/web/runner/runner.js +65 -22
- package/dist/web/sessions/base_session_service.js +8 -3
- package/dist/web/sessions/in_memory_session_service.js +8 -8
- package/dist/web/sessions/vertex_ai_session_service.js +24 -11
- package/dist/web/skills/loader.js +40 -6
- package/dist/web/tools/enterprise_web_search_tool.js +55 -0
- package/dist/web/tools/example_tool.js +42 -0
- package/dist/web/tools/get_user_choice_tool.js +25 -0
- package/dist/web/tools/load_web_page.js +221 -0
- package/dist/web/tools/mcp/load_mcp_resource_tool.js +107 -0
- package/dist/web/tools/mcp/mcp_session_manager.js +35 -21
- package/dist/web/tools/mcp/mcp_toolset.js +63 -0
- package/dist/web/tools/openapi_tool/openapi_spec_parser/tool_auth_handler.js +13 -10
- package/dist/web/tools/request_input_tool.js +26 -0
- package/dist/web/tools/skill/run_skill_inline_script_tool.js +51 -4
- package/dist/web/tools/skill/skill_toolset.js +4 -2
- package/dist/web/utils/branch_trie.js +13 -0
- package/dist/web/utils/crypto_shim.js +15 -0
- package/dist/web/utils/env_aware_utils.js +15 -13
- package/dist/web/utils/error_utils.js +92 -0
- package/dist/web/utils/file_utils.js +5 -2
- package/dist/web/utils/output_schema_utils.js +15 -0
- package/dist/web/utils/streaming_utils.js +1 -1
- package/dist/web/utils/vertex_ai_utils.js +2 -0
- package/dist/web/version.js +1 -1
- package/package.json +1 -1
|
@@ -8,12 +8,23 @@ const require = topLevelCreateRequire(import.meta.url);
|
|
|
8
8
|
class InMemoryMemoryService {
|
|
9
9
|
constructor() {
|
|
10
10
|
this.memories = [];
|
|
11
|
-
|
|
11
|
+
/**
|
|
12
|
+
* A map from user key to a map from session ID to events.
|
|
13
|
+
*
|
|
14
|
+
* The inner map is keyed by `session.id`, which arrives off the request path
|
|
15
|
+
* and contains no `/`, so it can be exactly `__proto__`. On a plain object
|
|
16
|
+
* literal that key would reach the inherited `__proto__` setter and
|
|
17
|
+
* re-parent the map instead of creating an own property, silently dropping
|
|
18
|
+
* the session from the `Object.values` scan in `searchMemory`. The outer key
|
|
19
|
+
* always contains a `/` (see `getUserKey`) and cannot collide, but is
|
|
20
|
+
* created the same way for consistency.
|
|
21
|
+
*/
|
|
22
|
+
this.sessionEvents = /* @__PURE__ */ Object.create(null);
|
|
12
23
|
}
|
|
13
24
|
async addSessionToMemory(session) {
|
|
14
25
|
const userKey = getUserKey(session.appName, session.userId);
|
|
15
26
|
if (!this.sessionEvents[userKey]) {
|
|
16
|
-
this.sessionEvents[userKey] =
|
|
27
|
+
this.sessionEvents[userKey] = /* @__PURE__ */ Object.create(null);
|
|
17
28
|
}
|
|
18
29
|
this.sessionEvents[userKey][session.id] = session.events.filter(
|
|
19
30
|
(event) => {
|
|
@@ -24,7 +24,10 @@ var __spreadValues = (a, b) => {
|
|
|
24
24
|
import { Client } from "@google-cloud/vertexai";
|
|
25
25
|
import { createUserContent } from "@google/genai";
|
|
26
26
|
import { logger } from "../utils/logger.js";
|
|
27
|
-
import {
|
|
27
|
+
import {
|
|
28
|
+
EXPRESS_MODE_UNSUPPORTED_MESSAGE,
|
|
29
|
+
getExpressModeApiKey
|
|
30
|
+
} from "../utils/vertex_ai_utils.js";
|
|
28
31
|
const GENERATE_MEMORIES_KNOWN_FIELDS = [
|
|
29
32
|
"disableConsolidation",
|
|
30
33
|
"waitForCompletion",
|
|
@@ -105,6 +108,9 @@ class VertexAiMemoryBankService {
|
|
|
105
108
|
if (options.client) {
|
|
106
109
|
this.memories = options.client.agentEnginesInternal.memories;
|
|
107
110
|
} else {
|
|
111
|
+
if (this.expressModeApiKey && (!this.projectId || !this.location)) {
|
|
112
|
+
throw new Error(EXPRESS_MODE_UNSUPPORTED_MESSAGE);
|
|
113
|
+
}
|
|
108
114
|
const client = new Client({
|
|
109
115
|
project: this.projectId,
|
|
110
116
|
location: this.location
|
|
@@ -73,8 +73,10 @@ class BasePlugin {
|
|
|
73
73
|
* @param params.invocationContext The context for the entire invocation.
|
|
74
74
|
* @param params.event The event raised by the runner.
|
|
75
75
|
* @returns An optional value. A non-`undefined` return may be used by the
|
|
76
|
-
* framework to modify or replace the response.
|
|
77
|
-
*
|
|
76
|
+
* framework to modify or replace the response. Copy `params.event` when
|
|
77
|
+
* constructing a replacement to preserve fields that are not being
|
|
78
|
+
* modified, such as event actions. Returning `undefined` allows the
|
|
79
|
+
* original response to be used.
|
|
78
80
|
*/
|
|
79
81
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
80
82
|
async onEventCallback(params) {
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
import {createRequire as topLevelCreateRequire} from 'module';
|
|
2
|
+
const require = topLevelCreateRequire(import.meta.url);
|
|
3
|
+
/**
|
|
4
|
+
* @license
|
|
5
|
+
* Copyright 2026 Google LLC
|
|
6
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
7
|
+
*/
|
|
8
|
+
import { injectSessionState } from "../agents/instructions.js";
|
|
9
|
+
import { ReadonlyContext } from "../agents/readonly_context.js";
|
|
10
|
+
import { BasePlugin } from "./base_plugin.js";
|
|
11
|
+
class GlobalInstructionPlugin extends BasePlugin {
|
|
12
|
+
/**
|
|
13
|
+
* Initializes the GlobalInstructionPlugin.
|
|
14
|
+
*
|
|
15
|
+
* @param globalInstruction The instruction to apply globally. Can be a string
|
|
16
|
+
* or an InstructionProvider function that takes ReadonlyContext and
|
|
17
|
+
* returns a string (sync or async).
|
|
18
|
+
* @param name The name of the plugin (defaults to 'global_instruction').
|
|
19
|
+
*/
|
|
20
|
+
constructor(globalInstruction, name = "global_instruction") {
|
|
21
|
+
super(name);
|
|
22
|
+
this.globalInstruction = globalInstruction;
|
|
23
|
+
}
|
|
24
|
+
async beforeModelCallback(params) {
|
|
25
|
+
if (!this.globalInstruction) {
|
|
26
|
+
return;
|
|
27
|
+
}
|
|
28
|
+
const readonlyContext = new ReadonlyContext(
|
|
29
|
+
params.callbackContext.invocationContext
|
|
30
|
+
);
|
|
31
|
+
const finalGlobalInstruction = await this.resolveGlobalInstruction(readonlyContext);
|
|
32
|
+
if (!finalGlobalInstruction) {
|
|
33
|
+
return;
|
|
34
|
+
}
|
|
35
|
+
if (!params.llmRequest.config) {
|
|
36
|
+
params.llmRequest.config = {};
|
|
37
|
+
}
|
|
38
|
+
const existingInstruction = params.llmRequest.config.systemInstruction;
|
|
39
|
+
if (!existingInstruction || Array.isArray(existingInstruction) && existingInstruction.length === 0) {
|
|
40
|
+
params.llmRequest.config.systemInstruction = finalGlobalInstruction;
|
|
41
|
+
return;
|
|
42
|
+
}
|
|
43
|
+
if (typeof existingInstruction === "string") {
|
|
44
|
+
params.llmRequest.config.systemInstruction = "".concat(finalGlobalInstruction, "\n\n").concat(existingInstruction);
|
|
45
|
+
} else if (Array.isArray(existingInstruction)) {
|
|
46
|
+
params.llmRequest.config.systemInstruction = [
|
|
47
|
+
finalGlobalInstruction,
|
|
48
|
+
...existingInstruction
|
|
49
|
+
];
|
|
50
|
+
} else {
|
|
51
|
+
params.llmRequest.config.systemInstruction = [
|
|
52
|
+
finalGlobalInstruction,
|
|
53
|
+
existingInstruction
|
|
54
|
+
];
|
|
55
|
+
}
|
|
56
|
+
return;
|
|
57
|
+
}
|
|
58
|
+
async resolveGlobalInstruction(readonlyContext) {
|
|
59
|
+
if (typeof this.globalInstruction === "string") {
|
|
60
|
+
return await injectSessionState(this.globalInstruction, readonlyContext);
|
|
61
|
+
}
|
|
62
|
+
return await this.globalInstruction(readonlyContext);
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
export {
|
|
66
|
+
GlobalInstructionPlugin
|
|
67
|
+
};
|
|
@@ -191,7 +191,7 @@ class Runner {
|
|
|
191
191
|
this,
|
|
192
192
|
function() {
|
|
193
193
|
return __asyncGenerator(this, null, function* () {
|
|
194
|
-
var _a2, _b, _c, _d, _e, _f, _g, _h, _i, _j;
|
|
194
|
+
var _a2, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k;
|
|
195
195
|
const session = yield new __await(this.sessionService.getSession({
|
|
196
196
|
appName: this.appName,
|
|
197
197
|
userId,
|
|
@@ -252,7 +252,7 @@ class Runner {
|
|
|
252
252
|
throw new Error("No parts in the newMessage.");
|
|
253
253
|
}
|
|
254
254
|
if (runConfig.saveInputBlobsAsArtifacts) {
|
|
255
|
-
yield new __await(this.saveArtifacts(
|
|
255
|
+
newMessage = yield new __await(this.saveArtifacts(
|
|
256
256
|
invocationContext.invocationId,
|
|
257
257
|
session.userId,
|
|
258
258
|
session.id,
|
|
@@ -310,21 +310,27 @@ class Runner {
|
|
|
310
310
|
if ((_h = params.abortSignal) == null ? void 0 : _h.aborted) {
|
|
311
311
|
return;
|
|
312
312
|
}
|
|
313
|
-
if (!event.partial) {
|
|
314
|
-
yield new __await(this.sessionService.appendEvent({ session, event }));
|
|
315
|
-
}
|
|
316
313
|
const modifiedEvent = yield new __await(this.pluginManager.runOnEventCallback({
|
|
317
314
|
invocationContext,
|
|
318
315
|
event
|
|
319
316
|
}));
|
|
320
|
-
|
|
321
|
-
|
|
317
|
+
const outputEvent = modifiedEvent ? __spreadProps(__spreadValues({}, modifiedEvent), {
|
|
318
|
+
id: event.id,
|
|
319
|
+
invocationId: event.invocationId,
|
|
320
|
+
timestamp: event.timestamp,
|
|
321
|
+
author: modifiedEvent.author || event.author,
|
|
322
|
+
branch: (_i = modifiedEvent.branch) != null ? _i : event.branch
|
|
323
|
+
}) : event;
|
|
324
|
+
if (!event.partial) {
|
|
325
|
+
yield new __await(this.sessionService.appendEvent({
|
|
326
|
+
session,
|
|
327
|
+
event: outputEvent
|
|
328
|
+
}));
|
|
322
329
|
}
|
|
323
|
-
if (
|
|
324
|
-
|
|
325
|
-
} else {
|
|
326
|
-
yield event;
|
|
330
|
+
if ((_j = params.abortSignal) == null ? void 0 : _j.aborted) {
|
|
331
|
+
return;
|
|
327
332
|
}
|
|
333
|
+
yield outputEvent;
|
|
328
334
|
}
|
|
329
335
|
} catch (temp) {
|
|
330
336
|
error = [temp];
|
|
@@ -337,7 +343,7 @@ class Runner {
|
|
|
337
343
|
}
|
|
338
344
|
}
|
|
339
345
|
yield new __await(this.pluginManager.runAfterRunCallback({ invocationContext }));
|
|
340
|
-
if ((
|
|
346
|
+
if ((_k = params.abortSignal) == null ? void 0 : _k.aborted) {
|
|
341
347
|
return;
|
|
342
348
|
}
|
|
343
349
|
}
|
|
@@ -354,7 +360,7 @@ class Runner {
|
|
|
354
360
|
}
|
|
355
361
|
/**
|
|
356
362
|
* Saves artifacts from the message parts and replaces the inline data with
|
|
357
|
-
* a file name placeholder.
|
|
363
|
+
* a file name placeholder and optional file reference.
|
|
358
364
|
*
|
|
359
365
|
* @param invocationId The current invocation ID.
|
|
360
366
|
* @param userId The user ID of the session.
|
|
@@ -364,27 +370,64 @@ class Runner {
|
|
|
364
370
|
async saveArtifacts(invocationId, userId, sessionId, message) {
|
|
365
371
|
var _a2;
|
|
366
372
|
if (!this.artifactService || !((_a2 = message.parts) == null ? void 0 : _a2.length)) {
|
|
367
|
-
return;
|
|
373
|
+
return message;
|
|
368
374
|
}
|
|
369
375
|
const sessionKey = {
|
|
370
376
|
appName: this.appName,
|
|
371
377
|
userId,
|
|
372
378
|
sessionId
|
|
373
379
|
};
|
|
380
|
+
const newParts = [];
|
|
381
|
+
let modified = false;
|
|
374
382
|
for (let i = 0; i < message.parts.length; i++) {
|
|
375
383
|
const part = message.parts[i];
|
|
376
384
|
if (!part.inlineData) {
|
|
385
|
+
newParts.push(part);
|
|
377
386
|
continue;
|
|
378
387
|
}
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
388
|
+
try {
|
|
389
|
+
const inlineData = part.inlineData;
|
|
390
|
+
const fileName = inlineData.displayName || "artifact_".concat(invocationId, "_").concat(i);
|
|
391
|
+
const version = await this.artifactService.saveArtifact(__spreadProps(__spreadValues({}, sessionKey), {
|
|
392
|
+
filename: fileName,
|
|
393
|
+
artifact: part
|
|
394
|
+
}));
|
|
395
|
+
newParts.push(createPartFromText('[Uploaded Artifact: "'.concat(fileName, '"]')));
|
|
396
|
+
try {
|
|
397
|
+
const artifactVersion = await this.artifactService.getArtifactVersion(
|
|
398
|
+
__spreadProps(__spreadValues({}, sessionKey), {
|
|
399
|
+
filename: fileName,
|
|
400
|
+
version
|
|
401
|
+
})
|
|
402
|
+
);
|
|
403
|
+
if ((artifactVersion == null ? void 0 : artifactVersion.canonicalUri) && /^(gs|https?):/i.test(artifactVersion.canonicalUri)) {
|
|
404
|
+
newParts.push({
|
|
405
|
+
fileData: {
|
|
406
|
+
fileUri: artifactVersion.canonicalUri,
|
|
407
|
+
mimeType: artifactVersion.mimeType || inlineData.mimeType || "",
|
|
408
|
+
displayName: fileName
|
|
409
|
+
}
|
|
410
|
+
});
|
|
411
|
+
}
|
|
412
|
+
} catch (error) {
|
|
413
|
+
logger.warn(
|
|
414
|
+
"Failed to resolve artifact version for ".concat(fileName, ":"),
|
|
415
|
+
error
|
|
416
|
+
);
|
|
417
|
+
}
|
|
418
|
+
modified = true;
|
|
419
|
+
logger.info("Successfully saved artifact: ".concat(fileName));
|
|
420
|
+
} catch (error) {
|
|
421
|
+
logger.error("Failed to save artifact for part ".concat(i, ":"), error);
|
|
422
|
+
newParts.push(part);
|
|
423
|
+
}
|
|
387
424
|
}
|
|
425
|
+
if (!modified) {
|
|
426
|
+
return message;
|
|
427
|
+
}
|
|
428
|
+
return __spreadProps(__spreadValues({}, message), {
|
|
429
|
+
parts: newParts
|
|
430
|
+
});
|
|
388
431
|
}
|
|
389
432
|
/**
|
|
390
433
|
* Determines the next agent to run to continue the session. This is primarily
|
|
@@ -61,7 +61,12 @@ class BaseSessionService {
|
|
|
61
61
|
if (key.startsWith(State.TEMP_PREFIX)) {
|
|
62
62
|
continue;
|
|
63
63
|
}
|
|
64
|
-
session.state
|
|
64
|
+
Object.defineProperty(session.state, key, {
|
|
65
|
+
value,
|
|
66
|
+
writable: true,
|
|
67
|
+
enumerable: true,
|
|
68
|
+
configurable: true
|
|
69
|
+
});
|
|
65
70
|
}
|
|
66
71
|
}
|
|
67
72
|
}
|
|
@@ -70,7 +75,7 @@ function trimTempDeltaState(event) {
|
|
|
70
75
|
return event;
|
|
71
76
|
}
|
|
72
77
|
const stateDelta = event.actions.stateDelta;
|
|
73
|
-
const filteredStateDelta =
|
|
78
|
+
const filteredStateDelta = /* @__PURE__ */ Object.create(null);
|
|
74
79
|
for (const [key, value] of Object.entries(stateDelta)) {
|
|
75
80
|
if (!key.startsWith(State.TEMP_PREFIX)) {
|
|
76
81
|
filteredStateDelta[key] = value;
|
|
@@ -80,7 +85,7 @@ function trimTempDeltaState(event) {
|
|
|
80
85
|
return event;
|
|
81
86
|
}
|
|
82
87
|
function trimTempState(state) {
|
|
83
|
-
const filteredState =
|
|
88
|
+
const filteredState = /* @__PURE__ */ Object.create(null);
|
|
84
89
|
for (const [key, value] of Object.entries(state)) {
|
|
85
90
|
if (!key.startsWith(State.TEMP_PREFIX)) {
|
|
86
91
|
filteredState[key] = value;
|
|
@@ -25,15 +25,15 @@ class InMemorySessionService extends BaseSessionService {
|
|
|
25
25
|
* A map from app name to a map from user ID to a map from session ID to
|
|
26
26
|
* session.
|
|
27
27
|
*/
|
|
28
|
-
this.sessions =
|
|
28
|
+
this.sessions = /* @__PURE__ */ Object.create(null);
|
|
29
29
|
/**
|
|
30
30
|
* A map from app name to a map from user ID to a map from key to the value.
|
|
31
31
|
*/
|
|
32
|
-
this.userState =
|
|
32
|
+
this.userState = /* @__PURE__ */ Object.create(null);
|
|
33
33
|
/**
|
|
34
34
|
* A map from app name to a map from key to the value.
|
|
35
35
|
*/
|
|
36
|
-
this.appState =
|
|
36
|
+
this.appState = /* @__PURE__ */ Object.create(null);
|
|
37
37
|
}
|
|
38
38
|
async createSession({
|
|
39
39
|
appName,
|
|
@@ -52,10 +52,10 @@ class InMemorySessionService extends BaseSessionService {
|
|
|
52
52
|
lastUpdateTime: Date.now()
|
|
53
53
|
});
|
|
54
54
|
if (!this.sessions[appName]) {
|
|
55
|
-
this.sessions[appName] =
|
|
55
|
+
this.sessions[appName] = /* @__PURE__ */ Object.create(null);
|
|
56
56
|
}
|
|
57
57
|
if (!this.sessions[appName][userId]) {
|
|
58
|
-
this.sessions[appName][userId] =
|
|
58
|
+
this.sessions[appName][userId] = /* @__PURE__ */ Object.create(null);
|
|
59
59
|
}
|
|
60
60
|
this.sessions[appName][userId][session.id] = session;
|
|
61
61
|
const copiedSession = cloneDeep(session);
|
|
@@ -220,12 +220,12 @@ class InMemorySessionService extends BaseSessionService {
|
|
|
220
220
|
if (event.actions && event.actions.stateDelta) {
|
|
221
221
|
for (const key of Object.keys(event.actions.stateDelta)) {
|
|
222
222
|
if (key.startsWith(State.APP_PREFIX)) {
|
|
223
|
-
this.appState[appName] = this.appState[appName] ||
|
|
223
|
+
this.appState[appName] = this.appState[appName] || /* @__PURE__ */ Object.create(null);
|
|
224
224
|
this.appState[appName][key.replace(State.APP_PREFIX, "")] = event.actions.stateDelta[key];
|
|
225
225
|
}
|
|
226
226
|
if (key.startsWith(State.USER_PREFIX)) {
|
|
227
|
-
this.userState[appName] = this.userState[appName] ||
|
|
228
|
-
this.userState[appName][userId] = this.userState[appName][userId] ||
|
|
227
|
+
this.userState[appName] = this.userState[appName] || /* @__PURE__ */ Object.create(null);
|
|
228
|
+
this.userState[appName][userId] = this.userState[appName][userId] || /* @__PURE__ */ Object.create(null);
|
|
229
229
|
this.userState[appName][userId][key.replace(State.USER_PREFIX, "")] = event.actions.stateDelta[key];
|
|
230
230
|
}
|
|
231
231
|
}
|
|
@@ -37,7 +37,10 @@ import { Client } from "@google-cloud/vertexai/build/src/genai/client.js";
|
|
|
37
37
|
import { isCompactedEvent } from "../events/compacted_event.js";
|
|
38
38
|
import { experimental } from "../utils/experimental.js";
|
|
39
39
|
import { logger } from "../utils/logger.js";
|
|
40
|
-
import {
|
|
40
|
+
import {
|
|
41
|
+
EXPRESS_MODE_UNSUPPORTED_MESSAGE,
|
|
42
|
+
getExpressModeApiKey
|
|
43
|
+
} from "../utils/vertex_ai_utils.js";
|
|
41
44
|
import { partialCopy } from "../utils/partial_copy.js";
|
|
42
45
|
import {
|
|
43
46
|
BaseSessionService,
|
|
@@ -65,16 +68,14 @@ let VertexAiSessionService = class extends BaseSessionService {
|
|
|
65
68
|
this.location,
|
|
66
69
|
options.expressModeApiKey
|
|
67
70
|
);
|
|
68
|
-
if (!options.sessions) {
|
|
69
|
-
if (!this.expressModeApiKey && (!this.projectId || !this.location)) {
|
|
70
|
-
throw new Error(
|
|
71
|
-
"Either (Project ID and Location) or an expressModeApiKey is required."
|
|
72
|
-
);
|
|
73
|
-
}
|
|
74
|
-
}
|
|
75
71
|
if (options.sessions) {
|
|
76
72
|
this.sessions = options.sessions;
|
|
77
73
|
} else {
|
|
74
|
+
if (!this.projectId || !this.location) {
|
|
75
|
+
throw new Error(
|
|
76
|
+
this.expressModeApiKey ? EXPRESS_MODE_UNSUPPORTED_MESSAGE : "Project ID and Location are required."
|
|
77
|
+
);
|
|
78
|
+
}
|
|
78
79
|
const client = new Client({
|
|
79
80
|
project: this.projectId,
|
|
80
81
|
location: this.location
|
|
@@ -98,19 +99,31 @@ let VertexAiSessionService = class extends BaseSessionService {
|
|
|
98
99
|
}
|
|
99
100
|
return match[3];
|
|
100
101
|
}
|
|
102
|
+
/**
|
|
103
|
+
* Creates a session on Vertex AI Agent Engine.
|
|
104
|
+
*
|
|
105
|
+
* @throws if both `ttl` and `expireTime` are specified.
|
|
106
|
+
*/
|
|
101
107
|
async createSession({
|
|
102
108
|
appName,
|
|
103
109
|
userId,
|
|
104
110
|
state,
|
|
105
|
-
sessionId
|
|
111
|
+
sessionId,
|
|
112
|
+
ttl,
|
|
113
|
+
expireTime
|
|
106
114
|
}) {
|
|
107
115
|
var _a;
|
|
116
|
+
if (ttl != null && expireTime != null) {
|
|
117
|
+
throw new Error(
|
|
118
|
+
"Cannot specify both 'ttl' and 'expireTime' simultaneously."
|
|
119
|
+
);
|
|
120
|
+
}
|
|
108
121
|
const reasoningEngineId = this.getReasoningEngineId(appName);
|
|
109
122
|
const filteredState = state ? trimTempState(state) : void 0;
|
|
110
123
|
let apiResponse = await this.sessions.createInternal({
|
|
111
124
|
name: "reasoningEngines/".concat(reasoningEngineId),
|
|
112
125
|
userId,
|
|
113
|
-
config: __spreadValues(__spreadValues({}, filteredState ? { sessionState: filteredState } : {}), sessionId ? { sessionId } : {})
|
|
126
|
+
config: __spreadValues(__spreadValues(__spreadValues(__spreadValues({}, filteredState ? { sessionState: filteredState } : {}), sessionId ? { sessionId } : {}), ttl != null ? { ttl } : {}), expireTime != null ? { expireTime } : {})
|
|
114
127
|
});
|
|
115
128
|
const operationName = apiResponse.name;
|
|
116
129
|
let attempts = 0;
|
|
@@ -195,7 +208,7 @@ let VertexAiSessionService = class extends BaseSessionService {
|
|
|
195
208
|
return session;
|
|
196
209
|
} catch (error) {
|
|
197
210
|
const err = error;
|
|
198
|
-
if (err.code === GRPC_NOT_FOUND || err.code === HTTP_NOT_FOUND) {
|
|
211
|
+
if (err.code === GRPC_NOT_FOUND || err.code === HTTP_NOT_FOUND || err.status === HTTP_NOT_FOUND) {
|
|
199
212
|
return void 0;
|
|
200
213
|
}
|
|
201
214
|
logger.error("Error getting session from Vertex AI: ".concat(err.message));
|
|
@@ -37,6 +37,9 @@ const ALLOWED_FRONTMATTER_KEYS = /* @__PURE__ */ new Set([
|
|
|
37
37
|
"description",
|
|
38
38
|
"license",
|
|
39
39
|
"allowed-tools",
|
|
40
|
+
// Camel-case alias: FrontmatterSchema's preprocessor derives `allowedTools`
|
|
41
|
+
// from `allowed-tools`, and `.loose()` passes either spelling through.
|
|
42
|
+
"allowedTools",
|
|
40
43
|
"metadata",
|
|
41
44
|
"compatibility"
|
|
42
45
|
]);
|
|
@@ -99,7 +102,7 @@ async function loadDir(directoryPath) {
|
|
|
99
102
|
}
|
|
100
103
|
return files;
|
|
101
104
|
}
|
|
102
|
-
function
|
|
105
|
+
function parseFrontmatterYaml(content) {
|
|
103
106
|
if (!content.startsWith("---")) {
|
|
104
107
|
throw new Error("SKILL.md must start with YAML frontmatter (---)");
|
|
105
108
|
}
|
|
@@ -111,15 +114,34 @@ function parseSkillMdContent(content) {
|
|
|
111
114
|
const body = parts.filter((_, i) => i >= 2).join("---").trim();
|
|
112
115
|
try {
|
|
113
116
|
const parsed = yaml.load(frontmatterStr);
|
|
114
|
-
if (typeof parsed !== "object" || parsed === null) {
|
|
117
|
+
if (typeof parsed !== "object" || parsed === null || Array.isArray(parsed)) {
|
|
115
118
|
throw new Error("SKILL.md frontmatter must be a YAML mapping");
|
|
116
119
|
}
|
|
117
|
-
|
|
118
|
-
return { frontmatter, body };
|
|
120
|
+
return { raw: parsed, body };
|
|
119
121
|
} catch (e) {
|
|
120
122
|
throw new Error("Invalid YAML in frontmatter: ".concat(e.message));
|
|
121
123
|
}
|
|
122
124
|
}
|
|
125
|
+
function validateFrontmatter(raw) {
|
|
126
|
+
try {
|
|
127
|
+
return FrontmatterSchema.parse(raw);
|
|
128
|
+
} catch (e) {
|
|
129
|
+
throw new Error("Invalid YAML in frontmatter: ".concat(e.message));
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
function parseSkillMdContent(content) {
|
|
133
|
+
const { raw, body } = parseFrontmatterYaml(content);
|
|
134
|
+
return { frontmatter: validateFrontmatter(raw), body };
|
|
135
|
+
}
|
|
136
|
+
function isDangerousZipEntryName(entryName) {
|
|
137
|
+
if (path.posix.isAbsolute(entryName) || path.win32.isAbsolute(entryName)) {
|
|
138
|
+
return true;
|
|
139
|
+
}
|
|
140
|
+
return entryName.split(/[/\\]/).some((segment) => segment === "..");
|
|
141
|
+
}
|
|
142
|
+
function isBareSkillName(name) {
|
|
143
|
+
return name !== "." && name !== ".." && path.basename(name) === name;
|
|
144
|
+
}
|
|
123
145
|
async function loadSkillFromDir(skillDir) {
|
|
124
146
|
const resolvedDir = path.resolve(skillDir);
|
|
125
147
|
const skill = await loadSkillFile(skillDir);
|
|
@@ -258,6 +280,11 @@ async function loadAllSkillsInDir(skillsBasePath) {
|
|
|
258
280
|
function loadSkillFromZipBuffer(zipBuffer) {
|
|
259
281
|
const zip = new AdmZip(zipBuffer);
|
|
260
282
|
const entries = zip.getEntries();
|
|
283
|
+
for (const entry of entries) {
|
|
284
|
+
if (isDangerousZipEntryName(entry.entryName)) {
|
|
285
|
+
throw new Error("Dangerous zip entry ignored: ".concat(entry.entryName));
|
|
286
|
+
}
|
|
287
|
+
}
|
|
261
288
|
let skillMdContent = "";
|
|
262
289
|
for (const entry of entries) {
|
|
263
290
|
if (entry.isDirectory) continue;
|
|
@@ -269,8 +296,15 @@ function loadSkillFromZipBuffer(zipBuffer) {
|
|
|
269
296
|
if (!skillMdContent) {
|
|
270
297
|
throw new Error("SKILL.md not found in zipped filesystem.");
|
|
271
298
|
}
|
|
272
|
-
const {
|
|
273
|
-
const
|
|
299
|
+
const { raw, body } = parseFrontmatterYaml(skillMdContent);
|
|
300
|
+
const skillName = raw["name"];
|
|
301
|
+
if (!skillName) {
|
|
302
|
+
throw new Error("SKILL.md frontmatter must contain 'name'");
|
|
303
|
+
}
|
|
304
|
+
if (typeof skillName !== "string" || !isBareSkillName(skillName)) {
|
|
305
|
+
throw new Error("Invalid skill name in SKILL.md: ".concat(String(skillName)));
|
|
306
|
+
}
|
|
307
|
+
const frontmatter = validateFrontmatter(raw);
|
|
274
308
|
const references = {};
|
|
275
309
|
const assets = {};
|
|
276
310
|
const scripts = {};
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
import {createRequire as topLevelCreateRequire} from 'module';
|
|
2
|
+
const require = topLevelCreateRequire(import.meta.url);
|
|
3
|
+
/**
|
|
4
|
+
* @license
|
|
5
|
+
* Copyright 2026 Google LLC
|
|
6
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
7
|
+
*/
|
|
8
|
+
import {
|
|
9
|
+
isGemini1Model,
|
|
10
|
+
isGeminiModel,
|
|
11
|
+
isGeminiModelIdCheckDisabled
|
|
12
|
+
} from "../utils/model_name.js";
|
|
13
|
+
import { BaseTool } from "./base_tool.js";
|
|
14
|
+
function applyEnterpriseWebSearch(llmRequest) {
|
|
15
|
+
if (!llmRequest.model) {
|
|
16
|
+
return;
|
|
17
|
+
}
|
|
18
|
+
const modelCheckDisabled = isGeminiModelIdCheckDisabled();
|
|
19
|
+
llmRequest.config = llmRequest.config || {};
|
|
20
|
+
llmRequest.config.tools = llmRequest.config.tools || [];
|
|
21
|
+
if (isGeminiModel(llmRequest.model) || modelCheckDisabled) {
|
|
22
|
+
if (isGemini1Model(llmRequest.model) && llmRequest.config.tools.length > 0) {
|
|
23
|
+
throw new Error(
|
|
24
|
+
"Enterprise Web Search tool cannot be used with other tools in Gemini 1.x."
|
|
25
|
+
);
|
|
26
|
+
}
|
|
27
|
+
llmRequest.config.tools.push({ enterpriseWebSearch: {} });
|
|
28
|
+
return;
|
|
29
|
+
}
|
|
30
|
+
throw new Error(
|
|
31
|
+
"Enterprise Web Search tool is not supported for model ".concat(llmRequest.model)
|
|
32
|
+
);
|
|
33
|
+
}
|
|
34
|
+
class EnterpriseWebSearchTool extends BaseTool {
|
|
35
|
+
constructor() {
|
|
36
|
+
super({
|
|
37
|
+
name: "enterprise_web_search",
|
|
38
|
+
description: "Enterprise Web Search Tool"
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
runAsync() {
|
|
42
|
+
return Promise.resolve();
|
|
43
|
+
}
|
|
44
|
+
async processLlmRequest({
|
|
45
|
+
llmRequest
|
|
46
|
+
}) {
|
|
47
|
+
applyEnterpriseWebSearch(llmRequest);
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
const ENTERPRISE_WEB_SEARCH = new EnterpriseWebSearchTool();
|
|
51
|
+
export {
|
|
52
|
+
ENTERPRISE_WEB_SEARCH,
|
|
53
|
+
EnterpriseWebSearchTool,
|
|
54
|
+
applyEnterpriseWebSearch
|
|
55
|
+
};
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import {createRequire as topLevelCreateRequire} from 'module';
|
|
2
|
+
const require = topLevelCreateRequire(import.meta.url);
|
|
3
|
+
/**
|
|
4
|
+
* @license
|
|
5
|
+
* Copyright 2026 Google LLC
|
|
6
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
7
|
+
*/
|
|
8
|
+
import { buildExampleSi } from "../examples/example_util.js";
|
|
9
|
+
import { appendInstructions } from "../models/llm_request.js";
|
|
10
|
+
import {
|
|
11
|
+
BaseTool
|
|
12
|
+
} from "./base_tool.js";
|
|
13
|
+
class ExampleTool extends BaseTool {
|
|
14
|
+
constructor(examples) {
|
|
15
|
+
super({
|
|
16
|
+
// Name and description are not used because this tool only changes
|
|
17
|
+
// llmRequest.
|
|
18
|
+
name: "example_tool",
|
|
19
|
+
description: "example tool"
|
|
20
|
+
});
|
|
21
|
+
this.examples = examples;
|
|
22
|
+
}
|
|
23
|
+
async runAsync(_request) {
|
|
24
|
+
throw new Error("ExampleTool should not be called by model");
|
|
25
|
+
}
|
|
26
|
+
async processLlmRequest({
|
|
27
|
+
toolContext,
|
|
28
|
+
llmRequest
|
|
29
|
+
}) {
|
|
30
|
+
var _a, _b;
|
|
31
|
+
const parts = (_a = toolContext.userContent) == null ? void 0 : _a.parts;
|
|
32
|
+
if (!parts || !((_b = parts[0]) == null ? void 0 : _b.text)) {
|
|
33
|
+
return;
|
|
34
|
+
}
|
|
35
|
+
appendInstructions(llmRequest, [
|
|
36
|
+
buildExampleSi(this.examples, parts[0].text, llmRequest.model)
|
|
37
|
+
]);
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
export {
|
|
41
|
+
ExampleTool
|
|
42
|
+
};
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import {createRequire as topLevelCreateRequire} from 'module';
|
|
2
|
+
const require = topLevelCreateRequire(import.meta.url);
|
|
3
|
+
/**
|
|
4
|
+
* @license
|
|
5
|
+
* Copyright 2026 Google LLC
|
|
6
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
7
|
+
*/
|
|
8
|
+
import { z } from "zod";
|
|
9
|
+
import { LongRunningFunctionTool } from "./long_running_tool.js";
|
|
10
|
+
const getUserChoiceTool = new LongRunningFunctionTool({
|
|
11
|
+
name: "get_user_choice",
|
|
12
|
+
description: "Presents a list of options to the user and awaits their selection.",
|
|
13
|
+
parameters: z.object({
|
|
14
|
+
options: z.array(z.string()).describe("List of options to present to the user.")
|
|
15
|
+
}),
|
|
16
|
+
execute: async (input, context) => {
|
|
17
|
+
if (context) {
|
|
18
|
+
context.actions.skipSummarization = true;
|
|
19
|
+
}
|
|
20
|
+
return null;
|
|
21
|
+
}
|
|
22
|
+
});
|
|
23
|
+
export {
|
|
24
|
+
getUserChoiceTool
|
|
25
|
+
};
|