Saturday, December 1, 2012

Enabling Android Webview to Ignore bad Certs..


Recently, in a small project I wanted to display a mobile optimized website inside of a WebView in a native Android App. So, I created the WebView and proceeded to load the website in it, and Voila ! it did not work ! I tried a few different settings for the webView, but each time I got a “Website not available” error.

Subsequently, I opened up the website on my desktop browser, and it worked great. Then, I opened up the website in the Android browser, and it opened up fine in either case. This was fairly baffling to me. [ Later I realized that in either case, I had set my browser to ignore bad SSL Certs ]
I was using a Custom webViewClient for loading the page, but was over-riding only three methods:

onPageStarted(WebView view, String url, Bitmap favicon)

onReceivedError(WebView view, int errorCode, String description, String failingUrl)
I had hoped that in-case of *any* kind of error, the onReceivedError would get triggered, but it was not getting triggered. After a little head-banging, I decided to take a deeper look at which other webViewClient methods I could over-ride and found some interesting ones.

onReceivedHttpAuthRequest(WebView view, HttpAuthHandler handler, String host, String realm)

onTooManyRedirects(WebView view, Message cancelMsg, Message continueMsg)

So, I proceeded to over-ride the above three methods as well. In my subsequent test, I found that the method “onReceivedSslError” was getting triggered ! This was excellent, because now I had a clue of where the problem could be, and which direction to proceed in. I subsequently went to my desktop browser, and stock Android browser, and made sure that I got prompted in-case of a bad SSL Cert. After that change, I could see that the stock Android browser, gave me a Dialog with three options, kind of like the image below.


The above image communicated to me that the SSL Cert was not trusted, and that all I would need to do to make it work, would be to ‘intercept’ this Dialog within the WebViewClient, and ignore the bad Cert.

After a little bit of digging, I found this post ( image above is sourced from the same ) from Damian Flannery’s Blog which mentions :

engine.setWebViewClient(new WebViewClient() {
 public void onReceivedSslError (WebView view, SslErrorHandler handler, SslError error) {
 handler.proceed() ;
 }

The single bolded line of code above, will make sure that the webView will ignore bad Cert warnings, and continue to load the website. I made the above change, and it was all good after that. 

Hoping that this post could save someone’s time when faced with a similar issue in the future…


1 comment:

Unknown said...

I was hoping you could help me. I am trying to pass an ssl wildcard cert to a webview and am having no luck. below is is my code in the webactivity java file. the page just comes up as webpage not available. Any suggestions?

package com.example.somesite;

import android.app.Activity;
import android.os.Bundle;
import android.webkit.WebView;
import android.net.http.SslError;
import android.webkit.SslErrorHandler;
import android.webkit.WebSettings;
import android.webkit.WebViewClient;

public class WebActivity6 extends Activity {

private WebView webView6;



public void onCreate(Bundle savedInstanceState) {


super.onCreate(savedInstanceState);
setContentView(R.layout.webcontent6);

webView6 = (WebView) findViewById(R.id.webView6);

webView6.getSettings().setJavaScriptEnabled(true);

webView6.loadUrl("https://somesite.com");
public void OnReceivedSslError(WebView webView6, SslErrorHandler handler,SslError error)
{
handler.proceed();
}

}

}