Get your dream built 10x faster

How to integrate LNBits Wallet with QR Code with OpenClaw

We build custom applications 5x faster and cheaper 🚀

Book a Free Consultation
4.9
Clutch rating 🌟
600+
Happy partners
17+
Countries served
190+
Team members
Matt Graham, CEO of Rapid Developers

Book a call with an Expert

Stuck on an error? Book a 30-minute call with an engineer and get a direct fix + next steps. No pressure, no commitment.

How to integrate LNBits Wallet with QR Code with OpenClaw

To integrate an LNbits wallet into an OpenClaw flow so users can receive a Lightning invoice as a QR code, build an explicit skill in ClawHub that holds the LNbits API key as a secret, have the skill call your LNbits REST API to create an invoice (receive a BOLT11 / payment request), render that BOLT11 as a QR (data URL or file) and return it to the user, and confirm payment either via a validated webhook or safe polling to your LNbits instance. Keep stateful / public HTTP endpoints (webhook receiver, long-running poller, database) outside the agent runtime, validate all webhooks and secrets, and debug by inspecting agent logs, API responses, and credential scopes.

 

 

 Overview: what runs where 

  • OpenClaw skill (runs in the agent runtime): makes authenticated REST calls to LNbits to request invoice creation, generates the QR image bytes (or base64 data URL) and returns that to the user. The skill is lightweight and stateless between requests.
  • External services (must live outside the agent): public webhook receiver (HTTP server), a small database or KV store for long-lived state (invoices, user mapping), an optional background worker for polling invoices if webhooks are unavailable. These are required for production reliability and uptime.
  • Secrets: LNbits API keys (admin or invoice key) must be stored securely in ClawHub/secret store and provided to the skill via environment variables; webhook shared secrets must be stored similarly.

 

 

 Prerequisites 

  • Access to an LNbits instance with an API key that can create invoices. Confirm the authentication method (typically an API key header).
  • A ClawHub account where you can create/configure the OpenClaw skill and save environment secrets (LNbits key, base URL, webhook secret, etc.).
  • Public HTTPS webhook endpoint (if you will receive push notifications). Otherwise plan for a polling approach.
  • Basic runtime (Node.js / Python) for example code and an image/QR generator library.

 

 

 High-level flow 

  • User asks the agent for an invoice (amount, optional memo).
  • The OpenClaw skill reads LNbits credentials from its environment (set in ClawHub), calls LNbits REST API to create an invoice (returns a BOLT11/payment\_request and invoice id).
  • The skill renders a QR from the BOLT11 (base64 PNG or SVG) and returns it to the user (image inline or link to a hosted image).
  • Payment confirmed by either: LNbits calling your webhook (best) or your background poller hitting LNbits’ invoice status endpoint and notifying the user (via the agent’s reply channel or another channel you control).

 

 

 Skill configuration in ClawHub (practical points) 

  • Install/declare the skill in ClawHub and set an environment variable for LNBITS_BASE_URL and LNBITS_API_KEY (or similar). Do not hard-code keys in code.
  • Permissions: Give the skill only the minimal secrets it needs. If ClawHub supports scoped secrets, use an invoice-only key rather than an admin key when possible.
  • Network: If your LNbits instance is private, ensure the agent runtime can reach it (VPC, NAT, allowed IPs).
  • Logging: Enable request/response logging of API calls at debug level (but scrub secrets) so you can inspect LNbits responses when something fails.

 

 

 Example: creating an invoice + generating a QR (Node.js, generic REST) 

Replace placeholders with your LNbits base URL, API key, and confirm the exact LNbits endpoint/field names from LNbits docs. This example uses fetch (Node 18+) and the qrcode package to create a data URL for a PNG.

<b>// install:</b>
<b>// npm install qrcode</b>

import QRCode from "qrcode";

const LNBITS_BASE_URL = process.env.LNBITS_BASE_URL;  <b>// e.g. https://lnbits.example</b>
const LNBITS_API_KEY = process.env.LNBITS_API_KEY;    <b>// store securely in ClawHub</b>

