@lamplitisles/dsh-nanocodex 0.1.0-beta.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/LICENSE +65 -0
- package/NOTICE +2 -0
- package/README.md +182 -0
- package/THIRD_PARTY_NOTICES.md +29 -0
- package/cordis.patch.yml +52 -0
- package/dist/index.d.ts +435 -0
- package/dist/index.js +3405 -0
- package/dist/standard-preset.d.ts +7 -0
- package/dist/standard-preset.js +25 -0
- package/engine-release.json +14 -0
- package/package.json +119 -0
- package/presets/standard/agent.cordis.yml +6 -0
- package/presets/standard/preset.yml +2 -0
- package/vendor/nanocodex/README.md +1344 -0
- package/vendor/nanocodex/actions/events.d.mts +10 -0
- package/vendor/nanocodex/actions/events.mjs +163 -0
- package/vendor/nanocodex/actions/index.d.mts +13 -0
- package/vendor/nanocodex/actions/index.mjs +35 -0
- package/vendor/nanocodex/actions/session.d.mts +66 -0
- package/vendor/nanocodex/actions/session.mjs +59 -0
- package/vendor/nanocodex/actions/turn.d.mts +59 -0
- package/vendor/nanocodex/actions/turn.mjs +37 -0
- package/vendor/nanocodex/actions/voice.d.mts +22 -0
- package/vendor/nanocodex/actions/voice.mjs +50 -0
- package/vendor/nanocodex/browser/Agent.d.mts +55 -0
- package/vendor/nanocodex/browser/Agent.mjs +11 -0
- package/vendor/nanocodex/browser/ChatGptSubscription.d.mts +7 -0
- package/vendor/nanocodex/browser/ChatGptSubscription.mjs +19 -0
- package/vendor/nanocodex/browser/InlineAgent.mjs +266 -0
- package/vendor/nanocodex/browser/Transport.d.mts +74 -0
- package/vendor/nanocodex/browser/Transport.mjs +61 -0
- package/vendor/nanocodex/browser/Voice.d.mts +71 -0
- package/vendor/nanocodex/browser/Voice.mjs +291 -0
- package/vendor/nanocodex/browser/VoiceSession.mjs +688 -0
- package/vendor/nanocodex/browser/WorkerAgent.d.mts +65 -0
- package/vendor/nanocodex/browser/WorkerAgent.mjs +1472 -0
- package/vendor/nanocodex/browser/agent.worker.mjs +3 -0
- package/vendor/nanocodex/browser/config.d.mts +36 -0
- package/vendor/nanocodex/browser/config.mjs +439 -0
- package/vendor/nanocodex/browser/engine.mjs +13 -0
- package/vendor/nanocodex/browser/harness.mjs +55 -0
- package/vendor/nanocodex/browser/host.d.mts +83 -0
- package/vendor/nanocodex/browser/host.mjs +555 -0
- package/vendor/nanocodex/browser/hostManagedWebSocket.d.mts +14 -0
- package/vendor/nanocodex/browser/hostManagedWebSocket.mjs +110 -0
- package/vendor/nanocodex/browser/index.d.mts +92 -0
- package/vendor/nanocodex/browser/index.mjs +23 -0
- package/vendor/nanocodex/browser/indexeddb-durability-store.mjs +197 -0
- package/vendor/nanocodex/browser/workspace.d.mts +16 -0
- package/vendor/nanocodex/browser/workspace.mjs +107 -0
- package/vendor/nanocodex/cloud/Client.d.mts +83 -0
- package/vendor/nanocodex/cloud/Client.mjs +231 -0
- package/vendor/nanocodex/cloud/Decorator.d.mts +31 -0
- package/vendor/nanocodex/cloud/Decorator.mjs +37 -0
- package/vendor/nanocodex/cloud/Dialog.d.mts +113 -0
- package/vendor/nanocodex/cloud/Dialog.mjs +366 -0
- package/vendor/nanocodex/cloud/Errors.d.mts +22 -0
- package/vendor/nanocodex/cloud/Errors.mjs +39 -0
- package/vendor/nanocodex/cloud/Principal.d.mts +26 -0
- package/vendor/nanocodex/cloud/Principal.mjs +88 -0
- package/vendor/nanocodex/cloud/RemoteProvider.mjs +88 -0
- package/vendor/nanocodex/cloud/Transport.d.mts +47 -0
- package/vendor/nanocodex/cloud/Transport.mjs +454 -0
- package/vendor/nanocodex/cloud/actions/account.d.mts +9 -0
- package/vendor/nanocodex/cloud/actions/account.mjs +19 -0
- package/vendor/nanocodex/cloud/actions/agent.d.mts +18 -0
- package/vendor/nanocodex/cloud/actions/agent.mjs +428 -0
- package/vendor/nanocodex/cloud/actions/connection.d.mts +133 -0
- package/vendor/nanocodex/cloud/actions/connection.mjs +580 -0
- package/vendor/nanocodex/cloud/actions/grant.d.mts +10 -0
- package/vendor/nanocodex/cloud/actions/grant.mjs +12 -0
- package/vendor/nanocodex/cloud/actions/index.d.mts +7 -0
- package/vendor/nanocodex/cloud/actions/index.mjs +7 -0
- package/vendor/nanocodex/cloud/actions/machineUsd.d.mts +23 -0
- package/vendor/nanocodex/cloud/actions/machineUsd.mjs +37 -0
- package/vendor/nanocodex/cloud/actions/model.d.mts +12 -0
- package/vendor/nanocodex/cloud/actions/model.mjs +50 -0
- package/vendor/nanocodex/cloud/actions/mpp.d.mts +28 -0
- package/vendor/nanocodex/cloud/actions/mpp.mjs +39 -0
- package/vendor/nanocodex/cloud/index.d.mts +30 -0
- package/vendor/nanocodex/cloud/index.mjs +9 -0
- package/vendor/nanocodex/cloud/internal.mjs +533 -0
- package/vendor/nanocodex/cloud/mercator.mjs +108 -0
- package/vendor/nanocodex/cloud/server/HostPrincipal.d.mts +34 -0
- package/vendor/nanocodex/cloud/server/HostPrincipal.mjs +202 -0
- package/vendor/nanocodex/cloud/server/index.d.mts +1 -0
- package/vendor/nanocodex/cloud/server/index.mjs +1 -0
- package/vendor/nanocodex/cloud/types.d.mts +211 -0
- package/vendor/nanocodex/cloudflare/Agent.d.mts +133 -0
- package/vendor/nanocodex/cloudflare/Agent.mjs +811 -0
- package/vendor/nanocodex/cloudflare/egress-subject.mjs +19 -0
- package/vendor/nanocodex/cloudflare/egress.d.mts +41 -0
- package/vendor/nanocodex/cloudflare/egress.mjs +119 -0
- package/vendor/nanocodex/cloudflare/event-socket.mjs +316 -0
- package/vendor/nanocodex/cloudflare/index.d.mts +7 -0
- package/vendor/nanocodex/cloudflare/index.mjs +6 -0
- package/vendor/nanocodex/host/Agent.d.mts +55 -0
- package/vendor/nanocodex/host/Agent.mjs +1 -0
- package/vendor/nanocodex/host/index.d.mts +82 -0
- package/vendor/nanocodex/host/index.mjs +10 -0
- package/vendor/nanocodex/index.d.mts +81 -0
- package/vendor/nanocodex/index.mjs +12 -0
- package/vendor/nanocodex/internal.mjs +1275 -0
- package/vendor/nanocodex/managed/Agent.d.mts +380 -0
- package/vendor/nanocodex/managed/Agent.mjs +1694 -0
- package/vendor/nanocodex/managed/ManagedError.d.mts +9 -0
- package/vendor/nanocodex/managed/ManagedError.mjs +8 -0
- package/vendor/nanocodex/managed/README.md +241 -0
- package/vendor/nanocodex/managed/Voice.mjs +202 -0
- package/vendor/nanocodex/managed/index.d.mts +20 -0
- package/vendor/nanocodex/managed/index.mjs +2 -0
- package/vendor/nanocodex/managed/internal.mjs +119 -0
- package/vendor/nanocodex/node/Agent.d.mts +50 -0
- package/vendor/nanocodex/node/Agent.mjs +203 -0
- package/vendor/nanocodex/node/ChatGptSubscription.d.mts +9 -0
- package/vendor/nanocodex/node/ChatGptSubscription.mjs +17 -0
- package/vendor/nanocodex/node/Transport.d.mts +44 -0
- package/vendor/nanocodex/node/Transport.mjs +46 -0
- package/vendor/nanocodex/node/host.mjs +731 -0
- package/vendor/nanocodex/node/index.d.mts +73 -0
- package/vendor/nanocodex/node/index.mjs +17 -0
- package/vendor/nanocodex/node/workspace.d.mts +10 -0
- package/vendor/nanocodex/node/workspace.mjs +198 -0
- package/vendor/nanocodex/package.json +200 -0
- package/vendor/nanocodex/pkg-node/nanocodex.d.ts +675 -0
- package/vendor/nanocodex/pkg-node/nanocodex.js +2628 -0
- package/vendor/nanocodex/pkg-node/nanocodex_bg.wasm.d.ts +105 -0
- package/vendor/nanocodex/pkg-node/package.json +1 -0
- package/vendor/nanocodex/pkg-web/.nanocodex-bindgen-stamp +6 -0
- package/vendor/nanocodex/pkg-web/nanocodex-build.json +1 -0
- package/vendor/nanocodex/pkg-web/nanocodex.d.ts +805 -0
- package/vendor/nanocodex/pkg-web/nanocodex.js +2714 -0
- package/vendor/nanocodex/pkg-web/nanocodex_bg.js +2615 -0
- package/vendor/nanocodex/pkg-web/nanocodex_bg.wasm +0 -0
- package/vendor/nanocodex/pkg-web/nanocodex_bg.wasm.d.ts +105 -0
- package/vendor/nanocodex/pkg-web/nanocodex_worker.js +9 -0
- package/vendor/nanocodex/pkg-web/package.json +1 -0
- package/vendor/nanocodex/runtime/chatgpt-subscription.mjs +212 -0
- package/vendor/nanocodex/runtime/cloudflare-durability-store.d.mts +26 -0
- package/vendor/nanocodex/runtime/cloudflare-durability-store.mjs +168 -0
- package/vendor/nanocodex/runtime/code-evaluator.worker.mjs +137 -0
- package/vendor/nanocodex/runtime/code-runtime.mjs +1 -0
- package/vendor/nanocodex/runtime/durability-store.d.mts +85 -0
- package/vendor/nanocodex/runtime/durability-store.mjs +631 -0
- package/vendor/nanocodex/runtime/durability.mjs +153 -0
- package/vendor/nanocodex/runtime/managed-transport.mjs +460 -0
- package/vendor/nanocodex/runtime/mcp-runtime.mjs +534 -0
- package/vendor/nanocodex/runtime/postgres-durability-store.d.mts +64 -0
- package/vendor/nanocodex/runtime/postgres-durability-store.mjs +532 -0
- package/vendor/nanocodex/runtime/quickjs-evaluator.d.mts +17 -0
- package/vendor/nanocodex/runtime/quickjs-evaluator.mjs +236 -0
- package/vendor/nanocodex/runtime/responses-transport.mjs +22 -0
- package/vendor/nanocodex/runtime/subagents.d.mts +107 -0
- package/vendor/nanocodex/runtime/subagents.mjs +54 -0
- package/vendor/nanocodex/runtime/subscription-store.d.mts +8 -0
- package/vendor/nanocodex/runtime/subscription-store.mjs +42 -0
- package/vendor/nanocodex/runtime/tempo-provider.d.mts +125 -0
- package/vendor/nanocodex/runtime/tempo-provider.mjs +264 -0
- package/vendor/nanocodex/runtime/tool-configuration.mjs +1 -0
- package/vendor/nanocodex/runtime/tool-router.mjs +1 -0
- package/vendor/nanocodex/runtime/utf8.mjs +1 -0
- package/vendor/nanocodex/runtime/worker-evaluator.mjs +162 -0
- package/vendor/nanocodex/runtime/workspace.d.mts +1 -0
- package/vendor/nanocodex/runtime/workspace.mjs +1 -0
- package/vendor/nanocodex/tools/Tools.d.mts +56 -0
- package/vendor/nanocodex/tools/Tools.mjs +136 -0
- package/vendor/nanocodex/tools/artifact.d.mts +1 -0
- package/vendor/nanocodex/tools/artifact.mjs +1 -0
- package/vendor/nanocodex/tools/attachment.mjs +1 -0
- package/vendor/nanocodex/tools/bash.d.mts +1 -0
- package/vendor/nanocodex/tools/bash.mjs +1 -0
- package/vendor/nanocodex/tools/browser/accountInfo.mjs +795 -0
- package/vendor/nanocodex/tools/browser/browserBuffer.mjs +18 -0
- package/vendor/nanocodex/tools/browser/browserCompiler.mjs +155 -0
- package/vendor/nanocodex/tools/browser/browserEgress.mjs +161 -0
- package/vendor/nanocodex/tools/browser/browserPython.mjs +133 -0
- package/vendor/nanocodex/tools/browser/browserShell.mjs +1075 -0
- package/vendor/nanocodex/tools/browser/browserSprintf.mjs +4 -0
- package/vendor/nanocodex/tools/browser/browserSsh.mjs +201 -0
- package/vendor/nanocodex/tools/browser/browserZlib.mjs +136 -0
- package/vendor/nanocodex/tools/browser/compiler.worker.mjs +160 -0
- package/vendor/nanocodex/tools/browser/devTunnelsSshBrowser.mjs +13 -0
- package/vendor/nanocodex/tools/browser/index.d.mts +209 -0
- package/vendor/nanocodex/tools/browser/index.mjs +174 -0
- package/vendor/nanocodex/tools/browser/opfsGit.mjs +248 -0
- package/vendor/nanocodex/tools/browser/python.worker.mjs +114 -0
- package/vendor/nanocodex/tools/browser/threadGit.mjs +197 -0
- package/vendor/nanocodex/tools/browser/unsupportedNodeRsa.mjs +5 -0
- package/vendor/nanocodex/tools/browser/workspace.mjs +83 -0
- package/vendor/nanocodex/tools/dataset.d.mts +1 -0
- package/vendor/nanocodex/tools/dataset.mjs +1 -0
- package/vendor/nanocodex/tools/datasetContract.mjs +1 -0
- package/vendor/nanocodex/tools/datasetEngine.mjs +1 -0
- package/vendor/nanocodex/tools/hostedCatalog.d.mts +1 -0
- package/vendor/nanocodex/tools/hostedCatalog.mjs +1 -0
- package/vendor/nanocodex/tools/index.d.mts +49 -0
- package/vendor/nanocodex/tools/index.mjs +19 -0
- package/vendor/nanocodex/tools/namedTool.mjs +1 -0
- package/vendor/nanocodex/tools/repository-workspace.d.mts +1 -0
- package/vendor/nanocodex/tools/repository-workspace.mjs +1 -0
- package/vendor/nanocodex/tools/ssh.d.mts +1 -0
- package/vendor/nanocodex/tools/ssh.mjs +1 -0
- package/vendor/nanocodex/tools/standard.mjs +1 -0
- package/vendor/nanocodex/tools/standardDescriptions.mjs +1 -0
- package/vendor/nanocodex/types.d.mts +663 -0
- package/vendor/nanocodex/wasm.d.mts +4 -0
- package/vendor/nanocodex/worker/ChatGptSubscription.d.mts +9 -0
- package/vendor/nanocodex/worker/ChatGptSubscription.mjs +29 -0
- package/vendor/nanocodex/worker/index.d.mts +18 -0
- package/vendor/nanocodex/worker/index.mjs +5 -0
- package/vendor/nanocodex-tools/README.md +65 -0
- package/vendor/nanocodex-tools/dist/hosted/app-tool-catalog.d.ts +7 -0
- package/vendor/nanocodex-tools/dist/hosted/app-tool-catalog.js +14 -0
- package/vendor/nanocodex-tools/dist/hosted/broker-core.d.ts +172 -0
- package/vendor/nanocodex-tools/dist/hosted/broker-core.js +1278 -0
- package/vendor/nanocodex-tools/dist/hosted/index.d.ts +3 -0
- package/vendor/nanocodex-tools/dist/hosted/index.js +3 -0
- package/vendor/nanocodex-tools/dist/hosted/protocol.d.ts +120 -0
- package/vendor/nanocodex-tools/dist/hosted/protocol.js +415 -0
- package/vendor/nanocodex-tools/dist/index.d.ts +19 -0
- package/vendor/nanocodex-tools/dist/index.js +14 -0
- package/vendor/nanocodex-tools/dist/memory.d.ts +204 -0
- package/vendor/nanocodex-tools/dist/memory.js +411 -0
- package/vendor/nanocodex-tools/dist/namespace.d.ts +87 -0
- package/vendor/nanocodex-tools/dist/namespace.js +338 -0
- package/vendor/nanocodex-tools/dist/repository-archive.d.ts +4 -0
- package/vendor/nanocodex-tools/dist/repository-archive.js +104 -0
- package/vendor/nanocodex-tools/dist/runtime.d.ts +30 -0
- package/vendor/nanocodex-tools/dist/runtime.js +37 -0
- package/vendor/nanocodex-tools/dist/session.d.ts +167 -0
- package/vendor/nanocodex-tools/dist/session.js +286 -0
- package/vendor/nanocodex-tools/dist/shell.d.ts +51 -0
- package/vendor/nanocodex-tools/dist/shell.js +553 -0
- package/vendor/nanocodex-tools/dist/ssh.d.ts +29 -0
- package/vendor/nanocodex-tools/dist/ssh.js +66 -0
- package/vendor/nanocodex-tools/dist/workspace.d.ts +45 -0
- package/vendor/nanocodex-tools/dist/workspace.js +237 -0
- package/vendor/nanocodex-tools/package.json +122 -0
- package/vendor/nanocodex-tools/runtime/code-runtime.mjs +817 -0
- package/vendor/nanocodex-tools/runtime/tool-configuration.mjs +50 -0
- package/vendor/nanocodex-tools/runtime/tool-router.mjs +730 -0
- package/vendor/nanocodex-tools/runtime/utf8.d.mts +2 -0
- package/vendor/nanocodex-tools/runtime/utf8.mjs +25 -0
- package/vendor/nanocodex-tools/tools/artifact.d.mts +69 -0
- package/vendor/nanocodex-tools/tools/artifact.mjs +270 -0
- package/vendor/nanocodex-tools/tools/attachment.mjs +603 -0
- package/vendor/nanocodex-tools/tools/bash.d.mts +90 -0
- package/vendor/nanocodex-tools/tools/bash.mjs +742 -0
- package/vendor/nanocodex-tools/tools/dataset.d.mts +9 -0
- package/vendor/nanocodex-tools/tools/dataset.mjs +47 -0
- package/vendor/nanocodex-tools/tools/datasetContract.mjs +54 -0
- package/vendor/nanocodex-tools/tools/datasetEngine.mjs +1167 -0
- package/vendor/nanocodex-tools/tools/execution-contract.d.mts +5 -0
- package/vendor/nanocodex-tools/tools/execution-contract.mjs +63 -0
- package/vendor/nanocodex-tools/tools/hostedCatalog.d.mts +20 -0
- package/vendor/nanocodex-tools/tools/hostedCatalog.mjs +67 -0
- package/vendor/nanocodex-tools/tools/hostedMachine.d.mts +10 -0
- package/vendor/nanocodex-tools/tools/hostedMachine.mjs +56 -0
- package/vendor/nanocodex-tools/tools/just-bash-browser.d.mts +1 -0
- package/vendor/nanocodex-tools/tools/just-bash-browser.mjs +1 -0
- package/vendor/nanocodex-tools/tools/namedTool.d.mts +3 -0
- package/vendor/nanocodex-tools/tools/namedTool.mjs +3 -0
- package/vendor/nanocodex-tools/tools/nodeProcess.d.mts +10 -0
- package/vendor/nanocodex-tools/tools/nodeProcess.mjs +314 -0
- package/vendor/nanocodex-tools/tools/processOutput.mjs +56 -0
- package/vendor/nanocodex-tools/tools/repository-workspace.d.mts +55 -0
- package/vendor/nanocodex-tools/tools/repository-workspace.mjs +397 -0
- package/vendor/nanocodex-tools/tools/ssh.d.mts +56 -0
- package/vendor/nanocodex-tools/tools/ssh.mjs +503 -0
- package/vendor/nanocodex-tools/tools/standard.mjs +458 -0
- package/vendor/nanocodex-tools/tools/standardDescriptions.mjs +3 -0
- package/vendor/nanocodex-tools/tools/types.d.mts +83 -0
- package/vendor/nanocodex-tools/tools/workspace.d.mts +25 -0
- package/vendor/nanocodex-tools/tools/workspace.mjs +282 -0
- package/vendor/nanocodex-tools/tools/x.d.mts +30 -0
- package/vendor/nanocodex-tools/tools/x.mjs +91 -0
|
@@ -0,0 +1,458 @@
|
|
|
1
|
+
import { IMAGE_DESCRIPTION, WEB_DESCRIPTION } from "./standardDescriptions.mjs";
|
|
2
|
+
import { namedTool } from "./namedTool.mjs";
|
|
3
|
+
import { toolResult } from "../runtime/code-runtime.mjs";
|
|
4
|
+
|
|
5
|
+
export { namedTool };
|
|
6
|
+
|
|
7
|
+
const MAX_VIEW_IMAGE_BYTES = 10 * 1024 * 1024;
|
|
8
|
+
const DEFAULT_WEB_URL = "/api/tools/web-search";
|
|
9
|
+
const DEFAULT_IMAGE_URL = "/api/tools/image-generation";
|
|
10
|
+
|
|
11
|
+
export function web(options = {}) {
|
|
12
|
+
const request = jsonRequester(options, DEFAULT_WEB_URL);
|
|
13
|
+
return namedTool("web__run", {
|
|
14
|
+
supportsParallelToolCalls: true,
|
|
15
|
+
description: WEB_DESCRIPTION,
|
|
16
|
+
parameters: webParameters,
|
|
17
|
+
outputSchema: { type: "string" },
|
|
18
|
+
async handler(input, context) {
|
|
19
|
+
const commands = normalizeWebCommands(input);
|
|
20
|
+
const result = requireObject(await request({
|
|
21
|
+
commands,
|
|
22
|
+
session_id: context.sessionId,
|
|
23
|
+
model: context.model,
|
|
24
|
+
}, context.signal), "web__run response");
|
|
25
|
+
return requireString(result.output, "web__run response.output");
|
|
26
|
+
},
|
|
27
|
+
});
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
export function imageGeneration(options = {}) {
|
|
31
|
+
const request = jsonRequester(options, DEFAULT_IMAGE_URL);
|
|
32
|
+
const recentImages = options.recentImages ?? (() => []);
|
|
33
|
+
const rememberImage = options.rememberImage ?? (() => {});
|
|
34
|
+
return namedTool("image_gen__imagegen", {
|
|
35
|
+
description: IMAGE_DESCRIPTION,
|
|
36
|
+
parameters: {
|
|
37
|
+
type: "object",
|
|
38
|
+
properties: {
|
|
39
|
+
prompt: { type: "string" },
|
|
40
|
+
referenced_image_paths: {
|
|
41
|
+
type: ["array", "null"],
|
|
42
|
+
items: { type: "string" },
|
|
43
|
+
maxItems: 5,
|
|
44
|
+
},
|
|
45
|
+
num_last_images_to_include: {
|
|
46
|
+
type: ["integer", "null"],
|
|
47
|
+
minimum: 1,
|
|
48
|
+
maximum: 5,
|
|
49
|
+
},
|
|
50
|
+
},
|
|
51
|
+
required: ["prompt"],
|
|
52
|
+
additionalProperties: false,
|
|
53
|
+
},
|
|
54
|
+
outputSchema: {
|
|
55
|
+
type: "object",
|
|
56
|
+
properties: {
|
|
57
|
+
image_url: { type: "string" },
|
|
58
|
+
output_hint: { type: "string" },
|
|
59
|
+
},
|
|
60
|
+
required: ["image_url"],
|
|
61
|
+
additionalProperties: true,
|
|
62
|
+
},
|
|
63
|
+
async handler(input, context) {
|
|
64
|
+
const args = requireObject(input, "image_gen__imagegen");
|
|
65
|
+
const prompt = requireString(args.prompt, "image_gen__imagegen.prompt");
|
|
66
|
+
const paths = optionalStringArray(args.referenced_image_paths);
|
|
67
|
+
const count = optionalInteger(args.num_last_images_to_include);
|
|
68
|
+
if (paths.length > 5) throw new Error("referenced_image_paths accepts at most 5 paths");
|
|
69
|
+
if (paths.length && count !== undefined) {
|
|
70
|
+
throw new Error("provide referenced_image_paths or num_last_images_to_include, not both");
|
|
71
|
+
}
|
|
72
|
+
if (count !== undefined && (count < 1 || count > 5)) {
|
|
73
|
+
throw new Error("num_last_images_to_include must be between 1 and 5");
|
|
74
|
+
}
|
|
75
|
+
const images = paths.length
|
|
76
|
+
? await Promise.all(paths.map((path) => workspaceImage(options.workspace, path)))
|
|
77
|
+
: count === undefined ? [] : recentImages(context.sessionId, count);
|
|
78
|
+
if (count !== undefined && images.length !== count) {
|
|
79
|
+
throw new Error(`requested ${count} recent images, but only ${images.length} are available`);
|
|
80
|
+
}
|
|
81
|
+
const result = requireObject(
|
|
82
|
+
await request({ images, prompt }, context.signal),
|
|
83
|
+
"image_gen__imagegen response",
|
|
84
|
+
);
|
|
85
|
+
const imageUrl = requireString(result.image_url, "image_gen__imagegen response.image_url");
|
|
86
|
+
rememberImage(context.sessionId, imageUrl);
|
|
87
|
+
return result;
|
|
88
|
+
},
|
|
89
|
+
});
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
export function viewImage(options) {
|
|
93
|
+
return namedTool("view_image", {
|
|
94
|
+
supportsParallelToolCalls: true,
|
|
95
|
+
description: "View a local image file from the filesystem when visual inspection is needed. Use this for images already available on disk.",
|
|
96
|
+
parameters: {
|
|
97
|
+
type: "object",
|
|
98
|
+
properties: {
|
|
99
|
+
path: { type: "string", description: "Local filesystem path to an image file." },
|
|
100
|
+
detail: { type: "string", enum: ["high", "original"], description: "Image detail level. Defaults to `high`; use `original` to preserve exact resolution." },
|
|
101
|
+
},
|
|
102
|
+
required: ["path"],
|
|
103
|
+
additionalProperties: false,
|
|
104
|
+
},
|
|
105
|
+
outputSchema: {
|
|
106
|
+
type: "object",
|
|
107
|
+
properties: {
|
|
108
|
+
image_url: { type: "string", description: "Data URL for the loaded image." },
|
|
109
|
+
detail: { type: "string", enum: ["high", "original"], description: "Image detail hint returned by view_image. Returns `high` for default resized behavior or `original` when original resolution is preserved." },
|
|
110
|
+
},
|
|
111
|
+
required: ["image_url", "detail"],
|
|
112
|
+
additionalProperties: false,
|
|
113
|
+
},
|
|
114
|
+
async handler(input) {
|
|
115
|
+
const args = requireObject(input, "view_image");
|
|
116
|
+
const path = requireString(args.path, "view_image.path");
|
|
117
|
+
const detail = args.detail === undefined ? "high" : args.detail;
|
|
118
|
+
if (detail !== "high" && detail !== "original") {
|
|
119
|
+
throw new Error("view_image.detail must be high or original");
|
|
120
|
+
}
|
|
121
|
+
const bytes = await options.workspace.readFile(path);
|
|
122
|
+
if (bytes.byteLength > MAX_VIEW_IMAGE_BYTES) {
|
|
123
|
+
throw new Error("view_image input exceeds 10 MiB");
|
|
124
|
+
}
|
|
125
|
+
const mimeType = imageMimeType(bytes);
|
|
126
|
+
if (!mimeType) throw new Error("view_image supports PNG, JPEG, GIF, and WebP files");
|
|
127
|
+
const result = { detail, image_url: `data:${mimeType};base64,${base64(bytes)}` };
|
|
128
|
+
return toolResult([{
|
|
129
|
+
type: "input_image",
|
|
130
|
+
image_url: result.image_url,
|
|
131
|
+
detail,
|
|
132
|
+
}], result, { value: result });
|
|
133
|
+
},
|
|
134
|
+
});
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
export function updatePlan() {
|
|
138
|
+
const plans = new Map();
|
|
139
|
+
return namedTool("update_plan", {
|
|
140
|
+
description: "Update the current task plan. At most one step may be in progress.",
|
|
141
|
+
parameters: {
|
|
142
|
+
type: "object",
|
|
143
|
+
properties: {
|
|
144
|
+
explanation: { type: "string" },
|
|
145
|
+
plan: {
|
|
146
|
+
type: "array",
|
|
147
|
+
items: {
|
|
148
|
+
type: "object",
|
|
149
|
+
properties: {
|
|
150
|
+
step: { type: "string" },
|
|
151
|
+
status: { type: "string", enum: ["pending", "in_progress", "completed"] },
|
|
152
|
+
},
|
|
153
|
+
required: ["step", "status"],
|
|
154
|
+
additionalProperties: false,
|
|
155
|
+
},
|
|
156
|
+
},
|
|
157
|
+
},
|
|
158
|
+
required: ["plan"],
|
|
159
|
+
additionalProperties: false,
|
|
160
|
+
},
|
|
161
|
+
outputSchema: {
|
|
162
|
+
type: "object",
|
|
163
|
+
properties: { updated: { type: "boolean", const: true } },
|
|
164
|
+
required: ["updated"],
|
|
165
|
+
additionalProperties: false,
|
|
166
|
+
},
|
|
167
|
+
async handler(input, context) {
|
|
168
|
+
const value = requireObject(input, "update_plan");
|
|
169
|
+
if (!Array.isArray(value.plan)) throw new Error("update_plan.plan must be an array");
|
|
170
|
+
const active = value.plan.filter((item) =>
|
|
171
|
+
typeof item === "object" && item !== null && item.status === "in_progress"
|
|
172
|
+
);
|
|
173
|
+
if (active.length > 1) throw new Error("at most one plan step may be in_progress");
|
|
174
|
+
plans.set(context.sessionId, structuredClone(value));
|
|
175
|
+
return { updated: true };
|
|
176
|
+
},
|
|
177
|
+
releaseSession(sessionId) {
|
|
178
|
+
plans.delete(sessionId);
|
|
179
|
+
},
|
|
180
|
+
dispose() {
|
|
181
|
+
plans.clear();
|
|
182
|
+
},
|
|
183
|
+
});
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
function jsonRequester(options, defaultUrl) {
|
|
187
|
+
if (!options || typeof options !== "object" || Array.isArray(options)) {
|
|
188
|
+
throw new TypeError("tool options must be an object");
|
|
189
|
+
}
|
|
190
|
+
const url = options.url ?? defaultUrl;
|
|
191
|
+
if (typeof url !== "string" && !(url instanceof URL)) {
|
|
192
|
+
throw new TypeError("tool url must be a string or URL");
|
|
193
|
+
}
|
|
194
|
+
const fetchImpl = options.fetch ?? globalThis.fetch;
|
|
195
|
+
if (typeof fetchImpl !== "function") throw new TypeError("tool fetch must be a function");
|
|
196
|
+
const headers = Object.freeze({
|
|
197
|
+
"content-type": "application/json",
|
|
198
|
+
...options.headers,
|
|
199
|
+
});
|
|
200
|
+
return async (body, signal) => {
|
|
201
|
+
const response = await fetchImpl(url, {
|
|
202
|
+
method: "POST",
|
|
203
|
+
headers,
|
|
204
|
+
body: JSON.stringify(body),
|
|
205
|
+
// These adapters commonly carry caller-owned bearer credentials.
|
|
206
|
+
// Never let fetch forward them to a redirect target.
|
|
207
|
+
redirect: "manual",
|
|
208
|
+
signal,
|
|
209
|
+
});
|
|
210
|
+
if (response.type === "opaqueredirect" || (response.status >= 300 && response.status < 400)) {
|
|
211
|
+
throw new Error("tool endpoint redirects are not allowed");
|
|
212
|
+
}
|
|
213
|
+
const payload = await response.json().catch(() => undefined);
|
|
214
|
+
if (!response.ok) {
|
|
215
|
+
const message = typeof payload?.error === "string" ? payload.error : `HTTP ${response.status}`;
|
|
216
|
+
throw new Error(message);
|
|
217
|
+
}
|
|
218
|
+
return payload;
|
|
219
|
+
};
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
function normalizeWebCommands(input) {
|
|
223
|
+
const value = requireObject(input, "web__run");
|
|
224
|
+
const commands = Object.keys(value).length === 1 && value.commands !== undefined
|
|
225
|
+
? requireObject(value.commands, "web__run.commands")
|
|
226
|
+
: value;
|
|
227
|
+
const normalized = { ...commands };
|
|
228
|
+
for (const operation of [
|
|
229
|
+
"search_query",
|
|
230
|
+
"image_query",
|
|
231
|
+
"open",
|
|
232
|
+
"click",
|
|
233
|
+
"find",
|
|
234
|
+
"finance",
|
|
235
|
+
"weather",
|
|
236
|
+
"sports",
|
|
237
|
+
"time",
|
|
238
|
+
]) {
|
|
239
|
+
const command = normalized[operation];
|
|
240
|
+
if (command === undefined || Array.isArray(command)) continue;
|
|
241
|
+
if (typeof command === "object" && command !== null) {
|
|
242
|
+
normalized[operation] = [command];
|
|
243
|
+
continue;
|
|
244
|
+
}
|
|
245
|
+
if (typeof command === "string" && (operation === "search_query" || operation === "image_query")) {
|
|
246
|
+
normalized[operation] = [{ q: command }];
|
|
247
|
+
continue;
|
|
248
|
+
}
|
|
249
|
+
if (typeof command === "string" && operation === "open") {
|
|
250
|
+
normalized.open = [{ ref_id: command }];
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
const operationCount = [
|
|
254
|
+
"search_query",
|
|
255
|
+
"image_query",
|
|
256
|
+
"open",
|
|
257
|
+
"click",
|
|
258
|
+
"find",
|
|
259
|
+
"finance",
|
|
260
|
+
"weather",
|
|
261
|
+
"sports",
|
|
262
|
+
"time",
|
|
263
|
+
].reduce((count, operation) => count + (Array.isArray(normalized[operation])
|
|
264
|
+
? normalized[operation].length
|
|
265
|
+
: 0), 0);
|
|
266
|
+
if (!operationCount) throw new Error("web__run requires at least one operation");
|
|
267
|
+
const queryCount = Array.isArray(normalized.search_query) ? normalized.search_query.length : 0;
|
|
268
|
+
if (queryCount > 4) throw new Error("web__run accepts at most 4 search queries");
|
|
269
|
+
if (queryCount === 4 && normalized.response_length !== "medium" && normalized.response_length !== "long") {
|
|
270
|
+
throw new Error("web__run requires response_length medium or long for 4 search queries");
|
|
271
|
+
}
|
|
272
|
+
return normalized;
|
|
273
|
+
}
|
|
274
|
+
|
|
275
|
+
function requireObject(value, name) {
|
|
276
|
+
if (typeof value !== "object" || value === null || Array.isArray(value)) {
|
|
277
|
+
throw new Error(`${name} requires an object`);
|
|
278
|
+
}
|
|
279
|
+
return value;
|
|
280
|
+
}
|
|
281
|
+
|
|
282
|
+
function requireString(value, name) {
|
|
283
|
+
if (typeof value !== "string" || !value.trim()) throw new Error(`${name} must be a non-empty string`);
|
|
284
|
+
return value;
|
|
285
|
+
}
|
|
286
|
+
|
|
287
|
+
function optionalInteger(value) {
|
|
288
|
+
if (value === undefined || value === null) return undefined;
|
|
289
|
+
if (!Number.isInteger(value)) throw new Error("num_last_images_to_include must be an integer");
|
|
290
|
+
return value;
|
|
291
|
+
}
|
|
292
|
+
|
|
293
|
+
function optionalStringArray(value) {
|
|
294
|
+
if (value === undefined || value === null) return [];
|
|
295
|
+
if (!Array.isArray(value) || value.some((item) => typeof item !== "string" || !item.trim())) {
|
|
296
|
+
throw new Error("referenced_image_paths must be an array of non-empty strings");
|
|
297
|
+
}
|
|
298
|
+
return value;
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
async function workspaceImage(workspace, path) {
|
|
302
|
+
if (!workspace || typeof workspace.readFile !== "function") {
|
|
303
|
+
throw new Error("referenced_image_paths requires an image-generation workspace");
|
|
304
|
+
}
|
|
305
|
+
const bytes = await workspace.readFile(path);
|
|
306
|
+
if (bytes.byteLength > MAX_VIEW_IMAGE_BYTES) {
|
|
307
|
+
throw new Error(`${path} exceeds the 10 MiB image limit`);
|
|
308
|
+
}
|
|
309
|
+
const mimeType = imageMimeType(bytes);
|
|
310
|
+
if (!mimeType) throw new Error(`${path} is not a supported image`);
|
|
311
|
+
return `data:${mimeType};base64,${base64(bytes)}`;
|
|
312
|
+
}
|
|
313
|
+
|
|
314
|
+
function imageMimeType(bytes) {
|
|
315
|
+
if (startsWith(bytes, [0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a])) return "image/png";
|
|
316
|
+
if (startsWith(bytes, [0xff, 0xd8, 0xff])) return "image/jpeg";
|
|
317
|
+
if (startsWith(bytes, [0x47, 0x49, 0x46, 0x38])) return "image/gif";
|
|
318
|
+
if (startsWith(bytes, [0x52, 0x49, 0x46, 0x46])
|
|
319
|
+
&& startsWith(bytes.subarray(8), [0x57, 0x45, 0x42, 0x50])) return "image/webp";
|
|
320
|
+
return undefined;
|
|
321
|
+
}
|
|
322
|
+
|
|
323
|
+
function startsWith(bytes, signature) {
|
|
324
|
+
return signature.every((value, index) => bytes[index] === value);
|
|
325
|
+
}
|
|
326
|
+
|
|
327
|
+
function base64(bytes) {
|
|
328
|
+
let binary = "";
|
|
329
|
+
for (let offset = 0; offset < bytes.length; offset += 32_768) {
|
|
330
|
+
binary += String.fromCharCode(...bytes.subarray(offset, offset + 32_768));
|
|
331
|
+
}
|
|
332
|
+
return btoa(binary);
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
const query = {
|
|
336
|
+
description: "Search query with optional domain and recency filters.",
|
|
337
|
+
type: "object",
|
|
338
|
+
properties: {
|
|
339
|
+
q: { type: "string" },
|
|
340
|
+
recency: { type: "integer" },
|
|
341
|
+
domains: { type: "array", items: { type: "string" } },
|
|
342
|
+
},
|
|
343
|
+
required: ["q"],
|
|
344
|
+
additionalProperties: false,
|
|
345
|
+
};
|
|
346
|
+
|
|
347
|
+
const webParameters = {
|
|
348
|
+
type: "object",
|
|
349
|
+
properties: {
|
|
350
|
+
search_query: {
|
|
351
|
+
type: "array",
|
|
352
|
+
description: "Query the internet search engine for a given list of queries.",
|
|
353
|
+
maxItems: 4,
|
|
354
|
+
items: query,
|
|
355
|
+
},
|
|
356
|
+
image_query: {
|
|
357
|
+
type: "array",
|
|
358
|
+
description: "Query the image search engine for source pages and captions.",
|
|
359
|
+
items: query,
|
|
360
|
+
},
|
|
361
|
+
open: {
|
|
362
|
+
type: "array",
|
|
363
|
+
description: "Open pages by reference id or URL.",
|
|
364
|
+
items: {
|
|
365
|
+
type: "object",
|
|
366
|
+
properties: { ref_id: { type: "string" }, lineno: { type: "integer" } },
|
|
367
|
+
required: ["ref_id"],
|
|
368
|
+
additionalProperties: false,
|
|
369
|
+
},
|
|
370
|
+
},
|
|
371
|
+
click: {
|
|
372
|
+
type: "array",
|
|
373
|
+
description: "Open numbered links from previously opened pages.",
|
|
374
|
+
items: {
|
|
375
|
+
type: "object",
|
|
376
|
+
properties: { ref_id: { type: "string" }, id: { type: "integer" } },
|
|
377
|
+
required: ["ref_id", "id"],
|
|
378
|
+
additionalProperties: false,
|
|
379
|
+
},
|
|
380
|
+
},
|
|
381
|
+
find: {
|
|
382
|
+
type: "array",
|
|
383
|
+
description: "Find text patterns in pages.",
|
|
384
|
+
items: {
|
|
385
|
+
type: "object",
|
|
386
|
+
properties: { ref_id: { type: "string" }, pattern: { type: "string" } },
|
|
387
|
+
required: ["ref_id", "pattern"],
|
|
388
|
+
additionalProperties: false,
|
|
389
|
+
},
|
|
390
|
+
},
|
|
391
|
+
finance: {
|
|
392
|
+
type: "array",
|
|
393
|
+
description: "Look up prices for stock symbols and other assets.",
|
|
394
|
+
items: {
|
|
395
|
+
type: "object",
|
|
396
|
+
properties: {
|
|
397
|
+
ticker: { type: "string" },
|
|
398
|
+
type: { type: "string", enum: ["equity", "fund", "crypto", "index"] },
|
|
399
|
+
market: { type: "string" },
|
|
400
|
+
},
|
|
401
|
+
required: ["ticker", "type"],
|
|
402
|
+
additionalProperties: false,
|
|
403
|
+
},
|
|
404
|
+
},
|
|
405
|
+
weather: {
|
|
406
|
+
type: "array",
|
|
407
|
+
description: "Look up weather forecasts.",
|
|
408
|
+
items: {
|
|
409
|
+
type: "object",
|
|
410
|
+
properties: {
|
|
411
|
+
location: { type: "string" },
|
|
412
|
+
start: { type: "string" },
|
|
413
|
+
duration: { type: "integer" },
|
|
414
|
+
},
|
|
415
|
+
required: ["location"],
|
|
416
|
+
additionalProperties: false,
|
|
417
|
+
},
|
|
418
|
+
},
|
|
419
|
+
sports: {
|
|
420
|
+
type: "array",
|
|
421
|
+
description: "Look up sports schedules and standings.",
|
|
422
|
+
items: {
|
|
423
|
+
type: "object",
|
|
424
|
+
properties: {
|
|
425
|
+
fn: { type: "string", enum: ["schedule", "standings"] },
|
|
426
|
+
league: {
|
|
427
|
+
type: "string",
|
|
428
|
+
enum: ["nba", "wnba", "nfl", "nhl", "mlb", "epl", "ncaamb", "ncaawb", "ipl"],
|
|
429
|
+
},
|
|
430
|
+
team: { type: "string" },
|
|
431
|
+
opponent: { type: "string" },
|
|
432
|
+
date_from: { type: "string" },
|
|
433
|
+
date_to: { type: "string" },
|
|
434
|
+
num_games: { type: "integer" },
|
|
435
|
+
locale: { type: "string" },
|
|
436
|
+
},
|
|
437
|
+
required: ["fn", "league"],
|
|
438
|
+
additionalProperties: false,
|
|
439
|
+
},
|
|
440
|
+
},
|
|
441
|
+
time: {
|
|
442
|
+
type: "array",
|
|
443
|
+
description: "Get time for the given UTC offsets.",
|
|
444
|
+
items: {
|
|
445
|
+
type: "object",
|
|
446
|
+
properties: { utc_offset: { type: "string" } },
|
|
447
|
+
required: ["utc_offset"],
|
|
448
|
+
additionalProperties: false,
|
|
449
|
+
},
|
|
450
|
+
},
|
|
451
|
+
response_length: {
|
|
452
|
+
type: "string",
|
|
453
|
+
description: "Set the length of the returned response.",
|
|
454
|
+
enum: ["short", "medium", "long"],
|
|
455
|
+
},
|
|
456
|
+
},
|
|
457
|
+
additionalProperties: false,
|
|
458
|
+
};
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
// Generated from the canonical Rust tool descriptions. Keep the parity test green.
|
|
2
|
+
export const WEB_DESCRIPTION = "Tool for accessing the internet.\n\n\n---\n\n## Examples of different commands available in this tool\n\nExamples of different commands available in this tool:\n* `search_query`: {\"search_query\": [{\"q\": \"What is the capital of France?\"}, {\"q\": \"What is the capital of belgium?\"}]}. Searches the internet for a given query (and optionally with a domain or recency filter)\n* `image_query`: {\"image_query\":[{\"q\": \"waterfalls\"}]}. Finds image-search source pages and captions; it does not return model-visible image bytes.\n* `open`: {\"open\": [{\"ref_id\": \"turn0search0\"}, {\"ref_id\": \"https://www.openai.com\", \"lineno\": 120}]}\n* `click`: {\"click\": [{\"ref_id\": \"turn0fetch3\", \"id\": 17}]}\n* `find`: {\"find\": [{\"ref_id\": \"turn0fetch3\", \"pattern\": \"Annie Case\"}]}\n* `finance`: {\"finance\":[{\"ticker\":\"AMD\",\"type\":\"equity\",\"market\":\"USA\"}]}, {\"finance\":[{\"ticker\":\"BTC\",\"type\":\"crypto\",\"market\":\"\"}]}\n* `weather`: {\"weather\":[{\"location\":\"San Francisco, CA\"}]}\n* `sports`: {\"sports\":[{\"fn\":\"standings\",\"league\":\"nfl\"}, {\"fn\":\"schedule\",\"league\":\"nba\",\"team\":\"GSW\",\"date_from\":\"2025-02-24\"}]}\n* `time`: {\"time\":[{\"utc_offset\":\"+03:00\"}]}\n\n---\n\n## Usage hints\nTo use this tool efficiently:\n* Use multiple commands and queries in one call to get more results faster; e.g. {\"search_query\": [{\"q\": \"bitcoin news\"}], \"finance\":[{\"ticker\":\"BTC\",\"type\":\"crypto\",\"market\":\"\"}], \"find\": [{\"ref_id\": \"turn0search0\", \"pattern\": \"Annie Case\"}, {\"ref_id\": \"turn0search1\", \"pattern\": \"John Smith\"}]}\n* Use \"response_length\" to control the amount of returned text, and omit it for the service default.\n* Only write required parameters; do not write empty lists or nulls where they could be omitted.\n* `search_query` must have length at most 4 in each call. If it has length > 3, response_length must be medium or long\n* If you find yourself in a situation where you accidentally call the `web.run` tool, it's best just to send an empty query: {\"search_query\": [{\"q\": \"\"}]}.\n\n---\n\n## Decision boundary\n\nIf the user makes an explicit request to search the internet, find latest information, look up, etc (or to not do so), you must obey their request.\nWhen you make an assumption, always consider whether it is temporally stable; i.e. whether there's even a small (>10%) chance it has changed. If it is unstable, you must verify with browsing the internet for verification.\n\n<situations_where_you_must_browse_the_internet>\nBelow is a list of scenarios where browsing the internet MUST be used. PAY CLOSE ATTENTION: you MUST browse the internet in these cases. If you're unsure or on the fence, you MUST bias towards browsing the internet.\n- The information could have changed recently: for example news; prices; laws; schedules; product specs; sports scores; economic indicators; political/public/company figures (e.g. the question relates to 'the president of country A' or 'the CEO of company B', which might change over time); rules; regulations; standards; software libraries that could be updated; exchange rates; recommendations (i.e., recommendations about various topics or things might be informed by what currently exists / is popular / is safe / is unsafe / is in the zeitgeist / etc.); and many many many more categories -- again, if you're on the fence, you MUST browse the internet!\n - For news queries, prioritize more recent events, ensuring you compare publish dates and the date that the event happened.\n- The user is seeking recommendations that could lead them to spend substantial time or money -- researching products, restaurants, travel plans, etc.\n- The user wants (or would benefit from) direct quotes, links, or precise source attribution.\n- A specific page, paper, dataset, PDF, or site is referenced and you haven't been given its contents.\n- You're unsure about a fact, the topic is niche or emerging, or you suspect there's at least a 10% chance you will incorrectly recall it\n- High-stakes accuracy matters (medical, legal, financial guidance). For these you generally should search by default because this information is highly temporally unstable\n- The user explicitly says to search, browse, verify, or look it up.\n</situations_where_you_must_browse_the_internet>\n\n---\n\n## Citations\n\nResults from `web.run` include internal reference IDs such as `turn2search5`. Use\nthose reference IDs only in calls to `web.run`; do not expose them in the final\nresponse.\n\nCite sources in the final response using Markdown links:\n\n- Cite a single source as `[descriptive source title](https://example.com/page)`.\n- Cite multiple sources with separate Markdown links, for example\n `[first source](https://example.com/one), [second source](https://example.com/two)`.\n- Link directly to the page that supports the claim. Do not link to search result\n pages or use bare URLs.\n\nFormatting of citations:\n\n- Place each citation as near as possible to the claim it supports, normally at\n the end of the sentence or paragraph and after punctuation.\n- Do not place citations inside code fences.\n- Do not put citations on a line by themselves or collect all citations at the\n end of the response.\n\nIf you browse the internet, cite statements supported by web sources. Each cited\nsource must directly support the associated claim. Prefer primary and\nauthoritative sources, and use sources from different domains when the response\nbenefits from multiple perspectives.\n\n---\n\n## Special cases\nIf these conflict with any other instructions, these should take precedence.\n\n<special_cases>\n- When the user asks for information about how to use OpenAI products, (ChatGPT, the OpenAI API, etc.), you should check the code in local env and only browse as fallback, when you browse restrict your sources to official OpenAI websites using the domains filter, unless otherwise requested.\n- When using search to answer technical questions, you must only rely on primary sources (research papers, official documentation, etc.)\n- Clearly indicate when you are making an inference from sources.\n</special_cases>\n\n---\n\n## Word limits\nResponses may not excessively quote or draw on a specific source. There are several limits here:\n- **Limit on verbatim quotes:**\n - You may not quote more than 25 words verbatim from any single non-lyrical source, unless the source is reddit.\n - For song lyrics, verbatim quotes must be limited to at most 10 words.\n - Long quotes from reddit are allowed, as long as you indicate that those are direct quotes via a markdown blockquote starting with \">\", copy verbatim, and link the source.\n- **Word limits:**\n - Each webpage source in the sources has a word limit label formatted like \"[wordlim N]\", in which N is the maximum number of words in the whole response that are attributed to that source. If omitted, the word limit is 200 words.\n - Non-contiguous words derived from a given source must be counted to the word limit.\n - The summarization limit N is a maximum for each source.\n - When using multiple sources, their summarization limits add together. However, each article used must be relevant to the response.\n- **Copyright compliance:**\n - You must avoid providing full articles, long verbatim passages, or extensive direct quotes due to copyright concerns.\n - If the user asked for a verbatim quote, the response should provide a short compliant excerpt and then answer with paraphrases and summaries.\n - Again, this limit does not apply to reddit content, as long as it's appropriately indicated that those are direct quotes and you link to the source.";
|
|
3
|
+
export const IMAGE_DESCRIPTION = "The `image_gen.imagegen` tool enables image generation from descriptions and editing of existing images based on specific instructions. Use it when:\n\n- The user requests an image based on a scene description, such as a diagram, portrait, comic, meme, or any other visual.\n- The user wants to modify an attached or previously generated image with specific changes, including adding or removing elements, altering colors, improving quality/resolution, or transforming the style (e.g., cartoon, oil painting).\n\nGuidelines:\n- imagegen needs a few minutes to finish. In code-mode, use the first-line @exec directive to give the initial call 120 seconds and the same yield for any waits that follow. Once it finishes, return the image with generatedImage(result).\n- Omit both `referenced_image_paths` and `num_last_images_to_include` when generating a brand new image.\n- For edits, use `referenced_image_paths` when every target image has a local file path.\n- If you have not seen a local image yet, use `view_image` to inspect it before editing.\n- Use `num_last_images_to_include` only when at least one target image has no local file path.\n- Set `num_last_images_to_include` to the smallest number of recent conversation images that includes every target image, up to 5.\n- Never provide both `referenced_image_paths` and `num_last_images_to_include`.\n- If neither mechanism can include every target image, ask the user to attach the missing images again.\n- Directly generate the image without reconfirmation or clarification unless required images must be attached again.\n- Always use this tool for image editing unless the user explicitly requests otherwise. Do not use the `python` tool for image editing unless specifically instructed.";
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
export type SubagentToolContext = Readonly<{
|
|
2
|
+
agentId: string;
|
|
3
|
+
parentAgentId: string | null;
|
|
4
|
+
sessionId: string;
|
|
5
|
+
role: string;
|
|
6
|
+
task: string;
|
|
7
|
+
}>;
|
|
8
|
+
|
|
9
|
+
export type ToolContext = Readonly<{
|
|
10
|
+
callId: string;
|
|
11
|
+
parentCallId: string;
|
|
12
|
+
sessionId: string;
|
|
13
|
+
model: string;
|
|
14
|
+
signal: AbortSignal;
|
|
15
|
+
subagent?: SubagentToolContext | undefined;
|
|
16
|
+
}>;
|
|
17
|
+
|
|
18
|
+
/** JSON Schema or other provider-owned JSON metadata used by a tool definition. */
|
|
19
|
+
export type ToolJson = Readonly<Record<string, unknown>>;
|
|
20
|
+
|
|
21
|
+
/** Grammar format for a Responses free-form custom tool. */
|
|
22
|
+
export type CustomToolFormat = Readonly<{
|
|
23
|
+
type: "grammar";
|
|
24
|
+
syntax: string;
|
|
25
|
+
definition: string;
|
|
26
|
+
}>;
|
|
27
|
+
|
|
28
|
+
/** Exact function or grammar-constrained custom definition sent to the model. */
|
|
29
|
+
export type ToolDefinition =
|
|
30
|
+
| Readonly<{
|
|
31
|
+
type: "function";
|
|
32
|
+
/** The router replaces this with the containing map or named-tool name. */
|
|
33
|
+
name?: string | undefined;
|
|
34
|
+
description: string;
|
|
35
|
+
strict: boolean;
|
|
36
|
+
defer_loading?: boolean | undefined;
|
|
37
|
+
async?: boolean | undefined;
|
|
38
|
+
parameters: ToolJson;
|
|
39
|
+
output_schema?: ToolJson | undefined;
|
|
40
|
+
}>
|
|
41
|
+
| Readonly<{
|
|
42
|
+
type: "custom";
|
|
43
|
+
/** The router replaces this with the containing map or named-tool name. */
|
|
44
|
+
name?: string | undefined;
|
|
45
|
+
description: string;
|
|
46
|
+
defer_loading?: boolean | undefined;
|
|
47
|
+
async?: boolean | undefined;
|
|
48
|
+
format: CustomToolFormat;
|
|
49
|
+
}>;
|
|
50
|
+
|
|
51
|
+
export type Tool = Readonly<{
|
|
52
|
+
description: string;
|
|
53
|
+
supportsParallelToolCalls?: boolean | undefined;
|
|
54
|
+
parameters?: Record<string, unknown> | undefined;
|
|
55
|
+
outputSchema?: Record<string, unknown> | undefined;
|
|
56
|
+
/** Optional provider-native definition; its name is canonicalized by the router. */
|
|
57
|
+
definition?: ToolDefinition | undefined;
|
|
58
|
+
handler(input: unknown, context: ToolContext): unknown | Promise<unknown>;
|
|
59
|
+
releaseSession?(sessionId: string): void;
|
|
60
|
+
dispose?(): void | Promise<void>;
|
|
61
|
+
}>;
|
|
62
|
+
|
|
63
|
+
export type NamedTool = Tool & Readonly<{ name: string }>;
|
|
64
|
+
export type ToolMap = Record<string, Tool>;
|
|
65
|
+
|
|
66
|
+
export type WorkspaceEntry = Readonly<{
|
|
67
|
+
kind: "directory" | "file";
|
|
68
|
+
modifiedAt?: number | undefined;
|
|
69
|
+
path: string;
|
|
70
|
+
size?: number | undefined;
|
|
71
|
+
}>;
|
|
72
|
+
|
|
73
|
+
export type Workspace = Readonly<{
|
|
74
|
+
root: string;
|
|
75
|
+
list(path?: string, options?: {
|
|
76
|
+
recursive?: boolean | undefined;
|
|
77
|
+
maxEntries?: number | undefined;
|
|
78
|
+
}): Promise<readonly WorkspaceEntry[]>;
|
|
79
|
+
readFile(path: string): Promise<Uint8Array>;
|
|
80
|
+
writeFile(path: string, contents: string | ArrayBuffer | ArrayBufferView): Promise<void>;
|
|
81
|
+
remove(path: string, options?: { recursive?: boolean | undefined }): Promise<void>;
|
|
82
|
+
mkdir(path: string): Promise<void>;
|
|
83
|
+
}>;
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import type { ToolMap, Workspace, WorkspaceEntry } from "./types.mjs";
|
|
2
|
+
|
|
3
|
+
export type { Workspace, WorkspaceEntry } from "./types.mjs";
|
|
4
|
+
|
|
5
|
+
export type WorkspaceBackend = {
|
|
6
|
+
list(path: string, options: { recursive: boolean; maxEntries: number }): Promise<readonly WorkspaceEntry[]>;
|
|
7
|
+
readFile(path: string): Promise<Uint8Array | ArrayBuffer | ArrayBufferView>;
|
|
8
|
+
writeFile(path: string, contents: Uint8Array): Promise<void>;
|
|
9
|
+
remove(path: string, options: { recursive: boolean }): Promise<void>;
|
|
10
|
+
mkdir(path: string): Promise<void>;
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
export function createWorkspace(options: {
|
|
14
|
+
backend: WorkspaceBackend;
|
|
15
|
+
root?: string | undefined;
|
|
16
|
+
}): Workspace;
|
|
17
|
+
|
|
18
|
+
export function tools(workspace: Workspace, options?: {
|
|
19
|
+
maxEntries?: number | undefined;
|
|
20
|
+
maxReadBytes?: number | undefined;
|
|
21
|
+
maxWriteBytes?: number | undefined;
|
|
22
|
+
}): ToolMap;
|
|
23
|
+
|
|
24
|
+
export function normalizeRelativePath(path: string): string;
|
|
25
|
+
export function resolveWorkspacePath(root: string, path: string): string;
|