EN

Accepting USDT in WHMCS: a crypto payment gateway step by step

Accepting USDT in WHMCS

Hosting, VPS and domain clients increasingly ask to pay in crypto, most often in USDT. This guide shows how to add crypto as a payment gateway in WHMCS 8.x or 9.x: the client opens an unpaid invoice, presses Pay Now, pays on the SnapEX Pay page in USDT on TRON, Ethereum, BSC, Solana, TON, Polygon or another network, or in another coin, and WHMCS marks the invoice paid by itself. You don't run a wallet or a blockchain node — the money lands in your SnapEX Pay merchant balance in USDT.

How a payment goes

client → unpaid invoice → Pay Now
WHMCS → SnapEX Pay: invoice in USD
client → pays on the SnapEX Pay page
SnapEX Pay → signed webhook → WHMCS
module → GET invoice from the API → paid?
WHMCS: invoice Paid
  1. The client presses Pay Now on the invoice. Only then does the module create a SnapEX Pay invoice for the amount due in USD and send the client to the payment page.
  2. The client chooses a coin and network and pays. When the invoice is paid, SnapEX Pay sends a signed webhook to your WHMCS.
  3. The module re-reads the invoice from the SnapEX Pay API and adds the payment only if the invoice is paid for the right amount. The webhook body alone never marks anything paid.

An invoice is marked paid three independent ways, whichever comes first: the signed webhook, the client returning from the payment page, and a check on WHMCS cron runs (each pending payment at most every 10 minutes, for 5 days). A lost webhook never leaves a paid invoice unpaid, and a payment is never added twice — even if the webhook, the return page and cron fire at the same moment.

What you need

  • WHMCS 8.x or 9.x with the system cron running (the same cron WHMCS needs for its own automation).
  • PHP 7.4 or newer with cURL.
  • HTTPS on the WHMCS address, so SnapEX Pay can deliver webhooks to it.
  • A SnapEX Pay merchant account: sign up at pay.snapex.pro.

Step 1. Upload the module

Download snapexpay-whmcs-1.1.0.zip (free) and unpack it into the WHMCS root folder, keeping the paths. Over SSH:

cd /path/to/whmcs
curl -fsSLO https://pay.snapex.pro/downloads/whmcs/snapexpay-whmcs-1.1.0.zip
unzip snapexpay-whmcs-1.1.0.zip -x README.md
rm snapexpay-whmcs-1.1.0.zip

These files should appear:

modules/gateways/snapexpay.php
modules/gateways/snapexpay/
modules/gateways/callback/snapexpay.php
includes/hooks/snapexpay.php

The file in includes/hooks/ is the cron check; without it, payments are still applied by the webhook and on the client's return, but you lose the safety net. With FTP or a hosting file manager, upload the same folders over the WHMCS root. The module creates its own table on first use: nothing to run in the database by hand.

Step 2. Get an API key

In the SnapEX Pay merchant cabinet open Developers and create an API key. The module needs the invoices.read and invoices.write scopes; a key created in the cabinet gets all Merchant API permissions, these included. The key is shown once — copy it right away. Reissuing the key revokes the old one at once, so update it in WHMCS at the same moment.

Step 3. Activate the gateway

In the WHMCS admin area open System Settings → Payment Gateways → All Payment Gateways and click SnapEX Pay (Crypto). Then, on the Manage Existing Gateways tab, fill in:

Setting What to put
API key The key from step 2.
Webhook secret See step 4.
Network fee paid by Merchant — the client pays exactly the invoice amount, and the fees are taken from what you receive. Client — the SnapEX Pay fee and the network fee are added on top. More: Who pays the fees on a crypto invoice.
Payment window, minutes How long the SnapEX Pay page stays valid: 1 to 1440, 60 by default.
Test mode See step 6.
Partner ID See step 7.
API URL Leave as is.

The client sees the gateway as SnapEX Pay (Crypto); you can rename it in the Display Name field.

Step 4. Set up the webhook

The webhook is optional but recommended: with it, an invoice turns Paid as soon as the payment is confirmed, not on the next cron run.

  1. Copy the webhook address shown under the Webhook secret field in WHMCS. It looks like https://<your WHMCS>/modules/gateways/callback/snapexpay.php.
  2. In the cabinet, on the Developers page, paste it as the webhook URL and save.
  3. The whsec_… signing secret is shown once, right after the first save. Paste it into Webhook secret in WHMCS and save the gateway.

