[evolution-mapi/gnome-3-30] I#1 - DTSTART/DTEND stored both with TZID and as UTC



commit a56f5941c8eb6952a3952d2302d7b970fddbf89c
Author: Milan Crha <mcrha redhat com>
Date:   Tue Jan 15 16:16:21 2019 +0100

    I#1 - DTSTART/DTEND stored both with TZID and as UTC
    
    Closes https://gitlab.gnome.org/GNOME/evolution-mapi/issues/1

 src/calendar/e-cal-backend-mapi.c            | 89 ++++++++++++++++++++++++++++
 src/libexchangemapi/e-mapi-cal-recur-utils.c | 10 ++--
 src/libexchangemapi/e-mapi-cal-utils.c       | 13 ++--
 3 files changed, 103 insertions(+), 9 deletions(-)
---
diff --git a/src/calendar/e-cal-backend-mapi.c b/src/calendar/e-cal-backend-mapi.c
index 1e7e5fb..922705d 100644
--- a/src/calendar/e-cal-backend-mapi.c
+++ b/src/calendar/e-cal-backend-mapi.c
@@ -53,6 +53,10 @@
 #define EDC_ERROR(_code) e_data_cal_create_error (_code, NULL)
 #define EDC_ERROR_EX(_code, _msg) e_data_cal_create_error (_code, _msg)
 
