DashboardCodeSession 0oTNP1IANwqs

Session 0oTNP1IANwqs

Full ID: 0oTNP1IANwqsgCBMg
Messages: 96
Distillations: 8
Time range: 2026-06-10 14:31:14 — 2026-06-10 14:43:43

Conversation (96 messages)

I'm designing a heuristic to dynamically identify two kinds of agent tools from their JSON-schema definitions (without hardcoding tool names): (1) a "read a file" tool, and (2) a "run a shell command" tool. I need the ACTUAL tool definitions used by several coding agents so I can survey the variety of names/params.

Research these GitHub repos and report the exact tool definitions:

  1. free-code (a Claude Code-style agent) — https://github.com/paoloanzn/free-code
  2. Cline — https://github.com/cline/cline (if accessible)
  3. OpenHands — https://github.com/All-Hands-AI/OpenHands (if accessible)
  4. Gemini CLI — https://github.com/google-gemini/gemini-cli (if accessible)

Also, document the well-known Claude Code tool shapes from public knowledge: its Bash tool (param command) and Read tool (param file_path), capitalization included.

For EACH agent, find and report:

  • The file-reading tool: exact tool name (case-sensitive), the exact parameter name(s) (e.g. path, filePath, file_path, file, absolute_path), each param's JSON type, which are required, and the description (or first sentence).
  • The shell/command-execution tool: exact tool name, the exact parameter name for the command (e.g. command, cmd, script), whether it's a string or array, other params, and the description.
  • Any tools that could cause false positives (edit/write/grep/glob/search) — names + param names only.
  • Source file path(s) / URL where the definitions live.

Use gh CLI and/or webfetch on raw.githubusercontent.com to read actual source. Browse repo trees to find tool definition files (look for tools/, description, parameters, inputSchema, input_schema, zod schemas).

Report concrete findings with exact strings and source URLs. If any agent has NO dedicated read tool (only shell), say so explicitly. Focus on breadth — I want to see how much the names and param names vary across agents.

gateway · 2026-06-10 14:31:14
reasoning

I'll start by exploring these repositories to understand their structure and locate the tool definition files, using the GitHub CLI to browse them efficiently.

I'll research these repos systematically. Let me start by exploring the repository structures in parallel.

claude-opus-4-8 · 2026-06-10 14:31:14 · ~94 tokens
result
.gitignore
CLAUDE.md
FEATURES.md
README.md
assets
assets/screenshot.png
bun.lock
changes.md
env.d.ts
install.sh
package.json
scripts
scripts/build.ts
src
src/QueryEngine.ts
src/Task.ts
src/Tool.ts
src/assistant
src/assistant/AssistantSessionChooser.tsx
src/assistant/sessionHistory.ts
src/bootstrap
src/bootstrap/state.ts
src/bridge
src/bridge/bridgeApi.ts
src/bridge/bridgeConfig.ts
src/bridge/bridgeDebug.ts
src/bridge/bridgeEnabled.ts
src/bridge/bridgeMain.ts
src/bridge/bridgeMessaging.ts
src/bridge/bridgePermissionCallbacks.ts
src/bridge/bridgePointer.ts
src/bridge/bridgeStatusUtil.ts
src/bridge/bridgeUI.ts
src/bridge/capacityWake.ts
src/bridge/codeSessionApi.ts
src/bridge/createSession.ts
src/bridge/debugUtils.ts
src/bridge/envLessBridgeConfig.ts
src/bridge/flushGate.ts
src/bridge/inboundAttachments.ts
src/bridge/inboundMessages.ts
src/bridge/initReplBridge.ts
src/bridge/jwtUtils.ts
src/bridge/pollConfig.ts
src/bridge/pollConfigDefaults.ts
src/bridge/remoteBridgeCore.ts
src/bridge/rep...
result
.agents/skills/cline-sdk/references/tools
.agents/skills/cline-sdk/references/tools/REFERENCE.md
.tool-versions
apps/cli/src/acp/tool-utils.ts
apps/cli/src/connectors/adapters/prompts.ts
apps/cli/src/runtime/prompt.test.ts
apps/cli/src/runtime/prompt.ts
apps/cli/src/runtime/tool-policies.test.ts
apps/cli/src/runtime/tool-policies.ts
apps/cli/src/runtime/tools.ts
apps/cli/src/tui/components/dialogs/tool-approval.tsx
apps/cli/src/tui/components/inline-tool-response.tsx
apps/cli/src/tui/components/queued-prompts.tsx
apps/cli/src/tui/components/tool-output.tsx
apps/cli/src/tui/hooks/use-prompt-input-controller.ts
apps/cli/src/tui/hooks/use-queued-prompts.test.ts
apps/cli/src/tui/hooks/use-queued-prompts.ts
apps/cli/src/tui/utils/tool-errors.test.ts
apps/cli/src/tui/utils/tool-errors.ts
apps/cli/src/tui/utils/tool-parsing.ts
apps/cline-hub/src/webview/src/components/ai-elements/prompt-input.tsx
apps/cline-hub/src/webview/src/components/ai-elements/tool.tsx
apps/cline-hub/src/webview/src/com...
result
docs/assets/connected_devtools.png
docs/cli/tutorials/web-tools.md
docs/reference/tools.md
docs/tools
docs/tools/activate-skill.md
docs/tools/ask-user.md
docs/tools/file-system.md
docs/tools/internal-docs.md
docs/tools/mcp-resources.md
docs/tools/mcp-server.md
docs/tools/memory.md
docs/tools/planning.md
docs/tools/shell.md
docs/tools/todos.md
docs/tools/tracker.md
docs/tools/web-fetch.md
docs/tools/web-search.md
evals/automated-tool-use.eval.ts
evals/tool_output_masking.eval.ts
integration-tests/hooks-system.after-tool-context.responses
integration-tests/hooks-system.allow-tool.responses
integration-tests/hooks-system.before-tool-selection.responses
integration-tests/hooks-system.before-tool-stop.responses
integration-tests/hooks-system.block-tool.responses
integration-tests/hooks-system.tail-tool-call.responses
integration-tests/parallel-tools.responses
integration-tests/parallel-tools.test.ts
packages/cli/src/commands/extensions/examples/exclude-tools
packages/cli/src/commands/extens...
result
frontend/__tests__/components/context-menu/tools-context-menu.test.tsx
frontend/__tests__/components/features/conversation-panel/system-message-modal/tool-item.test.tsx
frontend/__tests__/components/v1/chat/event-content-helpers/get-acp-tool-call-content.test.ts
frontend/__tests__/components/v1/chat/event-message-acp-tool-call.test.tsx
frontend/src/components/features/chat/chat-action-tooltip.tsx
frontend/src/components/features/chat/git-control-bar-tooltip-wrapper.tsx
frontend/src/components/features/controls/git-tools-submenu.tsx
frontend/src/components/features/controls/tools-context-menu-icon-text.tsx
frontend/src/components/features/controls/tools-context-menu.tsx
frontend/src/components/features/controls/tools.tsx
frontend/src/components/features/conversation-panel/system-message-modal/empty-tools-state.tsx
frontend/src/components/features/conversation-panel/system-message-modal/tool-item.tsx
frontend/src/components/features/conversation-panel/system-message-modal/tool-parameters...
gateway · 2026-06-10 14:31:35
reasoning

I'm starting to explore the tool definitions across different repositories—looking at free-code's Tool.ts file and its tools directory, then comparing with how Cline, OpenHands, and Gemini CLI structure their tools.

Let me dig deeper into each repo's tool definitions. Starting with free-code and finding the actual tool files.

claude-opus-4-8 · 2026-06-10 14:31:35 · ~114 tokens
result
README.md
src/Tool.ts
src/commands.ts
src/commands
src/commands/add-dir
src/commands/add-dir/add-dir.tsx
src/commands/add-dir/index.ts
src/commands/add-dir/validation.ts
src/commands/advisor.ts
src/commands/agents
src/commands/agents/agents.tsx
src/commands/agents/index.ts
src/commands/ant-trace
src/commands/ant-trace/index.js
src/commands/assistant
src/commands/assistant/assistant.tsx
src/commands/autofix-pr
src/commands/autofix-pr/index.js
src/commands/backfill-sessions
src/commands/backfill-sessions/index.js
src/commands/branch
src/commands/branch/branch.ts
src/commands/branch/index.ts
src/commands/break-cache
src/commands/break-cache/index.js
src/commands/bridge-kick.ts
src/commands/bridge
src/commands/bridge/bridge.tsx
src/commands/bridge/index.ts
src/commands/brief.ts
src/commands/btw
src/commands/btw/btw.tsx
src/commands/btw/index.ts
src/commands/bughunter
src/commands/bughunter/index.js
src/commands/chrome
src/commands/chrome/chrome.tsx
src/commands/chrome/index.ts
src/commands...
result
.agents/skills/cline-sdk/references/tools/REFERENCE.md
apps/vscode/src/core/prompts/system-prompt/tools/README.md
apps/vscode/src/core/prompts/system-prompt/tools/access_mcp_resource.ts
apps/vscode/src/core/prompts/system-prompt/tools/act_mode_respond.ts
apps/vscode/src/core/prompts/system-prompt/tools/apply_patch.ts
apps/vscode/src/core/prompts/system-prompt/tools/ask_followup_question.ts
apps/vscode/src/core/prompts/system-prompt/tools/attempt_completion.ts
apps/vscode/src/core/prompts/system-prompt/tools/browser_action.ts
apps/vscode/src/core/prompts/system-prompt/tools/execute_command.ts
apps/vscode/src/core/prompts/system-prompt/tools/focus_chain.ts
apps/vscode/src/core/prompts/system-prompt/tools/generate_explanation.ts
apps/vscode/src/core/prompts/system-prompt/tools/index.ts
apps/vscode/src/core/prompts/system-prompt/tools/init.ts
apps/vscode/src/core/prompts/system-prompt/tools/list_code_definition_names.ts
apps/vscode/src/core/prompts/system-prompt/tools/list_files.ts
apps/vs...
result
(no output)
result
docs/tools/shell.md
packages/core/src/tools/edit.test.ts
packages/core/src/tools/edit.ts
packages/core/src/tools/glob.test.ts
packages/core/src/tools/glob.ts
packages/core/src/tools/grep-utils.ts
packages/core/src/tools/grep.test.ts
packages/core/src/tools/grep.ts
packages/core/src/tools/ls.test.ts
packages/core/src/tools/ls.ts
packages/core/src/tools/read-file.test.ts
packages/core/src/tools/read-file.ts
packages/core/src/tools/read-many-files.test.ts
packages/core/src/tools/read-many-files.ts
packages/core/src/tools/read-mcp-resource.test.ts
packages/core/src/tools/read-mcp-resource.ts
packages/core/src/tools/shell.test.ts
packages/core/src/tools/shell.ts
packages/core/src/tools/shellBackgroundTools.integration.test.ts
packages/core/src/tools/shellBackgroundTools.test.ts
packages/core/src/tools/shellBackgroundTools.ts
packages/core/src/tools/shell_proactive.test.ts
packages/core/src/tools/write-file.test.ts
packages/core/src/tools/write-file.ts
packages/core/src/tools/write-todos.tes...
gateway · 2026-06-10 14:31:55
reasoning

