Search code examples
javatimerscheduled-taskstimertaskperiodic-task

Timer not able to execute task


I am trying to execute a task periodically. For example:

class MyTimerTask implements TimerTask 
{
   public void run() {
     // Some actions to perform
   }
   Timer cleaner = new Timer(true);
   cleaner.scheduleAtFixedRate(new MyTimerTask(), 0, PURGE_INTERVAL);
}

However, the run method is executing only once. But if I put the first time delay as 10 seconds, then the run method doesn't execute even once.

Example:

cleaner.scheduleAtFixedRate(new MyTimerTask(), 10, PURGE_INTERVAL);

Solution

  • This sounds like an issue with time units to me. Ensure that you're converting to milliseconds correctly.

    The easiest way to do this is to use Java's TimeUnit.

    Timer cleaner = new Timer(true);
    cleaner.scheduleAtFixedRate(new MyTimerTask(),
        TimeUnit.SECONDS.toMillis(10),
        TimeUnit.SECONDS.toMillis(30));
    

    It could also be caused by the Timer being started in daemon mode. If all your main method does is set up the timer and then return the timer will never execute since it's the last remaining thread and because it's a daemon thread the JVM will exit.

    To fix this either make the timer thread not a daemon (i.e. pass false in the constructor) or make the main thread wait for user input before exiting.

    Here's an example using both of the above:

    public class TimerDemo extends TimerTask {
    
        public void run() {
            System.out.printf("Time is now %s%n", LocalTime.now());
        }
    
        public static void main(String[] args) throws IOException {
            Timer timer = new Timer(true);
            timer.scheduleAtFixedRate(new TimerDemo(),
                    TimeUnit.SECONDS.toMillis(5),
                    TimeUnit.SECONDS.toMillis(10));
            System.out.printf("Program started at %s%n", LocalTime.now());
            System.out.println("Press enter to exit");
            try (BufferedReader reader = new BufferedReader(new InputStreamReader(System.in))) {
                // Wait for user to press enter
                reader.readLine();
            }
            System.out.println("Bye!");
        }
    }
    

    And output of running it:

    Program started at 14:49:42.207
    Press enter to exit
    Time is now 14:49:46.800
    Time is now 14:49:56.799
    Time is now 14:50:06.799
    Time is now 14:50:16.799
    Time is now 14:50:26.799
    [I pressed 'enter']
    Bye!
    
    Process finished with exit code 0