Ryan Malloy 618e9504e7 secondary: scaffold public CoreDNS secondary on ns.supported.systems
Adds a second non-HE public secondary that pulls AXFR from dell01 (the
hidden primary at 154.27.180.210) and answers public queries on
ns.supported.systems (64.177.113.227, 2001:19f0:5c00:4daa:5400:6ff:fe2d:38fa).

  secondary/
    Corefile                            generated, 84 zones + REFUSED catch-all
    docker-compose.yml                  CoreDNS in host-net mode
    Makefile                            up/down/logs/regen/test/axfr-test
    .env / .env.example                 image pin + bind IPs
    scripts/generate-secondary-corefile.sh  reads ../zones/*.zone

  scripts/notify-he.py → notify-secondaries.py
                                        adds 64.177.113.227 as a second
                                        NOTIFY target alongside HE's
                                        216.218.130.2

Uses CoreDNS's `bind` plugin to avoid colliding with systemd-resolved
on loopback :53. Authoritative-only — non-listed zones get REFUSED, no
recursion. AXFR pull requires opening TCP/53 on dell01's FortiWiFi for
the secondary's IP (manual step, separate from this commit).
2026-05-20 18:40:11 -06:00

53 lines
2.0 KiB
Makefile

.DEFAULT_GOAL := help
SHELL := /usr/bin/env bash
COMPOSE := docker compose
# Pull COREDNS_IMAGE and friends into the recipe env. The .env file is
# also auto-loaded by `docker compose` itself, but `include` makes the
# values available in shell snippets within Makefile recipes too.
include .env
export
.PHONY: help regen up down restart logs ps test axfr-test
help: ## Show this help
@awk 'BEGIN {FS = ":.*?## "} /^[a-zA-Z_-]+:.*?## / {printf " \033[36m%-12s\033[0m %s\n", $$1, $$2}' $(MAKEFILE_LIST)
regen: ## Re-generate Corefile from ../zones/*.zone
@./scripts/generate-secondary-corefile.sh
up: ## Start the secondary
$(COMPOSE) up -d
@sleep 2 && $(COMPOSE) logs --tail=20 coredns
down: ## Stop & remove containers
$(COMPOSE) down
restart: ## Restart CoreDNS (does NOT regen Corefile)
$(COMPOSE) restart coredns
logs: ## Tail CoreDNS logs
$(COMPOSE) logs -f coredns
ps: ## Show container status
$(COMPOSE) ps
# ---------------------------------------------------------------------------
# Smoke tests — these query the LOCAL CoreDNS (this machine)
# ---------------------------------------------------------------------------
test: ## Smoke-test plain DNS against the local secondary
@echo "=== SOA for supported.systems (should match dell01 + HE) ==="
@dig @127.0.0.1 supported.systems SOA +short +tries=1 +time=3
@echo "=== NS records for supported.systems ==="
@dig @127.0.0.1 supported.systems NS +short +tries=1 +time=3
@echo "=== A record for ns.supported.systems (the glue) ==="
@dig @127.0.0.1 ns.supported.systems A +short +tries=1 +time=3
axfr-test: ## Verify AXFR pull from dell01 works (TCP/53 to primary)
@echo "Probing TCP/53 reachability to dell01 (154.27.180.210)..."
@timeout 5 bash -c "</dev/tcp/154.27.180.210/53" && echo " ✓ TCP/53 open" \
|| (echo " ✗ TCP/53 BLOCKED — add this server's IP to dell01's FortiWiFi allow list" && exit 1)
@echo "Attempting AXFR for supported.systems..."
@dig @154.27.180.210 supported.systems AXFR +tcp +tries=1 +time=8 +short | head -5