1. 程式人生 > 其它 >ASP.NET Core定時之Quartz.NET使用

ASP.NET Core定時之Quartz.NET使用

ASP.NET Core定時之Quartz.NET使用
https://www.cnblogs.com/LaoPaoEr/p/15129899.html

一、什麼是Quartz.NET?

Quartz.NET 是一個功能齊全的開源作業排程系統,可用於從最小的應用程式到大型企業系統。

Quartz.NET是純淨的,它是一個.Net程式集,是非常流行的Java作業排程系統Quartz的C#實現。

二、Quartz.NET可以做什麼?

Quartz.NET很多特徵,如:資料庫支援,叢集,外掛,支援cron-like表示式等等,非常適合在平時的工作中,定時輪詢資料庫同步,定時郵件通知,定時處理資料等。

Quartz.NET允許開發人員根據時間間隔(或天)來排程作業。它實現了作業和觸發器的多對多關係,還能把多個作業與不同的觸發器關聯。

Quartz.NET的應用程式可以重用來自不同事件的作業,還可以為一個事件組合多個作業。

我此次選擇Quartz.Net使用的版本是 3.3.3

這裡強調一點:3.x的版本與2.x的版本使用方式有一定的差別

Quartz.NET官方文件:https://www.quartz-scheduler.net/documentation/quartz-3.x/quick-start.html

三、ASP.NET Core如何使用Quartz.NET?

  1. 首先我們需要建立一個ASP.NET Core web的專案,建立的過程就不展示了,我建立的是API專案,使用傳統三層架構。
  2. 專案建立好後,我們需要在NuGet包管理器中安裝Quartz.AspNetCore
    Quartz.Extensions.DependencyInjection

  3. 與2.x的使用方式不同,因為我使用的版本是3.3.3(此時最新版本)。我們就不像傳統的建立排程中心類。傳統的是定義作業工廠類【ResetJobFactory】,控制中心類【SchedulerCenter】,以及定期工作類【RegularWork】(如下圖)在這就不過多介紹了。
  4. 只需建立一個定期工作類【RegularWork】,並且繼承Quartz.net的IJob介面,I_RegularWork_BLL 能注入到RegularWork內需要UseMicrosoftDependencyInjectionJobFactory.
    ?
    1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44     private readonly I_RegularWork_BLL I_bll;     public RegularWork(I_RegularWork_BLL Ibll)     {         I_bll = Ibll;     }       public Task Execute(IJobExecutionContext context)     {         Input_RoomType model = new Input_RoomType();         model.currentPage = 1;         model.pageSize = 1;         var result = I_bll.getRoomTypeList(model);           return Task.Run(() =>         {             using (StreamWriter sw = new StreamWriter(@"F:/Quartz-NET.txt", true, Encoding.UTF8))             {                sw.WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss:fff =>") + JsonConvert.SerializeObject(result));             }         });     } }     private readonly I_RegularWork_BLL I_bll;     public RegularWork(I_RegularWork_BLL Ibll)     {         I_bll = Ibll;     }       public Task Execute(IJobExecutionContext context)     {         Input_RoomType model = new Input_RoomType();         model.currentPage = 1;         model.pageSize = 1;         var result = I_bll.getRoomTypeList(model);           return Task.Run(() =>         {             using (StreamWriter sw = new StreamWriter(@"F:/Quartz-NET.txt", true, Encoding.UTF8))             {                sw.WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss:fff =>") + JsonConvert.SerializeObject(result));             }         });     } }
  5. Startup.csConfigureServices方法內通過services去註冊RegularWork ?
    1 2 //Quartz的工作單元  services.AddTransient<RegularWork>();
  6. ConfigureServices方法內新增Quartz排程中心。Quartz.Extensions.DependencyInjection提供與Microsoft 依賴注入的整合,雖然Quartz 為作業工廠提供了兩個內建替代方案,可以通過呼叫UseMicrosoftDependencyInjectionJobFactory或UseMicrosoftDependencyInjectionScopedJobFactory(已棄用)進行配置。

    從 Quartz.NET 3.3.2 開始,預設作業工廠生成的所有作業都是作用域作業,不應再使用UseMicrosoftDependencyInjectionScopedJobFactory。

    AddJob-新增一個工作單元;StartNow表示作業現在就開始執行;

    WithInterval用於執行時間策略執行規則;

    TimeSpan.FromSeconds表示執行的時間間隔,秒為單位;RepeatForever代表重複工作,可以用WithRepeatCount(5)代替RepeatForever;WithRepeatCount(5)代表執行5次

    ?
    1 2 });            });           
  7. ConfigureServices方法內新增新增Quartz服務 ?
    1 2 3 4 5 6 // ASP.NET核心託管-新增Quartz伺服器  services.AddQuartzServer(options =>  {      // 關閉時,我們希望作業正常完成      options.WaitForJobsToComplete = false;  });

    完整程式碼如下

    ?
    1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 //Quartz的工作單元  services.AddTransient<RegularWork>();  //Quartz排程中心  services.AddQuartz(q =>  {      //用於注入      q.UseMicrosoftDependencyInjectionJobFactory();      // 基本Quartz排程器、作業和觸發器配置      var jobKey = new JobKey("RegularWork", "regularWorkGroup");      q.AddJob<RegularWork>(jobKey, j => j          .WithDescription("My regular work")      );      q.AddTrigger(t => t          .WithIdentity("Trigger")          .ForJob(jobKey)          .StartNow()          .WithSimpleSchedule(x => x.WithInterval(TimeSpan.FromSeconds(10))//開始秒數 10s          .WithRepeatCount(5))//持續工作          .WithDescription("My regular work trigger")      );    });  // ASP.NET核心託管-新增Quartz服務  services.AddQuartzServer(options =>  {      // 關閉時,我們希望作業正常完成      options.WaitForJobsToComplete = false;  }); //Quartz的工作單元  services.AddTransient<RegularWork>();  //Quartz排程中心  services.AddQuartz(q =>  {      //用於注入      q.UseMicrosoftDependencyInjectionJobFactory();      // 基本Quartz排程器、作業和觸發器配置      var jobKey = new JobKey("RegularWork", "regularWorkGroup");      q.AddJob<RegularWork>(jobKey, j => j          .WithDescription("My regular work")      );      q.AddTrigger(t => t          .WithIdentity("Trigger")          .ForJob(jobKey)          .StartNow()          .WithSimpleSchedule(x => x.WithInterval(TimeSpan.FromSeconds(10))//開始秒數 10s          .WithRepeatCount(5))//持續工作          .WithDescription("My regular work trigger")      );    });  // ASP.NET核心託管-新增Quartz服務  services.AddQuartzServer(options =>  {      // 關閉時,我們希望作業正常完成      options.WaitForJobsToComplete = false;  });
  8.  這時候我們啟動專案,定期工作開始執行。這時候的注入是有效的,查詢資料後結果列印在F盤下的Quartz-NET.txt檔案內(如下圖)。

