Quartz.Net在windows服務中的使用

寫在前面

這幾天在弄一個項目,須要定時抓取一些數據,當時也想直接用timer算了。由於以前也弄過這樣的項目,可是一想,已經用過了,再去使用同一種思路,未免太乏味了。就換了一種新玩法。這裏將以前看到的一篇文章中提出的一個思路,在這個項目中實踐了一下,發現樂在其中。html

Quarzt.net

[轉]C#建立服務及使用程序自動安裝服務,.NET建立一個便是可執行程序又是Windows服務的exewindows

這篇文章,給了一種好玩的方式,而且本身也實踐了一下,並且也確確實實在項目中用到了。app

簡單一個demo,先熟悉如何使用Quartz.NETide

關於如何windows service的內容,這裏再也不贅述,一搜一大堆。函數

首先引入lib中的dll。post

 1 using System;
 2 using System.Collections.Generic;
 3 using System.ComponentModel;
 4 using System.Data;
 5 using System.Diagnostics;
 6 using System.Linq;
 7 using System.ServiceProcess;
 8 using System.Text;
 9 using System.Threading.Tasks;
10 using Quartz;
11 using Quartz.Job;
12 using Common.Logging;
13 using Quartz.Impl;
14 using Statistics.WindowService.JobManager;
15 using System.Configuration;
16 namespace Statistics.WindowService
17 {
18     /// <summary>
19     /// 數據同步windows服務
20     /// </summary>
21     public partial class SyncDataService : ServiceBase
22     {
23         private readonly ILog logger;
24         private IScheduler scheduler;
25         //時間間隔
26         private readonly string StrCron = ConfigurationManager.AppSettings["cron"] == null ? "* 10 * * * ?" : ConfigurationManager.AppSettings["cron"];
27         /// <summary>
28         ///構造函數
29         /// </summary>
30         public SyncDataService()
31         {
32             InitializeComponent();
33             //初始化
34             logger = LogManager.GetLogger(this.GetType());
35             //新建一個調度器工工廠
36             ISchedulerFactory factory = new StdSchedulerFactory();
37             //使用工廠生成一個調度器
38             scheduler = factory.GetScheduler();
39 
40         }
41         /// <summary>
42         /// 服務開啓
43         /// </summary>
44         /// <param name="args"></param>
45         protected override void OnStart(string[] args)
46         {
47             if (!scheduler.IsStarted)
48             {
49                 //啓動調度器
50                 scheduler.Start();
51                 //新建一個任務
52                 IJobDetail job = JobBuilder.Create<AppLogJob>().WithIdentity("AppLogJob", "AppLogJobGroup").Build();
53                 //新建一個觸發器
54                 ITrigger trigger = TriggerBuilder.Create().StartNow().WithCronSchedule(StrCron).Build();
55                 //將任務與觸發器關聯起來放到調度器中
56                 scheduler.ScheduleJob(job, trigger);
57                 logger.Info("Quarzt 數據同步服務開啓");
58             }
59 
60         }
61         /// <summary>
62         /// 服務中止
63         /// </summary>
64         protected override void OnStop()
65         {
66             if (!scheduler.IsShutdown)
67             {
68                 scheduler.Shutdown();
69             }
70         }
71         /// <summary>
72         /// 暫停
73         /// </summary>
74         protected override void OnPause()
75         {
76             scheduler.PauseAll();
77             base.OnPause();
78         }
79         /// <summary>
80         /// 繼續
81         /// </summary>
82         protected override void OnContinue()
83         {
84             scheduler.ResumeAll();
85             base.OnContinue();
86         }
87     }
88 }

時間間隔採用的是cron表達式,關於cron表達式的定義,能夠參考這篇文章:http://www.cnblogs.com/linjiqin/archive/2013/07/08/3178452.htmlui

