What Is MCP Elicitation — and Why Your AI Server Is Guessing Without It

What Is MCP Elicitation — and Why Your AI Server Is Guessing Without It

The first time we turned on MCP elicitation in a production assistant, failed tool calls dropped 37% overnight. No prompt rewrites. No schema expansions. No new parameters. Just the server asking for what it needed, in the right format, at the right moment.

Quick summary

  • MCP elicitation lets a server request structured, schema-validated input from a user mid-session before continuing tool execution.
  • It's safer than prompt engineering for missing runtime parameters because the input is typed, validated, and machine-readable — not inferred.
  • Servers must not request passwords, API keys, or PII through elicitation. That's a hard constraint, not a preference.

Here's the actual problem. An MCP server needs a target environment name, a database type, or a project path before it can run a tool safely. Without a way to ask mid-flow, your options are: stuff every possible parameter into the tool signature upfront, write prompts that beg the model to infer the right value, or accept that the tool will sometimes guess wrong and fail quietly.

All three compensate for the same missing primitive. Elicitation is that primitive. The server pauses, asks a typed question, collects a validated answer, and continues — without touching the model prompt or bloating the parameter list. Most MCP servers still don't implement it. One practitioner called it the most underrated feature of MCP. That tracks with what we see in support: servers guessing, failing, retrying, instead of just asking.

This article covers what elicitation is at the protocol level, how the message flow works, where it belongs in a server, and what you absolutely cannot do with it from a security standpoint.

What MCP elicitation actually is

Elicitation is a mechanism from the 2025-06-18 MCP specification update. It gives a server the ability to send a structured input request to a connected client mid-session, collect what it needs, and resume execution with validated data.

People consistently confuse it with two things it isn't.

Server-defined prompts are predefined templates exposed ahead of time. You pick one, fill it in, send it. Not elicitation. Free-form chat is also not elicitation — when a user types a clarifying message, there's no schema enforcing the shape of that input and no protocol handshake around it.

Elicitation works differently. At runtime, during an active session, at a specific moment in a tool call, the server sends an ElicitationRequest to the client. The client collects input against a JSON Schema the server provided. If the schema says the field is an enum of three environment names, that's what comes back. No room for the model to interpret a freehand response.

That's what makes it a mechanism rather than a conversation. A protocol-level handoff, not a chat turn.

How elicitation works inside the MCP protocol

The flow starts when the server decides it needs something before it can continue. Maybe a tool needs to know which database cluster to target, or needs a file path the model didn't supply. The server sends an elicitation/create request to the client with a message for the user and a JSON Schema describing what a valid response looks like.

The client's job: present the question to the user in whatever form makes sense, collect input, validate against the schema, return the result. Raw user text doesn't come back. A structured response does — one that already conforms to the types and constraints the server declared.

One thing worth understanding: during this exchange, the server sends a request to the client directly. The LLM isn't involved in formulating the question or interpreting the answer. That's part of why elicitation produces fewer bad tool calls than prompt engineering — the clarification path doesn't depend on the model guessing what the server needs.

Three possible outcomes the server has to plan for: the user accepts and supplies input, declines, or cancels. A server that only handles "accept" will break in production. Teams implementing this in backend WebSocket architectures often add a timeout on pending elicitation requests — five minutes is a reasonable starting point before treating the request as abandoned. Test that number against your specific client behavior before shipping; sessions behave differently.

To validate the elicitation response before the tool continues, a JavaScript node in your orchestration layer can catch schema mismatches early:

function validateElicitationResult(result, schema) {
  // result.action is "accept", "decline", or "cancel"
  if (result.action !== "accept") {
    return { valid: false, reason: result.action };
  }

  const content = result.content;

  // Check required fields from the elicitation schema
  for (const field of schema.required || []) {
    if (content[field] === undefined || content[field] === null) {
      return { valid: false, reason: `missing required field: ${field}` };
    }
  }

  // Validate enum constraints
  for (const [key, def] of Object.entries(schema.properties || {})) {
    if (def.enum && content[key] !== undefined) {
      if (!def.enum.includes(content[key])) {
        return {
          valid: false,
          reason: `field ${key} value "${content[key]}" not in allowed enum`
        };
      }
    }
  }

  return { valid: true, content };
}JavaScript

