2015-11-20 12 views
17

Ich habe eine webview für die Lade-URL, aber nicht funktionieren.Android-Fehler in webview.loadUrl() - Trust-Anker für Zertifizierungspfad nicht gefunden

Blick auf meinem Code:

public class MainActivity extends AppCompatActivity { 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_main); 

    WebView wv = (WebView) findViewById(R.id.webView); 

    //Log.d("rudyy", "aqui"); 
    wv.loadUrl("https://tripulanteaims.tam.com.br/wtouch/wtouch.exe/index"); 
    //Log.d("rudyy", "fim"); 


    } 
} 

Wenn Sie diesen Code ausführen, Android diese Fehler zurück:

Failed to validate the certificate chain, error: java.security.cert.CertPathValidatorException: Trust anchor for certification path not found. 

Hilfe-ich bitte.

Antwort

37

erstellen WebViewClient:

private class WvClient extends WebViewClient 
{ 
    @Override 
    public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError er) { 
     handler.proceed(); 
     // Ignore SSL certificate errors 
    } 
} 

Und gesetzt den initialisierten WebViewClient ("WvClient"), um Ihre WebView ("wv" in diesem Fall):

wv.setWebViewClient(new WvClient()); 

Oder in einer Zeile:

wv.setWebViewClient(new WebViewClient() {@Override public void onReceivedSslError(WebView v, SslErrorHandler handler, SslError er){ handler.proceed(); }}); 
+1

bitte akzeptieren ... –

+1

das gleiche mit Anon sein '' 'webView.setWebViewClient (neu WebViewClient() { @Override public void onReceivedSslError (WebView Ansicht, SslErrorHandler Handler, SslError Fehler) { handler.proceed(); } }); '' ' – tyoc213

+1

genau was ich brauche .. – MKY

4

Ich habe damit zu tun und ehrlich gesagt erlaubt MITM-Angriffe ist ein Oh nein. Hier ist eine sauberere Lösung, die das Pinning unterstützt. Speichern Sie das Zertifikat in Ihrem Raw-Ressourcenordner.
HINWEIS: Leider gibt SSLError uns ein SslCertificate, wenn Sie getCertificate() aufrufen. SslCertificate ist irgendwie nutzlos. Es ist öffentliche API ermöglicht es Ihnen nicht, den öffentlichen Schlüssel zu überprüfen, nur das erstellt am, abgelaufenes Datum, ausgestellt von, ausgestellt von. Wenn Sie diese Klasse öffnen, sehen Sie jedoch eine X509Certificate-Membervariable, die nicht exposed ist. IDK, warum diese Designentscheidung getroffen wurde. Aber es gibt eine API zum Abrufen des Bundles, und die X509-Zertifikat-Mitgliedsvariable wird dort gespeichert. Also greifen wir auf diese Weise zu, weil das Zertifikat viel mehr nützliche Methoden enthält.

@Override 
public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) { 
    SslCertificate sslCertificateServer = error.getCertificate(); 
    Certificate pinnedCert = getCertificateForRawResource(R.raw.your_cert, mContext); 
    Certificate serverCert = convertSSLCertificateToCertificate(sslCertificateServer); 

    if(pinnedCert.equals(serverCert)) { 
     handler.proceed(); 
    } else { 
     super.onReceivedSslError(view, handler, error); 
    } 
} 

public static Certificate getCertificateForRawResource(int resourceId, Context context) { 
    CertificateFactory cf = null; 
    Certificate ca = null; 
    Resources resources = context.getResources(); 
    InputStream caInput = resources.openRawResource(resourceId); 

    try { 
     cf = CertificateFactory.getInstance("X.509"); 
     ca = cf.generateCertificate(caInput); 
    } catch (CertificateException e) { 
     Log.e(TAG, "exception", e); 
    } finally { 
     try { 
      caInput.close(); 
     } catch (IOException e) { 
      Log.e(TAG, "exception", e); 
     } 
    } 

    return ca; 
} 

public static Certificate convertSSLCertificateToCertificate(SslCertificate sslCertificate) { 
    CertificateFactory cf = null; 
    Certificate certificate = null; 
    Bundle bundle = sslCertificate.saveState(sslCertificate); 
    byte[] bytes = bundle.getByteArray("x509-certificate"); 

    if (bytes != null) { 
     try { 
      CertificateFactory certFactory = CertificateFactory.getInstance("X.509"); 
      Certificate cert = certFactory.generateCertificate(new ByteArrayInputStream(bytes)); 
      certificate = cert; 
     } catch (CertificateException e) { 
      Log.e(TAG, "exception", e); 
     } 
    } 

    return certificate; 
} 
+0

Hallo Ryan ... müssen wir nur diese Methoden überschreiben? – RickON

+0

@RickON Erweitern Sie WebViewClient und überschreiben Sie die Methode onReceivedSslError. –

+0

FYI, Wenn Sie die Zertifikatsfixierung verwenden und das Zertifikat, an das Sie sich geankert haben, geändert wird, wird Ihre App beschädigt. Nur etwas zu beachten ... –

Verwandte Themen