Guide

How to Add Crypto Payments (USDT) to WordPress and WooCommerce

KriptoGo Team··3 min read

WooCommerce lets you add a payment method with one PHP class. Combined with a crypto gateway that gives you a hosted checkout page and signed webhooks, you can accept USDT on a store in an afternoon without touching the theme.

Overview

The flow is the standard one: when the customer chooses "Pay with crypto (USDT)" and places the order, your plugin creates a KriptoGo invoice from the server, stores the invoice id on the order and redirects the customer to the hosted checkout page. When KriptoGo confirms the payment, it calls your webhook; the plugin verifies the signature and marks the order as processing or completed.

Plugin skeleton

Create wp-content/plugins/kriptogo-payments/kriptogo-payments.php with the standard plugin header. Hook into plugins_loaded to define the gateway class only when WooCommerce is active, and add the class name to the woocommerce_payment_gateways filter. Register the webhook route with register_rest_route under a namespace like kriptogo/v1.

Settings and keys

Use the gateway's init_form_fields to add fields for the API key and secret key. WooCommerce stores them with get_option. If you prefer, read them from constants in wp-config.php so they never sit in the database. Either way, keep them out of the theme and out of any client-side script.

The payment gateway class

class-wc-gateway-kriptogo.php
class WC_Gateway_KriptoGo extends WC_Payment_Gateway {
    public function __construct() {
        $this->id                 = 'kriptogo';
        $this->method_title       = 'Crypto (USDT TRC-20)';
        $this->method_description = 'Accept USDT on the TRON network via KriptoGo.';
        $this->has_fields         = false;
        $this->init_form_fields();
        $this->init_settings();
        $this->title   = $this->get_option('title', 'Pay with crypto (USDT)');
        $this->api_key = $this->get_option('api_key');
        add_action('woocommerce_update_options_payment_gateways_' . $this->id, [$this, 'process_admin_options']);
    }
}

process_payment: creating the invoice

process_payment()
public function process_payment($order_id) {
    $order = wc_get_order($order_id);
    $res = wp_remote_post('https://kriptogo.com/api/create-invoice', [
        'headers' => ['Content-Type' => 'application/json'],
        'body'    => wp_json_encode([
            'apiKey'      => $this->api_key,
            'amount'      => (float) $order->get_total(),
            'callbackUrl' => rest_url('kriptogo/v1/webhook'),
            'returnUrl'   => $this->get_return_url($order),
        ]),
        'timeout' => 15,
    ]);
    $inv = json_decode(wp_remote_retrieve_body($res), true);
    if (empty($inv['checkout_url'])) { wc_add_notice('Could not start the crypto payment. Please try again.', 'error'); return; }
    $order->update_meta_data('_kriptogo_invoice_id', $inv['invoice_id']);
    $order->update_status('pending', 'Awaiting USDT payment.');
    $order->save();
    return ['result' => 'success', 'redirect' => $inv['checkout_url']];
}

The store's currency should be USD or the total should be converted to USDT before the call; the invoice amount is always in USDT.

The webhook endpoint

REST route callback
function kriptogo_webhook(WP_REST_Request $req) {
    $raw = $req->get_body();
    $expected = hash_hmac('sha256', $raw, get_option('woocommerce_kriptogo_settings')['secret_key']);
    if (!hash_equals($expected, $req->get_header('x-kriptogo-signature') ?? '')) return new WP_REST_Response('bad signature', 401);
    $data = json_decode($raw, true);
    $orders = wc_get_orders(['meta_key' => '_kriptogo_invoice_id', 'meta_value' => $data['invoice_id'], 'limit' => 1]);
    if ($orders && $data['status'] === 'PAID' && !$orders[0]->is_paid()) {
        $orders[0]->payment_complete($data['tx_hash']);
        $orders[0]->add_order_note('Paid ' . $data['paid_amount'] . ' USDT via KriptoGo.');
    }
    return new WP_REST_Response('ok', 200);
}

Set permission_callback to __return_true for this route; the signature is the authentication. The is_paid() check makes repeated deliveries harmless.

Order statuses

Pending while the invoice is open; processing or completed after payment_complete() depending on whether the products are virtual. If the invoice expires without payment, WooCommerce's pending-order timeout cancels it automatically, or you can cancel it from a scheduled check of the status endpoint.

Checkout UX

Name the method clearly ("Pay with crypto - USDT on TRON") and add a short description that only TRC-20 USDT is accepted and that the payment page opens after the order is placed. The hosted page handles QR codes and countdowns, and the return URL brings the customer back to the order-received page.

Testing and go-live

Place a low-value order, pay it, and watch the order note appear. Send a request with a wrong signature to the webhook URL and confirm a 401. Check that a second delivery does not add a second note. Then enable the method for customers. If you build the plugin with an AI tool, the WordPress option in the dashboard prompt generator produces exactly this structure.

Regulatory noteThe use of crypto assets for payments is regulated differently from country to country, and some jurisdictions restrict it. This article is a technical guide, not legal or tax advice. Confirm with a professional that your activity complies with the laws of the country you operate in.

Frequently asked questions

Is there an official KriptoGo WooCommerce plugin?

The integration is a small custom plugin as shown here, and the dashboard's setup prompt can generate it for you. It is about a hundred lines of PHP.

My store currency is not USD. What do I do?

Convert the order total to USD at your chosen rate before creating the invoice, and store the rate on the order for your records. The invoice amount must be in USDT.

Can I use this without WooCommerce?

Yes. On plain WordPress, add a form that posts to a small PHP endpoint that creates the invoice, and a REST route for the webhook, as in the PHP examples in the docs.

Accept crypto payments in 30 minutes with KriptoGo

No setup fee, no monthly fee. Just 1% on successful payments.

Create a free account