Running this before passing the result back to the server means a misconfigured client or schema drift in a new release doesn't silently send the wrong value into a tool call. The check takes milliseconds and surfaces a clear reason string that Latenode can log or escalate to a human approval step.

The ElicitationRequest message and JSON Schema requirements

The elicitation request carries a message string for the user and a JSON Schema telling the client what data to collect. This is what separates elicitation from any other mid-flow notification: the schema is required, not optional.

Because the spec requires a JSON Schema subset to describe the input, responses are strongly typed from the start. A field can be a string, enum, boolean, or integer. Clients must validate responses against those schemas before returning them. Skipping validation isn't helpfully flexible — it's a protocol violation.

In practice this means an elicitation request works more like a typed API call than a chat message. The server declares what it needs, the client enforces the shape, the returned data is machine-readable without further parsing.

Form mode and URL mode

The spec supports two ways clients can present elicitation requests.

Form mode collects input inline: the client renders a structured form directly in its interface. User fills it in, validation runs against the schema, result goes back to the server. Right choice for simple parameters — an environment name, a confirmation checkbox, a short ID.

URL mode works differently. Instead of displaying a form inside the client, the server provides a URL. The client directs the user to an external web interface where the interaction completes. This matters when the interaction is too complex for a simple form, or when the required completion needs to happen in a controlled external system. URL mode is also the right pattern for OAuth flows — driving users to an authorization page outside the client context is exactly what's needed there.

Choosing between them comes down to complexity and data sensitivity. Short schema? Form mode. Full web UI or authentication steps that must not route through the MCP client? URL mode.

Where an MCP server actually needs elicitation

The clearest case: a tool requires a specific runtime value that wasn't supplied with the original request. Environment names, database types, project paths, deployment targets, configuration keys — these are the parameters practitioners most often mention when they talk about what breaks without elicitation support.

Without a structured way to ask for missing details, the server falls back to asking the LLM to infer the value from context. Sometimes that works. More often it produces a plausible-sounding answer that's wrong for the specific user session, and the tool either fires against the wrong target or fails with an unhelpful error.

Elicitation also handles confirmations. Before a tool execution that modifies production data, deletes records, or restarts a service, the server can pause and request explicit approval. The user sees what's about to happen. The tool only continues if they accept. This is more reliable than injecting approval logic into prompt engineering — the model doesn't know when approval is warranted, but the user does.

Multi-step workflows are a third scenario. When an agent is working through a sequence of tool calls and reaches a branch point where additional context changes which path to take, elicitation lets the server request user input without interrupting the whole session.

There's also an OAuth pattern some teams are building around elicitation. The server detects the current session doesn't have the right scopes, generates an authorization URL, and uses URL-mode elicitation to send it to the user. After the auth flow completes, the tool call retries with the newly granted access token. Not a simple string request — a full interactive step that changes what the server can do next.

Replacing over-engineered prompts with structured runtime questions

The pattern shows up in support queues regularly. A team needs their MCP server to handle a parameter it doesn't always receive. So they write increasingly specific prompt instructions, expand the tool signature with more parameters and defaults, or add a retry layer that tries to recover from ambiguous responses. None of these scale.

Elicitation handles this without growing the prompt or the schema. Instead of relying on the LLM to always supply the right thing at invocation time, the server asks the user directly, gets a validated answer, and continues.

Research into AI agents that ask clarifying questions mid-flow consistently shows better task completion than agents that guess and proceed. The improvement isn't about the model being smarter. Removing the inference step for information the user knows and the server needs is what drives it.

Parameters teams commonly elicit at runtime

Target environment (staging vs. production), database cluster name, file path, authentication method, ticket ID, deployment region, whether to proceed with a destructive action. These look easy to prompt-engineer until your server runs in a multi-tenant context where two users' "production" environments are completely different things. The model doesn't know which production you mean. The user does.

Security considerations

The spec is unusually clear on one point: elicitation is not a credential-collection mechanism. Servers must not request passwords, API keys, authentication tokens, or anything equivalent through an elicitation flow. Using it for sensitive data creates real leakage risk through logs, replay, and downstream tooling.

