fix(node): allow IPv6-only addresses (#537)

This commit is contained in:
sagit
2026-08-03 11:05:04 +08:00
committed by GitHub
parent cbe2fc492e
commit a8fd01d4d8
2 changed files with 53 additions and 0 deletions
@@ -3,6 +3,7 @@ package handler
import (
"fmt"
"net"
"net/netip"
"strings"
)
@@ -75,6 +76,12 @@ func IsValidNodeAddress(addr string) error {
if strings.ContainsAny(addr, "/?") {
return fmt.Errorf("address must not contain path or query parameters")
}
// A bare IPv6 literal contains multiple colons, so net.SplitHostPort treats
// it as a malformed host:port pair. Accept IP literals before attempting
// host:port parsing; netip also handles scoped IPv6 addresses.
if _, err := netip.ParseAddr(addr); err == nil {
return nil
}
_, _, err := net.SplitHostPort(addr)
if err != nil {
@@ -0,0 +1,46 @@
package handler
import "testing"
func TestIssue515IsValidNodeAddressAcceptsBareIPv6(t *testing.T) {
for _, addr := range []string{
"2001:db8::1",
"::1",
"fe80::1%eth0",
} {
t.Run(addr, func(t *testing.T) {
if err := IsValidNodeAddress(addr); err != nil {
t.Fatalf("expected bare IPv6 address %q to be accepted: %v", addr, err)
}
})
}
}
func TestIsValidNodeAddressKeepsExistingAddressForms(t *testing.T) {
for _, addr := range []string{
"203.0.113.10",
"node.example.com",
"node.example.com:6365",
"[2001:db8::1]:6365",
} {
t.Run(addr, func(t *testing.T) {
if err := IsValidNodeAddress(addr); err != nil {
t.Fatalf("expected node address %q to be accepted: %v", addr, err)
}
})
}
}
func TestIsValidNodeAddressRejectsURLComponents(t *testing.T) {
for _, addr := range []string{
"https://node.example.com",
"node.example.com/path",
"node.example.com?transport=tcp",
} {
t.Run(addr, func(t *testing.T) {
if err := IsValidNodeAddress(addr); err == nil {
t.Fatalf("expected node address %q to be rejected", addr)
}
})
}
}