Spring SchedulingConfigurer与CronTrigger表达式失效问题:如何实现每5分钟执行定时任务
解决Spring SchedulingConfigurer配置每5分钟执行定时任务的问题
我来帮你排查这个问题——你的定时任务没按预期每5分钟执行,核心问题出在Cron表达式的配置上,咱们一步步来解决:
问题根源
你用的Cron表达式 * */5 * * * * 逻辑不对:这个6位表达式(Spring默认是秒 分 时 日 月 周的顺序)意味着每秒都会触发任务,但仅在每5分钟的那些分钟内生效。结果就是每到第0、5、10...55分钟时,任务会被连续执行60次(每秒一次),完全不符合你“每5分钟执行一次”的需求。
正确的Cron表达式
要实现每5分钟执行一次,需要把秒位固定为0,分位设置为*/5,这样任务会在每个小时的0分、5分、10分……55分的整秒精准执行一次。
正确的表达式是:
0 */5 * * * *
修改后的完整代码
另外建议把CronTrigger的实例化提前,避免每次调用nextExecutionTime都新建对象,优化后的代码如下:
import java.util.Date; import java.util.concurrent.Executor; import java.util.concurrent.Executors; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.scheduling.Trigger; import org.springframework.scheduling.TriggerContext; import org.springframework.scheduling.annotation.EnableScheduling; import org.springframework.scheduling.annotation.SchedulingConfigurer; import org.springframework.scheduling.config.ScheduledTaskRegistrar; import org.springframework.scheduling.support.CronTrigger; @Configuration @EnableScheduling public class SchedulerConfig implements SchedulingConfigurer { @Bean(destroyMethod = "shutdown") public Executor taskExecutor() { return Executors.newScheduledThreadPool(100); } @Override public void configureTasks(ScheduledTaskRegistrar taskRegistrar) { taskRegistrar.setScheduler(taskExecutor()); // 提前实例化CronTrigger,避免重复创建对象 CronTrigger fiveMinuteTrigger = new CronTrigger("0 */5 * * * *"); taskRegistrar.addTriggerTask( // 任务逻辑 () -> System.out.println("Scheduler task is running: " + java.time.LocalDateTime.now()), // 触发规则 triggerContext -> fiveMinuteTrigger.nextExecutionTime(triggerContext) ); } }
匹配该Cron表达式的正则校验规则
如果你需要用正则来验证这类“每5分钟执行一次”的Spring Cron表达式,可以用以下正则:
^0\s*\/5\s*\*\s*\*\s*\*\s*\*$
正则说明:
^0:强制匹配秒位为0\s*\/5\s*:匹配分位的*/5,允许前后有任意空格(包括无空格)\s*\*\s*:依次匹配时、日、月、周位为*,同样允许前后空格$:匹配字符串结束,确保没有多余内容
如果要求必须用单个空格分隔各字段,可调整为:
^0\s+\/5\s+\*\s+\*\s+\*\s+\*$
内容的提问来源于stack exchange,提问作者Shailesh Vikram Singh
相关产品推荐
相关产品推荐

