2011-05-10 25 views
6

Bir sunucuya POST istekleri göndermek için HTTPS kullanmalıyım (kendinden imzalı bir sertifika kullanarak). Bu benim böyle yaparız: olarak tanımlananHTTPS ve kendinden imzalı sertifika sorunu

getHttpClient ile
HttpClient httpClient = getHttpClient(); 

for (int i = 0; i < PARAMS.length && !mHttpPost.isAborted(); ++i) { 
    mHttpPost.setURI(URI.create(mUri + "/" + PARAMS[i].getPath())); 
    mHttpPost.setEntity(new UrlEncodedFormEntity(PARAMS[i].getContents(), HTTP.UTF_8)); 
    HttpResponse response = httpClient.execute(mHttpPost); 
    [...] 
} 

() aşağıdaki gibidir:

public static DefaultHttpClient getHttpClient() { 

    DefaultHttpClient client = null; 

    // Setting up parameters 
    HttpParams params = new BasicHttpParams(); 
    HttpProtocolParams.setVersion(params, HttpVersion.HTTP_1_1); 
    HttpProtocolParams.setContentCharset(params, "utf-8"); 
    params.setBooleanParameter("http.protocol.expect-continue", false); 

    // Setting timeout 
    HttpConnectionParams.setConnectionTimeout(params, TIMEOUT); 
    HttpConnectionParams.setSoTimeout(params, TIMEOUT); 

    // Registering schemes for both HTTP and HTTPS 
    SchemeRegistry registry = new SchemeRegistry(); 
    registry.register(new Scheme("http", PlainSocketFactory.getSocketFactory(), 80)); 
    final SSLSocketFactory sslSocketFactory = SSLSocketFactory.getSocketFactory(); 
    sslSocketFactory.setHostnameVerifier(SSLSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER); 
    registry.register(new Scheme("https", sslSocketFactory, 443)); 

    // Creating thread safe client connection manager 
    ThreadSafeClientConnManager manager = new ThreadSafeClientConnManager(params, registry); 

    // Creating HTTP client 
    client = new DefaultHttpClient(manager, params); 

    return client; 

} 

Ama "Değil güvenilen sunucu sertifikası" istisna olsun. Kendinden imzalı sertifikalarla ilgili birkaç soru daha önce burada yayınlanmıştır, ancak hiçbiri benim için çalışmadı ...

Herkes nasıl yapılacağını biliyor mu?

Bazı ayrıntılar: Emülatörde API düzey 4 (Android 1.6) ile çalışıyorum.

cevap

13

nihayet çözüldü gerçekleştirmeden önce bu deneyin:

public class CustomSSLSocketFactory extends SSLSocketFactory { 

    private SSLContext sslContext = SSLContext.getInstance("TLS"); 

    public CustomSSLSocketFactory(KeyStore truststore) throws NoSuchAlgorithmException, KeyManagementException, KeyStoreException, UnrecoverableKeyException { 

     super(truststore); 

     TrustManager tm = new X509TrustManager() { 

      public void checkClientTrusted(X509Certificate[] chain, String authType) throws certificateException { 
     } 

      public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException { 
      } 

      public X509Certificate[] getAcceptedIssuers() { 
       return null; 
      } 

     }; 

     sslContext.init(null, new TrustManager[] {tm}, null); 

    } 

    @Override 
    public Socket createSocket(Socket socket, String host, int port, boolean autoClose) throws IOException, UnknownHostException { 
     return sslContext.getSocketFactory().createSocket(socket, host, port, autoClose); 
    } 

    @Override 
    public Socket createSocket() throws IOException { 
     return sslContext.getSocketFactory().createSocket(); 
    } 

} 

Ve şöyle bunu kullanın:

