У меня есть веб-сайт, на котором я могу включить ssl для службы RESTful. Мы зарегистрировались в RapidSSL, установили сертификаты, и он передает проверку RapidSSL. Я могу получить доступ к сайту с различными браузерами, включая браузеры для Android (встроенные, firefox и opera) без проблем, никаких предупреждений.
Однако, когда я пытаюсь получить к нему доступ с помощью своего приложения для Android, я получаю следующее исключение:
08-11 20:04:05.586 363 381 E HttpProvider: Error executing request: No peer certificate
08-11 20:04:05.586 363 381 E HttpProvider: javax.net.ssl.SSLPeerUnverifiedException: No peer certificate
08-11 20:04:05.586 363 381 E HttpProvider: at org.apache.harmony.xnet.provider.jsse.SSLSessionImpl.getPeerCertificates(SSLSessionImpl.java:259)
08-11 20:04:05.586 363 381 E HttpProvider: at org.apache.http.conn.ssl.AbstractVerifier.verify(AbstractVerifier.java:93)
08-11 20:04:05.586 363 381 E HttpProvider: at org.apache.http.conn.ssl.SSLSocketFactory.createSocket(SSLSocketFactory.java:381)
08-11 20:04:05.586 363 381 E HttpProvider: at org.apache.http.impl.conn.DefaultClientConnectionOperator.openConnection(DefaultClientConnectionOperator.java:164)
08-11 20:04:05.586 363 381 E HttpProvider: at org.apache.http.impl.conn.AbstractPoolEntry.open(AbstractPoolEntry.java:164)
08-11 20:04:05.586 363 381 E HttpProvider: at org.apache.http.impl.conn.AbstractPooledConnAdapter.open(AbstractPooledConnAdapter.java:119)
08-11 20:04:05.586 363 381 E HttpProvider: at org.apache.http.impl.client.DefaultRequestDirector.execute(DefaultRequestDirector.java:359)
08-11 20:04:05.586 363 381 E HttpProvider: at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:555)
08-11 20:04:05.586 363 381 E HttpProvider: at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:487)
08-11 20:04:05.586 363 381 E HttpProvider: at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:465)
08-11 20:04:05.586 363 381 E HttpProvider: at com.xxxxx.netlib.http.HttpProvider.executeRequest(HttpProvider.java:75)
Это происходит на Android 2.3.3 на эмуляторе и на планшете 3.2. Я видел много хитов на этом, но ничего, что я нашел, помогает мне решить проблему.
Дополнительные данные:
$ openssl s_client -CAfile www.xxxxx.com.pem -connect www.xxxxx.com:443
CONNECTED(00000003)
depth=3 C = US, O = Equifax, OU = Equifax Secure Certificate Authority
verify return:1
depth=2 C = US, O = GeoTrust Inc., CN = GeoTrust Global CA
verify return:1
depth=1 C = US, O = "GeoTrust, Inc.", CN = RapidSSL CA
verify return:1
depth=0 serialNumber = 1-7wArtEjdTwJ94d5iVDooDmmC4mXyVj, OU = GT82425783, OU = See www.rapidssl.com/resources/cps (c)12, OU = Domain Control Validated - RapidSSL(R), CN = www.xxxxx.com
verify return:1
---
Certificate chain
0 s:/serialNumber=1-7wArtEjdTwJ94d5iVDooDmmC4mXyVj/OU=GT82425783/OU=See www.rapidssl.com/resources/cps (c)12/OU=Domain Control Validated - RapidSSL(R)/CN=www.xxxxx.com
i:/C=US/O=GeoTrust, Inc./CN=RapidSSL CA
1 s:/C=US/O=GeoTrust, Inc./CN=RapidSSL CA
i:/C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
2 s:/C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
i:/C=US/O=Equifax/OU=Equifax Secure Certificate Authority
---
[snip]
Код, который я запускаю для настройки клиента:
public class HttpProvider implements INetworkProvider {
private static final String LOG = "HttpProvider";
protected DefaultHttpClient client;
public HttpProvider() {
SchemeRegistry registry = new SchemeRegistry();
registry.register(new Scheme("http", PlainSocketFactory.getSocketFactory(), 80));
final SSLSocketFactory sslSocketFactory = SSLSocketFactory.getSocketFactory();
sslSocketFactory.setHostnameVerifier(SSLSocketFactory.BROWSER_COMPATIBLE_HOSTNAME_VERIFIER);
registry.register(new Scheme("https", sslSocketFactory, 443));
client = new DefaultHttpClient(
new ThreadSafeClientConnManager((new BasicHttpParams()), registry), new BasicHttpParams()
);
}
[snip]
Я также пробовал с STRICT_HOSTNAME_VERIFIER и до сих пор не радуюсь.
Из того, что я понимаю, мне не нужно настраивать какие-либо пользовательские магазины доверия или хранилища ключей, так как я зарегистрирован у признанного поставщика сертификатов.
Я очень новичок в ssl и считаю, что я плаваю в море трех буквенных сокращений, и я надеялся, что кто-то здесь сможет дать мне толчок в правильном направлении.