app: show what the server reports as facts, not as inputs

The settings card offered three editable boxes and said nothing about the
server itself — which addresses a test will actually use, on which ports,
what it can measure. That is the part a person checks before trusting a
result, and "which address did this come from" is precisely the question
a report leaves open.

The server now publishes it. The profile's targets carried one IPv4 and a
TODO; it reports both families and both alternates, derived from the UDP
listen spec rather than configured separately, so the list cannot drift
from what is actually bound. No reservation means no alternate is
claimed: announcing a second address as the RFC 5780 alternate when none
was set aside would promise a redirect the server will not send.

The app renders them read-only, in a panel visibly distinct from the
fields above. An editable box that changes nothing is worse than no box,
and these are facts to read rather than settings to apply.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
mrambossek
2026-08-02 08:14:42 +02:00
co-authored by Claude Opus 5
parent fe4ec23ba1
commit c4f2a10790
8 changed files with 207 additions and 8 deletions
+38
View File
@@ -322,6 +322,44 @@ func (c *Config) Listeners() []Listener {
}
}
// MeasurementAddrs picks out the addresses this server can be measured on, by family, splitting
// primaries from the reserved alternates.
//
// Derived from what is actually bound rather than configured separately: a second list of the
// server's own addresses is a second thing to keep in step, and the copy that drifts is the one
// clients are told about.
func (c *Config) MeasurementAddrs() (ip4, ip6, ip4Alt, ip6Alt string) {
reserved := map[string]bool{}
for _, ip := range c.ReservedIPs() {
reserved[ip.String()] = true
}
// The UDP data plane binds every address a client may be pointed at, which makes it the
// honest source for this.
for _, a := range Addrs(c.UDPListen) {
host, _, err := net.SplitHostPort(a)
if err != nil {
continue
}
host = strings.Trim(host, "[]")
ip := net.ParseIP(host)
if ip == nil {
continue
}
alt := reserved[ip.String()]
switch {
case ip.To4() != nil && alt && ip4Alt == "":
ip4Alt = host
case ip.To4() != nil && !alt && ip4 == "":
ip4 = host
case ip.To4() == nil && alt && ip6Alt == "":
ip6Alt = host
case ip.To4() == nil && !alt && ip6 == "":
ip6 = host
}
}
return
}
// Addrs splits a comma-separated listen spec into individual addresses.
// Explicit per-address binds matter on multi-IP hosts: a wildcard bind
// (":8443") would also claim addresses reserved for other purposes (e.g. an