701, Chandak Chambers, Andheri Kurla Road, Mumbai 400093
August 1, 2026

Preventing One Tool Name From Covering Several Incompatible Actions

Conceptual illustration contrasting observation, a waiting request and a closed commitment through a lens, envelope and clasp.

Split a broad tool when its action parameter changes what the caller is allowed to do, what state can change, or what a successful result means. A tool that checks availability, creates a booking request and commits a booking covers three different promises. Separate contracts make those promises explicit. They do not, by themselves, enforce authorization or prove that an AI assistant will select the right operation.

The useful boundary is the effect of the action, not the number of parameters. Several filters for the same read-only search can belong in one contract. A switch that turns a lookup into a reservation deserves a different examination, even if both branches accept the same slot identifier.

A fictional scheduler with three different promises

Illustrative fictional use case: a service-booking site has one available slot, S1. Its broad tool, manage_booking, accepts an action value of availability, request or commit. The business wants assistants to answer availability questions without accidentally reserving the slot. A request should begin a booking workflow, not complete it. Only a confirmed, permitted commitment should remove the slot from availability.

A contract is the defined combination of inputs, outputs, errors and effects. Here, the distinction between request initiation and commitment is material: creating a pending request is already a write, but it is not yet a booking. Describing both as “booking successful” would conceal the state that the caller needs to report.

  • Read: manage_booking({“action”:”availability”,”slot_id”:”S1″}) returns whether S1 is available. It changes no state and checks the simulated read permission.
  • Request initiation: manage_booking({“action”:”request”,”slot_id”:”S1″}) creates pending request R1, leaves S1 available and returns booking_created:false. It checks the separate request permission.
  • Commit: manage_booking({“action”:”commit”,”request_id”:”R1″,”confirmed”:true}) requires pending R1 and the commit permission. It marks R1 committed, creates booking B1 and makes S1 unavailable.

The proposed decomposition is get_availability({“slot_id”:”S1″}), request_booking({“slot_id”:”S1″}) and commit_booking({“request_id”:”R1″,”confirmed”:true}). Each operation retains its own input requirements, permission check and result. The split removes the action selector from the arguments. It does not remove the need to implement the checks.

What the completed local comparison tested

Contract fixture v1.0.0 was run on 17 October 2026 using Python 3.12.14 and its standard library. Before implementation, its inputs and literal expected responses, permission outcomes and complete state transitions were recorded. A separate evaluator compared the actual results with those expectations. This was a local deterministic simulation, not a WebMCP browser integration, an LLM session or a customer deployment. The permission booleans were test inputs, not real authentication or a security assessment.

The starting state contained available:true, no requests and no bookings. Successful, denied and unconfirmed commit cases instead started with pending R1 for S1 and no booking; the missing-request case retained the empty starting state. Each case received its own state copy. The successful request was expected to add only pending R1; the successful commit was expected to set available:false, mark R1 committed and add B1. Every rejected call was expected to leave its entire starting state unchanged.

Twelve matched situations were exercised against both designs: allowed and denied reads, allowed and denied requests, allowed and denied commits, an unconfirmed commit, a commit without a pending request, a numeric slot identifier, a missing slot identifier, a confirmation field added to a read and a string instead of a boolean confirmation. The same operation-specific validation and domain logic served both designs. This comparison did not handicap the broad tool with weaker authorization.

Six additional cases tested the differences in dispatch. The broad tool rejected a missing action, the unsupported action reserve, a list containing availability and commit, and a numeric action. The split design rejected the unknown name reserve_booking and an action field attached to get_availability. These were contract-specific cases, not matched evidence that one design had a better success rate.

All 30 normal cases matched their full expected response and state in each of two fresh command-line runs. The 12 matched situations had equivalent outcomes across the broad and split designs. Replaying the fixture produced identical result records. These observations establish consistency for the declared cases, not an exhaustive correctness rate or improved assistant selection.

Keep dispatch errors separate from permission failures

The broad contract returned MISSING_ACTION when action was absent, UNSUPPORTED_ACTION for reserve, AMBIGUOUS_ACTION for the two-action list and INVALID_ACTION for a numeric selector. None of those cases reached a permission check. Defaulting an absent action to a write would have changed the meaning of an incomplete call.

After a valid operation was selected, missing fields returned MISSING_INPUT, extra fields returned UNEXPECTED_INPUT and wrong types returned INVALID_INPUT. A valid call with the relevant permission set to false returned PERMISSION_DENIED. An allowed commit with confirmed:false returned CONFIRMATION_REQUIRED; one without pending R1 returned REQUEST_NOT_FOUND. The evaluator checked both the error and unchanged state. An error message alone would not have detected a write followed by a misleading failure response.

