Shahal
Shahal

Reputation: 1070

Webview failure when internet is off

I've a web based application, where the url is loaded when the app starts. I'm trying to handle a issue when

Internet of WiFi is turned off when resources are loading( resources are loaded in async format).

I'm using onReceivedError(WebView view, int errorCode, String description, String failingUrl) of WebViewClient for checking url failure. I've also tried onReceivedError(WebView view, WebResourceRequest request, WebResourceError error).

But i'm not getting any failure callback when internet of WiFi is turned off during resources are loading.

Upvotes: 2

Views: 851

Answers (3)

Shahal
Shahal

Reputation: 1070

This may not be the most efficient approach, but it's serving my purpose in this scenario. I'm using ping service(8.8.8.8 for now), JS callback and ConnectivityManager NetworkCallback to achieve this.

We're using a JS to check whether all the resources are loaded on not, it'll either give error, 'no' or 'yes'. Error & 'no' means html is not loaded completely.

ConnectivityManager NetworkCallback is used to know when internet of the same WiFi comes back when user is in Settings screen because if internet comes back we need to redirect user back to App. onLinkPropertiesChanged will be called in this scenario and we check whether internet is available using Ping service.

Network flow chart

Registering NetworkCallback

connectivityManager =
                    (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);

            NetworkRequest.Builder builder = new NetworkRequest.Builder();
            builder.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET);
            builder.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR);
            builder.addTransportType(NetworkCapabilities.TRANSPORT_WIFI);
            builder.addTransportType(NetworkCapabilities.TRANSPORT_VPN);
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
                connectivityManager.registerNetworkCallback(builder.build(), networkCallback);
            }

networkCallback

ConnectivityManager.NetworkCallback networkCallback = new ConnectivityManager.NetworkCallback() {

        @RequiresApi(api = Build.VERSION_CODES.M)
        @Override
        public void onAvailable(Network network) {
            // network available
            networkCheck(network);
        }

        @Override
        public void onLinkPropertiesChanged(Network network, LinkProperties linkProperties) {
            super.onLinkPropertiesChanged(network, linkProperties);
            networkCheck(network);
        }

        @Override
        public void onLost(Network network) {
            // network unavailable
            onDisconnected();
        }
    };

networkCheck to check whether internet is available or not. Maybe this step can be ignore, while writing i though NET_CAPABILITY_VALIDATED would check internet. But it is failing in some scenario.

private void networkCheck(Network network) {
        ConnectivityManager cm = (ConnectivityManager) getApplicationContext().getSystemService(Context.CONNECTIVITY_SERVICE);
        NetworkInfo info = cm.getNetworkInfo(network);
        boolean isConnected = (info != null && info.isConnectedOrConnecting());

        if (!isConnected) {
            onDisconnected();
            return;
        }
        NetworkCapabilities nc = cm.getNetworkCapabilities(network);
        if (nc == null || !nc.hasCapability(NetworkCapabilities.NET_CAPABILITY_VALIDATED) || !checkPingService()) {
            onDisconnected();
            return;
        }
        onConnected();
    }

checkPingService to check internet is available

private boolean checkPingService() {
        try {
            Process p1 = java.lang.Runtime.getRuntime().exec("ping -c 1 8.8.8.8");
            int returnVal = p1.waitFor();
            return (returnVal == 0);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return false;
    }

This is working in all the scenarios we tested so far. So feel free to comment in case any doubt.

Upvotes: 1

Dipankar Baghel
Dipankar Baghel

Reputation: 2049

Create receiver for network change you can detect network is off or on like below you can send local broadcast to your activity -

public class NetworkChangeReceiver extends BroadcastReceiver {
@Override
public void onReceive(final Context context, final Intent intent) {

    ConnectivityManager connectivityManager = (ConnectivityManager)context.getSystemService(Context.CONNECTIVITY_SERVICE );
      NetworkInfo activeNetInfo = connectivityManager.getNetworkInfo(ConnectivityManager.TYPE_MOBILE);
      boolean isConnected = activeNetInfo != null && activeNetInfo.isConnectedOrConnecting();   
      if (isConnected)       
          Log.i("NET", "Connected" + isConnected);   
      else 
          Log.i("NET", "Not Connected" + isConnected);
    }
}

Add below lines in menifest.xml file

 <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
 <uses-permission android:name="android.permission.INTERNET" />
 <receiver
        android:name="NetworkChangeReceiver"
        android:label="NetworkChangeReceiver" >
        <intent-filter>
            <action android:name="android.net.conn.CONNECTIVITY_CHANGE" />
            <action android:name="android.net.wifi.WIFI_STATE_CHANGED" />
        </intent-filter>
    </receiver>

Upvotes: 0

Kalpesh Rupani
Kalpesh Rupani

Reputation: 1049

Try this:

You can put the conditions for network check and than build your logic as you want

WebView mWebView;
NetworkInfo networkInfoWifi = (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE).getNetworkInfo(ConnectivityManager.TYPE_WIFI);

mWebView.setWebViewClient(mWebClient);

WebViewClient mWebClient = new WebViewClient(){

    @Override
    public boolean shouldOverrideUrlLoading(WebView  view, String  url){
        return true;
    }

    @Override
    public void onLoadResource(WebView  view, String  url){
        if (networkInfoWifi.isConnected()) {
            //Take action
        }
    }

}

Hope this will work!

Upvotes: 0

Related Questions