I've got some promising leads to follow. The free-code repository likely has tool schemas defined in a tools directory within src, so I should search for that structure. For Cline, there are two key locations—the VSCode extension has tool prompt definitions scattered across the core prompts directory, but the SDK's definitions file is probably the authoritative source for how tools are actually structured.

OpenHands didn't show up in my initial grep, so I need to try a different search approach since they use litellm's ChatCompletionToolParam format. For Gemini CLI, I've spotted read-file.ts and shell.ts which should contain what I need.

Let me batch these reads together and start by locating the free-code tools directory and finding where OpenHands defines its tools.

Now let me read the actual tool definitions. Let me fetch the key files in parallel.

claude-opus-4-8 · 2026-06-10 14:31:55 · ~293 tokens
result
src/components/FileEditToolDiff.tsx
src/components/FileEditToolUpdatedMessage.tsx
src/components/FileEditToolUseRejectedMessage.tsx
src/components/permissions/BashPermissionRequest/bashToolUseOptions.tsx
src/components/permissions/FileEditPermissionRequest
src/components/permissions/FileEditPermissionRequest/FileEditPermissionRequest.tsx
src/services/tools/StreamingToolExecutor.ts
src/services/tools/toolExecution.ts
src/services/tools/toolHooks.ts
src/services/tools/toolOrchestration.ts
src/tools.ts
src/tools
src/tools/AgentTool
src/tools/AgentTool/AgentTool.tsx
src/tools/AgentTool/UI.tsx
src/tools/AgentTool/agentColorManager.ts
src/tools/AgentTool/agentDisplay.ts
src/tools/AgentTool/agentMemory.ts
src/tools/AgentTool/agentMemorySnapshot.ts
src/tools/AgentTool/agentToolUtils.ts
src/tools/AgentTool/built-in
src/tools/AgentTool/built-in/claudeCodeGuideAgent.ts
src/tools/AgentTool/built-in/exploreAgent.ts
src/tools/AgentTool/built-in/generalPurposeAgent.ts
src/tools/AgentTool/built-in/pla...
result
enterprise/migrations/versions/093_add_pending_free_credits.py
enterprise/migrations/versions/095_drop_pending_free_credits.py
enterprise/migrations/versions/109_add_llm_profiles_to_user.py
enterprise/migrations/versions/116_add_llm_profiles_to_org.py
enterprise/server/routes/org_profiles.py
enterprise/server/routes/readiness.py
enterprise/server/sharing/filesystem_shared_event_service.py
enterprise/tests/unit/test_org_profiles.py
openhands/app_server/event/filesystem_event_service.py
openhands/app_server/file_store/__init__.py
openhands/app_server/file_store/files.py
openhands/app_server/file_store/google_cloud.py
openhands/app_server/file_store/local.py
openhands/app_server/file_store/memory.py
openhands/app_server/file_store/s3.py
openhands/app_server/secrets/file_secrets_store.py
openhands/app_server/settings/file_settings_store.py
openhands/app_server/settings/llm_profiles.py
tests/unit/app_server/file_store/__init__.py
tests/unit/app_server/file_store/test_file_store.py
tests/uni...
gateway · 2026-06-10 14:32:11
reasoning

I'm looking for the FileRead tool in free-code's src/tools directory, then checking where OpenHands keeps its tool definitions since they've recently migrated to a new agent-sdk structure with separate openhands-sdk and openhands-tools repositories.

claude-opus-4-8 · 2026-06-10 14:32:11 · ~88 tokens
result
src/tools/BashTool
src/tools/BashTool/BashTool.tsx
src/tools/BashTool/BashToolResultMessage.tsx
src/tools/BashTool/UI.tsx
src/tools/BashTool/bashCommandHelpers.ts
src/tools/BashTool/bashPermissions.ts
src/tools/BashTool/bashSecurity.ts
src/tools/BashTool/commandSemantics.ts
src/tools/BashTool/commentLabel.ts
src/tools/BashTool/destructiveCommandWarning.ts
src/tools/BashTool/modeValidation.ts
src/tools/BashTool/pathValidation.ts
src/tools/BashTool/prompt.ts
src/tools/BashTool/readOnlyValidation.ts
src/tools/BashTool/sedEditParser.ts
src/tools/BashTool/sedValidation.ts
src/tools/BashTool/shouldUseSandbox.ts
src/tools/BashTool/toolName.ts
src/tools/BashTool/utils.ts
src/tools/FileEditTool
src/tools/FileEditTool/FileEditTool.ts
src/tools/FileEditTool/UI.tsx
src/tools/FileEditTool/constants.ts
src/tools/FileEditTool/prompt.ts
src/tools/FileEditTool/types.ts
src/tools/FileEditTool/utils.ts
src/tools/FileReadTool
src/tools/FileReadTool/FileReadTool.ts
src/tools/FileReadTool/UI.tsx
src/tools/F...
result
src/tools/AgentTool/agentColorManager.ts
src/tools/AgentTool/agentDisplay.ts
src/tools/AgentTool/agentMemory.ts
src/tools/AgentTool/agentMemorySnapshot.ts
src/tools/AgentTool/agentToolUtils.ts
src/tools/AgentTool/built-in/claudeCodeGuideAgent.ts
src/tools/AgentTool/built-in/exploreAgent.ts
src/tools/AgentTool/built-in/generalPurposeAgent.ts
src/tools/AgentTool/built-in/planAgent.ts
src/tools/AgentTool/built-in/statuslineSetup.ts
src/tools/AgentTool/built-in/verificationAgent.ts
src/tools/AgentTool/builtInAgents.ts
src/tools/AgentTool/constants.ts
src/tools/AgentTool/forkSubagent.ts
src/tools/AgentTool/loadAgentsDir.ts
src/tools/AgentTool/prompt.ts
src/tools/AgentTool/resumeAgent.ts
src/tools/AgentTool/runAgent.ts
src/tools/AskUserQuestionTool/prompt.ts
src/tools/BashTool/bashCommandHelpers.ts
src/tools/BashTool/bashPermissions.ts
src/tools/BashTool/bashSecurity.ts
src/tools/BashTool/commandSemantics.ts
src/tools/BashTool/commentLabel.ts
src/tools/BashTool/destructiveCommandWarning.ts
s...
gateway · 2026-06-10 14:32:30
reasoning

I'm looking at the tools available in free-code—FileReadTool, BashTool, FileEditTool, FileWriteTool, GlobTool, and GrepTool—and I need to examine their implementations. I'm fetching the source files for FileReadTool, BashTool, and their associated configuration files to understand how they're structured and what input schemas they use.

free-code has FileReadTool, BashTool, FileEditTool, FileWriteTool, GlobTool, GrepTool. Let me read the actual schema definitions.

claude-opus-4-8 · 2026-06-10 14:32:30 · ~161 tokens
result
...output truncated...

Full output saved to: /home/byk/.local/share/opencode/tool-output/tool_eb1f2ff78001B7rMqcWQjOO5qk

// Here to break circular dependency from prompt.ts
export const BASH_TOOL_NAME = 'Bash'
gateway · 2026-06-10 14:32:46
reasoning

I need to check the saved file and extract the key fields like inputSchema, name, and description.

