Scoping an MCP Server Project: What to Decide Before the Quote

What are you actually scoping?

It is easy to write the request down as an integration project: connect the agent to our ticketing system. That shape hides the unit of work. An MCP server is not a connection. It is a published surface that a client reads and calls, and the part of it that carries the effort is the tool list: each tool with a name, a description, an input schema, a return shape, an error contract and a permission. A server can also expose resources and prompts, and those belong on the same inventory. What you are scoping is that surface, the identity model behind it, and the record it leaves.

The reframing changes the first meeting. Instead of asking which system, ask which verbs. A server that exposes search_tickets and get_ticket is a different piece of work from one that also exposes create_ticket, add_comment and close_ticket, even though both talk to the same API.

This article covers the decisions that have to be made before anyone estimates a build. The controls that sit on a finished server are a separate exercise, and our MCP Server Security Checklist post covers that side.

Do you need an MCP server, or just an API call?

If one agent, built by one team, needs to reach one system, and nothing else will ever call it, a direct client inside the agent is a defensible answer. The MCP layer adds a process to run, a schema to maintain and a deployment to watch. Weigh that against what the layer gives you when a single caller already has the SDK in hand.

MCP earns its place when more than one client needs the same capability, when the tool set has to change without redeploying every client, or when access rules and the audit trail need to sit in one reviewable place instead of scattered through several codebases. If none of those holds today but one is planned, put it in the scope, because it changes how tools are named and versioned.

Start with the tool list, not the system

Write the tool inventory before anyone estimates anything. Granularity is the judgment call. A single do_the_thing tool with a free-text parameter pushes the whole problem into the model and makes failures hard to attribute. A long list of narrow tools crowds the model’s choice. Aim for tools that match the decisions a person makes doing the task by hand, and treat the first list as a draft: put a point in the schedule to revise it after an agent has been run against it.

For each tool on the list, agree on the following:

  • The name and one-line description, written for a model to read, since that description is how it decides whether to call the tool.
  • The input schema: types, required fields, defaults, and what the tool does with an ambiguous or partial input.
  • The return shape, including what happens to a large result set. Pagination and truncation are design decisions, not implementation details, because context has a limit.
  • Whether it reads or writes, and whether calling it twice with the same arguments is safe.
  • The upstream calls it makes, and its behavior when one of them fails or times out.

Whose identity does each tool act as?

Permissions belong in the scope next to the tool list, because the identity model reaches into every tool on it. The first question is whether the server acts as itself or as the person on the other end of the conversation. With a single service account, every caller can reach everything that account can reach. Passing the end user’s identity through keeps existing entitlements in force, and it brings token exchange, session handling and partial-access cases with it.

Other decisions belong in the scope rather than a later ticket: which tools need explicit human approval before they run, whether write tools are separated so they can be granted apart from read tools, how tenants are kept apart if the server serves more than one, and what happens when a token expires mid-task. If any of these changes after the build has started, the revision can reach every tool on the list, which is the argument for settling them on paper.

The scoping question here is narrow. Name the model, name who signs it off, and note which tools the choice constrains. Threat modeling the tokens and identities themselves is a security review in its own right, and it is better run by someone who did not design the tool surface.

What has to be reconstructable afterward?

Audit is the third scope driver, and the useful question is who will ask for the record. Support wants to know what the agent did in one conversation. A security reviewer wants to know which identity called which tool with which arguments. A compliance owner wants to know how long the record is kept and who can read it. Those three want different fields, so decide them together.

Per tool, settle what gets written: caller identity, timestamp, arguments with a redaction rule for anything sensitive inside them, the allow or deny decision, and a correlation id tying the tool call back to the agent turn and the user request that started it. If the correlation id is added after the fact, it has to be threaded back through the client, the server and the upstream call, so decide on it while the tool list is still on paper.

Where the estimate can move

The protocol layer is the part that is easy to picture from a brief. The systems underneath it are harder to see, and a scope written on the tool list alone can come apart on them. Each item below is a question you can answer before signing, and each one can change what a tool has to do.

Ask for these to be addressed in the estimate, with the unknowns written down as unknowns rather than absorbed into a contingency:

  • Upstream APIs that do not offer the operation your tool promises, so the tool composes several calls and has to reconcile partial failures.
  • Rate limits, pagination, and authentication flows built for a browser session rather than a background process, which can bite once an agent is calling in a loop.
  • Test environments without representative data, which makes it hard to tell a bad tool description from a bad upstream response.
  • Error semantics. An agent is more likely to recover from a failure when the message says what to do differently, so error text has to be written, not just caught.
  • Client differences: what a coding assistant, a Copilot Studio agent and your own application each expect from the same server.

A scoping brief you can hand to a vendor

A brief built from the questions above is short, and its main use is making proposals comparable. Two vendors answering the same tool inventory, the same identity model and the same audit record are quoting for the same thing. When each vendor writes the scope during its own discovery, you are comparing different projects.

Put the following in writing before you send it out:

  • The tool inventory, with reads and writes marked separately.
  • The identity model: service account or delegated user identity, and the reason for the choice.
  • Which tools require human approval before they execute.
  • The audit record per tool, and who reads it.
  • Which clients must work against the server, and which of them you will test against.
  • The upstream systems, their documentation, and who can grant a test account.
  • How the server is deployed, and who operates it after handover.
  • The acceptance test: a set of realistic requests, and the tool calls you expect an agent to make in response.

Related service: Related reading: our MCP development service page covers this area of our work, and our MCP Server Security Checklist post picks up where this article stops, at the controls that sit on a tool surface once it is defined.

Related service: MCP server development.

Recorded Demonstrations

For reference while scoping: a recorded session of an MCP server exposing a full building-automation station to an agent.