四、Quartz的cron表示式

官方的文件介紹:https://www.quartz-scheduler.net/documentation/quartz-2.x/tutorial/crontrigger.html#format

由7段構成:秒 分 時 日 月 星期 年(可選)
"-" :表示範圍  MON-WED表示星期一到星期三
"," :表示列舉 MON,WEB表示星期一和星期三
"*" :表是“每”,每月,每天,每週,每年等
"/" :表示增量:0/15(處於分鐘段裡面) 每15分鐘,在0分以後開始,3/20 每20分鐘,從3分鐘以後開始
"?" :只能出現在日,星期段裡面,表示不指定具體的值
"L" :只能出現在日,星期段裡面,是Last的縮寫,一個月的最後一天,一個星期的最後一天(星期六)
"W" :表示工作日,距離給定值最近的工作日
"#" :表示一個月的第幾個星期幾,例如:"6#3"表示每個月的第三個星期五(1=SUN...6=FRI,7=SAT)

Expression Meaning
0 0 12 * * ? 每天中午12點觸發
0 15 10 ? * * 每天上午10:15觸發
0 15 10 * * ? 每天上午10:15觸發
0 15 10 * * ? * 每天上午10:15觸發
0 15 10 * * ? 2005 2005年的每天上午10:15觸發
0 * 14 * * ? 在每天下午2點到下午2:59期間的每1分鐘觸發
0 0/5 14 * * ? 在每天下午2點到下午2:55期間的每5分鐘觸發
0 0/5 14,18 * * ? 在每天下午2點到2:55期間和下午6點到6:55期間的每5分鐘觸發
0 0-5 14 * * ? 在每天下午2點到下午2:05期間的每1分鐘觸發
0 10,44 14 ? 3 WED 每年三月的星期三的下午2:10和2:44觸發
0 15 10 ? * MON-FRI 週一至週五的上午10:15觸發
0 15 10 15 * ? 每月15日上午10:15觸發
0 15 10 L * ? 每月最後一日的上午10:15觸發
0 15 10 L-2 * ? Fire at 10:15am on the 2nd-to-last last day of every month
0 15 10 ? * 6L 每月的最後一個星期五上午10:15觸發
0 15 10 ? * 6L Fire at 10:15am on the last Friday of every month
0 15 10 ? * 6L 2002-2005 2002年至2005年的每月的最後一個星期五上午10:15觸發
0 15 10 ? * 6#3 每月的第三個星期五上午10:15觸發
0 0 12 1/5 * ? Fire at 12pm (noon) every 5 days every month, starting on the first day of the month.
0 11 11 11 11 ? Fire every November 11th at 11:11am.

 

