我正在使用Quartz 1.8.6的Spring 3。我已经通过以下方式在applicationcontext文件中定义了SchedulerFactoryBean:
<bean id="quartzscheduler" class="org.springframework.scheduling.quartz.SchedulerFactoryBean" lazy-init="false">
<property name="autoStartup">
<value>true</value>
</property>
<property name="quartzProperties">
<props>
<prop key="org.quartz.scheduler.instanceId">AUTO</prop>
<prop key="org.quartz.scheduler.instanceName">MyClusteredScheduler</prop>
<prop key="org.quartz.jobStore.class">org.quartz.impl.jdbcjobstore.JobStoreTX</prop>
<prop key="org.quartz.jobStore.driverDelegateClass">org.quartz.impl.jdbcjobstore.StdJDBCDelegate</prop>
<prop key="org.quartz.jobStore.tablePrefix">QRTZ_</prop>
<prop key="org.quartz.jobStore.isClustered">true</prop>
<prop key="org.quartz.jobStore.clusterCheckinInterval">20000</prop>
<prop key="org.quartz.jobStore.misfireThreshold">60000</prop>
</props>
</property>
<property name="dataSource">
<ref bean="quartzdataSource" />
</property>
</bean>
<bean id="quartzdataSource"
class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="com.mysql.jdbc.Driver" />
<property name="url" value="jdbc:mysql://localhost:3305/quartz" />
<property name="username" value="root" />
<property name="password" value="root" />
</bean>
这是我的工作类,它实际上是一个实体bean类,按以下方式定义:
@Entity
@Table(name = "DATABASEMONITOR")
public class DatabaseMonitor implements Serializable, Job {
@Id
@GeneratedValue
@Column(name = "ID", unique = true, nullable = false)
private Integer id;
@Column(name = "NAME", nullable = false)
private String name;
public DatabaseMonitor(String name, String sqlQuery){
this.name = name;
this.sqlQuery = sqlQuery;
}
@Override
public void execute(JobExecutionContext context)
throws JobExecutionException {
System.out.println("inside job");
}
}
这是我的调度程序控制器类:
public class SchedulerController {
public static void addJob(DatabaseMonitor databaseMonitor){
JobDetail job = new JobDetail();
job.setName(databaseMonitor.getName());
job.setJobClass(DatabaseMonitor.class);
CronTrigger trigger = new CronTrigger();
trigger.setName(databaseMonitor.getName());
try {
trigger.setCronExpression("0/2 * * * * ?");
Scheduler scheduler = (Scheduler) BeansManager.getInstance().getBean("quartzscheduler");
scheduler.scheduleJob(job, trigger);
} catch (ParseException e) {
e.printStackTrace();
} catch (SchedulerException e) {
e.printStackTrace();
}
}
}
从主类我调用这个调度函数来在运行时添加作业:
DatabaseMonitor databaseMonitor = new DatabaseMonitor(new Date().toString(), "query string");
SchedulerController.addJob(databaseMonitor);
现在问题是一切正常,没有任何异常,工作细节在预定义的石英数据库详细信息中得到更新。但这项工作没有得到执行。你能帮帮我吗?
答案 0 :(得分:0)
您的DatabaseMonitor
应该有默认构造函数。 Quartz将尝试执行JobDetail
。 JobDetail
将从头开始创建DatabaseMonitor
并执行其execute方法。由于DatabaseMonitor
没有默认构造函数,因此无法执行。
由于您已经有一个默认构造函数,我建议稍微重构一下。我使用带有弹簧的2.2.1版本的石英,因此一些类名可能会有所不同。
首先让你的实体分成两部分。
import javax.persistence.Column;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
public class DatabaseMonitor {
@Id
@GeneratedValue
@Column(name = "ID", unique = true, nullable = false)
private Integer id;
@Column(name = "NAME", nullable = false)
private String name;
@Column(name = "SQL_QUERY", nullable = false)
private String sqlQuery;
// Getters && Setters && Def. Const etc.
}
我稍后会解释工作部分。然后让你的控制器重构为一个spring bean。
import org.quartz.JobDataMap;
import org.quartz.Scheduler;
import org.quartz.SchedulerException;
import org.quartz.impl.JobDetailImpl;
import org.quartz.impl.triggers.CronTriggerImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import java.text.ParseException;
@Component
public class SchedulerController {
@Autowired
Scheduler scheduler;
public void addJob(DatabaseMonitor databaseMonitor) {
final JobDataMap jobDataMap = new JobDataMap();
jobDataMap.put("sqlQuery", databaseMonitor.getSqlQuery());
final JobDetailImpl jobDetail = new JobDetailImpl();
jobDetail.setName(databaseMonitor.getName());
jobDetail.setDurability(true);
jobDetail.setJobDataMap(jobDataMap);
jobDetail.setJobClass(DatabaseJob.class);
try {
final CronTriggerImpl trigger = new CronTriggerImpl();
trigger.setCronExpression("0/2 * * * * ?");
trigger.setName(databaseMonitor.getName());
scheduler.scheduleJob(jobDetail, trigger);
} catch (ParseException | SchedulerException e) {
e.printStackTrace();
}
}
}
如您所见,我正在使用JobDataMap将参数传递给我的作业。这个参数可能是sqlQuery。让我们检查一下我们的工作。
import org.quartz.Job;
import org.quartz.JobDataMap;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import java.io.Serializable;
public class DatabaseJob implements Job, Serializable {
@Override
public void execute(JobExecutionContext context) throws JobExecutionException {
final JobDataMap jobDataMap = context.getMergedJobDataMap();
final String sqlQuery = jobDataMap.getString("sqlQuery");
System.out.println("SqlQuery: " + sqlQuery);
}
}
我正在从上下文中读取我的查询。我的工作不包含任何州。在您的实施中,您的工作也是一个实体。 Hibernate(或其他JPA实现)代理几乎所有东西,并拥有很多状态。这会因石英执行而中断。
我创建了一个示例应用程序并将其放到github。
答案 1 :(得分:0)
您的配置缺少必填项
CONTAINS(*, 'NOT Tokyo')
和org.quartz.threadPool.class
属性。
请参阅: http://quartz-scheduler.org/documentation/quartz-1.x/configuration/ConfigThreadPool