Thread.sleep() vs handler.postDelay() to execute network call in every 30sec

Viewed 1185

I want perform a network call in every 30sec to push some metrics to Server. Currently I am doing it using thread.sleep(). I found some articles saying thread.sleep() has some drawbacks. I need to know am I doing it right? or Replacing the thread with Handler will improve my code?

public static void startSending(final Context con) {
    if (running) return;
    running = true;
    threadToSendUXMetrics = new Thread(new Runnable() {

        @Override
        public void run() {
            do {
                try {
                    Thread.sleep(AugmedixConstants.glassLogsPushInterval);
                } catch (InterruptedException e) {
                    mLogger.error(interrupt_exception + e.getMessage());
                }
                // to do to send each time, should have some sleep code
                if (AugmedixConstants.WEBAPP_URL.equals(AugmedixConstants.EMPTY_STRING)||!StatsNetworkChecker.checkIsConnected(con)) {
                    Utility.populateNetworkStat();
                    mLogger.error(may_be_provider_not_login_yet);
                } else
                    sendUXMetrics();

            } while (running);

            if (!uxMetricsQueue.isEmpty()) sendUXMetrics();

        }
    });
    threadToSendUXMetrics.start();
}
3 Answers

If You are using only one thread in the network, then usage of the thread.sleep() is fine. If there are multiple threads in synchronization, then the thread.sleep() command will block all the other threads that are currently running. As per the details you've provided, there is only one thread present which isn't blocking any other active threads which are running in synchronization, so using thread.sleep() shouldn't be a problem.

Use Handler.postDelayed to schedule tasks if you are working in UI Thread and Thread.sleep if you are working in background thread.

Apparently you are sending some data using network, you must do it in the background thread, hence Thread.sleep is recommended.

Simple is:

  • Thread.sleep(millisSeconds): With this method, you only can call in background tasks, for example in AsyncTask::doInBackground(), you can call to delay actions after that. RECOMMENDED CALL THIS METHOD IN BACKGROUND THREAD.
  • Handler().postDelayed({METHOD}, millisSeconds): With this instance, METHOD will trigged after millisSeconds declared.

But, to easy handle life cycle of Handler(), you need to declare a Handler() instance, with a Runnable instance. For example, when your Activity has paused or you just no need call that method again, you can remove callback from Handler(). Below is example:

public class MainActivity extends Activity {

   private Handler mHandler = Handler();

   public void onStart(...) {
      super.onStart(...)
      this.mHandler.postDelayed(this.foo, 1000)
   }

   public void onPaused(...) {
      this.mHandler.removeCallback(this.foo)
      super.onPaused(...)
   }

   private Runnable foo = new Runnable() {
      @Override
      public void run() {
         // your code will call after 1 second when activity start
         // end remove callback when activity paused

         // continue call...
         mHandler.postDelayed(foo, 1000)
      }
   }

}

The code above just for reference, I type by hand because don't have IDE to write then copy paste.

Related