quarkusio/quarkus · error · RuntimeException

Could not find a public, no-argument constructor for the hos

Error message

Could not find a public, no-argument constructor for the hostname verifier class " + verifier

What it means

When TLS is configured via properties, registerHostnameVerifier loads the configured hostname verifier class by name and instantiates it with its public no-arg constructor. If the class has no such constructor, a NoSuchMethodException is wrapped in this RuntimeException. Only the constructor lookup fails here — class loading and casting failures get their own messages.

Source

Thrown at extensions/resteasy-reactive/rest-client/runtime/src/main/java/io/quarkus/rest/client/reactive/runtime/RestClientCDIDelegateBuilder.java:291

        Optional<String> maybeKeyStore = oneOf(restClientConfig.keyStore(), configRoot.keyStore());
        if (maybeKeyStore.isPresent() && !maybeKeyStore.get().isBlank() && !NONE.equals(maybeKeyStore.get())) {
            registerKeyStore(maybeKeyStore.get(), builder);
        }

        Optional<String> maybeHostnameVerifier = oneOf(restClientConfig.hostnameVerifier(), configRoot.hostnameVerifier());
        if (maybeHostnameVerifier.isPresent()) {
            registerHostnameVerifier(maybeHostnameVerifier.get(), builder);
        }

        oneOf(restClientConfig.verifyHost(), configRoot.verifyHost()).ifPresent(builder::verifyHost);
    }

    private void registerHostnameVerifier(String verifier, QuarkusRestClientBuilder builder) {
        try {
            Class<?> verifierClass = Thread.currentThread().getContextClassLoader().loadClass(verifier);
            builder.hostnameVerifier((HostnameVerifier) verifierClass.getDeclaredConstructor().newInstance());
        } catch (NoSuchMethodException e) {
            throw new RuntimeException(
                    "Could not find a public, no-argument constructor for the hostname verifier class " + verifier, e);
        } catch (ClassNotFoundException e) {
            throw new RuntimeException("Could not find hostname verifier class " + verifier, e);
        } catch (InstantiationException | IllegalAccessException | InvocationTargetException e) {
            throw new RuntimeException(
                    "Failed to instantiate hostname verifier class " + verifier
                            + ". Make sure it has a public, no-argument constructor",
                    e);
        } catch (ClassCastException e) {
            throw new RuntimeException("The provided hostname verifier " + verifier + " is not an instance of HostnameVerifier",
                    e);
        }
    }

    private void registerKeyStore(String keyStorePath, QuarkusRestClientBuilder builder) {
        Optional<String> keyStorePassword = oneOf(restClientConfig.keyStorePassword(), configRoot.keyStorePassword());
        Optional<String> keyStoreType = oneOf(restClientConfig.keyStoreType(), configRoot.keyStoreType());

View on GitHub (pinned to e1c734241f)

Solutions

  1. Give the HostnameVerifier implementation a public no-argument constructor (make it a public top-level or static nested class).
  2. Verify the property value is the fully-qualified class name of the right class.
  3. If construction needs parameters, instantiate it programmatically via the builder instead of through the property.

Example fix

// before
public class MyVerifier implements HostnameVerifier {
    private MyVerifier() { } // no public ctor
}

// after
public class MyVerifier implements HostnameVerifier {
    public MyVerifier() { }
    public boolean verify(String hostname, SSLSession session) { ... }
}
Defensive patterns

Strategy: validation

Validate before calling

Class<?> c = Class.forName("com.example.MyVerifier", true, Thread.currentThread().getContextClassLoader());
if (c.getDeclaredConstructor() == null || !java.lang.reflect.Modifier.isPublic(c.getDeclaredConstructor().getModifiers())) {
    throw new IllegalStateException("Hostname verifier needs a public no-arg constructor");
}

Type guard

boolean hasPublicNoArgCtor(Class<?> c) {
    try { return java.lang.reflect.Modifier.isPublic(c.getDeclaredConstructor().getModifiers()); }
    catch (NoSuchMethodException e) { return false; }
}

Try / catch

try {
    // build client with the configured hostname verifier
} catch (RuntimeException e) {
    if (e.getMessage() != null && e.getMessage().contains("no-argument constructor")) {
        builder.hostnameVerifier((h, s) -> true); // fallback verifier
    } else throw e;
}

Prevention

When it happens

Trigger: Setting quarkus.rest-client.<key>.hostname-verifier (or TLS configuration trust/hostname-verifier property) to a class whose constructor is private, takes arguments, or is inherited/non-public.

Common situations: Pointing the property at a verifier requiring constructor parameters; a nested/inner class implicitly non-static or with an implicit non-public constructor; copy-pasting a verifier from another framework that used DI.

Related errors


AI-assisted analysis of quarkusio/quarkus@e1c734241f (2026-09-05). Data as JSON: /api/errors/2929a5c838dff1bb. Report an issue: GitHub.