Skip to main content

Testing Your Integration

Legacy provider

This page covers testing against OpenNode, a legacy per-merchant option. Strike is the default payment provider, and new accounts should start there. Unless you have a specific reason to stay on OpenNode, see Testing Your Strike Integration.

This guide walks you through testing your Lightning Enable integration with OpenNode as your payment provider.

How Testing Works on the Hosted Platform​

Lightning Enable is a hosted platform at api.lightningenable.com, and it connects to OpenNode's production API. That means:

  • Your OpenNode API key must be a production key from app.opennode.com (KYB required).
  • Test payments are small real mainnet payments (e.g., $1). Lightning fees make this cheap, and you keep the funds in your own OpenNode account.
  • OpenNode's dev/testnet environment (app.dev.opennode.com, dev-api.opennode.com) is useful for exploring OpenNode's own API directly, but dev keys cannot be used with the hosted platform.
SettingValue
OpenNode Dashboardapp.opennode.com
Lightning Enable APIhttps://api.lightningenable.com
Bitcoin NetworkMainnet
KYB RequiredYes (OpenNode requirement)

Setup​

Step 1: Configure Your OpenNode Key​

Save your production OpenNode API key in Lightning Enable — via the dashboard (Settings → Payment Provider) or the merchant API:

curl -X PUT https://api.lightningenable.com/api/merchant/opennode-key \
-H "X-API-Key: your-merchant-api-key" \
-H "Content-Type: application/json" \
-d '{ "apiKey": "your-opennode-api-key" }'

Step 2: Validate the Key​

curl -X POST https://api.lightningenable.com/api/merchant/validate-opennode \
-H "X-API-Key: your-merchant-api-key"

A successful response confirms Lightning Enable can reach OpenNode with your key.

Step 3: Get a Lightning Wallet​

You need a Lightning wallet with a small balance to pay test invoices. Any mainnet Lightning wallet works (e.g., Strike, Phoenix, Breez, Wallet of Satoshi, or your own node).

Test Payment Flow​

Create Test Payment​

curl -X POST https://api.lightningenable.com/api/payments \
-H "X-API-Key: your-merchant-api-key" \
-H "Content-Type: application/json" \
-d '{
"orderId": "TEST-001",
"amount": 1.00,
"currency": "USD",
"description": "Test payment"
}'

Response:

{
"invoiceId": "inv_test123",
"orderId": "TEST-001",
"status": "unpaid",
"lightningInvoice": "lnbc10u1p...",
"amountSats": 2500
}

Pay Test Invoice​

  1. Copy the lightningInvoice value
  2. Open your Lightning wallet
  3. Paste or scan the invoice
  4. Confirm payment

Verify Payment​

Check payment status:

curl https://api.lightningenable.com/api/payments/inv_test123 \
-H "X-API-Key: your-merchant-api-key"

Response after payment:

{
"invoiceId": "inv_test123",
"orderId": "TEST-001",
"status": "paid",
"paidAt": "2026-06-29T12:05:00Z"
}

Test Webhooks​

Local Webhook Testing​

Lightning Enable delivers webhooks to your server. To receive them on your development machine before your production endpoint exists, expose your local webhook handler with ngrok:

# Start your webhook handler locally (whatever stack it runs on),
# then expose it:
ngrok http 3000

Configure the ngrok URL as your webhook endpoint via the merchant self-service API:

curl -X PUT https://api.lightningenable.com/api/merchant/webhook-url \
-H "X-API-Key: your-merchant-api-key" \
-H "Content-Type: application/json" \
-d '{
"webhookUrl": "https://abc123.ngrok.io/webhooks/lightning"
}'

Verify Webhook Received​

After a test payment, check your server logs for:

POST /webhooks/lightning
{
"event": "payment.completed",
"data": {
"invoiceId": "inv_test123",
"status": "paid"
}
}

Test Refunds​

Create Refund​

First, generate a Lightning invoice from your wallet (for the refund amount), then:

