Skip to content

mertkaradayi/stellar-x402-facilitator

Repository files navigation

Stellar x402 Facilitator

A fully-functional x402 V1-compliant payment facilitator for the Stellar blockchain.

Status: ✅ PRODUCTION READY

This is a complete implementation of the x402 protocol on Stellar, fully compatible with the Coinbase x402 specification.

What is x402?

x402 is an open payment protocol that leverages the HTTP 402 "Payment Required" status code to enable seamless, internet-native payments. This implementation brings x402 to Stellar.

Quick Start

# Install dependencies
pnpm install

# Terminal 1: Start Redis (required for replay protection)
docker run -d -p 6379:6379 redis

# Terminal 2: Start the facilitator server
pnpm --filter facilitator dev

# Terminal 3: Start the demo app
pnpm --filter demo dev

# Open http://localhost:3000
# Connect your Freighter wallet and click "Pay to Unlock"

The Flow

1. User clicks "Pay to Unlock"
   ↓
2. GET /api/content → HTTP 402 + payment requirements
   ↓
3. User connects Freighter wallet
   ↓
4. App builds Stellar transaction
   ↓
5. User signs in Freighter popup
   ↓
6. App sends X-PAYMENT header with signed transaction
   ↓
7. Facilitator /verify → validates the transaction
   ↓
8. Facilitator /settle → submits to Stellar testnet
   ↓
9. Server returns 200 + content + X-PAYMENT-RESPONSE header
   ↓
10. Content unlocked! 🎉

x402 Spec Compliance

This implementation follows the Coinbase x402 specification:

Requirement Status
402 Response Format
X-PAYMENT Header
X-PAYMENT-RESPONSE Header
Facilitator /verify
Facilitator /settle
Facilitator /supported
Base64 Encoding
XDR Validation
Replay Protection
Settlement Idempotency
Fee Sponsorship (Fee-bump)

See COMPATIBILITY.md for full details.

Project Structure

stellar-x402-facilitator/
├── packages/
│   └── facilitator/           # x402 Facilitator server
│       ├── src/
│       │   ├── index.ts           # Express server (port 4022)
│       │   ├── types.ts           # x402 TypeScript types
│       │   ├── routes/
│       │   │   ├── verify.ts      # POST /verify
│       │   │   └── settle.ts      # POST /settle
│       │   ├── stellar/
│       │   │   ├── verify.ts      # Stellar XDR verification
│       │   │   └── settle.ts      # Stellar settlement + fee-bump
│       │   └── storage/
│       │       ├── redis.ts       # Redis client
│       │       └── replay-store.ts # Replay protection & caching
│       └── package.json
├── apps/
│   └── demo/                  # Next.js demo app
│       ├── app/
│       │   ├── page.tsx       # Pay-to-view UI with Freighter
│       │   └── api/content/   # Protected endpoint (returns 402)
│       └── lib/
│           └── x402.ts        # Client x402 helpers
├── COMPATIBILITY.md           # x402 spec compliance details
└── README.md

API Reference

Facilitator Endpoints

GET /health

Health check endpoint.

GET /supported

List supported (scheme, network) combinations.

// Response (per x402 spec)
{
  "kinds": [
    { "x402Version": 1, "scheme": "exact", "network": "stellar-testnet" }
  ]
}

POST /verify

Verify a payment authorization.

// Request
{
  "x402Version": 1,
  "paymentHeader": "<raw X-PAYMENT header string (base64)>",
  "paymentRequirements": {
    "scheme": "exact",
    "network": "stellar-testnet",
    "maxAmountRequired": "100000",
    "asset": "C...",
    "payTo": "G..."
  }
}

// Response (per x402 spec)
{
  "isValid": true,
  "payer": "GABC..."
}

// Error Response
{
  "isValid": false,
  "invalidReason": "Insufficient amount",
  "payer": "GABC..."
}

POST /settle

Execute a verified payment on the Stellar network.

// Request (same as /verify)
{
  "x402Version": 1,
  "paymentHeader": "<raw X-PAYMENT header string (base64)>",
  "paymentRequirements": { ... }
}

// Response (per x402 spec)
{
  "success": true,
  "payer": "GABC...",
  "transaction": "abc123def456...",
  "network": "stellar-testnet"
}

// Error Response
{
  "success": false,
  "errorReason": "Transaction failed",
  "payer": "GABC...",
  "transaction": "",
  "network": "stellar-testnet"
}

Note: The request supports both paymentHeader (base64 string) and paymentPayload (JSON object) formats for compatibility with different x402 clients.

x402 Headers

  • Request: X-PAYMENT: <base64 encoded PaymentPayload>
  • Response: X-PAYMENT-RESPONSE: <base64 encoded SettlementResponse>

Wallet Setup

Freighter (Recommended)

  1. Install Freighter browser extension
  2. Switch to Testnet in Freighter settings
  3. Fund with testnet XLM:
    https://friendbot.stellar.org?addr=YOUR_PUBLIC_KEY
    

Configuration

Copy the example environment file and customize:

cp packages/facilitator/env.example.local .env

Key settings:

# Server port
PORT=4022

# Redis URL (required for replay protection)
REDIS_URL=redis://localhost:6379

# Fee sponsorship: set this to pay user fees via fee-bump
# Generate at: https://laboratory.stellar.org/#account-creator?network=test
FACILITATOR_SECRET_KEY=S...

# Your Stellar address that receives payments
PAY_TO_ADDRESS=G...

# Asset: "native" for XLM, or contract address for tokens
ASSET_CONTRACT=native

Testing

# Run unit and integration tests
pnpm --filter facilitator test

# Test 402 response
curl http://localhost:3000/api/content
# → HTTP 402 + payment requirements JSON

# Test facilitator health
curl http://localhost:4022/health
# → {"status":"ok","service":"x402-stellar-facilitator"}

# Test supported schemes
curl http://localhost:4022/supported
# → {"kinds":[{"x402Version":1,"scheme":"exact","network":"stellar-testnet"}]}

Features

Feature Status Description
XDR Validation Parses signed transactions to verify payment details
Replay Protection Redis-backed, prevents duplicate payments
Settlement Idempotency Same transaction returns cached result
Fee Sponsorship Optional fee-bump via FACILITATOR_SECRET_KEY
USDC Soroban Token Using native XLM for now

Roadmap

  • USDC Soroban Token support
  • Stellar mainnet deployment
  • SDK package (@stellar/x402-sdk)

Resources

License

MIT

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors