2011-03-28 4 views
7

J'écris actuellement une partie client pour Android (2.2) et un serveur en utilisant SSL. J'ai réussi à échanger des messages entre le serveur et un client normal, mais Android ne semble pas très heureux des certificats autosignés. J'ai cherché Stackoverflow et googled BEAUCOUP et beaucoup de gens ont des problèmes similaires. Toutes les réponses que j'ai trouvées jusqu'ici ne fonctionnaient pas ou n'avaient aucun sens. La plupart des exemples de code sont HTTPS, mais je ne peux pas les utiliser, car j'ai besoin de communiquer via une socket (SSLSocket est ma meilleure estimation). J'ai essayé beaucoup de code différent, mais maintenant je suis de retour à zéro.client SSL sur Android

Jusqu'à présent, j'ai compris que je dois créer un certificat (pense que je suis arrivé ce droit) et un TrustManager personnalisé. Évidemment, je n'ai pas réussi à trouver de code de travail, c'est pourquoi je demande ici, car il y a généralement des gens vraiment utiles.

Je cherche une description détaillée de ce qui est censé être fait, et un code qui peut être transformé en un code client Android de travail.

Merci à l'avance

Répondre

1

Je l'ai fait avec le portage navigateur natif Android. Je viens de changer la façon dont le contexte ssl est créé. je lui ai promis que je mets aussi quelques exemples de travail sur place SandroB mais ... :)

https://market.android.com/details?id=org.sandrob

http://code.google.com/p/sandrob/source/browse/misc/examples/HttpsConnection.java

+0

Merci pour votre réponse. J'ai regardé le code auquel vous étiez lié, et cela semble intéressant. Le problème est qu'il utilise beaucoup de classes, ce qui semble être fait sur mesure. J'ai cherché certains d'entre eux sur Google et j'ai constaté qu'ils avaient été implémentés dans d'autres bibliothèques. Permet de prendre le CertificateChainValidator semble être supposé être dans le paquet android.net.http - mais ce n'est pas là. Existe-t-il un exemple de travail simplifié, utilisant des bibliothèques standard? – Casper

1

CertificateChainValidator fait partie des sources Android. au moins dans la version/tag 2.2.1_r1

Pour le faire fonctionner, vous pouvez construire à partir de sources navigateur Android et changer à quel point SSLContext est initialisé dans le fichier HttpsConnection.java.

Vous devez keyManagers (initialisés avec cerfile/mot de passe) et trustManagers (confiance tout).

sslContext.engineInit (keyManagers, trustManagers, null, cache, null);

+1

Bonjour. Je ne peux pas sembler l'importer, et selon http://developer.android.com/reference/android/net/http/package-summary.html la fonction ne semble pas exister. Pour autant que je sais que je vais devoir créer des gestionnaires de douane pour gérer les certificats, mais je suis encore à trouver un code de travail. J'utilise Android 2.2 (API 8) en passant. – Casper

1
public class MySSLSocketFactory extends SSLSocketFactory { 
    SSLContext sslContext = SSLContext.getInstance("TLS"); 

    public MySSLSocketFactory(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(); 
    } 
} 

Et vous HttpClient est

public HttpClient getNewHttpClient() { 
     try { 
      KeyStore trustStore = KeyStore.getInstance(KeyStore 
        .getDefaultType()); 
      trustStore.load(null, null); 

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

      HttpParams params = new BasicHttpParams(); 
      HttpProtocolParams.setVersion(params, HttpVersion.HTTP_1_1); 
      HttpProtocolParams.setContentCharset(params, HTTP.UTF_8); 

      SchemeRegistry registry = new SchemeRegistry(); 
      registry.register(new Scheme("http", PlainSocketFactory 
        .getSocketFactory(), 80)); 
      registry.register(new Scheme("https", sf, 443)); 

      ClientConnectionManager ccm = new ThreadSafeClientConnManager(
        params, registry); 

      return new DefaultHttpClient(ccm, params); 
     } catch (Exception e) { 
      return new DefaultHttpClient(); 
     } 
    } 

espérons qu'il vous aidera.