2015-10-08 3 views
2

Я знаю, что могу исключить исключение для подавления дальнейших исполнений задачи, которая была запланирована для повторного выполнения внутри ScheduledExecutorService (см. this question).Остановка и удаление задачи из ScheduledExecutorService

Я также знаю, что могу установитьRemoveOnCancelPolicy (true), чтобы убедиться, что отмененные задачи удалены из очереди.

Мои вопросы: действительно ли задача удалена из планировщика, когда я выхожу из него исключение? Это происходит, неявно отменяя будущее? Если да, значит ли это, что setRemoveOnCancelPolicy() также относится к этому случаю?

В Javadocs ничего не найдено.

ответ

1

Мне было интересно, что в документах ничего не найдено, поэтому я попробовал. Наблюдение:

  • бросание RuntimeException помечает будущее как сделано, не отменена.
  • Runnable удаляется из очереди планировщика независимо от из setRemoveOnCancelPolicy().

Попробуйте себя:

public class SchedulerTest { 
    protected final Logger log = LoggerFactory.getLogger(this.getClass()); 

    @Test 
    public void schedulerExecutionException() throws Exception { 
     log.info("Test: schedulerExecutionException"); 

     ScheduledThreadPoolExecutor sched = new ScheduledThreadPoolExecutor(2); 
     sched.setRemoveOnCancelPolicy(true); 

     ScheduledFuture future1 = sched.scheduleAtFixedRate(new Runnable() { 
      int counter = 0; 
      @Override 
      public void run() { 
       log.info("Runnable 1: "+ ++counter); 

       if (counter >= 2) { 
        log.info("Runnable 1: BOOOM"); 
        throw new RuntimeException("boom"); 
       } 

      } 
     }, 1, 1, TimeUnit.SECONDS); 

     ScheduledFuture future2 = sched.scheduleAtFixedRate(new Runnable() { 
      int counter = 0; 
      @Override 
      public void run() { 
       log.info("Runnable 2: "+ ++counter); 
      } 
     }, 1, 1, TimeUnit.SECONDS); 

     long cutoff = new Date().getTime() + 6000; 

     while (new Date().getTime() < cutoff) { 
      log.info("Scheduler Queue size: "+ sched.getQueue().size()); 
      log.info("Future 1: is "+ (future1.isCancelled() ? "" : "not ") +"cancelled, is "+ (future1.isDone()? "" : "not ") +"done"); 
      log.info("Future 2: is "+ (future2.isCancelled() ? "" : "not ") +"cancelled, is "+ (future2.isDone()? "" : "not ") +"done"); 
      Thread.sleep(1000); 
     } 
     assertEquals(sched.getQueue().size(), 1); 

     future2.cancel(true); 
     log.info("Scheduler Queue size: "+ sched.getQueue().size()); 
     log.info("Future 1: is "+ (future1.isCancelled() ? "" : "not ") +"cancelled, is "+ (future1.isDone()? "" : "not ") +"done"); 
     log.info("Future 2: is "+ (future2.isCancelled() ? "" : "not ") +"cancelled, is "+ (future2.isDone()? "" : "not ") +"done"); 

     assertEquals(sched.getQueue().size(), 0); 

     sched.shutdownNow(); 
    } 
}