- Our target server (censored.local) has HTTPS certificate with CN = censored.com, *.censored.com
- The test raises an exception:
javax.net.ssl.SSLException: Certificate for
"censored.local" doesn't match any of the subject alternative
names: [censored.com, *.censored.com]
- I understand why this happens (RFC 2818) but I would like to bypass this for testing purposes. It is not possible to install a different certificate on the target server.
- .relaxedHTTPSValidation() and .allowAllHostnames() did not work. So, I tried to code my way into this:
My test class:
...
.given().spec(reqSpec)
...
My configuration class:
public abstract class Configurator {
protected static TestEnv envConf = chooseEnv();
protected static RequestSpecification reqSpec;
static { try { reqSpec = configureRestAssured(); } catch (Exception e) {e.printStackTrace(); } }
protected static TestEnv chooseEnv() {
// Some logic following to select an instance from TestEnv (not shown here)
...
envConf = TestEnv.BETA;
return envConf;
}
protected static RequestSpecification configureRestAssured() {
RequestSpecification reqSpec = new RequestSpecBuilder().build();
reqSpec
.header("Authorization", String.format("Bearer %s", envConf.getBearerToken()))
// This gets the censored.local URI:
.baseUri(envConf.getBaseURI())
.config(getRAconfig());
return reqSpec;
}
private static RestAssuredConfig getRAconfig() {
SSLSocketFactory sslSocket = getSSLsocket (envConf.getKeystoreFile(), "keystorePassword", "PrivateKeyPassword");
RestAssuredConfig raConfig = RestAssuredConfig.config()
.sslConfig(SSLConfig.sslConfig().sslSocketFactory(sslSocket));
return raConfig;
}
private static SSLSocketFactory getSSLsocket(String ksPath, String ksPassword, String pkPassword) {
KeyStore keystore = KeyStore.getInstance("JKS");
keystore.load(new FileInputStream(ksPath), ksPassword.toCharArray());
SSLContext context = SSLContexts.custom()
.loadKeyMaterial(keystore, pkPassword.toCharArray(), firstPrivateKeyStrategy())
.loadTrustMaterial(trustEveryoneStrategy())
.build();
return new SSLSocketFactory(context);
}
private static PrivateKeyStrategy firstPrivateKeyStrategy() {
return new PrivateKeyStrategy() {
@Override
public String chooseAlias(Map<String, PrivateKeyDetails> aliases, Socket socket) {
return aliases.keySet().iterator().next();
}
};
}
private static TrustStrategy trustEveryoneStrategy() {
return new TrustStrategy() {
@Override
public boolean isTrusted(X509Certificate[] chain, String authType)
throws CertificateException {
return true;
}
};
}}
- I don't know if it helps, but during debugging, I can see:
raConfig = {RestAssuredConfig@2752}
configs = {HashMap@2753} size = 17
...
{Class@2003} "class io.restassured.config.SSLConfig" -> {SSLConfig@3257}
key = {Class@2003} "class io.restassured.config.SSLConfig"
value = {SSLConfig@3257}
pathToKeyStore = null
pathToTrustStore = null
keyStorePassword = null
trustStorePassword = null
keyStoreType = "pkcs12"
trustStoreType = "pkcs12"
port = -1
trustStore = null
keyStore = null
x509HostnameVerifier = {StrictHostnameVerifier@3286} "STRICT"
Is STRICT basically showing my problem? If so, how to hack a not-STRICT x509HostnameVerifier?
- Also, I am aware of the following, but no idea how to use this for my Rest Assured connections: https://tutoref.com/how-to-disable-ssl-certificat-validation-in-java/