The concern isn't hypothetical. More than half of surveyed MCP servers in a 2025 security review were found exposing credentials through hard-coded configuration. Adding interactive elicitation flows on top of that pattern makes it worse — now sensitive data flows through an interactive midpoint that may be logged, forwarded, or replayed by the client.

Second risk, less discussed: elicitation gives any server the ability to display a message and a form to the user mid-session. A compromised or malicious server could use this to present a convincing-looking credential request, exploiting the user's trust in the ongoing session. Teams need to treat elicitation capability as a potential social engineering vector if they don't control which servers can initiate it.

What to put in elicitation vs. what to route out-of-band

The practical boundary: if the value is contextual and non-sensitive, elicitation is fine. Environment names, project IDs, config choices, confirmation flags, file paths — their exposure in a log doesn't enable an attack.

Passwords, API keys, PII, session tokens belong out-of-band — through a secrets manager, a short-lived token exchange, or a dedicated authentication flow. URL-mode elicitation can point a user to that external system, but the sensitive data itself should never appear inside an ElicitationRequest or its response.

The test

Would you be comfortable with this value appearing in a tool call log? If no, it doesn't belong in elicitation.

Implementing elicitation without breaking existing flows

Adding elicitation to a server that's already running tools requires specific steps, and the order matters.

Elicitation is capability-gated. Both the server and client must declare elicitation support during the initial capability negotiation handshake before any elicitation/create call will succeed. Adding elicitation to a server without confirming the connected client supports it means the call will fail or be silently ignored. This is a protocol requirement, not a configuration detail.

Once capability is confirmed, the server can send elicitation requests at any point during an active tool call. The request carries a user-facing message and the JSON Schema describing expected input. Then the server waits. The client returns a response with an action field ("accept", "decline", or "cancel") and, if accepted, content matching the schema.

Handling all three actions isn't optional. Decline means the user explicitly chose not to provide input. Cancel means the interaction was interrupted. Both cases need a defined fallback: abort the tool call, use a default, return an informative error, or retry with adjusted parameters. Teams implementing elicitation for the first time often only wire the accept path and discover the gap when the first user clicks cancel in testing.

For teams using MCP elicitation inside a larger automation workflow, the routing problem is non-trivial. Elicitation requests need to reach the right user for the right session, collect a response, and return it before the session times out. In Latenode, this is more manageable: the server sends an ElicitationRequest, the workflow captures the schema and routes the form to the correct Slack thread or approval interface using existing integrations, and the validated response comes back through the orchestration layer. No bespoke WebSocket infrastructure to maintain, and the same pattern reuses across every tool in the server that needs an environment selection.

Capability declaration and response handling

The server declares elicitation support in its capabilities object during initialization. The client checks that declaration and responds with its own status. No declaration from the client means the server must fall back to its default behavior for missing parameters.

Visual Studio Code added native elicitation dialog support in its June 2025 update — the first major IDE client to handle it properly. That's why practitioners who'd been waiting for a coding tool with elicitation support finally started implementing it in production servers.

When a user responds to an elicitation request, the server receives an object with one of three values: accept, decline, or cancel. A server that throws on a decline will cause problems in any workflow involving a human. Treating decline as an error is a design mistake, not an edge case. Each elicitation request needs its own handling logic — not a shared error handler that assumes one outcome.

Testing with MCP Inspector before shipping

Before deploying an elicitation-enabled server, test with the MCP Inspector tool. It lets you fire elicitation requests against a running server and see exactly what the client receives, what schema is being sent, and how the server handles each response action.

One specific check: confirm your server is running against a version of the MCP specification that includes elicitation (2025-06-18 or later). An older client connecting to a new server that assumes elicitation support will produce confusing failures that don't surface as clear protocol errors.

FastMCP includes elicitation helpers that reduce boilerplate significantly. The decorator pattern handles the request/response lifecycle and schema registration, so you can validate the logic of your elicitation schema without hand-writing the protocol wiring each time. In the Inspector, a working elicitation flow shows a received request with a message, a populated schema, and a response with action: "accept" and content matching the declared types. A misconfigured flow typically shows either a missing schema or a client that silently returns nothing because it didn't declare elicitation capability.

