Quartz使用总结

说起调度任务,在.NET中不得不说的就是Quartz.NET了,Quartz.NET是一个强大的、开源的轻量的作业调度框架,是 OpenSymphony 的 Quartz API 的.NET移植,用C#改写。官网地址:https://www.quartz-scheduler.net/

在日常的开发中会经常会使用到调度任务的这种场景,例如数据库在每天的凌晨2点进行一次备份,还有就是对账系统在每隔多久进行一次对账等等。接下来我们就用一个小实例来介绍一下Quartz.NET的基本使用

一.安装

通过nuget管理工具搜索并安装Quartz

 

 二.实例

Quartz中有三个概念,调度器、任务、和触发器。调度器通过任务和触发器完成任务的调度

1.创建任务

  public class TimeJob : IJob
    {
        public async Task Execute(IJobExecutionContext context)
        {
            var jobKey = context.JobDetail.Key;//获取job信息
            var triggerKey = context.Trigger.Key;//获取trigger信息
            Console.WriteLine($"{DateTime.Now} QuartzJob:==>>自动执行.{jobKey.Name}|{triggerKey.Name}");
            await Task.CompletedTask;
        }
    }

2.创建调度器

               //调度器
                IScheduler scheduler;
                //调度器工厂
                ISchedulerFactory factory;
                //1、创建一个调度器
                factory = new StdSchedulerFactory();
                scheduler =await factory.GetScheduler();
                await scheduler.Start();

3.触发策略

Quartz中有两种触发的策略,SimpleTrigger和CronTrigger

SimpleTrigger

如果您需要让某个作业在特定时间或特定时间执行一次,然后在特定时间间隔重复执行一次,SimpleTrigger应该可以满足您的计划需求。如果您想让扳机在2005年1月13日上午11:23:54触发,然后每十秒钟触发五次

1.为特定时间建立触发器,不要重复:

    ISimpleTrigger trigger = (ISimpleTrigger) TriggerBuilder.Create()
    .WithIdentity("trigger1", "group1")
    .StartAt(myStartTime) // some Date 
    .ForJob("job1", "group1") // identify job with name, group strings
    .Build();

2.建立一个特定时间的触发器,然后每十秒钟重复十次:

ITrigger trigger = TriggerBuilder.Create()
    .WithIdentity("trigger3", "group1")
    .StartAt(myTimeToStartFiring) //如果没有给出开始时间(如果省略了这一行),则表示“现在”
    .WithSimpleSchedule(x => x
        .WithIntervalInSeconds(10)
        .WithRepeatCount(10)) //请注意,10次重复将给出总共11次触发
    .ForJob(myJob) 
    .Build();

3.建立一个触发器,该触发器将在未来五分钟触发一次:

ITrigger trigger = TriggerBuilder.Create()
    .WithIdentity("trigger5", "group1")
    .StartAt(DateBuilder.FutureDate(5, IntervalUnit.Minute)) //使用DateBuilder创建时间
    .ForJob(myJobKey) 
    .Build();

CronTrigger

  Cron表达式

Cron-Expressions用于配置CronTrigger的实例。Cron-Expression是实际上由七个子表达式组成的字符串,它们描述了日程表的各个细节。这些子表达式用空格分隔,代表:

1.秒
2.分钟
3.小时
4.每月的一天
5.月
6.星期几
7.年(可选字段)

完整的cron表达式的示例是字符串0 0 12 ? * WED-表示“每个星期三的12:00 pm”。

各个子表达式可以包含范围和/或列表。例如,上一个(读为“ WED”)示例中的“星期几”字段可以替换为“ MON-FRI”,“ MON,WED,FRI”,甚至“ MON-WED,SAT”。

通配符(*字符)可以用来表示此字段的“所有”可能值。因此*,上一个示例的“月”字段中字符仅表示“每个月”。一个*在某一天的周场显然是指“一周中的每一天”。

所有字段都有一组可以指定的有效值。这些值应该非常明显-例如秒和分钟的数字0到59,小时的数字0到23。Day-of-Month可以是0-31之间的任何值,但是您需要注意给定月份中有多少天!可以将月份指定为0到11之间的值,也可以使用字符串JAN,FEB,MAR,APR,MAY,JUN,JUL,AUG,SEP,OCT,NOV和DEC来指定。每周的天数可以指定为1到7之间的值(1 =星期日),也可以使用字符串SUN,MON,TUE,WED,THU,FRI和SAT。

“ /”字符可用于指定值的增量。例如,如果您在“分钟”字段中输入“ 0/15”,则表示“每15分钟,从零分钟开始”。如果您在“分钟”字段中使用“ 3/20”,则表示“每小时每20分钟,从第三分钟开始”,换句话说,与在“分钟”中指定“ 3,23,43”相同场地。

这 '?' 星期几和星期几字段允许使用字符。用于指定“无特定值”。当您需要在两个字段之一中指定某项而不是另一个字段时,这很有用。有关说明,请参见下面的示例(和CronTrigger API文档)。

建立一个触发器,该触发器每天每天从早上8点到下午5点之间每隔一分钟触发一次:

ITrigger trigger = TriggerBuilder.Create()
    .WithIdentity("trigger3", "group1")
    .WithCronSchedule("0 0/2 8-17 * * ?")
    .ForJob("myJob", "group1")
    .Build();

建立触发器,每天10:42 am触发:

ITrigger trigger = TriggerBuilder.Create()
    .WithIdentity("trigger3", "group1")
    .WithSchedule(CronScheduleBuilder.DailyAtHourAndMinute(10, 42))
    .ForJob(myJobKey)
    .Build();

 

完整实例

 class Program
    {

        static void Main(string[] args)
        {
            TestRun().Wait();
            Console.WriteLine("hello world");
            Console.ReadLine();
        }

        private static async Task TestRun()
        {
            try
            {
                //调度器
                IScheduler scheduler;
                //调度器工厂
                ISchedulerFactory factory;
                //1、创建一个调度器
                factory = new StdSchedulerFactory();
                scheduler =await factory.GetScheduler();
                await scheduler.Start();

                //2、创建一个任务
                IJobDetail job = JobBuilder.Create<TimeJob>().WithIdentity("job1", "group1").Build();

                //3、创建一个触发器
                //DateTimeOffset runTime = DateBuilder.EvenMinuteDate(DateTimeOffset.UtcNow);
                ITrigger trigger = TriggerBuilder.Create()
                    .WithIdentity("trigger1", "group1")
                    .WithCronSchedule("0/5 * * * * ?")     //5秒执行一次
                                                           //.StartAt(runTime)
                    .Build();

                ITrigger trigger2 = TriggerBuilder.Create()
                 .WithIdentity("trigger1", "group1")
                 .WithSimpleSchedule(x=>x.WithInterval(1))    
                 .Build();

                //4、将任务与触发器添加到调度器中
                await scheduler.ScheduleJob(job, trigger);
                //5、开始执行
                await scheduler.Start();
            }
            catch (Exception ex)
            {
                await Console.Error.WriteLineAsync(ex.ToString());
            }

        }
    }

 

posted @ 2021-02-23 16:33  hello-*-world  阅读(173)  评论(0编辑  收藏  举报