Skip to content

Commit a11de06

Browse files
committed
Initial project scaffold for lnbot
Add initial library scaffold for the lnbot Python SDK: package sources (src/lnbot) including client, errors, and types with py.typed; project metadata (pyproject.toml); README and MIT LICENSE; OpenAPI specification (openapi.json); repository config (.gitignore, .gitattributes); and GitHub Actions workflows for CI and release. This commit establishes the base structure, docs, and CI/release automation for further development.
0 parents  commit a11de06

File tree

13 files changed

+3478
-0
lines changed

13 files changed

+3478
-0
lines changed

.gitattributes

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
# Auto detect text files and perform LF normalization
2+
* text=auto

.github/workflows/ci.yml

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
name: CI
2+
3+
on:
4+
push:
5+
branches: [main]
6+
pull_request:
7+
8+
jobs:
9+
build:
10+
runs-on: ubuntu-latest
11+
strategy:
12+
matrix:
13+
python-version: ["3.10", "3.11", "3.12", "3.13"]
14+
steps:
15+
- uses: actions/checkout@v4
16+
17+
- uses: actions/setup-python@v5
18+
with:
19+
python-version: ${{ matrix.python-version }}
20+
21+
- run: pip install -e .
22+
- run: python -c "from lnbot import LnBot, AsyncLnBot; print('OK')"

.github/workflows/release.yml

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
name: Release
2+
3+
on:
4+
release:
5+
types: [published]
6+
7+
permissions:
8+
contents: read
9+
id-token: write
10+
11+
jobs:
12+
publish:
13+
runs-on: ubuntu-latest
14+
environment: pypi
15+
steps:
16+
- uses: actions/checkout@v4
17+
18+
- uses: actions/setup-python@v5
19+
with:
20+
python-version: "3.13"
21+
22+
- run: pip install build
23+
- run: python -m build
24+
25+
- uses: pypa/gh-action-pypi-publish@release/v1
26+
with:
27+
password: ${{ secrets.PYPI_TOKEN }}

.gitignore

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
__pycache__/
2+
*.py[cod]
3+
*.egg-info/
4+
dist/
5+
build/
6+
.venv/
7+
.env
8+
.env.*
9+
*.log
10+
.DS_Store
11+
.mypy_cache/
12+
.ruff_cache/
13+
*.tgz

LICENSE

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
MIT License
2+
3+
Copyright (c) 2026 LnBot
4+
5+
Permission is hereby granted, free of charge, to any person obtaining a copy
6+
of this software and associated documentation files (the "Software"), to deal
7+
in the Software without restriction, including without limitation the rights
8+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9+
copies of the Software, and to permit persons to whom the Software is
10+
furnished to do so, subject to the following conditions:
11+
12+
The above copyright notice and this permission notice shall be included in all
13+
copies or substantial portions of the Software.
14+
15+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21+
SOFTWARE.

README.md

