No description
  • Go 98.1%
  • Makefile 1.1%
  • Dockerfile 0.8%
Find a file
Pierre-Olivier Mercier 85b10f296d checker: join SRV record Hdr.Name to service domain before parsing
SRV record owners inside the service body are relative to the service
location (subdomain.domain). Using Hdr.Name directly produced relative
owners in the report and broke grouping/dedup. Join via
sdk.JoinRelative against the already-computed serviceDomain.
2026-04-30 08:46:34 +07:00
checker checker: join SRV record Hdr.Name to service domain before parsing 2026-04-30 08:46:34 +07:00
plugin Initial commit 2026-04-26 18:17:38 +07:00
.gitignore Initial commit 2026-04-26 18:17:38 +07:00
Dockerfile Initial commit 2026-04-26 18:17:38 +07:00
go.mod Initial commit 2026-04-26 18:17:38 +07:00
go.sum Initial commit 2026-04-26 18:17:38 +07:00
LICENSE Initial commit 2026-04-26 18:17:38 +07:00
main.go Initial commit 2026-04-26 18:17:38 +07:00
Makefile Initial commit 2026-04-26 18:17:38 +07:00
README.md Initial commit 2026-04-26 18:17:38 +07:00

checker-srv

Generic SRV records checker for happyDomain.

For every SRV record attached to a service, verifies:

  • DNS resolution of each target (A/AAAA)
  • RFC 2782 compliance: target is not "." (null), target is not a CNAME
  • TCP reachability on target:port (for _tcp SRVs)
  • UDP reachability on target:port (for _udp SRVs), via ICMP port-unreachable detection

TLS/certificate testing is intentionally out of scope, it belongs to a dedicated TLS checker.

The HTML report surfaces the most common failure scenarios at the top with actionable remediation guidance (DNS failure, CNAME-as-target, TCP unreachable, explicit null-target).

Usage

Standalone HTTP server

# Build and run
make
./checker-srv -listen :8080

The server exposes:

  • GET /health, health check
  • GET /definition, checker definition (options, rules, availability)
  • POST /collect, collect SRV observations (happyDomain external checker protocol)
  • POST /evaluate, evaluate observations against the rules
  • POST /report, render the HTML report

Docker

make docker
docker run -p 8080:8080 happydomain/checker-srv

happyDomain plugin

make plugin
# produces checker-srv.so, loadable by happyDomain as a Go plugin

The plugin exposes a NewCheckerPlugin symbol returning the checker definition and observation provider, which happyDomain registers in its global registries at load time.

Versioning

The binary, plugin, and Docker image embed a version string overridable at build time:

make CHECKER_VERSION=1.2.3
make plugin CHECKER_VERSION=1.2.3
make docker CHECKER_VERSION=1.2.3

happyDomain remote endpoint

Set the endpoint admin option for the SRV checker to the URL of the running checker-srv server (e.g., http://checker-srv:8080). happyDomain will delegate observation collection to this endpoint.

Protocol

POST /collect

Request:

{
  "key": "srv_records",
  "target": {"userId": "...", "domainId": "...", "serviceId": "..."},
  "options": {
    "service": {"_svctype": "svcs.UnknownSRV", "Service": {"srv": [ /* dns.SRV records */ ]}},
    "subdomain": "_sip._tcp",
    "domain": "example.com",
    "tcpTimeout": 3000,
    "udpTimeout": 2000
  }
}

Response:

{
  "data": {
    "serviceDomain": "_sip._tcp.example.com",
    "records": [
      {
        "service": "sip",
        "proto": "tcp",
        "owner": "_sip._tcp.example.com",
        "target": "sip1.example.com",
        "port": 5061,
        "priority": 10,
        "weight": 20,
        "addresses": ["203.0.113.5"],
        "probes": [
          {
            "address": "203.0.113.5:5061",
            "proto": "tcp",
            "connected": true,
            "latencyMs": 12.4
          }
        ]
      }
    ]
  }
}

Discovered TLS endpoints

As a by-product of every /collect, this checker publishes DiscoveryEntry records of type tls.endpoint.v1 (see checker-tls/contract) so that the TLS checker can probe the targets without re-parsing SRV data:

  • Direct TLS entries (empty STARTTLS) for service names that imply implicit TLS on connect: _https, _ldaps, _sips, _imaps, _pop3s, _smtps, _submissions, _xmpps-client, _xmpps-server, _ftps, _nntps, _ircs, _telnets, _ipps, _mqtts, _coaps, _stuns, _turns.
  • STARTTLS entries for service names that upgrade mid-stream: _smtp (opportunistic), _submission (required), _imap (required), _pop3 (required), _xmpp-client (required), _xmpp-server (opportunistic), _ldap, _nntp, _ftp, _sieve, _postgresql.

Null targets (.) and unknown service names are skipped. SNI is set to the SRV target hostname.

Rules

Name Description
srv_records_present At least one SRV record is published.
srv_null_target Detects "." targets (RFC 2782, service intentionally unavailable).
srv_target_not_cname Warns when an SRV target is a CNAME (RFC 2782 violation).
srv_targets_resolve Every target resolves to at least one A/AAAA.
srv_tcp_reachable Every _tcp SRV target:port accepts a TCP connection.
srv_udp_reachable UDP targets do not return ICMP port-unreachable.
srv_redundancy At least two distinct targets exist (no single point of failure).

License & licensing roadmap

This project is currently licensed under the GNU Affero General Public License v3.0 (see LICENSE), because it still imports happydns.ServiceMessage from the happyDomain server module (git.happydns.org/happyDomain/model), which is itself distributed under AGPL-3.0 and a commercial license.

The core checker types (CheckerOptions, CheckerDefinition, ObservationProvider, CheckRule, …) have already been migrated to checker-sdk-go; only the service-message types remain on the AGPL side.

Planned relicensing: as soon as the remaining ServiceMessage dependency has been removed (moved into a dedicated permissively licensed module), this project will be relicensed under the MIT License, in line with the rest of the happyDomain checker ecosystem (see checker-dummy for the target shape).

Contributors notice: by submitting a contribution to this repository, you accept that your contribution will be relicensed from AGPL-3.0 to MIT at the time of the relicensing described above. If you do not agree with this, please do not submit contributions until the relicensing has taken place.

The third-party Apache-2.0 attributions for checker-sdk-go are recorded in NOTICE and must accompany any binary or source redistribution of this project.