nsqio/nsq · error
--http-client-tls-cert must be specified with --http-client-
Error message
--http-client-tls-cert must be specified with --http-client-tls-key
What it means
Mirror image of the missing-key case: opts.HTTPClientTLSKey is set while opts.HTTPClientTLSCert is empty, so the X509 key pair for nsqadmin's outbound HTTP client cannot be loaded and New() refuses to start. A TLS private key alone is never sufficient for client-certificate authentication.
Source
Thrown at nsqadmin/nsqadmin.go:57
n := &NSQAdmin{
notifications: make(chan *AdminAction),
}
n.swapOpts(opts)
if len(opts.NSQDHTTPAddresses) == 0 && len(opts.NSQLookupdHTTPAddresses) == 0 {
return nil, errors.New("--nsqd-http-address or --lookupd-http-address required")
}
if len(opts.NSQDHTTPAddresses) != 0 && len(opts.NSQLookupdHTTPAddresses) != 0 {
return nil, errors.New("use --nsqd-http-address or --lookupd-http-address not both")
}
if opts.HTTPClientTLSCert != "" && opts.HTTPClientTLSKey == "" {
return nil, errors.New("--http-client-tls-key must be specified with --http-client-tls-cert")
}
if opts.HTTPClientTLSKey != "" && opts.HTTPClientTLSCert == "" {
return nil, errors.New("--http-client-tls-cert must be specified with --http-client-tls-key")
}
n.httpClientTLSConfig = &tls.Config{
InsecureSkipVerify: opts.HTTPClientTLSInsecureSkipVerify,
}
if opts.HTTPClientTLSCert != "" && opts.HTTPClientTLSKey != "" {
cert, err := tls.LoadX509KeyPair(opts.HTTPClientTLSCert, opts.HTTPClientTLSKey)
if err != nil {
return nil, fmt.Errorf("failed to LoadX509KeyPair %s, %s - %s",
opts.HTTPClientTLSCert, opts.HTTPClientTLSKey, err)
}
n.httpClientTLSConfig.Certificates = []tls.Certificate{cert}
}
if opts.HTTPClientTLSRootCAFile != "" {
tlsCertPool := x509.NewCertPool()
caCertFile, err := os.ReadFile(opts.HTTPClientTLSRootCAFile)
if err != nil {
return nil, fmt.Errorf("failed to read TLS root CA file %s - %s",View on GitHub (pinned to 85cf10c09c)
Solutions
- Add the certificate: --http-client-tls-cert=/etc/nsq/client.pem.
- Confirm the cert and key match: compare 'openssl x509 -noout -modulus' with 'openssl rsa -noout -modulus'.
- If mTLS is not actually required by the servers, remove both TLS client flags entirely.
Example fix
# before nsqadmin --nsqd-http-address=10.0.0.1:4151 --http-client-tls-key=/etc/nsq/client.key # after nsqadmin --nsqd-http-address=10.0.0.1:4151 --http-client-tls-cert=/etc/nsq/client.pem --http-client-tls-key=/etc/nsq/client.key
Defensive patterns
Strategy: validation
Validate before calling
func validateClientTLSPair(cert, key string) error {
if (cert == "") != (key == "") {
return errors.New("--http-client-tls-cert and --http-client-tls-key must be set together")
}
if cert != "" {
if _, err := tls.LoadX509KeyPair(cert, key); err != nil {
return fmt.Errorf("preflight keypair check failed: %w", err)
}
}
return nil
} Prevention
- Never ship one half of a TLS pair in config management; the pair is the unit of deployment.
- Run openssl moduli comparison in cert-rotation jobs to catch mismatched halves early.
When it happens
Trigger: Launching nsqadmin with --http-client-tls-key=/path/key.pem but no --http-client-tls-cert. The empty-string check fires before LoadX509KeyPair, so this is about a missing flag, not an unreadable or mismatched file.
Common situations: Secrets automation that injects only the key file; PEM bundles where the user assumed the certificate would be discovered automatically; renaming flags during upgrades leaving the cert flag behind.
Understand the failure class
- SSL/TLS and certificate errors — how TLS handshakes and certificate validation fail.
Related errors
- --http-client-tls-key must be specified with --http-client-t
- --nsqd-http-address or --lookupd-http-address required
- use --nsqd-http-address or --lookupd-http-address not both
- cannot require TLS client connections without TLS key and ce
- address should not contain scheme
AI-assisted analysis of nsqio/nsq@85cf10c09c (2026-08-16).
Data as JSON: /api/errors/ce60ebdfa0865563.
Report an issue: GitHub.