Https Connection Android

后端 未结 15 1701
萌比男神i
萌比男神i 2020-11-22 04:43

I am doing a https post and I\'m getting an exception of ssl exception Not trusted server certificate. If i do normal http it is working perfectly fine. Do I have to accept

15条回答
  •  清酒与你
    2020-11-22 05:44

    http://madurangasblogs.blogspot.in/2013/08/avoiding-javaxnetsslsslpeerunverifiedex.html

    Courtesy Maduranga

    When developing an application that uses https, your test server doesn't have a valid SSL certificate. Or sometimes the web site is using a self-signed certificate or the web site is using free SSL certificate. So if you try to connect to the server using Apache HttpClient, you will get a exception telling that the "peer not authenticated". Though it is not a good practice to trust all the certificates in a production software, you may have to do so according to the situation. This solution resolves the exception caused by "peer not authenticated".

    But before we go to the solution, I must warn you that this is not a good idea for a production application. This will violate the purpose of using a security certificate. So unless you have a good reason or if you are sure that this will not cause any problem, don't use this solution.

    Normally you create a HttpClient like this.

    HttpClient httpclient = new DefaultHttpClient();

    But you have to change the way you create the HttpClient.

    First you have to create a class extending org.apache.http.conn.ssl.SSLSocketFactory.

    import org.apache.http.conn.ssl.SSLSocketFactory;
    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;
    
    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();
        }
    }
    

    Then create a method like this.

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

    Then you can create the HttpClient.

    HttpClient httpclient = getNewHttpClient();

    If you are trying to send a post request to a login page the rest of the code would be like this.

    private URI url = new URI("url of the action of the form");
    HttpPost httppost =  new HttpPost(url);
    List nameValuePairs = new ArrayList();  
    nameValuePairs.add(new BasicNameValuePair("username", "user"));  
    nameValuePairs.add(new BasicNameValuePair("password", "password"));
    try {
        httppost.setEntity(new UrlEncodedFormEntity(nameValuePairs));
        HttpResponse response = httpclient.execute(httppost);
        HttpEntity entity = response.getEntity();
        InputStream is = entity.getContent();
    } catch (UnsupportedEncodingException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (ClientProtocolException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
    

    You get the html page to the InputStream. Then you can do whatever you want with the returned html page.

    But here you will face a problem. If you want to manage a session using cookies, you will not be able to do it with this method. If you want to get the cookies, you will have to do it via a browser. Then only you will receive cookies.

提交回复
热议问题