Skip to content

Presets & self-test

The presets are named sugar over createPaymentGate: say what you’re selling instead of wiring a gate. Each one resolves to a standard gate, so the 402 it builds is byte-identical to the hand-written equivalent — no new wire, no new behaviour, just less to type and a clearer mental model. token defaults to USDC; every other createPaymentGate option (onPaid, exact, receipts, discovery, isUsed/markUsed, …) still works.

createPaywall — a fixed price for a resource

Section titled “createPaywall — a fixed price for a resource”

The API / SaaS / premium-content case: one resource, one price.

import { createPaywall, toWorker } from '@piprail/sdk'
const gate = createPaywall({ chain: 'base', amount: '0.05', payTo: '0xYourWallet' })
// token defaults to USDC. Drive it with any adapter:
export default toWorker(gate, () => Response.json({ report: 'unlocked' }))
OptionRequired?Notes
chainrequiredEVM ('base', 'bnb', …) or a non-EVM family name.
amountrequiredThe fixed price, e.g. '0.05'.
payTorequiredYour receiving address — no private key (receiving needs only the address).
tokendefault 'USDC'A symbol, 'native', or a custom { address, decimals }.
…restoptionalAny other createPaymentGate option (onPaid, exact, receipts, …).

createTipJar — pay what you want (≥ a minimum)

Section titled “createTipJar — pay what you want (≥ a minimum)”

The creator / tip / donation case. The gate is priced at min, and the on-chain verify rejects only an under-payment (amount_too_low) — so a payer can always give more. The minimum is a floor, not a fixed price.

import { createTipJar } from '@piprail/sdk'
const gate = createTipJar({ chain: 'base', min: '1.00', payTo: '0xYourWallet' })
// accepts any payment ≥ 1.00 USDC.

gate.selfTest() — “did I wire this right?”

Section titled “gate.selfTest() — “did I wire this right?””

A read-only config check that never throws and never signs or sends. It resolves the gate’s rails (the same lazy resolution the first challenge() does) and reports what it would charge — or why it can’t. Perfect for a startup assertion or an npm run verify script before you deploy.

const result = await gate.selfTest()
// {
// ok: true,
// rails: [{ network: 'eip155:8453', asset: '0x833…', symbol: 'USDC',
// decimals: 6, amount: '0.05', payTo: '0x…', schemes: ['onchain-proof'] }],
// warnings: [],
// }
if (!result.ok) throw new Error(`Gate misconfigured: ${result.error}`)

A malformed payTo, an unknown token, or an unresolvable chain returns { ok: false, error } — never an exception. A custom token with no built-in symbol is surfaced as a non-fatal warning.

A preset returns the same PaymentGate as createPaymentGate, so drive it with the built-in framework adapterstoFetchHandler for any fetch runtime (Next.js, Netlify, Bun, Deno, Hono, Vercel, …) or toWorker for Cloudflare — or requirePayment for Express.