@google/adk 2.1.0 → 2.2.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/agent_card.js +8 -0
- package/dist/cjs/a2a/agent_executor.js +8 -3
- package/dist/cjs/agents/llm_agent.js +15 -1
- package/dist/cjs/agents/processors/content_processor_utils.js +10 -2
- package/dist/cjs/agents/processors/nl_planning_processor.js +114 -0
- package/dist/cjs/artifacts/gcs_artifact_service.js +13 -7
- package/dist/cjs/auth/auth_credential.js +12 -2
- package/dist/cjs/code_executors/code_execution_utils.js +3 -3
- package/dist/cjs/common.js +45 -0
- package/dist/cjs/examples/example.js +92 -0
- package/dist/cjs/examples/example_util.js +28 -4
- package/dist/cjs/examples/index.js +39 -0
- package/dist/cjs/examples/vertex_ai_example_store.js +39 -0
- package/dist/cjs/index.js +46 -0
- package/dist/cjs/memory/vertex_ai_memory_bank_service.js +17 -5
- package/dist/cjs/models/base_llm.js +1 -6
- package/dist/cjs/models/chrome_prompt_llm.js +16 -2
- package/dist/cjs/models/chrome_prompt_utils.js +54 -2
- package/dist/cjs/models/gemini_llm_connection.js +5 -4
- package/dist/cjs/planners/base_planner.js +56 -0
- package/dist/cjs/planners/built_in_planner.js +85 -0
- package/dist/cjs/planners/plan_re_act_planner.js +172 -0
- package/dist/cjs/plugins/base_plugin.js +46 -61
- package/dist/cjs/tools/example_tool.js +1 -1
- package/dist/cjs/tools/mcp/mcp_session_manager.js +14 -8
- package/dist/cjs/tools/openapi_tool/auth/auth_helpers.js +281 -2
- package/dist/cjs/tools/openapi_tool/auth/credential_exchangers/auto_auth_credential_exchanger.js +15 -1
- package/dist/cjs/tools/openapi_tool/auth/credential_exchangers/base_auth_credential_exchanger.js +70 -0
- package/dist/cjs/tools/openapi_tool/auth/credential_exchangers/oauth2_exchanger.js +120 -0
- package/dist/cjs/tools/openapi_tool/auth/credential_exchangers/service_account_exchanger.js +10 -10
- package/dist/cjs/tools/openapi_tool/common/common.js +139 -0
- package/dist/cjs/tools/openapi_tool/openapi_spec_parser/openapi_spec_parser.js +11 -6
- package/dist/cjs/tools/openapi_tool/openapi_spec_parser/operation_parser.js +73 -13
- package/dist/cjs/tools/openapi_tool/openapi_spec_parser/tool_auth_handler.js +146 -34
- package/dist/cjs/tools/openapi_tool/openapi_toolset.js +14 -2
- package/dist/cjs/tools/openapi_tool/rest_api_tool.js +90 -28
- package/dist/cjs/tools/skill/skill_toolset.js +2 -0
- package/dist/cjs/tools/tool_context.js +41 -0
- package/dist/cjs/tools/webmcp/index.js +37 -0
- package/dist/cjs/tools/webmcp/webmcp_tool.js +156 -0
- package/dist/cjs/tools/webmcp/webmcp_toolset.js +116 -0
- package/dist/cjs/tools/webmcp/webmcp_types.js +50 -0
- package/dist/cjs/utils/case_utils.js +52 -2
- package/dist/cjs/utils/client_labels.js +67 -0
- package/dist/cjs/utils/gemini_schema_util.js +103 -3
- package/dist/cjs/utils/hash_utils.js +73 -0
- package/dist/cjs/utils/live_connection_utils.js +10 -9
- package/dist/cjs/utils/model_name.js +17 -2
- package/dist/cjs/utils/simple_zod_to_json.js +5 -0
- package/dist/cjs/version.js +1 -1
- package/dist/esm/a2a/agent_card.js +8 -0
- package/dist/esm/a2a/agent_executor.js +8 -3
- package/dist/esm/agents/llm_agent.js +18 -1
- package/dist/esm/agents/processors/content_processor_utils.js +10 -2
- package/dist/esm/agents/processors/nl_planning_processor.js +87 -0
- package/dist/esm/artifacts/gcs_artifact_service.js +13 -7
- package/dist/esm/auth/auth_credential.js +11 -1
- package/dist/esm/code_executors/code_execution_utils.js +3 -3
- package/dist/esm/common.js +38 -2
- package/dist/esm/examples/example.js +85 -0
- package/dist/esm/examples/example_util.js +25 -3
- package/dist/esm/examples/index.js +11 -0
- package/dist/esm/examples/vertex_ai_example_store.js +11 -0
- package/dist/esm/index.js +51 -1
- package/dist/esm/memory/vertex_ai_memory_bank_service.js +17 -5
- package/dist/esm/models/base_llm.js +2 -7
- package/dist/esm/models/chrome_prompt_llm.js +20 -3
- package/dist/esm/models/chrome_prompt_utils.js +51 -2
- package/dist/esm/models/gemini_llm_connection.js +6 -5
- package/dist/esm/planners/base_planner.js +28 -0
- package/dist/esm/planners/built_in_planner.js +57 -0
- package/dist/esm/planners/plan_re_act_planner.js +145 -0
- package/dist/esm/plugins/base_plugin.js +46 -61
- package/dist/esm/tools/example_tool.js +1 -1
- package/dist/esm/tools/mcp/mcp_session_manager.js +14 -8
- package/dist/esm/tools/openapi_tool/auth/auth_helpers.js +272 -1
- package/dist/esm/tools/openapi_tool/auth/credential_exchangers/auto_auth_credential_exchanger.js +15 -1
- package/dist/esm/tools/openapi_tool/auth/credential_exchangers/base_auth_credential_exchanger.js +43 -0
- package/dist/esm/tools/openapi_tool/auth/credential_exchangers/oauth2_exchanger.js +93 -0
- package/dist/esm/tools/openapi_tool/auth/credential_exchangers/service_account_exchanger.js +10 -12
- package/dist/esm/tools/openapi_tool/common/common.js +112 -0
- package/dist/esm/tools/openapi_tool/openapi_spec_parser/openapi_spec_parser.js +11 -6
- package/dist/esm/tools/openapi_tool/openapi_spec_parser/operation_parser.js +80 -13
- package/dist/esm/tools/openapi_tool/openapi_spec_parser/tool_auth_handler.js +146 -33
- package/dist/esm/tools/openapi_tool/openapi_toolset.js +14 -2
- package/dist/esm/tools/openapi_tool/rest_api_tool.js +89 -28
- package/dist/esm/tools/skill/skill_toolset.js +2 -0
- package/dist/esm/tools/tool_context.js +15 -0
- package/dist/esm/tools/webmcp/index.js +10 -0
- package/dist/esm/tools/webmcp/webmcp_tool.js +131 -0
- package/dist/esm/tools/webmcp/webmcp_toolset.js +89 -0
- package/dist/esm/tools/webmcp/webmcp_types.js +22 -0
- package/dist/esm/utils/case_utils.js +49 -1
- package/dist/esm/utils/client_labels.js +65 -0
- package/dist/esm/utils/gemini_schema_util.js +102 -3
- package/dist/esm/utils/hash_utils.js +45 -0
- package/dist/esm/utils/live_connection_utils.js +11 -10
- package/dist/esm/utils/model_name.js +15 -2
- package/dist/esm/utils/simple_zod_to_json.js +5 -0
- package/dist/esm/version.js +1 -1
- package/dist/types/agents/llm_agent.d.ts +12 -1
- package/dist/types/agents/processors/nl_planning_processor.d.ts +30 -0
- package/dist/types/auth/auth_credential.d.ts +9 -0
- package/dist/types/common.d.ts +16 -4
- package/dist/types/examples/base_example_provider.d.ts +2 -2
- package/dist/types/examples/example.d.ts +75 -0
- package/dist/types/examples/example_util.d.ts +13 -2
- package/dist/types/examples/index.d.ts +18 -0
- package/dist/types/examples/vertex_ai_example_store.d.ts +7 -0
- package/dist/types/index.d.ts +12 -3
- package/dist/types/memory/memory_entry.d.ts +15 -0
- package/dist/types/memory/vertex_ai_memory_bank_service.d.ts +9 -0
- package/dist/types/models/chrome_prompt_utils.d.ts +29 -0
- package/dist/types/planners/base_planner.d.ts +50 -0
- package/dist/types/planners/built_in_planner.d.ts +53 -0
- package/dist/types/planners/plan_re_act_planner.d.ts +21 -0
- package/dist/types/plugins/base_plugin.d.ts +52 -52
- package/dist/types/skills/skill_registry.d.ts +8 -0
- package/dist/types/tools/openapi_tool/auth/auth_helpers.d.ts +110 -1
- package/dist/types/tools/openapi_tool/auth/credential_exchangers/auto_auth_credential_exchanger.d.ts +32 -2
- package/dist/types/tools/openapi_tool/auth/credential_exchangers/base_auth_credential_exchanger.d.ts +35 -0
- package/dist/types/tools/openapi_tool/auth/credential_exchangers/oauth2_exchanger.d.ts +54 -0
- package/dist/types/tools/openapi_tool/common/common.d.ts +60 -0
- package/dist/types/tools/openapi_tool/openapi_spec_parser/openapi_spec_parser.d.ts +7 -0
- package/dist/types/tools/openapi_tool/openapi_spec_parser/operation_parser.d.ts +56 -2
- package/dist/types/tools/openapi_tool/openapi_spec_parser/tool_auth_handler.d.ts +73 -5
- package/dist/types/tools/openapi_tool/openapi_toolset.d.ts +11 -0
- package/dist/types/tools/openapi_tool/rest_api_tool.d.ts +42 -8
- package/dist/types/tools/tool_context.d.ts +19 -0
- package/dist/types/tools/webmcp/index.d.ts +12 -0
- package/dist/types/tools/webmcp/webmcp_tool.d.ts +47 -0
- package/dist/types/tools/webmcp/webmcp_toolset.d.ts +67 -0
- package/dist/types/tools/webmcp/webmcp_types.d.ts +69 -0
- package/dist/types/utils/case_utils.d.ts +36 -0
- package/dist/types/utils/client_labels.d.ts +33 -0
- package/dist/types/utils/gemini_schema_util.d.ts +13 -0
- package/dist/types/utils/hash_utils.d.ts +25 -0
- package/dist/types/utils/logger.d.ts +10 -2
- package/dist/types/utils/model_name.d.ts +30 -2
- package/dist/types/version.d.ts +1 -1
- package/dist/web/index_web.js +112 -79
- package/dist/web/index_web.js.map +4 -4
- package/package.json +8 -2
|
@@ -17,15 +17,37 @@ var __decorateClass = (decorators, target, key, kind) => {
|
|
|
17
17
|
* SPDX-License-Identifier: Apache-2.0
|
|
18
18
|
*/
|
|
19
19
|
import { experimental } from "../../utils/experimental.js";
|
|
20
|
+
import { openApiSchemaToGeminiSchema } from "../../utils/gemini_schema_util.js";
|
|
20
21
|
import { BaseTool } from "../base_tool.js";
|
|
21
22
|
import { applyCredential } from "./auth/auth_helpers.js";
|
|
22
23
|
import {
|
|
23
24
|
OperationParser
|
|
24
25
|
} from "./openapi_spec_parser/operation_parser.js";
|
|
25
26
|
import { ToolAuthHandler } from "./openapi_spec_parser/tool_auth_handler.js";
|
|
27
|
+
const MAX_TOOL_NAME_LENGTH = 60;
|
|
28
|
+
const SECURITY_SCHEME_TYPES = [
|
|
29
|
+
"apiKey",
|
|
30
|
+
"http",
|
|
31
|
+
"oauth2",
|
|
32
|
+
"openIdConnect"
|
|
33
|
+
];
|
|
34
|
+
function readSchemeType(value) {
|
|
35
|
+
return typeof value === "object" && value !== null && "type" in value ? value.type : void 0;
|
|
36
|
+
}
|
|
37
|
+
__name(readSchemeType, "readSchemeType");
|
|
38
|
+
function isSecurityScheme(value) {
|
|
39
|
+
const type = readSchemeType(value);
|
|
40
|
+
return typeof type === "string" && SECURITY_SCHEME_TYPES.includes(type);
|
|
41
|
+
}
|
|
42
|
+
__name(isSecurityScheme, "isSecurityScheme");
|
|
43
|
+
function serializeCookieHeader(cookies) {
|
|
44
|
+
return Object.entries(cookies).map(([name, value]) => `${name}=${encodeURIComponent(value)}`).join("; ");
|
|
45
|
+
}
|
|
46
|
+
__name(serializeCookieHeader, "serializeCookieHeader");
|
|
26
47
|
let RestApiTool = class extends BaseTool {
|
|
27
48
|
constructor(name, description, endpoint, operation, authScheme, authCredential, options = {}) {
|
|
28
|
-
|
|
49
|
+
var _a;
|
|
50
|
+
super({ name: name.slice(0, MAX_TOOL_NAME_LENGTH), description });
|
|
29
51
|
this.endpoint = endpoint;
|
|
30
52
|
this.operation = operation;
|
|
31
53
|
this.authScheme = authScheme;
|
|
@@ -34,7 +56,7 @@ let RestApiTool = class extends BaseTool {
|
|
|
34
56
|
this.authCredential = authCredential;
|
|
35
57
|
this.headerProvider = options.headerProvider;
|
|
36
58
|
this.credentialKey = options.credentialKey;
|
|
37
|
-
this.operationParser = new OperationParser(operation, options);
|
|
59
|
+
this.operationParser = (_a = options.operationParser) != null ? _a : new OperationParser(operation, options);
|
|
38
60
|
}
|
|
39
61
|
configureAuthScheme(authScheme) {
|
|
40
62
|
this.authScheme = authScheme;
|
|
@@ -46,14 +68,16 @@ let RestApiTool = class extends BaseTool {
|
|
|
46
68
|
this.credentialKey = credentialKey;
|
|
47
69
|
}
|
|
48
70
|
_getDeclaration() {
|
|
49
|
-
const schema = this.operationParser.getJsonSchema();
|
|
50
71
|
return {
|
|
51
72
|
name: this.name,
|
|
52
73
|
description: this.description,
|
|
53
|
-
parameters:
|
|
74
|
+
parameters: openApiSchemaToGeminiSchema(
|
|
75
|
+
this.operationParser.getJsonSchema()
|
|
76
|
+
)
|
|
54
77
|
};
|
|
55
78
|
}
|
|
56
79
|
async runAsync(request) {
|
|
80
|
+
var _a;
|
|
57
81
|
const context = request.toolContext;
|
|
58
82
|
const args = request.args;
|
|
59
83
|
const authHandler = ToolAuthHandler.fromToolContext(
|
|
@@ -75,7 +99,8 @@ let RestApiTool = class extends BaseTool {
|
|
|
75
99
|
url: initialUrl,
|
|
76
100
|
headers,
|
|
77
101
|
body: parsedBody,
|
|
78
|
-
bodyData
|
|
102
|
+
bodyData,
|
|
103
|
+
cookies
|
|
79
104
|
} = prepareRequestParams(
|
|
80
105
|
this.endpoint,
|
|
81
106
|
this.operationParser.getParameters(),
|
|
@@ -91,30 +116,36 @@ let RestApiTool = class extends BaseTool {
|
|
|
91
116
|
initialUrl,
|
|
92
117
|
headers,
|
|
93
118
|
credential,
|
|
94
|
-
this.authScheme
|
|
119
|
+
(_a = authResult.authScheme) != null ? _a : this.authScheme
|
|
95
120
|
);
|
|
96
121
|
if (this.headerProvider) {
|
|
97
122
|
const providerHeaders = this.headerProvider(context);
|
|
98
123
|
Object.assign(headers, providerHeaders);
|
|
99
124
|
}
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
125
|
+
const hasCookieHeader = Object.keys(headers).some(
|
|
126
|
+
(header) => header.toLowerCase() === "cookie"
|
|
127
|
+
);
|
|
128
|
+
if (Object.keys(cookies).length > 0 && !hasCookieHeader) {
|
|
129
|
+
headers["Cookie"] = serializeCookieHeader(cookies);
|
|
130
|
+
}
|
|
131
|
+
const response = await globalThis.fetch(url, {
|
|
132
|
+
method,
|
|
133
|
+
headers,
|
|
134
|
+
// eslint-disable-next-line no-undef
|
|
135
|
+
body
|
|
136
|
+
});
|
|
137
|
+
if (response.status >= 400) {
|
|
138
|
+
const errorDetails = await response.text();
|
|
114
139
|
return {
|
|
115
|
-
error: `
|
|
140
|
+
error: `Tool ${this.name} execution failed. Analyze this execution error and your inputs. Retry with adjustments if applicable. But make sure don't retry more than 3 times. Execution Error: ${errorDetails}`
|
|
116
141
|
};
|
|
117
142
|
}
|
|
143
|
+
const text = await response.text();
|
|
144
|
+
try {
|
|
145
|
+
return JSON.parse(text);
|
|
146
|
+
} catch {
|
|
147
|
+
return { text };
|
|
148
|
+
}
|
|
118
149
|
}
|
|
119
150
|
};
|
|
120
151
|
__name(RestApiTool, "RestApiTool");
|
|
@@ -148,6 +179,7 @@ __name(encodePathParamValue, "encodePathParamValue");
|
|
|
148
179
|
function prepareRequestParams(endpoint, parameters, args) {
|
|
149
180
|
const headers = {};
|
|
150
181
|
const queryParams = new URLSearchParams();
|
|
182
|
+
const cookies = {};
|
|
151
183
|
let body = void 0;
|
|
152
184
|
const paramsMap = new Map(parameters.map((p) => [p.name, p]));
|
|
153
185
|
const pathParams = {};
|
|
@@ -163,9 +195,13 @@ function prepareRequestParams(endpoint, parameters, args) {
|
|
|
163
195
|
String(argValue)
|
|
164
196
|
);
|
|
165
197
|
} else if (location === "query") {
|
|
166
|
-
|
|
198
|
+
if (argValue !== void 0 && argValue !== null && argValue !== "") {
|
|
199
|
+
queryParams.append(originalName, String(argValue));
|
|
200
|
+
}
|
|
167
201
|
} else if (location === "header") {
|
|
168
202
|
headers[originalName] = String(argValue);
|
|
203
|
+
} else if (location === "cookie") {
|
|
204
|
+
cookies[originalName] = String(argValue);
|
|
169
205
|
} else if (location === "body") {
|
|
170
206
|
if (originalName === "body" || originalName === "array" || originalName === "") {
|
|
171
207
|
body = argValue;
|
|
@@ -178,7 +214,8 @@ function prepareRequestParams(endpoint, parameters, args) {
|
|
|
178
214
|
/\{([^{}]+)\}/g,
|
|
179
215
|
(placeholder, name) => Object.hasOwn(pathParams, name) ? pathParams[name] : placeholder
|
|
180
216
|
);
|
|
181
|
-
|
|
217
|
+
const baseUrl = endpoint.baseUrl.endsWith("/") ? endpoint.baseUrl.slice(0, -1) : endpoint.baseUrl;
|
|
218
|
+
let url = `${baseUrl}${resolvedPath}`;
|
|
182
219
|
const urlParts = url.split("?");
|
|
183
220
|
if (urlParts.length > 1) {
|
|
184
221
|
const pathQueryParams = new URLSearchParams(urlParts[1]);
|
|
@@ -191,9 +228,13 @@ function prepareRequestParams(endpoint, parameters, args) {
|
|
|
191
228
|
if (queryString) {
|
|
192
229
|
url += `?${queryString}`;
|
|
193
230
|
}
|
|
194
|
-
return { url, headers, body, bodyData };
|
|
231
|
+
return { url, headers, body, bodyData, cookies };
|
|
195
232
|
}
|
|
196
233
|
__name(prepareRequestParams, "prepareRequestParams");
|
|
234
|
+
function isRawBody(value) {
|
|
235
|
+
return typeof value === "string" || ArrayBuffer.isView(value) || value instanceof ArrayBuffer || value instanceof Blob;
|
|
236
|
+
}
|
|
237
|
+
__name(isRawBody, "isRawBody");
|
|
197
238
|
function prepareRequestBody(requestBody, body, bodyData, headers) {
|
|
198
239
|
const finalData = body !== void 0 ? body : Object.keys(bodyData).length > 0 ? bodyData : void 0;
|
|
199
240
|
if (requestBody && "content" in requestBody) {
|
|
@@ -213,6 +254,9 @@ function prepareRequestBody(requestBody, body, bodyData, headers) {
|
|
|
213
254
|
}
|
|
214
255
|
}
|
|
215
256
|
return formData;
|
|
257
|
+
} else if (mimeType === "application/octet-stream") {
|
|
258
|
+
headers["Content-Type"] = mimeType;
|
|
259
|
+
return isRawBody(finalData) ? finalData : String(finalData);
|
|
216
260
|
} else if (mimeType === "text/plain") {
|
|
217
261
|
headers["Content-Type"] = mimeType;
|
|
218
262
|
return String(finalData);
|
|
@@ -226,20 +270,37 @@ function prepareRequestBody(requestBody, body, bodyData, headers) {
|
|
|
226
270
|
}
|
|
227
271
|
__name(prepareRequestBody, "prepareRequestBody");
|
|
228
272
|
function createRestApiTool(parsed, options = {}) {
|
|
273
|
+
var _a, _b;
|
|
274
|
+
const operationParser = parsed.parameters ? OperationParser.load(
|
|
275
|
+
parsed.operation,
|
|
276
|
+
parsed.parameters,
|
|
277
|
+
parsed.returnValue
|
|
278
|
+
) : new OperationParser(parsed.operation, options);
|
|
229
279
|
return new RestApiTool(
|
|
230
|
-
parsed.name,
|
|
231
|
-
parsed.description,
|
|
280
|
+
(_a = parsed.name) != null ? _a : operationParser.getFunctionName(),
|
|
281
|
+
(_b = parsed.description) != null ? _b : operationParser.getDescription(),
|
|
232
282
|
parsed.endpoint,
|
|
233
283
|
parsed.operation,
|
|
234
284
|
parsed.authScheme,
|
|
235
|
-
|
|
236
|
-
options
|
|
285
|
+
parsed.authCredential,
|
|
286
|
+
{ ...options, operationParser }
|
|
237
287
|
);
|
|
238
288
|
}
|
|
239
289
|
__name(createRestApiTool, "createRestApiTool");
|
|
290
|
+
function createRestApiToolFromJson(parsedOperationJson) {
|
|
291
|
+
const parsed = JSON.parse(parsedOperationJson);
|
|
292
|
+
if (parsed.authScheme && !isSecurityScheme(parsed.authScheme)) {
|
|
293
|
+
throw new Error(
|
|
294
|
+
`Unsupported security scheme type: ${JSON.stringify(readSchemeType(parsed.authScheme))}. Expected one of: ${SECURITY_SCHEME_TYPES.join(", ")}.`
|
|
295
|
+
);
|
|
296
|
+
}
|
|
297
|
+
return createRestApiTool(parsed);
|
|
298
|
+
}
|
|
299
|
+
__name(createRestApiToolFromJson, "createRestApiToolFromJson");
|
|
240
300
|
export {
|
|
241
301
|
RestApiTool,
|
|
242
302
|
createRestApiTool,
|
|
303
|
+
createRestApiToolFromJson,
|
|
243
304
|
prepareRequestBody,
|
|
244
305
|
prepareRequestParams
|
|
245
306
|
};
|
|
@@ -74,7 +74,9 @@ let SkillToolset = class extends BaseToolset {
|
|
|
74
74
|
return [...this.tools, ...dynamicTools];
|
|
75
75
|
}
|
|
76
76
|
async close() {
|
|
77
|
+
var _a, _b;
|
|
77
78
|
this.fetchedSkillCache.clear();
|
|
79
|
+
await ((_b = (_a = this.registry) == null ? void 0 : _a.close) == null ? void 0 : _b.call(_a));
|
|
78
80
|
}
|
|
79
81
|
getSkill(name) {
|
|
80
82
|
return this.skills[name];
|
|
@@ -0,0 +1,15 @@
|
|
|
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
|
+
Context,
|
|
10
|
+
Context as Context2
|
|
11
|
+
} from "../agents/context.js";
|
|
12
|
+
export {
|
|
13
|
+
Context as CallbackContext,
|
|
14
|
+
Context2 as ToolContext
|
|
15
|
+
};
|
|
@@ -0,0 +1,10 @@
|
|
|
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
|
+
export * from "./webmcp_tool.js";
|
|
9
|
+
export * from "./webmcp_toolset.js";
|
|
10
|
+
export * from "./webmcp_types.js";
|
|
@@ -0,0 +1,131 @@
|
|
|
1
|
+
import {createRequire as topLevelCreateRequire} from 'module';
|
|
2
|
+
const require = topLevelCreateRequire(import.meta.url);
|
|
3
|
+
var __defProp = Object.defineProperty;
|
|
4
|
+
var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
|
|
5
|
+
/**
|
|
6
|
+
* @license
|
|
7
|
+
* Copyright 2026 Google LLC
|
|
8
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
9
|
+
*/
|
|
10
|
+
import { Type } from "@google/genai";
|
|
11
|
+
import { toGeminiSchema } from "../../utils/gemini_schema_util.js";
|
|
12
|
+
import { logger } from "../../utils/logger.js";
|
|
13
|
+
import { BaseTool } from "../base_tool.js";
|
|
14
|
+
import {
|
|
15
|
+
getModelContext
|
|
16
|
+
} from "./webmcp_types.js";
|
|
17
|
+
const argEncodingByContext = /* @__PURE__ */ new WeakMap();
|
|
18
|
+
function isArgParseFailure(value) {
|
|
19
|
+
var _a, _b;
|
|
20
|
+
let text = "";
|
|
21
|
+
if (typeof value === "string") {
|
|
22
|
+
text = value;
|
|
23
|
+
} else if (value && typeof value === "object") {
|
|
24
|
+
const candidate = value;
|
|
25
|
+
text = String((_b = (_a = candidate.error) != null ? _a : candidate.message) != null ? _b : "");
|
|
26
|
+
}
|
|
27
|
+
return /failed to parse input arguments|could not parse .*arguments/i.test(
|
|
28
|
+
text
|
|
29
|
+
);
|
|
30
|
+
}
|
|
31
|
+
__name(isArgParseFailure, "isArgParseFailure");
|
|
32
|
+
const _WebMCPTool = class _WebMCPTool extends BaseTool {
|
|
33
|
+
constructor(params) {
|
|
34
|
+
var _a, _b;
|
|
35
|
+
super({
|
|
36
|
+
name: (_a = params.name) != null ? _a : params.tool.name,
|
|
37
|
+
description: (_b = params.tool.description) != null ? _b : ""
|
|
38
|
+
});
|
|
39
|
+
this.webmcpTool = params.tool;
|
|
40
|
+
this.doc = params.document;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* The tool's JSON Schema as an object.
|
|
44
|
+
*
|
|
45
|
+
* `inputSchema` is specified as an object, but a browser handing back a JSON
|
|
46
|
+
* string would otherwise convert to a parameterless declaration, leaving the
|
|
47
|
+
* model no argument names to fill in — it then calls the tool with `{}`.
|
|
48
|
+
*/
|
|
49
|
+
resolveInputSchema() {
|
|
50
|
+
const raw = this.webmcpTool.inputSchema;
|
|
51
|
+
if (raw == null) return void 0;
|
|
52
|
+
if (typeof raw === "string") {
|
|
53
|
+
try {
|
|
54
|
+
const parsed = JSON.parse(raw);
|
|
55
|
+
return typeof parsed === "object" && parsed !== null ? parsed : void 0;
|
|
56
|
+
} catch {
|
|
57
|
+
logger.warn(
|
|
58
|
+
`WebMCP tool '${this.webmcpTool.name}' has an inputSchema string that is not valid JSON; exposing it with no parameters.`
|
|
59
|
+
);
|
|
60
|
+
return void 0;
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
if (typeof raw === "object") return raw;
|
|
64
|
+
return void 0;
|
|
65
|
+
}
|
|
66
|
+
_getDeclaration() {
|
|
67
|
+
var _a;
|
|
68
|
+
const schema = this.resolveInputSchema();
|
|
69
|
+
const parameters = schema ? (_a = toGeminiSchema(schema)) != null ? _a : { type: Type.OBJECT, properties: {} } : { type: Type.OBJECT, properties: {} };
|
|
70
|
+
if (schema && !parameters.properties) {
|
|
71
|
+
logger.warn(
|
|
72
|
+
`WebMCP tool '${this.webmcpTool.name}' declared an inputSchema that produced no parameters; the model will be unable to pass arguments.`
|
|
73
|
+
);
|
|
74
|
+
}
|
|
75
|
+
return {
|
|
76
|
+
name: this.name,
|
|
77
|
+
description: this.description,
|
|
78
|
+
parameters
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
async checkRequireConfirmation() {
|
|
82
|
+
var _a;
|
|
83
|
+
return !!((_a = this.webmcpTool.annotations) == null ? void 0 : _a.consequentialHint);
|
|
84
|
+
}
|
|
85
|
+
async runAsync(request) {
|
|
86
|
+
var _a, _b;
|
|
87
|
+
const modelContext = getModelContext(this.doc);
|
|
88
|
+
if (!modelContext) {
|
|
89
|
+
throw new Error(
|
|
90
|
+
"document.modelContext is unavailable, so WebMCP tools cannot be executed. WebMCP requires a browser with the API enabled."
|
|
91
|
+
);
|
|
92
|
+
}
|
|
93
|
+
const args = (_a = request.args) != null ? _a : {};
|
|
94
|
+
const signal = (_b = request.toolContext) == null ? void 0 : _b.abortSignal;
|
|
95
|
+
const options = signal ? { signal } : void 0;
|
|
96
|
+
const invoke = /* @__PURE__ */ __name((encoding) => modelContext.executeTool(
|
|
97
|
+
this.webmcpTool,
|
|
98
|
+
encoding === "json-string" ? JSON.stringify(args) : args,
|
|
99
|
+
options
|
|
100
|
+
), "invoke");
|
|
101
|
+
const known = argEncodingByContext.get(modelContext);
|
|
102
|
+
if (known) {
|
|
103
|
+
return await invoke(known);
|
|
104
|
+
}
|
|
105
|
+
let firstResult;
|
|
106
|
+
try {
|
|
107
|
+
firstResult = await invoke("object");
|
|
108
|
+
if (!isArgParseFailure(firstResult)) {
|
|
109
|
+
argEncodingByContext.set(modelContext, "object");
|
|
110
|
+
return firstResult;
|
|
111
|
+
}
|
|
112
|
+
} catch (err) {
|
|
113
|
+
if (!isArgParseFailure(err)) throw err;
|
|
114
|
+
firstResult = err;
|
|
115
|
+
}
|
|
116
|
+
const retried = await invoke("json-string");
|
|
117
|
+
if (isArgParseFailure(retried)) {
|
|
118
|
+
return firstResult;
|
|
119
|
+
}
|
|
120
|
+
argEncodingByContext.set(modelContext, "json-string");
|
|
121
|
+
logger.debug(
|
|
122
|
+
"This browser expects JSON-string WebMCP tool arguments; using that encoding."
|
|
123
|
+
);
|
|
124
|
+
return retried;
|
|
125
|
+
}
|
|
126
|
+
};
|
|
127
|
+
__name(_WebMCPTool, "WebMCPTool");
|
|
128
|
+
let WebMCPTool = _WebMCPTool;
|
|
129
|
+
export {
|
|
130
|
+
WebMCPTool
|
|
131
|
+
};
|
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
import {createRequire as topLevelCreateRequire} from 'module';
|
|
2
|
+
const require = topLevelCreateRequire(import.meta.url);
|
|
3
|
+
var __defProp = Object.defineProperty;
|
|
4
|
+
var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
|
|
5
|
+
/**
|
|
6
|
+
* @license
|
|
7
|
+
* Copyright 2026 Google LLC
|
|
8
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
9
|
+
*/
|
|
10
|
+
import { logger } from "../../utils/logger.js";
|
|
11
|
+
import { BaseToolset } from "../base_toolset.js";
|
|
12
|
+
import { WebMCPTool } from "./webmcp_tool.js";
|
|
13
|
+
import { getModelContext } from "./webmcp_types.js";
|
|
14
|
+
const _WebMCPToolset = class _WebMCPToolset extends BaseToolset {
|
|
15
|
+
constructor(options = {}) {
|
|
16
|
+
var _a;
|
|
17
|
+
super((_a = options.toolFilter) != null ? _a : [], options.prefix);
|
|
18
|
+
this.changeListeners = /* @__PURE__ */ new Set();
|
|
19
|
+
this.doc = options.document;
|
|
20
|
+
this.fromOrigins = options.fromOrigins;
|
|
21
|
+
}
|
|
22
|
+
/** Whether this document exposes WebMCP. */
|
|
23
|
+
isSupported() {
|
|
24
|
+
return !!getModelContext(this.doc);
|
|
25
|
+
}
|
|
26
|
+
async getTools(context) {
|
|
27
|
+
const modelContext = getModelContext(this.doc);
|
|
28
|
+
if (!modelContext) {
|
|
29
|
+
logger.debug(
|
|
30
|
+
"document.modelContext is unavailable; WebMCPToolset is exposing no tools."
|
|
31
|
+
);
|
|
32
|
+
return [];
|
|
33
|
+
}
|
|
34
|
+
const registered = await modelContext.getTools(
|
|
35
|
+
this.fromOrigins ? { fromOrigins: this.fromOrigins } : void 0
|
|
36
|
+
);
|
|
37
|
+
const tools = registered.map(
|
|
38
|
+
(tool) => new WebMCPTool({
|
|
39
|
+
tool,
|
|
40
|
+
name: this.prefix ? `${this.prefix}_${tool.name}` : tool.name,
|
|
41
|
+
document: this.doc
|
|
42
|
+
})
|
|
43
|
+
);
|
|
44
|
+
const filter = this.toolFilter;
|
|
45
|
+
if (!filter || Array.isArray(filter) && filter.length === 0) {
|
|
46
|
+
return tools;
|
|
47
|
+
}
|
|
48
|
+
if (Array.isArray(filter)) {
|
|
49
|
+
return tools.filter((tool) => filter.includes(tool.name));
|
|
50
|
+
}
|
|
51
|
+
if (context) {
|
|
52
|
+
return tools.filter((tool) => filter(tool, context));
|
|
53
|
+
}
|
|
54
|
+
logger.warn(
|
|
55
|
+
"WebMCPToolset: a ToolPredicate toolFilter was provided but getTools() was called without a ReadonlyContext. The filter will not be applied."
|
|
56
|
+
);
|
|
57
|
+
return tools;
|
|
58
|
+
}
|
|
59
|
+
/**
|
|
60
|
+
* Subscribes to the WebMCP `toolchange` event, which fires when the page
|
|
61
|
+
* registers or removes tools. Returns an unsubscribe function.
|
|
62
|
+
*/
|
|
63
|
+
onToolChange(listener) {
|
|
64
|
+
const modelContext = getModelContext(this.doc);
|
|
65
|
+
if (!modelContext) return () => {
|
|
66
|
+
};
|
|
67
|
+
const handler = /* @__PURE__ */ __name(() => listener(), "handler");
|
|
68
|
+
this.changeListeners.add(handler);
|
|
69
|
+
modelContext.addEventListener("toolchange", handler);
|
|
70
|
+
return () => {
|
|
71
|
+
modelContext.removeEventListener("toolchange", handler);
|
|
72
|
+
this.changeListeners.delete(handler);
|
|
73
|
+
};
|
|
74
|
+
}
|
|
75
|
+
async close() {
|
|
76
|
+
const modelContext = getModelContext(this.doc);
|
|
77
|
+
if (modelContext) {
|
|
78
|
+
for (const handler of this.changeListeners) {
|
|
79
|
+
modelContext.removeEventListener("toolchange", handler);
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
this.changeListeners.clear();
|
|
83
|
+
}
|
|
84
|
+
};
|
|
85
|
+
__name(_WebMCPToolset, "WebMCPToolset");
|
|
86
|
+
let WebMCPToolset = _WebMCPToolset;
|
|
87
|
+
export {
|
|
88
|
+
WebMCPToolset
|
|
89
|
+
};
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import {createRequire as topLevelCreateRequire} from 'module';
|
|
2
|
+
const require = topLevelCreateRequire(import.meta.url);
|
|
3
|
+
var __defProp = Object.defineProperty;
|
|
4
|
+
var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
|
|
5
|
+
/**
|
|
6
|
+
* @license
|
|
7
|
+
* Copyright 2026 Google LLC
|
|
8
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
9
|
+
*/
|
|
10
|
+
function getModelContext(doc) {
|
|
11
|
+
const target = doc != null ? doc : globalThis.document;
|
|
12
|
+
return target == null ? void 0 : target.modelContext;
|
|
13
|
+
}
|
|
14
|
+
__name(getModelContext, "getModelContext");
|
|
15
|
+
function isWebMCPSupported(doc) {
|
|
16
|
+
return !!getModelContext(doc);
|
|
17
|
+
}
|
|
18
|
+
__name(isWebMCPSupported, "isWebMCPSupported");
|
|
19
|
+
export {
|
|
20
|
+
getModelContext,
|
|
21
|
+
isWebMCPSupported
|
|
22
|
+
};
|
|
@@ -23,6 +23,54 @@ function camelCaseKeys(val) {
|
|
|
23
23
|
return val;
|
|
24
24
|
}
|
|
25
25
|
__name(camelCaseKeys, "camelCaseKeys");
|
|
26
|
+
const PYTHON_KEYWORDS = /* @__PURE__ */ new Set([
|
|
27
|
+
"False",
|
|
28
|
+
"None",
|
|
29
|
+
"True",
|
|
30
|
+
"and",
|
|
31
|
+
"as",
|
|
32
|
+
"assert",
|
|
33
|
+
"async",
|
|
34
|
+
"await",
|
|
35
|
+
"break",
|
|
36
|
+
"class",
|
|
37
|
+
"continue",
|
|
38
|
+
"def",
|
|
39
|
+
"del",
|
|
40
|
+
"elif",
|
|
41
|
+
"else",
|
|
42
|
+
"except",
|
|
43
|
+
"finally",
|
|
44
|
+
"for",
|
|
45
|
+
"from",
|
|
46
|
+
"global",
|
|
47
|
+
"if",
|
|
48
|
+
"import",
|
|
49
|
+
"in",
|
|
50
|
+
"is",
|
|
51
|
+
"lambda",
|
|
52
|
+
"nonlocal",
|
|
53
|
+
"not",
|
|
54
|
+
"or",
|
|
55
|
+
"pass",
|
|
56
|
+
"raise",
|
|
57
|
+
"return",
|
|
58
|
+
"try",
|
|
59
|
+
"while",
|
|
60
|
+
"with",
|
|
61
|
+
"yield"
|
|
62
|
+
]);
|
|
63
|
+
const DEFAULT_RESERVED_WORD_PREFIX = "param_";
|
|
64
|
+
function toSnakeCaseName(text) {
|
|
65
|
+
return text.replace(/[^a-zA-Z0-9]+/g, "_").replace(/([a-z0-9])([A-Z])/g, "$1_$2").replace(/([A-Z]+)([A-Z][a-z])/g, "$1_$2").toLowerCase().replace(/_+/g, "_").replace(/^_+|_+$/g, "");
|
|
66
|
+
}
|
|
67
|
+
__name(toSnakeCaseName, "toSnakeCaseName");
|
|
68
|
+
function renameReservedKeywords(s, prefix = DEFAULT_RESERVED_WORD_PREFIX) {
|
|
69
|
+
return PYTHON_KEYWORDS.has(s) ? prefix + s : s;
|
|
70
|
+
}
|
|
71
|
+
__name(renameReservedKeywords, "renameReservedKeywords");
|
|
26
72
|
export {
|
|
27
|
-
camelCaseKeys
|
|
73
|
+
camelCaseKeys,
|
|
74
|
+
renameReservedKeywords,
|
|
75
|
+
toSnakeCaseName
|
|
28
76
|
};
|
|
@@ -14,6 +14,7 @@ const ADK_LABEL = "google-adk";
|
|
|
14
14
|
const LANGUAGE_LABEL = "gl-typescript";
|
|
15
15
|
const AGENT_ENGINE_TELEMETRY_TAG = "remote_reasoning_engine";
|
|
16
16
|
const AGENT_ENGINE_TELEMETRY_ENV_VARIABLE_NAME = "GOOGLE_CLOUD_AGENT_ENGINE_ID";
|
|
17
|
+
const TRACKING_HEADER_NAMES = ["x-goog-api-client", "user-agent"];
|
|
17
18
|
const clientLabelLocalStorage = new AsyncLocalStorage();
|
|
18
19
|
const USER_AGENT_PATTERNS = [
|
|
19
20
|
["Edge", /(?:Edg|Edge|EdgA)\/([0-9.]+)/i],
|
|
@@ -63,8 +64,72 @@ function getClientLabels() {
|
|
|
63
64
|
return labels;
|
|
64
65
|
}
|
|
65
66
|
__name(getClientLabels, "getClientLabels");
|
|
67
|
+
function getTrackingHeaders() {
|
|
68
|
+
const headerValue = getClientLabels().join(" ");
|
|
69
|
+
return {
|
|
70
|
+
"x-goog-api-client": headerValue,
|
|
71
|
+
"user-agent": headerValue
|
|
72
|
+
};
|
|
73
|
+
}
|
|
74
|
+
__name(getTrackingHeaders, "getTrackingHeaders");
|
|
75
|
+
function isTrackingHeaderName(name) {
|
|
76
|
+
return TRACKING_HEADER_NAMES.some((trackingName) => trackingName === name);
|
|
77
|
+
}
|
|
78
|
+
__name(isTrackingHeaderName, "isTrackingHeaderName");
|
|
79
|
+
function isHeaders(headers) {
|
|
80
|
+
return typeof headers.forEach === "function";
|
|
81
|
+
}
|
|
82
|
+
__name(isHeaders, "isHeaders");
|
|
83
|
+
function headerEntries(headers) {
|
|
84
|
+
if (!headers) {
|
|
85
|
+
return [];
|
|
86
|
+
}
|
|
87
|
+
if (Array.isArray(headers)) {
|
|
88
|
+
return headers.map(([name, value]) => [name, value]);
|
|
89
|
+
}
|
|
90
|
+
if (isHeaders(headers)) {
|
|
91
|
+
const entries = [];
|
|
92
|
+
headers.forEach((value, name) => {
|
|
93
|
+
entries.push([name, value]);
|
|
94
|
+
});
|
|
95
|
+
return entries;
|
|
96
|
+
}
|
|
97
|
+
return Object.entries(headers);
|
|
98
|
+
}
|
|
99
|
+
__name(headerEntries, "headerEntries");
|
|
100
|
+
function mergeTrackingHeaders(headers) {
|
|
101
|
+
var _a, _b;
|
|
102
|
+
const merged = {};
|
|
103
|
+
const callerValues = /* @__PURE__ */ new Map();
|
|
104
|
+
for (const [name, value] of headerEntries(headers)) {
|
|
105
|
+
const lowerName = name.toLowerCase();
|
|
106
|
+
if (isTrackingHeaderName(lowerName)) {
|
|
107
|
+
callerValues.set(lowerName, [
|
|
108
|
+
...(_a = callerValues.get(lowerName)) != null ? _a : [],
|
|
109
|
+
value
|
|
110
|
+
]);
|
|
111
|
+
} else {
|
|
112
|
+
merged[name] = value;
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
for (const [name, trackingValue] of Object.entries(getTrackingHeaders())) {
|
|
116
|
+
const tokens = trackingValue.split(" ");
|
|
117
|
+
for (const value of (_b = callerValues.get(name)) != null ? _b : []) {
|
|
118
|
+
for (const token of value.split(/\s+/)) {
|
|
119
|
+
if (token && !tokens.includes(token)) {
|
|
120
|
+
tokens.push(token);
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
merged[name] = tokens.join(" ");
|
|
125
|
+
}
|
|
126
|
+
return merged;
|
|
127
|
+
}
|
|
128
|
+
__name(mergeTrackingHeaders, "mergeTrackingHeaders");
|
|
66
129
|
export {
|
|
67
130
|
getClientLabels,
|
|
131
|
+
getTrackingHeaders,
|
|
132
|
+
mergeTrackingHeaders,
|
|
68
133
|
parseUserAgent,
|
|
69
134
|
runWithClientLabel
|
|
70
135
|
};
|