Skip to main content

A federated end-to-end encrypted messaging protocol delivered over DNS

Project description

DNS Mesh Protocol

End-to-end encrypted messaging with no central server, no app store, no gatekeeper, delivered over DNS, on the relays and infrastructure the internet already runs on.


Status: alpha, pre-external-audit. Full federation (client fan-out + union reader + node-side anti-entropy + manifest gossip), bootstrap discovery, key rotation + revocation (M5.4), multi-tenant node auth with per-user publish tokens (M5.5), and the formal protocol spec are shipped. The remaining path to v1.0 is a certification backlog: external cryptographic audit, mobile/web clients, standalone CLI binaries, traffic-analysis hardening.

Don't route secrets through DMP until the external cryptographic audit is done. The codebase has had ~40+ rounds of automated review across all milestones, but automated review is not a substitute for professional cryptanalysis. A human auditor catches a different class of bugs (crypto composition errors, side-channel weaknesses, protocol-level attacks, implementation-vs-spec drift) that no amount of LLM-driven pattern matching will find. The audit is a post-beta deliverable; until then treat DMP as experimental for confidentiality-critical traffic.

The pitch

Instead of sending messages through a central server you have to trust, DNS Mesh Protocol encrypts each message end-to-end and writes it as DNS records on a node you choose. The recipient looks those records up the same way any computer looks up google.com. If DNS works on your network, DMP works on your network.

  • One docker container is a complete, deployable node.
  • One command-line tool covers identity, key management, send, and receive.
  • One protocol composes Ed25519 signatures, X25519 ECDH, ChaCha20-Poly1305, Argon2id passphrase derivation, one-time prekeys for forward secrecy, and Reed-Solomon erasure coding for chunk loss.

Quick start

git clone https://github.com/oscarvalenzuelab/DNSMeshProtocol.git
cd DNSMeshProtocol

# Install the CLI
pip install -e .

# Build and run the node
docker build -t dnsmesh-node:latest .
docker run -d -p 5353:5353/udp -p 8053:8053/tcp \
  -v dnsmesh-data:/var/lib/dmp dnsmesh-node:latest

# Set up an identity and send your first message
export DMP_PASSPHRASE=a-strong-passphrase
dnsmesh init alice --domain mesh.local \
               --endpoint http://127.0.0.1:8053 \
               --dns-host 127.0.0.1 --dns-port 5353
dnsmesh identity publish

Full walk-through with two users: Getting Started.

