00Field guide / tool authority
Review MCP Tool Permissions
Before a coding agent calls a tool, establish which operation is allowed, which data it can reach and which evidence supports that decision. This guide follows a first-party test fixture; it does not approve a real server or enable tool execution in the public demo.
01Identity
Start with the contract you intended to allow.
A familiar tool name is not enough to identify what will execute. Record the capability version, package and manifest digests, transport, publisher-review status and the exact tool contract. Compare the discovered tool’s input and output schemas with the reviewed contract before making it eligible. A changed schema can widen the data or actions available even when the name stays the same.
Its production path requires separate marketplace, transport identity and isolation inputs. A server’s reported name or a successful connection does not supply those approvals. Keep the source of each trust decision separate from the data the server reports.
02Scope
Read-only describes an effect, not every security property.
A read operation can still expose private source, return excessive data or deliver hostile instructions. Review the accessible files and data classes, permitted network destinations, output limits and credential scope alongside the declared effect. Keep read, write, destructive and publication capabilities separate.
Hints such as readOnlyHint belong in the review, but a label alone does not enforce a filesystem or network boundary. Check the runtime that constrains the operation and the policy that issues its grant. Retain the distinction between a declared property, a tested mechanism and an approved deployment.
- Exact capability and tool version
- Named permission and data scope
- Current grant and expiry
- Enforced runtime and network boundary
03Worked fixture
Allow a bounded list operation and reject broader requests.
The repository’s authored fixture is named fixture_reader_list_items. Its input accepts one required integer named limit, from 1 through 10, with no additional properties. Its declared permission is project.artifact.read, its effect is read_only and its network policy is none. These names describe an internal test fixture, not a public API to call.
With the fixture’s exact reviewed contract and a valid matching grant, the broker test invokes the tool and receives an items array containing alpha. The result retains workspace data classification and is marked untrusted. The receipt records the effective permission; the fixture’s reported server identity remains non-authoritative.
The refusal test submits limit: 0 and expects tool_input_schema_invalid. It then removes the grant’s permission and expects permission_not_granted. Finally, it sets grant expiry to the current test time and expects grant_expired. The test checks that the server was not called for any of those rejected requests. This last observation matters: an error returned after dispatch would not prove prevention.
04Change
Treat rediscovered schema drift as a new review problem.
Suppose the same fixture version is rediscovered with a looser input schema that accepts additional properties. The broker’s schema-drift test expects quarantine and closes both the previous and newly discovered sessions. A later invocation is refused because the capability is no longer eligible. It does not keep using the old session merely because that session once passed discovery.
For a real integration, preserve the earlier manifest, new discovery result, session lifecycle and refusal reason. Review the changed contract and its actual implementation before issuing new authority. Do not resolve the mismatch by copying the newly reported schema into the trusted manifest without review. A version string that stayed constant does not establish unchanged behavior.
05Output
Validate returned data without treating it as an instruction.
A schema-valid result can still contain misleading or adversarial text. Keep its source and data classification attached as it moves into later reasoning or tools. Returned text must not become permission to disclose files, expand network access, change a grant or mark a task accepted.
The broker has separate checks for structured output and an independent byte limit. Review the failure path too: a tool call may already have happened before its malformed output is rejected. Preserve that distinction in the record and investigate any possible external effect before retrying. Input refusal before dispatch and output rejection after dispatch are different outcomes.
06Review record
Keep the decision reproducible and its limits visible.
Retain the reviewed contract and source version, relevant grant identity and expiry, discovery result, requested operation, input-validation decision, whether dispatch occurred and the resulting receipt or refusal. Keep raw credentials out of the record. Use independently maintained policy and runtime evidence to decide whether the integration is eligible for its intended environment.
The worked cases come from packages/extensions/test/mcp-broker.test.ts, with implementation in packages/extensions/src/mcp-broker.ts and packages/extensions/src/policy.ts, reviewed at core revision 4690941f. They are authored mechanism tests. They do not establish the safety of an arbitrary server, complete production isolation or independent acceptance of a model-produced change.
It accepts no MCP server connection and provides no live tool execution. Use the secure-agent guide for the wider authority model and the runtime-evidence guide for the separate question of which runtime was actually observed.
Design partners
Make each tool call fit a reviewed grant.
Check identity, scope, input and runtime before dispatch. Retain output provenance and refusal evidence afterwards. Expand authority only when the required review supports the exact new operation.
Join the waitlist