天天看點

Quartz.NET開源作業排程架構系列(二):CronTrigger

  CronTriggers比SimpleTrigger更加的靈活和有用,對于比較複雜的任務觸發規則。例如"每個星期天的晚上12:00"進行備份任務,SimpleTrigger就不能勝任,隻能選擇CronTriggers。利用CronTrigger, 你不但能實作在"每個星期天的晚上12:00"進行備份的任務。還可以執行  "在每個星期一/星期三/星期五的上午9:00到10:00期間每隔5 分鐘"進行某個自動化任務。

1 Cron Expressions

  Cron-Expressions 是使用者配置執行個體化的CronTrigger. Cron-Expressions是一個6個或者7個字元的字元串表達式, 每一個字元都表示一個具體的含義并且有取值範圍. 每個字元用空格進行分隔,其表達的意義為(從左到右):

Quartz.NET開源作業排程架構系列(二):CronTrigger

  一般來說Cron-Expressions 以6位居多,年一般省略.上圖的中每個字元的描述為 字元的意義+取值範圍(用[])+可用的特殊字元({}).例如  秒[0-59] { , - * /}就代表第一個字元是秒,取值範圍是0-59,同時可用的特殊字元為 , - * /  例如"0  15  10 ?  *  6L"代表的意義就是每月最後一個星期五的10:15. 下面介紹一下特殊字元的含義:

特殊字元 含義
* 所有值(all values)
? 沒有具體的值(no specific value)
- 範圍 0-10
, 附加值 1,2,5
L 在不同的字元位置代表的意義不同,"L" 在月天數段代表每月最後一天;如果單獨出現在星期段,代表7,就是星期最後一天周六(英文習慣用法).
W 給定日期最近的(周一到周五). 月天數段"15W",表示離每月第15天最近的工作日
# 月份的第多少天,"6#3" 表示月份中第三個星期5(6 = 周五 and "#3" =在月份中第三個).

2 常見的表達式

   下面給出一些常見的Cron-Expressions示例:

表達式
0 0 12 * * ? 每天12pm啟動
0 15 10 ? * * 每天10:15am啟動
0 15 10 * * ?
0 15 10 * * ? *
0 15 10 * * ? 2005  在 2005年每天10:15am啟動
0 * 14 * * ? 每天在 2pm到2:59pm之間的每分鐘進行啟動
0 0/5 14 * * ? 每天在 2pm到2:55pm之間的每5分鐘進行啟動
0 0/5 14,18 * * ? 每天在 2pm到2:55pm和6pm到6:55pm之間的每5分鐘進行啟動
0 0-5 14 * * ? 每天在 2pm到2:05pm之間的每分鐘進行啟動
0 10,44 14 ? 3 WED 每個三月份的星期三的2:10pm到 2:44pm進行啟動
0 15 10 ? * MON-FRI 每個星期一到星期五的10:15am進行啟動
0 15 10 15 * ? 每個月第15天的10:15am進行啟動
0 15 10 L * ? 每個月最後一天的10:15am進行啟動
0 15 10 L-2 * ? 每個月第二天到最後一天的10:15am進行啟動
0 15 10 ? * 6L 每月最後一個星期五的10:15am進行啟動
0/1 * * * * ?      
每秒進行啟動
0 15 10 ? * 6L 2002-2005 從2002年到2005年的每月最後一個星期五的10:15am進行啟動
0 15 10 ? * 6#3 每月第三個星期五的10:15am進行啟動
0 0 12 1/5 * ? 從每月第一天開始,每隔5天的12pm進行啟動
0 11 11 11 11 ? 每年11月11日的11:11am進行啟動 

3 CronTrigger示例

由上面的常見表達式我們知道表達式 "0/1 * * * * ?"代表了每秒執行 , 其CronTrigger定義如下:

ITrigger trigger = TriggerBuilder.Create()
.WithIdentity("cronTrigger1", "SimpleGroup")
.WithCronSchedule("0/1 * * * * ?", x => x
    .WithMisfireHandlingInstructionFireAndProceed())
.ForJob("HelloJob", "SimpleGroup")
.Build();      

 也可以用下面的方法進行定義(注意預設時間不是系統時間-中原標準時間,是以如果列印出Job第一次列印的時間不是正确的時間,但是好像不影響使用):

//定義job
IJobDetail job3 = JobBuilder.Create<ColorJob>()
.WithIdentity("job3", "group1")
.Build();
//定義cronTrigger
ICronTrigger cronTrigger = (ICronTrigger)TriggerBuilder.Create()
        .WithIdentity("cronTrigger", "group1")
        .WithCronSchedule("0/20 * * * * ?", x => x
        .InTimeZone(TimeZoneInfo.FindSystemTimeZoneById("China Standard Time")))
        .Build();
//預設開始時間
DateTimeOffset scheduleTime3 = sched.ScheduleJob(job3, cronTrigger);
//轉換到本地時間(中原標準時間)
DateTimeOffset dt=  scheduleTime3.ToLocalTime();//
//中原標準時間為預設時間+8小時
DateTimeOffset scheduleTimeChina = scheduleTime3.AddHours(8);
//傳回Cron Expression
string cronExpression = cronTrigger.CronExpressionString;      

如果在定義的時間規則下,我想排除一些日期,那麼如何實作呢?用ModifiedByCalendar即可實作:

//排除的日期
HolidayCalendar cal = new HolidayCalendar();
DateTime dt排除 = new DateTime(2015, 12, 1);
cal.AddExcludedDate(dt排除)
sched.AddCalendar("myHolidayCalendar", cal, false, true);
 //定義job
IJobDetail job3 = JobBuilder.Create<ColorJob>()
 .WithIdentity("job3", "group1")
 .Build();
//定義cronTrigger
ICronTrigger cronTrigger = (ICronTrigger)TriggerBuilder.Create()
     .WithIdentity("cronTrigger", "group1")
     .WithCronSchedule("0/20 * * * * ?", x => x
     .InTimeZone(TimeZoneInfo.FindSystemTimeZoneById("China Standard Time")))
     .ModifiedByCalendar("myHolidayCalendar")
     .Build();
//預設開始時間
DateTimeOffset scheduleTime3 = sched.ScheduleJob(job3, cronTrigger);
 //轉換到本地時間(中原標準時間)
//  2015-12-02 00:00:00 +08:00 不包含 2015-12-01
DateTimeOffset dt = scheduleTime3.ToLocalTime();
 //中原標準時間為預設時間+8小時
DateTimeOffset scheduleTimeChina = scheduleTime3.AddHours(8);
//傳回Cron Expression
string cronExpression = cronTrigger.CronExpressionString;      

繼續閱讀