Clients and grants
Website, storefront, backoffice, agent forwarder and MCP clients, with third-party defaults.
Every caller has its own Auth0 client and an explicit grant. Nothing is inherited. Machine clients allow only client
credentials and use client_secret_post.
| Client | Type | Grant on the Shop API | Scopes |
|---|---|---|---|
| Website | Regular web app | User | Agent scopes plus payment_methods:write and account:security |
| Storefront | Machine to machine | Client | catalog:read, cart:read, cart:write, checkout, orders:read, guest |
Backoffice (backoffice_api) |
Machine to machine | Client | ops:read only |
MCP server (shop_mcp) |
Custom API client (resource_server) |
User, through On-Behalf-Of | Agent scopes only |
| Proxy Auth0 | Regular web app | User, through CTE | Agent scopes only, on the Shop API and the MCP resource |
Independent agent (personal_agents) |
Confidential regular web app | No direct Shop API grant; invited-agent CTE and Session Delegation | Approved owner-backed browser permissions only |
Web agent forwarder (web_agent_forwarder) |
Machine to machine | Client | Agent scopes plus agent:forward |
MCP agent forwarder (mcp_agent_forwarder) |
Machine to machine | Client | catalog:read, cart:read, cart:write, agent:forward |
The storefront grant excludes all account:*, payment_methods:* and ops:* scopes. The backoffice grant is
exactly ops:read. Neither agent forwarder can acquire guest, operator, card-write or account-security authority, and the API
accepts an agent-forwarder token only together with exactly one original artifact (see
Callers and tokens). Agent forwarder and storefront credentials are
secret stack bindings and never appear in plain settings.
Independent invited agents
The optional personal_agents client authenticates independent identities in the agents connection. It uses a
separate invited-agent exchange profile and Session Delegation into the website; shared commerce calls subsequently
use the web agent forwarder with live consent checks. Its own rotating refresh token belongs to its independent login, while
the delegated website session has no delegated refresh token. It is not a Poppy Account Token or a direct API grant.
See invited-agent setup for the required switches, platform registrations and bindings.
Self-registered MCP clients
MCP clients register themselves through Dynamic Client Registration. They are third-party clients in strict mode. A default grant for third-party clients gives them the agent scopes on the MCP resource and nothing else.
- The default grant covers every third-party client in the tenant, including ones created later. That is acceptable because it only covers the MCP resource, never the Shop API.
- A dynamic client can’t get a Shop API token directly. Auth0 refuses, because no third-party grant exists for that audience.
- An MCP token presented directly to the API is rejected on audience.
The MCP server’s own identity
The MCP server has one Custom API client linked to the MCP resource, allowed to perform only the On-Behalf-Of
exchange. It authenticates with a client secret held in the MCP Worker’s secrets (MCP_CLIENT_ID,
MCP_CLIENT_SECRET). Its grant to the Shop API is user-delegated and limited to agent scopes, so even with route
guards disabled Auth0 would refuse to issue payment_methods:write, account:security, guest or ops:read to it.
Management clients
shop_managementis bound to the webshop Worker. It requests exactlyread:sessions,delete:sessionsanddelete:refresh_tokensfor browser session listing and revocation. Selected browser actions and sign out everywhere deny linked Poppy grants through the Auth0 proxy before requesting Auth0 revocation with refresh tokens.ops_managementserves the API’s operator customer reads throughAPI_OPS_MANAGEMENT_*; its grant is exactlyread:users. Terraformmovedblocks (contract-moves.tf) keep the identity it had asbackoffice_management.
The website client’s back-channel logout URL points at the webshop (website_backchannel_logout_url,
https://<shop>/api/auth0/backchannel-logout), not at the API. See
back-channel logout.
Refresh tokens for the website
The website’s refresh-token policy covers the Shop API with website_api_scopes and, when enabled, My Account with
shop_my_account_scopes, so one refresh token serves both (multi-resource refresh tokens). Every website login
requests the Shop API audience, and rotation keeps zero leeway. See My Account.