Lines changed: 218 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,218 @@
1+
# lnbot
2+
3+
[![PyPI version](https://img.shields.io/pypi/v/lnbot)](https://pypi.org/project/lnbot/)
4+
[![PyPI downloads](https://img.shields.io/pypi/dm/lnbot)](https://pypi.org/project/lnbot/)
5+
[![Python](https://img.shields.io/pypi/pyversions/lnbot)](https://pypi.org/project/lnbot/)
6+
[![License: MIT](https://img.shields.io/badge/license-MIT-green)](./LICENSE)
7+
8+
**The official Python SDK for [LnBot](https://ln.bot)** — Bitcoin for AI Agents.
9+
10+
Give your AI agents, apps, and services access to Bitcoin over the Lightning Network. Create wallets, send and receive sats, and get real-time payment notifications.
11+
12+
```python
13+
from lnbot import LnBot
14+
15+
ln = LnBot(api_key="lnbot_...")
16+
17+
invoice = ln.invoices.create(amount=1000, memo="Coffee")
18+
ln.payments.create(target="alice@ln.bot", amount=500)
19+
```
20+
21+
> LnBot also ships a **[TypeScript SDK](https://www.npmjs.com/package/@lnbot/sdk)**, **[CLI](https://ln.bot/docs)**, and **[MCP server](https://ln.bot/docs)**.
22+
23+
---
24+
25+
## Install
26+
27+
```bash
28+
pip install lnbot
29+
```
30+
31+
---
32+
33+
## Quick start
34+
35+
### 1. Create a wallet
36+
37+
```python
38+
from lnbot import LnBot
39+
40+
ln = LnBot()
41+
wallet = ln.wallets.create(name="my-agent")
42+
43+
print(wallet.primary_key) # your API key
44+
print(wallet.address) # your Lightning address
45+
print(wallet.recovery_passphrase) # back this up!
46+
```
47+
48+
### 2. Receive sats
49+
50+
```python
51+
ln = LnBot(api_key=wallet.primary_key)
52+
53+
invoice = ln.invoices.create(amount=1000, memo="Payment for task #42")
54+
print(invoice.bolt11)
55+
```
56+
57+
### 3. Wait for payment
58+
59+
```python
60+
for event in ln.invoices.wait_for_settlement(invoice.number):
61+
if event.event == "settled":
62+
print("Paid!")
63+
```
64+
65+
### 4. Send sats
66+
67+
```python
68+
ln.payments.create(target="alice@ln.bot", amount=500)
69+
ln.payments.create(target="lnbc10u1p...")
70+
```
71+
72+
### 5. Check balance
73+
74+
```python
75+
wallet = ln.wallets.current()
76+
print(f"{wallet.available} sats available")
77+
```
78+
79+
---
80+
81+
## Async support
82+
83+
Every method has an async equivalent via `AsyncLnBot`:
84+
85+
```python
86+
from lnbot import AsyncLnBot
87+
88+
async with AsyncLnBot(api_key="lnbot_...") as ln:
89+
wallet = await ln.wallets.current()
90+
invoice = await ln.invoices.create(amount=1000)
91+
92+
async for event in ln.invoices.wait_for_settlement(invoice.number):
93+
if event.event == "settled":
94+
print("Paid!")
95+
```
96+
97+
---
98+
99+
## Error handling
100+
101+
```python
102+
from lnbot import LnBot, BadRequestError, UnauthorizedError, NotFoundError, ConflictError, LnBotError
103+
104+
try:
105+
ln.payments.create(target="invalid", amount=100)
106+
except BadRequestError:
107+
... # 400
108+
except UnauthorizedError:
109+
... # 401
110+
except NotFoundError:
111+
... # 404
112+
except ConflictError:
113+
... # 409
114+
except LnBotError as e:
115+
print(e.status, e.body)
116+
```
117+
118+
## Configuration
119+
120+
```python
121+
from lnbot import LnBot
122+
123+
ln = LnBot(
124+
api_key="lnbot_...", # or set LNBOT_API_KEY env var
125+
base_url="https://api.ln.bot", # optional — this is the default
126+
timeout=30.0, # optional — request timeout in seconds
127+
)
128+
```
129+
130+
The API key can also be provided via the `LNBOT_API_KEY` environment variable. If both are provided, the constructor argument takes precedence.
131+
132+
---
133+
134+
## API reference
135+
136+
### Wallets
137+
138+
| Method | Description |
139+
| --- | --- |
140+
| `ln.wallets.create(name=)` | Create a new wallet (no auth required) |
141+
| `ln.wallets.current()` | Get current wallet info and balance |
142+
| `ln.wallets.update(name=)` | Update wallet name |
143+
144+
### Invoices
145+
146+
| Method | Description |
147+
| --- | --- |
148+
| `ln.invoices.create(amount=, memo=, reference=)` | Create a BOLT11 invoice |
149+
| `ln.invoices.list(limit=, after=)` | List invoices |
150+
| `ln.invoices.get(number)` | Get invoice by number |
151+
| `ln.invoices.wait_for_settlement(number, timeout=)` | SSE stream for settlement/expiry |
152+
153+
### Payments
154+
155+
| Method | Description |
156+
| --- | --- |
157+
| `ln.payments.create(target=, amount=, ...)` | Send sats to a Lightning address or BOLT11 invoice |
158+
| `ln.payments.list(limit=, after=)` | List payments |
159+
| `ln.payments.get(number)` | Get payment by number |
160+
161+
### Addresses
162+
163+
| Method | Description |
164+
| --- | --- |
165+
| `ln.addresses.create(address=)` | Create a random or vanity Lightning address |
166+
| `ln.addresses.list()` | List all addresses |
167+
| `ln.addresses.delete(address)` | Delete an address |
168+
| `ln.addresses.transfer(address, target_wallet_key=)` | Transfer address to another wallet |
169+
170+
### Transactions
171+
172+
| Method | Description |
173+
| --- | --- |
174+
| `ln.transactions.list(limit=, after=)` | List credit and debit transactions |
175+
176+
### Webhooks
177+
178+
| Method | Description |
179+
| --- | --- |
180+
| `ln.webhooks.create(url=)` | Register a webhook endpoint (max 10) |
181+
| `ln.webhooks.list()` | List all webhooks |
182+
| `ln.webhooks.delete(webhook_id)` | Delete a webhook |
183+
184+
### API Keys
185+
186+
| Method | Description |
187+
| --- | --- |
188+
| `ln.keys.list()` | List API keys (metadata only) |
189+
| `ln.keys.rotate(slot)` | Rotate a key (0 = primary, 1 = secondary) |
190+
191+
### Backup & Restore
192+
193+
| Method | Description |
194+
| --- | --- |
195+
| `ln.backup.recovery()` | Generate 12-word BIP-39 recovery passphrase |
196+
| `ln.backup.passkey_begin()` | Start passkey backup (WebAuthn) |
197+
| `ln.backup.passkey_complete(session_id=, attestation=)` | Complete passkey backup |
198+
| `ln.restore.recovery(passphrase=)` | Restore wallet with recovery passphrase |
199+
| `ln.restore.passkey_begin()` | Start passkey restore (WebAuthn) |
200+
| `ln.restore.passkey_complete(session_id=, assertion=)` | Complete passkey restore |
201+
202+
---
203+
204+
## Requirements
205+
206+
- Python 3.10+
207+
- Get your API key at [ln.bot](https://ln.bot)
208+
209+
## Links
210+
211+
- [ln.bot](https://ln.bot) — website
212+
- [Documentation](https://ln.bot/docs)
213+
- [GitHub](https://github.com/lnbotdev)
214+
- [TypeScript SDK](https://www.npmjs.com/package/@lnbot/sdk)
215+
216+
## License
217+
218+
MIT

0 commit comments

Comments
 (0)