Skip to main content
The same tools as the workspace endpoint, behind a bearer token bound to one contact. It exists so one of your end users can connect their own assistant with a credential you can revoke for that person alone, without affecting anyone else. Advertised as mcp.peeve.ai/{workspaceId}/u/{contactId}.
The guide-only rule and the Growth plan gate apply here exactly as they do to the workspace endpoint. A grant authenticates the caller; it does not unlock writes. tools/call still returns guidance and never performs an action.

The token

A grant token looks like pv_grant_ followed by high-entropy random data. It is bound to a specific (workspace, contact) pair, and is passed as a bearer credential.
A token is accepted only when every one of these holds:
  • it starts with pv_grant_;
  • it matches a grant on this workspace;
  • that grant is bound to this contact;
  • it has not been revoked;
  • it has not expired.
Any failure returns the same 401 — the endpoint never tells a caller which condition failed, or whether the grant exists.
Because the token is bound to both the workspace and the contact in the URL, a valid token for one contact cannot be used against another contact’s endpoint, and a token from another workspace matches nothing.

Issuing a grant

Grants are issued from the dashboard, on the contact’s detail page. The token is shown once; hand it to that user through a channel you already trust for credentials.
Treat a grant token as a secret belonging to that one person. It is long-lived, it is a bearer credential, and it identifies them. Do not log it, put it in a URL, or send it over a channel you would not send a password over.

Revoking a grant

Revoke from the same contact detail page. Revocation takes effect on the next request — validation is a single indexed lookup with no cache in front of it, so there is no propagation delay. An expiry may also be set, and is checked on every request. Peeve stamps a last-used timestamp on each successful call, so you can see which grants are actually in use before you revoke.

GET — discovery card

Requires the bearer token, like the POST.

Errors

Identical to the workspace endpoint, with one addition. On GET, an auth failure is a plain 401 { "error": "unauthorized" }; the JSON-RPC framing above applies to POST. A malformed workspace or contact UUID returns 404.

Rate limits

Bucketed per workspace and per contact — the identity the grant is bound to. The token itself never goes in a limiter bucket, because it is a secret. Ceilings follow your plan. This matters more here than on the workspace endpoint: a grant is a long-lived token in a third-party assistant, and a looping client would otherwise query your data indefinitely.

Auditing

Every call is recorded against the contact, so the trail attributes each tools/call to the specific revocable credential rather than to “someone with the URL”. The record carries the capability key, the method and the outcome — never the arguments. This is the main practical reason to prefer per-user grants over the workspace endpoint when you can: the workspace endpoint tells you that a tool was called, and per-user grants tell you whose assistant called it.