Crypto Billing
Ledgerline supports cryptocurrency payments via NOWPayments, a hosted custodial gateway with 200+ coins. Crypto payments are available for two use cases:
- Platform billing — Ledgerline charges tenants in crypto for their platform subscription/invoices.
- End-customer payments — Tenants can offer crypto as a checkout option for store customers.
Both paths share the same adapter and IPN webhook.
Supported Coins
| Token | Network | Symbol |
|---|---|---|
| Bitcoin | Bitcoin | btc |
| XRP | XRP Ledger | xrp |
| Tether | TRON (TRC-20) | usdttrc20 |
| Tether | Ethereum (ERC-20) | usdterc20 |
| Ethereum | Ethereum | eth |
| Litecoin | Litecoin | ltc |
| Dogecoin | Dogecoin | doge |
| BNB | BNB Smart Chain | bnb |
| MATIC | Polygon | matic |
The live list is fetched from the NOWPayments /currencies endpoint and cached for 24 hours in Valkey. If a coin drops out of the list it will no longer appear as available.
Customer Payment Flow
- Customer selects a crypto coin at checkout.
- Ledgerline calls NOWPayments
POST /invoiceand returns a hosted payment URL. - The customer is redirected to the NOWPayments hosted page, where they see the exact crypto amount and the wallet address.
- NOWPayments monitors the blockchain and fires an IPN webhook to Ledgerline when the payment status changes.
- Ledgerline enqueues an outbox message for the relevant event:
finished→ marks the invoice/order as paid.partially_paid→ flags for manual reconciliation (see runbook).failed/expired→ marks the invoice failed.
Invoice Expiry
NOWPayments invoices expire roughly 20 minutes after creation by default. The adapter uses the expiration_estimate_date from the API response when available. After expiry the customer must start a new checkout.
NOWPayments Fee
0.5% of each transaction, deducted by NOWPayments from the received amount. Ledgerline does not mark up this fee.
Admin Configuration
Environment Variables
| Variable | Required | Description |
|---|---|---|
NOWPAYMENTS_API_KEY | Yes (if crypto enabled) | API key from NOWPayments dashboard → API Keys. |
NOWPAYMENTS_IPN_SECRET | Yes in production | HMAC-SHA512 IPN secret, set in NOWPayments → IPN Settings. |
NOWPAYMENTS_API_URL | No | Override API URL. Defaults to production endpoint. Set to https://api-sandbox.nowpayments.io/v1 for sandbox testing. |
Set all three in the Render Dashboard (never commit them to the repo).
Enabling Crypto Payments
- Create a NOWPayments account at nowpayments.io.
- Obtain an API key from Dashboard → API Keys.
- Set your IPN callback URL in Dashboard → IPN Settings to:
https://<your-render-url>/api/nowpayments/webhook - Copy the IPN secret displayed after saving.
- Set
NOWPAYMENTS_API_KEYandNOWPAYMENTS_IPN_SECRETin Render. - (Optional) Set
NOWPAYMENTS_API_URLto the sandbox URL while testing.
Disabling Crypto Payments
Remove (or leave blank) NOWPAYMENTS_API_KEY. When the key is absent, the CryptoPaymentPort is unbound and the adapter is not instantiated. No crypto invoice creation will be possible. The IPN webhook endpoint will still be registered but will fail gracefully (no outboxService → endpoint not registered).
Reconciliation
Crypto payments are occasionally under-paid due to network fees, exchange rate slippage, or user error. When NOWPayments reports a partially_paid status, Ledgerline enqueues an outbox message of kind nowpayments_partial_payment. This message:
- Does NOT automatically confirm the order.
- Triggers a notification to Michael (platform admin) and the tenant admin.
- Requires manual review — see the crypto incidents runbook.
Sandbox / Test Mode
Set NOWPAYMENTS_API_URL=https://api-sandbox.nowpayments.io/v1 to use the NOWPayments sandbox. The sandbox issues test invoices with fake addresses and simulates payment events. You can trigger payment status changes from the NOWPayments sandbox dashboard.
For local development without a secret, set IS_PRODUCTION=false (the default for CONFIG_ENV != prod). The IPN endpoint will accept unsigned requests so you can fire webhooks manually with curl.