Agentfy integration
The runtime boundary and delegated context below are implementation requirements. Availability notes reflect the inspection on 2 October 2026, not a live status check. For module transport and writes, use only REST 1.0.
Three authority boundaries
Agentfy runtime ──(1) agent credential + (2) conversation grant──▶ Store Deputy MCP
│ policy, audit
│
(3) connection signature, never (1) or (2) ────┘
▼
OpenCart module REST API| Boundary | Proof | Issued by, held by | Valid only at | Never |
|---|---|---|---|---|
| Agent → Store Deputy | Authorization: Bearer sdak_…, one per provisioned agent | Store Deputy; Agentfy keeps it as a team secret | Store Deputy MCP | Forwarded to a shop, shown to the model, accepted as a person's authority |
| Person or shopper | X-SD-Context: sdcg_…, one per conversation | Store Deputy; Agentfy carries it per conversation | Store Deputy MCP, for that agent and thread | Holds permissions of its own; survives a revoked membership |
| Store Deputy → shop | HMAC with the connection secret, both directions | Store Deputy and the module, at pairing | That one shop's module | Leaves Store Deputy's servers or the shop |
The shopper's storefront session is a fourth secret, and it never leaves the shop. The module verifies it and hands Store Deputy only an opaque reference (see shoppers).
Store Deputy MCP
Transport. One endpoint, {STORE_DEPUTY_API}/mcp, Streamable HTTP, protocol version 2025-06-18 (the version Agentfy's client sends today). It is stateless: Agentfy opens a new MCP session for every call, so initialize must be cheap and no state may hang on Mcp-Session-Id. tools/list returns every tool in one page, because Agentfy does not follow nextCursor.
Tools for the Admin Agent (Stage A). All read-only, all need the catalog.read capability except store_status.
| Tool | Does |
|---|---|
store_status | Which shop, reachable or not, paused or not, which tools work now |
catalog_find_products | Find by SKU, model, EAN and other identifiers; returns every match, never picks one |
catalog_get_products | Current details by product ID; missing IDs are listed |
catalog_list_products | Page through the catalog, optionally only recent changes |
Tools for the Frontend Agent (Stage B): cart_get, cart_add_item, cart_update_item, cart_remove_item. Price changes stay off until STOR-5 has its own approval check.
Rules every tool follows:
- No argument names a store, team, person, customer, conversation, price authority or permission. Every object schema forbids extra properties. Passing
store_idis refused withinvalid_arguments; it never selects anything. The check script enforces both. - Names use letters, digits and underscores only. Model providers behind Agentfy reject dots, and Agentfy silently drops names a provider cannot accept.
- A tool is listed only if the agent's profile includes it, the shop's manifest declares its capability, and the team's entitlement allows it. Calling a tool that is not listed is refused on the server, not only hidden.
- Results. Success returns
structuredContentand the same JSON as text. Failure setsisErrorand returns{ "error": { "code", "message", "retryable", "details" } }. Agentfy does not readisErrortoday, so the message must make sense to the model on its own. - Shop text is data. Product names and option labels are returned as fields, never merged into instructions. A product called "ignore previous instructions" changes nothing.
- IDs are text (
"42") so the schema stays the same on every platform; money is a decimal string with four places.
Trusted context
What Agentfy sends
| Header | Set by | Store Deputy checks |
|---|---|---|
Authorization: Bearer sdak_… | Agentfy, from the team secret storedeputy:Authorization (works today) | Known, not revoked; gives team, store and profile |
X-Agentfy-Agent-Id | Agentfy runtime | Equals the agent the credential was issued to |
X-SD-Context: sdcg_… | Agentfy runtime, per conversation | Exists, not expired or revoked, issued for this agent and this thread |
X-Agentfy-Thread-Id | Agentfy runtime | Equals the thread the grant was issued for |
X-Agentfy-Turn-Id | Agentfy runtime | Audit only |
X-Agentfy-Tool-Call-Id | Agentfy runtime | Becomes the stable operation key of a change |
X-Agentfy-Initiated-By | Agentfy runtime | human, heartbeat or agent; only human turns may carry a person's grant |
The model sets none of these. The headers ride on the same TLS request as the agent credential, so they are as trustworthy as Agentfy itself; a signed context token is not needed unless a relay is ever placed between Agentfy and Store Deputy.
What Store Deputy derives
On every tool call, before any shop request, Store Deputy turns the headers into one resolved context: team, store, profile, actor and effective scopes. Tool code sees only that result.
| Actor | When | May do |
|---|---|---|
employee | A person opened the conversation in the app; grant names a Store Deputy user | The intersection of the grant, their live team role, the agent's profile, the entitlement and the shop's capabilities |
agent | A scheduled or agent-to-agent turn, no grant | Reads the owner allowed for the agent; never a change that needs a person's approval |
shopper | A visitor opened the storefront chat; grant names a shopper binding | Their own cart only, while the module still confirms the binding |
Changing a role, removing a member, disconnecting the store or revoking a grant takes effect on the next call, because nothing is cached in the grant. A grant from one conversation is refused in another, so two parallel conversations of one agent cannot mix.
What Agentfy does not do yet
These come from reading Agentfy's main on 2 October 2026. They are requirements for STOR-22 and related tasks, to agree with the Agentfy team, not changes to make here.
| Today in Agentfy | Needed |
|---|---|
| MCP calls carry only team-shared static headers; by policy no agent, user or conversation context is sent | Opt-in, per MCP server, the headers listed above, set by the runtime |
| No per-conversation secret | Store a Store Deputy grant per thread, outside the prompt, and send it on that thread's calls |
| Visitor turns get no MCP tools at all | Allow them for a server that is marked as frontend (Stage B) |
isError is not inspected | Treat it as a failed tool step (recommended) |
| Cabinet threads are keyed by Agentfy user | A separate thread per Store Deputy person, so their grants never meet |
| No service credential; creating agents and MCP servers needs a user session | A service-to-service way to provision an agent (STOR-23) |
How Agentfy receives a grant when a conversation starts depends on who opens the conversation, which is still open (see open points). The proposal is that Store Deputy opens it, because the app is where the person signed in.