slackhq/nebula · error
%swas not a number; `%s`
Error message
%swas not a number; `%s`
What it means
parsePortValue returns this error when strconv.ParseUint fails with any error other than ErrRange, i.e. the string is not a syntactically valid base-10 number (or is empty). It means the port field in the firewall config does not parse as an integer.
Source
Thrown at firewall.go:1117
// parsePortValue accepts a base-10 decimal in [0, 65535] and returns it
// widened to int32. Using strconv.ParseUint with bitSize 16 rejects
// negative input, out-of-range input (>65535), and any non-decimal byte
// by construction, so the int32 widening that follows is provably safe
// and cannot collide with firewall.PortAny (0) or firewall.PortFragment
// (-1) via integer truncation.
//
// prefix is prepended to both error messages so callers can disambiguate
// the single-port path (prefix="") from the range bounds (prefix="beginning
// range " / "ending range "), preserving the historical error strings.
func parsePortValue(prefix, s string) (int32, error) {
n, err := strconv.ParseUint(s, 10, 16)
if err == nil {
return int32(n), nil
}
if errors.Is(err, strconv.ErrRange) {
return 0, fmt.Errorf("%sout of range [0,65535]; `%s`", prefix, s)
}
return 0, fmt.Errorf("%swas not a number; `%s`", prefix, s)
}
View on GitHub (pinned to dd8f660c0a)
Solutions
- Replace the value in the config with a numeric port or a numeric range like '22-23'
- Omit the port key entirely to match any port instead of writing 'any'
- Validate the config with `nebula -test -config ...` before restarting
Example fix
// before
firewall:
inbound:
- port: any
proto: tcp
// after
firewall:
inbound:
- proto: tcp Defensive patterns
Strategy: validation
Validate before calling
func isNumericPort(v interface{}) bool {
s, ok := v.(string)
if !ok {
return false
}
_, err := strconv.Atoi(strings.TrimSpace(s))
return err == nil
} Prevention
- Never write 'any', service names, or comma lists in port fields — omit the key or use a range
- Validate configs with `nebula -test -config` as a pre-start step
- Quote string values in YAML carefully to avoid accidental non-string coercion
- Add schema validation for firewall rule fields in config management tooling
When it happens
Trigger: A firewall rule port value in the Nebula config is a non-numeric string such as 'any', '443,8080', 'https', or contains stray characters/whitespace, when the config is parsed at startup via parsePort/addFireWallRulesFromConfig.
Common situations: Writing 'port: any' instead of omitting the field, comma-separated lists instead of a range, YAML type quirks making the value a map/list, service-name style ports ('ssh').
Related errors
- group should contain a single value, an array with more than
- no firewall rules
- config `%s` has invalid value (type %T): %v
- config `%s` contains both true and false rules, but no defau
- config `%s` contains both true and false rules, but no defau
AI-assisted analysis of slackhq/nebula@dd8f660c0a (2026-09-03).
Data as JSON: /api/errors/d6c292588c43b8be.
Report an issue: GitHub.