一、什麼是Quartz.NET?

Quartz.NET 是一個功能齊全的開源作業排程系統,可用於從最小的應用程式到大型企業系統。

Quartz.NET是純淨的,它是一個.Net程式集,是非常流行的Java作業排程系統Quartz的C#實現。

二、Quartz.NET可以做什麼?

Quartz.NET很多特徵,如:資料庫支援,叢集,外掛,支援cron-like表示式等等,非常適合在平時的工作中,定時輪詢資料庫同步,定時郵件通知,定時處理資料等。

Quartz.NET允許開發人員根據時間間隔(或天)來排程作業。它實現了作業和觸發器的多對多關係,還能把多個作業與不同的觸發器關聯。

Quartz.NET的應用程式可以重用來自不同事件的作業,還可以為一個事件組合多個作業。

我此次選擇Quartz.Net使用的版本是 3.3.3

這裡強調一點:3.x的版本與2.x的版本使用方式有一定的差別

Quartz.NET官方文件:https://www.quartz-scheduler.net/documentation/quartz-3.x/quick-start.html

三、ASP.NET Core如何使用Quartz.NET?

  1. 首先我們需要建立一個ASP.NET Core web的專案,建立的過程就不展示了,我建立的是API專案,使用傳統三層架構。
  2. 專案建立好後,我們需要在NuGet包管理器中安裝Quartz.AspNetCoreQuartz.Extensions.DependencyInjection

  3. 與2.x的使用方式不同,因為我使用的版本是3.3.3(此時最新版本)。我們就不像傳統的建立排程中心類。傳統的是定義作業工廠類【ResetJobFactory】,控制中心類【SchedulerCenter】,以及定期工作類【RegularWork】(如下圖)在這就不過多介紹了。
  4. 只需建立一個定期工作類【RegularWork】,並且繼承Quartz.net的IJob介面,I_RegularWork_BLL 能注入到RegularWork內需要UseMicrosoftDependencyInjectionJobFactory. ?
    1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44     private readonly I_RegularWork_BLL I_bll;     public RegularWork(I_RegularWork_BLL Ibll)     {         I_bll = Ibll;     }       public Task Execute(IJobExecutionContext context)     {         Input_RoomType model = new Input_RoomType();         model.currentPage = 1;         model.pageSize = 1;         var result = I_bll.getRoomTypeList(model);           return Task.Run(() =>         {             using (StreamWriter sw = new StreamWriter(@"F:/Quartz-NET.txt", true, Encoding.UTF8))             {                sw.WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss:fff =>") + JsonConvert.SerializeObject(result));             }         });     } }     private readonly I_RegularWork_BLL I_bll;     public RegularWork(I_RegularWork_BLL Ibll)     {         I_bll = Ibll;     }       public Task Execute(IJobExecutionContext context)     {         Input_RoomType model = new Input_RoomType();         model.currentPage = 1;         model.pageSize = 1;         var result = I_bll.getRoomTypeList(model);           return Task.Run(() =>         {             using (StreamWriter sw = new StreamWriter(@"F:/Quartz-NET.txt", true, Encoding.UTF8))             {                sw.WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss:fff =>") + JsonConvert.SerializeObject(result));             }         });     } }
  5. Startup.csConfigureServices方法內通過services去註冊RegularWork ?
    1 2 //Quartz的工作單元  services.AddTransient<RegularWork>();
  6. ConfigureServices方法內新增Quartz排程中心。Quartz.Extensions.DependencyInjection提供與Microsoft 依賴注入的整合,雖然Quartz 為作業工廠提供了兩個內建替代方案,可以通過呼叫UseMicrosoftDependencyInjectionJobFactory或UseMicrosoftDependencyInjectionScopedJobFactory(已棄用)進行配置。

    從 Quartz.NET 3.3.2 開始,預設作業工廠生成的所有作業都是作用域作業,不應再使用UseMicrosoftDependencyInjectionScopedJobFactory。

    AddJob-新增一個工作單元;StartNow表示作業現在就開始執行;

    WithInterval用於執行時間策略執行規則;

    TimeSpan.FromSeconds表示執行的時間間隔,秒為單位;RepeatForever代表重複工作,可以用WithRepeatCount(5)代替RepeatForever;WithRepeatCount(5)代表執行5次

    ?
    1 2 });            });           
  7. ConfigureServices方法內新增新增Quartz服務 ?
    1 2 3 4 5 6 // ASP.NET核心託管-新增Quartz伺服器  services.AddQuartzServer(options =>  {      // 關閉時,我們希望作業正常完成      options.WaitForJobsToComplete = false;  });

    完整程式碼如下

    ?
    1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 //Quartz的工作單元  services.AddTransient<RegularWork>();  //Quartz排程中心  services.AddQuartz(q =>  {      //用於注入      q.UseMicrosoftDependencyInjectionJobFactory();      // 基本Quartz排程器、作業和觸發器配置      var jobKey = new JobKey("RegularWork", "regularWorkGroup");      q.AddJob<RegularWork>(jobKey, j => j          .WithDescription("My regular work")      );      q.AddTrigger(t => t          .WithIdentity("Trigger")          .ForJob(jobKey)          .StartNow()          .WithSimpleSchedule(x => x.WithInterval(TimeSpan.FromSeconds(10))//開始秒數 10s          .WithRepeatCount(5))//持續工作          .WithDescription("My regular work trigger")      );    });  // ASP.NET核心託管-新增Quartz服務  services.AddQuartzServer(options =>  {      // 關閉時,我們希望作業正常完成      options.WaitForJobsToComplete = false;  }); //Quartz的工作單元  services.AddTransient<RegularWork>();  //Quartz排程中心  services.AddQuartz(q =>  {      //用於注入      q.UseMicrosoftDependencyInjectionJobFactory();      // 基本Quartz排程器、作業和觸發器配置      var jobKey = new JobKey("RegularWork", "regularWorkGroup");      q.AddJob<RegularWork>(jobKey, j => j          .WithDescription("My regular work")      );      q.AddTrigger(t => t          .WithIdentity("Trigger")          .ForJob(jobKey)          .StartNow()          .WithSimpleSchedule(x => x.WithInterval(TimeSpan.FromSeconds(10))//開始秒數 10s          .WithRepeatCount(5))//持續工作          .WithDescription("My regular work trigger")      );    });  // ASP.NET核心託管-新增Quartz服務  services.AddQuartzServer(options =>  {      // 關閉時,我們希望作業正常完成      options.WaitForJobsToComplete = false;  });
  8.  這時候我們啟動專案,定期工作開始執行。這時候的注入是有效的,查詢資料後結果列印在F盤下的Quartz-NET.txt檔案內(如下圖)。

