Skip to main content

Overview

Webhooks deliver real-time event notifications to your application via HTTP POST requests. Use them to react to payments, policy violations, agent status changes, and x402 session events.

Setting Up Webhooks

Via SDK

const webhook = await aw.webhooks.create({
  url: "https://your-app.com/webhooks/agentwallex",
  events: [
    "payment.completed",
    "payment.failed",
    "agent.frozen",
    "policy.violated",
  ],
  secret: "whsec_your_signing_secret",
});

Via API

curl -X POST https://api.agentwallex.com/api/v1/webhooks \
  -H "X-API-Key: awx_your_api_key" \
  -H "Content-Type: application/json" \
  -d '{
    "url": "https://your-app.com/webhooks/agentwallex",
    "events": ["payment.completed", "payment.failed", "agent.frozen", "policy.violated"],
    "secret": "whsec_your_signing_secret"
  }'

Event Types

EventDescription
payment.completedTransaction confirmed on-chain
payment.failedTransaction failed or reverted
payment.pendingTransaction submitted, awaiting confirmation
agent.frozenAgent wallet was frozen
agent.unfrozenAgent wallet was unfrozen
policy.violatedTransaction rejected by policy engine
x402.session.expiredx402 session budget or TTL exceeded
approval.requestedHigh-value transaction awaiting human approval

Webhook Payload

Every webhook delivery includes a JSON payload with this structure:
{
  "id": "evt_abc123",
  "type": "payment.completed",
  "created_at": "2025-06-15T14:30:00Z",
  "data": {
    "transaction_id": "tx_xyz789",
    "agent_id": "agent_abc123",
    "amount": "50.00",
    "token": "USDC",
    "chain": "eip155:8453",
    "hash": "0xabc...def",
    "status": "confirmed"
  }
}

Signature Verification

Every webhook delivery includes a signature header for verification. Always verify signatures before processing webhook events.

How It Works

AgentWallex signs each webhook payload using the secret you provided at registration. The signature is sent in the X-AgentWallex-Signature header.

Verification Example

import crypto from "crypto";

function verifyWebhookSignature(
  payload: string,
  signature: string,
  secret: string
): boolean {
  const expected = crypto
    .createHmac("sha256", secret)
    .update(payload)
    .digest("hex");
  return crypto.timingSafeEqual(
    Buffer.from(signature),
    Buffer.from(expected)
  );
}

// In your webhook handler
app.post("/webhooks/agentwallex", (req, res) => {
  const signature = req.headers["x-agentwallex-signature"] as string;
  const isValid = verifyWebhookSignature(
    JSON.stringify(req.body),
    signature,
    "whsec_your_signing_secret"
  );

  if (!isValid) {
    return res.status(401).send("Invalid signature");
  }

  // Process the event
  const event = req.body;
  console.log(`Received ${event.type} event`);
  res.status(200).send("OK");
});
Always use constant-time comparison (e.g., timingSafeEqual or hmac.compare_digest) when verifying signatures to prevent timing attacks.

Testing Webhooks

Send a test event to your webhook endpoint:
curl -X POST https://api.agentwallex.com/api/v1/webhooks/whk_abc123/test \
  -H "X-API-Key: awx_your_api_key"

Viewing Deliveries

Check the delivery history for a webhook:
curl -X GET https://api.agentwallex.com/api/v1/webhooks/whk_abc123/deliveries \
  -H "X-API-Key: awx_your_api_key"

Managing Webhooks

# List all webhooks
GET /webhooks

# Get a specific webhook
GET /webhooks/:id

# Update a webhook
PUT /webhooks/:id

# Delete a webhook
DELETE /webhooks/:id

Best Practices

Respond to webhook deliveries with a 2xx status code within 5 seconds. If your handler needs to do heavy processing, acknowledge the webhook immediately and process asynchronously.
  • Always verify signatures before processing events.
  • Handle duplicates — Webhook deliveries may be retried. Use the id field for idempotency.
  • Return 200 quickly — Acknowledge receipt before doing heavy processing.
  • Monitor delivery failures — Check the deliveries endpoint for failed deliveries.
  • Use specific event filters — Subscribe only to the events you need rather than receiving all events.