Skip to documentation
DocumentationApprovals

Approvals and grants

Choose which calls wait for a person, answer the card, and know what the agent does while it waits.

On this page

Every call runs straight through by default. You choose where a call waits for a person: one agent, one connection, one class at a time.

Choose which calls wait for you

Open Agents and pick the agent. Its Access list has one row per connection.

  • Turn on Ask every call to approve each call on that connection.
  • Or set the read, write and destructive columns one by one. Automatic runs the call, Approval required waits for a person, Denied refuses it.
  • Tick Code to add a six-digit authenticator code to destructive calls. The column appears once you set up Authenticator app in Settings.

Sallyport classes a call by its HTTP method. GET, HEAD and OPTIONS read. POST, PUT and PATCH write. DELETE and any other method are destructive. A read turns into a write when a path segment starts with a word such as send, run, exec, build, trigger, invoke or webhook. A service’s recipe can adjust this for calls it knows.

A call past a budget you set waits, see Limits.

Where the card reaches you

The card goes to the person the agent acts for and to every owner and admin. The first answer decides. Set the channels in Notifications.

ChannelHow it works
ConsoleThe card opens in the corner of any screen, and the Approvals row counts what waits. Cards in the console turns the corner card off.
BrowserSend cards to this browser delivers cards while the console is closed. If the browser blocked them, allow notifications in the site settings and reload.
TelegramPress Connect Telegram, then Open the bot and press Start. Only a private chat gets cards, with Approve, Deny and Approve for 1 hour buttons.
EmailOff by default. Send cards by email turns it on, and each email carries a link to the card.
The agentThe agent shows you approve_url. It opens the same card at https://my.sallyport.cloud/approve/<call_id>.

Each connected channel has Send a test. The What reaches you where table picks which events use Browser, Telegram and Email. Telegram offers only Deny for a destructive call, plus a link to the card.

Answer the card

The card shows what will be sent, which agent asks and from which workspace. Details holds the rule, the key, the call ID, the deadline and the agent’s own words, marked unverified. The card shows each part of the request up to 2 KiB. When a part is longer, the card says so above the buttons, and Show the whole request loads all of it. Details also lists a header the agent sent in the key’s own place, with the value it sent; it does not go out.

ButtonWhat it does
ApproveRuns this one call.
RefuseOpens a Reason field; press Refuse again to send. The agent reads the reason and does not repeat the call.
Approve GET /client/v4/zones for 24 h, up to 200 callsRuns this call and creates a grant. The same agent, connection, class and path then run without a card until the time or the count runs out.
Allow every read on api.cloudflare.com from now onRuns this call and sets this class to Automatic for this agent on this connection. Only owners and admins see it.
Hand overPasses the card to another owner, admin or approver.

A destructive call needs a reason to approve as well. If Code is ticked on that row, the card also asks for the six-digit code from your authenticator.

A grant from the card lasts as long as Longest grant (seconds) in Settings, Organization, which is 24 hours by default. It allows 200 reads, 20 writes or 1 destructive call. Approve for 1 hour in Telegram grants 20 calls for one hour. Review and revoke grants at Grants, which opens from Approvals; an agent’s page lists the grants it runs on.

The from now on button appears only while the class is Approval required. The change lands in Rule changes, where Revert puts it back. Setting a class to Denied revokes the grants it covered.

What the agent sees while it waits

Every waiting answer carries a call_id and an approve_url. A repeat with the same call_id continues the same call and never starts a second one.

  • An MCP client that sends a progress token keeps the call open. Sallyport reports progress every 10 seconds, for up to 240 seconds.
  • A client without a progress token waits up to 45 seconds.
  • When that wait ends, the agent gets APPROVAL_PENDING with call_id, approve_url, expires_at and poll_after_ms. Then get_call answers at once, and a repeat with call_id waits again.
  • A client that supports MCP Tasks gets a task to poll. A client that supports URL elicitation shows you approve_url and repeats the call by itself.
  • On /p/ the answer is 202 with X-Sallyport-Call-Id. Poll GET https://mcp.sallyport.cloud/p/calls/{call_id}: 202 while it waits, the service’s answer after approval, 403 after a refusal, 410 after expiry.

An answer reaches a waiting call at once. Claude Code moves a call that waits over 2 minutes to the background and delivers the result when it arrives.

How long a card waits

  • A card stays open for 60 minutes by default. Approval window (seconds) in Settings, Organization, changes it.
  • Opening the full card adds 5 minutes, at most twice. The corner card adds nothing.
  • Reminders go out 2, 15 and 45 minutes after the card opened. A reminder that would fall after the deadline is skipped.
  • After a refusal the agent gets APPROVAL_DENIED with your reason. Nothing ran.
  • After expiry the agent gets APPROVAL_EXPIRED. Nothing ran; if the action is still needed, the agent repeats it without call_id.

Bursts of calls

  • Identical calls from one agent join the card that is already open, however far apart they come. The call runs once, and every copy gets its result.
  • An agent with 20 open cards, or an organization with 100, raises no more. The agent is paused, one card says why, and Resume agent on its page starts it again.

When the agent has no key

A card answers a call that already has a key. A call to a service without one opens a request in Needs a key and gives the agent its link.

The same happens for a paused connection, a retired key or an expired OAuth sign-in. Add the key with Grant access, and the agent repeats its call. See Credentials and agents.