#11453: fix: apply normalizeToolName() at all tool lookup points
gateway
agents
stale
size: S
Cluster:
Error Handling in Agent Tools
## Summary
Apply `normalizeToolName()` consistently at tool dispatch entry points to handle model-generated tool names with leading/trailing whitespace or unexpected casing. Fixes #11441.
## Problem
When a model outputs a tool call with leading/trailing whitespace in the tool name (e.g., `" exec"` instead of `"exec"`), OpenClaw fails to find the tool and returns "Tool not found". The existing `normalizeToolName()` function already handles `.trim()` + `.toLowerCase()` + alias resolution, but was not applied at all lookup points.
## Changes
- **`src/gateway/tools-invoke-http.ts`**: Replace bare `.trim()` with `normalizeToolName()` for the HTTP tools/invoke endpoint — this also adds alias resolution (`bash` → `exec`) and case normalization that `.trim()` alone misses.
- **`src/auto-reply/reply/get-reply-inline-actions.ts`**: Normalize `dispatch.toolName` before tool lookup in skill command dispatch.
- **`src/agents/tool-policy.normalize-tool-name.test.ts`**: Add test coverage for `normalizeToolName()` edge cases — whitespace trimming, case normalization, alias resolution, and empty input handling.
## Upstream note
The core model→tool dispatch in `@mariozechner/pi-agent-core` (`agent-loop.js` `executeToolCalls`) also uses strict `===` equality without trimming:
```js
const tool = tools?.find((t) => t.name === toolCall.name);
```
Fixing that lookup upstream would fully resolve the issue for all model-generated tool calls. This PR addresses the OpenClaw-controlled dispatch points.
## Testing
- [x] New unit tests for `normalizeToolName()` covering whitespace, casing, aliases, empty input
- [x] AI-assisted (OpenClaw agent + Claude Opus 4.6); changes reviewed and understood
- [x] CI: `pnpm build && pnpm check && pnpm test`
<!-- greptile_comment -->
<h2>Greptile Overview</h2>
<h3>Greptile Summary</h3>
This PR makes tool dispatch more tolerant of model-generated tool names by applying `normalizeToolName()` (trim + lowercase + alias resolution) at additional entry points:
- `/tools/invoke` HTTP handler now normalizes `body.tool` before policy checks and lookup.
- Inline skill command tool dispatch now normalizes `dispatch.toolName` before searching the available tool list.
- Adds Vitest coverage for `normalizeToolName()` behavior around whitespace, casing, aliases, and empty input.
Overall this improves resilience to minor formatting differences in tool call names, but care is needed to ensure alias normalization doesn’t break lookups when any tools are registered under an aliased (non-canonical) name.
<h3>Confidence Score: 4/5</h3>
- This PR is likely safe to merge, with one correctness check needed around alias vs canonical tool names in HTTP tool invocation.
- Changes are small and targeted (normalizing tool names at dispatch boundaries plus unit tests). The main remaining risk is behavior change when callers send an alias (e.g. "bash") but the actual registered tool name is the alias rather than the canonical name, which would cause a new 404 until lookup/registration is made consistent.
- src/gateway/tools-invoke-http.ts
<!-- greptile_other_comments_section -->
<sub>(2/5) Greptile learns from your feedback when you react with thumbs up/down!</sub>
**Context used:**
- Context from `dashboard` - CLAUDE.md ([source](https://app.greptile.com/review/custom-context?memory=fd949e91-5c3a-4ab5-90a1-cbe184fd6ce8))
- Context from `dashboard` - AGENTS.md ([source](https://app.greptile.com/review/custom-context?memory=0d0c8278-ef8e-4d6c-ab21-f5527e322f13))
<!-- /greptile_comment -->
Most Similar PRs
#21166: fix(agents): sanitize tool names in session transcript repair (#8595)
by dinakars777 · 2026-02-19
81.6%
#19024: fix: Fix normalise toolid
by chetaniitbhilai · 2026-02-17
80.5%
#4964: fix: strip null-valued optional parameters from tool calls for prov...
by umut-polat · 2026-01-30
80.2%
#19094: Fix empty tool_call_id and function names in provider transcript pa...
by yxshee · 2026-02-17
79.6%
#11274: fix(tools): truncate overly long tool names for API compatibility
by avirweb · 2026-02-07
79.4%
#10232: Fix: Add anthropic mode for tool call ID sanitization
by StreetJammer · 2026-02-06
78.5%
#19394: fix(agents): normalize tool call arguments dropped to {} (#19261)
by DevvGwardo · 2026-02-17
78.4%
#13831: fix(agents): include Anthropic in tool call ID sanitization
by lailoo · 2026-02-11
78.3%
#8345: fix: prevent synthetic error repair from creating tool_result for d...
by vishaltandale00 · 2026-02-03
77.9%
#21873: fix: sanitize Bedrock toolUse.name in conversation history
by shan-lvr · 2026-02-20
77.7%