hashicorp/nomad · error
Failed to parse Serf address: %v
Error message
Failed to parse Serf address: %v
What it means
Same normalization pass as RPC/HTTP: Addresses.Serf is validated with normalizeBind against BindAddr. A Serf bind address that cannot be parsed (invalid IP or failing template) stops agent startup with this error. The wrapped %v explains the concrete parse problem.
Source
Thrown at command/agent/config.go:2393
c.BindAddr = ipStr
}
c.BindAddr = ipaddr.NormalizeAddr(c.BindAddr)
httpAddrs, err := normalizeMultipleBind(c.Addresses.HTTP, c.BindAddr)
if err != nil {
return fmt.Errorf("Failed to parse HTTP address: %v", err)
}
c.Addresses.HTTP = strings.Join(httpAddrs, " ")
addr, err := normalizeBind(c.Addresses.RPC, c.BindAddr)
if err != nil {
return fmt.Errorf("Failed to parse RPC address: %v", err)
}
c.Addresses.RPC = addr
addr, err = normalizeBind(c.Addresses.Serf, c.BindAddr)
if err != nil {
return fmt.Errorf("Failed to parse Serf address: %v", err)
}
c.Addresses.Serf = addr
c.normalizedAddrs = &NormalizedAddrs{
RPC: normalizeAddrWithPort(c.Addresses.RPC, c.Ports.RPC),
Serf: normalizeAddrWithPort(c.Addresses.Serf, c.Ports.Serf),
}
c.normalizedAddrs.HTTP = make([]string, len(httpAddrs))
for i, addr := range httpAddrs {
c.normalizedAddrs.HTTP[i] = normalizeAddrWithPort(addr, c.Ports.HTTP)
}
addr, err = normalizeAdvertise(c.AdvertiseAddrs.HTTP, httpAddrs[0], c.Ports.HTTP, c.DevMode)
if err != nil {
return fmt.Errorf("Failed to parse HTTP advertise address (%v, %v, %v, %v): %v", c.AdvertiseAddrs.HTTP, c.Addresses.HTTP, c.Ports.HTTP, c.DevMode, err)
}
c.AdvertiseAddrs.HTTP = addr
View on GitHub (pinned to 482b49bf1a)
Solutions
- Correct addresses.serf to a valid IP or fix the template syntax
- Confirm the interface name in the template exists on the host
- Ensure the value is a bare address without scheme or port
- Check the wrapped %v message for the underlying cause
Example fix
// before
addresses { serf = "{{ GetInterfaceIP \"en01\" }}" } # interface typo
// after
addresses { serf = "{{ GetInterfaceIP \"en0\" }}" } Defensive patterns
Strategy: validation
Validate before calling
func validSerfAddr(v string) bool {
if v == "" { return true }
return net.ParseIP(v) != nil || strings.HasPrefix(v, "{{")
}
// plus confirm any templated interface exists: iface, _ := net.InterfaceByName(name) Prevention
- Verify interface names referenced by templates exist on the host
- Use `consul validate` in CI for every config change
- Avoid quotes/whitespace artifacts around the value
When it happens
Trigger: addresses.serf set to a malformed IP, a template ({{ GetInterfaceIP ... }}) that fails or returns nothing parseable, or an address containing an illegal port/zone component.
Common situations: Typo in interface name inside the template (e.g. eth01); LAN interface absent at boot on VMs/containers so the template resolves empty; stray whitespace or quotes around the value in HCL/JSON.
Understand the failure class
- Parsing and encoding errors: unexpected token, malformed input — why parsers reject input and how to find the real culprit.
Related errors
- Bind address resolution failed: %v
- Failed to parse HTTP address: %v
- Failed to parse RPC address: %v
- Failed to parse Serf advertise address: %v
- No addresses found, please configure one.
AI-assisted analysis of hashicorp/nomad@482b49bf1a (2026-09-04).
Data as JSON: /api/errors/909d0818e5af649b.
Report an issue: GitHub.