Loupe

Générer un fichier iCalendar avec la notion de fuseau horaire

Qu'est ce qu'un iCalendar ?

<humour>iCalendar c'est le nouveau logiciel Apple présenté il y a peu. Ce calendrier vous permet de gérer votre agenda en utilisant l'assistante Siri pour être mieux organisé. Bref, c'est une révolution !</humour>

Plus sérieusement, iCalendar est un format de données qui permet de faire transiter les données d'un ou plusieurs événements d'un agenda à un autre. Vous avez surement dû en croiser quelques-uns, ce sont des petits fichiers au format ics ou ical qui contiennent les informations primaires des événements. Ainsi, quand vous ajoutez ce fichier à votre agenda Outlook, Gmail, Apple, ... le ou les événements apparaissent avec les informations contenues dans ce fichier.

Comment est structuré un fichier ics ?

Un ics est structuré en nœuds. Le nœud racine est un VCALENDAR qui contient quelques informations sur le calendrier, comme son nom ou le nom du système qui l'a généré, par exemple. Il contient également le ou les événements du calendrier à travers le noeud VEVENT. Le noeud event contient les informations de l'événement, notamment son titre, sa description, ses dates et heures de début et de fin, son lieu.

Schéma structure ics

Voici un exemple avec un événement :

BEGIN:VCALENDAR
PRODID:InfiniteSquare Blogs
	BEGIN:VEVENT
		CREATED:20180818T151139Z
		DESCRIPTION:Un super article a lire d'urgence
		DTEND:20180820T072000
		DTSTAMP:20180818T151139Z
		DTSTART:20180820T070000
		LAST-MODIFIED:20180818T151139Z
		LOCATION:https://blogs.infinitesquare.com/blogger/posts/generer-un-fichier-icalendar-avec-la-notion-de-fuseau-horaire
		SUMMARY;LANGUAGE=fr:Lire l'article de Teddy sur la génération d'un icalendar
	END:VEVENT
END:VCALENDAR

En théorie, au vu des informations contenues dans ce fichier, la génération n'a pas l'air si complexe que cela ... mais en pratique c'est pas aussi simple !

Les dates, c'est toujours un problème ...

Le problème principal pour générer ce fichier se trouve dans les dates ! En effet, dans un fichier iCalendar, les dates de l'événement sont transmises au format UTC. Si je reprends mon exemple précédent, les dates de l'événement (DTSTART, DTEND) sont transmises sous la forme AAAAMMDDThhmmssZ si j'ajoute ce fichier dans mon calendrier Outlook (paramétré sur le fuseau horaire de Paris en heure d'été, GMT+2), l'événement sera ajouté dans mon calendrier le 20/08/2018 de 9h à 9h20. Dans bien des cas, ce comportement est voulu mais à partir du moment où le besoin est d'ajouter un événement non pas sur le fuseau horaire de l'utilisateur, mais dans un fuseau horaire défini, la génération de ce petit fichier devient beaucoup plus complexe. Il est possible de spécifier un fuseau horaire dans la valeur de DTSTART et DTEND, à travers le format suivant :

DTSTART;TZID=America/Los_Angeles:20180820T070000
DTEND;TZID=America/Los_Angeles:20180820T072000

La valeur du TZID se base sur le nom du fuseau horaire défini dans la base de données du IANA disponible sur Wikipedia ou sur le site officiel du IANA

Si maintenant j'ajoute ce fichier sur Outlook j'aurai le même comportement que précédemment, mon événement sera ajouté dans mon calendrier le 20/08/2018 de 9h à 9h20. Par contre, si j'ajoute ce même fichier sur Google, mon événement sera ajouté dans mon calendrier le 20/08/2018 de 16h à 16h20 (heure locale GMT+2, heure Los Angeles GMT-7, une différence de 9h), ce qui correspond bien au fuseau horaire défini dans le fichier. Si je change le fuseau horaire de mon agenda Google pour le mettre sur celui de Los Angeles, mon événement s'affiche de 9h à 9h20. Le comportement de Google est donc bien le comportement voulu, mais pourquoi sur Outlook, cela ne fonctionne pas ?

Car Outlook ne reconnait pas les fuseaux horaires normés par IANA, il reconnait UNIQUEMENT les fuseaux horaires Microsoft, sinon il ajoute l'événement dans le fuseau courant de l'utilisateur. Outlook et Google Agenda étant des logiciels beaucoup utilisés, il est obligatoire que le fichier généré fonctionne sur les deux.

Ajout de la définition du fuseau horaire Windows dans le fichier ics

Reprenons l'exemple précédent du fuseau horaire de Los Angeles, qui, sur Windows, porte le nom de "Pacific Standard Time". Le noeud VTIMEZONE permet de définir les informations du fuseau horaire, et notamment : son id, le décalage horaire, et pour les fuseaux horaires ayant des heures d'été, le décalage en heure d'été, et la règle d'application pour savoir quand le fuseau passe de l'horaire d'été à l'horaire d'hiver et inversement.

BEGIN:VTIMEZONE
TZID:Pacific Standard Time
	BEGIN:STANDARD
		DTSTART:16011104T020000
		RRULE:FREQ=YEARLY;BYDAY=1SU;BYMONTH=11
		TZOFFSETFROM:-0700
		TZOFFSETTO:-0800
	END:STANDARD
	BEGIN:DAYLIGHT
		DTSTART:16010311T020000
		RRULE:FREQ=YEARLY;BYDAY=2SU;BYMONTH=3
		TZOFFSETFROM:-0800
		TZOFFSETTO:-0700
	END:DAYLIGHT
END:VTIMEZONE

Sur mon exemple, le fuseau horaire "Pacific Standard Time" est un fuseau avec une heure d'été.

Dans le nœud STANDARD est défini le fuseau horaire en heure d'hiver, à savoir :

  • DTSTART, à partir de quand cette heure s'applique ici depuis le 04/11/1601 à 2h GMT
  • RRULE, quand s'applique cette heure ici le 1er dimanche (BYDAY=1SU) du mois de novembre (BYMONTH=11) tous les ans (FREQ=YEARLY)
  • TZOFFSETFROM, le décalage horaire d'avant, ici GMT-7
  • TZOFFSETTO, le décalage horaire a appliquer, ici GMT-8

Dans le nœud DAYLIGHT est défini le fuseau horaire en heure d'été, à savoir: 

  • DTSTART, à partir de quand cette heure s'applique ici depuis le 11/03/1601 à 2h GMT
  • RRULE, quand s'applique cette heure ici le 2ème dimanche (BYDAY=2SU) du mois de mars (BYMONTH=3) tous les ans (FREQ=YEARLY)
  • TZOFFSETFROM, le décalage horaire d'avant, ici GMT-8
  • TZOFFSETTO, le décalage horaire a appliquer, ici GMT-7

Ainsi si on rajoute la définition du fuseau horaire tel que présenté ci-dessus et que l'on remplace le TZID=America/Los_Angeles par TZID="Pacific Standard Time" dans la valeur DTSTART et DTEND de l'événement, Outlook va ajouter l'événement dans le fuseau horaire "Pacific Standard Time" et Google Agenda, va placer l'événement avec le décalage défini à savoir GMT-7 en heure d'été et GMT-8 en heure d'hiver.

La gestion des dates et des fuseaux horaires est assez complexe, au vu des cas possibles et des comportements différents entre les systèmes. J'espère que cet article permet de mieux appréhender cette problématique dans le cadre de la génération de icalendar.

Photo de profil

Ces billets pourraient aussi vous intéresser

Vous nous direz ?!

Commentaires

comments powered by Disqus