Ahm*_*war 12 scheduling timer java-ee
我创建了一个doWork()预定每天凌晨1点运行的功能,功能如下:
@Schedule(hour = "1", persistent = false)
public void doWork()
{
System.out.println("Starting .....\nTIME: " + System.currentTimeMillis());
System.out.println("this : " + this);
//Some code here, if-conditions and try/catch blocks. No loops
System.out.println("Exiting .....\nTIME: " + System.currentTimeMillis());
System.out.println("this : " + this);
}
Run Code Online (Sandbox Code Playgroud)
问题是这个函数不止一次运行,而不是按计划运行.
一旦我创建它,它就完全按预期运行(每天凌晨1:00:00).几天后,它开始在1:03:00运行(这没有任何意义,因为它是非持久性的,并且服务器中没有任何停机时间).之后,该功能开始运行不止一次,间隔间隔很短(秒差)
有谁知道可能导致这种情况的原因,或者告诉我我能做些什么来解决它?
[编辑]:环境细节
Application Server:WebSphere Application Server 8.5.5
IDE:Rational Application Developer 9.1
数据库管理系统:IBM DB2 10.1
我相信您正在观察容器尝试重试失败的调用doWork()。
EJB 计时器服务是事务性的。
\n\n如果执行超时方法引发任何运行时异常,则事务将回滚,并且容器将尝试再次执行超时方法。请参阅 EJB 3.1 规范的 \xc2\xa718.2.8 事务。
\n\n此外,如果事务超时到期,某些实现将仅将当前事务标记为回滚并继续处理。这将导致计时器调用最终失败并尝试重试。
\n\n这种重试机制没有明确规定,实际行为因实现而异。有些人会永远重试,而另一些人会在多次尝试后放弃。例如,WebSphere 提供了一种指定重试策略的方法。请参阅使用企业 Bean 的 EJB 计时器服务创建计时器。
\n\n最后,如果您的应用程序跨多个节点运行,那么您可能会在每个服务器实例上运行一个计时器。根据规范的 \xc2\xa718.2.3 非持久计时器:
\n\n\n\n\n对于自动非持久计时器,容器会在应用程序初始化期间为容器所分布的每个 JVM 创建一个新的非持久计时器。
\n
如果这些都执行相同的任务,那么可能会导致足够的混乱,从而产生错误、回滚和后续重试。
\n