在不同的日期和不同的时间设置 Cron 表达式

Setting Cron expressions on different day and different time

我有一个 Azure 网络作业,每周 运行 下午 1.30 进行一次。现在我需要更改时间表,这是本周的时间表。

Monday at 3pm
Tuesday at 7pm
Friday at 12pm

以下表达式 运行s 表示每个星期一 (* 01 30 * * 1)。我可以在下午 1 点 30 分(* 01 30 * * 1、2、5)的同一时间将其更改为 运行,但不确定如何为不同的日期设置不同的时间。

* 01 30 * * 1 
* 01 30 * * 1,2,5

我知道实现它的三种方法。

  1. 最简单的方法,像这样在Function.cs中创建多个静态webjob方法

    // Function triggered by a timespan schedule every 15 sec.
    public static void TimerJob([TimerTrigger("00:00:15")] TimerInfo timerInfo, 
                                TextWriter log)
    {
        log.WriteLine("1st scheduled job fired!");
    }
    
    // Function triggered by a timespan schedule every 5 minute.
    public static void TimerJob([TimerTrigger("0 */5 * * * *")] TimerInfo timerInfo, 
                                TextWriter log)
    {
        log.WriteLine("2nd scheduled job fired!");
    }
    
  2. 使用 CustomSchedule class 定义时间表。这是github中的webjob sample,是周或月,你需要在app.config中这样定义时间跨度。

    <appSettings> <add key="Mon" value="08:11:20|09:24:20|09:28:20"/> <add key="Tue" value="09:19:40"/> <add key="Wed" value="09:15:40"/> <add key="Thu" value="09:15:40"/> <add key="Fri" value="09:15:40"/> <add key="Sat" value="09:15:40"/> <add key="Sun" value="09:15:40"/> </appSettings>

  3. 这种方式类似于第二种方式,使用[TimerSchedule]抽象class构建支持多个cron表达式的自定义调度程序。更多信息你可以参考这个博客:Combining cron expressions in Azure WebJobs TimerTriggers.

    public class CombinedCronSchedule : TimerSchedule
    {
    private readonly Func<IEnumerable<DateTime>, DateTime> _nextOccurenceSelector;
    private readonly IReadOnlyCollection<CronSchedule> _schedules;
    
    public CombinedCronSchedule(params string[] expressions) : this(dates => dates.Min(), expressions)
    {
    }
    
    public CombinedCronSchedule(Func<IEnumerable<DateTime>, DateTime> nextOccurenceSelector, params string[] expressions)
    {
        _nextOccurenceSelector = nextOccurenceSelector;
        _schedules = expressions.Select(s => new CronSchedule(s)).ToList();
    }
    
    public override DateTime GetNextOccurrence(DateTime now)
    {
        return _nextOccurenceSelector(_schedules.Select(s => s.GetNextOccurrence(now)));
    }
    
    public override string ToString()
    {
        var schedules = string.Join(", ", _schedules.Select(s => s.ToString()));
        return $"Schedules: {schedules}";
    }
    }
    

    创建代表我们新时间表的 class:

    public class PeakNonPeakSchedule : CombinedCronSchedule
    {
        // Every 15 minutes, between 06:00 AM and 08:59 PM
        private const string PeakHours = "0 */15 6-20 * * *";
    
        // Every hour from 12:00 AM to 06:00 AM and 09:00 PM to 12:00 AM
        private const string NonPeakHours = "0 0 0-5,21-23 * * *";
    
        public PeakNonPeakSchedule() : base(PeakHours, NonPeak)
        {
        }
    }
    

    创建你的工作。

    public static void Cleanup([TimerTrigger(typeof(PeakNonPeakSchedule))] TimerInfo timer)
    {
        DoCleanup();
    }
    
    // No second job needed!
    

希望对您有所帮助。