DNS VMs (Technitium)
Deployment reference for the four Technitium DNS VMs: host placement, IP addresses, zone replication, RFC 2136 dynamic updates, and firewall rules.
Four Technitium DNS Server v14+ VMs serve the core.aorxi.io internal zone across both sites. This page covers deployment specifics — VM placement, IPs, zone replication, dynamic update wiring, and firewall rules. For the DNS architecture design and zone rationale, see DNS.
VM Inventory
All four VMs sit on VLAN 30 (VM Services) and are sized identically: 2 vCPU, 1 GB RAM, 8 GB disk. Technitium runs as a Proxmox LXC container (Ubuntu 22.04) or VM. DNS listens on port 53; the web UI and cluster API listen on port 5380.
| VM | Site | Proxmox Host | IP | Role |
|---|---|---|---|---|
sa-dns-01 | Site A | sa-stor-01 | 10.10.30.10 | Primary |
sa-dns-02 | Site A | see caution below | 10.10.30.11 | Secondary |
sb-dns-01 | Site B | sb-cmp-01 | 10.20.30.10 | Secondary |
sb-dns-02 | Site B | sb-cmp-02 | 10.20.30.11 | Secondary |
Tentative — sa-dns-02 host not confirmed
The Proxmox host for sa-dns-02 is sa-cmp-01 or sa-cmp-02. The choice has not been finalized.
Replication and Cluster
sa-dns-01 is the authoritative primary. All zones are authored there; the other three nodes are read-only secondaries. sa-dns-01 sends DNS NOTIFY to all secondaries on every zone change. Zone transfers are secured with the TSIG key opnsense-ddns (HMAC-SHA256). Default zone TTL is 300 s.
| Replication path | Transport | Port | Auth |
|---|---|---|---|
sa-dns-01 → sa-dns-02 | AXFR (TCP) | 53 | TSIG opnsense-ddns |
sa-dns-01 → sb-dns-01 | AXFR (TCP) over WireGuard | 53 | TSIG opnsense-ddns |
sa-dns-01 → sb-dns-02 | AXFR (TCP) over WireGuard | 53 | TSIG opnsense-ddns |
Zone transfer is restricted to specific IPs only: 10.10.30.11, 10.20.30.10, 10.20.30.11.
WireGuard dependency for Site B
sb-dns-01 and sb-dns-02 pull zone updates over the WireGuard tunnel. If the tunnel is down, Site B nodes serve their last replicated copy — stale but functional for resolution. New or changed records do not appear at Site B until the tunnel recovers.
Technitium Cluster
The Technitium cluster synchronizes server settings, apps, and catalog zone membership from sa-dns-01 to all secondaries — this is separate from AXFR zone replication. All four nodes are managed from the sa-dns-01 web panel at http://10.10.30.10:5380.
Zone Design
Forward Zone
One primary forward zone: core.aorxi.io. Hosted as Primary on sa-dns-01, replicated as Secondary to the other three nodes. SOA primary NS: sa-dns-01.core.aorxi.io. NS records are added for all four VMs.
Recursion is enabled with full root-server resolution — no upstream forwarders configured.
Reverse Zones
All reverse zones are created as Primary on sa-dns-01 and replicated identically. The zone name is formed by reversing the network octets and appending .in-addr.arpa. Each /24 VLAN gets one zone; /22 VLANs (40 and 100) each produce four /24 zones.
Site A reverse zones (representative set):
| VLAN | Subnet | Reverse zone |
|---|---|---|
| 10 | 10.10.10.0/24 | 10.10.10.in-addr.arpa |
| 20 | 10.10.20.0/24 | 20.10.10.in-addr.arpa |
| 25 | 10.10.25.0/24 | 25.10.10.in-addr.arpa |
| 30 | 10.10.30.0/24 | 30.10.10.in-addr.arpa |
| 40 | 10.10.40.0/22 | 40.10.10.in-addr.arpa, 41.10.10.in-addr.arpa, 42.10.10.in-addr.arpa, 43.10.10.in-addr.arpa |
| 60 | 10.10.60.0/24 | 60.10.10.in-addr.arpa |
| 90 | 10.10.90.0/24 | 90.10.10.in-addr.arpa |
| 100 | 10.10.100.0/22 | 100.10.10.in-addr.arpa, 101.10.10.in-addr.arpa, 102.10.10.in-addr.arpa, 103.10.10.in-addr.arpa |
| 253 | 10.10.253.0/24 | 253.10.10.in-addr.arpa |
Site B follows the same pattern with 10.20.x → x.20.10.in-addr.arpa. The WireGuard transit subnet (10.255.0.0/24) gets a single zone: 0.255.10.in-addr.arpa.
DHCP DNS Assignment
OPNsense DHCP scopes hand out the two local Technitium VMs as DNS servers. The search domain for all VLANs is core.aorxi.io.
| Site | DNS Server 1 | DNS Server 2 |
|---|---|---|
| Site A | 10.10.30.10 (sa-dns-01) | 10.10.30.11 (sa-dns-02) |
| Site B | 10.20.30.10 (sb-dns-01) | 10.20.30.11 (sb-dns-02) |
RFC 2136 Dynamic Updates
Dynamic DNS registration is enabled for three VLANs. All other VLANs (10, 20, 25, 60, 65, 80, 90, 253) use static records managed manually in the Technitium UI on sa-dns-01.
| VLAN | Direction | Notes |
|---|---|---|
| 30 (VM Services) | A + PTR | New VMs auto-register |
| 40 (Kubernetes Nodes) | A + PTR | Kubernetes node VMs |
| 100 (Lab / Trusted Client) | A + PTR | Dev and admin devices |
All dynamic updates are signed with the opnsense-ddns TSIG key (HMAC-SHA256). Zone policy on the three dynamic zones: signed updates only.
OPNsense DDNS
Both Site A and Site B OPNsense DHCP servers send RFC 2136 updates to sa-dns-01 at 10.10.30.10. Configure per VLAN scope under OPNsense → Services → DHCP → Dynamic DNS:
Update Server: 10.10.30.10 # sa-dns-01 — both sites point here
Protocol: RFC 2136
Zone: core.aorxi.io (forward) / <reverse-zone> (PTR)
Key name: opnsense-ddns
Key algorithm: hmac-sha256
Key secret: <generated on sa-dns-01>
TTL: 300Site B DHCP DDNS updates travel over WireGuard to reach sa-dns-01. New DHCP leases on Site B do not auto-register until the tunnel is up — acceptable for an infra-change workflow.
Kubernetes external-dns
external-dns pushes Kubernetes Ingress and Service hostnames into Technitium via RFC 2136. The same opnsense-ddns TSIG key is reused. Deployment args:
- --source=ingress
- --source=service
- --provider=rfc2136
- --rfc2136-host=10.10.30.10 # sa-dns-01 primary
- --rfc2136-port=53
- --rfc2136-zone=core.aorxi.io
- --rfc2136-tsig-secret=<opnsense-ddns-secret>
- --rfc2136-tsig-secret-alg=hmac-sha256
- --rfc2136-tsig-keyname=opnsense-ddns
- --rfc2136-tsig-axfr=true
- --domain-filter=core.aorxi.io
- --txt-owner-id=k8s-site-a # use k8s-site-b for Site B cluster
- --policy=upsert-onlyThe txt-owner-id prevents the two site clusters from clobbering each other's TXT ownership records.
Firewall Rules
Rules are applied on OPNsense at each site on the WireGuard interface.
Site A — WireGuard inbound
| Proto | Source | Dest | Port | Purpose |
|---|---|---|---|---|
| TCP | 10.20.30.10, 10.20.30.11 | 10.10.30.10 | 53 | AXFR pull (sb-dns-01/02) |
| UDP | 10.20.30.10, 10.20.30.11 | 10.10.30.10 | 53 | DDNS updates (OPNsense-B) |
| TCP | 10.255.0.2 | 10.10.30.10 | 5380 | Technitium cluster API |
Site B — WireGuard inbound
| Proto | Source | Dest | Port | Purpose |
|---|---|---|---|---|
| UDP | 10.10.30.10 | 10.20.30.10, 10.20.30.11 | 53 | NOTIFY from sa-dns-01 |
| TCP | 10.10.30.10 | 10.20.30.10, 10.20.30.11 | 5380 | Technitium cluster API |
| UDP | any Site B client VLAN | 10.20.30.10, 10.20.30.11 | 53 | Client queries |
| TCP | any Site B client VLAN | 10.20.30.10, 10.20.30.11 | 53 | Client queries (large responses) |
Setup
1. Install Technitium on all four VMs
curl -sSL https://download.technitium.com/dns/install.sh | sudo bash
# DNS: port 53 | Web UI / cluster API: port 5380Open http://<vm-ip>:5380 and change the default admin password immediately.
2. Configure recursion
On all nodes: Settings → Recursion → Enabled. Leave Forwarders empty — use root-server recursive resolution.
3. Set up the Technitium cluster
On sa-dns-01: Settings → Cluster → Enable Clustering → set node as Primary → generate join token.
On each of sa-dns-02, sb-dns-01, sb-dns-02: Settings → Cluster → Enable Clustering → set node as Secondary → enter sa-dns-01's address and join token → verify the node appears in sa-dns-01's cluster view.
4. Create zones and configure replication
On sa-dns-01:
- Zones → Add Zone → Primary →
core.aorxi.io. Set SOA, add NS records for all four VMs, add all infrastructure A records. - Add each reverse zone as Primary. Add PTR records for all static hosts.
- For every zone: Zone Options → Zone Transfer → restrict to
10.10.30.11,10.20.30.10,10.20.30.11→ set NOTIFY to the same IPs → attach the TSIG key.
On each secondary:
- Zones → Add Zone → Secondary →
core.aorxi.io→ primary server:10.10.30.10→ attach TSIG key. - Repeat for each reverse zone.
5. Configure TSIG and enable dynamic updates
Generate the TSIG secret on sa-dns-01:
openssl rand -base64 32In the Technitium UI on sa-dns-01: Settings → TSIG Keys → Add key → name opnsense-ddns, algorithm HMAC-SHA256. Record the secret for OPNsense and external-dns.
For the forward zone and PTR zones covering VLANs 30, 40, and 100: Zone Options → Dynamic Updates → Policy: Signed updates only (TSIG) → allowed key: opnsense-ddns.
Cutover from OPNsense Unbound
OPNsense Unbound acts as the fallback resolver during Phase 5 bring-up and is disabled after cutover is verified.
Update static DNS configuration on each Proxmox node:
# /etc/resolv.conf (or network config per distro)
nameserver 10.10.30.10
nameserver 10.10.30.11
search core.aorxi.ioPer VLAN DHCP cutover: OPNsense → Services → DHCP → each scope → DNS Server 1 = 10.10.30.10 → DNS Server 2 = 10.10.30.11 → save and apply. Renew DHCP on a test client and confirm resolution of sa-stor-01.core.aorxi.io.
Rollback: flip the DHCP DNS options back to the OPNsense IP. The change takes effect on the next lease renewal.
Site B VMs (sb-dns-01, sb-dns-02) are provisioned after the WireGuard tunnel is up (Phase 8 of the build sequence).
Related Pages
- DNS — DNS architecture, zone design rationale, and infrastructure record tables
- WireGuard — site-to-site VPN that carries cross-site AXFR and DDNS traffic
- VLAN Reference — VLAN 30 (VM Services) where all DNS VMs reside
- Kubernetes Planning —
external-dnsand Kubernetes service DNS integration - CA & Certificates — Let's Encrypt DNS-01 certificate strategy via Cloudflare
Platform Services
Application and platform services for the AORXI homelab: internal DNS via Technitium VMs, OpenBao secrets management, the UniFi OS Server controller, Kafka and database operations patterns, container build infrastructure, and certificate management via Let's Encrypt DNS-01 and step-ca.
Secrets — OpenBao
Two independent OpenBao instances (sa-bao-01, sb-bao-01) on the edge E200s: secret tiers, cross-site transit auto-unseal, AppRole consumers, and the break-glass fallback.