将cron表达式转换为日期/时间格式的SQL查询

将cron表达式转换为日期/时间格式的SQL查询,sql,oracle,cron,Sql,Oracle,Cron,我在Linux主机上安排了一些cron作业。 每个作业都在Oracle数据库表中写入执行日志。该表有一个结果列,可以使用“OK”或“KO”对其进行赋值。该表还有一个timestamp列,该列的值与作业的最后一次执行时间相同。 这样,我对工作的结果很有把握。 现在,我需要确保作业已实际运行。 我有另一个带有作业ID和cron表达式的表,例如: JOB_ID SCHEDULE 102 00 09 * * * 如何编写sql select来对照SCHEDULE字段(

我在Linux主机上安排了一些cron作业。 每个作业都在Oracle数据库表中写入执行日志。该表有一个结果列,可以使用“OK”或“KO”对其进行赋值。该表还有一个timestamp列,该列的值与作业的最后一次执行时间相同。 这样,我对工作的结果很有把握。 现在,我需要确保作业已实际运行。 我有另一个带有作业ID和cron表达式的表,例如:

JOB_ID        SCHEDULE
102           00 09 * * *
如何编写sql select来对照SCHEDULE字段(cron表达式)检查上次执行时间

如果您有任何建议,我将不胜感激。我可以更改我的方法,但我希望在数据库表中使用cron语法

问候
Giova

您可以使用
regexp\u substr
函数从调度元组中提取单个元素。例如,
regexp_substr(schedule,[0-9*]+',1,1)
将提取分钟元素,而
regexp_substr(sched,[0-9*]+',1,2)
将提取小时元素。第四个参数选择所需的元素。然后,您可以使用
提取
TO_CHAR
函数获取时间戳的各个部分以进行比较

with cron(ID, Sched) as (
  select 102, '00 9 * * * *' from dual
), exec(id, ts) as (
  select 102, to_timestamp('2017-11-05 9:00:00', 'yyyy-mm-dd hh24:mi:ss') from dual union all
  select 102, to_timestamp('2017-11-05 9:05:00', 'yyyy-mm-dd hh24:mi:ss') from dual
), c2 as (
select id
     , sched 
     , regexp_substr(sched,'[0-9*]+',1,1) min
     , regexp_substr(sched,'[0-9*]+',1,2) hour
     , regexp_substr(sched,'[0-9*]+',1,3) day
     , regexp_substr(sched,'[0-9*]+',1,4) mon
     , regexp_substr(sched,'[0-9*]+',1,5) wday
     , regexp_substr(sched,'[0-9*]+',1,6) year
  from cron
)
select c2.*
     , exec.ts
     , case when (year = '*' or to_number(to_char(ts,'yyyy')) = to_number(year))
             and (mon  = '*' or to_number(to_char(ts,'mm')  ) = to_number(mon ))
             and (day  = '*' or to_number(to_char(ts,'dd')  ) = to_number(day ))
             and (hour = '*' or to_number(to_char(ts,'hh24')) = to_number(hour))
             and (min  = '*' or to_number(to_char(ts,'mi')  ) = to_number(min ))
             and (wday = '*' or to_number(to_char(ts,'d')   ) = to_number(wday))
            then 'OK'
            else 'KO'
       end Match
  from exec 
  join c2 
    on c2.id = exec.id;

根据需要从case语句中部分或全部移动逻辑表达式,以获得所需的结果。

您可以使用
regexp\u substr
函数从明细表元组中提取单个元素。例如,
regexp_substr(schedule,[0-9*]+',1,1)
将提取分钟元素,而
regexp_substr(sched,[0-9*]+',1,2)
将提取小时元素。第四个参数选择所需的元素。然后,您可以使用
提取
TO_CHAR
函数获取时间戳的各个部分以进行比较

with cron(ID, Sched) as (
  select 102, '00 9 * * * *' from dual
), exec(id, ts) as (
  select 102, to_timestamp('2017-11-05 9:00:00', 'yyyy-mm-dd hh24:mi:ss') from dual union all
  select 102, to_timestamp('2017-11-05 9:05:00', 'yyyy-mm-dd hh24:mi:ss') from dual
), c2 as (
select id
     , sched 
     , regexp_substr(sched,'[0-9*]+',1,1) min
     , regexp_substr(sched,'[0-9*]+',1,2) hour
     , regexp_substr(sched,'[0-9*]+',1,3) day
     , regexp_substr(sched,'[0-9*]+',1,4) mon
     , regexp_substr(sched,'[0-9*]+',1,5) wday
     , regexp_substr(sched,'[0-9*]+',1,6) year
  from cron
)
select c2.*
     , exec.ts
     , case when (year = '*' or to_number(to_char(ts,'yyyy')) = to_number(year))
             and (mon  = '*' or to_number(to_char(ts,'mm')  ) = to_number(mon ))
             and (day  = '*' or to_number(to_char(ts,'dd')  ) = to_number(day ))
             and (hour = '*' or to_number(to_char(ts,'hh24')) = to_number(hour))
             and (min  = '*' or to_number(to_char(ts,'mi')  ) = to_number(min ))
             and (wday = '*' or to_number(to_char(ts,'d')   ) = to_number(wday))
            then 'OK'
            else 'KO'
       end Match
  from exec 
  join c2 
    on c2.id = exec.id;

根据需要将逻辑表达式从case语句中部分或全部移动,以获得所需的结果。

您使用的是哪个数据库?@Sentinel:我使用的是Oracle您使用的是哪个数据库?@Sentinel:我使用的是Oracle非常感谢!我明天试试,我会通知你的。非常感谢!我明天试试,我会通知你的。