定義Job,能夠經過自定義類,而且實現IJob接口,能夠很方便的定義一個任務,而且也很是容易擴展。this

 1 using System;  2 using System.Collections.Generic;  3 using System.Linq;  4 using System.Text;  5 using System.Threading.Tasks;  6 using Quartz;  7 using Quartz.Job;  8 namespace Statistics.WindowService.JobManager  9 { 10 /// <summary> 11 /// 同步applog任務 12 /// </summary> 13 public class AppLogJob:IJob 14  { 15 //使用Common.Logging.dll日誌接口實現日誌記錄 16 private static readonly Common.Logging.ILog logger = Common.Logging.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 17 /// <summary> 18 /// 定時任務執行 19 /// </summary> 20 /// <param name="context"></param> 21 public void Execute(IJobExecutionContext context) 22  { 23 try 24  { 25 logger.Info("AppLogJob 任務開始運行"); 26 27 for (int i = 0; i < 10; i++) 28  { 29 logger.InfoFormat("AppLogJob 正在運行{0}", i); 30  } 31 32 logger.Info("AppLogJob 任務運行結束"); 33  } 34 catch (Exception ex) 35  { 36 logger.Error("AppLogJob 運行異常", ex); 37  } 38  } 39  } 40 }

修改windows 服務的入口程序:url

 1 using System;
 2 using System.Collections.Generic;
 3 using System.Diagnostics;
 4 using System.Linq;
 5 using System.ServiceProcess;
 6 using System.Text;
 7 using System.Threading.Tasks;
 8 
 9 namespace Statistics.WindowService
10 {
11     static class Program
12     {
13         /// <summary>
14         /// 應用程序的主入口點。
15         /// </summary>
16         static void Main(string[] args)
17         {
18             //若是傳遞了參數 s 就啓動服務
19             if (args.Length > 0 && args[0] == "s")
20             {
21                 ServiceBase[] ServicesToRun;
22                 ServicesToRun = new ServiceBase[] { new SyncDataService() };
23                 ServiceBase.Run(ServicesToRun);
24             }
25             else
26             {
27                 Console.WriteLine("這是Windows應用程序");
28                 Console.WriteLine("請選擇,[1]安裝服務 [2]卸載服務 [3]退出");
29                 var rs = int.Parse(Console.ReadLine());
30                 string strServiceName = "syncService[數據同步服務]";
31                 switch (rs)
32                 {
33                     case 1:
34                         //取當前可執行文件路徑,加上"s"參數,證實是從windows服務啓動該程序
35                         var path = Process.GetCurrentProcess().MainModule.FileName + " s";
36                         Process.Start("sc", "create " + strServiceName + " binpath= \"" + path + "\" displayName= " + strServiceName + " start= auto");
37                         Console.WriteLine("安裝成功");
38                         Console.Read();
39                         break;
40                     case 2:
41                         Process.Start("sc", "delete " + strServiceName + "");
42                         Console.WriteLine("卸載成功");
43                         Console.Read();
44                         break;
45                     case 3: break;
46                 }
47 
48             }
49 
50 
51         }
52     }
53 }

修改app.configspa

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <configSections>
    <section name="quartz" type="System.Configuration.NameValueSectionHandler, System, Version=1.0.5000.0,Culture=neutral, PublicKeyToken=b77a5c561934e089"/>
    <section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler, log4net"/>
    <sectionGroup name="common">
      <section name="logging" type="Common.Logging.ConfigurationSectionHandler, Common.Logging"/>
    </sectionGroup>
  </configSections>
  <common>
    <logging>
      <factoryAdapter type="Common.Logging.Log4Net.Log4NetLoggerFactoryAdapter, Common.Logging.Log4net">
        <arg key="configType" value="INLINE"/>
      </factoryAdapter>
    </logging>
  </common>
  <log4net>
    <appender name="InfoFileAppender" type="log4net.Appender.RollingFileAppender">
      <file value="log/" />
      <appendToFile value="true" />
      <param name="DatePattern" value="yyyyMMdd&quot;.txt&quot;" />
      <rollingStyle value="Date" />
      <maxSizeRollBackups value="100" />
      <maximumFileSize value="1024KB" />
      <staticLogFileName value="false" />
      <Encoding value="UTF-8" />
      <filter type="log4net.Filter.LevelRangeFilter">
        <param name="LevelMin" value="INFO" />
        <param name="LevelMax" value="INFO" />
      </filter>
      <layout type="log4net.Layout.PatternLayout">
        <conversionPattern value="%date %-5level %logger  - %message%newline" />
      </layout>
    </appender>
    <appender name="ErrorFileAppender" type="log4net.Appender.RollingFileAppender">
      <file value="log/error.txt" />
      <appendToFile value="true" />
      <rollingStyle value="Size" />
      <maxSizeRollBackups value="100" />
      <maximumFileSize value="10240KB" />
      <staticLogFileName value="true" />
      <Encoding value="UTF-8" />
      <filter type="log4net.Filter.LevelRangeFilter">
        <param name="LevelMin" value="WARN" />
        <param name="LevelMax" value="FATAL" />
      </filter>
      <layout type="log4net.Layout.PatternLayout">
        <conversionPattern value="%date %-5level %logger - %message%newline" />
      </layout>
    </appender>
    <root>
      <level value="INFO" />
      <appender-ref ref="InfoFileAppender" />
      <appender-ref ref="ErrorFileAppender" />
    </root>
  </log4net>
  <startup>
    <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
  </startup>
  <appSettings>
    <!--每五分鐘執行一次-->
    <add key="cron" value="* 5 * * * ?"/>
  </appSettings>
</configuration>

弄這個demo的目的是先讓Quartz.net
找到bin目錄下的exe文件,右鍵以管理員身份運行。

查看生成的log日誌

 1 2015-05-22 10:43:23,115 INFO  Quartz.Impl.StdSchedulerFactory  - Default Quartz.NET properties loaded from embedded resource file
 2 2015-05-22 10:43:23,147 INFO  Quartz.Impl.StdSchedulerFactory  - Using default implementation for object serializer
 3 2015-05-22 10:43:23,168 INFO  Quartz.Impl.StdSchedulerFactory  - Using default implementation for ThreadExecutor
 4 2015-05-22 10:43:23,181 INFO  Quartz.Core.SchedulerSignalerImpl  - Initialized Scheduler Signaller of type: Quartz.Core.SchedulerSignalerImpl
 5 2015-05-22 10:43:23,181 INFO  Quartz.Core.QuartzScheduler  - Quartz Scheduler v.2.0.0.400 created.
 6 2015-05-22 10:43:23,184 INFO  Quartz.Simpl.RAMJobStore  - RAMJobStore initialized.
 7 2015-05-22 10:43:23,186 INFO  Quartz.Core.QuartzScheduler  - Scheduler meta-data: Quartz Scheduler (v2.0.0.400) 'DefaultQuartzScheduler' with instanceId 'NON_CLUSTERED'
 8   Scheduler class: 'Quartz.Core.QuartzScheduler' - running locally.
 9   NOT STARTED.
10   Currently in standby mode.
11   Number of jobs executed: 0
12   Using thread pool 'Quartz.Simpl.SimpleThreadPool' - with 10 threads.
13   Using job-store 'Quartz.Simpl.RAMJobStore' - which does not support persistence. and is not clustered.
14 
15 2015-05-22 10:43:23,186 INFO  Quartz.Impl.StdSchedulerFactory  - Quartz scheduler 'DefaultQuartzScheduler' initialized
16 2015-05-22 10:43:23,187 INFO  Quartz.Impl.StdSchedulerFactory  - Quartz scheduler version: 2.0.0.400
17 2015-05-22 10:43:23,191 INFO  Quartz.Core.QuartzScheduler  - Scheduler DefaultQuartzScheduler_$_NON_CLUSTERED started.
18 2015-05-22 10:43:23,250 INFO  Statistics.WindowService.SyncDataService  - Quarzt 數據同步服務開啓
19 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務開始運行
20 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行0
21 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行1
22 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行2
23 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行3
24 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行4
25 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行5
26 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行6
27 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行7
28 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行8
29 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行9
30 2015-05-22 10:44:01,042 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務運行結束
31 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務開始運行
32 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行0
33 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行1
34 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行2
35 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行3
36 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行4
37 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行5
38 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行6
39 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行7
40 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行8
41 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行9
42 2015-05-22 10:45:03,518 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務運行結束
43 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務開始運行
44 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行0
45 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行1
46 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行2
47 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行3
48 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行4
49 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行5
50 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行6
51 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行7
52 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行8
53 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行9
54 2015-05-22 10:46:03,557 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務運行結束
55 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務開始運行
56 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行0
57 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行1
58 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行2
59 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行3
60 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行4
61 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行5
62 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行6
63 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行7
64 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行8
65 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行9
66 2015-05-22 10:47:03,373 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務運行結束
67 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務開始運行
68 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行0
69 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行1
70 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行2
71 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行3
72 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行4
73 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行5
74 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行6
75 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行7
76 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行8
77 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行9
78 2015-05-22 10:48:03,170 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務運行結束
79 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務開始運行
80 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行0
81 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行1
82 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行2
83 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行3
84 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行4
85 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行5
86 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行6
87 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行7
88 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行8
89 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 正在運行9
90 2015-05-22 10:49:01,001 INFO  Statistics.WindowService.JobManager.AppLogJob  - AppLogJob 任務運行結束
91 2015-05-22 10:49:17,048 INFO  Quartz.Core.QuartzScheduler  - Scheduler DefaultQuartzScheduler_$_NON_CLUSTERED shutting down.
92 2015-05-22 10:49:17,048 INFO  Quartz.Core.QuartzScheduler  - Scheduler DefaultQuartzScheduler_$_NON_CLUSTERED paused.
93 2015-05-22 10:49:17,052 INFO  Quartz.Core.QuartzScheduler  - Scheduler DefaultQuartzScheduler_$_NON_CLUSTERED Shutdown complete.

總結

內容很簡單。只是將以前在博客園看到的一種方式在項目中實踐了一下。

 參考文章:

http://www.cnblogs.com/lzrabbit/archive/2012/04/15/2448326.html

相關文章
相關標籤/搜索