// Create invoice via LNbits REST API (confirm the exact path/fields in your LNbits instance docs)
export async function createInvoice({sats, memo}) {
  const body = {
    <b>// Confirm exact field names for your LNbits instance; common fields are amount/memo.</b>
    amount: sats,
    memo: memo || ""
  };

  const res = await fetch(`${LNBITS_BASE_URL}/api/v1/payments`, {
    method: "POST",
    headers: {
      "Content-Type": "application/json",
      "X-Api-Key": LNBITS_API_KEY
    },
    body: JSON.stringify(body)
  });

  if (!res.ok) {
    const text = await res.text();
    throw new Error(`LNBITS create-invoice failed: ${res.status} ${text}`);
  }

  const data = await res.json();
  <b>// Look for the BOLT11 / payment_request field in the response (names vary: 'payment_request', 'bolt11', etc.)</b>
  const bolt11 = data.payment_request || data.bolt11 || data.payment_request_bech32 || data.bolt_11;
  const invoiceId = data.id || data.uid || data.payment_hash;

  if (!bolt11) throw new Error("No payment request found in LNbits response; inspect response shape.");

  // Create a PNG data URL for the QR
  const qrDataUrl = await QRCode.toDataURL(bolt11, {type: "image/png"});
  return {invoiceId, bolt11, qrDataUrl, raw: data};
}
  • How the agent returns the QR: the skill can return the data URL string directly (small PNGs are OK), return an inline PNG binary if the channel supports it, or upload the PNG to an object store and return a public short-lived link.

 

 

 Payment confirmation: webhook vs polling 

  • Webhook (recommended): If your LNbits instance can POST to a webhook when invoice status changes, register a public HTTPS webhook endpoint. Verify incoming webhooks using a shared secret (HMAC) or check the included API key/headers. On receipt, confirm invoice details by querying LNbits API to avoid trusting unauthenticated payloads.
  • Polling (fallback): If webhooks are not available, run a background worker (outside the agent) that periodically GETs invoice status using invoiceId. When status is "paid", notify the user through whatever channel you use (send message via agent system or external notification).

Example webhook handler (minimal Express):

import express from "express";
const app = express();
app.use(express.json());

const WEBHOOK_SECRET = process.env.WEBHOOK_SECRET;

app.post("/lnbits-webhook", (req, res) => {
  <b>// Verify signature / secret depending on how you configured it with LNbits.</b>
  const incomingSecret = req.header("X-Webhook-Secret");
  if (WEBHOOK_SECRET && incomingSecret !== WEBHOOK_SECRET) {
    return res.status(403).send("Forbidden");
  }

  <b>// Inspect payload and (optionally) re-query LNbits to confirm status</b>
  const payload = req.body;
  console.log("LNbits webhook:", payload);

  <b>// Acknowledge quickly</b>
  res.status(200).send("ok");

  <b>// Then process asynchronously: map invoice -> user, mark paid, notify user</b>
});

Example polling snippet (safe rate, run in external worker):

<b>// Periodically check invoice status and notify when paid</b>
async function pollInvoice(invoiceId) {
  const res = await fetch(`${LNBITS_BASE_URL}/api/v1/payments/${invoiceId}`, {
    headers: { "X-Api-Key": LNBITS_API_KEY }
  });
  const data = await res.json();
  <b>// Inspect data.status (or equivalent) for 'paid' / 'settled'</b>
  return data;
}

 

 

 Security and operational best practices 

  • Least privilege: Use an invoice-only key if LNbits supports it. Don’t ship admin keys in agent code.
  • Secrets in ClawHub: Store LNBITS_API_KEY, webhook secrets, and any S3/host keys in ClawHub secret storage and expose them as environment variables to the skill.
  • Webhook validation: Use HMAC-signed payloads or a shared secret header. If LNbits cannot sign, verify by calling the LNbits API to confirm invoice status and payment amounts.
  • Do not store critical state in the agent runtime: Use an external DB for mapping invoices to users, retries, and notification queues.
  • Rate limiting and backoff: Respect LNbits rate limits; implement exponential backoff and idempotency keys where appropriate.

 

 

 Debugging checklist when things go wrong 

  • Check the agent skill logs in ClawHub for the exact request and response bodies (without printing secrets).
  • Verify the LNbits API key and base URL (test with curl from a trusted host).
  • Confirm response shape from LNbits — find the exact field that contains the BOLT11 string and invoice id.
  • If webhooks don’t arrive: verify public routing, correct webhook URL configured in LNbits, firewall and TLS, and webhook signature if required.
  • If invoice never becomes "paid": confirm the amount and that the payer used the correct network and BOLT11 string; re-query the invoice status via LNbits API to compare.

 

 

 Common pitfalls 

  • Using an API key with insufficient scope (cannot create invoices) — validate the key’s permissions.
  • Assuming the name of invoice fields — confirm the response field names with your LNbits instance docs before parsing.
  • Embedding raw keys in logs or responses — redact secrets.
  • Expecting the agent runtime to be always-on for polling — move long-running pollers out of the agent into an external worker.

