Bitcoin Lightning wallet for the command line — zero required runtime npm dependencies, Node.js 18+ built-ins only.
35 commands for custodial and self-custodial (Spark) wallet management, payments, invoices, swaps, L402 paywall operations (consumer + producer), service discovery, and budget controls. It's just a CLI — anything that can run a process and set an environment variable can use it: a shell, a cron job, a Python bot on a VPS, or an AI agent.
- Zero required runtime dependencies — custodial and credential-free commands use only Node.js 18+ built-ins (
node:crypto,node:fs,node:util, etc.); two optional packages power the self-custodialspark-*commands and load only when one runs - 35 commands — balance, payments, invoices, QR codes, swaps, non-custodial (Spark) accounts, L402 consumer + producer, service discovery, budget controls
- Custodial + self-custodial — use a Blink custodial account, or hold your own keys in a Spark account via the Breez SDK
- L402 paywall toolkit — create Lightning paywalls (producer) and pay them (consumer)
- 777 tests, 0 failing —
node:testframework, no test library dependencies - JSON-first output — structured JSON to stdout, status messages to stderr
- AI-agent native — published on ClawHub for OpenClaw/Hermes agents; equally usable by any script or bot
Blink offers two account types. Pick one — the commands you run and the credentials you need differ.
| Custodial | Non-custodial (Spark) | |
|---|---|---|
| Who holds the keys | Blink | You (a 12-word seed) |
| You need | BLINK_API_KEY |
SPARK_MNEMONIC + BREEZ_API_KEY |
| Runtime deps | None (Node 18+ built-ins) | Two optional packages, Node 22+ |
| Balance / history | Blink API | Local, via the Breez SDK (not on the Blink API) |
| Receive | Blink API invoice | Public LNURL-pay on blink.sv — no credentials needed |
| Send | Blink API | Signed locally by the SDK (not on the Blink API) |
Custodial — benefits: simplest setup (one API key, nothing to build); runs on Node 18+; USD/Stablesats wallets and swaps; the full L402 producer/consumer toolkit. Limitations: Blink holds the funds — you trust Blink's solvency and availability, and the API key is the only thing between an attacker and your balance.
Non-custodial — benefits: you hold the keys, so Blink cannot move or freeze
your funds; receive works with no credentials at all (any Blink Lightning
address); send is signed locally with no server signer.
Limitations: whoever has the seed has the funds — lose it and they're gone,
leak it and they're stolen; funds are BTC plus BTKN tokens (USDB — send,
receive, and sats<->token conversions; USD/Stablesats remains custodial-side);
requires Node 22+ and a native module build; and the extra BREEZ_API_KEY.
Both account types share the blink.sv Lightning-address domain — the account
type is not encoded in the address. See
blink/references/non-custodial.md for the
full model.
- Accept Lightning payments anywhere — create invoices, generate QR codes, and receive to a human-readable Lightning address (
you@blink.sv) with no API key and no seed. - Pay and get paid programmatically — send to invoices, Lightning addresses, or LNURL, with fee probing and budget limits so a script never overspends.
- Build and pay L402 paywalls — gate an API or resource behind a Lightning invoice (producer), or let an agent auto-pay for metered access (consumer), with spend controls.
- Run a self-custodial agent wallet — hold keys in a seed, check balance and send BTC without trusting a custodian, via the Breez Spark SDK.
- Automate bitcoin from any environment — a shell script, a cron job, a Python bot on a VPS, or an LLM agent. JSON-first output and budget guardrails let any of them hold and spend within limits you set.
export BLINK_API_KEY="blink_..."
blink balance # wallet balances + USD estimates
blink create-invoice 1000 "Coffee payment" # create a Lightning invoice
blink pay-invoice lnbc... # pay a Lightning invoice
blink price 50000 # convert sats to USD
blink l402-challenge --amount 100 --expiry 3600 # create an L402 paywall challenge
blink l402-verify --token <macaroon>:<preimage> # verify a client's payment proof| Command | Description |
|---|---|
blink balance |
Show BTC and USD wallet balances with pre-computed USD estimates |
blink account-info |
Show account level, spending limits, and wallet summary |
blink transactions |
List recent wallet transactions with pagination |
blink price |
BTC/USD price, currency conversion, and price history (no API key required) |
| Command | Description |
|---|---|
blink pay-invoice <bolt11> |
Pay a BOLT-11 Lightning invoice |
blink pay-lnaddress <addr> <sats> |
Send sats to a Lightning Address (user@domain) |
blink pay-lnurl <lnurl> <sats> |
Send sats to a raw LNURL payRequest string |
blink fee-probe <bolt11> |
Estimate the fee for paying a Lightning invoice without sending |
| Command | Description |
|---|---|
blink create-invoice <sats> [memo] |
Create a BTC Lightning invoice with optional auto-subscribe |
blink create-invoice-usd <cents> [memo] |
Create a USD-denominated Lightning invoice |
blink check-invoice <hash> |
Check payment status of a Lightning invoice by payment hash |
blink subscribe-invoice <bolt11> |
Watch an invoice for payment via WebSocket |
blink subscribe-updates |
Stream account activity updates via WebSocket (NDJSON) |
blink qr <bolt11> |
Generate a QR code for a Lightning invoice (terminal + PNG file) |
Commands for the self-custodial (Spark) account type described in
Two ways to use it. See
blink/references/non-custodial.md for the
full model and the API-growth research.
Receive — no credentials, no seed (works for any Blink Lightning Address,
custodial or non-custodial; uses public LNURL-pay on blink.sv):
| Command | Description |
|---|---|
blink resolve-receiver <identifier> |
Classify a user@blink.sv / bare username as custodial or Spark |
blink create-invoice-lnaddress <addr> <sats> [memo] |
Receive to any Blink address via LNURL-pay + LUD-21 verify (no API key) |
Balance / send / history / events — require the account seed via the Breez
Spark SDK (optional dependency @breeztech/breez-sdk-spark, Node 22+). Set
SPARK_MNEMONIC (12/24 BIP39 words — spend authority, keep secret) and
BREEZ_API_KEY:
| Command | Description |
|---|---|
blink spark-balance |
Show a Spark account BTC balance via the SDK |
blink spark-info |
Show a Spark account info (getInfo) via the SDK |
blink spark-token-info <usdb|id> |
Show BTKN token metadata (name, ticker, decimals) |
blink spark-receive-token <amount> |
Mint a Spark invoice to receive USDB / BTKN tokens |
blink spark-lnaddress get|check|register|delete |
Manage the wallet's @blink.sv Lightning address |
blink spark-send <destination> <sats> |
Sign & send BTC from a Spark account (--dry-run shows fees) |
blink spark-transactions |
List Spark account payments (SDK-local history) |
blink spark-subscribe |
Stream live Spark wallet events |
Getting a BREEZ_API_KEY. The spark-* commands will not connect without
one. It is a Breez infrastructure credential, not custody — it never touches
the seed, cannot sign, and cannot spend. One key works with any seed. Get a free
key via the request form,
or programmatically (the key is emailed to you):
curl -d "fullname=<name>" -d "company=<company>" \
-d "email=<email>" -d "message=<message>" \
https://breez.technology/contact/apikeyThen export BREEZ_API_KEY="..." alongside SPARK_MNEMONIC. See
blink/references/non-custodial.md for the
full detail.
Note: Non-custodial send is signed locally with the seed (no Blink API signer) — BTC to BOLT-11/LNURL/Spark destinations, plus BTKN token sends and sats<->token conversions (
--token,--from-btc,--from-token). Receive works credential-free at any Blink Lightning address. USD (Stablesats) remains custodial-side only.
The spark-* commands and l402-pay --spark need two optional packages. Neither is required for any
custodial command, and neither is loaded unless a spark-* command or l402-pay --spark runs:
npm install # installs optionalDependencies by default@breeztech/breez-sdk-spark(Node 22+) stores wallet state in SQLite viabetter-sqlite3, a native module that is compiled during install. It needspython3,makeand a C++ compiler (build-essentialon Debian/Ubuntu, Xcode command line tools on macOS).bip39validates the seed's BIP39 checksum.
Two install flags will leave you with a broken Spark setup:
| Flag | Effect |
|---|---|
--ignore-scripts |
better-sqlite3 is unpacked but never built. The SDK suppresses the warning, so the install looks fine and every spark-* command then fails at connect time. Fix with npm rebuild better-sqlite3. |
--omit=optional |
Skips both packages. spark-* commands refuse to run rather than proceeding without seed validation. |
Both cases are detected at runtime and reported with the fix, rather than failing obscurely or — worse — continuing unvalidated.
| Command | Description |
|---|---|
blink swap-quote <direction> <amount> |
Get a BTC <-> USD conversion quote (no funds moved) |
blink swap-execute <direction> <amount> |
Execute a BTC <-> USD wallet conversion |
| Command | Description |
|---|---|
blink l402-discover <url> |
Probe a URL for L402 payment requirements (no payment made) |
blink l402-pay <url> |
Fetch an L402-gated resource, paying automatically via Blink |
blink l402-store <subcommand> |
Manage the L402 token cache (~/.blink/l402-tokens.json) |
blink l402-search [query] |
Search L402 service directories (l402.directory, 402index.io) |
blink l402-info <service_id> |
Get full service details + paid health reports |
| Command | Description |
|---|---|
blink l402-challenge --amount <sats> |
Create an L402 payment challenge (invoice + signed macaroon) |
blink l402-verify --token <mac>:<pre> |
Verify an L402 payment token (preimage + HMAC + caveats) |
| Command | Description |
|---|---|
blink budget status |
Show current spend vs rolling limits and remaining budget |
blink budget set --hourly <sats> --daily <sats> |
Set per-hour and per-day spending limits |
blink budget allowlist list|add|remove <domain> |
Manage L402 domain allowlist |
blink budget log [--last N] |
Show recent spending entries |
blink budget reset |
Clear spending history |
git clone https://github.com/blinkbitcoin/blink-skills.git
cd blink-skills
export BLINK_API_KEY="blink_..."
./bin/blink.js balanceOr add to your PATH:
export PATH="$PATH:$(pwd)/bin"
blink balancePublished on ClawHub as blink-wallet — check the registry for the latest served version (the mirror can briefly lag GitHub releases, which are the authoritative source). The older blink skill is deprecated. The full skill manifest and agent instructions are in blink/SKILL.md.
For MCP-native clients (Claude Desktop, Cursor, etc.), see blink-mcp. The CLI is typically 80-100x more token-efficient per agent session than MCP tool calls.
| Variable | Required | Description |
|---|---|---|
BLINK_API_KEY |
Yes (wallet ops) | Blink API key (blink_...). Not needed for price. |
BLINK_API_URL |
No | Override API endpoint. Default: https://api.blink.sv/graphql |
BLINK_L402_ROOT_KEY |
No | 64-char hex root key for L402 producer HMAC signing. Auto-generated to ~/.blink/l402-root-key if not set. |
BLINK_BUDGET_HOURLY_SATS |
No | Max sats spendable in rolling 1-hour window. |
BLINK_BUDGET_DAILY_SATS |
No | Max sats spendable in rolling 24-hour window. |
BLINK_L402_ALLOWED_DOMAINS |
No | Comma-separated domain allowlist for L402 auto-pay. |
Staging / testnet:
export BLINK_API_URL="https://api.staging.blink.sv/graphql"npm test # 777 tests, node:test framework, zero test dependenciesFull command reference, output examples, security model, and agent instructions: blink/SKILL.md
MIT