Ответ 1
Вы можете получить доступ к существующему менеджеру доверия по умолчанию и перенести его самостоятельно, используя что-то вроде этого:
TrustManagerFactory tmf = TrustManagerFactory
.getInstance(TrustManagerFactory.getDefaultAlgorithm());
// Using null here initialises the TMF with the default trust store.
tmf.init((KeyStore) null);
// Get hold of the default trust manager
X509TrustManager x509Tm = null;
for (TrustManager tm : tmf.getTrustManagers()) {
if (tm instanceof X509TrustManager) {
x509Tm = (X509TrustManager) tm;
break;
}
}
// Wrap it in your own class.
final X509TrustManager finalTm = x509Tm;
X509TrustManager customTm = new X509TrustManager() {
@Override
public X509Certificate[] getAcceptedIssuers() {
return finalTm.getAcceptedIssuers();
}
@Override
public void checkServerTrusted(X509Certificate[] chain,
String authType) throws CertificateException {
finalTm.checkServerTrusted(chain, authType);
}
@Override
public void checkClientTrusted(X509Certificate[] chain,
String authType) throws CertificateException {
finalTm.checkClientTrusted(chain, authType);
}
};
SSLContext sslContext = SSLContext.getInstance("TLS");
sslContext.init(null, new TrustManager[] { customTm }, null);
// You don't have to set this as the default context,
// it depends on the library you're using.
SSLContext.setDefault(sslContext);
Затем вы можете реализовать свою собственную логику вокруг finalTm.checkServerTrusted(chain, authType);
.
Однако вы должны убедиться, что вы делаете исключение для конкретного сертификата, который вы хотите игнорировать.
То, что вы делаете в следующем, - это пропускать любой сертификат с этими DN и Subject DN эмитента (который не сложно подделать):
if(chain[0].getIssuerDN().getName().equals("MyTrustedServer") && chain[0].getSubjectDN().getName().equals("MyTrustedServer"))
return true;
Вместо этого вы можете загрузить экземпляр X509Certificate
из известной ссылки и сравнить фактическое значение в цепочке.
Кроме того, checkClientTrusted
и checkServerTrusted
не являются методами, возвращающими методы true
или false
, но void
, которые по умолчанию будут выполняться молча. Если в ожидаемом сертификате что-то не так, бросьте CertificateException
явно.