Book Your Free 30‑Minute Migration Call

Speak one‑on‑one with a senior engineer about your no‑code app, migration goals, and budget. In just half an hour you’ll leave with clear, actionable next steps—no strings attached.

Book a Free Consultation

Troubleshooting LNBits Wallet with QR Code and OpenClaw Integration

1

OpenClaw LNBits Wallet API 401 Unauthorized when creating invoice with LNBits admin key?

 

Troubleshoot 401 when creating an invoice

 

Direct answer: A 401 usually means the request didn’t present the LNBits API key the endpoint expects (wrong header, wrong key, wrong wallet/instance or revoked key). Confirm you send the correct key in the header the LNBits server expects and call the correct base URL.

  • Check header: Use X-Api-Key (not Bearer/Authorization) unless your deployment documents otherwise.
  • Confirm key belongs to the target wallet/instance and isn’t expired/revoked.
  • Validate URL — test against the same host/environment shown in LNBits UI.
  • Inspect logs and responses for token-related messages and retry with curl to isolate client code problems.

curl example:

# <b>//</b> send invoice creation with X-Api-Key
curl -X POST https://lnbits.example/api/v1/payments -H "X-Api-Key: YOUR_ADMIN_KEY" -H "Content-Type: application/json" -d '{"amount":100,"memo":"test"}'

Node fetch:

/* <b>//</b> Node fetch example */
fetch(url, {method:'POST', headers:{'X-Api-Key':key,'Content-Type':'application/json'}, body:JSON.stringify(body)})

2

OpenClaw QR code modal not displaying after LNBits invoice creation in OpenClaw UI?

 

Direct answer

 

Most often the QR modal doesn’t appear because the frontend never receives a properly shaped LN invoice or the UI event that opens the modal isn’t triggered (network/CORS, runtime error, missing invoice field like payment_request/bolt11). Check the LNBits response, the agent/skill logs, and the browser console/network for the invoice payload and modal trigger.

 

Troubleshoot steps

 
  • Verify LNBits creds & env vars and successful API call in agent logs.
  • Inspect network/console for invoice JSON, CORS, or JS errors.
  • Confirm invoice fields include payment_request/bolt11 and expiry; UI expects that.
  • Check event path (websocket/SSE or REST response) that should notify the UI to open modal.
  • Look at CSS/DOM (z-index/visibility) and modal library errors.
// verify invoice payload and open modal
fetch('/api/latest-invoice').then(r=>r.json()).then(inv=>{
  // ensure expected field exists
  if(inv && (inv.payment_request || inv.bolt11)){
    openQrModal(inv.payment_request || inv.bolt11);
  } else {
    console.error('Missing payment_request/bolt11', inv);
  }
});

3

OpenClaw not receiving LNBits webhook callback for paid invoice — how to configure callback URL and webhook secret?

The direct fix: point LNBits' webhook/callback setting to a publicly reachable HTTPS endpoint that your OpenClaw skill or your external webhook receiver exposes, set a shared webhook secret in the LNBits webhook configuration and put the identical secret into your OpenClaw skill's environment (ClawHub or env var). Make sure the receiver validates the secret/signature, returns HTTP 200 quickly, and that the URL is reachable (use ngrok for local dev) and not blocked by firewall.

 

Checklist and example

 

