Как отложить ManagedScheduledExecutorService, пока контейнер не будет приостановлен?
Я расследую использование javax.enterprise.concurrent.ManagedScheduledExecutorService
на WildFly Full 11.0.0.Final (WildFly Core 3.0.8.Final)
,
Мой Startup EJB напоминает
import java.time.LocalTime;
import java.util.concurrent.TimeUnit;
import javax.annotation.PostConstruct;
import javax.annotation.Resource;
import javax.ejb.Singleton;
import javax.ejb.Startup;
import javax.enterprise.concurrent.ManagedScheduledExecutorService;
@Startup
@Singleton
public class Scheduler {
static final long INITIAL_DELAY = 0L;
static final long PERIOD = 2L;
@Resource
ManagedScheduledExecutorService scheduler;
@PostConstruct
public void init() {
this.scheduler.scheduleAtFixedRate(this::invokePeriodically, INITIAL_DELAY, PERIOD, TimeUnit.SECONDS);
}
public void invokePeriodically() {
System.out.println("@@@@@@@@@@ - Don't use sout in prod " + LocalTime.now());
}
}
При запуске сервера я вижу эти сообщения:-
10:15:26,022 ERROR [org.jboss.as.ee] (EE-ManagedScheduledExecutorService-default-Thread-1) WFLYEE0110:
Failed to run scheduled task: java.lang.IllegalStateException:
WFLYEE0111: Cannot run scheduled task com.research.Scheduler$$Lambda$932/1222053658@1b50d7a0 as container is suspended
at org.jboss.as.ee.concurrent.ControlPointUtils$ControlledScheduledRunnable.run(ControlPointUtils.java:164)
at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511)
at java.util.concurrent.FutureTask.runAndReset(FutureTask.java:308)
at org.glassfish.enterprise.concurrent.internal.ManagedScheduledThreadPoolExecutor$ManagedScheduledFutureTask.access$201(ManagedScheduledThreadPoolExecutor.java:383)
at org.glassfish.enterprise.concurrent.internal.ManagedScheduledThreadPoolExecutor$ManagedScheduledFutureTask.run(ManagedScheduledThreadPoolExecutor.java:534)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
at org.glassfish.enterprise.concurrent.ManagedThreadFactoryImpl$ManagedThread.run(ManagedThreadFactoryImpl.java:250)
at org.jboss.as.ee.concurrent.service.ElytronManagedThreadFactory$ElytronManagedThread.run(ElytronManagedThreadFactory.java:78)
Когда я увеличиваю начальную задержку
static final long INITIAL_DELAY = 60L;
Запуск сервера "чистый".
Существуют ли какие-либо доступные механизмы / методы, которые я могу использовать (кроме предположения о том, какой должна быть моя первоначальная задержка), чтобы всегда запускать чистый сервер и планировать свой EJB как можно скорее?
1 ответ
Вам может быть лучше использовать таймер EJB для этой цели. Сервер гарантированно не будет запускать методы таймера, пока EJB не будет в работе.
Вы можете проверить API для создания таймеров в javax.ejb.TimerService.
Обратите внимание, что если вы создаете постоянные таймеры, то сервер попытается "догнать" пропущенные срабатывания при перезагрузке сервера.
Если это просто периодическая задача, не создавайте постоянные таймеры.
Немного поздно ответить на этот вопрос, но вместо того, чтобы полагаться на другой API, вы можете использовать встроенную аннотацию EE: @Schedule
над объявлением вашего метода. Он предоставляет возможность определять тайм-ауты и постоянство внутри.