Payment Codes

Redeem Code — Payment Codes

One-time use codes — issuer pre-authorizes, recipient redeems

The Payment Codes model is issuer-initiated. The issuer (payer) connects their EVM wallet, signs an EIP-3009 transferWithAuthorization, and RelAI registers it on SKALE L3 — returning a short 8-character code. The issuer passes the code to the recipient (merchant, cashier, agent). When the recipient enters the code at /redeem, USDC settles instantly — even if the issuer is offline.

Think of it as a digital cheque: the issuer writes it, hands it over, and the recipient cashes it at any time before expiry.

1-use
Familiar UX
Authorize on your phone, hand the code to the cashier — same concept, on-chain
$0
Zero Gas
SKALE L3 registration and L2 settlement — all fees sponsored by RelAI
Offline
Issuer Can Go Offline
Authorization is committed at code creation — issuer does not need to be present at redemption

How It Works

Payment Code flow
1. Issuer connects wallet at /dashboard/payment-codes
↓ signs EIP-3009 authorization (amount, recipient = settler contract)
2. RelAI registers the authorization on SKALE L3 (gasless)
↓ returns 8-char code, valid for configured TTL (default 5 min)
3. Issuer shares the code with the recipient
↓ recipient enters it at /redeem
4. RelAI calls PaymentSettler.settle() on L2 (Base)
↓ USDC moves from issuer to recipient atomically in one tx

Security: The EIP-3009 signature commits the exact amount and the settler contract as recipient. No one can redirect the funds or change the amount. The code alone is sufficient to trigger settlement — keep it private until redemption.

SKALE private settlement: When using the SKALE Base Sepolia network, the settlement transaction is BITE-encrypted — amounts and participants are private on-chain.

Using the Redeem UI

Recipients redeem codes at /redeem. No wallet or login required for the recipient — just the 8-character code.

  1. 1Enter the 8-character code received from the issuer
  2. 2Optionally enter your wallet address as payee (defaults to relayer if blank)
  3. 3Click Redeem — no signature required from the recipient
  4. 4L3 registration confirmed → L2 settlement executes
  5. 5Explorer links for both L3 (SKALE) and L2 (Base) transactions shown on success

Paying a merchant payment request instead? See Pay docs or go to /pay.

Generating Codes (API)

Codes can be generated programmatically via the facilitator API. The issuer must provide a pre-signed EIP-3009 authorization.

POST
/facilitator/payment-codes

Register a pre-signed EIP-3009 authorization and receive an 8-char code.

POST
/facilitator/payment-codes/:code/redeem

Redeem a code. Triggers L2 settlement. Returns tx hashes.

GET
/facilitator/payment-codes/:code

Check code status (active, redeemed, expired).

DELETE
/facilitator/payment-codes/:code

Cancel an active code before redemption.

Generate a payment code
curl -X POST https://api.relai.fi/facilitator/payment-codes \
  -H "X-Service-Key: sk_live_..." \
  -H "Content-Type: application/json" \
  -d '{
    "from": "0xIssuerWallet",
    "signature": "0xEIP3009Signature...",
    "value": 5000000,
    "validBefore": 1735000000,
    "nonce": "0xRandomNonce32Bytes",
    "settlementNetwork": "base-sepolia",
    "ttl": 300
  }'

# Response
{
  "code": "D92T5TPW",
  "validBefore": 1735000000,
  "expiresIn": 300
}
Successful redemption response
{
  "success": true,
  "code": "D92T5TPW",
  "l3TxHash": "0xskale...",
  "l2TxHash": "0xbase...",
  "explorerUrl": "https://basescan.org/tx/0xbase...",
  "settlementNetwork": "base-sepolia",
  "private": false
}

Settlement Networks

NetworkIDL3 RegistrationL2 SettlementPrivacy
Base Sepoliabase-sepoliaSKALE L3 (gasless)Base SepoliaPublic
SKALE Base Sepoliaskale-base-sepoliaSKALE L3 (gasless)SKALE Base Sepolia🔒 BITE encrypted

Error Handling

not_foundCode not found

The code does not exist — check for typos or confirm the issuer generated it successfully.

expiredCode expired

The TTL elapsed. The issuer must generate a new code.

already_redeemedAlready redeemed

This code was already settled. Each code is single-use.

cancelledCode cancelled

The issuer cancelled the code before it was redeemed.

settlement_failedL3 OK · L2 failed

The SKALE L3 registration succeeded but L2 settlement failed. Contact support with the L3 tx hash.