【发布时间】:2017-06-12 09:02:31
【问题描述】:
我的目标是通过 GlassFish 服务器上的 Quartz 调度程序启动 JSR-352 批处理作业,但有一个大问题。首先,这是我的代码。
我的 JSR-352 工作:
<job id="myJob" ...>
<step id="myBatchlet">
<batchlet ref="mypackage.MyBatchlet" />
</step>
</job>
对应的Java代码:
public class MyBatchlet implements Batchlet {
@Override
public String process() throws Exception {
System.out.println("Hello World!");
return BatchStatus.COMPLETED.toString();
}
@Override
public void stop() throws Exception {
}
}
当我通过 servlet 在 GlassFish 4.0 b89 服务器上开始这项工作时,它运行良好:
public class StartJobServlet extends HttpServlet {
private void processRequest(...) throws ... {
long executionId = BatchRuntime.getJobOperator().start("myJob", new Properties());
System.out.println("myJob started, execution ID = " + executionId);
}
}
但现在我想使用 Quartz 2.2.3 调度器,所以我这样写了一个 Quartz 作业:
public class StartMyJob implements Job {
@Override
public void execute(JobExecutionContext context) throws JobExecutionException {
long executionId = BatchRuntime.getJobOperator().start("myJob", new Properties());
System.out.println("myJob started, execution ID = " + executionId);
}
}
我已经为这项工作配置了 Quartz 和触发器。
但是当 myJob 应该启动时,它仍然处于 STARTING 状态并且从未真正运行。
根据日志,实际启动批处理作业的com.ibm.jbatch.container.util.BatchWorkUnit::run 过程永远不会被调用,而在使用 servlet 时是这样。
编辑:我发现了其他人的类似问题(相同症状)there,但由于我没有 glassfish-web.xml 文件,因此给定的解决方案不适合。
【问题讨论】:
-
它看起来更像是线程池问题而不是类加载器问题。由于您的工作从您的 servlet 运行良好,因此来自 Quartz 的路径似乎存在问题(假设您没有更改线程池配置)。我对 Glassfish 中的 Quartz 不太熟悉,也许您可以分享一些有关如何在服务器中获取 Quartz 作业控制的详细信息(例如 Quartz 是在服务器中运行还是远程运行?)。
-
是的,我重新创建了同样的东西。如果我有任何东西会回复更多。
-
我的示例失败的原因是 Quartz 使用自己的线程来启动 JSR 352 作业。我认为正在发生的事情是 A)Glassfish 似乎使用了 ManagedExecutorService 的某种风格来执行作业(传播 EE 上下文)但是 B)Quartz 正在使用的非托管线程上没有 EE 上下文。不确定是否值得深入研究 Quartz 和/或 Glassfish 配置以某种方式解决此问题,或者是否值得重新审视您的用例(例如,如果您要在 EE 中,您从 Quartz 中得到什么与说 EJB 计时器)无论如何应用程序)。希望能有所帮助。
标签: java jakarta-ee glassfish quartz-scheduler jsr352