1

How to check programmatically whether the Wifi network the phone is connected to has internet access ?

I cannot use "ping google.com" type solutions because it does not work on some devices such as Honor 10

matdev
  • 4,115
  • 6
  • 35
  • 56
  • 1
    https://stackoverflow.com/questions/3841317/how-do-i-see-if-wi-fi-is-connected-on-android – Sanjay Hadiya Jun 11 '19 at 14:56
  • *I'd like to avoid "ping google.com" type solutions* there is no other way. To check if you can reach some resource on internet, you have to attempt to reach it – Tim Jun 11 '19 at 14:57
  • Ping a site and the return response will give you all the information. if not.. then you dont have internet connection. – Sayed Muhammad Idrees Jun 11 '19 at 15:00
  • @Tim Castelijns ping does not work from devices such as Honor 10: https://stackoverflow.com/questions/32749462/why-does-ping-works-on-some-devices-and-not-others – matdev Jun 26 '19 at 15:07
  • @matdev I do not mean to directly use ping. I was referring to "ping type solutions" e.g. trying to connect to a server to see if it is reachable – Tim Jun 26 '19 at 15:18
  • Thanks Tim. I've posted a solution using the Volley library which works fine on the devices I've tested. – matdev Jun 27 '19 at 13:48

3 Answers3

1

Well, in order to decide whether a device is connected to the internet we have to define what "connected to the internet" actually means. As far as I know, the Android SDK doesn't offer any way to check that and I think that is because you have to ping a specific address after all, in order to see if it is reachable.

On my Android device, the WiFi indicator in the status bar shows an exclamation point whenever I am connected to the WiFi network but my internet connection is down. I am not sure, but I think it pings a google server (like 8.8.8.8) behind the scenes in order to find out.

I think the best approach is not to ping Google, rather ping the specific address that you use in your app, for example if you use Last.fm API, ping that instead, because you could get in a situation where the Google server is reachable but the Last.fm API is down. This is just a general example, but the solution depends on your goal.


Obsidian
  • 3,719
  • 8
  • 17
  • 30
Radu S.
  • 11
  • 2
  • Thanks. I think it's a shame that the Android SDK does not offer any way to check if wifi network has internet access, since the OS knows this information. It would save a ping to the server. – matdev Jun 12 '19 at 08:54
1

Just try connecting to whatever it is that you need to talk to, and handle failures in a graceful way.

Pinging something (even the server you want to talk to) isn't reliable, as the server, or some part of the network may block PING.

Pinging something "well known" (like Google's name-server on 8.8.8.8) isn't reliable because it only tells you that it is up, not necessarily that you can reach the server you want to talk to. (Or, it might even be that the "well known" entity is down or unreachable, but your server is working OK).

Doing something other than just trying to connect to what you want risks introducing TOCTOU (Time-of-check to time-of-use) errors.

TripeHound
  • 2,721
  • 23
  • 37
  • 1
    The OS displays this information with the crossed Wifi symbol, but the Android API does not provide it :( – matdev Jun 12 '19 at 08:56
  • The OS will, I'm pretty certain, be checking whether _something_ out there (probably a Google server of some kind) is responding or not. That can give an _indication_ as to whether you'll be able to talk to the resource you need to, but won't be definitive. Whatever you attempt _ahead_ of actually _needing_ to talk to your server can be wrong by the time you actually _try_ talking to your server, so it is in that "real" process where I think you should put the effort to handle failures gracefully. – TripeHound Jun 12 '19 at 09:04
  • I understand your point, but still, the information I need is "Has the wifi network internet access ?", not whether a particular server is pingable – matdev Jun 12 '19 at 09:14
  • But as the other answer says, there isn't a (precisely defined) state of "having internet access"... the WiFi can be connected or not (to a router). Beyond that, it's "can _this host_ (the phone) talk to _another [specific] host_" or not. So you have to choose a specific host (that's almost guaranteed to be "up") and see if you can connect in some manner. I'm pretty certain that's all the phrase "_since the OS knows this information_" you left in a comment on the other answer means. – TripeHound Jun 12 '19 at 09:52
0

I've found a solution that is quick and does not require using ping command or having to load a page.

The solution uses Volley, Android's HTTP library:

public static void isInternetAccessWorking(Context context, final InternetAccessListener listener) {

    StringRequest stringRequest = new StringRequest(Request.Method.GET, "https://www.google.com",
            new Response.Listener<String>() {

                @Override
                public void onResponse(String response) {
                    listener.hasInternet(true);
                }
            }, 
            new Response.ErrorListener() {
               @Override
               public void onErrorResponse(VolleyError error) {
                   listener.hasInternet(false);
               }
    });

    Volley.newRequestQueue(context).add(stringRequest);
}

This method is not blocking: the activity or fragment calling isInternetAccessWorking() has to provide a parameter implementing InternetAccessListener that will receive the response

public interface InternetAccessListener {
    void hasInternet(Boolean result);
}
matdev
  • 4,115
  • 6
  • 35
  • 56