One package to connect three layers of agent infrastructure: identity, payments, and data.
Built by arcabot.ai — AI agent infrastructure. Docs at a3stack.arcabot.ai.
The agent infra stack has three layers being built by different teams with no coordination:
| Layer | Tech | Status |
|---|---|---|
| Identity | ERC-8004 (on-chain agent registration) | Deployed on 17+ chains, no SDK |
| Payments | x402 protocol, any ERC-20 (USDC, EURC, …) | npm packages exist, no agent integration |
| Data | MCP servers, onchain oracles | SDK exists, no identity/payment layer |
None of these layers talk to each other. This SDK is the glue.
import{A3Stack}from"@a3stack/core";import{base}from"viem/chains";import{privateKeyToAccount}from"viem/accounts";import{z}from"zod";constagent=newA3Stack({account: privateKeyToAccount(process.env.PRIVATE_KEY),chain: base,server: {name: "MyAgent",payment: {amount: "1000"},// 0.001 USDC per call},});agent.tool("analyze",{query: z.string()},async({ query })=>({content: [{type: "text",text: `Analysis: ${query}`}],}));awaitagent.start();// serves MCP at http://localhost:3000/mcpAnother agent connects and pays automatically:
constclient=awaitcreateAgentMcpClient({agentId: "eip155:8453:0x8004...#42",// ERC-8004 global IDpayer: { account },// x402 auto-payment});constresult=awaitclient.callTool("analyze",{query: "ETH price trend"});// Payment of 0.001 USDC happened automatically@a3stack/identity — ERC-8004 registration, verification, discovery
@a3stack/payments — x402 client (paying) + server (receiving) — any ERC-20
@a3stack/data — MCP server/client with identity + payment
@a3stack/core — The glue: A3Stack class + all re-exports
Use them independently or together via @a3stack/core.
# All-in-one
npm install @a3stack/core viem @x402/fetch @x402/evm @modelcontextprotocol/sdk zod
# Or modular
npm install @a3stack/identity viem
npm install @a3stack/payments @x402/fetch @x402/evm viem
npm install @a3stack/data @modelcontextprotocol/sdk viem zodimport{AgentIdentity}from"@a3stack/identity";import{base}from"viem/chains";constidentity=newAgentIdentity({ account,chain: base});const{ agentId, globalId }=awaitidentity.register({name: "MyAgent",description: "An AI agent that does X",services: [{name: "MCP",endpoint: "https://mcp.myagent.ai/mcp",version: "2025-06-18"},{name: "web",endpoint: "https://myagent.ai"},],x402Support: true,active: true,});// globalId: "eip155:8453:0x8004...#42"import{verifyAgent}from"@a3stack/identity";constresult=awaitverifyAgent("eip155:8453:0x8004...#2376");// result.valid — on-chain ownership + back-reference check// result.owner — owner address// result.paymentWallet — payment wallet (if set)// result.registration — full registration fileimport{getMcpEndpoint}from"@a3stack/identity";consturl=awaitgetMcpEndpoint("eip155:8453:0x8004...#2376");// "https://mcp.arcabot.ai/mcp"x402 now supports any ERC-20 token via Permit2 + EIP-3009 (Transfer with Authorization). USDC is the default, but you can accept EURC, or any ERC-20 by passing its token address.
import{createPaymentClient}from"@a3stack/payments";constpayer=createPaymentClient({ account });// Auto-pays x402 requirements (works with any ERC-20 the server requests)constresponse=awaitpayer.fetch("https://api.paidagent.ai/tool");// Check USDC balance (default)constbalance=awaitpayer.getBalance("eip155:8453");// { amount: 1500000n, formatted: "1.500000", symbol: "USDC" }// Check any ERC-20 balanceconsteurcBalance=awaitpayer.getBalance("eip155:8453",undefined,EURC_BASE);// Decode payment receipt from responseconstreceipt=payer.decodeReceipt(response);import{createPaymentServer,EURC_BASE}from"@a3stack/payments";// Accept USDC (default)constreceiver=createPaymentServer({payTo: "0x1be93C...",amount: "100000",// 0.10 USDCnetwork: "eip155:8453",description: "My AI tool",});// Accept EURC insteadconsteurcReceiver=createPaymentServer({payTo: "0x1be93C...",amount: "100000",// 0.10 EURCasset: EURC_BASE,// any ERC-20 address works herenetwork: "eip155:8453",description: "My AI tool (Euro payments)",});// Express middlewareapp.use("/tool",receiver.middleware(),(req,res)=>{// Payment verified — req.payment has detailsres.json({result: "paid content"});});// Build payment requirements for manual 402constrequirements=receiver.buildRequirements("https://myapi.ai/tool");import{createAgentMcpServer}from"@a3stack/data";import{z}from"zod";constserver=createAgentMcpServer({name: "DataAgent",version: "1.0.0",identity: {chainId: 8453,agentId: 2376,// auto-exposes "agent://identity" resource},payment: {payTo: "0x1be93C...",amount: "10000",// 0.01 USDCfreeTools: ["ping"],},});server.tool("get-data",{query: z.string()},async({ query })=>({content: [{type: "text",text: awaitfetchData(query)}],}));const{ url }=awaitserver.listen(3000);// Serving at http://localhost:3000/mcp// Returns 402 if payment header missingimport{createAgentMcpClient}from"@a3stack/data";// By ERC-8004 identity (auto-resolves URL + pays)constclient=awaitcreateAgentMcpClient({agentId: "eip155:8453:0x8004...#2376",payer: { account,maxAmount: "100000"},});// By direct URL (no identity check)constclient=awaitcreateAgentMcpClient({url: "https://mcp.agent.ai/mcp"});consttools=awaitclient.listTools();constresult=awaitclient.callTool("get-data",{query: "ETH"});constidentity=awaitclient.getAgentIdentity();// reads agent://identity resourceawaitclient.close();The A3Stack class is the all-in-one interface:
import{A3Stack}from"@a3stack/core";import{base}from"viem/chains";import{privateKeyToAccount}from"viem/accounts";import{z}from"zod";constagent=newA3Stack({account: privateKeyToAccount(process.env.PRIVATE_KEY),chain: base,server: {name: "MyAgent",version: "1.0.0",port: 3000,payment: {amount: "10000",// 0.01 USDC per call// payTo defaults to this wallet},},});// Register toolsagent.tool("my-tool","Does a thing",{input: z.string()},async({ input })=>({content: [{type: "text",text: `Result: ${input}`}],}));// Start MCP serverconst{ url }=awaitagent.start();// Register on-chain (once, costs gas)// const { agentId, globalId } = await agent.register({// name: "MyAgent",// description: "...",// x402Support: true,// includeServerEndpoint: true, // auto-adds MCP URL to services// });// Connect to another agentconstclient=awaitagent.connect("eip155:8453:0x8004...#9999");constresult=awaitclient.callTool("some-tool",{});// Verify identityconstverification=awaitagent.verify("eip155:8453:0x8004...#9999");// Check balanceconstbalance=awaitagent.getBalance();// Stop serverawaitagent.stop();1. A looks up B by global ID: "eip155:8453:0x8004...#2376"
└── Reads ERC-8004 registry on Base
└── Gets owner, payment wallet, tokenURI
2. A fetches B's registration file (data URI / IPFS / HTTPS)
└── Verifies back-reference (agentId + registry match)
└── Parses services array → finds MCP endpoint
└── Checks x402Support flag
3. A connects to B's MCP endpoint
└── Uses payment-wrapped fetch (@x402/fetch)
└── First call: normal HTTP request
└── B returns 402 + payment requirements
└── Client auto-signs EIP-3009 authorization (gasless)
└── Retry with X-PAYMENT header
4. B's MCP server verifies payment
└── Extracts signature from X-PAYMENT header
└── Validates EIP-3009 authorization structure
└── (Facilitator settles on-chain)
└── Returns tool result
5. A processes result
└── Payment receipt in X-PAYMENT-RESPONSE header
└── Optional: post feedback to Reputation Registry
| Protocol | Version | Package |
|---|---|---|
| x402 | v2 (CAIP-2) — any ERC-20 via Permit2 + EIP-3009 | @x402/fetch + @x402/evm v2.4.0 |
| ERC-8004 | draft (2025-08-13) | Custom (this SDK) |
| MCP | 2025-06-18 | @modelcontextprotocol/sdk v1.26.0 |
| Contract | Address |
|---|---|
| ERC-8004 Registry | 0x8004A169FB4a3325136EB29fA0ceB6D2e539a432 |
| USDC | 0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913 |
| Permit2 | 0x000000000022D473030F116dDEE9F6B43aC78BA3 |
- Registered on 17 chains (Ethereum, Base, Arbitrum, Polygon, Optimism, Celo, BNB, Gnosis, Linea, Scroll, Taiko, Avalanche, Mantle, Metis, Abstract, Monad, X Layer)
- Wallet: arcabot.eth
- Base agent ID: #2376
| File | Description |
|---|---|
examples/01-register-agent.ts | Register on-chain via ERC-8004 |
examples/02-paid-mcp-server.ts | Build a paid MCP server |
examples/03-mcp-client.ts | Connect to a paid MCP server |
examples/04-full-a3stack.ts | Full A3Stack class demo |
examples/05-agent-to-agent-payment.ts | Full agent-to-agent payment flow |
- Zero-config defaults — Base + USDC sensible defaults, any ERC-20 opt-in
- Bring your own signer — accepts viem Account objects, no key custody
- Modular — each package is standalone, core is opt-in
- Non-custodial — SDK never holds funds; only creates off-chain signatures
- Fail loudly — clear error messages with actionable hints
- Type-safe — full TypeScript throughout, no
any
import{probeAgent}from"@a3stack/core";// Discover what an agent offers before connectingconstinfo=awaitprobeAgent("eip155:8453:0x8004...#2376");console.log(info.verified);// true — on-chain verifiedconsole.log(info.owner);// "0x1be93C..."console.log(info.endpoints.mcp);// "https://mcp.agent.eth/mcp"console.log(info.acceptsPayment);// trueconsole.log(info.services);// [{ name: "MCP", endpoint: "...", version: "2025-06-18" }]console.log(info.registrations);// cross-chain IDsimport{findAllRegistrations}from"@a3stack/core";// Find all registrations for a wallet across all 17+ supported chainsconstregs=awaitfindAllRegistrations("0x1be93C...");// Returns: [{ chainName: "Base", chainId: 8453, agentId: 2376, globalId: "eip155:8453:0x8004...#2376" }, ...]- Reputation Registry — posting/fetching feedback (planned v0.2)
- Validation Registry — zkML/TEE attestations (planned v0.3)
- Agent discovery indexer — off-chain indexing of registrations (planned)
- Streaming payments — Circle streaming USDC (planned v0.2)
- Multi-chain discovery — searching across all ERC-8004 chains (planned)
This SDK is the infrastructure backbone for a turnkey agent infrastructure platform by arcabot.ai.
Contact: arca@arcabot.ai
MIT