claude-opus-4-8 · 2026-06-10 14:32:46 · ~37 tokens
result
Found 224 matches (more matches available)
/home/byk/.local/share/opencode/tool-output/tool_eb1f2ff78001B7rMqcWQjOO5qk:
  Line 119: function isBlockedDevicePath(filePath: string): boolean {

  Line 120:   if (BLOCKED_DEVICE_PATHS.has(filePath)) return true

  Line 123:     filePath.startsWith('/proc/') &&

  Line 124:     (filePath.endsWith('/fd/0') ||

  Line 125:       filePath.endsWith('/fd/1') ||

  Line 126:       filePath.endsWith('/fd/2'))

  Line 132: // Narrow no-break space (U+202F) used by some macOS versions in screenshot filenames

  Line 138:  * filenames depending on the macOS version. This function tries the alternate space

  Line 141:  * @param filePath - The normalized file path to resolve

  Line 149: function getAlternateScreenshotPath(filePath: string): string | undefined {

  Line 150:   const filename = path.basename(filePath)

  Line 152:   const match = filename.match(amPmPattern)

  Line 157:   return filePath.replace(

  Line 164: type FileReadListener = ...
gateway · 2026-06-10 14:32:57
reasoning

I'm looking at the FileReadTool details now, specifically its name and description, along with the BashTool's input schema to understand what I'm working with.

claude-opus-4-8 · 2026-06-10 14:32:57 · ~58 tokens
result
<path>/home/byk/.local/share/opencode/tool-output/tool_eb1f2ff78001B7rMqcWQjOO5qk</path>
<type>file</type>
<content>
225: 
226:   return null
227: }
228: 
229: const inputSchema = lazySchema(() =>
230:   z.strictObject({
231:     file_path: z.string().describe('The absolute path to the file to read'),
232:     offset: semanticNumber(z.number().int().nonnegative().optional()).describe(
233:       'The line number to start reading from. Only provide if the file is too large to read at once',
234:     ),
235:     limit: semanticNumber(z.number().int().positive().optional()).describe(
236:       'The number of lines to read. Only provide if the file is too large to read at once.',
237:     ),
238:     pages: z
239:       .string()
240:       .optional()
241:       .describe(
242:         `Page range for PDF files (e.g., "1-5", "3", "10-20"). Only applicable to PDF files. Maximum ${PDF_MAX_PAGES_PER_READ} pages per request.`,
243:       ),
244:   }),
245: )
246: type InputSchema = ...
result
<path>/home/byk/.local/share/opencode/tool-output/tool_eb1f2ff78001B7rMqcWQjOO5qk</path>
<type>file</type>
<content>
338: 
339: export const FileReadTool = buildTool({
340:   name: FILE_READ_TOOL_NAME,
341:   searchHint: 'read files, images, PDFs, notebooks',
342:   // Output is bounded by maxTokens (validateContentTokens). Persisting to a
343:   // file the model reads back with Read is circular — never persist.
344:   maxResultSizeChars: Infinity,
345:   strict: true,
346:   async description() {
347:     return DESCRIPTION
348:   },
349:   async prompt() {
350:     const limits = getDefaultFileReadingLimits()
351:     const maxSizeInstruction = limits.includeMaxSizeInPrompt
352:       ? `. Files larger than ${formatFileSize(limits.maxSizeBytes)} will return an error; use offset and limit for larger files`
353:       : ''
354:     const offsetInstruction = limits.targetedRangeNudge
355:       ? ...
gateway · 2026-06-10 14:33:02
reasoning

I'm looking for the FILE_READ_TOOL_NAME and DESCRIPTION values by searching through the definitions.

claude-opus-4-8 · 2026-06-10 14:33:02 · ~38 tokens
result
Found 4 matches
/home/byk/.local/share/opencode/tool-output/tool_eb1f2ff78001B7rMqcWQjOO5qk:
  Line 82:   FILE_READ_TOOL_NAME,

  Line 87:   renderPromptTemplate,

  Line 340:   name: FILE_READ_TOOL_NAME,

  Line 357:     return renderPromptTemplate(
gateway · 2026-06-10 14:33:15
reasoning

I need to check the FileReadTool prompt and the BashTool's input schema to understand what FILE_READ_TOOL_NAME and DESCRIPTION are, so I'm looking through the saved files to find the BashTool inputSchema definition.

claude-opus-4-8 · 2026-06-10 14:33:15 · ~76 tokens
result
=== FileReadTool/prompt.ts ===
import { isPDFSupported } from '../../utils/pdfUtils.js'
import { BASH_TOOL_NAME } from '../BashTool/toolName.js'

// Use a string constant for tool names to avoid circular dependencies
export const FILE_READ_TOOL_NAME = 'Read'

export const FILE_UNCHANGED_STUB =
  'File unchanged since last read. The content from the earlier Read tool_result in this conversation is still current — refer to that instead of re-reading.'

export const MAX_LINES_TO_READ = 2000

export const DESCRIPTION = 'Read a file from the local filesystem.'

export const LINE_FORMAT_INSTRUCTION =
  '- Results are returned using cat -n format, with line numbers starting at 1'

export const OFFSET_INSTRUCTION_DEFAULT =
  "- You can optionally specify a line offset and limit (especially handy for long files), but it's recommended to read the whole file by not providing these parameters"

export const OFFSET_INSTRUCTION_TARGETED =
  '- When you already know which part of the file you need, ...
gateway · 2026-06-10 14:33:29
reasoning

I'm looking at the BashTool configuration to find its input schema definition in the saved file.

Now let me find the Bash tool's input schema in the saved BashTool.tsx file.

claude-opus-4-8 · 2026-06-10 14:33:29 · ~63 tokens
result
229:const inputSchema = lazySchema(() =>
230:  z.strictObject({
246:type InputSchema = ReturnType<typeof inputSchema>
260:    z.object({
262:      file: z.object({
--
363:  get inputSchema(): InputSchema {
364:    return inputSchema()
1281:export function isSearchOrReadBashCommand(command: string): {
1364:function isSilentBashCommand(command: string): boolean {
1413:const fullInputSchema = lazySchema(() => z.strictObject({
1414:  command: z.string().describe('The command to execute'),
1415:  timeout: semanticNumber(z.number().optional()).describe(`Optional timeout in milliseconds (max ${getMaxTimeoutMs()})`),
1416:  description: z.string().optional().describe(`Clear, concise description of what this command does in active voice. Never use words like "complex" or "risk" in the description - just describe what it does.
1427:  run_in_background: semanticBoolean(z.boolean().optional()).describe(`Set to true to run this command in the background. Use Read to read the output later.`),
1429: ...
gateway · 2026-06-10 14:33:35
reasoning

I'm looking at the Bash tool's schema and documentation to get the full details on its structure and description, including checking around line 1607 for the name and description fields.

claude-opus-4-8 · 2026-06-10 14:33:35 · ~67 tokens
result
<path>/home/byk/.local/share/opencode/tool-output/tool_eb1f2ff78001B7rMqcWQjOO5qk</path>
<type>file</type>
<content>
1413: const fullInputSchema = lazySchema(() => z.strictObject({
1414:   command: z.string().describe('The command to execute'),
1415:   timeout: semanticNumber(z.number().optional()).describe(`Optional timeout in milliseconds (max ${getMaxTimeoutMs()})`),
1416:   description: z.string().optional().describe(`Clear, concise description of what this command does in active voice. Never use words like "complex" or "risk" in the description - just describe what it does.
1417: 
1418: For simple commands (git, npm, standard CLI tools), keep it brief (5-10 words):
1419: - ls → "List files in current directory"
1420: - git status → "Show working tree status"
1421: - npm install → "Install package dependencies"
1422: 
1423: For commands that are harder to parse at a glance (piped commands, obscure flags, etc.), add enough context to clarify what it does:
1424: - find . -name ...
gateway · 2026-06-10 14:33:48
reasoning

I'm gathering the tool definitions for the false-positive tools by pulling their names and parameter schemas from their prompt and constants files in a single batch request.

Now let me get free-code's false-positive tools (Edit/Write/Grep/Glob) names and params.

claude-opus-4-8 · 2026-06-10 14:33:48 · ~92 tokens
result
===== src/tools/FileEditTool/constants.ts =====
2:export const FILE_EDIT_TOOL_NAME = 'Edit'
===== src/tools/FileWriteTool/prompt.ts =====
3:export const FILE_WRITE_TOOL_NAME = 'Write'
===== src/tools/GlobTool/prompt.ts =====
1:export const GLOB_TOOL_NAME = 'Glob'
===== src/tools/GrepTool/prompt.ts =====
4:export const GREP_TOOL_NAME = 'Grep'
=== schema grep in *.ts files ===
----- src/tools/FileEditTool/FileEditTool.ts -----
----- src/tools/FileWriteTool/FileWriteTool.ts -----
63:    content: z.string().describe('The content to write to the file'),
75:    filePath: z.string().describe('The path to the file that was written'),
76:    content: z.string().describe('The content that was written to the file'),
----- src/tools/GlobTool/GlobTool.ts -----
28:    pattern: z.string().describe('The glob pattern to match files against'),
47:      .describe('Array of file paths that match the pattern'),
50:      .describe('Whether results were truncated (limited to 100 files)'),
----- ...
gateway · 2026-06-10 14:34:07
reasoning

I'm pulling the input schemas for FileEditTool, GlobTool, and GrepTool to check their parameter definitions and constraints.

claude-opus-4-8 · 2026-06-10 14:34:07 · ~46 tokens
result
=== FileEditTool input schema ===
61:  inputSchema,
103:  get inputSchema() {
104:    return inputSchema()
595:} satisfies ToolDef<ReturnType<typeof inputSchema>, FileEditOutput>)
=== GrepTool full input schema (first ~95 lines) ===
    path: z
      .string()
      .optional()
      .describe(
        'File or directory to search in (rg PATH). Defaults to current working directory.',
      ),
    glob: z
      .string()
      .optional()
      .describe(
        'Glob pattern to filter files (e.g. "*.js", "*.{ts,tsx}") - maps to rg --glob',
      ),
    output_mode: z
      .enum(['content', 'files_with_matches', 'count'])
      .optional()
      .describe(
        'Output mode: "content" shows matching lines (supports -A/-B/-C context, -n line numbers, head_limit), "files_with_matches" shows file paths (supports head_limit), "count" shows match counts (supports head_limit). Defaults to "files_with_matches".',
      ),
    '-B': semanticNumber(z.number().optional()).describe(
      ...
gateway · 2026-06-10 14:34:23
reasoning

I notice GrepTool has a pattern parameter too, so I need to check the FileEditTool's input schema. The schema is imported from elsewhere—looks like it's coming from types.ts based on line 61, so let me search for where it's defined.

claude-opus-4-8 · 2026-06-10 14:34:23 · ~83 tokens
result
=== GrepTool pattern param (top of schema) ===
  renderToolUseMessage,
} from './UI.js'

const inputSchema = lazySchema(() =>
  z.strictObject({
    pattern: z
      .string()
      .describe(
        'The regular expression pattern to search for in file contents',
      ),
    path: z
      .string()
      .optional()
=== FileEditTool: where inputSchema defined ===
  FILE_UNEXPECTEDLY_MODIFIED_ERROR,
} from './constants.js'
import { getEditToolDescription } from './prompt.js'
import {
  type FileEditInput,
  type FileEditOutput,
  inputSchema,
  outputSchema,
} from './types.js'
import {
  getToolUseSummary,
=== FileEditTool/types.ts ===
5:// The input schema with optional replace_all
7:  z.strictObject({
8:    file_path: z.string().describe('The absolute path to the file to modify'),
9:    old_string: z.string().describe('The text to replace'),
10:    new_string: z
12:      .describe(
13:        'The text to replace it with (must be different from old_string)',
15:    replace_all: ...
gateway · 2026-06-10 14:34:35
reasoning

I've got the free-code tools covered, though I should double-check FileWriteTool's file_path parameter alongside its content field. Now I need to pull the Cline definitions from the SDK's definitions.ts file, plus review the prompt files for read_file and execute_command to get the full picture.

free-code is complete. Now let me get Cline's definitions. Let me check the SDK definitions and the prompt tool files.

claude-opus-4-8 · 2026-06-10 14:34:35 · ~143 tokens
result
branch=main
=== SDK definitions.ts (read_file + execute_command sections) ===
845 /tmp/opencode/cline_defs.ts
82:	properties: {
85:		commandCount: number;
90:		tool_name: "run_commands",
91:		effective_timeout_ms: properties.effectiveTimeoutMs,
92:		timeout_source: properties.timeoutSource,
93:		command_count: properties.commandCount,
94:		duration_ms: properties.durationMs,
114: * Reads the content of one or more files from the filesystem.
123:		name: "read_files",
124:		description:
125:			"Read the full content of text or image files at the provided absolute paths, or return only an inclusive one-based line range when start_line/end_line are provided. " +
127:			"Returns file contents or error messages for each path. ",
136:				requests = [{ path: validate }];
139:					typeof value === "string" ? { path: value } : value,
146:					typeof file === "string" ? { path: file } : file,
148:			} else if ("file_paths" in validate) {
149:				const filePaths = ...
gateway · 2026-06-10 14:34:46
reasoning

I'm noticing the SDK uses plural forms for these tools—read_files and run_commands—and they validate inputs at runtime using Zod, accepting various parameter names like path, file_paths, paths, command, cmd, and commands. I need to examine how these tools actually expose their input schemas as JSON schemas to understand the parameter structure better.

claude-opus-4-8 · 2026-06-10 14:34:46 · ~128 tokens
result
<path>/tmp/opencode/cline_defs.ts</path>
<type>file</type>
<content>
108: // AgentTool Factory Functions
109: // =============================================================================
110: 
111: /**
112:  * Create the read_files tool
113:  *
114:  * Reads the content of one or more files from the filesystem.
115:  */
116: export function createReadFilesTool(
117: 	executor: FileReadExecutor,
118: 	config: Pick<DefaultToolsConfig, "fileReadTimeoutMs"> = {},
119: ): AgentTool<ReadFilesInput, ToolOperationResult[]> {
120: 	const timeoutMs = config.fileReadTimeoutMs ?? 10000;
121: 
122: 	return createTool<ReadFilesInput, ToolOperationResult[]>({
123: 		name: "read_files",
124: 		description:
125: 			"Read the full content of text or image files at the provided absolute paths, or return only an inclusive one-based line range when start_line/end_line are provided. " +
126: 			"Binary files that are not image and large files are not supported. ...
gateway · 2026-06-10 14:35:04
reasoning

I need to locate the ReadFilesInputSchema and run_commands schema definitions, which are probably in a schemas.ts file within the tools directory.

This SDK uses Zod schemas converted via zodToJsonSchema. Let me find the actual schema definitions and the run_commands schema.

claude-opus-4-8 · 2026-06-10 14:35:04 · ~97 tokens
result
=== run_commands tool definition (lines 267-360) ===
 * Create the run_commands tool
 *
 * Executes shell commands in the project directory.
 */
export function createBashTool(
	executor: BashExecutor,
	config: Pick<DefaultToolsConfig, "cwd" | "bashTimeoutMs"> = {},
): AgentTool<RunCommandsInput, ToolOperationResult[]> {
	const timeoutMs = config.bashTimeoutMs ?? 30000;
	const timeoutSource =
		config.bashTimeoutMs === undefined
			? "default_setting"
			: "configured_setting";
	const cwd = config.cwd ?? process.cwd();

	return createTool<RunCommandsInput, ToolOperationResult[]>({
		name: "run_commands",
		description:
			"Run shell commands from the root of the workspace. " +
			"Use for listing files, checking git status, running builds, executing tests, etc. " +
			"Commands should be properly shell-escaped and targeted to avoid error or timeout. " +
			"For long-running commands, run them in background and redirect output to a tmp file that you can read from ...
gateway · 2026-06-10 14:35:16
result
345 /tmp/opencode/cline_schemas.ts
17:	.describe("The absolute file path of a text file to read content from");
19:export const ReadFileLineRangeSchema = z
21:		start_line: z
27:			.describe(
30:		end_line: z
36:			.describe(
40:	.describe("Optional inclusive one-based file line range");
42:export const ReadFileRequestSchema = z
44:		path: AbsolutePath,
45:		start_line: ReadFileLineRangeSchema.shape.start_line,
46:		end_line: ReadFileLineRangeSchema.shape.end_line,
48:	.describe(
55:export const ReadFilesInputSchema = z.object({
58:		.describe(
59:			"Array of file read requests. Omit start_line/end_line or set them to null to return the full file content boundaries; provide integers to return only that inclusive one-based line range. Prefer this tool over running terminal command to get file content for better performance and reliability.",
66:export const ReadFilesInputUnionSchema = z.union([
72:	z.object({ files: z.array(z.union([AbsolutePath, ReadFileRequestSchema])) ...
gateway · 2026-06-10 14:35:34
reasoning

Looking at the Cline SDK schemas, the canonical input format for file operations uses a files parameter that accepts an array of objects, each containing a file path and optional line range boundaries. The union of these schemas defines what parameters the model can actually work with.

For command execution, the canonical parameter is commands as an array of strings, though the schema also accepts alternative parameter names like command or cmd.

I should also check the classic VS Code extension implementation, which uses a different tool structure with singular parameters like read_file and execute_command — those are the historically well-known Cline tool shapes that users might be familiar with. Let me pull the exact schema definitions from both the SDK and the VS Code extension prompt files to get the precise parameter names and structures.

Let me get the exact schema lines and also Cline's classic VS Code extension tool definitions.

claude-opus-4-8 · 2026-06-10 14:35:34 · ~326 tokens
result
<path>/tmp/opencode/cline_schemas.ts</path>
<type>file</type>
<content>
10: export const INPUT_ARG_CHAR_LIMIT = 6000;
11: 
12: /**
13:  * Schema for read tool input
14:  */
15: const AbsolutePath = z
16: 	.string()
17: 	.describe("The absolute file path of a text file to read content from");
18: 
19: export const ReadFileLineRangeSchema = z
20: 	.object({
21: 		start_line: z
22: 			.number()
23: 			.int()
24: 			.positive()
25: 			.nullable()
26: 			.optional()
27: 			.describe(
28: 				"Optional one-based starting line number to read from; use null or omit for the start of the file",
29: 			),
30: 		end_line: z
31: 			.number()
32: 			.int()
33: 			.positive()
34: 			.nullable()
35: 			.optional()
36: 			.describe(
37: 				"Optional one-based ending line number to read through; use null or omit for the end of the file",
38: 			),
39: 	})
40: 	.describe("Optional inclusive one-based file line range");
41: 
42: export const ReadFileRequestSchema = z
43: 	.object({
44: 		path: ...
gateway · 2026-06-10 14:35:51
reasoning

I need to look at Cline's standard VS Code extension tools—specifically the read_file and execute_command implementations—to understand how they structure their tool specifications and parameters, then check the EditFileInputSchema to catch any edge cases.

Now Cline's classic VS Code extension tool definitions (the well-known XML-style ones):

claude-opus-4-8 · 2026-06-10 14:35:51 · ~120 tokens
result
===== read_file.ts =====
import { ModelFamily } from "@/shared/prompts"
import { ClineDefaultTool } from "@/shared/tools"
import type { ClineToolSpec } from "../spec"
import { TASK_PROGRESS_PARAMETER } from "../types"

const id = ClineDefaultTool.FILE_READ

const READ_FILE_DESCRIPTION =
	"Request to read the contents of a file at the specified path. Use this when you need to examine the contents of an existing file you do not know the contents of, for example to analyze code, review text files, or extract information from configuration files. Returned text lines are prefixed with line labels (e.g. `1 |`, `2 |`). These labels are metadata, not part of the file content. For large files, output is automatically limited to 1000 lines. Use start_line and end_line to read specific sections. Automatically extracts raw text from PDF and DOCX files. May not be suitable for other types of binary files, as it returns the raw content as a string. ...
gateway · 2026-06-10 14:36:05
reasoning

I'm noticing that NATIVE_GPT_5 and GEMINI_3 variants both use ClineDefaultTool.BASH as their tool name, so I need to check what those constant values actually are and look at the shared tools module. I also want to identify the false-positive tools for Cline classic, specifically the write_to_file and replace_in_file implementations with their path and content parameters.

Let me get the ClineDefaultTool enum values and the classic false-positive tools (write/replace/search/list).

claude-opus-4-8 · 2026-06-10 14:36:05 · ~168 tokens
result
=== ClineDefaultTool enum ===
apps/vscode/src/shared/tools.ts
5:export type ClineTool = OpenAITool | AnthropicTool | GoogleTool
9:	ASK = "ask_followup_question",
10:	ATTEMPT = "attempt_completion",
11:	BASH = "execute_command",
12:	FILE_EDIT = "replace_in_file",
13:	FILE_READ = "read_file",
14:	FILE_NEW = "write_to_file",
15:	SEARCH = "search_files",
16:	LIST_FILES = "list_files",
17:	LIST_CODE_DEF = "list_code_definition_names",
18:	BROWSER = "browser_action",
19:	MCP_USE = "use_mcp_tool",
20:	MCP_ACCESS = "access_mcp_resource",
21:	MCP_DOCS = "load_mcp_documentation",
22:	NEW_TASK = "new_task",
23:	PLAN_MODE = "plan_mode_respond",
24:	ACT_MODE = "act_mode_respond",
25:	TODO = "focus_chain",
26:	WEB_FETCH = "web_fetch",
27:	WEB_SEARCH = "web_search",
28:	CONDENSE = "condense",
29:	SUMMARIZE_TASK = "summarize_task",
30:	REPORT_BUG = "report_bug",
31:	NEW_RULE = "new_rule",
32:	APPLY_PATCH = "apply_patch",
33:	GENERATE_EXPLANATION = "generate_explanation",
34:	USE_SKILL = ...
gateway · 2026-06-10 14:36:22
reasoning

So the BASH tool maps to "execute_command" and FILE_READ maps to "read_file", which means in the NATIVE_GPT_5 variant where the name is set to BASH, it resolves to "execute_command". For the classic Cline variant, I'm identifying potential false positives: replace_in_file handles file edits with path and diff parameters, write_to_file creates new files with path and content, and search_files searches across files using a path parameter.

Now I need to grab the exact parameter names from write_to_file, replace_in_file, and search_files to be precise about what the user's asking for.

claude-opus-4-8 · 2026-06-10 14:36:22 · ~201 tokens
result
===== write_to_file.ts =====
25:const id = ClineDefaultTool.FILE_NEW
30:	name: "write_to_file",
35:			name: "path",
41:			name: "content",
54:	name: "write_to_file",
59:			name: "absolutePath",
64:			name: "content",
===== replace_in_file.ts =====
6:const id = ClineDefaultTool.FILE_EDIT
67:	name: "replace_in_file",
72:			name: "path",
78:			name: "diff",
90:	name: "replace_in_file",
95:			name: "absolutePath",
100:			name: "diff",
===== search_files.ts =====
21:const id = ClineDefaultTool.SEARCH
26:	name: "search_files",
31:			name: "path",
37:			name: "regex",
43:			name: "file_pattern",
56:	name: "search_files",
61:			name: "path",
67:			name: "regex",
73:			name: "file_pattern",
===== list_files.ts =====
6:const id = ClineDefaultTool.LIST_FILES
11:	name: "list_files",
16:			name: "path",
23:			name: "recursive",
36:	name: "list_files",
41:			name: "path",
46:			name: "recursive",
gateway · 2026-06-10 14:36:40
reasoning

I'm noticing that some variants like NATIVE_GPT_5 use absolutePath instead of path for their file operations. Now I'm looking at the Gemini CLI tools in the read-file and shell modules—Gemini's ReadFileTool takes an absolute_path parameter while ShellTool uses command.

Cline done. Now Gemini CLI — read-file.ts and shell.ts:

claude-opus-4-8 · 2026-06-10 14:36:40 · ~116 tokens
result
branch=main
===== read-file.ts: name/displayName/description/schema =====
119:          type: ToolErrorType.PATH_NOT_IN_WORKSPACE,
138:          type: result.errorType,
160:      typeof result.llmContent === 'string'
182:      if (typeof llmContent === 'string') {
198:        name: READ_FILE_DISPLAY_NAME,
199:        description: this.getDescription(),
201:        result: { type: 'text', text: result.returnDisplay || '' },
226:      Kind.Read,
227:      READ_FILE_DEFINITION.base.parametersJsonSchema,
gateway · 2026-06-10 14:36:46
reasoning

I need to track down where READ_FILE_DEFINITION is imported from and find its definition in the read-file.ts file.

claude-opus-4-8 · 2026-06-10 14:36:46 · ~43 tokens
result
7:import type { MessageBus } from '../confirmation-bus/message-bus.js';
8:import path from 'node:path';
9:import { makeRelative, shortenPath } from '../utils/paths.js';
10:import {
21:import { ToolErrorType } from './tool-error.js';
22:import { buildFilePathArgsPattern } from '../policy/utils.js';
24:import type { PartListUnion } from '@google/genai';
25:import {
29:import type { Config } from '../config/config.js';
30:import { FileOperation } from '../telemetry/metrics.js';
31:import { getProgrammingLanguage } from '../telemetry/telemetry-utils.js';
32:import { logFileOperation } from '../telemetry/loggers.js';
33:import { FileOperationEvent } from '../telemetry/types.js';
34:import { READ_FILE_TOOL_NAME, READ_FILE_DISPLAY_NAME } from './tool-names.js';
35:import { FileDiscoveryService } from '../services/fileDiscoveryService.js';
36:import { READ_FILE_DEFINITION } from './definitions/coreTools.js';
37:import { resolveToolDeclaration } from './definitions/resolver.js';
38:import ...
gateway · 2026-06-10 14:36:54

The definitions live in definitions/coreTools.js. Let me read that file and the tool names.

claude-opus-4-8 · 2026-06-10 14:36:54 · ~31 tokens
result
289 /tmp/opencode/gem_defs.ts
=== READ_FILE_DEFINITION + SHELL_DEFINITION ===
25:  GLOB_TOOL_NAME,
26:  GREP_TOOL_NAME,
60:  GREP_PARAM_INCLUDE_PATTERN,
61:  GREP_PARAM_EXCLUDE_PATTERN,
62:  GREP_PARAM_NAMES_ONLY,
63:  GREP_PARAM_MAX_MATCHES_PER_FILE,
64:  GREP_PARAM_TOTAL_MAX_MATCHES,
65:  GREP_PARAM_FIXED_STRINGS,
66:  GREP_PARAM_CONTEXT,
67:  GREP_PARAM_AFTER,
68:  GREP_PARAM_BEFORE,
69:  GREP_PARAM_NO_IGNORE,
127:export const READ_FILE_DEFINITION: ToolDefinition = {
134:export const WRITE_FILE_DEFINITION: ToolDefinition = {
141:export const GREP_DEFINITION: ToolDefinition = {
148:export const RIP_GREP_DEFINITION: ToolDefinition = {
162:export const EDIT_DEFINITION: ToolDefinition = {
169:export const GLOB_DEFINITION: ToolDefinition = {
178:    return DEFAULT_LEGACY_SET.list_directory;
180:  overrides: (modelId) => getToolSet(modelId).list_directory,
253:      getToolSet(modelId).run_shell_command(
gateway · 2026-06-10 14:36:59
result
<path>/tmp/opencode/gem_defs.ts</path>
<type>file</type>
<content>
120:   }
121: }
122: 
123: // ============================================================================
124: // TOOL DEFINITIONS (LEGACY EXPORTS)
125: // ============================================================================
126: 
127: export const READ_FILE_DEFINITION: ToolDefinition = {
128:   get base() {
129:     return DEFAULT_LEGACY_SET.read_file;
130:   },
131:   overrides: (modelId) => getToolSet(modelId).read_file,
132: };
133: 
134: export const WRITE_FILE_DEFINITION: ToolDefinition = {
135:   get base() {
136:     return DEFAULT_LEGACY_SET.write_file;
137:   },
138:   overrides: (modelId) => getToolSet(modelId).write_file,
139: };
140: 
141: export const GREP_DEFINITION: ToolDefinition = {
142:   get base() {
143:     return DEFAULT_LEGACY_SET.grep_search;
144:   },
145:   overrides: (modelId) => getToolSet(modelId).grep_search,
146: };
147: 
148: export const RIP_GREP_DEFINITION: ToolDefinition = ...
gateway · 2026-06-10 14:37:12
reasoning

I need to track down where the schema definitions are stored—they're in DEFAULT_LEGACY_SET from another file in the toolsets declarations. I'm looking at the imports in coreTools.ts to find the declarations file and understand how read_file, write_file, grep_search, replace, glob, and run_shell_command are defined.

The actual schemas are in DEFAULT_LEGACY_SET. Let me find the declaration files.

claude-opus-4-8 · 2026-06-10 14:37:12 · ~143 tokens
result
packages/core/src/tools/definitions/__snapshots__
packages/core/src/tools/definitions/__snapshots__/coreToolsModelSnapshots.test.ts.snap
packages/core/src/tools/definitions/base-declarations.ts
packages/core/src/tools/definitions/coreTools.ts
packages/core/src/tools/definitions/coreToolsModelSnapshots.test.ts
packages/core/src/tools/definitions/dynamic-declaration-helpers.ts
packages/core/src/tools/definitions/model-family-sets
packages/core/src/tools/definitions/model-family-sets/default-legacy.ts
packages/core/src/tools/definitions/model-family-sets/gemini-3.ts
packages/core/src/tools/definitions/modelFamilyService.ts
packages/core/src/tools/definitions/resolver.test.ts
packages/core/src/tools/definitions/resolver.ts
packages/core/src/tools/definitions/trackerTools.ts
packages/core/src/tools/definitions/types.ts
gateway · 2026-06-10 14:37:19
result
138 /tmp/opencode/gem_base.ts
=== read_file & run_shell_command declarations ===
46:// -- list_directory --
47:export const LS_TOOL_NAME = 'list_directory';
50:// -- read_file --
51:export const READ_FILE_TOOL_NAME = 'read_file';
55:// -- run_shell_command --
56:export const SHELL_TOOL_NAME = 'run_shell_command';
57:export const SHELL_PARAM_COMMAND = 'command';
gateway · 2026-06-10 14:37:33
reasoning

I see that the actual schema definitions with properties are in default-legacy.ts, not in the base declarations file. Let me check that file instead.

claude-opus-4-8 · 2026-06-10 14:37:33 · ~55 tokens
result
764 /tmp/opencode/gem_legacy.ts
84:  read_file: {
85:    name: READ_FILE_TOOL_NAME,
86:    description: `Reads and returns the content of a specified file. If the file is large, the content will be truncated. The tool's response will clearly indicate if truncation has occurred and will provide details on how to read more of the file using the 'start_line' and 'end_line' parameters. Handles text, images (PNG, JPG, GIF, WEBP, SVG, BMP), audio files (MP3, WAV, AIFF, AAC, OGG, FLAC), and PDF files. For text files, it can read specific line ranges.`,
87:    parametersJsonSchema: {
89:      properties: {
91:          description: 'The path to the file to read.',
95:          description:
101:          description:
107:      required: [PARAM_FILE_PATH],
111:  write_file: {
112:    name: WRITE_FILE_TOOL_NAME,
113:    description: `Writes content to a specified file in the local filesystem. ...
gateway · 2026-06-10 14:37:58
reasoning

I need to check the exact property names for the read_file function—whether it's absolute_path or path—and locate the run_shell_command declaration, which might be dynamically generated through getShellDeclaration rather than statically defined. Let me examine lines 84-135 to get the precise property names and find where run_shell_command is declared.

claude-opus-4-8 · 2026-06-10 14:37:58 · ~124 tokens
result
<path>/tmp/opencode/gem_legacy.ts</path>
<type>file</type>
<content>
84:   read_file: {
85:     name: READ_FILE_TOOL_NAME,
86:     description: `Reads and returns the content of a specified file. If the file is large, the content will be truncated. The tool's response will clearly indicate if truncation has occurred and will provide details on how to read more of the file using the 'start_line' and 'end_line' parameters. Handles text, images (PNG, JPG, GIF, WEBP, SVG, BMP), audio files (MP3, WAV, AIFF, AAC, OGG, FLAC), and PDF files. For text files, it can read specific line ranges.`,
87:     parametersJsonSchema: {
88:       type: 'object',
89:       properties: {
90:         [PARAM_FILE_PATH]: {
91:           description: 'The path to the file to read.',
92:           type: 'string',
93:         },
94:         [READ_FILE_PARAM_START_LINE]: {
95:           description:
96:             'Optional: The 1-based line number to start reading from.',
97:           type: 'integer',
98:       ...
gateway · 2026-06-10 14:38:13
reasoning

I'm looking for several constants defined in base-declarations.ts — PARAM_FILE_PATH, READ_FILE_PARAM_START_LINE, READ_FILE_PARAM_END_LINE, WRITE_FILE_PARAM_CONTENT, and PARAM_PATTERN — and I need to find the run_shell_command declaration which appears to be dynamically generated.

claude-opus-4-8 · 2026-06-10 14:38:13 · ~98 tokens
result
=== base-declarations constants ===
16:export const PARAM_FILE_PATH = 'file_path';
18:export const PARAM_PATTERN = 'pattern';
52:export const READ_FILE_PARAM_START_LINE = 'start_line';
53:export const READ_FILE_PARAM_END_LINE = 'end_line';
57:export const SHELL_PARAM_COMMAND = 'command';
58:export const SHELL_PARAM_IS_BACKGROUND = 'is_background';
62:export const WRITE_FILE_PARAM_CONTENT = 'content';
66:export const EDIT_PARAM_INSTRUCTION = 'instruction';
67:export const EDIT_PARAM_OLD_STRING = 'old_string';
68:export const EDIT_PARAM_NEW_STRING = 'new_string';
69:export const EDIT_PARAM_ALLOW_MULTIPLE = 'allow_multiple';
=== full base-declarations (read-related lines 40-138) ===
export const GREP_PARAM_FIXED_STRINGS = 'fixed_strings';
export const GREP_PARAM_CONTEXT = 'context';
export const GREP_PARAM_AFTER = 'after';
export const GREP_PARAM_BEFORE = 'before';
export const GREP_PARAM_NO_IGNORE = 'no_ignore';

// -- list_directory --
export const LS_TOOL_NAME = ...
gateway · 2026-06-10 14:38:30
reasoning

I'm noticing a discrepancy in the Gemini CLI parameter naming — the current implementation uses file_path, but the user's hypothesis mentioned absolute_path, which was historically used. I should check if there's a gemini-3.ts variant that still uses the older parameter name, and also verify the run_shell_command declaration while I'm at it.

Now the shell declaration (dynamic) and the gemini-3 variant overrides:

claude-opus-4-8 · 2026-06-10 14:38:30 · ~145 tokens
result
=== getShellDeclaration ===
17:  SHELL_TOOL_NAME,
20:  SHELL_PARAM_COMMAND,
34: * Generates the platform-specific description for the shell tool.
45:      - Pagination: Always disable terminal pagination to ensure commands terminate (e.g., use \`git --no-pager\`, \`systemctl --no-pager\`, or set \`PAGER=cat\`).`
53:      Exit Code: Only included if non-zero (command failed).
61:      ? `To run a command in the background, set the \`${SHELL_PARAM_IS_BACKGROUND}\` parameter to true. Do NOT use PowerShell background constructs.`
63:    return `This tool executes a given shell command as \`powershell.exe -NoProfile -Command <command>\`. ${backgroundInstructions}${efficiencyGuidelines}${returnedInfo}`;
66:      ? `To run a command in the background, set the \`${SHELL_PARAM_IS_BACKGROUND}\` parameter to true. Do NOT use \`&\` to background commands.`
68:    return `This tool executes a given shell command as \`bash -c <command>\`. ...
gateway · 2026-06-10 14:38:37
reasoning

I'm checking the Gemini shell tool's parameters and requirements, specifically looking at the run_shell_command function to understand which fields are required and what the exact parameter names are.

claude-opus-4-8 · 2026-06-10 14:38:37 · ~72 tokens
result
<path>/tmp/opencode/gem_dyn.ts</path>
<type>file</type>
<content>
96:     parametersJsonSchema: {
97:       type: 'object',
98:       properties: {
99:         [SHELL_PARAM_COMMAND]: {
100:           type: 'string',
101:           description: getCommandDescription(),
102:         },
103:         [PARAM_DESCRIPTION]: {
104:           type: 'string',
105:           description:
106:             'Brief description of the command for the user. Be specific and concise. Ideally a single sentence. Can be up to 3 sentences for clarity. No line breaks.',
107:         },
108:         [PARAM_DIR_PATH]: {
109:           type: 'string',
110:           description:
111:             '(OPTIONAL) The path of the directory to run the command in. If not provided, the project root directory is used. Must be a directory within the workspace and must already exist.',
112:         },
113:         [SHELL_PARAM_IS_BACKGROUND]: {
114:           type: 'boolean',
115:           description:
116:             ...
gateway · 2026-06-10 14:38:47
result
<path>/tmp/opencode/gem_dyn.ts</path>
<type>file</type>
<content>
155:           : {}),
156:       },
157:       required: [SHELL_PARAM_COMMAND],
158:     },
159:   };
160: }
161: 
162: /**
163:  * Returns the FunctionDeclaration for exiting plan mode.
164:  */
165: export function getExitPlanModeDeclaration(): FunctionDeclaration {
166:   return {
167:     name: EXIT_PLAN_MODE_TOOL_NAME,
168:     description:
169:       'Finalizes the planning phase and transitions to implementation by presenting the plan for formal user approval. You MUST reach an informal agreement with the user in the chat regarding the proposed strategy BEFORE calling this tool. This tool MUST be used to exit Plan Mode before any source code edits can be performed.',
170:     parametersJsonSchema: {
171:       type: 'object',
172:       required: [EXIT_PLAN_PARAM_PLAN_FILENAME],
173:       properties: {
174:         [EXIT_PLAN_PARAM_PLAN_FILENAME]: {
175:           type: 'string',
176:           description: `The ...
gateway · 2026-06-10 14:38:54
reasoning

I'm checking the Gemini shell tool parameters to verify that PARAM_DIR_PATH is set to 'directory' based on what I saw in the coreTools.ts shell description test.

claude-opus-4-8 · 2026-06-10 14:38:54 · ~58 tokens
result
/tmp/opencode/gem_base.ts:17:export const PARAM_DIR_PATH = 'dir_path';
/tmp/opencode/gem_base.ts:23:export const PARAM_DESCRIPTION = 'description';
/tmp/opencode/gem_base.ts:78:export const TODOS_ITEM_PARAM_DESCRIPTION = 'description';
/tmp/opencode/gem_base.ts:112:export const ASK_USER_OPTION_PARAM_DESCRIPTION = 'description';
/tmp/opencode/gem_dyn.ts:22:  PARAM_DIR_PATH,
/tmp/opencode/gem_dyn.ts:108:        [PARAM_DIR_PATH]: {
=== gemini-3 read_file/shell override param check ===
30:  PARAM_FILE_PATH,
93:  read_file: {
99:        [PARAM_FILE_PATH]: {
116:      required: [PARAM_FILE_PATH],
126:        [PARAM_FILE_PATH]: {
136:      required: [PARAM_FILE_PATH, WRITE_FILE_PARAM_CONTENT],
190:      'Searches for a regular expression pattern within file contents. This tool is FAST and optimized, powered by ripgrep. PREFERRED over standard `run_shell_command("grep ...")` due to better performance and automatic output limiting (defaults to 100 matches, but can be increased via ...
gateway · 2026-06-10 14:39:11
reasoning

The shell tool uses dir_path as its directory parameter, not directory. For the Gemini CLI's read_file function, both default-legacy and gemini-3 use file_path, though historically it was called absolute_path. Let me verify the Gemini CLI's edit functionality next.

The replace tool has parameters for file_path, old_string, new_string, instruction, and allow_multiple, plus glob and grep params with pattern and path. Now I need to check OpenHands—their tools might be in the agent-sdk or under openhands/tools, so I'm searching the repo for tool definitions like ChatCompletionToolParam or functions like execute_bash and str_replace_editor.

Gemini CLI done (note: read_file param is file_path, shell dir param is dir_path). Now OpenHands — let me locate its tool definitions.

claude-opus-4-8 · 2026-06-10 14:39:11 · ~270 tokens
result
branch=main
=== search for tool definition terms ===
.agents/skills/custom-codereview-guide.md
.devcontainer/README.md
README.md
containers/README.md
containers/dev/README.md
enterprise/README.md
enterprise/doc/architecture/README.md
enterprise/enterprise_local/README.md
enterprise/integrations/bitbucket/bitbucket_view.py
enterprise/integrations/bitbucket_data_center/bitbucket_dc_view.py
enterprise/integrations/github/github_view.py
enterprise/integrations/gitlab/gitlab_view.py
enterprise/integrations/jira/jira_view.py
enterprise/integrations/jira_dc/jira_dc_view.py
enterprise/integrations/slack/slack_view.py
enterprise/migrations/README.md
enterprise/server/maintenance_task_processor/README.md
enterprise/server/routes/readiness.py
enterprise/server/sharing/README.md
enterprise/sync/README.md
enterprise/tests/unit/integrations/bitbucket/test_bitbucket_view.py
enterprise/tests/unit/integrations/bitbucket_data_center/test_bitbucket_dc_view.py
enterprise/tests/unit/integrations/github/tes...
gateway · 2026-06-10 14:39:33
reasoning

The OpenHands repository structure has shifted — tool definitions are no longer stored directly in the main repo but are imported from the separate agent-sdk package instead. I need to track down where the actual tools are defined, likely checking the skills directory, documentation files, and the All-Hands-AI/agent-sdk repository.

OpenHands moved tool definitions to a separate SDK. Let me check both the main repo's tool docs and the agent-sdk repo.

claude-opus-4-8 · 2026-06-10 14:39:33 · ~156 tokens
result
=== OpenHands skills/default-tools.md (first part) ===
---
# This is a repo microagent that is always activated
# to include necessary default tools implemented with MCP
name: default-tools
type: repo
version: 1.0.0
agent: CodeActAgent
mcp_tools:
  stdio_servers:
    - name: "fetch"
      command: "uvx"
      args: ["mcp-server-fetch"]
# We leave the body empty because MCP tools will automatically add the
# tool description for LLMs in tool calls, so there's no need to add extra descriptions.
---
=== look for agent-sdk repos ===
OpenHands/software-agent-sdk | A clean, modular SDK for building AI agents with OpenHands V1.
{"message":"Not Found","documentation_url":"https://docs.github.com/rest/repos/repos#get-a-repository","status":"404"}gh: Not Found (HTTP 404)
gateway · 2026-06-10 14:39:41
reasoning

I need to check the OpenHands/software-agent-sdk repository for the tool definitions since the org was renamed from All-Hands-AI. Let me look for where BashTool, ExecuteBashAction, FileEditorTool and the other tools are defined.

OpenHands V1 tools live in OpenHands/software-agent-sdk. Let me find the tool definitions there.

claude-opus-4-8 · 2026-06-10 14:39:41 · ~114 tokens
result
branch=main
1487 /tmp/opencode/sdk_tree.txt
examples/01_standalone_sdk/02_custom_tools.py
examples/01_standalone_sdk/06_interactive_terminal_w_reasoning.py
examples/01_standalone_sdk/41_task_tool_set.py
examples/01_standalone_sdk/45_parallel_tool_execution.py
examples/01_standalone_sdk/49_switch_llm_tool.py
examples/01_standalone_sdk/53_client_defined_tools.py
examples/02_remote_agent_server/06_custom_tool/custom_tools/__init__.py
examples/02_remote_agent_server/06_custom_tool/custom_tools/log_data.py
examples/02_remote_agent_server/06_custom_tool/main.py
examples/02_remote_agent_server/14_client_defined_tools.py
examples/04_llm_specific_tools/01_gpt5_apply_patch_preset.py
examples/04_llm_specific_tools/02_gemini_file_tools.py
openhands-agent-server/openhands/agent_server/bash_router.py
openhands-agent-server/openhands/agent_server/bash_service.py
openhands-agent-server/openhands/agent_server/tool_preload_service.py
openhands-agent-server/openhands/agent_server/tool_router.py
openhands...
gateway · 2026-06-10 14:39:46
result
openhands-tools/openhands/tools/file_editor/__init__.py
openhands-tools/openhands/tools/file_editor/definition.py
openhands-tools/openhands/tools/file_editor/utils/__init__.py
openhands-tools/openhands/tools/gemini/read_file/__init__.py
openhands-tools/openhands/tools/gemini/read_file/definition.py
openhands-tools/openhands/tools/glob/__init__.py
openhands-tools/openhands/tools/glob/definition.py
openhands-tools/openhands/tools/grep/__init__.py
openhands-tools/openhands/tools/grep/definition.py
openhands-tools/openhands/tools/planning_file_editor/__init__.py
openhands-tools/openhands/tools/planning_file_editor/definition.py
openhands-tools/openhands/tools/task_tracker/__init__.py
openhands-tools/openhands/tools/task_tracker/definition.py
openhands-tools/openhands/tools/terminal/__init__.py
openhands-tools/openhands/tools/terminal/definition.py
openhands-tools/openhands/tools/terminal/terminal/__init__.py
openhands-tools/openhands/tools/terminal/utils/__init__.py
gateway · 2026-06-10 14:39:53
reasoning

I'm looking at the OpenHands tools available—terminal, file_editor, gemini/read_file, glob, and grep—and I need to examine the definition files for the terminal, file_editor, and gemini/read_file tools to understand how they work.

claude-opus-4-8 · 2026-06-10 14:39:53 · ~81 tokens
result
############# terminal/definition.py #############
1:"""Execute shell commands in a persistent terminal session."""
8:from pydantic import Field
23:    register_tool,
30:from openhands.tools.terminal.descriptions import (
37:class TerminalAction(Action):
38:    """Schema for terminal command execution."""
40:    command: str = Field(
41:        description=(
42:            "The shell command to execute. Can be empty string to view"
44:            " special key name when `is_input` is True: `C-c` (Ctrl+C),"
48:            " `BS` (Backspace), `ENTER`. You can only execute one command"
50:            " in the tool description when chaining commands."
53:    is_input: bool = Field(
55:        description="If True, the command is an input to the running process. If False, the command is executed in the terminal session. Default is False.",  # noqa
57:    timeout: float | None = Field(
60:        description=f"Optional. Sets a maximum time limit (in seconds) for running the command. ...
gateway · 2026-06-10 14:40:07
reasoning

I need to find the TerminalTool class and check what name it's registered under, along with its description.

claude-opus-4-8 · 2026-06-10 14:40:07 · ~41 tokens
result
<path>/tmp/opencode/oh_term.py</path>
<type>file</type>
<content>
219: class TerminalTool(ToolDefinition[TerminalAction, TerminalObservation]):
220:     """A ToolDefinition subclass that automatically initializes a TerminalExecutor with auto-detection."""  # noqa: E501
221: 
222:     def declared_resources(self, action: Action) -> DeclaredResources:  # noqa: ARG002
223:         # When using the tmux backend, TmuxPanePool handles concurrency
224:         # internally via pane-level isolation — opt out of framework
225:         # serialization so parallel calls are allowed.
226:         # When using the subprocess backend there is only a single
227:         # session, so we declare a resource key to serialize terminal
228:         # calls against each other without blocking unrelated tools.
229:         if getattr(self.executor, "is_pooled", False):
230:             return DeclaredResources(keys=(), declared=True)
231:         return DeclaredResources(keys=("terminal:session",), ...
gateway · 2026-06-10 14:40:10
result
<path>/tmp/opencode/oh_term.py</path>
<type>file</type>
<content>
288:                 observation_type=TerminalObservation,
289:                 description=tool_description,
290:                 annotations=ToolAnnotations(
291:                     title="terminal",
292:                     readOnlyHint=False,
293:                     destructiveHint=True,
294:                     idempotentHint=False,
295:                     openWorldHint=True,
296:                 ),
297:                 executor=executor,
298:             )
299:         ]
300: 
301: 
302: # Automatically register the tool when this module is imported
303: register_tool(TerminalTool.name, TerminalTool)

(End of file - total 303 lines)
</content>
gateway · 2026-06-10 14:40:32
reasoning

I'm trying to figure out where TerminalTool.name comes from — it's being passed to register_tool(), so it must be a class attribute defined somewhere in the file. Let me check the top of the file to see if there's a name attribute or if it's inherited from a base class like ToolDefinition.

claude-opus-4-8 · 2026-06-10 14:40:32 · ~103 tokens
result
=== terminal __init__.py ===
# Core tool interface
from openhands.tools.terminal.definition import (
    TerminalAction,
    TerminalObservation,
    TerminalTool,
)
from openhands.tools.terminal.impl import TerminalExecutor

# Terminal session architecture - import from sessions package
from openhands.tools.terminal.terminal import (
    TerminalCommandStatus,
    TerminalSession,
    create_terminal_session,
)


__all__ = [
    # === Core Tool Interface ===
    "TerminalTool",
    "TerminalAction",
    "TerminalObservation",
    "TerminalExecutor",
    # === Terminal Session Architecture ===
    "TerminalSession",
    "TerminalCommandStatus",
    "create_terminal_session",
]
=== grep name in terminal/definition.py top ===
from openhands.tools.terminal.descriptions import (
    UNIX_TOOL_DESCRIPTION,
    WINDOWS_TOOL_DESCRIPTION,
)
from openhands.tools.terminal.metadata import CmdOutputMetadata


class TerminalAction(Action):
    """Schema for terminal command execution."""

    ...
gateway · 2026-06-10 14:40:50
reasoning

I'm tracing through how the tool name gets derived from the class name. TerminalTool gets converted to snake_case as "terminal_tool", then the "_tool" suffix is stripped, leaving "terminal" as the final tool name.

I should verify this logic applies consistently across other tools like FileEditorTool which would become "file_editor". Now I need to check the actual definitions for file_editor and the Gemini read_file tool to understand their action schemas and parameters.

Key finding: OpenHands derives tool names via _camel_to_snake(cls.__name__).removesuffix("_tool"), so TerminalToolterminal. Now the file_editor and gemini read_file tools:

claude-opus-4-8 · 2026-06-10 14:40:50 · ~226 tokens
result
############# file_editor/definition.py #############
4:from pathlib import Path
5:from typing import TYPE_CHECKING, Literal
7:from pydantic import Field, PrivateAttr
21:    register_tool,
26:CommandLiteral = Literal["view", "create", "str_replace", "insert", "undo_edit"]
29:class FileEditorAction(Action):
32:    command: CommandLiteral = Field(
33:        description="The commands to run. Allowed options are: `view`, `create`, "
34:        "`str_replace`, `insert`, `undo_edit`."
36:    path: str = Field(description="Absolute path to file or directory.")
37:    file_text: str | None = Field(
39:        description="Required parameter of `create` command, with the content of "
42:    old_str: str | None = Field(
44:        description="Required parameter of `str_replace` command containing the "
45:        "string in `path` to replace.",
47:    new_str: str | None = Field(
49:        description="Optional parameter of `str_replace` command containing the "
51:        "of `insert` ...
gateway · 2026-06-10 14:41:06
reasoning

I need to verify how the FileEditorTool is registered in OpenHands, since it's a dual-purpose tool that can both read files via the view command and write/edit them. Let me check the registration details in the configuration files.

claude-opus-4-8 · 2026-06-10 14:41:06 · ~82 tokens
result
21:    register_tool,
33:        description="The commands to run. Allowed options are: `view`, `create`, "
36:    path: str = Field(description="Absolute path to file or directory.")
39:        description="Required parameter of `create` command, with the content of "
44:        description="Required parameter of `str_replace` command containing the "
49:        description="Optional parameter of `str_replace` command containing the "
56:        description="Required parameter of `insert` command. The `new_str` will "
61:        description="Optional parameter of `view` command when `path` points to a "
73:        description=(
79:    path: str | None = Field(default=None, description="The file path that was edited.")
82:        description="Indicates if the file previously existed. If not, it was created.",
85:        default=None, description="The content of the file before the edit."
88:        default=None, description="The content of the file after the ...
gateway · 2026-06-10 14:41:11
reasoning

I'm converting the class name FileEditorTool to snake_case to get file_editor_tool, then stripping the _tool suffix to arrive at file_editor as the tool name. Now I need to check the tool description section to pull out the opening sentence.

claude-opus-4-8 · 2026-06-10 14:41:11 · ~88 tokens
result
<path>/tmp/opencode/oh_fe.py</path>
<type>file</type>
<content>
160: TOOL_DESCRIPTION = """Custom editing tool for viewing, creating and editing files in plain-text format
161: * State is persistent across command calls and discussions with the user
162: * If `path` is a text file, `view` displays the result of applying `cat -n`. If `path` is a directory, `view` lists non-hidden files and directories up to 2 levels deep
163: * The `create` command cannot be used if the specified `path` already exists as a file
164: * If a `command` generates a long output, it will be truncated and marked with `<response clipped>`
165: * The `undo_edit` command will revert the last edit made to the file at `path`
166: * This tool can be used for creating and editing files in plain-text format.
167: 
168: 
169: Before using this tool:
170: 1. Use the view tool to understand the file's contents and context
171: 2. ...
gateway · 2026-06-10 14:41:21
reasoning

Looking at the Gemini read_file definition to understand its structure, then checking for any glob or grep patterns that might cause false positives.

Now OpenHands' Gemini-specific dedicated read_file tool + glob/grep:

claude-opus-4-8 · 2026-06-10 14:41:21 · ~78 tokens
result
############# gemini/read_file/definition.py #############
4:from pathlib import Path
7:from pydantic import Field
16:    register_tool,
24:class ReadFileAction(Action):
27:    file_path: str = Field(description="The path to the file to read.")
28:    offset: int | None = Field(
29:        default=None,
30:        ge=0,
31:        description=(
36:    limit: int | None = Field(
37:        default=None,
38:        ge=1,
39:        description=(
41:            "Use with 'offset' to paginate through large files."
46:class ReadFileObservation(Observation):
49:    file_path: str = Field(description="The file path that was read.")
50:    file_content: str = Field(default="", description="The content read from the file.")
51:    is_truncated: bool = Field(
52:        default=False,
53:        description="Whether the content was truncated due to size limits.",
55:    lines_shown: tuple[int, int] | None = Field(
56:        default=None,
57:        description=(
61:    total_lines: int | None ...
gateway · 2026-06-10 14:41:39
reasoning

I'm trying to verify the correct tool naming for OpenHands' gemini ReadFileAction—checking whether the class is ReadFileTool with a registered name of read_file, and I need to confirm this by looking at the actual class definition and registration.

claude-opus-4-8 · 2026-06-10 14:41:39 · ~89 tokens
result
16:    register_tool,
109:class ReadFileTool(ToolDefinition[ReadFileAction, ReadFileObservation]):
165:register_tool(ReadFileTool.name, ReadFileTool)
gateway · 2026-06-10 14:41:59
reasoning

I'm tracing through how the tool names get converted across different systems—the ReadFileTool becomes read_file_tool in the Gemini format, then read_file as the actual function name with file_path as the parameter. Let me verify that OpenHands' to_openai_tool method correctly uses self.name for the function name, and I should check whether the terminal tool has any name overrides that might complicate things.

So my confirmed tool names are terminal, file_editor, read_file, glob, and grep. I have the key false positives identified—file_editor is the main one to watch. Let me quickly verify the exact parameters for the free-code FileWriteTool to make sure I have content and file_path correct.

Let me quickly confirm free-code's Write tool params and OpenHands apply_patch for completeness.

claude-opus-4-8 · 2026-06-10 14:41:59 · ~281 tokens
result
=== free-code FileWriteTool schema ===
56:const inputSchema = lazySchema(() =>
57:  z.strictObject({
58:    file_path: z
60:      .describe(
63:    content: z.string().describe('The content to write to the file'),
66:type InputSchema = ReturnType<typeof inputSchema>
69:  z.object({
72:      .describe(
75:    filePath: z.string().describe('The path to the file that was written'),
76:    content: z.string().describe('The content that was written to the file'),
79:      .describe('Diff patch showing the changes'),
83:      .describe(
gateway · 2026-06-10 14:42:10
reasoning

I'm compiling the report now, organizing the data by agent with their exact strings and source URLs. I need to track down the repository branches and API references to ensure I have the correct source information for each entry.

I have everything I need. Let me confirm free-code's default branch for accurate source URLs.

claude-opus-4-8 · 2026-06-10 14:42:10 · ~112 tokens
result
paoloanzn/free-code -> main
cline/cline -> main
OpenHands/software-agent-sdk -> main
google-gemini/gemini-cli -> main
gateway · 2026-06-10 14:43:43
reasoning

Now I'm compiling the comprehensive report with exact details for each agent, starting with the free-code tool and its read functionality with the file_path parameter. Grep also has additional parameters like type, head_limit, offset, and multiline. Now looking at Cline's implementation, which has two different surfaces: the classic VS Code extension uses XML-based tool specs with read_file and execute_command, while the newer SDK uses a plural naming convention with read_files and run_commands that accept arrays of file paths and command strings respectively.

OpenHands takes a different approach where file reading is integrated into the file_editor tool via a "view" command rather than a standalone read operation, though there's a Gemini-specific variant that does have a dedicated read_file tool. The terminal tool handles command execution with parameters for input, timeout, and reset behavior. ...

Research complete. Here are the concrete findings for all agents, with exact strings and source URLs.


1. free-code (paoloanzn/free-code) — Claude Code clone

This is a near-verbatim Claude Code reimplementation; tool names/params are capitalized exactly like Claude Code.

📖 File-reading tool

  • name: Read (export const FILE_READ_TOOL_NAME = 'Read')
  • schema: z.strictObject({...})
  • params:
    • file_pathstring, required"The absolute path to the file to read"
    • offsetnumber (int, ≥0), optional
    • limitnumber (int, >0), optional
    • pagesstring, optional (PDF page range)
  • description: 'Read a file from the local filesystem.' (long form: "Reads a file from the local filesystem. You can access any file directly by using this tool...")
  • source: src/tools/FileReadTool/FileReadTool.ts (schema L229–244), src/tools/FileReadTool/prompt.ts (name+desc)
    • https://github.com/paoloanzn/free-code/blob/main/src/tools/FileReadTool/FileReadTool.ts

🖥️ Shell tool

  • name: Bash (export const BASH_TOOL_NAME = 'Bash')
  • schema: z.strictObject({...})
  • params:
    • commandstring (not array), required"The command to execute"
    • timeoutnumber, optional (ms)
    • descriptionstring, optional
    • run_in_backgroundboolean, optional
    • dangerouslyDisableSandboxboolean, optional
    • (_simulatedSedEdit — internal, stripped from model-facing schema)
  • source: src/tools/BashTool/BashTool.tsx (schema L1413), src/tools/BashTool/toolName.ts

⚠️ False positives

| name | params | |---|---| | Edit | file_path, old_string, new_string, replace_all | | Write | file_path, content | | Glob | pattern, path | | Grep | pattern, path, glob, output_mode, -A/-B/-C, context, -n, -i, type, head_limit, offset, multiline |


2. Cline (cline/cline) — TWO distinct tool surfaces

A. ...

claude-opus-4-8 · 2026-06-10 14:43:43 · ~4.5K tokens

Distillations (8)

Gen 0 2026-06-10 20:42:06 · 618 tokens

<observations> Date: June 10, 2026  * 🟡 (14:43) Research completed on file-read and shell tool specs across 5 agents: free-code, Cline (classic + SDK), OpenHands, Gemini CLI, Claude Code.  * 🟡 (14:43) **free-code (`paoloanzn/free-code`)** — Read tool: name=`Read` (constant `FILE_READ_TOOL_NAME = 'Read'`), params: `file_path` (string, required), `offset` (int ≥0, optional), `limit` (int >0, opti…

Gen 0 2026-06-10 20:36:36 · 678 tokens

<observations> Date: June 10, 2026  * 🟡 (14:40) OpenHands `oh_term.py` (303 lines): `TerminalTool` registered at line 303 via `register_tool(TerminalTool.name, TerminalTool)`; `ToolAnnotations` set as `title="terminal"`, `readOnlyHint=False`, `destructiveHint=True`, `idempotentHint=False`, `openWorldHint=True` * 🟡 (14:40) OpenHands `tool.py` line 241: tool name derived via `_camel_to_snake(cls.…

Gen 0 2026-06-10 20:33:06 · 906 tokens

<observations> Date: June 10, 2026  * 🟡 (14:37) Gemini CLI `gem_legacy.ts` (764 lines): `read_file` definition at lines 84-109; `write_file` at lines 111-131; `grep_search` at lines 133-176; `grep_search_ripgrep` at lines 180-257; `glob` at lines 261+ * 🟡 (14:38) Gemini CLI `read_file` tool params (from `gem_legacy.ts` lines 84-109): required param `[PARAM_FILE_PATH]` = `'file_path'` (type: str…

Gen 0 2026-06-10 20:30:36 · 525 tokens

<observations> Date: June 10, 2026  * 🟡 (14:36) Cline tool file locations confirmed: `write_to_file.ts`, `replace_in_file.ts`, `search_files.ts`, `list_files.ts` in Cline SDK tools directory * 🟡 (14:36) Cline `write_to_file` tool: `ClineDefaultTool.FILE_NEW`; base variant params: `path`, `content`; NATIVE_GPT_5/GEMINI_3 variant params: `absolutePath`, `content` * 🟡 (14:36) Cline `replace_in_fi…

Gen 0 2026-06-10 20:28:05 · 1130 tokens

<observations> Date: June 10, 2026  * 🟡 (14:34) free-code tool names confirmed: `FileEditTool` → `'Edit'` (from `FILE_EDIT_TOOL_NAME` in `src/tools/FileEditTool/constants.ts`); `FileWriteTool` → `'Write'` (from `FILE_WRITE_TOOL_NAME` in `src/tools/FileWriteTool/prompt.ts`); `GlobTool` → `'Glob'`; `GrepTool` → `'Grep'` * 🟡 (14:34) free-code `FileEditTool` input schema (from `src/tools/FileEditTo…

Gen 0 2026-06-10 20:25:35 · 1141 tokens

<observations> Date: June 10, 2026  * 🟡 (14:31) free-code repo `src/tools/` directory enumerated — tool subdirectories found: `AgentTool`, `AskUserQuestionTool`, `BashTool`, `BriefTool`, `ConfigTool`, `EnterPlanModeTool`, `EnterWorktreeTool`, `ExitPlanModeTool`, `ExitWorktreeTool`, `FileEditTool`, `FileReadTool`, `FileWriteTool`, `GlobTool`, `GrepTool`, `LSPTool`, `ListMcpResourcesTool`, `MCPToo…

Gen 0 2026-06-10 20:23:24 · 597 tokens

Date: June 10, 2026  * 🟡 (14:31) Tool search results returned for free-code repo — key tool-related files identified: `src/Tool.ts`, `src/QueryEngine.ts`, `src/Task.ts`; no dedicated tools subdirectory found at top level * 🟡 (14:31) Tool search results returned for Cline repo — key tool-related files identified: `apps/cli/src/runtime/tools.ts`, `apps/cli/src/runtime/tool-policies.ts`, `apps/vsc…

Gen 0 2026-06-10 19:26:43 · 284 tokens

<observations> Date: June 10, 2026  * 🔴 (14:31) User is designing a heuristic to dynamically identify two kinds of agent tools from JSON-schema definitions (without hardcoding tool names): (1) a "read a file" tool, and (2) a "run a shell command" tool. * 🔴 (14:31) User wants ACTUAL tool definitions from several coding agents to survey variety of names/params — "I want to see how much the names …