# crypt.pe Python SDK

> **crypt.pe** — the non-custodial crypto payment gateway with **0% transaction fees**. Payments settle wallet-to-wallet on-chain, directly to a wallet you control. The hosted alternative to running BTCPay Server. Accept BTC, ETH, SOL, USDT, USDC and 24 coins across 13 chains with a Stripe-style API.

- Website: https://crypt.pe · Docs: https://crypt.pe/docs · Plain-text spec: https://crypt.pe/docs.md
- Free API key (no KYC): https://crypt.pe/signup

## Install

Single file, **stdlib only** — no `requests`, nothing to pip install (Python 3.8+):

```bash
curl https://crypt.pe/api/sdk/python -o cryptpe.py
```

## Quick start — accept a crypto payment

```python
import os
from cryptpe import Cryptpe, CryptpeError

cryptpe = Cryptpe(os.environ["CRYPTPE_SECRET_KEY"])  # sk_live_...

# 1. Create an order and redirect the customer to checkout
order = cryptpe.payments.create(
    amount_usd=25.0,
    accepted_coins=["btc", "usdt-trc20"],
    return_url="https://your-site.com/thanks",
    webhook_url="https://your-site.com/hooks/cryptpe",
    metadata={"order_ref": "1234"},
)
print(order["checkout_url"])  # send the payer here

# 2. Verify signed webhooks (FastAPI example)
from fastapi import Request, HTTPException

@app.post("/hooks/cryptpe")
async def hook(request: Request):
    raw = await request.body()  # raw bytes — do NOT re-serialise
    try:
        event = cryptpe.webhooks.verify(
            raw_body=raw,
            signature=request.headers["x-cryptpe-signature"],
            secret=os.environ["CRYPTPE_WEBHOOK_SECRET"],  # whsec_...
        )
    except CryptpeError as e:
        raise HTTPException(400, f"signature: {e}")
    if event["type"] == "payment.confirmed":
        fulfill(event["data"]["order_id"])
    return {"ok": True}
```

## Why non-custodial?

| | crypt.pe | custodial gateways (BitPay, Coinbase Commerce) |
|---|---|---|
| transaction fee | **0%** (flat plans, free tier) | 1–2% per sale |
| who holds funds | **you** — wallet-to-wallet | the platform, until payout |
| account freezes | structurally impossible | possible |
| settlement | instant on-chain | batch / withdrawal |

## API surface

SDK methods: `payments.create(amount_usd, accepted_coins, ...)` · `payments.retrieve(order_id)` · `payments.refund(order_id, tx_hash=...)` (records an on-chain refund you already sent — crypt.pe never moves funds) · `payments.cancel(order_id)` · `webhooks.verify(raw_body=, signature=, secret=)` (raises `CryptpeError` on tampering/replay, returns the parsed event).

Additional REST endpoints (same `Authorization: Bearer sk_live_...` header): `POST /api/v1/payments/{id}/verify-tx` (rescue a payment by tx hash) · `POST /api/v1/payments/{id}/test-pay` (sandbox) — full spec: https://crypt.pe/docs.md

Keywords: crypto payment gateway API python, non-custodial payments, accept bitcoin python, USDT payment API, 0% fee crypto checkout, BTCPay Server alternative, Stripe crypto alternative.
