A minimal Nostr relay for ESP32-S3.
Wisp-ESP32 is an ephemeral Nostr relay that runs on $10 hardware. Your relay, your rules, your data—and it cleans up after itself.
Why run your own embedded relay?
- Privacy: Events never touch third-party infrastructure
- Sovereignty: Works offline, no cloud dependency
- Ephemeral by design: 21-day TTL means data automatically disappears
- Edge-ready: Building block for mesh networks and air-gapped setups
Wisp pairs with keep-esp32 for private threshold signing coordination. Instead of leaking signing activity to public relays:
┌─────────────┐ ┌─────────────┐ ┌─────────────┐
│ Keep #1 │ │ Wisp │ │ Keep #2 │
│ (signer) │◄───►│ (relay) │◄───►│ (signer) │
└─────────────┘ └─────────────┘ └─────────────┘
▲
│
┌─────────────┐
│ Coordinator │
│ (CLI) │
└─────────────┘
- DKG ceremony events stay local
- Signing coordination never hits public relays
- 21-day TTL auto-purges ceremony artifacts
5-10 connections is perfect for a household or small community running their own infrastructure without a VPS.
Unlike stateless mesh relays, Wisp provides ephemeral-but-persistent storage—nodes can query recent history while data still auto-expires.
| Resource | Value |
|---|---|
| Connections | 5-10 concurrent WebSocket |
| Storage | 5,000 events |
| TTL | 21 days |
| Crypto | Schnorr via libnostr-c/noscrypt |
Supported NIPs:
- NIP-01 (protocol)
- NIP-09 (deletion)
- NIP-11 (relay info)
- NIP-40 (expiration)
ESP-IDF v5.3.4
git clone -b v5.3.4 --recursive https://github.com/espressif/esp-idf.git
cd esp-idf && ./install.sh esp32s3
source export.shClone repositories as siblings:
cd ~/projects # or your preferred directory
git clone -b esp-idf-support https://github.com/privkeyio/secp256k1-frost
git clone https://github.com/privkeyio/wisp-esp32
git clone -b esp-idf-support https://github.com/privkeyio/noscrypt
git clone https://github.com/privkeyio/libnostr-cYour directory structure should look like:
~/projects/
├── wisp-esp32/ # This repo
├── libnostr-c/ # Nostr library (symlinked in components/)
├── noscrypt/ # NIP-44 crypto (symlinked in components/)
└── secp256k1-frost/ # Schnorr signatures
cd wisp-esp32
source ~/path/to/esp-idf/export.sh
idf.py build
idf.py -p /dev/ttyACM0 flash monitor- ESP32-S3 with 8MB Flash
- PSRAM optional (5000 event index with PSRAM, 1000 without)
- Tested on M5Stack CoreS3 Lite, ESP32-S3-DevKitC-1-N8R8
- AtomS3 Lite works but has limited PSRAM (reduced index capacity)
Requires: nak, websocat, curl, jq
# Install tools
go install github.com/fiatjaf/nak@latest # or build from source
cargo install websocat
sudo apt install curl jq # or brew install
# Run integration tests
RELAY=ws://<relay-ip>:4869 ./test/hardware/integration_test.sh
# Run stress tests
RELAY=ws://<relay-ip>:4869 ./test/hardware/stress_test.sh allcd test/native
mkdir -p ../../managed_components/espressif__cjson
git clone https://github.com/DaveGamble/cJSON.git ../../managed_components/espressif__cjson/cJSON
mkdir -p build && cd build
cmake .. && make
./test_routerMIT
