Skip to content

Commit 8aaa7c6

Browse files
committed
docs: update changelog and release-notes for v0.3.20 changes
1 parent 060ebe7 commit 8aaa7c6

2 files changed

Lines changed: 160 additions & 0 deletions

File tree

docs/en/16_CHANGELOG.md

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,29 @@
22

33
This file contains high-level release notes and migration guidance.
44

5+
## Unreleased (v0.3.20)
6+
7+
**Cache**
8+
9+
- feat(cache): persistence via `dump_file` / `dump_interval`; cache survives restarts with binary dump/load
10+
- fix(cache): include DNSSEC flags (DO/AD/CD) in cache key to prevent serving DNSSEC responses to non-DNSSEC clients
11+
- fix(cache): remove 5 internal-only config options (refresh_worker_count, refresh_queue_capacity, enable_cleanup, cleanup_interval_secs, cleanup_pressure_threshold); now constants
12+
13+
**Audit / WebUI**
14+
15+
- refactor(audit): merge audit into the `web` feature; no longer a standalone plugin or feature
16+
- refactor(audit): remove file-writing, config struct, and standalone plugin registration
17+
- feat(webui): read-only config viewer with sequence flow visualization and expandable plugin args
18+
- feat(webui): reload error banner showing backend validation messages
19+
- feat(webui): split Admin page into ManagementTab / ConfigTab components
20+
21+
**Config cleanup**
22+
23+
- fix(fallback): remove dead `threshold` and `always_standby` config keys (never implemented)
24+
- refactor(domain_validator): remove redundant `blacklist` feature (use `domain_set` + `black_hole`)
25+
- refactor: remove vestigial `Plugin::priority()` system (sequence controls order)
26+
- refactor: remove legacy `PluginConfig.config` field (all plugins use `args:`)
27+
528
## Release v0.3.13 - 2026-07-06
629

730
Bug-fix release focused on correctness of the forward and cache paths under load.

docs/v0.3-release-notes.md