+/* Current data version */
+#define EMA_DATA_VERSION       1
+#define EMA_DATA_VERSION_KEY   "ema-data-version"
+
 G_DEFINE_TYPE (ECalBackendMAPI, e_cal_backend_mapi, E_TYPE_CAL_META_BACKEND)
 
 struct _ECalBackendMAPIPrivate {
@@ -1727,6 +1731,76 @@ ecb_mapi_get_destination_address (EBackend *backend,
        return result;
 }
 
+static gboolean
+ecb_mapi_update_tzid_cb (ECache *cache,
+                        const gchar *uid,
+                        const gchar *revision,
+                        const gchar *object,
+                        EOfflineState offline_state,
+                        gint ncols,
+                        const gchar *column_names[],
+                        const gchar *column_values[],
+                        gchar **out_revision,
+                        gchar **out_object,
+                        EOfflineState *out_offline_state,
+                        ECacheColumnValues **out_other_columns,
+                        gpointer user_data)
+{
+       icalcomponent *icomp;
+       icalproperty *prop;
+       gboolean changed = FALSE;
+
+       g_return_val_if_fail (object != NULL, FALSE);
+       g_return_val_if_fail (out_object != NULL, FALSE);
+
+       icomp = icalcomponent_new_from_string (object);
+       if (!icomp)
+               return TRUE;
+
+       prop = icalcomponent_get_first_property (icomp, ICAL_DTSTART_PROPERTY);
+       if (prop && icalproperty_get_first_parameter (prop, ICAL_TZID_PARAMETER)) {
+               struct icaltimetype itt;
+
+               itt = icalproperty_get_dtstart (prop);
+               if (icaltime_is_valid_time (itt) && icaltime_is_utc (itt)) {
+                       itt.zone = NULL;
+                       icalproperty_set_dtstart (prop, itt);
+                       changed = TRUE;
+               }
+       }
+
+       prop = icalcomponent_get_first_property (icomp, ICAL_DTEND_PROPERTY);
+       if (prop && icalproperty_get_first_parameter (prop, ICAL_TZID_PARAMETER)) {
+               struct icaltimetype itt;
+
+               itt = icalproperty_get_dtend (prop);
+               if (icaltime_is_valid_time (itt) && icaltime_is_utc (itt)) {
+                       itt.zone = NULL;
+                       icalproperty_set_dtend (prop, itt);
+                       changed = TRUE;
+               }
+       }
+
+       if (changed)
+               *out_object = icalcomponent_as_ical_string_r (icomp);
+
+       icalcomponent_free (icomp);
+
+       return TRUE;
+}
+
+static void
+ecb_mapi_migrate (ECalBackendMAPI *cbmapi,
+                 ECalCache *cal_cache,
+                 gint data_version)
+{
+       if (data_version < 1) {
+               /* DTSTART/DTEND stores with both TZID and 'Z' suffix */
+               e_cache_foreach_update (E_CACHE (cal_cache), E_CACHE_EXCLUDE_DELETED, NULL,
+                       ecb_mapi_update_tzid_cb, NULL, NULL, NULL);
+       }
+}
+
 static gchar *
 ecb_mapi_dup_component_revision_cb (ECalCache *cal_cache,
                                    icalcomponent *icalcomp)
@@ -1750,6 +1824,7 @@ ecb_mapi_constructed (GObject *object)
 {
        ECalBackendMAPI *cbmapi = E_CAL_BACKEND_MAPI (object);
        ECalCache *cal_cache;
+       gint data_version;
 
        /* Chaing up to parent's method */
        G_OBJECT_CLASS (e_cal_backend_mapi_parent_class)->constructed (object);
@@ -1765,6 +1840,20 @@ ecb_mapi_constructed (GObject *object)
        g_signal_connect (cal_cache, "dup-component-revision",
                G_CALLBACK (ecb_mapi_dup_component_revision_cb), NULL);
 
+       data_version = e_cache_get_key_int (E_CACHE (cal_cache), EMA_DATA_VERSION_KEY, NULL);
+
+       if (EMA_DATA_VERSION != data_version) {
+               GError *local_error = NULL;
+
+               ecb_mapi_migrate (cbmapi, cal_cache, data_version);
+
+               if (!e_cache_set_key_int (E_CACHE (cal_cache), EMA_DATA_VERSION_KEY, EMA_DATA_VERSION, 
&local_error)) {
+                       g_warning ("%s: Failed to store data version: %s\n", G_STRFUNC, local_error ? 
local_error->message : "Unknown error");
+               }
+
+               g_clear_error (&local_error);
+       }
+
        g_clear_object (&cal_cache);
 }
 
diff --git a/src/libexchangemapi/e-mapi-cal-recur-utils.c b/src/libexchangemapi/e-mapi-cal-recur-utils.c
index d34e1bd..0b8288b 100644
--- a/src/libexchangemapi/e-mapi-cal-recur-utils.c
+++ b/src/libexchangemapi/e-mapi-cal-recur-utils.c
@@ -915,7 +915,7 @@ e_mapi_cal_util_bin_to_rrule (const guint8 *lpb, guint32 cb, ECalComponent *comp
                        ECalComponentDateTime *dt = g_new0 (ECalComponentDateTime, 1);
                        time_t ictime = convert_recurrence_minutes_to_timet (rp->DeletedInstanceDates[i]);
 
-                       tt = icaltime_from_timet_with_zone (ictime, 1, 0);
+                       tt = icaltime_from_timet_with_zone (ictime, 1, NULL);
 
                        val = g_new0(struct icaltimetype, 1);
                        memcpy (val, &tt, sizeof(struct icaltimetype));
@@ -930,7 +930,7 @@ e_mapi_cal_util_bin_to_rrule (const guint8 *lpb, guint32 cb, ECalComponent *comp
        /* end date */
        if (rp->EndType == END_AFTER_DATE) {
                time_t ict = convert_recurrence_minutes_to_timet (rp->EndDate);
-               rt.until = icaltime_from_timet_with_zone (ict, 1, 0);
+               rt.until = icaltime_from_timet_with_zone (ict, 1, NULL);
        }
 
        /* Set the recurrence */
@@ -960,18 +960,18 @@ e_mapi_cal_util_bin_to_rrule (const guint8 *lpb, guint32 cb, ECalComponent *comp
                        /* make a shallow clone of comp */
                        detached[i] = e_cal_component_clone (comp);
 
-                       tt = icaltime_from_timet_with_zone (convert_recurrence_minutes_to_timet 
(ei->OriginalStartDate), 0, 0);
+                       tt = icaltime_from_timet_with_zone (convert_recurrence_minutes_to_timet 
(ei->OriginalStartDate), 0, NULL);
                        rid.type = E_CAL_COMPONENT_RANGE_SINGLE;
                        rid.datetime.value = &tt;
                        rid.datetime.tzid = recur_zone ? icaltimezone_get_tzid (recur_zone) : "UTC";
                        e_cal_component_set_recurid (detached[i], &rid);
 
-                       tt = icaltime_from_timet_with_zone (convert_recurrence_minutes_to_timet 
(ei->StartDateTime), 0, 0);
+                       tt = icaltime_from_timet_with_zone (convert_recurrence_minutes_to_timet 
(ei->StartDateTime), 0, NULL);
                        edt.value = &tt;
                        edt.tzid = recur_zone ? icaltimezone_get_tzid (recur_zone) : "UTC";
                        e_cal_component_set_dtstart (detached[i], &edt);
 
-                       tt = icaltime_from_timet_with_zone (convert_recurrence_minutes_to_timet 
(ei->EndDateTime), 0, 0);
+                       tt = icaltime_from_timet_with_zone (convert_recurrence_minutes_to_timet 
(ei->EndDateTime), 0, NULL);
                        edt.value = &tt;
                        edt.tzid = recur_zone ? icaltimezone_get_tzid (recur_zone) : "UTC";
                        e_cal_component_set_dtend (detached[i], &edt);
diff --git a/src/libexchangemapi/e-mapi-cal-utils.c b/src/libexchangemapi/e-mapi-cal-utils.c
index daa3166..a4bb2fc 100644
--- a/src/libexchangemapi/e-mapi-cal-utils.c
+++ b/src/libexchangemapi/e-mapi-cal-utils.c
@@ -1017,7 +1017,9 @@ e_mapi_cal_util_object_to_comp (EMapiConnection *conn,
 
                if (e_mapi_util_find_array_datetime_propval (&t, &object->properties, 
PidLidAppointmentStartWhole) == MAPI_E_SUCCESS) {
                        icaltimezone *zone = dtstart_tz_location ? icaltimezone_get_builtin_timezone 
(dtstart_tz_location) : utc_zone;
-                       prop = icalproperty_new_dtstart (icaltime_from_timet_with_zone (t.tv_sec, all_day, 
zone));
+                       struct icaltimetype itt = icaltime_from_timet_with_zone (t.tv_sec, all_day, zone);
+                       itt.zone = zone;
+                       prop = icalproperty_new_dtstart (itt);
                        if (!all_day && zone && icaltimezone_get_tzid (zone)) {
                                icalproperty_add_parameter (prop, icalparameter_new_tzid 
(icaltimezone_get_tzid (zone)));
                        }
@@ -1040,12 +1042,15 @@ e_mapi_cal_util_object_to_comp (EMapiConnection *conn,
 
                if (e_mapi_util_find_array_datetime_propval (&t, &object->properties, 
PidLidAppointmentEndWhole) == MAPI_E_SUCCESS) {
                        icaltimezone *zone;
+                       struct icaltimetype itt;
 
                        if (!dtend_tz_location)
                                dtend_tz_location = dtstart_tz_location;
 
                        zone = dtend_tz_location ? icaltimezone_get_builtin_timezone (dtend_tz_location) : 
utc_zone;
-                       prop = icalproperty_new_dtend (icaltime_from_timet_with_zone (t.tv_sec, all_day, 
zone));
+                       itt = icaltime_from_timet_with_zone (t.tv_sec, all_day, zone);
+                       itt.zone = zone;
+                       prop = icalproperty_new_dtend (itt);
                        if (!all_day && zone && icaltimezone_get_tzid (zone)) {
                                icalproperty_add_parameter (prop, icalparameter_new_tzid 
(icaltimezone_get_tzid (zone)));
                        }
@@ -1199,8 +1204,8 @@ e_mapi_cal_util_object_to_comp (EMapiConnection *conn,
                                ECalComponentAlarmTrigger trigger;
 
                                trigger.type = E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_START;
-                               trigger.u.rel_duration = icaltime_subtract (icaltime_from_timet_with_zone 
(displaytime.tv_sec, 0, 0),
-                                                                           icaltime_from_timet_with_zone 
(start.tv_sec, 0, 0));
+                               trigger.u.rel_duration = icaltime_subtract (icaltime_from_timet_with_zone 
(displaytime.tv_sec, 0, NULL),
+                                                                           icaltime_from_timet_with_zone 
(start.tv_sec, 0, NULL));
 
                                e_cal_component_alarm_set_action (e_alarm, E_CAL_COMPONENT_ALARM_DISPLAY);
                                e_cal_component_alarm_set_trigger (e_alarm, trigger);


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]