我正在尝试使用此代码发出https请求:
RequestQueue queue = Volley.newRequestQueue(getApplicationContext());
request = new Request<String>(Request.Method.GET,"https://devblahblahblah.com/service/etc",errListener);
但是我收到了这个错误:
com.android.volley.NoConnectionError: javax.net.ssl.SSLHandshakeException: java.security.cert.CertPathValidatorException:信任锚 未找到证书路径。
需要注意两点:
我实际上需要知道Android Volley框架中是否有任何交换机/选项,我将成功点击HTTPS网址?
答案 0 :(得分:52)
以下这些代码可能会对您有所帮助:
1.创建一个实现HttpsTrustManager
的{{1}}类:
X509TrustManager
2.在发出https请求之前添加public class HttpsTrustManager implements X509TrustManager {
private static TrustManager[] trustManagers;
private static final X509Certificate[] _AcceptedIssuers = new X509Certificate[]{};
@Override
public void checkClientTrusted(
java.security.cert.X509Certificate[] x509Certificates, String s)
throws java.security.cert.CertificateException {
}
@Override
public void checkServerTrusted(
java.security.cert.X509Certificate[] x509Certificates, String s)
throws java.security.cert.CertificateException {
}
public boolean isClientTrusted(X509Certificate[] chain) {
return true;
}
public boolean isServerTrusted(X509Certificate[] chain) {
return true;
}
@Override
public X509Certificate[] getAcceptedIssuers() {
return _AcceptedIssuers;
}
public static void allowAllSSL() {
HttpsURLConnection.setDefaultHostnameVerifier(new HostnameVerifier() {
@Override
public boolean verify(String arg0, SSLSession arg1) {
return true;
}
});
SSLContext context = null;
if (trustManagers == null) {
trustManagers = new TrustManager[]{new HttpsTrustManager()};
}
try {
context = SSLContext.getInstance("TLS");
context.init(null, trustManagers, new SecureRandom());
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (KeyManagementException e) {
e.printStackTrace();
}
HttpsURLConnection.setDefaultSSLSocketFactory(context
.getSocketFactory());
}
}
:
HttpsTrustManager.allowAllSSL()
答案 1 :(得分:15)
这个链接可能会对您有所帮助:Using Android Volley With Self-Signed SSL Certificate
答案 2 :(得分:10)
答案 3 :(得分:3)
到目前为止,唯一的答案是关于添加不受信任的证书作为解决方案,但由于您的浏览器没有抱怨,通常意味着Volley无法找到完成完整信任链的中间证书。 / p>
LetsEncrypt证书发生在我身上。大多数浏览器已经拥有中间证书,所以在浏览器上看起来一切都很好,但是Volley显然缺少一些东西。
解决方案
将中间证书添加到您的Web服务器配置中。对于Apache,您可以遵循以下参考:
https://access.redhat.com/solutions/43575
对于LetsEncrypt,具体是这个文件:/etc/letsencrypt/live/your.website.com/chain.pem
所以除了你的CertificateFile和KeyFile,你应该已经有了工作,你现在有了第三行:
SSLCertificateChainFile /etc/letsencrypt/live/your.website.com/chain.pem
只需添加该行,重新启动apache并且Volley不再抱怨,并且您没有引入任何安全漏洞!
答案 4 :(得分:3)
如果您正在使用排球并想要HTTPS请求或SSL认证服务,那么您可以选择以下最简单的方式: - &gt;
步骤 - &gt; 1.将.cer文件保存到res / raw /文件夹中。
步骤 - &gt; 2.使用此方法并将.cer文件名替换为.cer文件,并替换您的主机名。
private SSLSocketFactory getSocketFactory() {
CertificateFactory cf = null;
try {
cf = CertificateFactory.getInstance("X.509");
InputStream caInput = getResources().openRawResource(R.raw.cert_name);
Certificate ca;
try {
ca = cf.generateCertificate(caInput);
Log.e("CERT", "ca=" + ((X509Certificate) ca).getSubjectDN());
} finally {
caInput.close();
}
String keyStoreType = KeyStore.getDefaultType();
KeyStore keyStore = KeyStore.getInstance(keyStoreType);
keyStore.load(null, null);
keyStore.setCertificateEntry("ca", ca);
String tmfAlgorithm = TrustManagerFactory.getDefaultAlgorithm();
TrustManagerFactory tmf = TrustManagerFactory.getInstance(tmfAlgorithm);
tmf.init(keyStore);
HostnameVerifier hostnameVerifier = new HostnameVerifier() {
@Override
public boolean verify(String hostname, SSLSession session) {
Log.e("CipherUsed", session.getCipherSuite());
return hostname.compareTo("10.199.89.68")==0; //The Hostname of your server.
}
};
HttpsURLConnection.setDefaultHostnameVerifier(hostnameVerifier);
SSLContext context = null;
context = SSLContext.getInstance("TLS");
context.init(null, tmf.getTrustManagers(), null);
HttpsURLConnection.setDefaultSSLSocketFactory(context.getSocketFactory());
SSLSocketFactory sf = context.getSocketFactory();
return sf;
} catch (CertificateException e) {
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (KeyStoreException e) {
e.printStackTrace();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (KeyManagementException e) {
e.printStackTrace();
}
return null;
}
步骤 - &gt; 3.将此行替换为“RequestQueue queue = Volley.newRequestQueue(this);” “RequestQueue queue = Volley.newRequestQueue(this,new HurlStack(null,getSocketFactory()));”在排球的请求。
答案 5 :(得分:1)
我无法打开@ Ogre_BGR提供的链接,但在浏览网页时,我发现实际的实现是在smanikandan14 Github之后完成的。请查看他的SSl-connection explanation以了解更多信息。
答案 6 :(得分:0)
出现这种情况有几个原因,包括:
解决方案: 您可以在请求中提供证书文件
答案 7 :(得分:0)
对于遇到此类问题并且您对SSL使用 Letsencrypt 和对Web服务器使用 node.js 的任何人,请尝试此操作。假设您有这样的事情。我通过添加 const chain = fs ... 这一行来解决此问题,希望对您有所帮助
...
const app = express();
const privateKey = fs.readFileSync('ssl/privkey.pem', 'utf8');
const certificate = fs.readFileSync('ssl/cert.pem', 'utf8');
const chain = fs.readFileSync('ssl/chain.pem', 'utf8');
const credentials = {key: privateKey, cert: certificate, ca: chain};
...
var httpsServer = https.createServer(credentials, app);
答案 8 :(得分:0)
答案 9 :(得分:0)
当我从cloudflare关闭代理时,收到此错误 check image here 解决此问题的最佳方法是您可以重新打开代理,还可以对ssl证书添加完全安全的访问权限。
答案 10 :(得分:0)
如果有人使用nginx和来自letsencrypt的SSL证书,解决方案是简单地使用文件fullchain.pem
中的证书而不是cert.pem
:
ssl_certificate /.../fullchain.pem;
此文件包括您的证书和CA的串联。