简体   繁体   English

Quartz CronTrigger没有在指定的startAt()时间触发

[英]Quartz CronTrigger is not firing at the specified startAt() time

I have a scenario where I need to schedule a job which has to be execute daily at a specific time. 我有一种情况,我需要安排一个必须在特定时间每天执行的作业。 When I schedule it with specific time as the start time for scheduler the quartz won't trigger the job at the set start time instead it would trigger at the next cycle ie after 24 hrs delay.Even on checking the the nextFireTime, we get a day's delay. 当我以特定的时间作为调度程序的开始时间进行调度时,石英将不会在设置的开始时间触发作业,而是会在下一个周期即延迟24小时后触发。即使检查nextFireTime,我们也会得到一个一天的延迟。

For Eg: I need to schedule a job daily to run at 6 pm in the evening. 对于例如:我需要安排一份工作,每天晚上6点运行。 And start it at 5 pm Today (27th March 2018).The job doesn't start and nextFireTime is 6pm 28th March 2018. 并于今天(2018年3月27日)下午5点开始工作。该工作没有开始,nextFireTime是2018年3月28日下午6点。


Code snippet : 程式码片段:


Date startDateTime = new Date(scheduler.getStartDateTime());
Calendar calendar = GregorianCalendar.getInstance();
calendar.setTime(startDateTime);
int hours = calendar.get(Calendar.HOUR_OF_DAY);
int minutes = calendar.get(Calendar.MINUTE);
CronTrigger trigger = TriggerBuilder.newTrigger().withIdentity(scheduleTriggerName, schdeuleGroupName).startAt(startDateTime).withSchedule(dailyAtHourAndMinute(hours, minutes)).build();
JobDetail jobDetail = this.getJobDetail(schdeuleJobName, schdeuleGroupName);

Scheduler configuration for spring Spring的调度程序配置


SchedulerFactoryBean schedulerFactoryBean= new SchedulerFactoryBean();

QuartzAutowireBeanFactory jobFactory = new QuartzAutowireBeanFactory();
jobFactory.setApplicationContext(applicationContext);
schedulerFactoryBean.setJobFactory(jobFactory);
schedulerFactoryBean.scheduleJob(jobDetail, trigger)// scheduling the job

Solution

One liner: 一班轮:

Cron only handles 1-minute resolutions Cron仅处理1分钟的分辨率

The starttime that which was passed to the startAt() function was a timestamp till milliseconds and cron does support till minutes. 传递给startAt()函数的启动时间是一个时间戳,直到毫秒,而cron确实支持了几分钟。

so the simple solution was to use the calendar to set the minutes and seconds as zero. 因此,简单的解决方案是使用日历将分钟和秒设置为零。

calendar.setTime(startDateTime);
            calendar.set(Calendar.SECOND, 0); // this was the solution
            calendar.set(Calendar.MILLISECOND, 0); // this was the solution
            int hours = calendar.get(Calendar.HOUR_OF_DAY);
            int minutes = calendar.get(Calendar.MINUTE);
            trigger = TriggerBuilder.newTrigger();
            trigger.startAt(calendar.getTime()).withSchedule(dailyAtHourAndMinute(hours, minutes));

Detailed One: Finally I got the reason for the behavior, while debugging I saw that it was setting the delay of 24 hours but when one would print the time it would be in hh:mm:00 format I mean the output would set the seconds parts as 00 as default , so the problem was the starttime that was passed as parameter was a timestamp through the UI consisting of seconds and milliseconds so after reading on the Cron format I came to know that it supported till minutes resolutions so wherever it use to get the timestamp the startAt(startDateTime) in the 详细的一:最终,我得到了该行为的原因,在调试时,我看到它设置了24小时的延迟,但是当打印时间时,将采用hh:mm:00格式,这意味着输出将设置秒部件默认为00,所以问题是启动时间是作为参数传递的,是通过UI的时间戳,该时间戳是由秒和毫秒组成的,因此在阅读Cron格式后,我知道它支持直到分钟的分辨率,无论它用于哪里获得时间戳记中的startAt(startDateTime)

CronTrigger trigger = TriggerBuilder.newTrigger().withIdentity(scheduleTriggerName, schdeuleGroupName).startAt(startDateTime).withSchedule(dailyAtHourAndMinute(hours, minutes)).build();

it would calculate the next run by skipping the seconds and milliseconds part. 它将跳过秒和毫秒部分来计算下一次运行。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM