我已经查看了有关如何通过Android上的HTTPS
从使用自签名证书的服务器检索某些内容的各种帖子。但是,它们似乎都不起作用 - 它们都无法删除
javax.net.ssl.SSLException:不受信任的服务器证书消息。
不能选择修改服务器以获得可信证书,也不能使服务器证书与服务器的IP地址匹配。
请注意,服务器没有DNS名称,只有IP地址。 GET请求看起来像这样:
https://username:password@anyIPAddress/blabla/index.php?param=1¶m2=3
我完全清楚这种解决方案容易发生中间人攻击等。
因此,解决方案必须忽略对证书缺乏信任,并忽略主机名不匹配。
有人知道使用Java for Android的代码吗?
有很多尝试在stackoverflow.com和大量代码片段上解释这一点,但它们似乎没有用,并且没有人提供一个解决这个问题的代码块,尽我所能看到。如果有人真的解决了这个问题,或者Android只是阻止了不受信任的证书,那将会很有趣。
答案 0 :(得分:36)
我制作了一个使用自签名或信任所有证书的应用。来源在这里:http://code.google.com/p/meneameandroid/source/browse/#svn/trunk/src/com/dcg/auth并可以免费使用:P
只需使用HttpManager并使用信任所有人创建SSL工厂:http://code.google.com/p/meneameandroid/source/browse/trunk/src/com/dcg/util/HttpManager.java
编辑:链接已更新
答案 1 :(得分:35)
正如您正确指出的那样,有两个问题:a)证书不受信任,b)证书上的名称与主机名不匹配。
警告:对于任何其他人来到这个答案,这是一个肮脏,可怕的黑客,你一定不能用它来做任何重要事情。没有身份验证的SSL / TLS比没有加密更糟糕 - 为攻击者读取和修改“加密”数据琐碎,而甚至不知道它正在发生
还在我身边吗?我担心......
a)通过创建TrustManager接受任何内容的自定义SSLContext来解决:
SSLContext ctx = SSLContext.getInstance("TLS");
ctx.init(null, new TrustManager[] {
new X509TrustManager() {
public void checkClientTrusted(X509Certificate[] chain, String authType) {}
public void checkServerTrusted(X509Certificate[] chain, String authType) {}
public X509Certificate[] getAcceptedIssuers() { return new X509Certificate[]{}; }
}
}, null);
HttpsURLConnection.setDefaultSSLSocketFactory(ctx.getSocketFactory());
和b)创建一个HostnameVerifier,即使证书与主机名不匹配,也允许连接继续:
HttpsURLConnection.setDefaultHostnameVerifier(new HostnameVerifier() {
public boolean verify(String hostname, SSLSession session) {
return true;
}
});
在您开始使用HttpsURLConnections等之前,两者都必须在代码的开头发生。这适用于Android和常规JRE。享受。
答案 2 :(得分:6)
如果您正在使用HttpsURLConnection,请尝试在setHostnameVerifier
之前调用connect()
,然后将HostnameVerifier
传递给您,而不管其真实性如何。
答案 3 :(得分:6)
答案 4 :(得分:2)
答案 5 :(得分:1)
如果你问我,请以安全的方式进行。
找到了一个很好的教程http://blog.antoine.li/index.php/2010/10/android-trusting-ssl-certificates/,实现起来并不困难。
Maciek推荐的教程也非常好。
我测试了它,它在我的应用程序中运行没有问题。
答案 6 :(得分:0)
我制作了一个使用自签名证书的应用程序4个月前,这是我希望它有用的代码:https://bitbucket.org/momo0002/tlsdemo.git