Cron 表达式
解析五段/六段表达式,逐字段说明并列出未来若干次实际触发时间。
这个工具把一条 Cron 表达式拆成字段逐个讲解:每个写法的含义、解析后的取值集合、一句人话描述,以及从基准时刻起的未来触发时刻。它同时覆盖两种方言。POSIX/vixie 的 5 段写法(分 时 日 月 周):只认 * , - / 和分钟/小时/月/日的数字与三字母名称(JAN、MON 等),星期 0–7 中 0 和 7 都是周日。Quartz 的 6/7 段写法(秒在最前,可选年份):额外支持 ?(日与星期二选一时占位)、L(最后一天/最后一个星期几)、W(最近工作日)、n#m(第几个星期几)。所有计算在浏览器本地时区完成,时间推算逐日扫描匹配,与 crontab(5) 描述的守护进程行为一致。
两套方言的星期编号也不同:vixie 是 0=周日,Quartz 是 1=周日;?、L、W、n#m 这四种是 Quartz 专有,出现在 5 段模式里会明确报「Quartz 专有写法」。两个最容易被坑的点会直接写在提示条里:一是「日」和「周」同时受限时 vixie-cron 取的是并集(或),命中日期或命中星期都会执行,而不是大多数人以为的交集——想表达「且」只能拆两行 crontab;二是像 0 0 30 2 * 这种「2 月 30 日」组合永远不会触发,工具在静态检查阶段就给出「2 月没有 30 日,永远不会触发」,而不是让你空等。
Cron 表达式怎么用
- 选方言:方言下拉框在「方言与基准」折叠里,默认 POSIX(Linux/Unix 的 crontab -e、/etc/crontab)。Quartz 用于 Java 生态(Spring @Scheduled、Quartz Scheduler、部分 CI):段数变成 6 或 7,秒在第一位,允许 ?、L、W、#。同一层里还有「识别 @ 别名与 @every」开关和一排示例表达式,方言、别名开关、示例表达式与基准输入都折在这一层里,折叠标题会跟着状态写成「· POSIX 5 段 · 基准跟随现在」这样的实际值。
- 改基准时间:默认「跟随现在」,每次推算都取真实当前时刻,页面放着不过期,基准输入框是禁用状态、由工具自己回填,这样页面挂着一小时也不会给你一屏过期的"未来"。要验证任意时刻的行为(比如月初 0 点任务在夏令时切换日的表现),点「钉住此刻」才冻结在你选的那一分钟,再在 datetime-local 里改;改完按钮变成「把钉住的时刻改成现在」,而钉住的具体时刻不跨刷新保存。
- 看逐字段表:每个字段的原始写法逐 token 解释并给出解析后的取值集合,特殊形态(如 15W、6#3)单独列出;右侧「未来触发时刻」先给 6 条,展开折叠看满 12 条,第 7–12 次收在「再看 N 次(第 7–12 次)」折叠里;首屏还有一条「距下次」实时读数,每秒只改它自己那一个节点,不动其它 DOM。用的是浏览器本地时区,跨夏令时不存在的墙钟会标注跳过。基准时间填错或解析不了时,两张表会一起清空,不会留着旧结果和报错同屏。
- @ 别名与 @every:@yearly/@monthly/@weekly/@daily/@hourly/@reboot 和 cronie 的 @every 5m 也认识,可以用开关关掉别名按字面调试。
- 存在本机的状态:表达式、方言、基准模式存在本机 localStorage 的 kc-cron 里,只在本机、不会上传。
常见问题
为什么「几号」和「星期几」一起写会多出触发次数?
vixie-cron 的 crontab(5) 明确写着:当「一个月中的第几天」和「星期几」两个字段都受限制(不是 *)时,任务是按「或」执行的——0 0 13 * 5 表示每月 13 号 00:00 和每周五 00:00 都会跑。只有任一侧写 * 时,才是直觉的「与」。想让任务「只在恰好是周五的 13 号」执行,标准做法是在命令里再判断日期(如 [ "$(date +%u)" = 5 ]),或拆成两条任务分别承担;Quartz 方言干脆要求日与周二选一(另一侧写 ?),没有这条「或」规则。本工具命中该规则时提示条会写明。
Kubernetes CronJob 和 Linux crontab 有什么不一样?
K8s 的 schedule 字段用的是 Go 生态 robfig/cron 库的方言:接受标准 5 段,也接受可选的 6 段(秒在最前)和 @every 1h30m 这类写法,但不支持 Quartz 的 ?/L/W/#。更关键的差异在时区:Linux cron 按系统本地时区,而 CronJob 的 spec.schedule 默认由控制面按 UTC 解释,除非设置 spec.timeZone(1.27 起提供,按 IANA 时区名)。另外 CronJob 有 concurrencyPolicy、startingDeadlineSeconds、错过调度会记 Miss 而不是静默跳过,这些都是 crontab 没有的概念。
为什么定时任务在我容器里总是差 8 小时?
这是最经典的「容器里 cron 时间不对」:绝大多数基础镜像(Debian/Alpine 的精简版)没有配置本地时区,date 输出 UTC,而你的 crontab 是按北京时间写的,于是任务整体早 8 小时。三种修法任选其一:给容器挂 TZ=Asia/Shanghai 环境变量并在镜像里装 tzdata(glibc 与 vixie-cron 新版会读取);写 crontab 时换算成 UTC 时间;或改用 CRON_TZ=Asia/Shanghai 前缀(cronie 支持,Debian 的 vixie 派生版较新也支持)。本工具的触发时刻按浏览器本地时区算,页面上方提示条会写明所在时区,方便对照。