Documentation Index
Fetch the complete documentation index at: https://sigil-10dddbf2.mintlify.app/llms.txt
Use this file to discover all available pages before exploring further.
This guide walks through the two core flows: issuing a credential to an agent, and protecting an API endpoint so only credentialed agents can call it.
Issue a Sigil
A principal calls issueSigil to create an on-chain credential for an agent keypair. The principal’s wallet signs and pays for rent.
import { SigilClient } from '@sigil-xyz/sdk'
import { PublicKey } from '@solana/web3.js'
import BN from 'bn.js'
const client = new SigilClient({ connection, wallet: principalWallet })
const txSig = await client.issueSigil({
agent: new PublicKey('AgentPublicKeyHere...'),
capabilities: [
{
category: 'image-generation',
allowedDomains: ['api.openai.com', 'api.stability.ai'],
},
],
spendLimits: {
perTx: new BN(100_000), // 0.1 USDC per request
perDay: new BN(5_000_000), // 5 USDC daily cap
},
expiresAt: Math.floor(Date.now() / 1000) + 86_400 * 30, // 30 days
})
Spend amounts are in micro-USDC (6 decimal places). 1_000_000 = 1 USDC.
Fetch the credential right after to confirm it’s on-chain:
const sigil = await client.getSigil(agentPublicKey, principalWallet.publicKey)
console.log(sigil.capabilities, sigil.spendLimitPerTx.toString())
Gate an API endpoint
Add the middleware to your server. It verifies the agent’s signature, checks the on-chain Sigil, and records the spend — returning 402 if anything fails.
Express
Next.js App Router
import express from 'express'
import { createSigilMiddleware } from '@sigil-xyz/x402'
import BN from 'bn.js'
const app = express()
app.post(
'/api/generate',
createSigilMiddleware({
connection,
serverWallet,
requiredCapability: 'image-generation',
spendAmount: new BN(50_000), // 0.05 USDC per request
}),
(req, res) => {
// req.sigilAgent → verified agent pubkey (base58)
res.json({ result: 'generated' })
}
)
// app/api/generate/route.ts
import { withSigilAuth } from '@sigil-xyz/x402/next'
import { NextResponse } from 'next/server'
import BN from 'bn.js'
export const POST = withSigilAuth(
async (req) => {
// req.sigilAgent → verified agent pubkey (base58)
return NextResponse.json({ result: 'generated' })
},
{
connection,
serverWallet,
requiredCapability: 'image-generation',
spendAmount: new BN(50_000),
}
)
Call the protected endpoint from an agent
The agent signs each request using buildSigilHeaders and attaches the result as HTTP headers.
import { buildSigilHeaders } from '@sigil-xyz/x402'
import { Keypair } from '@solana/web3.js'
import BN from 'bn.js'
const agentKeypair = Keypair.fromSecretKey(/* agent's secret key */)
const headers = buildSigilHeaders({
agentKeypair,
method: 'POST',
path: '/api/generate',
spendAmount: new BN(50_000),
})
const response = await fetch('https://api.example.com/api/generate', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
...headers,
},
body: JSON.stringify({ prompt: 'a red fox' }),
})
If the Sigil is invalid, revoked, expired, or missing the required capability, the server returns 402 Payment Required:
{
"protocol": "sigil-v1",
"message": "Agent Sigil is invalid or lacks the 'image-generation' capability",
"requiredCapability": "image-generation",
"spendAmount": "50000",
"credentialProgram": "ZFK63KBXDhGCYm5orVo5QiTBaBhWD4PUcUDBG6fjTkH",
"network": "devnet",
"docs": "https://docs.sigil.xyz/x402"
}