Follow these concrete steps:

  • Configure callback URL in LNBits to the webhook endpoint (https://your-host/webhook).
  • Set webhook secret in LNBits and store same value in your OpenClaw skill env var (e.g., WEBHOOK_SECRET via ClawHub).
  • Validate and respond — compute HMAC of the raw body with the secret and compare to the signature header LNBits sends; return 200.
  • Debug with ngrok, requestbin, and LNBits delivery logs; watch your receiver logs for 200 vs 4xx/5xx.
const express = require('express');
const crypto = require('crypto');
const app = express();
app.use(express.raw({type: '*/*'})); 
app.post('/webhook', (req, res) => {
  <b>//</b> compute HMAC using shared secret from process.env.WEBHOOK_SECRET
  const sig = req.headers['x-signature'] || '';
  const h = crypto.createHmac('sha256', process.env.WEBHOOK_SECRET).update(req.body).digest('hex');
  if (!crypto.timingSafeEqual(Buffer.from(h), Buffer.from(sig))) return res.status(401).end();
  <b>//</b> process paid invoice payload
  res.status(200).end();
});
app.listen(3000);

4

OpenClaw invoice status stuck on PENDING after LNBits marks invoice as PAID (preimage not found)?

Direct answer: a PENDING invoice after LNBits shows PAID usually means OpenClaw (or your skill) never received the payment preimage or failed to validate it, so it can’t mark the invoice settled. Resolve by retrieving the preimage from LNBits/your node, re-delivering it to the OpenClaw skill or settlement endpoint, and fixing webhook/auth failures so future preimages arrive reliably.

 

Diagnose

 

Check these places:

  • Webhook logs — did OpenClaw receive the LNBits callback?
  • LNBits/payment record — is a preimage present or stored on your node?
  • Auth/signature — was the webhook rejected due to missing keys or mismatched secret?
  • Skill execution logs — did the settlement handler error or time out?

 

Remediation

 

  • Fetch the preimage from LNBits or your wallet and call your settlement handler with that preimage (or re-run the skill with correct env credentials).
  • Add retry and idempotency in the webhook processor so missed deliveries are replayable.
  • Fix environment vars/API keys and webhook signature verification; add alerting on mismatches.
Book a Free Consultation

Still stuck?
Copy this prompt into ChatGPT and get a clear, personalized explanation.

This prompt helps an AI assistant understand your setup and guide you through the fix step by step, without assuming technical knowledge.

AI AI Prompt


Recognized by the best

Trusted by 600+ businesses globally

From startups to enterprises and everything in between, see for yourself our incredible impact.

RapidDev was an exceptional project management organization and the best development collaborators I've had the pleasure of working with.

They do complex work on extremely fast timelines and effectively manage the testing and pre-launch process to deliver the best possible product. I'm extremely impressed with their execution ability.

Arkady
CPO, Praction
Working with Matt was comparable to having another co-founder on the team, but without the commitment or cost.

He has a strategic mindset and willing to change the scope of the project in real time based on the needs of the client. A true strategic thought partner!

Donald Muir
Co-Founder, Arc
RapidDev are 10/10, excellent communicators - the best I've ever encountered in the tech dev space.

They always go the extra mile, they genuinely care, they respond quickly, they're flexible, adaptable and their enthusiasm is amazing.

Mat Westergreen-Thorne
Co-CEO, Grantify
RapidDev is an excellent developer for custom-code solutions.

We’ve had great success since launching the platform in November 2023. In a few months, we’ve gained over 1,000 new active users. We’ve also secured several dozen bookings on the platform and seen about 70% new user month-over-month growth since the launch.

Emmanuel Brown
Co-Founder, Church Real Estate Marketplace
Matt’s dedication to executing our vision and his commitment to the project deadline were impressive. 

This was such a specific project, and Matt really delivered. We worked with a really fast turnaround, and he always delivered. The site was a perfect prop for us!

Samantha Fekete
Production Manager, Media Production Company
The pSEO strategy executed by RapidDev is clearly driving meaningful results.

Working with RapidDev has delivered measurable, year-over-year growth. Comparing the same period, clicks increased by 129%, impressions grew by 196%, and average position improved by 14.6%. Most importantly, qualified contact form submissions rose 350%, excluding spam.

Appreciation as well to Matt Graham for championing the collaboration!

Michael W. Hammond
Principal Owner, OCD Tech

We put the rapid in RapidDev

Need a dedicated strategic tech and growth partner? Discover what RapidDev can do for your business! Book a call with our team to schedule a free, no-obligation consultation. We’ll discuss your project and provide a custom quote at no cost.Â