四、Quartz的cron表示式

官方的文件介紹:https://www.quartz-scheduler.net/documentation/quartz-2.x/tutorial/crontrigger.html#format

由7段構成:秒 分 時 日 月 星期 年(可選)
"-" :表示範圍  MON-WED表示星期一到星期三
"," :表示列舉 MON,WEB表示星期一和星期三
"*" :表是“每”,每月,每天,每週,每年等
"/" :表示增量:0/15(處於分鐘段裡面) 每15分鐘,在0分以後開始,3/20 每20分鐘,從3分鐘以後開始
"?" :只能出現在日,星期段裡面,表示不指定具體的值
"L" :只能出現在日,星期段裡面,是Last的縮寫,一個月的最後一天,一個星期的最後一天(星期六)
"W" :表示工作日,距離給定值最近的工作日
"#" :表示一個月的第幾個星期幾,例如:"6#3"表示每個月的第三個星期五(1=SUN...6=FRI,7=SAT)

Expression Meaning
0 0 12 * * ? 每天中午12點觸發
0 15 10 ? * * 每天上午10:15觸發
0 15 10 * * ? 每天上午10:15觸發
0 15 10 * * ? * 每天上午10:15觸發
0 15 10 * * ? 2005 2005年的每天上午10:15觸發
0 * 14 * * ? 在每天下午2點到下午2:59期間的每1分鐘觸發
0 0/5 14 * * ? 在每天下午2點到下午2:55期間的每5分鐘觸發
0 0/5 14,18 * * ? 在每天下午2點到2:55期間和下午6點到6:55期間的每5分鐘觸發
0 0-5 14 * * ? 在每天下午2點到下午2:05期間的每1分鐘觸發
0 10,44 14 ? 3 WED 每年三月的星期三的下午2:10和2:44觸發
0 15 10 ? * MON-FRI 週一至週五的上午10:15觸發
0 15 10 15 * ? 每月15日上午10:15觸發
0 15 10 L * ? 每月最後一日的上午10:15觸發
0 15 10 L-2 * ? Fire at 10:15am on the 2nd-to-last last day of every month
0 15 10 ? * 6L 每月的最後一個星期五上午10:15觸發
0 15 10 ? * 6L Fire at 10:15am on the last Friday of every month
0 15 10 ? * 6L 2002-2005 2002年至2005年的每月的最後一個星期五上午10:15觸發
0 15 10 ? * 6#3 每月的第三個星期五上午10:15觸發
0 0 12 1/5 * ? Fire at 12pm (noon) every 5 days every month, starting on the first day of the month.
0 11 11 11 11 ? Fire every November 11th at 11:11am.