What you get

  • End-to-end encryption with forward secrecy for prekey-consumed messages. Past messages stay safe if long-term keys leak later; see Forward secrecy and prekeys.
  • Signed sender authentication. With pinned contacts, unknown signers are dropped. Without, receive runs in trust-on-first-use.
  • Zone-anchored identity addresses. alice@alice.example.com. Squatting requires compromising DNS for the zone.
  • Cross-chunk erasure coding. Loss of up to n-k chunks still reconstructs the message.
  • Resolver resilience. ResolverPool fans queries across multiple upstream resolvers with oracle-based demotion on lying resolvers. dnsmesh resolvers discover auto-builds the pool from public resolvers.
  • Multi-node federation (client AND node side). FanoutWriter publishes to every cluster node (quorum = ceil(N/2)); UnionReader reads the union with dedup. Nodes run pull-based anti-entropy against their peers so a node that was offline catches up when it rejoins. A 3-node docker-compose.cluster.yml is a checked-in operator starting point; see Clustered deployment.
  • Key rotation + revocation. dnsmesh identity rotate --experimental publishes a co-signed RotationRecord (new key ← old key) plus an optional self-signed RevocationRecord when --reason compromise or --reason lost_key is set. Rotation-aware contacts chain-walk from their pinned key to the current head automatically; a revocation aborts trust on any path that touches the revoked key. See docs/protocol/rotation.md.
  • Multi-tenant node auth (M5.5). DMP_AUTH_MODE=multi-tenant enables per-user publish tokens: every write to /v1/records/* is scope-checked against the token's subject, and dnsmesh register
    • /v1/registration/{challenge,confirm} give users a self-service path to mint their own tokens via an Ed25519-signed challenge. Shared-pool writes (mailbox + chunks) don't log subject or token hash, so an operator handed the DB cannot reconstruct who-delivered-to-whom. See Multi-tenant deployment.
  • Zero-config onboarding via bootstrap discovery. Given just alice@example.com, dnsmesh bootstrap discover me@my-domain --auto-pin resolves the cluster, verifies the two-hop trust chain (bootstrap signer → cluster operator), and cuts over atomically.
  • Persistent, size-bounded node. sqlite storage, TTL cleanup, token-bucket rate limits, bounded concurrency, Prometheus metrics.
  • Docker-first deploy. docker compose for dev, Caddy + Let's Encrypt overlay for production.
  • Formal protocol spec. Wire format, routing, flows, and threat model at docs/protocol/. Every constant cross-verified against the source; designed so a third party can build an interoperable client.

Running a node

# Dev
docker compose up -d

# Production (real hostname, auto TLS)
export DMP_NODE_HOSTNAME=dmp.example.com
docker compose -f docker-compose.yml -f docker-compose.prod.yml up -d

See Deployment. Before shipping to production, read the operator hardening guide, a mandatory checklist covering TLS, token hygiene, operator signing-key handling, DNS zone hygiene, file permissions, and network exposure.

Project layout

dmp/
├── core/       Protocol primitives: crypto, chunking, erasure,
│               manifests, identity, prekeys, DNS encoding
├── network/    DNSRecordWriter / DNSRecordReader abstraction +
│               Cloudflare, Route53, BIND, in-memory backends
├── storage/    SqliteMailboxStore: persistent TTL-aware record store
├── server/     DMPNode: UDP DNS server, HTTP API, cleanup worker,
│               metrics, rate limiting, structured logging
├── client/     DMPClient: send / receive / identity / prekeys
└── cli.py      `dnsmesh` command-line interface

docs/          Jekyll docs site (Just the Docs theme, GitHub Pages)
               Includes docs/protocol/ for the formal wire spec
tests/         1050+ unit, integration, fuzz, and docker-in-the-loop tests
               Includes tests/fuzz/ (hypothesis property tests) and
               tests/test_vectors.py (golden interop test vectors).
Dockerfile, docker-compose.yml, docker-compose.prod.yml, Caddyfile

Tests

pip install -e ".[dev]"
pytest                                         # ~1050 tests (incl. fuzz)
docker build -t dnsmesh-node:latest .
pytest tests/test_docker_integration.py        # 6 docker tests (incl. M5.4 rotation)
pytest tests/test_compose_cluster.py           # 3 compose-cluster tests
python examples/docker_e2e_demo.py             # single-node send/receive + rotation demo
python examples/cluster_e2e_demo.py            # 3-node federated e2e demo

Production installs use the hashed lockfile:

pip install --require-hashes -r requirements.lock
pip install . --no-deps

Not a good fit for

  • Real-time chat (seconds-to-minutes latency by design)
  • File transfer or media payloads
  • Anonymity from traffic analysis (DMP hides content, not metadata)

Contributing

See CONTRIBUTING.md. Every PR that changes behavior needs a test. Security-sensitive changes in dmp/core/crypto.py, dmp/core/manifest.py, dmp/core/prekeys.py, or the AEAD AAD surface get an extra round of review.

License

AGPL-3.0. If you host DMP as a service you must publish your source changes.

Author

Oscar Valenzuela · AlkamoD

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

dnsmesh-0.3.0.tar.gz (420.1 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

dnsmesh-0.3.0-py3-none-any.whl (274.4 kB view details)

Uploaded Python 3

File details

Details for the file dnsmesh-0.3.0.tar.gz.

File metadata

  • Download URL: dnsmesh-0.3.0.tar.gz
  • Upload date:
  • Size: 420.1 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for dnsmesh-0.3.0.tar.gz
Algorithm Hash digest
SHA256 a745eeea938dc9e04282b4908a7ba6af0411b8e8fd68f98e91d2cb7ad7f02a4d
MD5 97d98c9db975db8416d38561138f2242
BLAKE2b-256 ba39d946bdc93677fa1caed819484a6c61ea516f4a7919adb60c139a6343d6a6

See more details on using hashes here.

Provenance

The following attestation bundles were made for dnsmesh-0.3.0.tar.gz:

Publisher: publish-pypi.yml on oscarvalenzuelab/DNSMeshProtocol

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file dnsmesh-0.3.0-py3-none-any.whl.

File metadata

  • Download URL: dnsmesh-0.3.0-py3-none-any.whl
  • Upload date:
  • Size: 274.4 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for dnsmesh-0.3.0-py3-none-any.whl
Algorithm Hash digest
SHA256 9555ddfb1ce54cfa4552cfecbfdf1753e021ba6ba4e292c50c2a8c3fdc0b9ee5
MD5 e72d73a0e0a78736b161fa6c1fa2af07
BLAKE2b-256 9682534f45c0ad0b566da2e64ef1afb17f0d27a41d99d2eca5d1e517ca3a0dc2

See more details on using hashes here.

Provenance

The following attestation bundles were made for dnsmesh-0.3.0-py3-none-any.whl:

Publisher: publish-pypi.yml on oscarvalenzuelab/DNSMeshProtocol

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page