Lines changed: 137 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,137 @@
1+
# lazydns v0.3 — Release Notes
2+
3+
A high-performance DNS forwarder with a built-in web dashboard, written in Rust.
4+
5+
This release covers v0.3.0 through v0.2. It adds a real-time WebUI, cache persistence, DNSSEC-safe caching, and simplifies the configuration experience.
6+
7+
---
8+
9+
## Highlights
10+
11+
### Web dashboard
12+
13+
lazydns now ships with a built-in web dashboard (Svelte + axum). No external tools needed to see what your DNS server is doing.
14+
15+
- **Live query logs**: every DNS query streams in real time via SSE, with client IP, domain, response time, and answers
16+
- **Security events**: rate-limit violations, blocked domains, upstream failures, and ACL denials appear instantly
17+
- **Upstream health**: per-upstream success rate, average latency, and failure counts
18+
- **Alert engine**: configurable rules with deduplication and webhook notifications
19+
- **Dark mode**, responsive layout, embedded assets (single binary with `web-embed`)
20+
21+
Enable it in your config:
22+
23+
```yaml
24+
web:
25+
enabled: true
26+
listen: "0.0.0.0:8002"
27+
```
28+
29+
Build with `--features web-embed` to compile the dashboard into the binary.
30+
31+
### Configuration viewer
32+
33+
The Admin page now has a **Configuration** tab that shows your currently loaded plugins, sequences (as a visual step-by-step flow), and server settings. No more guessing what your server is actually running. Click any plugin to expand its full arguments.
34+
35+
When a config reload fails, the error message from the validator is shown inline so you can fix the problem without digging through logs.
36+
37+
### Cache persistence
38+
39+
The cache can now survive server restarts. Set `dump_file` and lazydns saves cached responses to a binary file on shutdown, then restores them on startup (skipping any that have expired).
40+
41+
```yaml
42+
- tag: cache
43+
type: cache
44+
args:
45+
size: 2048
46+
enable_lazycache: true
47+
dump_file: /var/lib/lazydns/cache.dump
48+
dump_interval: 300
49+
```
50+
51+
### Simpler configuration
52+
53+
We removed confusing and dead config options across the board:
54+
55+
- **`fallback`**: removed `threshold` and `always_standby` keys that were silently ignored (never implemented).
56+
- **`domain_validator`**: removed the `blacklist` option. Use `domain_set` + `black_hole` for domain blocking, which is more capable and supports file-based lists.
57+
- **`cache`**: removed 5 internal tuning knobs (`refresh_worker_count`, `refresh_queue_capacity`, `enable_cleanup`, `cleanup_interval_secs`, `cleanup_pressure_threshold`). These are now sensible built-in defaults.
58+
- **`priority`**: removed entirely. The sequence order in your config determines execution order; the `priority` field never did anything.
59+
60+
---
61+
62+
## Bug fixes
63+
64+
### Forwarding
65+
66+
- UDP responses were cross-pollinated between concurrent queries on the shared socket. Now multiplexed by query ID with a dedicated demux loop.
67+
- A response arriving at the exact moment of a timeout could be dropped. Now uses a fair select so the response wins.
68+
- Average response time (used by the `fastest` load-balancing strategy) was updated non-atomically, losing samples under concurrency. Fixed with CAS.
69+
- Replaced `std::sync::Mutex` with `parking_lot::Mutex` to avoid lock poisoning on panics.
70+
71+
### Cache
72+
73+
- Cached responses were mutated in place when served, corrupting the cache for subsequent queries. Now deep-cloned.
74+
- The question section of cached responses was not synced to the current request, causing query/response mismatches on cache hits.
75+
- A cache key stayed marked "refreshing" forever after the first LazyCache background refresh, silently disabling prefetch for that key. Now cleared via a completion hook.
76+
- Cache keys did not include DNSSEC flags (DO/AD/CD), causing DNSSEC-enabled responses to be served to clients that did not request DNSSEC. Now included.
77+
78+
### Servers
79+
80+
- TCP/DoT responses larger than 65535 bytes silently truncated the length prefix, corrupting the stream. Now clamped with an error.
81+
- DoQ `local_addr()` would panic on failure. Now degrades gracefully.
82+
83+
### Config
84+
85+
- The `config-simple.yaml` example used an unimplemented sequence syntax that produced a no-op sequence. Fixed.
86+
- Upstream address formats were inconsistent across examples. Standardized to `addr:` mapping form.
87+
88+
---
89+
90+
## Protocol support
91+
92+
All five DNS transport protocols are supported:
93+
94+
| Protocol | Config type | Port example |
95+
|---|---|---|
96+
| UDP | `udp_server` | `:53` |
97+
| TCP | `tcp_server` | `:53` |
98+
| DoT | `dot_server` | `:853` |
99+
| DoH | `doh_server` | `:443` |
100+
| DoQ | `doq_server` | `:853` |
101+
102+
DoT, DoH, and DoQ require TLS certificates (`cert_file` / `key_file`).
103+
104+
---
105+
106+
## Feature flags
107+
108+
```bash
109+
# Minimal (UDP/TCP only, no web)
110+
cargo build
111+
112+
# With WebUI dashboard
113+
cargo build --features web
114+
115+
# With embedded WebUI (single binary)
116+
cargo build --features web-embed
117+
118+
# Everything
119+
cargo build --features full
120+
```
121+
122+
---
123+
124+
## Getting started
125+
126+
```bash
127+
# Build
128+
cargo build --features web-embed
129+
130+
# Run with the example config
131+
./target/debug/lazydns -c examples/etc/config.yaml -d examples/etc/
132+
133+
# Open the dashboard
134+
open http://127.0.0.1:8002
135+
```
136+
137+
Full documentation: https://lazywalker.github.io/lazydns/docs/

0 commit comments

Comments
 (0)