Par exemple, utilisons l’expression cron suivante: “0 0 14 1 *?”
-> Incendie le 1er de chaque mois à 14h00.
J’ai utilisé Quartz CronScheduleBuilder pour construire l’expession, mais cela n’a aucune importance.
Mon fuseau horaire local est UTC + 01: 00 et l’heure d’été (cette année) commence le 31.03.2013 2:00, où l’heure est réglée sur 3:00.
Lorsque je planifie un nouveau Job en utilisant le déclencheur proposé, disons le 20.02.2013, Quartz calcule correctement le System.DateTimeOffset pour le “NextFireTimeUtc” pour:
DateTime: 01.03.2013 13:00:00 (il s’agit de l’heure UTC, soit une heure après le fuseau horaire local)
Heure locale: 01.03.2013 14:00:00
Le travail se déclenchera correctement à 14h00, comme spécifié.
Maintenant, si je planifie le travail le 20.03.2013, le “NextFireTimeUtc” a pour résultat:
DateTime: 01.04.2013 13:00:00 (il s’agit de l’heure UTC, qui a maintenant deux heures de retard sur le fuseau horaire local)
Heure locale: 01.04.2013 15:00:00
Notez que le NextFireTimeUtc résultant entre maintenant dans l’heure d’été locale. En conséquence, le LocalDateTime a également été “corrigé” d’une heure supplémentaire à partir de l’heure UTC. Cela se traduit par le travail en cours d’exécution à 15h00, ce qui n’est pas ce que je veux.
Ce que j’attendais (évidemment), c’est que le “14” dans l’expression “cron” entraîne toujours le déclenchement de la gâchette à 14h00, même en été.
Il doit y avoir un moyen facile de gérer ce phénomène, il me manque probablement quelque chose de conceptuel. Je suis confus.
MODIFIER:
Le problème semble être que Quartz calcule le premier NextFireTimeUtc en fonction des informations du fuseau horaire actuel . Pour tester cela, j’ai planifié deux déclencheurs cron différents et appelé GetFireTimeAfter () sur le déclencheur avec un décalage croissant pour afficher les temps de déclenchement résultants sur l’année.
Déclencheur 1: Tirez le 28 de chaque mois à 14h00.
GetFireTimeAfter now + 00 mois: 28.03.2013 13:00:00 +00: 00 <- ceci est correct
GetFireTimeAfter now + 01 mois: 28.04.2013 12:00:00 +00: 00
GetFireTimeAfter now + 02 mois: 28.05.2013 12:00:00 +00: 00
GetFireTimeAfter now + 03 mois: 28.06.2013 12:00:00 +00: 00
GetFireTimeAfter now + 04 months: 28.07.2013 12:00:00 +00: 00
GetFireTimeAfter now + 05 months: 28.08.2013 12:00:00 +00: 00
GetFireTimeAfter now + 06 mois: 28.09.2013 12:00:00 +00: 00
GetFireTimeAprès maintenant + 07 mois: 28.10.2013 13:00:00 +00: 00 <- heure d'été déjà terminée
GetFireTimeAfter now + 08 months: 28.11.2013 13:00:00 +00: 00
La première heure de tir est correcte, car elle tombe encore en “hiver”. Les heures de “l’heure d’été” sont décalées de -1, ce qui donne l’heure d’incendie correcte une fois que le fuseau horaire local a ajouté +2.
Déclencheur 1: tirez le premier jour de chaque mois à 14h00
GetFireTimeAfter now + 00 months: 01.04.2013 13:00:00 +00: 00 <- c'est faux?
GetFireTimeAfter now + 01 mois: 01.05.2013 12:00:00 +00: 00
GetFireTimeAfter now + 02 months: 01.06.2013 12:00:00 +00: 00
GetFireTimeAfter now + 03 mois: 01.07.2013 12:00:00 +00: 00
GetFireTimeAfter now + 04 months: 01.08.2013 12:00:00 +00: 00
GetFireTimeAfter now + 05 months: 01.09.2013 12:00:00 +00: 00
GetFireTimeAfter now + 06 mois: 01.10.2013 12:00:00 +00: 00
GetFireTimeAprès maintenant + 07 mois: 01.11.2013 13:00:00 +00: 00 <- heure d'été déjà terminée
GetFireTimeAfter now + 08 months: 01.12.2013 13:00:00 +00: 00
Le premier incendie se situe déjà dans la période estivale, mais il n’est compensé que par -1, ce qui donne un temps de déclenchement local de 15h00.
Donc, le déclencheur est correct, sauf pour le premier déclenchement, s’il est programmé pendant l’hiver et que la première exécution tombe pendant l’heure d’été. Comment gérer ça?
J’ai compris qu’il s’agissait en fait d’un bogue dans Quartz.NET 2.0.1, mais il a déjà été corrigé dans la version 2.1.0.
Voir cette réponse pour plus de détails.