What is the Wavelength SDK?
What it is
The Wavelength SDK is a TypeScript library for embedding a self-custodial Bitcoin, Lightning, and Ark wallet directly in your web or mobile app. Your users hold their own keys. You do not run a wallet server on their behalf. (Building a pure-native Kotlin or Swift app? The same embedded wallet ships as a native mobile SDK too.)
The full wallet daemon (wavelength) is compiled to run inside your app: to WebAssembly in the browser on web, and into the app binary on mobile. There is no separate process, no local socket, and no backend you must operate to host the wallet logic. Your app boots the daemon and talks to it through a typed client.
The Wavelength SDK ships as these packages:
Package
@lightninglabs/wavelength-coreRole
Shared types, the WavelengthClient interface, errors, and enums. No DOM, no transport.
Package
@lightninglabs/wavelength-webRole
The browser WASM transport. Framework-agnostic: use it from vanilla JS, Vue, Svelte, or React. Re-exports core.
Package
@lightninglabs/wavelength-react-nativeRole
The React Native transport. The daemon is compiled into the app binary. Re-exports core.
Package
@lightninglabs/wavelength-reactRole
React provider and hooks. Depends on core only and takes an injected client, so the same binding can run over the web or React Native transport.
React is the primary developer experience, but React is not required. On web, if you are not using React, install @lightninglabs/wavelength-web, call createWebClient(), and use the WavelengthClient methods directly. The React package is a thin binding over the same interface.
Native iOS and Android apps are covered as well: the wavelength-mobile wrappers embed the same daemon behind idiomatic Kotlin and Swift APIs, documented in the Native iOS & Android section.
Mental model
Think of the Wavelength SDK as your app talking to a local wallet daemon, not your app talking to a remote wallet API.
- Your app calls methods like
balance(),send(), anddeposit()on aWavelengthClient. - The client forwards those calls to the embedded daemon running in your app (on web, in a Web Worker by default, or the main thread if configured).
- The daemon holds keys, tracks VTXOs, coordinates Ark rounds, and reaches out to public infrastructure when it needs chain data, mailbox relay, or Lightning swaps.
The daemon connects to three backend services configured in RuntimeConfig:
- Ark operator + mailbox (
arkServerAddress) for rounds and VTXO/mailbox relay - Swap server (
swapServerAddress) for Lightning↔Ark atomic swaps - Esplora (
walletEsploraUrl) for chain and UTXO queries
On web, the Ark and swap addresses are REST URLs. On React Native, they are
host:port gRPC addresses. walletEsploraUrl is an HTTP Esplora endpoint on
both platforms.
Your app never calls those gateways directly. It only talks to the local daemon. User keys never leave the device. Seed generation, signing, and wallet state live on the device (OPFS in the browser; the app data directory on React Native). The gateways see protocol traffic, not your users’ private keys.
A minimal boot sequence looks like this:
import { createWebClient, defaultConfig } from '@lightninglabs/wavelength-web';
const client = createWebClient({ runtimeBaseUrl: '/wavewalletdk/' });
await client.ready(); // load WASM runtimeawait client.start(defaultConfig('signet')); // boot daemon, connect gatewaysconst { mnemonic } = await client.createWallet({ password: '…' }); // show mnemonic to the user for backupimport { createNativeClient, defaultConfig } from '@lightninglabs/wavelength-react-native';
const client = createNativeClient();
await client.ready(); // ready the native runtimeawait client.start(defaultConfig('signet')); // boot daemon, connect gatewaysconst { mnemonic } = await client.createWallet({ password: '…' }); // show mnemonic to the user for backupFrom here, use the same client for deposits, Lightning receive, sends, and activity. The System architecture page explains how those operations map to Ark, swaps, and on-chain exits.