golang/go · error
tls: invalid NextProtos value
Error message
tls: invalid NextProtos value
What it means
Thrown by makeClientHello when any entry in config.NextProtos (the ALPN protocol ID list) has a length of 0 or exceeds 255 bytes. ALPN protocol IDs are encoded with a single-byte length prefix on the wire, so each must be between 1 and 255 bytes long. An empty string or an excessively long protocol name violates this constraint.
Source
Thrown at src/crypto/tls/handshake_client.go:53
serverHello *serverHelloMsg
hello *clientHelloMsg
suite *cipherSuite
finishedHash finishedHash
masterSecret []byte
session *SessionState // the session being resumed
ticket []byte // a fresh ticket received during this handshake
}
func (c *Conn) makeClientHello() (*clientHelloMsg, *keySharePrivateKeys, *echClientContext, error) {
config := c.config
if len(config.ServerName) == 0 && !config.InsecureSkipVerify {
return nil, nil, nil, errors.New("tls: either ServerName or InsecureSkipVerify must be specified in the tls.Config")
}
nextProtosLength := 0
for _, proto := range config.NextProtos {
if l := len(proto); l == 0 || l > 255 {
return nil, nil, nil, errors.New("tls: invalid NextProtos value")
} else {
nextProtosLength += 1 + l
}
}
if nextProtosLength > 0xffff {
return nil, nil, nil, errors.New("tls: NextProtos values too large")
}
supportedVersions := config.supportedVersions(roleClient, c.quic != nil)
if len(supportedVersions) == 0 {
return nil, nil, nil, errors.New("tls: no supported versions satisfy MinVersion and MaxVersion")
}
// Since supportedVersions is sorted in descending order, the first element
// is the maximum version and the last element is the minimum version.
maxVersion := supportedVersions[0]
minVersion := supportedVersions[len(supportedVersions)-1]
hello := &clientHelloMsg{View on GitHub (pinned to b6b368adc5)
Solutions
- Remove empty strings from config.NextProtos before use
- Ensure each ALPN protocol ID is between 1 and 255 bytes long
- Filter the NextProtos list programmatically: slices.DeleteFunc(nextProtos, func(s string) bool { return len(s) == 0 || len(s) > 255 })
- Validate ALPN entries from external input (config files, user input) before assigning to NextProtos
Example fix
// before
config := &tls.Config{
NextProtos: []string{"h2", "", "http/1.1"}, // empty string → error
}
// after
config := &tls.Config{
NextProtos: []string{"h2", "http/1.1"},
} Defensive patterns
Strategy: validation
Validate before calling
func validateNextProtos(protos []string) error {
for _, p := range protos {
if l := len(p); l == 0 || l > 255 {
return fmt.Errorf("invalid ALPN protocol length %d: must be 1-255 bytes", l)
}
}
return nil
}
// Usage:
// if err := validateNextProtos(config.NextProtos); err != nil {
// log.Fatal(err)
// } Try / catch
// Pre-validate before assigning to config:
//
// protos := slices.DeleteFunc(rawProtos, func(s string) bool {
// return len(s) == 0 || len(s) > 255
// })
// config.NextProtos = protos Prevention
- Filter empty strings from NextProtos before assignment
- Validate ALPN entries from config files or user input
- Use constants for well-known protocol IDs (e.g., "h2", "http/1.1") instead of dynamic strings
When it happens
Trigger: Setting config.NextProtos to a slice containing an empty string (e.g., []string{"h2", ""}) or a string longer than 255 bytes (e.g., []string{strings.Repeat("a", 300)}).
Common situations: Accidentally including an empty string from a comma-split or whitespace-trim operation. Programmatically generated protocol names that exceed 255 bytes. A configuration file with a trailing comma producing an empty entry. Accidental nil interface conversion producing an empty string.
Understand the failure class
- SSL/TLS and certificate errors — how TLS handshakes and certificate validation fail.
Related errors
- tls: NextProtos values too large
- tls: either ServerName or InsecureSkipVerify must be specifi
- tls: no supported versions satisfy MinVersion and MaxVersion
- tls: short read from Rand:
- tls: no supported key exchange methods (CurveIDs)
AI-assisted analysis of golang/go@b6b368adc5 (2026-08-12).
Data as JSON: /api/errors/fdf1eb955f84556d.
Report an issue: GitHub.