How the module checks a notification:

  • the Webhook-Signature header: HMAC-SHA256 of {Webhook-Timestamp}.{raw request body} with your secret; a missing or wrong signature gets 401;
  • Webhook-Timestamp within 5 minutes of the server clock (older gets 400) — keep NTP on;
  • the invoice itself, re-read from the SnapEX Pay API with your key.

If the API can't be reached at that moment, the module answers 502, and SnapEX Pay retries the delivery. The cabinet has one webhook URL per account; events for invoices the module didn't create are answered 200 and skipped, so the same merchant account can also serve a shop or a bot. More about signatures and retries: Crypto payment webhooks.

Step 5. If WHMCS bills in another currency

SnapEX Pay invoices are in US dollars. If your default currency is EUR, RUB or anything else:

  1. Make sure USD exists in System Settings → Currencies and its exchange rate is up to date (WHMCS can update rates automatically).
  2. In the gateway settings set Convert To For Processing to USD.

The client pays the USD equivalent, and the payment is still recorded on the invoice in the client's currency, for the full amount due. Without this setting the Pay Now button is replaced by the note SnapEX Pay: set "Convert To For Processing" to USD in the gateway settings.

Step 6. A test payment without real money

  1. Turn on Test mode in the gateway settings. From now on only someone logged in to the WHMCS admin area can start a payment; other clients see SnapEX Pay is in test mode instead of the button, so nobody pays a real invoice by accident.
  2. In the same browser, open an unpaid invoice of a test client (for example, through Login as Owner on the client's profile) and press Pay Now — next to it there is a (test mode) note.
  3. The SnapEX Pay page has a Test label. Pick any coin and network: the page shows a test address, and in about 10 seconds the payment confirms by itself. You don't send anything.
  4. The invoice should turn Paid, and Billing → Gateway Log gets a Successful entry. If not, look at the log and at the delivery log on the Developers page in the cabinet.
  5. Turn test mode off.

Test payments are never applied once test mode is off (the log says Test payment while test mode is off — not applied), so test money can't pay for real services. More: How to test crypto payments without real money.

Step 7. Partner ID: who set up the module

The Partner ID field is optional. If you set up WHMCS for your own hosting company, leave it empty.

If you are an integrator or a WHMCS freelancer and set up billing for clients, paste your Partner ID: the client's merchant account is bound to you, and you get 35% of our fee on that client's payments. The client creates their own SnapEX Pay account and API key, and the money goes to their balance. Terms: SnapEX Pay partner program.

What the client sees

  • On an unpaid invoice — SnapEX Pay (Crypto) among the payment methods and the Pay Now button.
  • The SnapEX Pay payment page: USDT on TRC20, ERC20, BEP20, Solana, TON, Polygon and other networks, and other coins (60+ in total), if SnapEX Pay offers them for the invoice amount.
  • After paying, the client is sent back to the invoice. If the payment is already confirmed, WHMCS shows it as paid right away; otherwise it turns Paid on the webhook or the next cron check.
  • Pressing Pay Now again while the payment page is still valid opens the same page, not a second invoice. After it expires, a fresh one is created.

What lands in WHMCS

  • Paid in full → the payment is added to the invoice in the invoice currency and the invoice is Paid. The transaction ID is the SnapEX Pay invoice ID (INV-…), so you can find the payment in the cabinet.
  • Paid partly (the client sent less and didn't top up in time) → nothing is added automatically; the Gateway Log has Partial payment — review and apply manually with the coin, network and amount received. What you received is in your SnapEX Pay balance; add the payment in WHMCS by hand if you accept it. How underpayments work: The customer sent less than the invoice.
  • Not paid in time → the Gateway Log has Expired, the WHMCS invoice stays Unpaid, and the client can press Pay Now again.
  • Extra payment after the SnapEX Pay invoice closed → with the webhook set up, a Gateway Log entry Extra payment received — check the SnapEX Pay cabinet; the money is in your SnapEX Pay balance.
  • The invoice changed after the client opened the payment (for example, you added an item) → the old payment is not applied to the new amount (Amount mismatch — not applied); the client presses Pay Now again for the new amount.

If something doesn't work

  • The client sees "set Convert To For Processing to USD". Step 5: the invoice currency isn't USD and there's no conversion.
  • Clients don't see the button, only "SnapEX Pay is in test mode". Test mode is still on.
  • "Could not start the crypto payment: …". SnapEX Pay rejected the invoice — most often a wrong or revoked API key; the reason is in the message and in the Gateway Log (Error creating payment).
  • The webhook gets 401. The webhook secret in WHMCS doesn't match the cabinet one.
  • The webhook gets 400 "stale or missing timestamp". The server clock is off.
  • The webhook gets 503. Either the gateway isn't activated in WHMCS, or the URL is set in the cabinet but Webhook secret is empty.
  • A paid invoice turns Paid only after a while. No webhook: the payment was picked up by the cron check. Set up step 4 and check that the WHMCS cron runs.

Everything the module does is in Billing → Gateway Log. To remove the module, deactivate the gateway in WHMCS and delete the four paths from step 1.

Cost

1% per payment plus a fixed network fee that depends on the coin and network; no setup fee and no monthly fee. The module is free.

Module page: WHMCS. Choosing a gateway for hosting: How to choose a crypto payment gateway for a hosting company. Overview for hosting providers: Crypto payments for hosting. Sign-up: pay.snapex.pro.

More guides

Accepting USDT in WooCommerce: a crypto payment plugin step by step How to add crypto payments to WooCommerce with the free SnapEX Pay plugin from the WordPress.org catalog: install, API key, webhook, a non-USD store, a test order without real money, order statuses. Customers pay in USDT or 60+ coins, and the order is marked paid automatically. Accepting USDT in BILLmanager: crypto payments for hosting step by step How to connect SnapEX Pay crypto payments to BILLmanager 6: installing the module, API key, webhook, Partner ID, a test payment without real money, fees and what the client sees. Clients pay in USDT or 60+ coins, and the payment is credited automatically. Selling VPN subscriptions through a Telegram bot for USDT: setup step by step How to launch the SnapEX Pay Telegram VPN bot: plans, API key, Marzban, 3x-ui or Remnawave connection, HTTPS webhook and a test purchase without real money. The customer pays in USDT and gets the subscription link in the same chat. VPN subscription renewals paid in crypto: extend users without duplicates or lost days How the SnapEX Pay modules for Marzban, 3x-ui, Remnawave and the Telegram VPN bot handle a returning customer: which expiry the new days count from, what happens to traffic, configs and repeated webhooks. Crypto payments in Xboard and V2Board: accept USDT for VPN subscriptions step by step How to connect SnapEX Pay to an Xboard or V2Board panel: install the plugin, add the payment method, set up the webhook, convert CNY or other prices to USD and run a test order without real money. Crypto payment webhooks: verify the signature, handle retries and duplicates How SnapEX Pay webhooks are signed and delivered, how to verify them in PHP and Node.js, and how to make your handler safe against retries, duplicates and out-of-order events. The customer sent less than the invoice: how crypto underpayments work Exchanges often deduct their withdrawal fee from the amount, so a crypto invoice arrives short. What SnapEX Pay does with an underpayment, which webhooks you get and what to do with the order. How to choose a crypto payment gateway for a hosting company: 8 questions to ask A checklist for hosting and VPS providers choosing a crypto payment gateway: billing module, how paid invoices get marked paid, underpayments, fees, settlement, coins, test mode and multi-currency billing. SnapEX Pay vs NOWPayments, Cryptomus and CoinGate: fees and ready-made modules compared How SnapEX Pay compares with NOWPayments, Cryptomus and CoinGate on the published fee, monthly fees and ready-made modules for hosting billing, VPN panels and stores. Competitor data from their own websites, 11 October 2026. How to test crypto payments without real money Test invoices in SnapEX Pay go through the same statuses and send the same webhooks as live ones, but confirm by themselves and never touch your balance. Here is how to use them. Who pays the fees on a crypto invoice: you or your customer SnapEX Pay lets you choose per invoice who covers the service fee and the network allowance. What fee_on does, how it changes the amount the customer pays and the amount you receive.

Ready to accept crypto?

Create a merchant account and get an API key. 1% per payment, no monthly fee.