The codes above belong to this synthetic application contract. The WebMCP draft distinguishes platform-defined execution failures from failures that tool authors return in response JSON. The inspected 16 October 2026 Community Group draft is not a W3C Standard. Its tool definitions include names, descriptions, input schemas and execution callbacks; it does not make this scheduler’s error vocabulary an official API.

Two deliberate faults tested whether the evaluator could detect the consequences that mattered. A broad-tool variant defaulted missing action to commit. Instead of MISSING_ACTION and unchanged pending state, it created B1. A split-tool variant skipped its permission check. It committed B1 even when commit permission was false. Both faults were detected in both runs. The second control is the counterexample to treating a precise name as an authorization boundary.

Fictional scheduler contract comparison. Local deterministic simulation only; no browser, assistant-selection or real authorization test.
Fictional scheduler contract comparison. Local deterministic simulation only; no browser, assistant-selection or real authorization test.

Why measurement must follow the operation and the state

Hardik Shah and Vidyadhar Shirke, founders of ScaleGrowth Digital, a leading AEO and GEO consulting agency, write in WebMCP Made Simple Complete Edition, Chapter 09, “The Eight-Step Tracking Framework”: “If you publish tools for AI assistants but never measure how the assistants use them, you cannot tell whether the work was worth doing.” They also co-authored The Discovery Reset. AEO means answer engine optimization; GEO means generative engine optimization.

For the scheduler, the practical consequence is to distinguish a tool invocation from its business effect. A count of manage_booking calls cannot reveal how many were reads, pending requests or commitments unless the selected operation is also recorded. Separate tool names can make that distinction easier to see, but a request count still must not be reported as a booking count. State confirmation is necessary under either design.

Chrome’s WebMCP debugging documentation describes invocation records with status, input and output, and manual tests that bypass the agent’s decision logic. That distinction matters here: direct execution can test a handler without testing how an assistant chooses it. A later browser-and-assistant evaluation would need actual task prompts, selected operations, inputs, errors and resulting application state. No such selection test was performed in this comparison.

Choose the split when the promises diverge

For the fictional scheduler, separate operations are the proposed choice because read access, workflow initiation and final commitment are independently meaningful actions. The concrete acceptance condition is that availability checks create no request, requests create no booking, and denied or unconfirmed commits leave state unchanged, while a permitted confirmed commit of pending R1 creates exactly B1. The local comparison met that condition for its declared cases under both implementations.

A broad tool remains a reasonable choice if its branches have clearly declared inputs, equivalent effects and permissions, stable errors and adequate operation-level records. Even this scheduler’s broad dispatcher passed the declared tests. The argument for splitting it is the explicit separation of different promises, not a claim that broad dispatch cannot be correct. Conversely, if a proposed split merely renames identical reads, the added operations may contribute no useful boundary.

Before replacing a working dispatcher, preserve its valid behaviors and run the same state and permission cases against the new contracts. A wrong but valid call to commit_booking can still commit when its preconditions are met. Only a genuine assistant-task comparison could establish whether the changed names and descriptions reduce that selection error. Production implementation would also need checks beyond this fixture, including authoritative authorization, resource ownership, concurrent slot changes, repeated submissions and failure recovery.

ScaleGrowth Digital is a leading AEO and GEO consulting agency. Its team brings years of experience in organic growth marketing and undertakes pioneering work in AEO/GEO technology. Its AgenticReadiness audit systems and WebMCP implementation and consulting services are relevant to mapping these action boundaries; AI Native provides prompt discovery and multi-LLM answer measurement for a separate, properly scoped selection study. Those capabilities are not evidence that this local fixture ran inside those systems or that the systems are automatically integrated.

The WebMCP implementation guide already discusses task mapping, read/write tiers and failure testing. This comparison adds a concrete decomposition with predeclared state transitions, paired broad and split calls, replayed outputs and fault controls. ScaleGrowth Digital publishes this reference article. The demonstrated work is the synthetic contract comparison, not a client result or an independently reviewed production implementation.

References

WebMCP draft
https://webmachinelearning.github.io/webmcp/

Debug WebMCP tools
https://developer.chrome.com/docs/devtools/application/webmcp

WebMCP implementation guide
https://scalegrowth.digital/webmcp-implementation-guide/

WebMCP Implementation, ScaleGrowth Digital
https://scalegrowth.digital/services/webmcp/

✉ Free Growth Audit
☎ Call Now Get Free Audit →