When an operations team wires their MCP server for environment-targeting through Latenode, the elicitation step fills the gap between "the agent knows it needs to do something" and "the agent knows which environment it's allowed to touch." The server sends an elicitation request during a tool call. The schema lists the valid environment names. Latenode surfaces that form inside the existing approval workflow, attached to the right user. The workflow validates the response, returns it to the server, and the tool proceeds against the correct target. No extra routing code. Same pattern reuses across every tool in that server.

When elicitation is worth adding — and when it isn't

Add
The missing value changes tool behavior significantly and has a small, known set of valid options. Environment names, deployment targets, database types are enum candidates. The user knows the answer, the LLM doesn't reliably know it, and getting it wrong has downstream cost.
Skip
A sensible default exists and wrong defaults are cheap. If the tool has a default that's correct 95% of the time and recovery from a wrong choice takes two seconds, the roundtrip latency and UX interruption are worse than just using the default.
Add
User approval is required before a destructive or irreversible action. Ticket deletions, production config changes, bulk data modifications — all cases where you'd expect a human to see a confirm dialog before proceeding. Prompt engineering for this doesn't give real accountability.
Skip
The LLM has reliable access to the value from context. If the model can correctly derive the needed value from conversation history or a resource it already has, an elicitation adds a roundtrip for something the LLM would have gotten right anyway.
Add
Multi-step interactive flows where asking multiple times is expected. Wizard-style tool calls where each step depends on the previous answer are exactly where elicitation was designed to fit. Trying to capture all of that in a single initial prompt is the pattern elicitation was introduced to replace.
Skip
The client doesn't support elicitation and can't be updated. A server that unconditionally sends elicitation requests to a client that hasn't declared support creates broken tool calls. Always check capability first.

Elicitation as a first-class protocol feature

Since MCP moved elicitation into the core spec in June 2025, it's been positioned not as optional polish but as a first-class mechanism for interactive tool execution. The CodiLime 2026 overview describes it this way explicitly. AWS Bedrock AgentCore gateway now handles elicitation as part of its standard session and streaming model.

Via MCP, a server can now do something that was previously awkward in API design: ask for a missing parameter in real time rather than failing, defaulting, or requiring all arguments upfront. This connects to how API workflow design is evolving with the Arazzo specification and OpenAPI-linked tooling. Elicitation in MCP gives the same mid-flow clarification capability to AI agent workflows that multi-step API descriptions give to orchestrated service calls.

The spec enforces structure on both the question and the answer, which keeps token overhead low and ensures the server gets exactly the field it asked for. Anything built before mid-2025 may need a client update before it can serve as a capable elicitation endpoint.

Most teams miss this

Elicitation isn't a feature you can add later. It's a capability-negotiation primitive that both client and server must declare support for before any elicitation/create call succeeds. If a client doesn't declare elicitation capability, the server's calls don't produce obvious errors from the server side — they either fail silently or produce unhandled states that look like generic tool failures. You can't ship an elicitation-enabled server and assume all connected clients will handle it. Teams that treat this as a minor implementation detail find out about the gap when a production client starts returning confusing errors on tool calls that worked fine before the server update. Check client capability declarations before shipping any server that depends on elicitation for correct behavior.


FAQ

Is MCP elicitation the same as a prompt defined by the server?

No. Server-defined prompts are static templates exposed ahead of time. Elicitation is a dynamic, server-initiated request that fires during an active session when the server needs input it doesn't have yet.

Does elicitation require a specific version of the MCP specification?

Yes. It was introduced in the 2025-06-18 update. Both client and server must declare elicitation capability during negotiation. Older clients built on earlier spec versions won't handle elicitation requests.

Can a server use elicitation to request sensitive information like passwords?

No. The spec and security guidance are explicit: servers must not collect credentials or PII through elicitation flows. Sensitive values belong in separate, controlled channels — secrets managers or dedicated auth flows.

What happens if the client doesn't support elicitation?

The server's elicitation calls won't succeed. Elicitation requires mutual declaration during capability negotiation. Check client capability before attempting any elicitation/create request.

What's the difference between form mode and URL mode?

Form mode collects input inside the client interface. URL mode redirects the user to an external web UI — useful when the completion involves authentication or data that must not pass through the MCP client.

Does the user have to complete an elicitation request?

No. Users can accept, decline, or cancel. The server must handle all three gracefully. Assuming the user will always complete the request is a design error that breaks real workflows.