curl -X POST https://api.lightningenable.com/api/refunds \
-H "X-API-Key: your-merchant-api-key" \
-H "Content-Type: application/json" \
-d '{
"invoiceId": "inv_test123",
"amount": 1.00,
"currency": "USD",
"lightningInvoice": "lnbc..."
}'

Verify Refund​

curl https://api.lightningenable.com/api/refunds/ref_xyz123 \
-H "X-API-Key: your-merchant-api-key"

Test L402 (Optional)​

Create L402 Proxy​

curl -X POST https://api.lightningenable.com/api/proxy \
-H "X-API-Key: your-merchant-api-key" \
-H "Content-Type: application/json" \
-d '{
"name": "Test API",
"targetBaseUrl": "https://httpbin.org",
"defaultPriceSats": 10
}'

Test L402 Flow​

# Get 402 challenge
curl https://api.lightningenable.com/l402/proxy/test-api/get

# Pay the invoice from response
# ...

# Access with L402 credential
curl https://api.lightningenable.com/l402/proxy/test-api/get \
-H "Authorization: L402 <macaroon>:<preimage>"

Testing Checklist​

Basic Integration​

  • Create payment successfully
  • Receive Lightning invoice
  • Pay invoice with a Lightning wallet
  • Status updates to "paid"
  • Webhook received

Webhook Integration​

  • Webhook endpoint accessible
  • Signature verification works
  • Events processed correctly
  • Duplicate handling works

Error Handling​

  • Invalid API key returns 401
  • Invalid request returns 400
  • Not found returns 404
  • Errors have proper format

Refunds (if applicable)​

  • Create refund successfully
  • Refund received in wallet
  • Webhook notification sent

Common Test Scenarios​

Test Expired Invoice​

// Create invoice with short expiry
const payment = await createPayment({
orderId: 'TEST-EXPIRE',
amount: 1.00,
currency: 'USD'
});

// Wait for expiration (default 60 minutes)
// Or check status after expiry
const status = await getPayment(payment.invoiceId);
// status.status === 'expired'

Test Multiple Payments​

// Create multiple payments
const orders = ['ORDER-1', 'ORDER-2', 'ORDER-3'];

for (const orderId of orders) {
const payment = await createPayment({ orderId, amount: 1.00, currency: 'USD' });
console.log(`Created: ${payment.invoiceId}`);
}

Test Partial Refund​

// Original payment: $10
const payment = await createPayment({
orderId: 'ORDER-PARTIAL',
amount: 10.00,
currency: 'USD'
});

// Pay the invoice...

// Partial refund: $3
const refund1 = await createRefund({
invoiceId: payment.invoiceId,
amount: 3.00,
currency: 'USD',
lightningInvoice: 'lnbc...'
});

// Another partial refund: $5
const refund2 = await createRefund({
invoiceId: payment.invoiceId,
amount: 5.00,
currency: 'USD',
lightningInvoice: 'lnbc...'
});

Debugging​

Check OpenNode Dashboard​

  1. Log in to app.opennode.com
  2. Go to Transactions
  3. Find your test payments
  4. View status and details

Verify Webhook Delivery​

Check your own server logs to confirm the webhook POST arrived with a valid X-LightningEnable-Signature header. If a webhook didn't arrive (or you missed it), don't wait — reconcile against the authoritative status:

# Authoritative payment status
curl https://api.lightningenable.com/api/payments/{invoiceId} \
-H "X-API-Key: your-merchant-api-key"

# Or force a re-check against your payment provider
curl -X POST https://api.lightningenable.com/api/payments/{invoiceId}/sync \
-H "X-API-Key: your-merchant-api-key"

Going Live​

After successful testing:

  1. Update your webhook URL from the ngrok tunnel to your production endpoint (PUT /api/merchant/webhook-url)
  2. Verify signature validation is enabled on your production webhook handler
  3. Run one more small real payment against the production endpoint
  4. Monitor initial transactions in the OpenNode dashboard and your own logs

Next Steps​