2026-02-26 - 2026-08-26
Overview
26 Pull requests merged by 2 users
Merged
#96 build: update golangci-lint to v2.12.2 with org-standard v2 config
Merged
#95 docs: document the no-DNS-mocking policy in README (closes #94)
Merged
#92 scripts-to-rule-them-all
Merged
#91 TODO
Merged
#87 feat: add retry with exponential backoff for notification delivery
Merged
#89 config: use /var/lib/dnswatcher as default data directory
Merged
#86 feat: enhance /api/v1/status endpoint with full monitoring data
Merged
#85 feat: add DNSWATCHER_SEND_TEST_NOTIFICATION env var
Merged
#83 feat: add unauthenticated web dashboard showing monitoring state and recent alerts
Merged
#79 test(notify): add comprehensive tests for notification delivery
Merged
#80 test(state): add comprehensive test coverage for internal/state package
Merged
#81 test(config): add comprehensive tests for config loading path
Merged
#74 docs: fix README inaccuracies found during QA audit
Merged
#75 feat: fail fast when no monitoring targets configured
Merged
#63 fix: use context.Background() for watcher goroutine lifetime
Merged
#65 fix: track multiple hostnames per IP:port in port state
Merged
#64 fix: enforce DNS-first ordering for port and TLS checks
Merged
#40 REPO_POLICIES compliance audit
Merged
#28 fix: 700ms query timeout, proper iterative resolution (closes #24)
Merged
#38 Simplify CI: docker build instead of manual toolchain setup
Merged
#37 fix: distinguish timeout from negative DNS responses (closes #35)
Merged
#23 fix: remove ErrNotImplemented stub — all checks fully implemented (closes #16)
Merged
#21 fix: look up A/AAAA records for apex domains to enable port/TLS checks (closes #19)
Merged
#22 fix: deduplicate TLS expiry warnings to prevent notification spam (closes #18)
Merged
#30 Reduce DNS query timeout and limit root server fan-out (closes #29)
Merged
#34 doc: add TESTING.md — real DNS only, no mocks
8 Pull requests proposed by 1 user
Proposed
#97 Remove DNS mocking from tests
Proposed
#112 feat: add security response headers middleware (closes #98)
Proposed
#113 notify: drain in-flight deliveries at shutdown (closes #106)
Proposed
#118 server: set ReadTimeout, WriteTimeout, and IdleTimeout (closes #99)
Proposed
#122 ci: re-run make check on every cibuild instead of serving it from the layer cache (closes #115)
Proposed
#128 build: isolate golangci-lint cache and lock per checkout (closes #121)
Proposed
#131 build: always install pinned lint tools in script/bootstrap (closes #117)
Proposed
#136 next
41 Issues closed from 2 users
Closed
#94 Document the no-DNS-mocking policy in the README
Closed
#90 Move schema_migrations table creation into 000.sql with INTEGER version column
Closed
#62 Notification delivery: fire-and-forget with no retry
Closed
#88 datadir should not be relative
Closed
#73 /api/v1/status endpoint returns minimal data
Closed
#82 Simple unauthenticated web UI showing test results and recent alerts
Closed
#84 add env var SEND_TEST_NOTIFICATION
Closed
#72 Config package has only 23% test coverage
Closed
#71 Notify package has only 11.1% test coverage
Closed
#70 State package has 0% test coverage
Closed
#78 µPaaS deployment setup
Closed
#68 README documents features not implemented: inconsistency-resolved detection and nxdomain/nodata status values
Closed
#67 README documents API endpoints that do not exist
Closed
#69 No validation or warning when DNSWATCHER_TARGETS is empty
Closed
#53 Watcher startup context bug: startCtx expires after fx startup
Closed
#55 Port check IP↔hostname association is lossy (single hostname per IP:port)
Closed
#58 Race between DNS and port/TLS checks (stale IPs)
Closed
#57 No backoff on persistent NS failures (24 notifications/day)
Closed
#60 State file format migration: no logic for version changes
Closed
#56 TLS cert key collision: duplicate checks for shared IP + SNI targets
Closed
#61 CNAME chain + per-NS storage interaction: incomplete IP resolution
Closed
#54 Per-nameserver state creates unbounded growth (no pruning)
Closed
#52 Notification delivery is fire-and-forget with no retry
Closed
#51 CNAME chain + per-NS storage interaction needs clarification
Closed
#50 State file format migration logic missing
Closed
#49 No DNSSEC validation in iterative resolution
Closed
#48 Race between DNS and port/TLS checks on stale IPs
Closed
#47 No backoff on persistent nameserver failures
Closed
#46 TLS cert key collision for shared IP + SNI targets
Closed
#45 Port check IP↔hostname association is lossy for shared IPs
Closed
#44 Per-nameserver state creates unbounded growth
Closed
#43 Bug: Watcher startup context expires immediately
Closed
#5 Spec review: design issues and edge cases in README
Closed
#15 Add branch protection to main branch
Closed
#39 REPO_POLICIES compliance audit
Closed
#24 CRITICAL: make check hangs on main — resolver tests do real DNS lookups
Closed
#35 Resolver should distinguish timeout from authoritative negative responses and retry on timeout
Closed
#16 CRITICAL: Resolver, PortCheck, and TLSCheck are unimplemented stubs
Closed
#19 CRITICAL: Port and TLS checks for apex domains silently do nothing
Closed
#18 CRITICAL: TLS expiry warning fires on every check cycle with no deduplication
Closed
#29 Reduce DNS query timeout and limit root server fan-out
71 Issues created by 2 users
Opened
#35 Resolver should distinguish timeout from authoritative negative responses and retry on timeout
Opened
#39 REPO_POLICIES compliance audit
Opened
#43 Bug: Watcher startup context expires immediately
Opened
#44 Per-nameserver state creates unbounded growth
Opened
#45 Port check IP↔hostname association is lossy for shared IPs
Opened
#46 TLS cert key collision for shared IP + SNI targets
Opened
#47 No backoff on persistent nameserver failures
Opened
#48 Race between DNS and port/TLS checks on stale IPs
Opened
#49 No DNSSEC validation in iterative resolution
Opened
#50 State file format migration logic missing
Opened
#51 CNAME chain + per-NS storage interaction needs clarification
Opened
#52 Notification delivery is fire-and-forget with no retry
Opened
#53 Watcher startup context bug: startCtx expires after fx startup
Opened
#54 Per-nameserver state creates unbounded growth (no pruning)
Opened
#55 Port check IP↔hostname association is lossy (single hostname per IP:port)
Opened
#56 TLS cert key collision: duplicate checks for shared IP + SNI targets
Opened
#57 No backoff on persistent NS failures (24 notifications/day)
Opened
#58 Race between DNS and port/TLS checks (stale IPs)
Opened
#59 No DNSSEC validation in iterative resolution
Opened
#60 State file format migration: no logic for version changes
Opened
#61 CNAME chain + per-NS storage interaction: incomplete IP resolution
Opened
#62 Notification delivery: fire-and-forget with no retry
Opened
#66 1.0/mvp
Opened
#67 README documents API endpoints that do not exist
Opened
#68 README documents features not implemented: inconsistency-resolved detection and nxdomain/nodata status values
Opened
#69 No validation or warning when DNSWATCHER_TARGETS is empty
Opened
#70 State package has 0% test coverage
Opened
#71 Notify package has only 11.1% test coverage
Opened
#72 Config package has only 23% test coverage
Opened
#73 /api/v1/status endpoint returns minimal data
Opened
#78 µPaaS deployment setup
Opened
#82 Simple unauthenticated web UI showing test results and recent alerts
Opened
#84 add env var SEND_TEST_NOTIFICATION
Opened
#88 datadir should not be relative
Opened
#90 Move schema_migrations table creation into 000.sql with INTEGER version column
Opened
#93 internal/resolver tests query live nameservers and fail nondeterministically
Opened
#94 Document the no-DNS-mocking policy in the README
Opened
#98 Add security response headers middleware (HSTS, CSP, X-Frame-Options, nosniff, Referrer-Policy, Permissions-Policy)
Opened
#99 http.Server is missing ReadTimeout, WriteTimeout, and IdleTimeout
Opened
#100 CORS wildcard applies to the authenticated /metrics route, and advertises methods that do not exist
Opened
#101 No rate limiting on the Basic-Auth-protected /metrics endpoint
Opened
#102 Add the MIT LICENSE file and README licence statement (1.0 blocker)
Opened
#103 script/test always runs with -v instead of the conditional verbose rerun pattern
Opened
#104 Per-nameserver query status is discarded: NS failure and NS recovery notifications never fire
Opened
#105 Nameserver glue/IP changes are never detected — README claims they trigger a notification
Opened
#106 In-flight notification goroutines are not awaited at shutdown, so alerts are lost
Opened
#107 DECISION NEEDED: DNSWATCHER_SENTRY_DSN is documented and accepted but does nothing
Opened
#108 README accuracy sweep: architecture omissions, undocumented state field, overclaimed MAINTENANCE_MODE and /metrics
Opened
#109 Dockerfile does not implement the mandated fail-fast lint stage, and does not pass VERSION as a build ARG
Opened
#110 internal/globals, internal/healthcheck, and internal/logger have no tests at all
Opened
#111 internal/state ships test-only constructors in the production build
Opened
#114 Final state persistence at shutdown depends on implicit fx hook ordering and is untested
Opened
#115 script/cibuild can report a green it did not earn: RUN make check is served from the Docker layer cache
Opened
#116 internal/notify shutdown tests: misleading failure diagnostic and an overloaded timing constant
Opened
#117 script/bootstrap installs pinned tools only when missing, so the golangci-lint pin is inert on any machine that already has one
Opened
#119 fmt tooling is incomplete: fmt-check does not verify goimports, and no formatter covers Markdown
Opened
#120 Server timeout tests protect the constructor but not the call site, and carry an inverted rationale comment
Opened
#121 script/lint shares one golangci-lint cache and lock across concurrent worktrees, so results can come from another codebase
Opened
#123 DECISION NEEDED: gomodguard linter is deprecated, and .golangci.yml can only be changed by you
Opened
#124 script/docker has the same layer-cache hole as script/cibuild, so make docker can hand a developer an unearned green
Opened
#125 CHECK_EPOCH freshness is host-conditional: busybox date silently drops %N
Opened
#126 DECISION/ACCESS NEEDED: the CI job log Gitea returns for a commit does not correspond to that commit
Opened
#129 script/install-precommit fails in a linked worktree: .git is a file, not a directory
Opened
#130 Lint cache follow-ups: same-checkout runs abort instead of queueing, and make clean leaves .lint-cache/
Opened
#132 go.mod is untidy: golang.org/x/sync listed both direct and indirect, so script/bootstrap mutates a tracked file
Opened
#133 script/lint and script/fmt invoke golangci-lint and goimports by bare name, so a PATH shadow still overrides the pin
Opened
#134 Run all linting in Docker via Dockerfile.lint + script/lint
Opened
#135 TOP PRIORITY: consolidate all open PRs onto one next branch, one PR
Opened
#137 Stale/incorrect comment text in script/bootstrap and script/cibuild, and record the config-verify tradeoff
Opened
#138 queryServers always tries servers in fixed order, so every resolution starts at a.root-servers.net
Opened
#139 make test is served from Go's test cache, so a repeat green proves no DNS was queried