Несколько недель назад я писал об использовании Quartz.Net для планирования заданий в рабочих ролях Windows Azure. С тех пор я столкнулся с требованием, которое подтолкнуло меня к созданию обертки вокруг Quartz.Net IScheduler. JobSchedule отвечает за чтение строки расписания из CloudConfigurationManager и планирование задания.
CloudConfigurationManager считывает настройки из файла конфигурации роли, который можно редактировать через портал управления Windows Azure в разделе конфигурации облачных служб.
В следующем примере будет запланировано задание, которое должно выполняться ежедневно в 6, 8, 10, 12:30 и 16:30. Расписание определяется в настройках роли, которые можно редактировать в Visual Studio. Чтобы перейти к настройкам ролей, перейдите в проект облачной службы Windows Azure и найдите нужные конфигурации ролей в папке «Роль». Откройте редактор конфигурации, дважды щелкнув файл конфигурации, затем перейдите на вкладку «Настройки». Нажмите «Добавить параметр» и назовите новый параметр «JobDailySchedule» и установите для него значение 6: 0; 8: 0; 10: 0; 12: 30; 16: 30;
The code from this Post is part of the Brisebois.WindowsAzure NuGet Package
To install Brisebois.WindowsAzure, run the following command in the Package Manager Console
PM> Install-Package Brisebois.WindowsAzure
Get more details about the Nuget Package.
Затем с помощью расписания JobSchedule ежедневно выполняйте работу, используя расписание, определенное в файле конфигурации роли.
var schedule = new JobSchedule();
schedule.ScheduleDailyJob("JobDailySchedule",
typeof(DailyJob));
Реализация DailyJob работает следующим образом. Поскольку это демо, я не буду добавлять какую-либо конкретную логику к работе.
public class DailyJob : IJob
{
public void Execute(IJobExecutionContext context)
{
//Do your daily work here
}
}
JobSchedule оборачивает Quartz.Net IScheduler. В предыдущем посте я говорил о важности обертывания ваших сторонних инструментов, это отличный пример, потому что в нем содержится логика планирования заданий, и я мог бы потенциально изменить эту логику, не затрагивая код, использующий JobSchedule.
JobSchedule должен быть настроен при запуске роли, а экземпляр JobSchedule должен поддерживаться в течение всего времени жизни роли. Изменить расписание можно, изменив параметр «JobDailySchedule» на портале управления Windows Azure в разделе конфигурации облачных служб. Затем, чтобы применить новое расписание, перезапустите экземпляр роли через портал управления Windows Azure в разделе экземпляров облачных служб.
public class JobSchedule
{
private readonly IScheduler sched;
public JobSchedule()
{
var schedFact = new StdSchedulerFactory();
sched = schedFact.GetScheduler();
sched.Start();
}
/// <summary>
/// Will schedule jobs in Eastern Standard Time
/// </summary>
/// <param name="scheduleConfig">Setting Key from your CloudConfigurations,
/// value format "hh:mm;hh:mm;"</param>
/// <param name="jobType">must inherit from IJob</param>
public void ScheduleDailyJob(string scheduleConfig,
Type jobType)
{
ScheduleDailyJob(scheduleConfig,
jobType,
"Eastern Standard Time");
}
/// <param name="scheduleConfig">Setting Key from your CloudConfigurations,
/// value format "hh:mm;hh:mm;"</param>
/// <param name="jobType">must inherit from IJob</param>
public void ScheduleDailyJob(string scheduleConfig,
Type jobType,
string timeZoneId)
{
var schedule = CloudConfigurationManager.GetSetting(scheduleConfig);
if (schedule == "-")
return;
schedule.Split(';')
.Where(s => !string.IsNullOrWhiteSpace(s))
.ToList()
.ForEach(h =>
{
var index = h.IndexOf(':');
var hour = h.Substring(0, index);
var minutes = h.Substring(index + 1, h.Length - (index + 1));
var job = new JobDetailImpl(jobType.Name + hour + minutes, null,
jobType);
var dh = Convert.ToInt32(hour, CultureInfo.InvariantCulture);
var dhm = Convert.ToInt32(minutes, CultureInfo.InvariantCulture);
var tz = TimeZoneInfo.FindSystemTimeZoneById(timeZoneId);
var cronScheduleBuilder = CronScheduleBuilder
.DailyAtHourAndMinute(dh, dhm)
.InTimeZone(tz);
var trigger = TriggerBuilder.Create()
.StartNow()
.WithSchedule(cronScheduleBuilder)
.Build();
sched.ScheduleJob(job, trigger);
});
}
/// <summary>
/// Will schedule jobs in Eastern Standard Time
/// </summary>
/// <param name="scheduleConfig">Setting Key from your CloudConfigurations,
/// value format "hh:mm;hh:mm;"</param>
/// <param name="jobType">must inherit from IJob</param>
public void ScheduleWeeklyJob(string scheduleConfig,
Type jobType)
{
ScheduleWeeklyJob(scheduleConfig,
jobType,
"Eastern Standard Time");
}
/// <param name="scheduleConfig">Setting Key from your CloudConfigurations,
/// value format "hh:mm;hh:mm;"</param>
/// <param name="jobType">must inherit from IJob</param>
public void ScheduleWeeklyJob(string scheduleConfig,
Type jobType,
string timeZoneId)
{
var schedule = CloudConfigurationManager.GetSetting(scheduleConfig);
schedule.Split(';')
.Where(s => !string.IsNullOrWhiteSpace(s))
.ToList()
.ForEach(h =>
{
var index = h.IndexOf(':');
var hour = h.Substring(0, index);
var minutes = h.Substring(index + 1, h.Length - (index + 1));
var job = new JobDetailImpl(jobType.Name + hour + minutes, null,
jobType);
var dh = Convert.ToInt32(hour, CultureInfo.InvariantCulture);
var dhm = Convert.ToInt32(minutes, CultureInfo.InvariantCulture);
var tz = TimeZoneInfo.FindSystemTimeZoneById(timeZoneId);
var builder = CronScheduleBuilder
.WeeklyOnDayAndHourAndMinute(DayOfWeek.Monday,
dh,
dhm)
.InTimeZone(tz);
var trigger = TriggerBuilder.Create()
.StartNow()
.WithSchedule(builder)
.Build();
sched.ScheduleJob(job, trigger);
});
}
}