rcgen 0.14 replaced the separate Certificate + KeyPair args with a
unified Issuer type. Migrates ensure_ca and generate_service_cert:
- Load path: Issuer::from_ca_cert_der replaces the old
CertificateParams::from_ca_cert_pem + self_signed round-trip.
- Generate path: Issuer::new(params, key_pair) constructs directly
from the params used for self_signed (no DER re-parse).
- signed_by takes (&key_pair, &issuer) instead of (&key_pair, &cert, &key).
Also drops thiserror v1 from the dep tree (rcgen 0.14 uses v2).
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
v0.10.0 ships DNS-over-TLS. Tagged release v0.10.0 on main after
merge will pick up this Cargo.toml version, keeping tag and manifest
aligned for release.yml.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Refactor handle_query into transport-agnostic resolve_query that returns
a BytePacketBuffer, keeping the UDP path zero-alloc. Add a TLS listener
on port 853 with persistent connections, idle timeout, connection limits,
and coalesced writes. Supports user-provided certs or self-signed CA
fallback. Includes 5 integration tests.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
New: Windows DNS configuration (install/uninstall/auto-start).
Fix: DoH fallback uses IP to avoid DNS bootstrap loop.
Fix: UDP ConnectionReset crash on Windows.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Breaking: default mode changed from auto to forward.
New: memory footprint stats + dashboard panel.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* feat: in-flight query coalescing for recursive resolver
When multiple queries for the same (domain, qtype) arrive concurrently
and all miss the cache, only the first triggers recursive resolution.
Subsequent queries wait on a broadcast channel for the result.
Prevents thundering herd where N concurrent cache misses each
independently walk the full NS chain, compounding timeouts.
Uses InflightGuard (Drop impl) to guarantee map cleanup on
panic/cancellation — prevents permanent SERVFAIL poisoning.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* style: add InflightMap type alias for clippy
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* feat: add COALESCED query path and coalescing tests
Followers in the inflight coalescing path now log as COALESCED instead
of RECURSIVE, making it visible in the dashboard when queries were
deduplicated vs independently resolved. Adds 10 tests covering
InflightGuard cleanup, broadcast mechanics, and concurrent handle_query
coalescing through a mock TCP DNS server.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
* style: cargo fmt
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
* refactor: extract acquire_inflight, rewrite tests against real code
Move Disposition enum and inflight acquisition logic into a standalone
acquire_inflight() function. Rewrite 4 tests that were exercising tokio
primitives to call the real coalescing code path instead.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
---------
Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* feat: DNS-over-HTTPS upstream forwarding
Encrypt upstream queries via DoH — ISPs see HTTPS traffic on port 443,
not plaintext DNS on port 53. URL scheme determines transport:
https:// = DoH, bare IP = plain UDP. Falls back to Quad9 DoH when
system resolver cannot be detected.
- Upstream enum (Udp/Doh) with Display and PartialEq
- BytePacketBuffer::from_bytes constructor
- reqwest http2 feature for DoH server compatibility
- network_watch_loop guards against DoH→UDP silent downgrade
- 5 new tests (mock DoH server, HTTP errors, timeout)
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
* style: cargo fmt
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
* docs: add DoH to README — Why Numa, comparison table, roadmap
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
---------
Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
HTTPS proxy certs were generated once at startup. Services added at
runtime via API or LAN discovery got "not secure" in the browser
because their SAN wasn't in the cert. Now the cert is regenerated
on every service add/remove and swapped atomically via ArcSwap.
In-flight connections are unaffected.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Add LAN discovery section to README with mesh and hub mode docs.
Update comparison table and roadmap. Move Local Services panel
above Blocking in dashboard for developer-first layout.
Bump version from 0.1.0 to 0.3.0 to match release cadence.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Replace IP-based self-announcement filtering with a per-process instance
ID (pid ^ timestamp) so multiple instances on the same host can discover
each other. Enable SO_REUSEPORT for multicast socket binding on Unix.
Add multicast address validation on configured group.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Numa instances on the same network auto-discover each other's .numa
services. No config, no cloud — just multicast on 239.255.70.78:5390.
- PeerStore with lazy expiry (90s timeout, 30s broadcast interval)
- DNS resolves remote .numa services to peer's LAN IP (not localhost)
- Proxy forwards to peer IP for remote services
- Graceful degradation if multicast bind fails
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Dead code — certs are generated at startup, not loaded from PEM files.
Removes RUSTSEC-2025-0134 warning. Audit now passes clean.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
HTTP reverse proxy on port 80 lets developers use clean domain names
(frontend.numa, api.numa) instead of localhost:PORT. Includes WebSocket
upgrade support for HMR, TCP health checks, dashboard UI panel, and
REST API for service management. numa.numa is preconfigured for the
dashboard itself.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- DNS-level ad blocking: 385K+ domains via Hagezi Pro blocklist, subdomain
matching, one-click allowlist, pause/toggle, background refresh every 24h
- Live dashboard at :5380 with real-time stats, query log, override
management (create/edit/delete), blocking controls
- System DNS auto-discovery: parses scutil --dns on macOS to find
conditional forwarding rules (Tailscale, VPN split-DNS)
- REST API expanded to 18 endpoints (blocking, overrides, diagnostics)
- Startup banner with colored system info
- Performance benchmarks (bench/dns-bench.sh)
- Landing page updated with new positioning and comparison table
- CI, Dockerfile, LICENSE, development plan docs
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>