redis/jedis · critical · JedisConnectionException

The connection to ' ' failed ssl/tls hostname verification.

Error message

The connection to '${_hostAndPort.getHost()}' failed ssl/tls hostname verification.

What it means

After Jedis wraps the plain socket in an SSL socket, it runs the configured HostnameVerifier against the server certificate's session. If the certificate does not match the host in the HostAndPort used for the connection, it throws JedisConnectionException with 'The connection to <host> failed ssl/tls hostname verification.' This prevents man-in-the-middle attacks where a valid certificate is presented for a different name.

Solutions

  1. Use the exact hostname the server certificate was issued for in the client's HostAndPort configuration.
  2. Fix the server certificate: reissue it with SANs covering the hostnames/IPs clients actually connect to.
  3. Provide a custom SslOptions/HostnameVerifier only if you can verify identity another way (e.g. certificate pinning) — never disable verification in production.
  4. Check for hostname mismatch caused by DNS aliases or load balancers and align cert SANs with those names.
  5. Test with 'openssl s_client -connect host:port -servername host' to inspect the served certificate.

Example fix

// before
Jedis jedis = new Jedis(HostAndPort.from("10.0.0.5:6380"),
    DefaultJedisClientConfig.builder().ssl(true).build()); // cert is for redis.example.com

// after
Jedis jedis = new Jedis(HostAndPort.from("redis.example.com:6380"),
    DefaultJedisClientConfig.builder().ssl(true).build()); // hostname matches cert
Defensive patterns

Strategy: validation

Validate before calling

// verify the server cert covers the host before connecting
import javax.net.ssl.*;
SSLContext ctx = SSLContext.getDefault();
SSLSocketFactory f = ctx.getSocketFactory();
try (SSLSocket s = (SSLSocket) f.createSocket(host, port)) {
  s.startHandshake();
  if (!HttpsURLConnection.getDefaultHostnameVerifier().verify(host, s.getSession())) {
    throw new IllegalStateException("Cert does not match host " + host);
  }
}

Try / catch

try {
  jedis = new Jedis(hostAndPort, sslConfig);
} catch (JedisConnectionException e) {
  if (e.getMessage() != null && e.getMessage().contains("hostname verification")) {
    // align HostAndPort hostname with the certificate SANs, or reissue the cert
  }
  throw e;
}

Prevention

When it happens

Trigger: Connecting with ssl=true (or SslOptions) to a server whose TLS certificate CN/SAN does not match the hostname used in the client configuration — e.g. connecting via an IP address, 'localhost', a load balancer/CNAME, or a hostname spelled differently from the certificate; or supplying a restrictive custom HostnameVerifier.

Common situations: Pointing the client at a proxy/load balancer whose cert covers a different name; using IP addresses or service internal names (e.g. k8s pod names) not in the cert SANs; self-signed or internally-issued certs; renaming hosts after cert issuance; migrating from plaintext to TLS without updating certs.

Understand the failure class

Related errors


AI-assisted analysis of redis/jedis@6dac31d4c2 (2026-09-08). Data as JSON: /api/errors/9f6ebe84db70c9db. Report an issue: GitHub.

Appendix: source

Thrown at src/main/java/redis/clients/jedis/DefaultJedisSocketFactory.java:181

    }

    SSLSocket sslSocket = (SSLSocket) _sslSocketFactory.createSocket(socket,
        _hostAndPort.getHost(), _hostAndPort.getPort(), true);

    // Enable hostname verification by default (HTTPS algorithm).
    // Users can override by providing custom SSLParameters via JedisClientConfig.
    if (_sslParameters == null) {
      _sslParameters = new SSLParameters();
      _sslParameters.setEndpointIdentificationAlgorithm("HTTPS");
    }

    sslSocket.setSSLParameters(_sslParameters);

    // allowing HostnameVerifier for both SslOptions and legacy ssl config
    if (hostnameVerifier != null && !hostnameVerifier.verify(_hostAndPort.getHost(), sslSocket.getSession())) {
      String message = String.format("The connection to '%s' failed ssl/tls hostname verification.",
          _hostAndPort.getHost());
      throw new JedisConnectionException(message);
    }

    return new SSLSocketWrapper(sslSocket, plainSocket);
  }

  public void updateHostAndPort(HostAndPort hostAndPort) {
    this.hostAndPort = hostAndPort;
  }

  public HostAndPort getHostAndPort() {
    return this.hostAndPort;
  }

  protected HostAndPort getSocketHostAndPort() {
    HostAndPortMapper mapper = hostAndPortMapper;
    HostAndPort hap = this.hostAndPort;
    if (mapper != null) {
      HostAndPort mapped = mapper.getHostAndPort(hap);

View on GitHub (pinned to 6dac31d4c2)