Net作業調度(三) — Quartz.Net進階


介紹

前面介紹Quartz.Net的基本用法,但在實際應用中,往往有更多的特性需求,比如記錄job執行的執行歷史,發郵件等。

閱讀目錄

  1. Quartz.Net插件
  2. TriggerListener,JobListener
  3. Cron表達式
  4. Quartz.Net線程池
  5. 總結

Quartz.Net插件

     Quartz.net 自身提供了一個插件接口(ISchedulerPlugin)用來增加附加功能,看下官方定義:

  public interface ISchedulerPlugin
    {
        void Initialize(string pluginName, IScheduler sched);
       //關閉調度器
        void Shutdown();
        //插件啟動
        void Start();
    }

 繼承接口,實現自己的插件。

 public class MyPlugin : ISchedulerPlugin
    {
        public void  Initialize(string pluginName, IScheduler sched)
        {
            Console.WriteLine("實例化");
        }
        public  void Start()
        {
             Console.WriteLine("啟動");
        }
        public  void Shutdown()
        {
            Console.WriteLine("關閉");
        }
    }

  主函數里面配置要實現的插件,注釋部分,一句話搞定。

static void Main(string[] args)
        {
            var properties = new NameValueCollection();
           //MyPlugin 自定義名稱。    "命名空間.類名,程序名稱"
            properties["quartz.plugin.MyPlugin.type"] = "QuartzDemo3.MyPlugin,QuartzDemo3"; 

            var schedulerFactory = new StdSchedulerFactory(properties);
            var scheduler = schedulerFactory.GetScheduler();

            var job = JobBuilder.Create<HelloJob>()
                .WithIdentity("myJob", "group1")
                .Build();

            var trigger = TriggerBuilder.Create()
                                .WithIdentity("mytrigger", "group1")
                                .WithCronSchedule("/2 * * ? * *")
                                .Build();

            scheduler.ScheduleJob(job, trigger);
            scheduler.Start();
            Thread.Sleep(6000);
            scheduler.Shutdown(true);
            Console.ReadLine();

        }

運行結果如下:

 

TriggerListener,JobListener

這2個是對觸發器和job本身的行為監聽器,這樣更好方便跟蹤Job的狀態及運行情況。  

ITriggerListener是官方定義的接口,這里我們直接繼承實現。 

public class MyTriggerListener : ITriggerListener
    {
        private string name;

        public void TriggerComplete(ITrigger trigger, IJobExecutionContext context, SchedulerInstruction triggerInstructionCode)
        {
            Console.WriteLine("job完成時調用");
        }
        public void TriggerFired(ITrigger trigger, IJobExecutionContext context)
        {
            Console.WriteLine("job執行時調用");
        }
        public void TriggerMisfired(ITrigger trigger)
        {
            Console.WriteLine("錯過觸發時調用(例:線程不夠用的情況下)");
        }
        public bool VetoJobExecution(ITrigger trigger, IJobExecutionContext context)
        {
            //Trigger觸發后,job執行時調用本方法。true即否決,job后面不執行。
            return false;
        }
        public string Name { get { return name; } set { name = value; } }
    }

主函數添加:

           //添加監聽器到指定的trigger
            scheduler.ListenerManager.AddTriggerListener(myJobListener, KeyMatcher<TriggerKey>.KeyEquals(new TriggerKey("mytrigger", "group1")));

            ////添加監聽器到指定分類的所有監聽器。
            //scheduler.ListenerManager.AddTriggerListener(myJobListener, GroupMatcher<TriggerKey>.GroupEquals("myJobGroup"));

            ////添加監聽器到指定分類的所有監聽器。
            //scheduler.ListenerManager.AddTriggerListener(myJobListener, GroupMatcher<TriggerKey>.GroupEquals("myJobGroup"));

           ////添加監聽器到指定的2個分組。
            //scheduler.ListenerManager.AddTriggerListener(myJobListener, GroupMatcher<TriggerKey>.GroupEquals("myJobGroup"), GroupMatcher<TriggerKey>.GroupEquals("myJobGroup2"));

            ////添加監聽器到所有的觸發器上。
            //scheduler.ListenerManager.AddTriggerListener(myJobListener, GroupMatcher<TriggerKey>.AnyGroup());

            scheduler.Start();

JobListener同理,這里不多做描述。

Cron表達式

quartz中的cron表達式和Linux下的很類似,比如 "/5 * * ? * * *"  這樣的7位表達式,最后一位非必選。

表達式從左到右,依此是秒、分、時、月第幾天、月、周幾、年。下面表格是要遵守的規范:

字段名 允許的值 允許的特殊字符
Seconds 0-59 , - * /
Minutes 0-59 , - * /
Hours 0-23 , - * /
Day of month 1-31 , - * ? / L W
Month 1-12 or JAN-DEC , - * /
Day of week 1-7 or SUN-SAT , - * ? / L #
Year 空, 1970-2099 , - * /

 

 

 

 

 

 

特殊字符 解釋
, 或的意思。例:分鍾位 5,10  即第5分鍾或10分都觸發。 
/ a/b。 a:代表起始時間,b頻率時間。 例; 分鍾位  3/5,  從第三分鍾開始,每5分鍾執行一次。
* 頻率。 即每一次波動。    例;分鍾位 *  即表示每分鍾 
- 區間。  例: 分鍾位   5-10 即5到10分期間。 
? 任意值 。   即每一次波動。只能用在DayofMonth和DayofWeek,二者沖突。指定一個另一個一個要用?
L 表示最后。 只能用在DayofMonth和DayofWeek,4L即最后一個星期三
W 工作日。  表示最后。 只能用在DayofWeek
# 4#2。 只能用DayofMonth。 某月的第二個星期三  

 

 

 

 

 

 

 

 

 

 

實例介紹

”0 0 10,14,16 * * ?"    每天10點,14點,16點 觸發。

"0 0/5 14,18 * * ?"    每天14點或18點中,每5分鍾觸發 。

"0 4/15 14-18 * * ?"       每天14點到18點期間,  從第四分鍾觸發,每15分鍾一次。

"0 15 10 ? * 6L"        每月的最后一個星期五上午10:15觸發。

Quartz.Net線程池

線程池數量設置:

properties["quartz.threadPool.threadCount"] = "5";  

這個線程池的設置,是指同時間,調度器能執行Job的最大數量。

quartz是用每個線程跑一個job。上面的設置可以解釋是job並發時能執行5個job,剩下的job如果觸發時間恰好到了,當前job會進入暫停狀態,直到有可用的線程。

如果在指定的時間范圍依舊沒有可用線程,會觸發misfired時間。

quartz 提供了IThreadPool接口,也可以用自定義線程池來實現。

配置如下:

properties["quartz.threadPool.type"] = "Quartz.Simpl.SimpleThreadPool, Quartz"; 

一般來說作業調度很少並發觸發大量job,如果有上百個JOB,可在服務器承受范圍內適量增加線程數量。     

總結

官方有LoggingTriggerHistoryPlugin,LoggingJobHistoryPlugin  已實現的,觸發器和job歷史記錄的插件。

Quartz.Plugin 命名空間下有官方實現的其他一些插件,也可以自己增加擴展。

quartz中監聽器還有SchedulerListener,使用方法基本一樣。 

本文基於自用經驗和官方文檔代碼來寫的,部分是直接翻譯的。 

Quartz.Net官方教程http://www.quartz-scheduler.net/documentation/quartz-2.x/tutorial/index.html

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM