aselims
aselims

Reputation: 1893

Get a value from a thread

I tried to check Internet connectivity with the following code snippet:

     private static boolean done;

 public static boolean isInternetConnected(Context context) {
    boolean networkConnected = false;
    ConnectivityManager cm = (ConnectivityManager) context.getSystemService(
            Context.CONNECTIVITY_SERVICE);

    NetworkInfo wifiNetwork = cm.getNetworkInfo(ConnectivityManager.TYPE_WIFI);
    if (wifiNetwork != null && wifiNetwork.isConnected()) {
        networkConnected = true;
    }

    NetworkInfo mobileNetwork = cm.getNetworkInfo(ConnectivityManager.TYPE_MOBILE);
    if (mobileNetwork != null && mobileNetwork.isConnected()) {
        networkConnected = true;
    }

    NetworkInfo activeNetwork = cm.getActiveNetworkInfo();
    if (activeNetwork != null && activeNetwork.isConnected()) {
        networkConnected = true;
    }

    if(networkConnected) {
        Thread thread = new Thread(new Runnable() {
            @Override
            public void run() {

                try {
                    HttpURLConnection urlc = (HttpURLConnection) (new URL("http://www.google.com").openConnection());
                    urlc.setRequestProperty("User-Agent", "Test");
                    urlc.setRequestProperty("Connection", "close");
                    urlc.setConnectTimeout(1500);
                    urlc.connect();
                    done = (urlc.getResponseCode() == 200);
                    //1st
                    Log.d(TAG, "done =" + done);
                } catch (Exception e) {
                    Log.e(TAG, "Error checking internet connection", e);
                }

            }
        });

        thread.start();
        //2nd 
        Log.d(TAG, "after start done =" + done);
        return done;
    }

    return networkConnected;

}

The problem is that "done" inside the thread "//1st" is "true: but after the thread "//2nd" is "false". I do not know what is wrong in here? can somebody explain this weird behavior?

Upvotes: 0

Views: 55

Answers (3)

dave.c
dave.c

Reputation: 10908

There are two issues that I can see with your code. The first is as the other posters have pointed out, that thread.start() returns immediately, so your "after" section will actually execute before your spawned thread.

The second issue is that since the value of done is set in a separate thread, there is no guarantee that the change in the value will be visible in the main thread. So as well as fixing the logic of your program as others have suggested, you will also need to use the volatile keyword when declaring the boolean done.

Upvotes: 0

Emanuel
Emanuel

Reputation: 8106

You need to notify when the Thread has finished its work in the background. See my other answer for a solution how to notify your mainUI.

How to return an object from the asynctask to the main class in android

Upvotes: 0

Dave Morrissey
Dave Morrissey

Reputation: 4411

You are starting a thread that runs in the background, and will take a while to complete. The call to thread.start() will return immediately, so when you check the value of done at 2nd, it is still false because the background thread has not completed its work.

If you don't want your method to return until you've completed the test HTTP request, don't put it in a thread.

A side note - don't poll Google to test internet connectivity - it's a bit rude!

Upvotes: 1

Related Questions