Fast anonymous email accounts powered by Bitcoin Lightning Network payments. Get a private disposable email address in seconds - no personal information required, just pay with Bitcoin Lightning and start sending and receiving emails immediately.
- Fast & Anonymous: Get your email address instantly after Bitcoin Lightning payment - no signup, no verification
- Bitcoin-Powered Privacy: Pay with Lightning Network for maximum anonymity and speed
- Send & Receive: Full email functionality with Lightning payments for outgoing messages
- One-Year Duration: Email accounts valid for one year with renewal option
- Secure Access: Token-based authentication with no password storage
- API Access: Complete REST API for programmatic email management
- Core service handling Lightning Network payments, email management, and user authentication
- Connects to LND for Bitcoin Lightning payments via
LNDService - Manages email accounts and SMTP sending via
EmailService - Provides RESTful API endpoints for email reading, sending, and account management
- Uses SQLite with SQLModel ORM and Alembic migrations
- Stores email accounts, access tokens, payment status, and pending outgoing emails
- Manages expiration dates for accounts and email send payments
- Manages asynchronous tasks via task queue
- Handles Lightning payment verification via
check_payment_status - Processes email account creation after successful Bitcoin payment
- Handles outgoing email delivery after Lightning payment confirmation
- Creates individual email accounts via IPC (Inter-Process Communication)
- Uses file-based requests between services with locking mechanism
- Reads emails via IMAP protocol
- Sends emails via SMTP with authentication
- Account creation and Lightning payment interface (
index.html) - Email reading and composition interface (
inbox.html) - Static assets (CSS, JavaScript) for frontend functionality
-
Create Email Account
POST /api/v1/email- Generates Bitcoin Lightning invoice
- Returns invoice details, payment hash, and preliminary account info
-
Check Payment Status
GET /api/v1/payment/{payment_hash}- Returns Lightning payment status and account details if paid
-
List Emails
GET /api/v1/emails- Requires access token authentication
- Returns list of email headers
-
Get Email Content
GET /api/v1/emails/{email_id}- Requires access token authentication
- Returns email content with HTML stripped
-
Send Email
POST /api/v1/email/send- Requires access token authentication
- Generates Lightning invoice for email sending
-
Check Send Payment Status
GET /api/v1/email/send/status/{payment_hash}- Returns status of outgoing email Lightning payment
-
Get a New Invoice (different provider)
POST /api/v1/email/{payment_hash}/new-invoice(signup)POST /api/v1/email/send/{payment_hash}/new-invoice(send, authenticated)POST /api/v1/account/renew/{payment_hash}/new-invoice(renewal, authenticated)- Re-issues the invoice for a still-pending payment from a different
payment provider when one is configured, so a user who cannot pay the
current invoice can get a fresh one ("Can't pay this invoice? Get a
new one"). Optional JSON body:
{"exclude_provider": "<name>"}(and"years"for renewals). The invoice responses include aproviderfield naming the issuing provider.
All email access endpoints require a valid access token passed in the Authorization header:
Authorization: Bearer {access_token}
- Send & Receive: Full email functionality with Lightning payments for sending
- Web & API Access: Emails accessible through web interface and REST API
- Plain Text Focus: HTML content is stripped for security; emails are displayed as plain text
- Lightning Payments: Small Lightning payments required for each outgoing email
The EmailService class handles:
- Account creation via IPC with mail system
- Email listing and fetching via IMAP
- Email sending via SMTP with authentication
- Secure file-based inter-process communication with proper permissions handling
- Email header decoding for internationalization support
The system uses:
- A pluggable payment backend (
src/lnemail/services/payments/): the self-hosted LND node, one or more Nostr Wallet Connect (NWC) wallets, or a mix with automatic fallback. - Background job processing for Lightning payment verification
- Separate payment flows for account creation and email sending
Selected via environment variables:
PAYMENT_BACKEND-lnd(default) for the self-hosted node, ornwc/multito use NWC wallet(s).NWC_CONNECTIONS- newline- or comma-separatednostr+walletconnect://URIs. These are third-party providers. Do not wrap the value in quotes in the docker-composeenvironment:list form (- KEY=value): the quotes become part of the value. Surrounding quotes are stripped defensively, but prefer an unquoted value or theKEY: "value"mapping form.NWC_PRIMARY_CONNECTION- optional preferred URI, always tried first with the rest used only as fallback on error.NWC_ONLY- if true, do not include the LND node as a provider.
When several providers are configured, invoices are created on the primary (if set) and otherwise on a randomly chosen provider, falling back to the next one on error. Settlement is checked across all providers (a payment hash is specific to the wallet that issued it).
Privacy: NWC wallets are third parties, so they are treated as untrusted and only ever receive a generic invoice memo. The descriptive memo (which may contain the email address, access token, or recipient) is passed only to the self-hosted LND node.
-
Data Protection
- Emails stored in individual user mailboxes
- No long-term data retention (max 1 year)
- No personal information required from users
-
Authentication
- Token-based authentication with high entropy
- No password storage for user access
-
Payment Privacy
- Bitcoin Lightning Network payments for maximum privacy
- No identifying payment information required
LNemail is ideal for:
- Two-factor authentication requiring fast email delivery
- Anonymous communication with Bitcoin Lightning integration
- Account verification where anonymous registration is preferred
- Newsletter subscriptions without personal data exposure
- Services requiring persistent email beyond temporary mail services
- Bitcoin/Lightning-native applications needing full email integration
# Create directories and permissions
mkdir -p dev-data/mail-data
mkdir -p dev-data/mail-state
mkdir -p dev-data/mail-logs
mkdir -p dev-data/config/ssl
mkdir -p dev-data/config
mkdir -p dev-data/mail-agent
mkdir -p dev-data/shared/requests
mkdir -p dev-data/shared/responses
mkdir -p dev-data/lnemail-data
mkdir -p dev-data/redis-data
mkdir -p docker/lnd
# Set permissions
chmod -R 777 dev-data
# Start all services
docker compose up -dWait a few minutes for the Bitcoin node to sync and the LND nodes to initialize. You can track the progress with:
docker logs -f ofelia
docker exec lnd lncli --network=regtest {walletbalance|channelbalance|pendingchannels|listchannels}- Web Interface: http://localhost:8000
- API Docs: http://localhost:8000/docs
- LND REST: http://localhost:8081
- Bitcoin RPC: Available on port configured in .env
The development environment includes:
- Bitcoin regtest node with automatic mining
- Two LND nodes with channels for Lightning payments
- A Nostr relay + NIP-47 wallet so the stack runs with both payment
providers (NWC + LND fallback) by default (see
scripts/nwc-wallet/) - Mail server for email handling with SMTP support
- Redis for background job processing
- LNemail API and worker services
The web UI uses Tailwind CSS and a small set of web fonts. To keep the production site free of any third-party CDN requests, these are pre-compiled and self-hosted:
src/lnemail/static/css/tailwind.cssis generated fromfrontend/tailwind.config.js+frontend/tailwind.src.cssand is committed to the repo (so deployments need no Node/Bun toolchain).- Fonts (Inter, JetBrains Mono, Material Symbols Outlined) live under
src/lnemail/static/fonts/withinter.cssandwebfonts.css.
Rebuild the stylesheet after changing any template or JS that uses Tailwind classes:
cd frontend
bun install # first time only
bun run build # writes ../src/lnemail/static/css/tailwind.css
# bun run watch # rebuild on change during developmentRefresh the fonts (only needed to add a new Material Symbols icon or
update a font) with ./scripts/fetch_fonts.sh. The Material Symbols
font is subset to just the icons the UI references, keeping it ~34 KB
instead of ~4 MB.
Use the web or API to generate an invoice, then pay it from the second LND node:
docker exec router_lnd lncli --network=regtest --rpcserver=router_lnd:10010 --tlscertpath=/shared/router_tls.cert --macaroonpath=/shared/router_admin.macaroon payinvoice --force {invoice}Once you have an email account, you can send a test email to it. Use the
rootless-friendly SMTP port 2525 (privileged ports like 25 are not
reachable from the host under rootless Docker; 25 still works when
running as root):
swaks --to sereneforest630@lnemail.test \
--from sender@lnemail.test \
--server localhost:2525 \
--body "Test email body" \
--header "Subject: Test Email"You can also send emails from your LNemail account using the web interface or API.
Realistic Playwright tests drive the full UI against the running dev
stack and pay every Lightning invoice for real over the regtest
channel. See tests/e2e/README.md for details.
poetry install --with e2e
poetry run playwright install --with-deps chromium
poetry run pytest tests/e2e -v# Stop and remove everything
docker compose down -v --remove-orphans
# Remove volumes and certificates
docker volume rm lnemail_bitcoin lnemail_lnd lnemail_router_lnd
sudo rm -f dev-data/shared/*.cert dev-data/shared/*.macaroon dev-data/shared/lnd_*This project is licensed under the MIT License. See the LICENSE file for details.
Contact: npub1rkh3y6j0a64xyv5f89mpeh8ah68a9jcmjv5mwppc9kr4w9dplg9qpuxk76