Search code examples
javamultithreadingrunnablescheduledexecutorservice

ScheduledExecutorService not triggering correctly


I am attempting to have a method triggered after a delay with the following code:

ScheduledExecutorService exec = Executors.newSingleThreadScheduledExecutor();
exec.scheduleAtFixedRate(new UpdateTDDBRejections(), 5, 10, TimeUnit.SECONDS);

It should wait for the delay to pass, trigger the "UpdateTDDBRejections" method, which is in another, Runnable, class, which will print out a phrase and then sleep and then print the phrase again, etc, etc.

It does not do this, it simply prints the phrase and then stops.

However when I set it up like this:

ScheduledExecutorService exec = Executors.newSingleThreadScheduledExecutor();
exec.scheduleAtFixedRate(new Runnable() 
{
      @Override
      public void run() {
        // do stuff
           System.out.println("garbage garbage garbage");
      }
    }, 5, 10, TimeUnit.SECONDS);

It operates as one would expect from the ScheduledExecutorService. I was under the impression that since I am using Java 8.4 that I would not have to add a TimerTask to make this coordinate in the way I want. Any suggestions? Or am I simply not able to call other Runnable classes with the ScheduledExecutorService?

EDIT: This is the UpdateTDDBRejections class.

public class UpdateTDDBRejections implements Runnable
{
   UpdateTDDBRejections()
   {
       System.out.println("garbage garbage garbage");
   }
   @Override
   public void run()
   {
   }
}

Solution

  • It is the run method that is executed repeatedly. Try the following:

    public class UpdateTDDBRejections implements Runnable
    {
       @Override
       public void run()
       {
           System.out.println("garbage garbage garbage");
       }
    }
    

    Note that since you're using Java 8, you could do

    ScheduledExecutorService exec = Executors.newSingleThreadScheduledExecutor();
    exec.scheduleAtFixedRate(() -> System.out.println("garbage garbage garbage"),
                             5, 10, TimeUnit.SECONDS);
    

    If you want the constructor to run (which is perhaps what you tried with new UpdateTDDBRejections() you need to do:

    ScheduledExecutorService exec = Executors.newSingleThreadScheduledExecutor();
    exec.scheduleAtFixedRate(UpdateTDDBRejections::new, 5, 10, TimeUnit.SECONDS);
                          // ^^^^^^^^^^^^^^^^^^^^^^^^^