Make use of G_DEFINE_QUARK()
[platform/upstream/evolution-data-server.git] / calendar / libecal / e-cal.c
1 /*-*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
2 /* Evolution calendar ecal
3  *
4  * Copyright (C) 1999-2008 Novell, Inc. (www.novell.com)
5  * Copyright (C) 2009 Intel Corporation
6  *
7  * Authors: Federico Mena-Quintero <federico@ximian.com>
8  *          Rodrigo Moya <rodrigo@novell.com>
9  *          Ross Burton <ross@linux.intel.com>
10  *
11  * This program is free software; you can redistribute it and/or
12  * modify it under the terms of version 2 of the GNU Lesser General Public
13  * License as published by the Free Software Foundation.
14  *
15  * This program is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License for more details.
19  *
20  * You should have received a copy of the GNU Lesser General Public License
21  * along with this program; if not, write to the Free Software
22  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
23  */
24
25 /**
26  * SECTION:e-cal
27  *
28  * The old signal "cal-opened" is deprecated since 3.0 and is replaced with
29  * its equivalent "cal_opened_ex", which has a detailed #GError structure
30  * as a parameter, instead of a status code only.
31  *
32  * Deprecated: 3.2: Use #ECalClient instead.
33  */
34
35 #ifdef HAVE_CONFIG_H
36 #include <config.h>
37 #endif
38
39 #include <unistd.h>
40 #include <string.h>
41 #include <glib/gi18n-lib.h>
42
43 #include <libical/ical.h>
44
45 #include "e-cal-client.h"
46 #include "e-cal-check-timezones.h"
47 #include "e-cal-marshal.h"
48 #include "e-cal-time-util.h"
49 #include "e-cal-view-private.h"
50 #include "e-cal.h"
51
52 #define E_CAL_GET_PRIVATE(obj) \
53         (G_TYPE_INSTANCE_GET_PRIVATE \
54         ((obj), E_TYPE_CAL, ECalPrivate))
55
56 #define CLIENT_BACKEND_PROPERTY_CACHE_DIR               "cache-dir"
57 #define CLIENT_BACKEND_PROPERTY_CAPABILITIES            "capabilities"
58 #define CAL_BACKEND_PROPERTY_CAL_EMAIL_ADDRESS          "cal-email-address"
59 #define CAL_BACKEND_PROPERTY_ALARM_EMAIL_ADDRESS        "alarm-email-address"
60 #define CAL_BACKEND_PROPERTY_DEFAULT_OBJECT             "default-object"
61
62 static gboolean open_calendar (ECal *ecal, gboolean only_if_exists, GError **error,
63         ECalendarStatus *status,
64         gboolean async);
65
66 struct _ECalPrivate {
67         ECalClient *client;
68         gulong backend_died_handler_id;
69         gulong notify_online_handler_id;
70
71         /* Load state to avoid multiple loads */
72         ECalLoadState load_state;
73
74         ESource *source;
75         ECalSourceType type;
76
77         GList **free_busy_data;
78         GMutex free_busy_data_lock;
79 };
80
81 enum {
82         PROP_0,
83         PROP_SOURCE,
84         PROP_SOURCE_TYPE
85 };
86
87 enum {
88         CAL_OPENED,
89         CAL_OPENED_EX,
90         CAL_SET_MODE,
91         BACKEND_ERROR,
92         BACKEND_DIED,
93         LAST_SIGNAL
94 };
95
96 static guint signals[LAST_SIGNAL];
97
98 static void     e_cal_initable_init             (GInitableIface *interface);
99
100 G_DEFINE_TYPE_WITH_CODE (
101         ECal, e_cal, G_TYPE_OBJECT,
102         G_IMPLEMENT_INTERFACE (G_TYPE_INITABLE, e_cal_initable_init))
103
104 G_DEFINE_QUARK (e-calendar-error-quark, e_calendar_error)
105
106 /*
107  * If the GError is a remote error, extract the EBookStatus embedded inside.
108  * Otherwise return CORBA_EXCEPTION (I know this is DBus...).
109  */
110 static ECalendarStatus
111 get_status_from_error (const GError *error)
112 {
113         #define err(a,b) "org.gnome.evolution.dataserver.Calendar." a, b
114         static struct {
115                 const gchar *name;
116                 ECalendarStatus err_code;
117         } errors[] = {
118                 { err ("Success",                               E_CALENDAR_STATUS_OK) },
119                 { err ("Busy",                                  E_CALENDAR_STATUS_BUSY) },
120                 { err ("RepositoryOffline",                     E_CALENDAR_STATUS_REPOSITORY_OFFLINE) },
121                 { err ("PermissionDenied",                      E_CALENDAR_STATUS_PERMISSION_DENIED) },
122                 { err ("InvalidRange",                          E_CALENDAR_STATUS_OTHER_ERROR) },
123                 { err ("ObjectNotFound",                        E_CALENDAR_STATUS_OBJECT_NOT_FOUND) },
124                 { err ("InvalidObject",                         E_CALENDAR_STATUS_INVALID_OBJECT) },
125                 { err ("ObjectIdAlreadyExists",                 E_CALENDAR_STATUS_OBJECT_ID_ALREADY_EXISTS) },
126                 { err ("AuthenticationFailed",                  E_CALENDAR_STATUS_AUTHENTICATION_FAILED) },
127                 { err ("AuthenticationRequired",                E_CALENDAR_STATUS_AUTHENTICATION_REQUIRED) },
128                 { err ("UnsupportedField",                      E_CALENDAR_STATUS_OTHER_ERROR) },
129                 { err ("UnsupportedMethod",                     E_CALENDAR_STATUS_OTHER_ERROR) },
130                 { err ("UnsupportedAuthenticationMethod",       E_CALENDAR_STATUS_OTHER_ERROR) },
131                 { err ("TLSNotAvailable",                       E_CALENDAR_STATUS_OTHER_ERROR) },
132                 { err ("NoSuchCal",                             E_CALENDAR_STATUS_NO_SUCH_CALENDAR) },
133                 { err ("UnknownUser",                           E_CALENDAR_STATUS_UNKNOWN_USER) },
134                 { err ("OfflineUnavailable",                    E_CALENDAR_STATUS_OTHER_ERROR) },
135                 { err ("SearchSizeLimitExceeded",               E_CALENDAR_STATUS_OTHER_ERROR) },
136                 { err ("SearchTimeLimitExceeded",               E_CALENDAR_STATUS_OTHER_ERROR) },
137                 { err ("InvalidQuery",                          E_CALENDAR_STATUS_OTHER_ERROR) },
138                 { err ("QueryRefused",                          E_CALENDAR_STATUS_OTHER_ERROR) },
139                 { err ("CouldNotCancel",                        E_CALENDAR_STATUS_COULD_NOT_CANCEL) },
140                 { err ("OtherError",                            E_CALENDAR_STATUS_OTHER_ERROR) },
141                 { err ("InvalidServerVersion",                  E_CALENDAR_STATUS_INVALID_SERVER_VERSION) },
142                 { err ("InvalidArg",                            E_CALENDAR_STATUS_INVALID_ARG) },
143                 { err ("NotSupported",                          E_CALENDAR_STATUS_NOT_SUPPORTED) }
144         };
145         #undef err
146
147         if G_LIKELY (error == NULL)
148                 return E_CALENDAR_STATUS_OK;
149
150         if (g_error_matches (error, G_IO_ERROR, G_IO_ERROR_DBUS_ERROR)) {
151                 gchar *name;
152                 gint i;
153
154                 name = g_dbus_error_get_remote_error (error);
155
156                 for (i = 0; i < G_N_ELEMENTS (errors); i++) {
157                         if (g_ascii_strcasecmp (errors[i].name, name) == 0) {
158                                 g_free (name);
159                                 return errors[i].err_code;
160                         }
161                 }
162
163                 g_warning ("Unmatched error name %s", name);
164                 g_free (name);
165
166                 return E_CALENDAR_STATUS_OTHER_ERROR;
167         } else if (error->domain == E_CALENDAR_ERROR) {
168                 return error->code;
169         } else {
170                 /* In this case the error was caused by DBus */
171                 return E_CALENDAR_STATUS_DBUS_EXCEPTION;
172         }
173 }
174
175 /**
176  * e_cal_source_type_enum_get_type:
177  *
178  * Registers the #ECalSourceTypeEnum type with glib.
179  *
180  * Returns: the ID of the #ECalSourceTypeEnum type.
181  *
182  * Deprecated: 3.2: Use e_cal_client_source_type_enum_get_type() instead.
183  */
184 GType
185 e_cal_source_type_enum_get_type (void)
186 {
187         static volatile gsize enum_type__volatile = 0;
188
189         if (g_once_init_enter (&enum_type__volatile)) {
190                 GType enum_type;
191                 static GEnumValue values[] = {
192                         { E_CAL_SOURCE_TYPE_EVENT, "Event", "Event"},
193                         { E_CAL_SOURCE_TYPE_TODO, "ToDo", "ToDo"},
194                         { E_CAL_SOURCE_TYPE_JOURNAL, "Journal", "Journal"},
195                         { E_CAL_SOURCE_TYPE_LAST, "Invalid", "Invalid"},
196                         { -1, NULL, NULL}
197                 };
198
199                 enum_type = g_enum_register_static ("ECalSourceTypeEnum", values);
200                 g_once_init_leave (&enum_type__volatile, enum_type);
201         }
202
203         return enum_type__volatile;
204 }
205
206 /**
207  * e_cal_set_mode_status_enum_get_type:
208  *
209  * Registers the #ECalSetModeStatusEnum type with glib.
210  *
211  * Returns: the ID of the #ECalSetModeStatusEnum type.
212  *
213  * Deprecated: 3.2: This type has been dropped completely.
214  */
215 GType
216 e_cal_set_mode_status_enum_get_type (void)
217 {
218         static volatile gsize enum_type__volatile = 0;
219
220         if (g_once_init_enter (&enum_type__volatile)) {
221                 GType enum_type;
222                 static GEnumValue values[] = {
223                         { E_CAL_SET_MODE_SUCCESS,          "ECalSetModeSuccess",         "success"     },
224                         { E_CAL_SET_MODE_ERROR,            "ECalSetModeError",           "error"       },
225                         { E_CAL_SET_MODE_NOT_SUPPORTED,    "ECalSetModeNotSupported",    "unsupported" },
226                         { -1,                                   NULL,                              NULL}
227                 };
228
229                 enum_type = g_enum_register_static ("ECalSetModeStatusEnum", values);
230                 g_once_init_leave (&enum_type__volatile, enum_type);
231         }
232
233         return enum_type__volatile;
234 }
235
236 /**
237  * cal_mode_enum_get_type:
238  *
239  * Registers the #CalModeEnum type with glib.
240  *
241  * Returns: the ID of the #CalModeEnum type.
242  *
243  * Deprecated: 3.2: This type has been dropped completely.
244  */
245 GType
246 cal_mode_enum_get_type (void)
247 {
248         static volatile gsize enum_type__volatile = 0;
249
250         if (g_once_init_enter (&enum_type__volatile)) {
251                 GType enum_type;
252                 static GEnumValue values[] = {
253                         { CAL_MODE_INVALID,                     "CalModeInvalid",                  "invalid" },
254                         { CAL_MODE_LOCAL,                       "CalModeLocal",                    "local"   },
255                         { CAL_MODE_REMOTE,                      "CalModeRemote",                   "remote"  },
256                         { CAL_MODE_ANY,                         "CalModeAny",                      "any"     },
257                         { -1,                                   NULL,                              NULL      }
258                 };
259
260                 enum_type = g_enum_register_static ("CalModeEnum", values);
261                 g_once_init_leave (&enum_type__volatile, enum_type);
262         }
263
264         return enum_type__volatile;
265 }
266
267 static void
268 cal_backend_died_cb (EClient *client,
269                      ECal *cal)
270 {
271         /* Echo the signal emission from the ECalClient. */
272         g_signal_emit (cal, signals[BACKEND_DIED], 0);
273 }
274
275 static void
276 cal_notify_online_cb (EClient *client,
277                       GParamSpec *pspec,
278                       ECal *cal)
279 {
280         gboolean online = e_client_is_online (client);
281
282         g_signal_emit (
283                 cal, signals[CAL_SET_MODE], 0,
284                 E_CALENDAR_STATUS_OK, online ? Remote : Local);
285 }
286
287 static void
288 cal_set_source (ECal *cal,
289                 ESource *source)
290 {
291         g_return_if_fail (E_IS_SOURCE (source));
292         g_return_if_fail (cal->priv->source == NULL);
293
294         cal->priv->source = g_object_ref (source);
295 }
296
297 static void
298 cal_set_source_type (ECal *cal,
299                      ECalSourceType source_type)
300 {
301         cal->priv->type = source_type;
302 }
303
304 static void
305 cal_set_property (GObject *object,
306                   guint property_id,
307                   const GValue *value,
308                   GParamSpec *pspec)
309 {
310         switch (property_id) {
311                 case PROP_SOURCE:
312                         cal_set_source (
313                                 E_CAL (object),
314                                 g_value_get_object (value));
315                         return;
316
317                 case PROP_SOURCE_TYPE:
318                         cal_set_source_type (
319                                 E_CAL (object),
320                                 g_value_get_enum (value));
321                         return;
322         }
323
324         G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
325 }
326
327 static void
328 cal_get_property (GObject *object,
329                   guint property_id,
330                   GValue *value,
331                   GParamSpec *pspec)
332 {
333         switch (property_id) {
334                 case PROP_SOURCE:
335                         g_value_set_object (
336                                 value, e_cal_get_source (
337                                 E_CAL (object)));
338                         return;
339
340                 case PROP_SOURCE_TYPE:
341                         g_value_set_enum (
342                                 value, e_cal_get_source_type (
343                                 E_CAL (object)));
344                         return;
345         }
346
347         G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
348 }
349
350 static void
351 cal_dispose (GObject *object)
352 {
353         ECalPrivate *priv;
354
355         priv = E_CAL_GET_PRIVATE (object);
356
357         if (priv->client != NULL) {
358                 g_signal_handler_disconnect (
359                         priv->client,
360                         priv->backend_died_handler_id);
361                 g_signal_handler_disconnect (
362                         priv->client,
363                         priv->notify_online_handler_id);
364                 g_object_unref (priv->client);
365                 priv->client = NULL;
366         }
367
368         if (priv->source != NULL) {
369                 g_object_unref (priv->source);
370                 priv->source = NULL;
371         }
372
373         /* Chain up to parent's dispose() method. */
374         G_OBJECT_CLASS (e_cal_parent_class)->dispose (object);
375 }
376
377 static void
378 cal_finalize (GObject *object)
379 {
380         ECalPrivate *priv;
381
382         priv = E_CAL_GET_PRIVATE (object);
383
384         priv->load_state = E_CAL_LOAD_NOT_LOADED;
385
386         if (priv->free_busy_data) {
387                 g_mutex_lock (&priv->free_busy_data_lock);
388                 g_list_foreach (*priv->free_busy_data, (GFunc) g_object_unref, NULL);
389                 g_list_free (*priv->free_busy_data);
390                 *priv->free_busy_data = NULL;
391                 priv->free_busy_data = NULL;
392                 g_mutex_unlock (&priv->free_busy_data_lock);
393         }
394
395         g_mutex_clear (&priv->free_busy_data_lock);
396
397         /* Chain up to parent's finalize() method. */
398         G_OBJECT_CLASS (e_cal_parent_class)->finalize (object);
399 }
400
401 static gboolean
402 cal_initable_init (GInitable *initable,
403                    GCancellable *cancellable,
404                    GError **error)
405 {
406         ECal *cal = E_CAL (initable);
407         ECalClientSourceType source_type;
408         ESource *source;
409
410         source = e_cal_get_source (cal);
411
412         switch (e_cal_get_source_type (cal)) {
413                 case E_CAL_SOURCE_TYPE_EVENT:
414                         source_type = E_CAL_CLIENT_SOURCE_TYPE_EVENTS;
415                         break;
416                 case E_CAL_SOURCE_TYPE_TODO:
417                         source_type = E_CAL_CLIENT_SOURCE_TYPE_TASKS;
418                         break;
419                 case E_CAL_SOURCE_TYPE_JOURNAL:
420                         source_type = E_CAL_CLIENT_SOURCE_TYPE_MEMOS;
421                         break;
422                 default:
423                         g_return_val_if_reached (FALSE);
424         }
425
426         cal->priv->client = e_cal_client_new (source, source_type, error);
427
428         if (cal->priv->client == NULL)
429                 return FALSE;
430
431         cal->priv->backend_died_handler_id = g_signal_connect (
432                 cal->priv->client, "backend-died",
433                 G_CALLBACK (cal_backend_died_cb), cal);
434
435         cal->priv->notify_online_handler_id = g_signal_connect (
436                 cal->priv->client, "notify::online",
437                 G_CALLBACK (cal_notify_online_cb), cal);
438
439         return TRUE;
440 }
441
442 static void
443 e_cal_class_init (ECalClass *class)
444 {
445         GObjectClass *object_class;
446
447         g_type_class_add_private (class, sizeof (ECalPrivate));
448
449         object_class = G_OBJECT_CLASS (class);
450         object_class->set_property = cal_set_property;
451         object_class->get_property = cal_get_property;
452         object_class->dispose = cal_dispose;
453         object_class->finalize = cal_finalize;
454
455         g_object_class_install_property (
456                 object_class,
457                 PROP_SOURCE,
458                 g_param_spec_object (
459                         "source",
460                         "Source",
461                         "The data source for the ECal",
462                         E_TYPE_SOURCE,
463                         G_PARAM_READWRITE |
464                         G_PARAM_CONSTRUCT_ONLY |
465                         G_PARAM_STATIC_STRINGS));
466
467         g_object_class_install_property (
468                 object_class,
469                 PROP_SOURCE_TYPE,
470                 g_param_spec_enum (
471                         "source-type",
472                         "Source Type",
473                         "The iCalendar data type for the ECal",
474                         E_TYPE_CAL_SOURCE_TYPE,
475                         E_CAL_SOURCE_TYPE_EVENT,
476                         G_PARAM_READWRITE |
477                         G_PARAM_CONSTRUCT_ONLY |
478                         G_PARAM_STATIC_STRINGS));
479
480         /* XXX The "cal-opened" signal is deprecated. */
481         signals[CAL_OPENED] = g_signal_new (
482                 "cal_opened",
483                 G_TYPE_FROM_CLASS (class),
484                 G_SIGNAL_RUN_FIRST,
485                 G_STRUCT_OFFSET (ECalClass, cal_opened),
486                 NULL, NULL,
487                 g_cclosure_marshal_VOID__INT,
488                 G_TYPE_NONE, 1, G_TYPE_INT);
489
490         /**
491          * ECal::cal-opened-ex:
492          * @ecal:: self
493          * @error: (type glong):
494          */
495         signals[CAL_OPENED_EX] = g_signal_new (
496                 "cal_opened_ex",
497                 G_TYPE_FROM_CLASS (class),
498                 G_SIGNAL_RUN_FIRST,
499                 G_STRUCT_OFFSET (ECalClass, cal_opened_ex),
500                 NULL, NULL,
501                 g_cclosure_marshal_VOID__POINTER,
502                 G_TYPE_NONE, 1, G_TYPE_POINTER);
503
504         signals[CAL_SET_MODE] = g_signal_new (
505                 "cal_set_mode",
506                 G_TYPE_FROM_CLASS (class),
507                 G_SIGNAL_RUN_FIRST,
508                 G_STRUCT_OFFSET (ECalClass, cal_set_mode),
509                 NULL, NULL,
510                 e_cal_marshal_VOID__ENUM_ENUM,
511                 G_TYPE_NONE, 2,
512                 E_CAL_SET_MODE_STATUS_ENUM_TYPE,
513                 CAL_MODE_ENUM_TYPE);
514
515         signals[BACKEND_ERROR] = g_signal_new (
516                 "backend_error",
517                 G_TYPE_FROM_CLASS (class),
518                 G_SIGNAL_RUN_FIRST,
519                 G_STRUCT_OFFSET (ECalClass, backend_error),
520                 NULL, NULL,
521                 g_cclosure_marshal_VOID__STRING,
522                 G_TYPE_NONE, 1,
523                 G_TYPE_STRING);
524
525         signals[BACKEND_DIED] = g_signal_new (
526                 "backend_died",
527                 G_TYPE_FROM_CLASS (class),
528                 G_SIGNAL_RUN_FIRST,
529                 G_STRUCT_OFFSET (ECalClass, backend_died),
530                 NULL, NULL,
531                 g_cclosure_marshal_VOID__VOID,
532                 G_TYPE_NONE, 0);
533 }
534
535 static void
536 e_cal_initable_init (GInitableIface *interface)
537 {
538         interface->init = cal_initable_init;
539 }
540
541 static void
542 e_cal_init (ECal *ecal)
543 {
544         ecal->priv = E_CAL_GET_PRIVATE (ecal);
545
546         ecal->priv->load_state = E_CAL_LOAD_NOT_LOADED;
547
548         g_mutex_init (&ecal->priv->free_busy_data_lock);
549 }
550
551 static void async_open_report_result (ECal *ecal, const GError *error);
552
553 /**
554  * e_cal_new:
555  * @source: An #ESource to be used for the client.
556  * @type: Type of the client.
557  *
558  * Creates a new calendar client. This does not open the calendar itself,
559  * for that, e_cal_open() or e_cal_open_async() needs to be called.
560  *
561  * Returns: A newly-created calendar client, or NULL if the client could
562  * not be constructed because it could not contact the calendar server.
563  *
564  * Deprecated: 3.2: Use e_cal_client_new() instead.
565  **/
566 ECal *
567 e_cal_new (ESource *source,
568            ECalSourceType type)
569 {
570         g_return_val_if_fail (E_IS_SOURCE (source), NULL);
571         g_return_val_if_fail (type < E_CAL_SOURCE_TYPE_LAST, NULL);
572
573         return g_initable_new (
574                 E_TYPE_CAL, NULL, NULL,
575                 "source", source, "source-type", type, NULL);
576 }
577
578 static void
579 async_open_report_result (ECal *ecal,
580                           const GError *error)
581 {
582         ECalendarStatus status;
583
584         g_return_if_fail (E_IS_CAL (ecal));
585
586         if (!error)
587                 ecal->priv->load_state = E_CAL_LOAD_LOADED;
588
589         if (error) {
590                 status = get_status_from_error (error);
591         } else {
592                 status = E_CALENDAR_STATUS_OK;
593         }
594
595         g_signal_emit (G_OBJECT (ecal), signals[CAL_OPENED], 0, status);
596         g_signal_emit (G_OBJECT (ecal), signals[CAL_OPENED_EX], 0, error);
597 }
598
599 static void
600 async_open_ready_cb (GObject *source_object,
601                      GAsyncResult *result,
602                      gpointer user_data)
603 {
604         ECal *cal = E_CAL (user_data);
605         GError *error = NULL;
606
607         e_client_open_finish (E_CLIENT (source_object), result, &error);
608
609         async_open_report_result (cal, error);
610
611         if (error != NULL)
612                 g_error_free (error);
613
614         g_object_unref (cal);
615 }
616
617 static gboolean
618 open_calendar (ECal *ecal,
619                gboolean only_if_exists,
620                GError **error,
621                ECalendarStatus *status,
622                gboolean async)
623 {
624         gboolean success = TRUE;
625
626         if (ecal->priv->load_state == E_CAL_LOAD_LOADED)
627                 return TRUE;
628
629         ecal->priv->load_state = E_CAL_LOAD_LOADING;
630
631         *status = E_CALENDAR_STATUS_OK;
632         if (!async) {
633                 success = e_client_open_sync (
634                         E_CLIENT (ecal->priv->client),
635                         only_if_exists, NULL, error);
636                 if (success) {
637                         *status = E_CALENDAR_STATUS_OK;
638                         ecal->priv->load_state = E_CAL_LOAD_LOADED;
639                 } else {
640                         *status = E_CALENDAR_STATUS_DBUS_EXCEPTION;
641                         ecal->priv->load_state = E_CAL_LOAD_NOT_LOADED;
642                 }
643         } else {
644                 e_client_open (
645                         E_CLIENT (ecal->priv->client),
646                         only_if_exists, NULL,
647                         async_open_ready_cb,
648                         g_object_ref (ecal));
649         }
650
651         return success;
652 }
653
654 /**
655  * e_cal_open:
656  * @ecal: A calendar client.
657  * @only_if_exists: FALSE if the calendar should be opened even if there
658  * was no storage for it, i.e. to create a new calendar or load an existing
659  * one if it already exists.  TRUE if it should only try to load calendars
660  * that already exist.
661  * @error: Placeholder for error information.
662  *
663  * Makes a calendar client initiate a request to open a calendar.  The calendar
664  * client will emit the "cal_opened" signal when the response from the server is
665  * received. Since 3.0 is emitted also "cal_opened_ex" signal, which contains
666  * a GError pointer from the open operation (NULL when no error occurred).
667  * New signal deprecates the old "cal_opened" signal.
668  *
669  * Returns: TRUE on success, FALSE on failure to issue the open request.
670  *
671  * Deprecated: 3.2: Use e_client_open_sync() on an #ECalClient object instead.
672  **/
673 gboolean
674 e_cal_open (ECal *ecal,
675             gboolean only_if_exists,
676             GError **error)
677 {
678         ECalendarStatus status;
679         GError *err = NULL;
680         gboolean result;
681
682         result = open_calendar (ecal, only_if_exists, &err, &status, FALSE);
683         g_signal_emit (G_OBJECT (ecal), signals[CAL_OPENED], 0, status);
684         g_signal_emit (G_OBJECT (ecal), signals[CAL_OPENED_EX], 0, err);
685
686         if (err)
687                 g_propagate_error (error, err);
688
689         return result;
690 }
691
692 struct idle_async_error_reply_data
693 {
694         ECal *ecal; /* ref-ed */
695         GError *error; /* can be NULL */
696 };
697
698 static gboolean
699 idle_async_error_reply_cb (gpointer user_data)
700 {
701         struct idle_async_error_reply_data *data = user_data;
702
703         g_return_val_if_fail (data != NULL, FALSE);
704         g_return_val_if_fail (data->ecal != NULL, FALSE);
705
706         async_open_report_result (data->ecal, data->error);
707
708         g_object_unref (data->ecal);
709         if (data->error)
710                 g_error_free (data->error);
711         g_free (data);
712
713         return FALSE;
714 }
715
716 /* takes ownership of error */
717 static void
718 async_report_idle (ECal *ecal,
719                    GError *error)
720 {
721         struct idle_async_error_reply_data *data;
722
723         g_return_if_fail (ecal != NULL);
724
725         data = g_new0 (struct idle_async_error_reply_data, 1);
726         data->ecal = g_object_ref (ecal);
727         data->error = error;
728
729         g_idle_add (idle_async_error_reply_cb, data);
730 }
731
732 /**
733  * e_cal_open_async:
734  * @ecal: A calendar client.
735  * @only_if_exists: If TRUE, then only open the calendar if it already
736  * exists.  If FALSE, then create a new calendar if it doesn't already
737  * exist.
738  *
739  * Open the calendar asynchronously.  The calendar will emit the
740  * "cal_opened" signal when the operation has completed.
741  * Since 3.0 is emitted also "cal_opened_ex" signal, which contains
742  * a GError pointer from the open operation (NULL when no error occurred).
743  * New signal deprecates the old "cal_opened" signal.
744  *
745  * Deprecated: 3.2: Use e_client_open()/e_client_open_finish()
746  * on an #ECalClient object instead.
747  **/
748 void
749 e_cal_open_async (ECal *ecal,
750                   gboolean only_if_exists)
751 {
752         ECalPrivate *priv;
753         GError *error = NULL;
754         ECalendarStatus status;
755
756         g_return_if_fail (E_IS_CAL (ecal));
757
758         priv = ecal->priv;
759
760         switch (priv->load_state) {
761         case E_CAL_LOAD_LOADING :
762                 async_report_idle (ecal, g_error_new_literal (E_CALENDAR_ERROR, E_CALENDAR_STATUS_BUSY, e_cal_get_error_message (E_CALENDAR_STATUS_BUSY)));
763                 return;
764         case E_CAL_LOAD_LOADED :
765                 async_report_idle (ecal, NULL /* success */);
766                 return;
767         default:
768                 /* ignore everything else */
769                 break;
770         }
771
772         open_calendar (ecal, only_if_exists, &error, &status, TRUE);
773
774         if (error)
775                 async_report_idle (ecal, error);
776 }
777
778 /**
779  * e_cal_refresh:
780  * @ecal: A calendar client.
781  * @error: Placeholder for error information.
782  *
783  * Invokes refresh on a calendar. See @e_cal_get_refresh_supported.
784  *
785  * Returns: TRUE if calendar supports refresh and it was invoked, FALSE otherwise.
786  *
787  * Since: 2.30
788  *
789  * Deprecated: 3.2: Use e_cal_client_refresh_sync() instead.
790  **/
791 gboolean
792 e_cal_refresh (ECal *ecal,
793                GError **error)
794 {
795         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
796
797         return e_client_refresh_sync (
798                 E_CLIENT (ecal->priv->client), NULL, error);
799 }
800
801 /**
802  * e_cal_remove:
803  * @ecal: A calendar client.
804  * @error: Placeholder for error information.
805  *
806  * Removes a calendar.
807  *
808  * Returns: TRUE if the calendar was removed, FALSE if there was an error.
809  *
810  * Deprecated: 3.2: Use e_client_remove_sync() on an #ECalClient object instead.
811  */
812 gboolean
813 e_cal_remove (ECal *ecal,
814               GError **error)
815 {
816         ESource *source;
817
818         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
819
820         source = e_cal_get_source (ecal);
821
822         return e_source_remove_sync (source, NULL, error);
823 }
824
825 #if 0
826 /* Builds an URI list out of a CORBA string sequence */
827 static GList *
828 build_uri_list (GNOME_Evolution_Calendar_StringSeq *seq)
829 {
830         GList *uris = NULL;
831         gint i;
832
833         for (i = 0; i < seq->_length; i++)
834                 uris = g_list_prepend (uris, g_strdup (seq->_buffer[i]));
835
836         return uris;
837 }
838 #endif
839
840 /**
841  * e_cal_uri_list: (skip)
842  * @ecal: A calendar client.
843  * @mode: Mode of the URIs to get.
844  *
845  * Retrieves a list of all calendar clients for the given mode.
846  *
847  * Returns: list of uris.
848  *
849  * Deprecated: 3.2: This function has been dropped completely.
850  */
851 GList *
852 e_cal_uri_list (ECal *ecal,
853                 CalMode mode)
854 {
855         return NULL;
856 }
857
858 /**
859  * e_cal_get_source_type:
860  * @ecal: A calendar client.
861  *
862  * Gets the type of the calendar client.
863  *
864  * Returns: an #ECalSourceType value corresponding to the type
865  * of the calendar client.
866  *
867  * Deprecated: 3.2: Use e_cal_client_get_source_type() instead.
868  */
869 ECalSourceType
870 e_cal_get_source_type (ECal *ecal)
871 {
872         ECalPrivate *priv;
873
874         g_return_val_if_fail (E_IS_CAL (ecal), E_CAL_SOURCE_TYPE_LAST);
875
876         priv = ecal->priv;
877
878         return priv->type;
879 }
880
881 /**
882  * e_cal_get_load_state:
883  * @ecal: A calendar client.
884  *
885  * Queries the state of loading of a calendar client.
886  *
887  * Returns: A #ECalLoadState value indicating whether the client has
888  * not been loaded with e_cal_open() yet, whether it is being
889  * loaded, or whether it is already loaded.
890  *
891  * Deprecated: 3.2: Use e_client_is_opened() on an #ECalClient instead.
892  **/
893 ECalLoadState
894 e_cal_get_load_state (ECal *ecal)
895 {
896         g_return_val_if_fail (E_IS_CAL (ecal), E_CAL_LOAD_NOT_LOADED);
897
898         return ecal->priv->load_state;
899 }
900
901 /**
902  * e_cal_get_source: (skip)
903  * @ecal: A calendar client.
904  *
905  * Queries the source that is open in a calendar client.
906  *
907  * Returns: The source of the calendar that is already loaded or is being
908  * loaded, or NULL if the ecal has not started a load request yet.
909  *
910  * Deprecated: 3.2: Use e_client_get_source() on an #ECalClient object instead.
911  **/
912 ESource *
913 e_cal_get_source (ECal *ecal)
914 {
915         ECalPrivate *priv;
916
917         g_return_val_if_fail (E_IS_CAL (ecal), NULL);
918
919         priv = ecal->priv;
920         return priv->source;
921 }
922
923 /**
924  * e_cal_get_local_attachment_store:
925  * @ecal: A calendar client.
926  *
927  * Queries the URL where the calendar attachments are
928  * serialized in the local filesystem. This enable clients
929  * to operate with the reference to attachments rather than the data itself
930  * unless it specifically uses the attachments for open/sending
931  * operations.
932  *
933  * Returns: The URL where the attachments are serialized in the
934  * local filesystem.
935  *
936  * Deprecated: 3.2: Use e_cal_client_get_local_attachment_store() instead.
937  **/
938 const gchar *
939 e_cal_get_local_attachment_store (ECal *ecal)
940 {
941         g_return_val_if_fail (E_IS_CAL (ecal), NULL);
942
943         return e_cal_client_get_local_attachment_store (ecal->priv->client);
944 }
945
946 /**
947  * e_cal_is_read_only:
948  * @ecal: A calendar client.
949  * @read_only: Return value for read only status.
950  * @error: Placeholder for error information.
951  *
952  * Queries whether the calendar client can perform modifications
953  * on the calendar or not. Whether the backend is read only or not
954  * is specified, on exit, in the @read_only argument.
955  *
956  * Returns: TRUE if the call was successful, FALSE if there was an error.
957  *
958  * Deprecated: 3.2: Use e_cal_client_is_readonly() on an #ECalClient object instead.
959  */
960 gboolean
961 e_cal_is_read_only (ECal *ecal,
962                     gboolean *read_only,
963                     GError **error)
964 {
965         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
966         g_return_val_if_fail (read_only != NULL, FALSE);
967
968         *read_only = e_client_is_readonly (E_CLIENT (ecal->priv->client));
969
970         return TRUE;
971 }
972
973 /**
974  * e_cal_get_cal_address:
975  * @ecal: A calendar client.
976  * @cal_address: Return value for address information.
977  * @error: Placeholder for error information.
978  *
979  * Queries the calendar address associated with a calendar client.
980  *
981  * Returns: TRUE if the operation was successful, FALSE if there
982  * was an error.
983  *
984  * Deprecated: 3.2: Use e_client_get_backend_property_sync()
985  * with #CAL_BACKEND_PROPERTY_CAL_EMAIL_ADDRESS instead.
986  **/
987 gboolean
988 e_cal_get_cal_address (ECal *ecal,
989                        gchar **cal_address,
990                        GError **error)
991 {
992         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
993         g_return_val_if_fail (cal_address != NULL, FALSE);
994
995         return e_client_get_backend_property_sync (
996                 E_CLIENT (ecal->priv->client),
997                 CAL_BACKEND_PROPERTY_CAL_EMAIL_ADDRESS,
998                 cal_address, NULL, error);
999 }
1000
1001 /**
1002  * e_cal_get_alarm_email_address:
1003  * @ecal: A calendar client.
1004  * @alarm_address: Return value for alarm address.
1005  * @error: Placeholder for error information.
1006  *
1007  * Queries the address to be used for alarms in a calendar client.
1008  *
1009  * Returns: TRUE if the operation was successful, FALSE if there was
1010  * an error while contacting the backend.
1011  *
1012  * Deprecated: 3.2: Use e_client_get_backend_property_sync()
1013  * with #CAL_BACKEND_PROPERTY_ALARM_EMAIL_ADDRESS instead.
1014  */
1015 gboolean
1016 e_cal_get_alarm_email_address (ECal *ecal,
1017                                gchar **alarm_address,
1018                                GError **error)
1019 {
1020         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1021         g_return_val_if_fail (alarm_address != NULL, FALSE);
1022
1023         return e_client_get_backend_property_sync (
1024                 E_CLIENT (ecal->priv->client),
1025                 CAL_BACKEND_PROPERTY_ALARM_EMAIL_ADDRESS,
1026                 alarm_address, NULL, error);
1027 }
1028
1029 /**
1030  * e_cal_get_ldap_attribute:
1031  * @ecal: A calendar client.
1032  * @ldap_attribute: Return value for the LDAP attribute.
1033  * @error: Placeholder for error information.
1034  *
1035  * Queries the LDAP attribute for a calendar client.
1036  *
1037  * Returns: TRUE if the call was successful, FALSE if there was an
1038  * error contacting the backend.
1039  *
1040  * Deprecated: 3.2: This function has been dropped completely.
1041  */
1042 gboolean
1043 e_cal_get_ldap_attribute (ECal *ecal,
1044                           gchar **ldap_attribute,
1045                           GError **error)
1046 {
1047         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1048         g_return_val_if_fail (ldap_attribute != NULL, FALSE);
1049
1050         *ldap_attribute = NULL;
1051
1052         g_set_error (
1053                 error, E_CALENDAR_ERROR,
1054                 E_CALENDAR_STATUS_NOT_SUPPORTED,
1055                 _("Not supported"));
1056
1057         return FALSE;
1058 }
1059
1060 /**
1061  * e_cal_get_one_alarm_only:
1062  * @ecal: A calendar client.
1063  *
1064  * Checks if a calendar supports only one alarm per component.
1065  *
1066  * Returns: TRUE if the calendar allows only one alarm, FALSE otherwise.
1067  *
1068  * Deprecated: 3.2: Use e_cal_client_check_one_alarm_only() instead.
1069  */
1070 gboolean
1071 e_cal_get_one_alarm_only (ECal *ecal)
1072 {
1073         const gchar *cap = CAL_STATIC_CAPABILITY_ONE_ALARM_ONLY;
1074
1075         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1076
1077         return e_cal_get_static_capability (ecal, cap);
1078 }
1079
1080 /**
1081  * e_cal_get_organizer_must_attend:
1082  * @ecal: A calendar client.
1083  *
1084  * Checks if a calendar forces organizers of meetings to be also attendees.
1085  *
1086  * Returns: TRUE if the calendar forces organizers to attend meetings,
1087  * FALSE otherwise.
1088  *
1089  * Deprecated: 3.2: Use e_cal_client_check_organizer_must_attend() instead.
1090  */
1091 gboolean
1092 e_cal_get_organizer_must_attend (ECal *ecal)
1093 {
1094         const gchar *cap = CAL_STATIC_CAPABILITY_ORGANIZER_MUST_ATTEND;
1095
1096         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1097
1098         return e_cal_get_static_capability (ecal, cap);
1099 }
1100
1101 /**
1102  * e_cal_get_recurrences_no_master:
1103  * @ecal: A calendar client.
1104  *
1105  * Checks if the calendar has a master object for recurrences.
1106  *
1107  * Returns: TRUE if the calendar has a master object for recurrences,
1108  * FALSE otherwise.
1109  *
1110  * Deprecated: 3.2: Use e_cal_client_check_recurrences_no_master() instead.
1111  */
1112 gboolean
1113 e_cal_get_recurrences_no_master (ECal *ecal)
1114 {
1115         const gchar *cap = CAL_STATIC_CAPABILITY_RECURRENCES_NO_MASTER;
1116
1117         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1118
1119         return e_cal_get_static_capability (ecal, cap);
1120 }
1121
1122 /**
1123  * e_cal_get_static_capability:
1124  * @ecal: A calendar client.
1125  * @cap: Name of the static capability to check.
1126  *
1127  * Queries the calendar for static capabilities.
1128  *
1129  * Returns: TRUE if the capability is supported, FALSE otherwise.
1130  *
1131  * Deprecated: 3.2: Use e_client_check_capability() on an #ECalClient object instead.
1132  */
1133 gboolean
1134 e_cal_get_static_capability (ECal *ecal,
1135                              const gchar *cap)
1136 {
1137         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1138         g_return_val_if_fail (cap != NULL, FALSE);
1139
1140         return e_client_check_capability (E_CLIENT (ecal->priv->client), cap);
1141 }
1142
1143 /**
1144  * e_cal_get_save_schedules:
1145  * @ecal: A calendar client.
1146  *
1147  * Checks whether the calendar saves schedules.
1148  *
1149  * Returns: TRUE if it saves schedules, FALSE otherwise.
1150  *
1151  * Deprecated: 3.2: Use e_cal_client_check_save_schedules() instead.
1152  */
1153 gboolean
1154 e_cal_get_save_schedules (ECal *ecal)
1155 {
1156         const gchar *cap = CAL_STATIC_CAPABILITY_SAVE_SCHEDULES;
1157
1158         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1159
1160         return e_cal_get_static_capability (ecal, cap);
1161 }
1162
1163 /**
1164  * e_cal_get_organizer_must_accept:
1165  * @ecal: A calendar client.
1166  *
1167  * Checks whether a calendar requires organizer to accept their attendance to
1168  * meetings.
1169  *
1170  * Returns: TRUE if the calendar requires organizers to accept, FALSE
1171  * otherwise.
1172  *
1173  * Deprecated: 3.2: Use e_cal_client_check_organizer_must_accept() instead.
1174  */
1175 gboolean
1176 e_cal_get_organizer_must_accept (ECal *ecal)
1177 {
1178         const gchar *cap = CAL_STATIC_CAPABILITY_ORGANIZER_MUST_ACCEPT;
1179
1180         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1181
1182         return e_cal_get_static_capability (ecal, cap);
1183 }
1184
1185 /**
1186  * e_cal_get_refresh_supported:
1187  * @ecal: A calendar client.
1188  *
1189  * Checks whether a calendar supports explicit refreshing (see @e_cal_refresh).
1190  *
1191  * Returns: TRUE if the calendar supports refreshing, FALSE otherwise.
1192  *
1193  * Since: 2.30
1194  *
1195  * Deprecated: 3.2: Use e_client_check_refresh_supported() instead.
1196  */
1197 gboolean
1198 e_cal_get_refresh_supported (ECal *ecal)
1199 {
1200         const gchar *cap = CAL_STATIC_CAPABILITY_REFRESH_SUPPORTED;
1201
1202         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1203
1204         return e_cal_get_static_capability (ecal, cap);
1205 }
1206
1207 /**
1208  * e_cal_set_mode: (skip)
1209  * @ecal: A calendar client.
1210  * @mode: Mode to switch to.
1211  *
1212  * Switches online/offline mode on the calendar.
1213  *
1214  * Returns: TRUE if the switch was successful, FALSE if there was an error.
1215  *
1216  * Deprecated: 3.2: This function has been dropped completely.
1217  */
1218 gboolean
1219 e_cal_set_mode (ECal *ecal,
1220                 CalMode mode)
1221 {
1222         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1223         g_return_val_if_fail (mode & CAL_MODE_ANY, FALSE);
1224
1225         g_warning ("%s: This function is not supported since 3.2", G_STRFUNC);
1226
1227         return FALSE;
1228 }
1229
1230 /**
1231  * e_cal_get_default_object: (skip)
1232  * @ecal: A calendar client.
1233  * @icalcomp: Return value for the default object.
1234  * @error: Placeholder for error information.
1235  *
1236  * Retrives an #icalcomponent from the backend that contains the default
1237  * values for properties needed.
1238  *
1239  * Returns: TRUE if the call was successful, FALSE otherwise.
1240  *
1241  * Deprecated: 3.2: Use e_cal_client_get_default_object_sync() instead.
1242  */
1243 gboolean
1244 e_cal_get_default_object (ECal *ecal,
1245                           icalcomponent **icalcomp,
1246                           GError **error)
1247 {
1248         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1249         g_return_val_if_fail (icalcomp != NULL, FALSE);
1250
1251         return e_cal_client_get_default_object_sync (
1252                 ecal->priv->client, icalcomp, NULL, error);
1253 }
1254
1255 /**
1256  * e_cal_get_attachments_for_comp: (skip)
1257  * @ecal: A calendar client.
1258  * @uid: Unique identifier for a calendar component.
1259  * @rid: Recurrence identifier.
1260  * @list: Return the list of attachment uris.
1261  * @error: Placeholder for error information.
1262  *
1263  * Queries a calendar for a calendar component object based on its unique
1264  * identifier and gets the attachments for the component.
1265  *
1266  * Returns: TRUE if the call was successful, FALSE otherwise.
1267  *
1268  * Deprecated: 3.2: Use e_cal_client_get_attachment_uris_sync() instead.
1269  **/
1270 gboolean
1271 e_cal_get_attachments_for_comp (ECal *ecal,
1272                                 const gchar *uid,
1273                                 const gchar *rid,
1274                                 GSList **list,
1275                                 GError **error)
1276 {
1277         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1278         g_return_val_if_fail (uid != NULL, FALSE);
1279         g_return_val_if_fail (list != NULL, FALSE);
1280
1281         return e_cal_client_get_attachment_uris_sync (
1282                 ecal->priv->client, uid, rid, list, NULL, error);
1283 }
1284
1285 /**
1286  * e_cal_get_object: (skip)
1287  * @ecal: A calendar client.
1288  * @uid: Unique identifier for a calendar component.
1289  * @rid: Recurrence identifier.
1290  * @icalcomp: Return value for the calendar component object.
1291  * @error: Placeholder for error information.
1292  *
1293  * Queries a calendar for a calendar component object based on its unique
1294  * identifier.
1295  *
1296  * Returns: TRUE if the call was successful, FALSE otherwise.
1297  *
1298  * Deprecated: 3.2: Use e_cal_client_get_object_sync() instead.
1299  **/
1300 gboolean
1301 e_cal_get_object (ECal *ecal,
1302                   const gchar *uid,
1303                   const gchar *rid,
1304                   icalcomponent **icalcomp,
1305                   GError **error)
1306 {
1307         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1308         g_return_val_if_fail (uid != NULL, FALSE);
1309         g_return_val_if_fail (icalcomp != NULL, FALSE);
1310
1311         return e_cal_client_get_object_sync (
1312                 ecal->priv->client, uid, rid, icalcomp, NULL, error);
1313 }
1314
1315 /**
1316  * e_cal_get_objects_for_uid: (skip)
1317  * @ecal: A calendar client.
1318  * @uid: Unique identifier for a calendar component.
1319  * @objects: Return value for the list of objects obtained from the backend.
1320  * @error: Placeholder for error information.
1321  *
1322  * Queries a calendar for all calendar components with the given unique
1323  * ID. This will return any recurring event and all its detached recurrences.
1324  * For non-recurring events, it will just return the object with that ID.
1325  *
1326  * Returns: TRUE if the call was successful, FALSE otherwise.
1327  *
1328  * Deprecated: 3.2: Use e_cal_client_get_objects_for_uid_sync() instead.
1329  **/
1330 gboolean
1331 e_cal_get_objects_for_uid (ECal *ecal,
1332                            const gchar *uid,
1333                            GList **objects,
1334                            GError **error)
1335 {
1336         GSList *slist = NULL;
1337         gboolean success;
1338
1339         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1340         g_return_val_if_fail (uid != NULL, FALSE);
1341         g_return_val_if_fail (objects != NULL, FALSE);
1342
1343         *objects = NULL;
1344
1345         success = e_cal_client_get_objects_for_uid_sync (
1346                 ecal->priv->client, uid, &slist, NULL, error);
1347
1348         if (slist != NULL) {
1349                 GSList *link;
1350
1351                 /* XXX Never use GSList in a public API. */
1352                 for (link = slist; link != NULL; link = g_slist_next (link))
1353                         *objects = g_list_prepend (*objects, link->data);
1354                 *objects = g_list_reverse (*objects);
1355
1356                 g_slist_free (slist);
1357         }
1358
1359         return success;
1360 }
1361
1362 /**
1363  * e_cal_resolve_tzid_cb: (skip)
1364  * @tzid: ID of the timezone to resolve.
1365  * @data: Closure data for the callback.
1366  *
1367  * Resolves TZIDs for the recurrence generator.
1368  *
1369  * Returns: The timezone identified by the @tzid argument, or %NULL if
1370  * it could not be found.
1371  *
1372  * Deprecated: 3.2: Use e_cal_client_resolve_tzid_cb() instead.
1373  */
1374 icaltimezone *
1375 e_cal_resolve_tzid_cb (const gchar *tzid,
1376                        gpointer data)
1377 {
1378         ECal *ecal;
1379         icaltimezone *zone = NULL;
1380
1381         g_return_val_if_fail (data != NULL, NULL);
1382         g_return_val_if_fail (E_IS_CAL (data), NULL);
1383
1384         ecal = E_CAL (data);
1385
1386         /* FIXME: Handle errors. */
1387         e_cal_get_timezone (ecal, tzid, &zone, NULL);
1388
1389         return zone;
1390 }
1391
1392 /**
1393  * e_cal_get_changes: (skip)
1394  * @ecal: A calendar client.
1395  * @change_id: ID to use for comparing changes.
1396  * @changes: Return value for the list of changes.
1397  * @error: Placeholder for error information.
1398  *
1399  * Returns a list of changes made to the calendar since a specific time. That time
1400  * is identified by the @change_id argument, which is used by the backend to
1401  * compute the changes done.
1402  *
1403  * Returns: %TRUE if the call was successful, %FALSE otherwise.
1404  *
1405  * Deprecated: 3.2: This function has been dropped completely.
1406  */
1407 gboolean
1408 e_cal_get_changes (ECal *ecal,
1409                    const gchar *change_id,
1410                    GList **changes,
1411                    GError **error)
1412 {
1413
1414         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1415         g_return_val_if_fail (change_id != NULL, FALSE);
1416         g_return_val_if_fail (changes != NULL, FALSE);
1417
1418         *changes = NULL;
1419
1420         g_set_error (
1421                 error, E_CALENDAR_ERROR,
1422                 E_CALENDAR_STATUS_NOT_SUPPORTED,
1423                 _("Not supported"));
1424
1425         return FALSE;
1426 }
1427
1428 /**
1429  * e_cal_free_change_list: (skip)
1430  * @list: List of changes to be freed.
1431  *
1432  * Free a list of changes as returned by e_cal_get_changes().
1433  *
1434  * Deprecated: 3.2: Use () instead.
1435  */
1436 void
1437 e_cal_free_change_list (GList *list)
1438 {
1439         ECalChange *c;
1440         GList *l;
1441
1442         for (l = list; l; l = l->next) {
1443                 c = l->data;
1444
1445                 if (c != NULL && c->comp != NULL) {
1446                         g_object_unref (G_OBJECT (c->comp));
1447                         g_free (c);
1448                 } else
1449                         g_warn_if_reached ();
1450         }
1451
1452         g_list_free (list);
1453 }
1454
1455 /**
1456  * e_cal_get_object_list:
1457  * @ecal: A calendar client.
1458  * @query: Query string.
1459  * @objects: (out) (element-type long): Return value for list of objects.
1460  * @error: Placeholder for error information.
1461  *
1462  * Gets a list of objects from the calendar that match the query specified
1463  * by the @query argument. The objects will be returned in the @objects
1464  * argument, which is a list of #icalcomponent. When done, this list
1465  * should be freed by using the e_cal_free_object_list() function.
1466  *
1467  * Returns: TRUE if the operation was successful, FALSE otherwise.
1468  *
1469  * Deprecated: 3.2: Use e_cal_client_get_object_list_sync() instead.
1470  **/
1471 gboolean
1472 e_cal_get_object_list (ECal *ecal,
1473                        const gchar *query,
1474                        GList **objects,
1475                        GError **error)
1476 {
1477         GSList *slist = NULL;
1478         gboolean success;
1479
1480         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1481         g_return_val_if_fail (query != NULL, FALSE);
1482         g_return_val_if_fail (objects != NULL, FALSE);
1483
1484         *objects = NULL;
1485
1486         success = e_cal_client_get_object_list_sync (
1487                 ecal->priv->client, query, &slist, NULL, error);
1488
1489         if (slist != NULL) {
1490                 GSList *link;
1491
1492                 /* XXX Never use GSList in a public API. */
1493                 for (link = slist; link != NULL; link = g_slist_next (link))
1494                         *objects = g_list_prepend (*objects, link->data);
1495                 *objects = g_list_reverse (*objects);
1496
1497                 g_slist_free (slist);
1498         }
1499
1500         return success;
1501 }
1502
1503 /**
1504  * e_cal_get_object_list_as_comp: (skip)
1505  * @ecal: A calendar client.
1506  * @query: Query string.
1507  * @objects: Return value for list of objects.
1508  * @error: Placeholder for error information.
1509  *
1510  * Gets a list of objects from the calendar that match the query specified
1511  * by the @query argument. The objects will be returned in the @objects
1512  * argument, which is a list of #ECalComponent.
1513  *
1514  * Returns: TRUE if the operation was successful, FALSE otherwise.
1515  *
1516  * Deprecated: 3.2: Use e_cal_client_get_object_list_as_comps_sync() instead.
1517  */
1518 gboolean
1519 e_cal_get_object_list_as_comp (ECal *ecal,
1520                                const gchar *query,
1521                                GList **objects,
1522                                GError **error)
1523 {
1524         GSList *slist = NULL;
1525         gboolean success;
1526
1527         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1528         g_return_val_if_fail (query != NULL, FALSE);
1529         g_return_val_if_fail (objects != NULL, FALSE);
1530
1531         *objects = NULL;
1532
1533         success = e_cal_client_get_object_list_as_comps_sync (
1534                 ecal->priv->client, query, &slist, NULL, error);
1535
1536         if (slist != NULL) {
1537                 GSList *link;
1538
1539                 /* XXX Never use GSList in a public API. */
1540                 for (link = slist; link != NULL; link = g_slist_next (link))
1541                         *objects = g_list_prepend (*objects, link->data);
1542                 *objects = g_list_reverse (*objects);
1543
1544                 g_slist_free (slist);
1545         }
1546
1547         return success;
1548 }
1549
1550 /**
1551  * e_cal_free_object_list: (skip)
1552  * @objects: List of objects to be freed.
1553  *
1554  * Frees a list of objects as returned by e_cal_get_object_list().
1555  *
1556  * Deprecated: 3.2: Use e_cal_client_free_icalcomp_slist() instead.
1557  */
1558 void
1559 e_cal_free_object_list (GList *objects)
1560 {
1561         g_list_free_full (objects, (GDestroyNotify) icalcomponent_free);
1562 }
1563
1564 /**
1565  * e_cal_get_free_busy: (skip)
1566  * @ecal: A calendar client.
1567  * @users: List of users to retrieve free/busy information for.
1568  * @start: Start time for query.
1569  * @end: End time for query.
1570  * @freebusy: Return value for VFREEBUSY objects.
1571  * @error: Placeholder for error information.
1572  *
1573  * Gets free/busy information from the calendar server.
1574  *
1575  * Returns: TRUE if the operation was successful, FALSE otherwise.
1576  *
1577  * Deprecated: 3.2: Use e_cal_client_get_free_busy_sync() instead.
1578  */
1579 gboolean
1580 e_cal_get_free_busy (ECal *ecal,
1581                      GList *users,
1582                      time_t start,
1583                      time_t end,
1584                      GList **freebusy,
1585                      GError **error)
1586 {
1587         GSList *slist = NULL;
1588         gboolean success;
1589
1590         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1591         g_return_val_if_fail (users != NULL, FALSE);
1592         g_return_val_if_fail (freebusy != NULL, FALSE);
1593
1594         *freebusy = NULL;
1595
1596         /* XXX Never use GSList in a public API. */
1597         for (; users != NULL; users = g_list_next (users))
1598                 slist = g_slist_prepend (slist, users->data);
1599
1600         /* FIXME ECalClient's API for this is a giant W.T.F.
1601          *       There's no way to populate the freebusy list
1602          *       in a way that will avoid deadlocking for all
1603          *       cases.  I guess leave the list empty and hope
1604          *       no one notices until ECalClient grows a saner
1605          *       free/busy API. */
1606         success = e_cal_client_get_free_busy_sync (
1607                 ecal->priv->client, start, end, slist, NULL, error);
1608
1609         g_slist_free (slist);
1610
1611         return success;
1612 }
1613
1614 /**
1615  * e_cal_generate_instances: (skip)
1616  * @ecal: A calendar client.
1617  * @start: Start time for query.
1618  * @end: End time for query.
1619  * @cb: Callback for each generated instance.
1620  * @cb_data: Closure data for the callback.
1621  *
1622  * Does a combination of e_cal_get_object_list() and
1623  * e_cal_recur_generate_instances().
1624  *
1625  * The callback function should do a g_object_ref() of the calendar component
1626  * it gets passed if it intends to keep it around, since it will be unref'ed
1627  * as soon as the callback returns.
1628  *
1629  * Deprecated: 3.2: Use e_cal_client_generate_instances() instead.
1630  **/
1631 void
1632 e_cal_generate_instances (ECal *ecal,
1633                           time_t start,
1634                           time_t end,
1635                           ECalRecurInstanceFn cb,
1636                           gpointer cb_data)
1637 {
1638         g_return_if_fail (E_IS_CAL (ecal));
1639
1640         e_cal_client_generate_instances_sync (
1641                 ecal->priv->client, start, end, cb, cb_data);
1642 }
1643
1644 /**
1645  * e_cal_generate_instances_for_object: (skip)
1646  * @ecal: A calendar client.
1647  * @icalcomp: Object to generate instances from.
1648  * @start: Start time for query.
1649  * @end: End time for query.
1650  * @cb: Callback for each generated instance.
1651  * @cb_data: Closure data for the callback.
1652  *
1653  * Does a combination of e_cal_get_object_list() and
1654  * e_cal_recur_generate_instances(), like e_cal_generate_instances(), but
1655  * for a single object.
1656  *
1657  * The callback function should do a g_object_ref() of the calendar component
1658  * it gets passed if it intends to keep it around, since it will be unref'ed
1659  * as soon as the callback returns.
1660  *
1661  * Deprecated: 3.2: Use e_cal_client_generate_instances_for_object() instead.
1662  **/
1663 void
1664 e_cal_generate_instances_for_object (ECal *ecal,
1665                                      icalcomponent *icalcomp,
1666                                      time_t start,
1667                                      time_t end,
1668                                      ECalRecurInstanceFn cb,
1669                                      gpointer cb_data)
1670 {
1671         g_return_if_fail (E_IS_CAL (ecal));
1672
1673         e_cal_client_generate_instances_for_object (
1674                 ecal->priv->client, icalcomp,
1675                 start, end, NULL, cb, cb_data, NULL);
1676 }
1677
1678 /* Builds a list of ECalComponentAlarms structures */
1679 static GSList *
1680 build_component_alarms_list (ECal *ecal,
1681                              GList *object_list,
1682                              time_t start,
1683                              time_t end)
1684 {
1685         icaltimezone *default_zone;
1686         GSList *comp_alarms;
1687         GList *l;
1688
1689         comp_alarms = NULL;
1690
1691         default_zone = e_cal_client_get_default_timezone (ecal->priv->client);
1692
1693         for (l = object_list; l != NULL; l = l->next) {
1694                 ECalComponent *comp;
1695                 ECalComponentAlarms *alarms;
1696                 ECalComponentAlarmAction omit[] = {-1};
1697
1698                 comp = e_cal_component_new ();
1699                 if (!e_cal_component_set_icalcomponent (comp, icalcomponent_new_clone (l->data))) {
1700                         g_object_unref (G_OBJECT (comp));
1701                         continue;
1702                 }
1703
1704                 alarms = e_cal_util_generate_alarms_for_comp (
1705                         comp, start, end, omit, e_cal_resolve_tzid_cb,
1706                         ecal, default_zone);
1707                 if (alarms)
1708                         comp_alarms = g_slist_prepend (comp_alarms, alarms);
1709         }
1710
1711         return comp_alarms;
1712 }
1713
1714 /**
1715  * e_cal_get_alarms_in_range: (skip)
1716  * @ecal: A calendar client.
1717  * @start: Start time for query.
1718  * @end: End time for query.
1719  *
1720  * Queries a calendar for the alarms that trigger in the specified range of
1721  * time.
1722  *
1723  * Returns: A list of #ECalComponentAlarms structures.  This should be freed
1724  * using the e_cal_free_alarms() function, or by freeing each element
1725  * separately with e_cal_component_alarms_free() and then freeing the list with
1726  * g_slist_free().
1727  *
1728  * Deprecated: 3.2: This function has been dropped completely.
1729  **/
1730 GSList *
1731 e_cal_get_alarms_in_range (ECal *ecal,
1732                            time_t start,
1733                            time_t end)
1734 {
1735         ECalPrivate *priv;
1736         GSList *alarms;
1737         gchar *sexp, *iso_start, *iso_end;
1738         GList *object_list = NULL;
1739
1740         g_return_val_if_fail (E_IS_CAL (ecal), NULL);
1741
1742         priv = ecal->priv;
1743         g_return_val_if_fail (priv->load_state == E_CAL_LOAD_LOADED, NULL);
1744
1745         g_return_val_if_fail (start >= 0 && end >= 0, NULL);
1746         g_return_val_if_fail (start <= end, NULL);
1747
1748         iso_start = isodate_from_time_t (start);
1749         if (!iso_start)
1750                 return NULL;
1751
1752         iso_end = isodate_from_time_t (end);
1753         if (!iso_end) {
1754                 g_free (iso_start);
1755                 return NULL;
1756         }
1757
1758         /* build the query string */
1759         sexp = g_strdup_printf (
1760                 "(has-alarms-in-range? "
1761                 "(make-time \"%s\") "
1762                 "(make-time \"%s\"))",
1763                 iso_start, iso_end);
1764         g_free (iso_start);
1765         g_free (iso_end);
1766
1767         /* execute the query on the server */
1768         if (!e_cal_get_object_list (ecal, sexp, &object_list, NULL)) {
1769                 g_free (sexp);
1770                 return NULL;
1771         }
1772
1773         alarms = build_component_alarms_list (ecal, object_list, start, end);
1774
1775         g_list_foreach (object_list, (GFunc) icalcomponent_free, NULL);
1776         g_list_free (object_list);
1777         g_free (sexp);
1778
1779         return alarms;
1780 }
1781
1782 /**
1783  * e_cal_free_alarms: (skip)
1784  * @comp_alarms: A list of #ECalComponentAlarms structures.
1785  *
1786  * Frees a list of #ECalComponentAlarms structures as returned by
1787  * e_cal_get_alarms_in_range().
1788  *
1789  * Deprecated: 3.2: This function has been dropped completely.
1790  **/
1791 void
1792 e_cal_free_alarms (GSList *comp_alarms)
1793 {
1794         GSList *l;
1795
1796         for (l = comp_alarms; l; l = l->next) {
1797                 ECalComponentAlarms *alarms;
1798
1799                 alarms = l->data;
1800                 if (alarms != NULL)
1801                         e_cal_component_alarms_free (alarms);
1802                 else
1803                         g_warn_if_reached ();
1804         }
1805
1806         g_slist_free (comp_alarms);
1807 }
1808
1809 /**
1810  * e_cal_get_alarms_for_object:
1811  * @ecal: A calendar client.
1812  * @id: Unique identifier for a calendar component.
1813  * @start: Start time for query.
1814  * @end: End time for query.
1815  * @alarms: Return value for the component's alarm instances.  Will return NULL
1816  * if no instances occur within the specified time range.  This should be freed
1817  * using the e_cal_component_alarms_free() function.
1818  *
1819  * Queries a calendar for the alarms of a particular object that trigger in the
1820  * specified range of time.
1821  *
1822  * Returns: TRUE on success, FALSE if the object was not found.
1823  *
1824  * Deprecated: 3.2: This function has been dropped completely.
1825  **/
1826 gboolean
1827 e_cal_get_alarms_for_object (ECal *ecal,
1828                              const ECalComponentId *id,
1829                              time_t start,
1830                              time_t end,
1831                              ECalComponentAlarms **alarms)
1832 {
1833         ECalPrivate *priv;
1834         icalcomponent *icalcomp;
1835         icaltimezone *default_zone;
1836         ECalComponent *comp;
1837         ECalComponentAlarmAction omit[] = {-1};
1838
1839         g_return_val_if_fail (alarms != NULL, FALSE);
1840         *alarms = NULL;
1841
1842         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1843
1844         priv = ecal->priv;
1845         g_return_val_if_fail (priv->load_state == E_CAL_LOAD_LOADED, FALSE);
1846
1847         g_return_val_if_fail (id != NULL, FALSE);
1848         g_return_val_if_fail (start >= 0 && end >= 0, FALSE);
1849         g_return_val_if_fail (start <= end, FALSE);
1850
1851         if (!e_cal_get_object (ecal, id->uid, id->rid, &icalcomp, NULL))
1852                 return FALSE;
1853         if (!icalcomp)
1854                 return FALSE;
1855
1856         comp = e_cal_component_new ();
1857         if (!e_cal_component_set_icalcomponent (comp, icalcomp)) {
1858                 icalcomponent_free (icalcomp);
1859                 g_object_unref (G_OBJECT (comp));
1860                 return FALSE;
1861         }
1862
1863         default_zone = e_cal_client_get_default_timezone (ecal->priv->client);
1864
1865         *alarms = e_cal_util_generate_alarms_for_comp (
1866                 comp, start, end, omit, e_cal_resolve_tzid_cb,
1867                 ecal, default_zone);
1868
1869         return TRUE;
1870 }
1871
1872 /**
1873  * e_cal_discard_alarm:
1874  * @ecal: A calendar ecal.
1875  * @comp: The component to discard the alarm from.
1876  * @auid: Unique identifier of the alarm to be discarded.
1877  * @error: Placeholder for error information.
1878  *
1879  * Tells the calendar backend to get rid of the alarm identified by the
1880  * @auid argument in @comp. Some backends might remove the alarm or
1881  * update internal information about the alarm be discarded, or, like
1882  * the file backend does, ignore the operation.
1883  *
1884  * CALOBJ_MOD_ONLY_THIS is not supported in this call.
1885  *
1886  * Returns: TRUE if the operation was successful, FALSE otherwise.
1887  *
1888  * Deprecated: 3.2: Use e_cal_client_discard_alarm_sync() instead.
1889  */
1890 gboolean
1891 e_cal_discard_alarm (ECal *ecal,
1892                      ECalComponent *comp,
1893                      const gchar *auid,
1894                      GError **error)
1895 {
1896         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1897         g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE);
1898         g_return_val_if_fail (auid != NULL, FALSE);
1899
1900         g_set_error (
1901                 error, E_CALENDAR_ERROR,
1902                 E_CALENDAR_STATUS_NOT_SUPPORTED,
1903                 _("Not supported"));
1904
1905         return FALSE;
1906 }
1907
1908 /**
1909  * e_cal_get_component_as_string: (skip)
1910  * @ecal: A calendar client.
1911  * @icalcomp: A calendar component object.
1912  *
1913  * Gets a calendar component as an iCalendar string, with a toplevel
1914  * VCALENDAR component and all VTIMEZONEs needed for the component.
1915  *
1916  * Returns: the component as a complete iCalendar string, or NULL on
1917  * failure. The string should be freed after use.
1918  *
1919  * Deprecated: 3.2: Use e_cal_client_get_component_as_string() instead.
1920  **/
1921 gchar *
1922 e_cal_get_component_as_string (ECal *ecal,
1923                                icalcomponent *icalcomp)
1924 {
1925         g_return_val_if_fail (E_IS_CAL (ecal), NULL);
1926         g_return_val_if_fail (icalcomp != NULL, NULL);
1927
1928         return e_cal_client_get_component_as_string (
1929                 ecal->priv->client, icalcomp);
1930 }
1931
1932 /**
1933  * e_cal_create_object: (skip)
1934  * @ecal: A calendar client.
1935  * @icalcomp: The component to create.
1936  * @uid: Return value for the UID assigned to the new component by the calendar backend.
1937  * @error: Placeholder for error information.
1938  *
1939  * Requests the calendar backend to create the object specified by the @icalcomp
1940  * argument. Some backends would assign a specific UID to the newly created object,
1941  * in those cases that UID would be returned in the @uid argument.
1942  *
1943  * Returns: TRUE if the operation was successful, FALSE otherwise.
1944  *
1945  * Deprecated: 3.2: Use e_cal_client_create_object_sync() instead.
1946  */
1947 gboolean
1948 e_cal_create_object (ECal *ecal,
1949                      icalcomponent *icalcomp,
1950                      gchar **uid,
1951                      GError **error)
1952 {
1953         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1954         g_return_val_if_fail (icalcomp != NULL, FALSE);
1955         g_return_val_if_fail (uid != NULL, FALSE);
1956
1957         return e_cal_client_create_object_sync (
1958                 ecal->priv->client, icalcomp, uid, NULL, error);
1959 }
1960
1961 /**
1962  * e_cal_modify_object: (skip)
1963  * @ecal: A calendar client.
1964  * @icalcomp: Component to modify.
1965  * @mod: Type of modification.
1966  * @error: Placeholder for error information.
1967  *
1968  * Requests the calendar backend to modify an existing object. If the object
1969  * does not exist on the calendar, an error will be returned.
1970  *
1971  * For recurrent appointments, the @mod argument specifies what to modify,
1972  * if all instances (CALOBJ_MOD_ALL), a single instance (CALOBJ_MOD_THIS),
1973  * or a specific set of instances (CALOBJ_MOD_THISNADPRIOR and
1974  * CALOBJ_MOD_THISANDFUTURE).
1975  *
1976  * Returns: TRUE if the operation was successful, FALSE otherwise.
1977  *
1978  * Deprecated: 3.2: Use e_cal_client_modify_object_sync() instead.
1979  */
1980 gboolean
1981 e_cal_modify_object (ECal *ecal,
1982                      icalcomponent *icalcomp,
1983                      CalObjModType mod,
1984                      GError **error)
1985 {
1986         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
1987         g_return_val_if_fail (icalcomp != NULL, FALSE);
1988
1989         return e_cal_client_modify_object_sync (
1990                 ecal->priv->client, icalcomp, mod, NULL, error);
1991 }
1992
1993 /**
1994  * e_cal_remove_object_with_mod: (skip)
1995  * @ecal: A calendar client.
1996  * @uid: UID of the object to remove.
1997  * @rid: Recurrence ID of the specific recurrence to remove.
1998  * @mod: Type of removal.
1999  * @error: Placeholder for error information.
2000  *
2001  * This function allows the removal of instances of a recurrent
2002  * appointment. If what you want is to remove all instances, use
2003  * e_cal_remove_object instead.
2004  *
2005  * By using a combination of the @uid, @rid and @mod arguments, you
2006  * can remove specific instances. @uid is mandatory.  Empty or NULL
2007  * @rid selects the parent appointment (the one with the recurrence
2008  * rule). A non-empty @rid selects the recurrence at the time specified
2009  * in @rid, using the same time zone as the parent appointment's start
2010  * time.
2011  *
2012  * The exact semantic then depends on @mod. CALOBJ_MOD_THIS,
2013  * CALOBJ_MOD_THISANDPRIOR, CALOBJ_MOD_THISANDFUTURE and
2014  * CALOBJ_MOD_ALL ensure that the event does not recur at the selected
2015  * instance(s). This is done by removing any detached recurrence
2016  * matching the selection criteria and modifying the parent
2017  * appointment (adding EXDATE, adjusting recurrence rules, etc.).  It
2018  * is not an error if @uid+@rid do not match an existing instance.
2019  *
2020  * If not all instances are removed, the client will get a
2021  * "obj_modified" signal for the parent appointment, while it will get
2022  * an "obj_removed" signal when all instances are removed.
2023  *
2024  * CALOBJ_MOD_ONLY_THIS changes the semantic of CALOBJ_MOD_THIS: @uid
2025  * and @rid must select an existing instance. That instance is
2026  * removed without modifying the parent appointment. In other words,
2027  * e_cal_remove_object_with_mod(CALOBJ_MOD_ONLY_THIS) is the inverse
2028  * operation for adding a detached recurrence. The client is
2029  * always sent an "obj_removed" signal.
2030  *
2031  * Note that not all backends support CALOBJ_MOD_ONLY_THIS. Check for
2032  * the CAL_STATIC_CAPABILITY_REMOVE_ONLY_THIS capability before using
2033  * it. Previous releases did not check consistently for unknown
2034  * @mod values, using it with them may have had unexpected results.
2035  *
2036  * Returns: TRUE if the operation was successful, FALSE otherwise.
2037  *
2038  * Deprecated: 3.2: Use e_cal_client_remove_object_sync() instead.
2039  */
2040 gboolean
2041 e_cal_remove_object_with_mod (ECal *ecal,
2042                               const gchar *uid,
2043                               const gchar *rid,
2044                               CalObjModType mod,
2045                               GError **error)
2046 {
2047         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
2048         g_return_val_if_fail (uid != NULL, FALSE);
2049
2050         return e_cal_client_remove_object_sync (
2051                 ecal->priv->client, uid, rid, mod, NULL, error);
2052 }
2053
2054 /**
2055  * e_cal_remove_object:
2056  * @ecal:  A calendar client.
2057  * @uid: Unique identifier of the calendar component to remove.
2058  * @error: Placeholder for error information.
2059  *
2060  * Asks a calendar to remove all components with the given UID.
2061  * If more control of the removal is desired, then use e_cal_remove_object_with_mod().
2062  * If the server is able to remove the component(s), all clients will
2063  * be notified and they will emit the "obj_removed" signal.
2064  *
2065  * Returns: %TRUE if successful, %FALSE otherwise.
2066  *
2067  * Deprecated: 3.2: Use e_cal_client_remove_object_sync() instead, with rid set to NULL and mod set to CALOBJ_MOD_ALL.
2068  **/
2069 gboolean
2070 e_cal_remove_object (ECal *ecal,
2071                      const gchar *uid,
2072                      GError **error)
2073 {
2074         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
2075         g_return_val_if_fail (uid != NULL, FALSE);
2076
2077         return e_cal_remove_object_with_mod (
2078                 ecal, uid, NULL, CALOBJ_MOD_ALL, error);
2079 }
2080
2081 /**
2082  * e_cal_receive_objects: (skip)
2083  * @ecal:  A calendar client.
2084  * @icalcomp: An icalcomponent.
2085  * @error: Placeholder for error information.
2086  *
2087  * Makes the backend receive the set of iCalendar objects specified in the
2088  * @icalcomp argument. This is used for iTIP confirmation/cancellation
2089  * messages for scheduled meetings.
2090  *
2091  * Returns: %TRUE if successful, %FALSE otherwise.
2092  *
2093  * Deprecated: 3.2: Use e_cal_client_receive_objects_sync() instead.
2094  */
2095 gboolean
2096 e_cal_receive_objects (ECal *ecal,
2097                        icalcomponent *icalcomp,
2098                        GError **error)
2099 {
2100         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
2101         g_return_val_if_fail (icalcomp != NULL, FALSE);
2102
2103         return e_cal_client_receive_objects_sync (
2104                 ecal->priv->client, icalcomp, NULL, error);
2105 }
2106
2107 /**
2108  * e_cal_send_objects: (skip)
2109  * @ecal: A calendar client.
2110  * @icalcomp: An icalcomponent.
2111  * @users: List of users to send the objects to.
2112  * @modified_icalcomp: Return value for the icalcomponent after all the operations
2113  * performed.
2114  * @error: Placeholder for error information.
2115  *
2116  * Requests a calendar backend to send meeting information to the specified list
2117  * of users.
2118  *
2119  * Returns: TRUE if the operation was successful, FALSE otherwise.
2120  *
2121  * Deprecated: 3.2: Use e_cal_client_send_objects_sync() instead.
2122  */
2123 gboolean
2124 e_cal_send_objects (ECal *ecal,
2125                     icalcomponent *icalcomp,
2126                     GList **users,
2127                     icalcomponent **modified_icalcomp,
2128                     GError **error)
2129 {
2130         GSList *slist = NULL;
2131         gboolean success;
2132
2133         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
2134         g_return_val_if_fail (icalcomp != NULL, FALSE);
2135         g_return_val_if_fail (users != NULL, FALSE);
2136         g_return_val_if_fail (modified_icalcomp != NULL, FALSE);
2137
2138         success = e_cal_client_send_objects_sync (
2139                 ecal->priv->client, icalcomp, &slist,
2140                 modified_icalcomp, NULL, error);
2141
2142         if (slist != NULL) {
2143                 GSList *link;
2144
2145                 /* XXX Never use GSList in a public API. */
2146                 for (link = slist; link != NULL; link = g_slist_next (link))
2147                         *users = g_list_prepend (*users, link->data);
2148                 *users = g_list_reverse (*users);
2149
2150                 g_slist_free (slist);
2151         }
2152
2153         return success;
2154 }
2155
2156 /**
2157  * e_cal_get_timezone: (skip)
2158  * @ecal: A calendar client.
2159  * @tzid: ID of the timezone to retrieve.
2160  * @zone: Return value for the timezone.
2161  * @error: Placeholder for error information.
2162  *
2163  * Retrieves a timezone object from the calendar backend.
2164  *
2165  * Returns: TRUE if the operation was successful, FALSE otherwise.
2166  *
2167  * Deprecated: 3.2: Use e_cal_client_get_timezone_sync() instead.
2168  */
2169 gboolean
2170 e_cal_get_timezone (ECal *ecal,
2171                     const gchar *tzid,
2172                     icaltimezone **zone,
2173                     GError **error)
2174 {
2175         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
2176         g_return_val_if_fail (tzid != NULL, FALSE);
2177         g_return_val_if_fail (zone != NULL, FALSE);
2178
2179         return e_cal_client_get_timezone_sync (
2180                 ecal->priv->client, tzid, zone, NULL, error);
2181 }
2182
2183 /**
2184  * e_cal_add_timezone: (skip)
2185  * @ecal: A calendar client.
2186  * @izone: The timezone to add.
2187  * @error: Placeholder for error information.
2188  *
2189  * Add a VTIMEZONE object to the given calendar.
2190  *
2191  * Returns: TRUE if successful, FALSE otherwise.
2192  *
2193  * Deprecated: 3.2: Use e_cal_client_add_timezone_sync() instead.
2194  */
2195 gboolean
2196 e_cal_add_timezone (ECal *ecal,
2197                     icaltimezone *izone,
2198                     GError **error)
2199 {
2200         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
2201         g_return_val_if_fail (izone != NULL, FALSE);
2202
2203         return e_cal_client_add_timezone_sync (
2204                 ecal->priv->client, izone, NULL, error);
2205 }
2206
2207 /**
2208  * e_cal_get_query:
2209  * @ecal: A calendar client.
2210  * @sexp: S-expression representing the query.
2211  * @query: (out): Return value for the new query.
2212  * @error: Placeholder for error information.
2213  *
2214  * Creates a live query object from a loaded calendar.
2215  *
2216  * Returns: A query object that will emit notification signals as calendar
2217  * components are added and removed from the query in the server.
2218  *
2219  * Deprecated: 3.2: Use e_cal_client_get_view_sync() instead.
2220  **/
2221 gboolean
2222 e_cal_get_query (ECal *ecal,
2223                  const gchar *sexp,
2224                  ECalView **query,
2225                  GError **error)
2226 {
2227         ECalClientView *client_view = NULL;
2228         gboolean success;
2229
2230         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
2231         g_return_val_if_fail (sexp != NULL, FALSE);
2232         g_return_val_if_fail (query != NULL, FALSE);
2233
2234         *query = NULL;
2235
2236         success = e_cal_client_get_view_sync (
2237                 ecal->priv->client, sexp, &client_view, NULL, error);
2238
2239         /* Sanity check. */
2240         g_return_val_if_fail (
2241                 (success && (client_view != NULL)) ||
2242                 (!success && (client_view == NULL)), FALSE);
2243
2244         if (client_view != NULL) {
2245                 *query = _e_cal_view_new (ecal, client_view);
2246                 g_object_unref (client_view);
2247         }
2248
2249         return success;
2250 }
2251
2252 /**
2253  * e_cal_set_default_timezone: (skip)
2254  * @ecal: A calendar client.
2255  * @zone: A timezone object.
2256  * @error: Placeholder for error information.
2257  *
2258  * Sets the default timezone on the calendar. This should be called before opening
2259  * the calendar.
2260  *
2261  * Returns: TRUE if the operation was successful, FALSE otherwise.
2262  *
2263  * Deprecated: 3.2: Use e_cal_client_set_default_timezone() instead.
2264  */
2265 gboolean
2266 e_cal_set_default_timezone (ECal *ecal,
2267                             icaltimezone *zone,
2268                             GError **error)
2269 {
2270         g_return_val_if_fail (E_IS_CAL (ecal), FALSE);
2271         g_return_val_if_fail (zone != NULL, FALSE);
2272
2273         e_cal_client_set_default_timezone (ecal->priv->client, zone);
2274
2275         return TRUE;
2276 }
2277
2278 /**
2279  * e_cal_get_error_message:
2280  * @status: A status code.
2281  *
2282  * Gets an error message for the given status code.
2283  *
2284  * Returns: the error message.
2285  *
2286  * Deprecated: 3.2: Use e_cal_client_error_to_string() instead.
2287  */
2288 const gchar *
2289 e_cal_get_error_message (ECalendarStatus status)
2290 {
2291         switch (status) {
2292         case E_CALENDAR_STATUS_INVALID_ARG :
2293                 return _("Invalid argument");
2294         case E_CALENDAR_STATUS_BUSY :
2295                 return _("Backend is busy");
2296         case E_CALENDAR_STATUS_REPOSITORY_OFFLINE :
2297                 return _("Repository is offline");
2298         case E_CALENDAR_STATUS_NO_SUCH_CALENDAR :
2299                 return _("No such calendar");
2300         case E_CALENDAR_STATUS_OBJECT_NOT_FOUND :
2301                 return _("Object not found");
2302         case E_CALENDAR_STATUS_INVALID_OBJECT :
2303                 return _("Invalid object");
2304         case E_CALENDAR_STATUS_URI_NOT_LOADED :
2305                 return _("URI not loaded");
2306         case E_CALENDAR_STATUS_URI_ALREADY_LOADED :
2307                 return _("URI already loaded");
2308         case E_CALENDAR_STATUS_PERMISSION_DENIED :
2309                 return _("Permission denied");
2310         case E_CALENDAR_STATUS_UNKNOWN_USER :
2311                 return _("Unknown User");
2312         case E_CALENDAR_STATUS_OBJECT_ID_ALREADY_EXISTS :
2313                 return _("Object ID already exists");
2314         case E_CALENDAR_STATUS_PROTOCOL_NOT_SUPPORTED :
2315                 return _("Protocol not supported");
2316         case E_CALENDAR_STATUS_CANCELLED :
2317                 return _("Operation has been canceled");
2318         case E_CALENDAR_STATUS_COULD_NOT_CANCEL :
2319                 return _("Could not cancel operation");
2320         case E_CALENDAR_STATUS_AUTHENTICATION_FAILED :
2321                 return _("Authentication failed");
2322         case E_CALENDAR_STATUS_AUTHENTICATION_REQUIRED :
2323                 return _("Authentication required");
2324         case E_CALENDAR_STATUS_DBUS_EXCEPTION :
2325                 return _("A D-Bus exception has occurred");
2326         case E_CALENDAR_STATUS_OTHER_ERROR :
2327                 return _("Unknown error");
2328         case E_CALENDAR_STATUS_OK :
2329                 return _("No error");
2330         case E_CALENDAR_STATUS_NOT_SUPPORTED :
2331                 /* Translators: The string for NOT_SUPPORTED error */
2332                 return _("Not supported");
2333         default:
2334                 /* ignore everything else */
2335                 break;
2336         }
2337
2338         return NULL;
2339 }