eclipse-vertx/vert.x · error · SSLException

Only TLSv1.3 supported

Error message

Only TLSv1.3 supported

What it means

QuicSslContextFactory.createContext() throws SSLException when the configured enabled protocols do not include TLSv1.3. QUIC in Vert.x is built on Netty's QUIC implementation which mandates TLS 1.3; QUIC connections cannot be established with older TLS versions, so any other protocol set is rejected at context creation time.

Source

Thrown at vertx-core/src/main/java/io/vertx/core/spi/tls/QuicSslContextFactory.java:106

  public SslContext create() throws SSLException {
    return createContext(forClient, kmf, tmf);
  }

  @Override
  public SslContextFactory enabledCipherSuites(Set<String> enabledCipherSuites) {
    this.enabledCipherSuites = enabledCipherSuites;
    return this;
  }

  @Override
  public SslContextFactory applicationProtocols(List<String> applicationProtocols) {
    this.applicationProtocols = applicationProtocols;
    return this;
  }

  private SslContext createContext(boolean client, KeyManagerFactory kmf, TrustManagerFactory tmf) throws SSLException {
    if (!enabledProtocols.contains("TLSv1.3")) {
      throw new SSLException("Only TLSv1.3 supported");
    }
    QuicSslContextBuilder builder;
    if (client) {
      builder = QuicSslContextBuilder.forClient();
      if (kmf != null) {
        builder.keyManager(kmf, null);
      }
      builder.endpointIdentificationAlgorithm(endpointIdentificationAlgorithm);
    } else {
      builder = QuicSslContextBuilder.forServer(kmf, null);
      if (clientAuth != null) {
        builder.clientAuth(clientAuth);
      }
    }
    builder.keylog(keylog);
/*
    Collection<String> cipherSuites = enabledCipherSuites;
    switch (sslProvider) {

View on GitHub (pinned to fb308bd8c3)

Solutions

  1. Ensure "TLSv1.3" is present in the enabled protocols set passed to the factory (e.g. Set.of("TLSv1.3") or add it to the existing set).
  2. If TLS 1.2 is a hard requirement, use a regular TCP TLS transport (e.g. HttpServerOptions/HttpClientOptions) instead of the QUIC transport.
  3. Remove custom protocol restrictions from the QUIC configuration and let the factory default to TLSv1.3.

Example fix

// before
factory.enabledProtocols(Set.of("TLSv1.2"));
factory.create(); // SSLException: Only TLSv1.3 supported
// after
factory.enabledProtocols(Set.of("TLSv1.3"));
factory.create();
Defensive patterns

Strategy: validation

Validate before calling

Set<String> protocols = factory /* enabledProtocols */;
if (!protocols.contains("TLSv1.3")) throw new IllegalArgumentException("QUIC requires TLSv1.3");

Type guard

boolean isQuicCompatible(Set<String> enabled) { return enabled != null && enabled.contains("TLSv1.3"); }

Try / catch

try { return factory.create(); } catch (SSLException e) { if (e.getMessage().contains("Only TLSv1.3")) { /* fix protocol config */ } throw e; }

Prevention

When it happens

Trigger: Configuring QuicSslContextFactory with a set of enabled protocols that omits "TLSv1.3" (e.g. only TLSv1.2, or an empty/custom set) and then calling create(), which invokes createContext().

Common situations: Porting HTTP/3 or QUIC client/server options from TLS settings written for TCP endpoints; explicitly restricting protocols to TLSv1.2 for compliance on a QUIC channel; copying shared TLS config between a normal HTTPS server and a QUIC/HTTP3 server.

Related errors


AI-assisted analysis of eclipse-vertx/vert.x@fb308bd8c3 (2026-09-06). Data as JSON: /api/errors/f217dab1e023d0c8. Report an issue: GitHub.