public HttpClient getHttpClient() { 

    DefaultHttpClient client = null; 

    try { 

     KeyStore trustStore = KeyStore.getInstance(KeyStore.getDefaultType()); 
     trustStore.load(null, null); 

     SSLSocketFactory sf = new CustomSSLSocketFactory(trustStore); 
     sf.setHostnameVerifier(SSLSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER); 

     // Setting up parameters 
     HttpParams params = new BasicHttpParams(); 
     HttpProtocolParams.setVersion(params, HttpVersion.HTTP_1_1); 
     HttpProtocolParams.setContentCharset(params, "utf-8"); 
     params.setBooleanParameter("http.protocol.expect-continue", false); 

     // Setting timeout 
     HttpConnectionParams.setConnectionTimeout(params, TIMEOUT); 
     HttpConnectionParams.setSoTimeout(params, TIMEOUT); 

     // Registering schemes for both HTTP and HTTPS 
     SchemeRegistry registry = new SchemeRegistry(); 
     registry.register(new Scheme("http", PlainSocketFactory.getSocketFactory(), 80)); 
     registry.register(new Scheme("https", sf, 443)); 

     // Creating thread safe client connection manager 
     ClientConnectionManager ccm = new ThreadSafeClientConnManager(params, registry); 

     // Creating HTTP client 
     client = new DefaultHttpClient(ccm, params); 

     // Registering user name and password for authentication 
     client.getCredentialsProvider().setCredentials(
       new AuthScope(null, -1), 
       new UsernamePasswordCredentials(mUsername, mPassword)); 

    } catch (Exception e) { 
     client = new DefaultHttpClient(); 
    } 

    return client; 

} 

Bulduğum diğer çözümler neden benim için işe yaramadı bilmiyorum ...

+2

Merhaba, bu bir süre önce yazılan biliyorum çalışır. Ama şu anda bu HTTPS bağlantısına takıldım. Güvenli bir HTTPS sitesinde geçmeden önce yapmam gereken adımlar nelerdir? –

+1

Bu çözüm gerçekten tehlikelidir; HTTPS kullanmanın güvenlik avantajlarını atıyorsunuz (kodunuz körü körüne kötü sertifikalara güvenecek). – Brian

0

SSLSocketFactory özel bir alt sınıfını kullanarak, isteği

SSLSocketFactory ssl = (SSLSocketFactory)http.getConnectionManager().getSchemeRegistry().getScheme("https").getSocketFactory(); 
    ssl.setHostnameVerifier(SSLSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER); 
+0

dilerim, eşlenmeye benzer bir şekilde bu yapıyoruz, ama benim için ... – 2red13

6

kendini belgelemek ve diğerlerinin yanıtları kabul etmesine yardımcı olmak için yardımcı olmak için yanıtları kabul etti (ki bu benim için çalışır ancak java arasında ithalatı test etmek için zaman harcar. , javax. ve org.apache.http *):.

import java.io.IOException; 
import java.net.Socket; 
import java.net.UnknownHostException; 
import java.security.KeyManagementException; 
import java.security.KeyStore; 
import java.security.KeyStoreException; 
import java.security.NoSuchAlgorithmException; 
import java.security.UnrecoverableKeyException; 
import java.security.cert.CertificateException; 
import java.security.cert.X509Certificate; 

import javax.net.ssl.SSLContext; 
import javax.net.ssl.TrustManager; 
import javax.net.ssl.X509TrustManager; 

import org.apache.http.HttpVersion; 
import org.apache.http.client.HttpClient; 
import org.apache.http.conn.ClientConnectionManager; 
import org.apache.http.conn.scheme.PlainSocketFactory; 
import org.apache.http.conn.scheme.Scheme; 
import org.apache.http.conn.scheme.SchemeRegistry; 
import org.apache.http.conn.ssl.SSLSocketFactory; 
import org.apache.http.impl.client.DefaultHttpClient; 
import org.apache.http.impl.conn.tsccm.ThreadSafeClientConnManager; 
import org.apache.http.params.BasicHttpParams; 
import org.apache.http.params.HttpConnectionParams; 
import org.apache.http.params.HttpParams; 
import org.apache.http.params.HttpProtocolParams; 
İlgili konular