Core implementation of the x402 payment protocol. Provides transport-agnostic client, server, and facilitator components with both async and sync variants.
Install the core package with your preferred framework/client:
# HTTP clients (pick one)
uv add x402[httpx] # httpx client
uv add x402[requests] # requests client
# Server frameworks (pick one)
uv add x402[fastapi] # FastAPI middleware
uv add x402[flask] # Flask middleware
# Blockchain mechanisms (pick one or both)
uv add x402[evm] # EVM/Ethereum
uv add x402[svm] # Solana
# Multiple extras
uv add x402[fastapi,httpx,evm]
# Everything
uv add x402[all]from x402 import x402Client
from x402.mechanisms.evm.exact import ExactEvmScheme
client = x402Client()
client.register("eip155:*", ExactEvmScheme(signer=my_signer))
# Create payment from 402 response
payload = await client.create_payment_payload(payment_required)from x402 import x402ClientSync
from x402.mechanisms.evm.exact import ExactEvmScheme
client = x402ClientSync()
client.register("eip155:*", ExactEvmScheme(signer=my_signer))
payload = client.create_payment_payload(payment_required)from x402 import x402ResourceServer, ResourceConfig
from x402.http import HTTPFacilitatorClient
from x402.mechanisms.evm.exact import ExactEvmServerScheme
facilitator = HTTPFacilitatorClient(url="https://x402.org/facilitator")
server = x402ResourceServer(facilitator)
server.register("eip155:*", ExactEvmServerScheme())
server.initialize()
# Build requirements
config = ResourceConfig(
scheme="exact",
network="eip155:8453",
pay_to="0x...",
price="$0.01",
)
requirements = server.build_payment_requirements(config)
# Verify payment
result = await server.verify_payment(payload, requirements[0])from x402 import x402ResourceServerSync, ResourceConfig
from x402.http import HTTPFacilitatorClientSync
from x402.mechanisms.evm.exact import ExactEvmServerScheme
facilitator = HTTPFacilitatorClientSync(url="https://x402.org/facilitator")
server = x402ResourceServerSync(facilitator)
server.register("eip155:*", ExactEvmServerScheme())
server.initialize()
result = server.verify_payment(payload, requirements[0])from x402 import x402Facilitator
from x402.mechanisms.evm.exact import ExactEvmFacilitatorScheme
facilitator = x402Facilitator()
facilitator.register(
["eip155:8453", "eip155:84532"],
ExactEvmFacilitatorScheme(wallet=wallet),
)
result = await facilitator.verify(payload, requirements)
if result.is_valid:
settle_result = await facilitator.settle(payload, requirements)from x402 import x402FacilitatorSync
from x402.mechanisms.evm.exact import ExactEvmFacilitatorScheme
facilitator = x402FacilitatorSync()
facilitator.register(
["eip155:8453", "eip155:84532"],
ExactEvmFacilitatorScheme(wallet=wallet),
)
result = facilitator.verify(payload, requirements)Each component has both async and sync variants:
| Async (default) | Sync |
|---|---|
x402Client |
x402ClientSync |
x402ResourceServer |
x402ResourceServerSync |
x402Facilitator |
x402FacilitatorSync |
HTTPFacilitatorClient |
HTTPFacilitatorClientSync |
Async variants support both sync and async hooks (auto-detected). Sync variants only support sync hooks and raise TypeError if async hooks are registered.
| Framework | HTTP Client | Server | Facilitator Client |
|---|---|---|---|
| FastAPI | httpx | x402ResourceServer |
HTTPFacilitatorClient |
| Flask | requests | x402ResourceServerSync |
HTTPFacilitatorClientSync |
Mismatched variants raise TypeError at runtime.
Use from_config() for declarative setup:
from x402 import x402Client, x402ClientConfig, SchemeRegistration
config = x402ClientConfig(
schemes=[
SchemeRegistration(network="eip155:*", client=ExactEvmScheme(signer)),
SchemeRegistration(network="solana:*", client=ExactSvmScheme(signer)),
],
policies=[prefer_network("eip155:8453")],
)
client = x402Client.from_config(config)Filter or prioritize payment requirements:
from x402 import prefer_network, prefer_scheme, max_amount
client.register_policy(prefer_network("eip155:8453"))
client.register_policy(prefer_scheme("exact"))
client.register_policy(max_amount(1_000_000)) # 1 USDC maxfrom x402 import AbortResult, RecoveredPayloadResult
def before_payment(ctx):
print(f"Creating payment for: {ctx.selected_requirements.network}")
# Return AbortResult(reason="...") to cancel
def after_payment(ctx):
print(f"Payment created: {ctx.payment_payload}")
def on_failure(ctx):
print(f"Payment failed: {ctx.error}")
# Return RecoveredPayloadResult(payload=...) to recover
client.on_before_payment_creation(before_payment)
client.on_after_payment_creation(after_payment)
client.on_payment_creation_failure(on_failure)server.on_before_verify(lambda ctx: print(f"Verifying: {ctx.payload}"))
server.on_after_verify(lambda ctx: print(f"Result: {ctx.result.is_valid}"))
server.on_verify_failure(lambda ctx: print(f"Failed: {ctx.error}"))
server.on_before_settle(lambda ctx: ...)
server.on_after_settle(lambda ctx: ...)
server.on_settle_failure(lambda ctx: ...)facilitator.on_before_verify(...)
facilitator.on_after_verify(...)
facilitator.on_verify_failure(...)
facilitator.on_before_settle(...)
facilitator.on_after_settle(...)
facilitator.on_settle_failure(...)Register handlers for network families using wildcards:
# All EVM networks
client.register("eip155:*", ExactEvmScheme(signer))
# Specific network (takes precedence)
client.register("eip155:8453", CustomScheme())| Header | Description |
|---|---|
PAYMENT-SIGNATURE |
Base64-encoded payment payload |
PAYMENT-REQUIRED |
Base64-encoded payment requirements |
PAYMENT-RESPONSE |
Base64-encoded settlement response |
| Header | Description |
|---|---|
X-PAYMENT |
Base64-encoded payment payload |
X-PAYMENT-RESPONSE |
Base64-encoded settlement response |
x402.http- HTTP clients, middleware, and facilitator clientx402.mechanisms.evm- EVM/Ethereum implementationx402.mechanisms.svm- Solana implementationx402.extensions- Protocol extensions (Bazaar discovery)
See examples/python.