diff options
Diffstat (limited to 'calendar')
81 files changed, 0 insertions, 36634 deletions
diff --git a/calendar/.cvsignore b/calendar/.cvsignore deleted file mode 100644 index c038ed786..000000000 --- a/calendar/.cvsignore +++ /dev/null @@ -1,2 +0,0 @@ -Makefile -Makefile.in
\ No newline at end of file diff --git a/calendar/ChangeLog b/calendar/ChangeLog deleted file mode 100644 index 8b7e5b955..000000000 --- a/calendar/ChangeLog +++ /dev/null @@ -1,2442 +0,0 @@ -2004-05-28 JP Rosevear <jpr@novell.com> - - Fixes #55524 - - * backends/file/e-cal-backend-file.c - (e_cal_backend_file_receive_objects): don't sanitize the - component, we already check for valid timezones and the zones - aren't merged in yet anyhow - -2004-05-28 Rodrigo Moya <rodrigo@novell.com> - - * libedata-cal/e-data-cal-factory.c (backend_last_client_gone_cb): - disconnect from signals on the removed backend. - -2004-05-28 Harish Krishnaswamy <kharish@novell.com> - - - * backends/groupwise/e-cal-backend-groupwise-utils.c: - (e_gw_item_to_cal_component): Throw in null checks on - mandatory fields to bypass crashes in e-d-s while the server - gets fixed. - - -2004-05-27 Rodrigo Moya <rodrigo@novell.com> - - * backends/http/e-cal-backend-http.c (retrieval_done): make sure - we clean up the cache, or old events will always be kept. - -2004-05-27 Rodrigo Moya <rodrigo@novell.com> - - Fixes #58197 - - * libedata-cal/e-cal-backend.c (e_cal_backend_create_object, - e_cal_backend_modify_object): removed assertions on method - implementations, since backends can perfectly have unimplemented - methods. Instead, notify the error. - -2004-05-25 Sivaiah Nallagatla <snallagatla@novell.com> - - * backends/groupwise/e-cal-backends-groupwise.c (form_uri) : - new function to form the uri required for e_gw_connection - (connect_to_server) : use form_uri instead of convert_uri - -2004-05-25 Harish Krishnaswamy <kharish@novell.com> - - Fixes GW portion of #57218 and #54280 - - * backends/groupwise/e-cal-backend-groupwise-utils.c: - (start_freebusy_session): removed FIXME comments (the code had been - fixed much earlier). - (e_gw_item_set_changes):use the SET_DELTA macro to get accept_level - changes. - * backends/groupwise/e-cal-backend-groupwise.c: - (e_cal_backend_groupwise_modify_object), - (e_cal_backend_groupwise_remove_object), - (e_cal_backend_groupwise_send_objects): set return arguments correctly. - and removed dead code in remove_object. - -2004-05-25 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_modify_object): return ObjectNotFound error - instead of InvalidObject when the object is not found. - -2004-05-22 Rodrigo Moya <rodrigo@ximian.com> - - * backends/file/e-cal-backend-file.c (add_component): make sure we - process correctly the detached instances. - (match_object_sexp): deal with hash table entries not containing - a full_object (ie, detached recurrences). - -2004-05-21 JP Rosevear <jpr@novell.com> - - * backends/file/e-cal-backend-file.c - (e_cal_backend_file_receive_objects): make sure we only handle the - type of objects the backend is set up for plus timezones; directly - add the objects rather than using other functions - -2004-05-19 Chris Toshok <toshok@ximian.com> - - * backends/contacts/e-cal-backend-contacts.c (book_record_new): - use new e_book_new/e_book_open apis. - -2004-05-19 Rodrigo Moya <rodrigo@ximian.com> - - Removes 100s of error dialogs as reported in #54211 - - * backends/http/e-cal-backend-http.c: added a flag to know when the - backend has been opened. - (reload_cb): set the "opened" flag to TRUE when we reload. - (retrieval_done): only notify errors when opening the backend, not - on each reload, or we'll get many error message dialogs when left - running for a few hours. - -2004-05-18 Harish Krishnaswamy <kharish@novell.com> - - Fixes #56320 and related timezone issues. - Convert datetime from the Groupwise string format between icaltime - directly w/o using time_t structures. - * backends/groupwise/e-cal-backend-groupwise-utils.c: - (set_properties_from_cal_component), - (e_gw_item_new_from_cal_component), (e_gw_item_to_cal_component), - (e_gw_connection_send_appointment), (e_gw_item_set_changes): - use the default_timezone info while performing the conversions. - * backends/groupwise/e-cal-backend-groupwise-utils.h: - * backends/groupwise/e-cal-backend-groupwise.c: (populate_cache), - (get_deltas), (connect_to_server), - (e_cal_backend_groupwise_finalize), (e_cal_backend_groupwise_open), - (e_cal_backend_groupwise_add_timezone): - Add timezone to the cache and allow evolution to set the default timezone. - (e_cal_backend_groupwise_set_default_timezone), - (e_cal_backend_groupwise_create_object), - (e_cal_backend_groupwise_modify_object), (receive_object), - (send_object), (e_cal_backend_groupwise_init): - * libedata-cal/e-cal-backend-cache.c: - (e_cal_backend_cache_put_default_timezone), - (e_cal_backend_cache_get_default_timezone): - Store default timezone information in the cache so that eds remembers the - client timezone information while populating the cache in the next session. - Since the cache population happens while the calendar is still loading, evolution - would not have had a chance to set the timezone yet. - - * libedata-cal/e-cal-backend-cache.h: Added get/put functions for - default timezone. - -2004-05-18 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-sexp.c (func_occur_in_time_range): always - use a valid timezone. - - * libecal/e-cal-recur.c (cal_object_time_from_time): don't use invalid - timezones. - - * libecal/e-cal.c (e_cal_generate_instances): make sure we always have - a default timezone. - -2004-05-17 Rodney Dawes <dobey@ximian.com> - - * libecal/Makefile.am (libecal_la_LIBADD): - * libedata-cal/Makefile.am (libedata_cal_la_LIBADD): - Add $(EVOLUTION_CALENDAR_LIBS) to link to all the right dependencies - so that the mono bindings will work correctly - - Fixes #58615 - -2004-05-17 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #51412 - - * backends/file/e-cal-backend-file.c (remove_instance): re-add the - modified objects to the top-level icalcomponent after removing - instances. - (e_cal_backend_file_remove_object): manage the CALOBJ_MOD_THIS case - for an event with no RECURRENCE-ID. - -2004-05-14 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #56870 - - * libedata-cal/e-cal-backend-sync.c (e_cal_backend_sync_create_object, - e_cal_backend_sync_modify_object, e_cal_backend_sync_remove_object, - e_cal_backend_sync_discard_alarm, e_cal_backend_sync_receive_objects, - e_cal_backend_sync_send_objects): don't g_assert if the method is not - implemented on the underlying backend, just return an UnsupportedMethod - error. - -2004-05-14 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-sexp.c (e_cal_backend_sexp_func_make_time): - added extra check for function arguments. - - * libedata-cal/e-cal-backend-cache.c (e_cal_backend_cache_put_timezone): - added missing implementation from recurreces-work-branch. - - * libecal/e-cal-recur.c (e_cal_recur_generate_instances_of_rule): - use the default timezone if we can't get timezones for the start - and end dates. - -2004-05-13 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #54094 - - * backends/file/e-cal-backend-file.c (e_cal_backend_file_modify_object): - deal correctly with CALOBJ_MOD_THIS for master objects. - -2004-05-12 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (e_cal_generate_instances): fixed gtk-doc comments, - and process correctly detached instances. - (e_cal_generate_instances_for_object): new function. - (e_cal_set_default_timezone): set the internal default timezone when - the call to the backend is successful. - (process_detached_instances): process correctly the detached instances. - -2004-05-12 Harish Krishnaswamy <kharish@novell.com> - - - * backends/groupwise/e-cal-backend-groupwise-utils.c: - (set_properties_from_cal_component), (e_gw_item_to_cal_component), - (e_gw_connection_get_freebusy_info), (e_gw_item_set_changes): - Add implementation for modification of objects. - * backends/groupwise/e-cal-backend-groupwise-utils.h: - Add declaration for e_gw_item_set_changes. - * backends/groupwise/e-cal-backend-groupwise.c: - (e_cal_backend_groupwise_set_default_timezone): - Allow evo to set the timezone in the groupwise backend. - (e_cal_backend_groupwise_modify_object): - Modify implementation to use modifyItemRequest rather than - a sendItem. - -2004-05-07 JP Rosevear <jpr@ximian.com> - - Fixes #57908 - - * libecal/e-cal-component.c (e_cal_component_set_organizer): - prevent double frees - (e_cal_component_set_organizer): ditto - (e_cal_component_set_summary): ditto - -2004-05-06 Harish Krishnaswamy <kharish@novell.com> - - * libecal/e-cal.c: (load_static_capabilities): assign capabilities - to ecal->capabilities so that it need not be computed repeatedly. - * backends/groupwise/e-cal-backend-groupwise.c: - (populate_cache) : added message to view element to recieve - message bodies as plain text (default). - (connect_to_server) : the Tasks folder is also Calendar and - not Checklist in GW server. - (e_cal_backend_groupwise_get_static_capabilities) : - Added CAL_STATIC_CAPABILITY_SAVE_SCHEDULES. - -2004-05-04 Harish Krishnaswamy <kharish@novell.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.c: - (set_properties_from_cal_component), - (e_gw_item_new_from_cal_component), (e_gw_item_to_cal_component): - Patch the FIXMEs in the code handling recipient_list and message bodies - in events. This also resolves #57204 and 57883. - - -2004-05-03 William Jon McCann <mccann@jhu.edu> - - * libecal/e-cal-time-util.h: Add missing G_BEGIN_DECLS and G_END_DECLS - -2004-05-04 Harish Krishnaswamy <kharish@novell.com> - - Fixes #55922 - - * libedata-cal/e-data-cal-factory.c: (impl_CalFactory_getCal): - Hash the backends based on the uri 'and' the type (Both calendar - and tasks for GW share the same uri but need different e-data-cal - instances. - -2004-05-03 JP Rosevear <jpr@ximian.com> - - Partial fix for #57218 - - * libecal/e-cal.c (cal_objects_sent_cb): copy the object string - (e_cal_get_default_object): check the status explicitly - (e_cal_get_object): ditto - (e_cal_get_timezone): ditto - (e_cal_send_objects): parse the string here so we can handle bad - parsing properly - - * libecal/e-cal-marshal.list: replace marshaller signature - - * libecal/e-cal-listener.h: update signal proto - - * libecal/e-cal-listener.c (impl_notifyObjectsSent): send back - just the text like other similar routines - (e_cal_listener_class_init): send back a string as the third arg - in the send_objects signal - -2004-04-30 Dan Winship <danw@ximian.com> - - * libecal/e-cal-component.c (get_attendee_list): Fill in some - default values to avoid libical assertions later. Also, fix some - really awful cut+pastos - -2004-04-28 JP Rosevear <jpr@ximian.com> - - * tests/ecal/test-search.c: something to run searches with for - test purposes - - * tests/ecal/Makefile.am: build test search - -2004-04-28 JP Rosevear <jpr@ximian.com> - - Fixes #57080 - - * libedata-cal/e-cal-backend.c - (e_cal_backend_notify_object_modified): make sure the item was - actually in the query before so we don't send bogus removes - -2004-04-27 Harish Krishnaswamy <kharish@novell.com> - - Fixes #56535 - - * backends/groupwise/e-cal-backend-groupwise-utils.c: - (set_properties_from_cal_component), (e_gw_item_to_cal_component): - Added support for saving Alarms in the GW server as well as - read the alarm information during retrieval. - - -2004-04-23 Jeffrey Stedfast <fejj@ximian.com> - - * libedata-cal/e-data-cal.c (e_data_cal_notify_changes): Fixed a - c/p bug. Don't call notifyDefaultTimezoneSet, we want to - notifyChanges! Took me long enough to track this little bugger - down. - -2004-04-21 Jeffrey Stedfast <fejj@ximian.com> - - * backends/file/e-cal-backend-file.c - (e_cal_backend_file_receive_objects): Pass the address of calobj - to file_create_object(). - (e_cal_backend_file_compute_changes): "Gracefully" handle a NULL - return from e_xmlhash_new(). - -2004-04-20 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c (open_async): emit the open signal in an idle - loop - (async_signal_idle_cb): emit the signal and free the data - -2004-04-16 Harish Krishnaswamy <kharish@novell.com> - - Fixes #55802 - - * libecal/e-cal.c: (open_calendar): Create and lock - op mutex and unlock ecal before attempting to authenticate. - (open_async, async_auth_idle_cb,async_auth_func_cb): implement - async authentication to calendar. - - -2004-04-15 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c (e_cal_add_timezone): do a little more sanity - checking on what we send - -2004-04-12 Sarfraaz Ahmed <asarfraaz@novell.com> - - Fixes #56517 - - * libecal/e-cal.c (e_cal_add_timezone): Added a check for icalcomponent - structure. Return FALSE if icalcomponent is NULL. - -2004-04-12 Harish K <kharish@novell.com> - - Fixes #53926 - - * backends/groupwise/e-cal-backend-groupwise-utils.c - (e_gw_item_to_cal_component) : set the tzid to "UTC" - while setting the dueDate. - - -2004-04-08 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_get_static_capabilities): add the - ONE_ALARM_ONLY static capability. - -2004-04-06 Harish K <kharish@novell.com> - - Fixes #55169 - - * backends/groupwise/e-cal-backend-groupwise-utils.c - (e_gw_connection_get_freebusy_info) : Use icalproperty - to add free/busy data to ECalComponent. - -2004-04-05 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_remove_object): Use correct types for - e_cal_backend_groupwise_get_object's return value. - -2004-04-03 JP Rosevear <jpr@ximian.com> - - Fixes #56416 - - * backends/contacts/e-cal-backend-contacts.c - (e_cal_backend_contacts_get_timezone): implement - (e_cal_backend_contacts_add_timezone): ditto - (e_cal_backend_contacts_set_default_timezone): ditto - (free_zone): free a timezone - (e_cal_backend_contacts_finalize): destroy the zones hash table - (e_cal_backend_contacts_class_init): add new method - implementations - (e_cal_backend_contacts_init): set up zones hash table - -2004-04-02 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #51412 - - * backends/file/e-cal-backend-file.c (e_cal_backend_file_remove_object): - support being called with CALOBJ_MOD_THIS on the top level component. - -2004-04-02 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #55719 - - * backends/groupwise/e-cal-backend-groupwise.c (connect_to_server): - use correct type for populate_cache's return value. - (e_cal_backend_groupwise_set_mode): use correct type for - connect_to_server's return value. - -2004-03-30 JP Rosevear <jpr@ximian.com> - - * backends/file/e-cal-backend-file.c: allow debugging code to be - turned on and off easily - - * backends/http/e-cal-backend-http.c: ditto - -2004-03-31 JP Rosevear <jpr@ximian.com> - - Fixes #56111 - - * backends/contacts/e-cal-backend-contacts.c (create_component): - take a uid for the icalcomp - (create_birthday): create a uid from the contact uid and a - birthday designator - (create_anniversary): ditto for anniversary - (e_cal_backend_contacts_get_cal_address): set the address to NULL - when returning success - (e_cal_backend_contacts_get_ldap_attribute): ditto for the - attribute - (e_cal_backend_contacts_remove): can't remove a read only calendar - (e_cal_backend_contacts_get_object): implement - -2004-03-31 JP Rosevear <jpr@ximian.com> - - Fixes #54713 - - * libecal/e-cal.c (e_cal_get_object): only try to parse the string - if the status is good - (e_cal_get_timezone): ditto - (e_cal_get_default_object): ditto - -2004-03-29 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (e_cal_generate_instances): added support for dealing - with detached instances. - (process_detached_instances): replace all generated instances with the - detached ones. - -2004-03-29 Harish K <kharish@novell.com> - - * backends/groupwise/e-cal-backend-utils.c - (start_freebusy_session) : send UTC time to server instead of - floating time. remove namespaces to elements in request messages. - (e_gw_connection_get_freebusy_info) :send f/b information thro' - ECalComponentAttendee structure -not ECalComponentOrganizer. - -2004-03-26 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.h: add proto - - * libecal/e-cal.c (e_cal_get_source_type): accessor - -2004-03-26 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_create_object): replace the inbox container ID - in the ID returned by sendItemResponse with our container ID. - (e_cal_backend_groupwise_remove_object): if the object does not have the - GW server ID, use the iCalID property to remove it. - -2004-03-26 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.c - (e_gw_connection_send_appointment): set the container ID on the - EGwItem returned by e_gw_item_new_from_cal_component. - -2004-03-25 William Jon McCann <mccann@jhu.edu> - - * backends/http/e-cal-backend-http.c (retrieval_done): - (e_cal_backend_http_get_default_object): use the same component - kind as the backend. - -2004-03-25 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_create_object): add the X-EVOLUTION-GROUPWISE-ID - property to the newly-created component. - -2004-03-25 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-sync.[ch] - (e_cal_backend_sync_create_object): made the 'calobj' argument to - be inout, so that the caller gets the modified component, not the - original one sent to the backend. - (_e_cal_backend_sync_create_object): ditto, and notify listeners with - the modified calobj. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_create_object): - * backends/file/e-cal-backend-file.c (e_cal_backend_file_create_object): - adapted to changes in ECalBackendSync, and return the modified object - to the caller. - -2004-03-22 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.[ch] - (e_gw_connection_send_appointment): added a 'id' argument, to be - passed to e_gw_connection_send_item. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_create_object, - e_cal_backend_groupwise_modify_object, send_object): added extra - argument to e_gw_connection_send_appointment. - -2004-03-19 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.[ch] - (e_cal_backend_groupwise_notify_error_code): new function. - (populate_cache, get_deltas, connect_to_server, - e_cal_backend_groupwise_open): notify clients of any error. - -2004-03-19 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.c - (start_freebusy_session): don't use the "types:" prefix for the - <user> SOAP element. - -2004-03-19 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_remove_object): remove the object from the - cache in the remote case also. - -2004-03-19 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_remove_object): if we don't find the - X-EVOLUTION-GROUPWISE-ID property, the object didn't come from - the server, so don't try to remove it. - -2004-03-19 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-cache.[ch] - (e_cal_backend_cache_get_timezone, e_cal_backend_cache_put_timezone, - e_cal_backend_cache_remove_timezone): new functions to support - timezones in the cache. - (e_cal_backend_cache_get_components): only append to the returned - list the VEVENT's and VTODO's components. - (e_cal_backend_cache_init): create a hash table to store all the - icaltimezone objects we create in e_cal_backend_cache_get_timezone. - (e_cal_backend_cache_finalize): free the timezones hash table. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_remove_object): remove object based on the - Groupwise item ID, not the iCalendar ID. - -2004-03-18 JP Rosevear <jpr@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.c - (e_gw_connection_get_freebusy_info): send back "freeBusySessionId" - rather than "session" - -2004-03-18 JP Rosevear <jpr@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.c - (start_freebusy_session): put the xml prefixes back in, they - weren't the issue - -2004-03-18 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.c - (set_properties_from_cal_component): set the GW item ID based on the - X-EVOLUTION-GROUPWISE-ID property. - (e_gw_item_to_cal_component): add the above property to the created - ECalComponent, and use our iCalendar ID to set the "iCalId" property. - -2004-03-18 JP Rosevear <jpr@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.c - (start_freebusy_session): remove xml prefixes - -2004-03-18 JP Rosevear <jpr@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.c - (start_freebusy_session): list the the addresses in the <email> - attribute - -2004-03-18 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c: add e_return_error macro to fail more - gracefully as per ebook - -2004-03-18 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_create_object, - e_cal_backend_groupwise_modify_object): don't update the cache when we - get an error from the server. - -2004-03-17 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #55719 - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_get_cal_address): deal with online/offline - modes. - (e_cal_backend_groupwise_finalize): free new private field. - -2004-03-16 Harish K <kharish@novell.com> - - * libecal/e-cal.c : Move open_calendar call into async_idle_cb - and rearrange mutex lock/unlock sequences. This fixes the calendar - authentication problems observed while using the Password Dialog. - -2004-03-15 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-sexp.c (func_occur_in_time_range): expand - recurrences for the given time range to be sure that we return the - correct events. - (check_instance_time_range_cb): callback to check the expanded recurrences. - -2004-03-15 Rodney Dawes <dobey@ximian.com> - - * libecal/libecal-1.0.pc.in: - * libedata-cal/libedata-cal-1.0.pc.in: Add @LIBBONOBO_REQUIRED@ for - the libbonobo dependency - -2004-03-14 Harish K <kharish@novell.com> - - * calendar/backends/groupwise/e-cal-backend-groupwise.c : - Update calls to e_gw_connection_get_items with the new prototype. - -2004-03-11 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-data-cal.c (e_data_cal_notify_objects_sent): guard - against sending NULL strings to CORBA. - - * backends/contacts/e-cal-backend-contacts.c - (e_cal_backend_contacts_receive_objects, - e_cal_backend_contacts_send_objects): return PermissionDenied error. - -2004-03-09 JP Rosevear <jpr@ximian.com> - - Fixes #55389 - - * backends/file/e-cal-backend-file.c - (e_cal_backend_file_send_objects): return the calendar object - properly - -2004-03-09 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (e_cal_resolve_tzid): don't default to UTC timezone, - the default timezone is used by the timezone look up code. - -2004-03-09 Thomas Mirlacher <dent@cosy.sbg.ac.at> - - Fixes #53885 - - * backends/contacts/e-cal-backend-contacts.c: - intermediate fix for recurring entries starting before 1970 - set the dtend for making valid whole-day entries - -2004-03-05 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #54280 - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_send_objects): added missing implementation. - -2004-03-05 Harish K <kharish@novell.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.c : - timezone values in ECalDateComponent structures should be - set to "UTC" for GW items. - -2004-03-01 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #33243 - - * libedata-cal/e-cal-backend-sexp.c (matches_location): new function - to check if a component's location matches a string. - (matches_any): call matches_location also. - (func_contains): added support for searching the location also. - -2004-03-01 Rodrigo Moya <rodrigo@ximian.com> - - * idl/Evolution-DataServer-Calendar.idl: added new arguments to the - notifyObjectsSent method for backends to return the list of users and - events for which it operated. - - * libedata-cal/e-data-cal.[ch] (e_data_cal_notify_objects_sent): added - new argument and call the listener's notifyObjectsSent method with - a GNOME_Evolution_Calendar_UserList. - - * libedata-cal/e-cal-backend-sync.[ch] (e_cal_backend_sync_send_objects, - _e_cal_backend_send_objects): added new arguments. - - * backends/file/e-cal-backend-file.c (e_cal_backend_file_send_objects): - * backends/http/e-cal-backend-http.c (e_cal_backend_http_send_objects): - * backends/contacts/e-cal-backend-contacts.c - (e_cal_backend_contacts_send_objects): - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_send_objects): adapted to changes in - ECalBackend/ECalBackendSync API. - - * backends/file/e-cal-backend-file.c (e_cal_backend_file_receive_objects, - e_cal_backend_file_send_objects): removed wrong return statement. - - * libecal/e-cal-marshal.list: added new marshaller. - - * libecal/e-cal.[ch] (e_cal_send_objects): get the user list from the - operation's result. - (cal_objects_sent_cb): added the new arguments and copy them to the - operation's result. - - * libecal/e-cal-listener.[ch]: added new arguments to "send_objects" - signal. - (impl_notifyObjectsSent): added UserList argument to CORBA method, and - convert the CORBA user list to a GList to be passed to the signal - handlers. - (e_cal_listener_class_init): added new arguments to "send_objects" - signal. - -2004-02-26 JP Rosevear <jpr@ximian.com> - - * tests/ecal/test-ecal.c: make EXPECTED a macro so it compiles - -2004-02-26 Harish K <kharish@novell.com> - - * tests/ecal/test-ecal.c : Added implementation of - test cases. - * (tests/ecal/test-runner.sh, tests/ecal/cleanup.sh - tests/ecal/testdata.ics) : Added test scripts and test data. - * tests/ecal/Makefile.am : Add scripts to EXTRA_DIST. - -2004-02-23 JP Rosevear <jpr@ximian.com> - - * backends/groupwise/Makefile.am: Add includes for srcdir != - builddir - - * backends/file/Makefile.am: ditto - - * backends/contacts/Makefile.am: ditto - - * libedata-cal/Makefile.am: ditto - - * libecal/Makefile.am: ditto - - * tests/ecal/Makefile.am: ditto - -2004-02-17 Harish K <kharish@novell.com> - * libecal/e-cal.c : - (e_cal_new_system_calendar, e_cal_new_system_tasks) : arguments - to g_build_filename should be NULL terminated. - -2004-02-12 Chris Toshok <toshok@ximian.com> - - * backends/contacts/e-cal-backend-contacts.c (book_record_new): - quiet the compiler, and free the list of requested fields after - the e_book_get_book_view call. - (e_cal_backend_contacts_init): use e_book_get_addressbooks instead - of using gconf and hardcoding the sourcelist xml key. - -2004-02-10 Rodrigo Moya <rodrigo@ximian.com> - - * backends/file/e-cal-backend-file.c (e_cal_backend_file_receive_objects): - switch wrongly-placed creation/modification of objects. - -2004-02-06 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.c - (set_properties_from_cal_component, e_gw_item_to_cal_component): - adapted to changes in EGwItem. - - * libecal/e-cal.c (e_cal_open_async): no need to make the thread joinable. - -2004-02-06 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise-utils.[ch]: new files - to contain all calendar-specific code from libegroupwise. - (e_gw_item_new_from_cal_component, e_gw_item_to_cal_component, - e_gw_connection_send_appointment): new functions. - - * backends/groupwise/e-cal-backend-groupwise.c: include new header - file. - -2004-02-06 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/create-account.c: - * backends/groupwise/soap-test.c: - * backends/groupwise/e-gw-*: moved to $top_srcdir/servers/groupwise. - - * backends/groupwise/Makefile.am: removed files and don't build test - programs. - -2004-02-06 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c (parse_response_status): - "Status" is now "status". - -2004-02-04 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.h: update proto - - * libecal/e-cal.c (async_idle_cb): return FALSE to remove the idle - handler - (get_default): take an auth func and use it - (e_cal_open_default): ditto - -2004-02-04 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.h: redo protos - - * libecal/e-cal.c (e_cal_open_default): open the default ecal - based on type - (e_cal_set_default): set the default based on type - (e_cal_set_default_source): ditto - (e_cal_get_sources): get the source list based on type - -2004-02-04 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (open_calendar): new function created from - e_cal_open, without signal emissions. - (e_cal_open): call open_calendar() and emit signals. - (e_cal_open_async): changed to use a thread instead - of an idle callback. - (open_async): converted to a GThreadFunc, call open_calendar and - setup idle callback to emit the "cal_opened" signal. - (async_idle_cb): idle callback, notify listeners with the - "cal_opened" signal and free ECalAsyncData. - - * backends/file/e-cal-backend-file.c: store an ordered list of all - detached recurrences, as well as the hash table, for each object. - (free_object): free the recurrences list, and the object's data. - (add_component, remove_instance): add the recurrences to the - recurrences list also. - (e_cal_backend_file_modify_object): remove the recurrence from the - list also, and it to the list when adding it to the hash table. - (remove_object_instance_cb): remove the recurrences from the list - also. - (e_cal_backend_file_receive_objects): remove cancelled meetings from the - received toplevel component before merging it. Add/Update received - objects approppriately for PUBLISH/REQUEST/REPLY. - -2004-02-04 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (open_async): g_object_unref the ECal, not the - ECalAsyncData structure. - -2004-02-03 Rodney Dawes <dobey@ximian.com> - - * backends/http/e-cal-backend-http.c: Don't keep a global SoupMessage - (e_cal_backend_http_fianlize): Abort the session, as we may have - multiple messages running - (webcal_to_http_method): Return a copy if we aren't parsing a webcal:, - as there is no need to return NULL, since we just check and copy the - original anyway - (retrieval_done): Handle redirection, and don't rely on a global - SoupMessage for things, and don't try to set the SoupMessage to NULL - (begin_retrieval_cb): Allow multiple messages, and disable automatic - redirect handling, as we need to handle it ourselves - (maybe_start_reload_timeout): We want minutes, not seconds, so we need - to multiply the refresh value by 60000 instead of 1000 - -2004-02-03 Dan Winship <danw@ximian.com> - - * backends/http/e-cal-backend-http.c (e_cal_backend_http_finalize, - retrieval_done): Don't unref the soup message; that happens - automatically after the callback runs. #53645 - -2004-02-03 Harish K <kharish@novell.com> - - * backends/groupwise/e-cal-backend-groupwise.c : - added get_deltas function as the callback to update cache. - * backends/groupwise/e-gw-connection.[ch] (parse_response_status): - Removed UpdateCacheHandle structure as - the callback is now local to e-cal-backend-groupwise.c - (e_gw_connection_get_deltas) : modified the function to return - list of EGwItems. - (set_attendee_list_from_soap_parameter) : moved to EGwItem. - * backends/groupwise/e-gw-item.c : Added attendee_list to priv - structure and updated e_gw_item_dispose to free it. - (e_gw_item_new_from_soap_parameter) : added code to parse 'changes' - element in item. - -2004-02-03 Chris Toshok <toshok@ximian.com> - - * backends/groupwise/e-gw-connection.c (parse_response_status): - E_GW_CONNECTION_BAD_PARAMETER -> - E_GW_CONNECTION_STATUS_BAD_PARAMETER. - -2004-02-02 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.[ch] (parse_response_status): - added new error code. - -2004-02-02 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c (populate_cache): - add all retrieved items to the cache, since calendar and tasks - both use the same cache file. - (e_cal_backend_groupwise_get_object, - e_cal_backend_groupwise_get_object_list): only return items of the - same kind as the backend. - (e_cal_backend_groupwise_create_object): only allow storing of - items of the same kind as the backend. - -2004-02-02 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-item.c (e_gw_item_append_to_soap_message): - fixed argument ordering in call to e_gw_message_write_string_parameter. - -2004-02-02 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c (populate_cache): - changed to have an ECalBackendGroupwise as argument, and only add - to the cache objects of the same kind as the backend. - (connect_to_server): pass the ECalBackendGroupwise to populate_cache. - - * backends/groupwise/e-gw-item.c (e_gw_item_to_calcomponent): - set altrep to NULL on ECalComponentText's. - -2004-02-02 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-item.c (e_gw_item_to_calcomponent): moved - calls to e_cal_component_set_new_vtype up, so that the internal - icalcomponent gets created. Added missing 'break' statement. - -2004-02-02 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c - (e_gw_connection_get_freebusy_info): fixed warning. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_remove_object): pass the container_id to - e_gw_connection_remove_item. - -2004-02-02 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c (connect_to_server): - set the ESource's name to the name of the folder. - -2004-02-01 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.h: order the signals more sensibly - - * libecal/e-cal.c (destroy_factories): use G_STRLOC - (categories_changed_cb): set the size of the array so the length - is set - (e_cal_init): remove extra listener args, listen for new signals - - * libecal/e-cal-marshal.list: add signal marshaller - - * libecal/e-cal-listener.h: add new signals, remove function - callback protos, update protos - - * libecal/e-cal-listener.c (impl_notifyErrorOccurred): emit error - signal - (impl_notifyCategoriesChanged): emit categories changed signal - (e_cal_listener_init): remove dead initializations - (e_cal_listener_finalize): remove dead finalizations - (e_cal_listener_class_init): add category and error signals - (e_cal_listener_construct): remove error and category function - params - (e_cal_listener_new): ditto - -2004-01-31 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c (e_cal_is_read_only): return a proper GError and - boolean - - * backends/contacts/e-cal-backend-contacts.c - (e_cal_backend_contacts_get_type): remove debug statements - -2004-01-30 Radek Doulik <rodo@ximian.com> - - * backends/contacts/e-cal-backend-contacts.c (contact_record_new): - make sure anniversary/birthday components were created before - using them - (contact_record_free): ditto - (contact_record_cb): ditto - -2004-01-30 Rodrigo Moya <rodrigo@ximian.com> - - * backends/http/Makefile.am: LOG_DOMAIN is ...http, not ...file. - - * backends/http/e-cal-backend-http.c (reaload_cb): don't start a new - updload if we're already uploading. - -2004-01-29 Hans Petter Jansson <hpj@ximian.com> - - * backends/http/e-cal-backend-http.c (retrieval_done): Clear the - is_loading flag. - (begin_retrieval_cb): Set the is_loading flag, maybe start the reload - timeout. - (reload_cb): Implement. - (maybe_start_reload_timeout): Implement. - (e_cal_backend_http_open): Init reload timeout ID. - -2004-01-29 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-item.c (e_gw_item_append_to_soap_message): - write all properties to the message. - -2004-01-29 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-item.[ch] (e_gw_item_new_from_soap_parameter, - e_gw_item_to_cal_component, e_gw_item_get_id, e_gw_item_set_id, - e_gw_item_get_creation_date, e_gw_item_set_creation_date, - e_gw_item_get_start_date, e_gw_item_set_start_date, - e_gw_item_get_classification, e_gw_item_set_classification, - e_gw_item_get_accept_level, e_gw_item_set_accept_level, - e_gw_item_get_subject, e_gw_item_set_subject, - e_gw_item_get_priority, e_gw_item_set_priority, - e_gw_item_get_message, e_gw_item_set_message, - e_gw_item_get_completed, e_gw_item_set_completed, - e_gw_item_get_due_date, e_gw_item_set_due_date, - e_gw_item_get_end_date, e_gw_item_set_end_date, - e_gw_item_get_place, e_gw_item_set_place): new functions. - (e_gw_item_new_from_cal_component): renamed. Don't keep the - ECalComponent, there's no need for it. - (append_appointment_properties): don't use the private ECalComponent, - it's not stored anymore. - (e_gw_item_dispose): free all properties. - (e_gw_item_append_to_soap_message): added support for tasks. - - * backends/groupwise/e-gw-connection.c (e_gw_connection_get_items): - (e_gw_connection_send_appointment): use - e_gw_item_new_from_cal_component. - (get_e_cal_component_from_soap_parameter, get_evo_date_from_string): - removed. - (e_gw_item_get_deltas, update_cache_item): disabled until migrated to - use EGwItem's. - (e_gw_connection_get_date_from_string): new function. - - * backends/groupwise/e-gw-container.c (e_gw_container_finalize): fixed - warnings. - -2004-01-28 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-item.c: added missing header. - -2004-01-28 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #53465 - - * libecal/e-cal.c (e_cal_get_error_message): fixed typo. - -2004-01-28 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-item.[ch] - (e_gw_item_append_to_soap_message): new function. - - * backends/groupwise/e-gw-connection.c (e_gw_connection_send_item): - finished implementation. - -2004-01-28 Harish K <kharish@novell.com> - - * calendar/backends/groupwise/e-cal-backend-groupwise.c : - Pass the correct arguments to the callback function - * calendar/backends/groupwise/e-gw-connection.c : - (e_gw_connection_get_container_id) : Initialize container_list. - (e-gw-connection_get_deltas) : fixed the prototype to match - the callback prototype - (set_attendee_list_from_soap_param): modified - get_attendee_list_from_soap_param to update calendar component - within the same function. - (e-gw-connection_get_items) : check item types before creating - e-cal-components. - * calendar/backends/groupwise/e-gw-connection.h : added - CacheUpdateHandle structure. - -2004-01-28 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.h: add protos - - * libecal/e-cal.c (e_cal_new_system_calendar): return a pointer to - the system calendar - (e_cal_new_system_tasks): ditto for tasks - (get_default): gets the default calendar/tasks - (e_cal_get_default_calendar): gets the default calendar - (e_cal_get_default_tasks): ditto for tasks - (e_cal_set_default_calendar): sets the default calendar - (e_cal_set_default_tasks): ditto for tasks - (set_default_source): set the default calendar/tasks source - (e_cal_set_default_calendar_source): set the default calendar - source - (e_cal_set_default_tasks_source): ditto for tasks - (get_sources): get a source list given a gconf key - (e_cal_get_calendars): get the calendar source list - (e_cal_get_tasks): get the tasks source list - -2004-01-28 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-container.[ch]: new class to contain all - information about containers in the server. - - * backends/groupwise/e-gw-connection.[ch] - (e_ge_connection_free_container_list): new function. - (e_gw_connection_get_container_list): changed to return a list of - EGwContainer's. - (e_gw_connection_get_container_id): adapted to changes made in - e_gw_connection_get_container_list(). - -2004-01-27 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.h: update proto - - * libecal/e-cal.c (e_cal_remove): rename from - e_cal_remove_calendar - (e_cal_get_error_message): key on new status name - - * libecal/e-cal-types.h: rename - E_CALENDAR_STATUS_CARD_ID_ALREADY_EXISTS to - E_CALENDAR_STATUS_OBJECT_ID_ALREADY_EXISTS, delete duplicate enum - - * idl/Evolution-DataServer-Calendar.idl: rename - CardIdAlreadyExists to ObjectIdAlreadyExists - - * libecal/e-cal-listener.c (convert_status): key on new name - - * backends/file/e-cal-backend-file.c - (e_cal_backend_file_create_object): return object id already - exists - -2004-01-27 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c - (get_e_cal_component_from_soap_parameter): not having the priority - or dueDate properties is not an error. - -2004-01-27 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c - (get_attendee_list_from_soap_parameter): don't allocate memory for - ECalComponentAttendee's fields, make them just point to the values - contained in the SoupSoapResponse. - (get_e_cal_component_from_soap_parameter): don't free - ECalComponentAttendee's fields, free the structure. - (e_gw_connection_send_item): fixed warnings. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_get_object): - (e_cal_backend_groupwise_remove): lock/unlock the mutex when accessing - private fields. - -2004-01-27 JP Rosevear <jpr@ximian.com> - - * libedata-cal/e-cal-backend-cache.c (get_filename_from_uri): take - a const uri - (e_cal_backend_cache_set_property): pass a const value - (e_cal_backend_cache_constructor): uri is const - (e_cal_backend_cache_put_component): rid is const - (e_cal_backend_cache_get_components): distinguish between GList - and GSList - - * libedata-cal/e-cal-backend-sexp.c (func_uid): make sure we - always set a return value - -2004-01-27 JP Rosevear <jpr@ximian.com> - - * backends/groupwise/e-gw-connection.c - (get_e_cal_component_from_soap_parameter): description is not - const - -2004-01-27 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_start_query): fixed memory leaks and use - g_list_* functions for GList's, not g_slist_*. - (match_object_sexp, match_recurrence_sexp): removed unneeded functions, - we match the object directly in get_object_list. - (e_cal_backend_groupwise_start_query): call get_object_list to retrieve - the matched objects and call e_data_cal_view_notify_* functions - appropriately. - -2004-01-26 Harish K <kharish@novell.com> - - * calendar/backends/groupwise/e-cal-backend-groupwise.c : - (e_cal_backend_groupwise_internal_get_default_timezone, - e_cal_backend_groupwise_internal_get_timezone) : added and - implemented. - (e_cal_backend_groupwise_get_object_list) : fixed incorrect - access to the list. - (e_cal_backend_groupwise_start_query) : fixed compiler warnings. - - * calendar/backends/groupwise/e-gw-connection.c : - (e_gw_connection_get_container_id) : Modified elements 'Folders' to - the 'folders' due to change in the server implementation. - Fixed compiler warnings. - -2004-01-24 Rodrigo Moya <rodrigo@ximian.com> - - * backends/http/e-cal-backend-http.c: make it use - ECalBackendCache for its cache, and libsoup for the HTTP - retrieval. - (retrieval_progress_cb, uri_to_cache_dir, ensure_cache_dir): removed - unneeded functions. - (e_cal_backend_http_finalize): cancel Soup message here, if any, and - close Soup session. - (begin_retrieval_cb): use soup_session_queue_message() to send the - HTTP request to the server. - (retrieval_done): update the cache on success, and changed to be the - callback for the Soup async message. - (e_cal_backend_http_open): create a ECalBackendCache, not an - ECalBackendFile. - (e_cal_backend_http_remove): remove the cache. - (e_cal_backend_http_is_loaded, e_cal_backend_http_get_default_object, - e_cal_backend_http_get_object, e_cal_backend_http_get_timezone, - e_cal_backend_http_add_timezone, - e_cal_backend_http_set_default_timezone, - e_cal_backend_http_get_object_list, e_cal_backend_http_start_query, - e_cal_backend_http_get_default_timezone, - e_cal_backend_http_get_timezone): - dont proxy calls to the file backend, use the cache instead. - (e_cal_backend_http_create_object, e_cal_backend_http_modify_object, - e_cal_backend_http_remove_object, e_cal_backend_http_receive_objects, - e_cal_backend_http_send_objects): - the HTTP backend is read only, return permission denied error. - - * backends/http/Makefile.am: added SOUP_CFLAGS|LIBS. - - * backends/groupwise/Makefile.am: s/GROUPWISE/SOUP. - -2004-01-23 Harish K <kharish@novell.com> - - * calendar/backends/groupwise/e-cal-backend-groupwise.c - Removed update_cache function and refactored the call-back - to use e-gw-connection_get_deltas instead of update_cache. - * calendar/backends/groupwise/e-gw-connection.c - use g_new0 instead of g_malloc0 and added NULL check for - validating the soap responses. - (get_e_cal_component_from_soap_parameter) added code to - parse 'message' into description. - -2004-01-22 Harish K <kharish@novell.com> - - * calendar/backends/groupwise/e-cal-backend-groupwise.c - (populate_cache, e_cal_backend_groupwise_get_object_list, - e_cal_backend_groupwise_get_free_busy ) :changed implementation - to use GList instead of GSList, aligning to the rest of the - backends. - (e_cal_backend_groupwise_get_changes, update_cache): implemented. - - * calendar/backends/groupwise/e-gw-connection.c - (get_attendee_list_from_soap_parameter) : modified - get_attendee_list_from_string to handle recipients element. - (get_e_cal_component_from_soap_parameter) -fixed memory leaks. - (update_cache_item) : implemented. - (e_gw_connection_get_freebusy_info, start_freebusy_session) - GSList to GList changes. - - * calendar/backends/groupwise/e-gw-connection.h : updated - declarations for the above changes. - - * calendar/libedata-cal/e-cal-backend-cache.[ch] : - (e_cal_backend_cache_get_components) : return GList instead of - GSList. - -2004-01-21 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_remove): remove the cache from disk - when removing the calendar. - - * backends/file/e-cal-backend-file.c - (e_cal_backend_file_remove): added missing call to g_dir_close(). - -2004-01-21 Rodrigo Moya <rodrigo@ximian.com> - - * backends/file/e-cal-backend-file.c (e_cal_backend_file_remove): - use the full path when removing files. - -2004-01-21 JP Rosevear <jpr@ximian.com> - - * libecal/Makefile.am: don't build client test - -2004-01-21 JP Rosevear <jpr@ximian.com> - - * tests/ecal/test-ecal.c: the beginnings of a test client - - * tests/ecal/Makefile.am: build the test client - - * tests/Makefile.am: add ecal subdir - - * Makefile.am: add tests subdir - -2004-01-21 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (e_cal_new): create the component listener - here, so that backend_died_cb gets called when the backend dies. - -2004-01-21 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (connect_to_server): added code for retrieving the container ID - for tasks also. - -2004-01-21 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_open): added missing g_mutex_unlock - call. - -2004-01-21 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c - (get_e_cal_component_from_soap_parameter): check arguments before - passing them to functions to avoid warnings at runtime. - -2004-01-21 Rodrigo Moya <rodrigo@ximian.com> - - * backends/file/e-cal-backend-file.c (create_cal): create - directory tree to contain the calendar. - -2004-01-21 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c - (get_e_cal_component_from_soap_parameter): return error when - the type of the component does not match the supported ones. - -2004-01-21 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #51705 - - * backends/file/e-cal-backend-file.c (e_cal_backend_file_remove): - remove all files in the directory and the directory itself. - -2004-01-21 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c (match_recurrence_sexp, - match_object_sexp): use a GSList, which is what we are passed - to e_cal_backend_groupwise_get_object_list. - (e_cal_backend_groupwise_start_query): fixed warning. - -2004-01-20 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_set_mode): split out the connection code. - (connect_to_server): and moved it here. - (e_cal_backend_groupwise_open): call connect_to_server, not - set_mode, to avoid online/offline notifications. - -2004-01-19 Harish K <kharish@novell.com> - - * backends/groupwise/e-gw-connection.c : - (get_e_cal_component_from_soap_parameter): - 'due' property set for TODOs instead of dtend. - added code for mapping all values of GW data to - percent, priority, classification, transparency - properties in ECalComponent. - Fixed compiler warnings. - -2004-01-18 Harish K <kharish@novell.com> - - * backends/groupwise/e-cal-backend-groupwise.c : - (e_cal_backend_groupwise_get_free_busy): Implemented. - * backends/groupwise/e-gw-connection.[ch] : - (e_gw_connection_get_deltas) : Implemented parsing of - the response. - (e_gw_connection_get_free_busy_info) : Implemented - including private functions - (get_attendee_list_from_string, start_freebusy_session and - close_freebusy_session). - (e_gw_connection_get_container_id) : remove unused variable. - (get_e_cal_component_from_soap_parameter) : added code to - set attendee_list to the e_cal_component. - (get_evo_date_from_string) : fixed typo. - -2004-01-16 JP Rosevear <jpr@ximian.com> - - * backends/file/e-cal-backend-file.c (save): remove test bits - -2004-01-16 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c (categories_changed_idle_cb): remove debug - statement - -2004-01-16 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (e_cal_open): return AUTH_REQUIRED error if - we don't get a password from the authentication function. - - * backends/file/e-cal-backend-file.c - (e_cal_backend_file_modify_object): store the old object before - actually losing it. - -2004-01-16 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c: name space the idle data structs properly - -2004-01-16 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c (backend_error_idle_cb): idle handler to - actually proxy the signal emission to the main thread - (backend_error_cb): use above - (categories_changed_idle_cb): idle handler for proxying - (categories_changed_cb): use above - - Fixes #52743 - -2004-01-16 Christian Neumair <chris@gnome-de.org> - - * libedata-cal/e-cal-backend-sexp.c (func_uid): - Error message string fix. - -2004-01-16 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-cache.c (get_filename_from_uri): use - ~/.evolution/cache/calendar for the cache files. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_get_object_list): lock/unlock the - private mutex. - -2004-01-16 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c - (e_gw_connection_get_container_id): fixed duplicated variable name. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_open): removed check for 'only_if_exists', - we'll return NoSuchCal error if we can't find the calendar to open. - -2004-01-15 Mark McLoughlin <mark@skynet.ie> - - * libecal/e-cal-listener.c: (impl_notifyCalSetMode), - (impl_notifyErrorOccurred), (impl_notifyCategoriesChanged): - Remove debugging spew. - -2004-01-15 Radek Doulik <rodo@ximian.com> - - * libecal/e-cal.c (e_cal_is_read_only): fix the return value, it - was returning ECalendarStatus instead of bool, it compares status - to E_CALENDAR_STATUS_OK now - -2004-01-14 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_open): if trying to create a new calendar, - return an error, since we don't support that. - (e_cal_backend_groupwise_remove): return "Permission Denied". - -2004-01-14 Harish K <kharish@novell.com> - - * libedata-cal/e-cal-backend-cache.c - (e_cal_backend_cache_get_components): return a list of e-cal-components - rather than e-cal-component strings. - -2004-01-13 JP Rosevear <jpr@ximian.com> - - * backends/groupwise/e-gw-connection.c - (get_e_cal_component_from_soap_parameter): remove C99 declaration - -2004-01-13 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-item.[ch] (e_gw_item_new_appointment): - added a 'container' argument. - (e_gw_item_dispose): free new field in the private structure. - - * backends/groupwise/e-gw-connection.[ch] - (e_gw_connection_send_appointment): added a 'container' argument. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_create_object, - e_cal_backend_groupwise_modify_object): adapted to changes in - e_gw_connection_send_appointment. - (e_cal_backend_groupwise_receive_objects): implemented. - -2004-01-13 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.[ch] - (e_gw_connection_get_items): moved the folder retrieving code to... - (e_gw_connection_get_container_id): ...here, new function. - - * backends/groupwise/e-cal-backend-groupwise.c: added 'container_id' - field to private structure. - (e_cal_backend_groupwise_finalize): free the container_id. - (populate_cache): pass the container_id to e_gw_connection_get_items. - (e_cal_backend_groupwise_set_mode): retrieve the container ID after - connecting to the server. - -2004-01-13 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.[ch] (logout): unref the message - if we dont get a response, not the response, which is NULL, and unref - it also before exiting the function. - (e_gw_connection_remove_item): new function. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_remove_object): implemented. - -2004-01-13 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal-component.[ch] (e_cal_component_get_recurid_as_string): - new function, moved from the file and groupwise backends. - - * libedata-cal/e-cal-backend-cache.[ch] - (e_cal_backend_cache_put_component): changed to get an ECalComponent. - - * backends/groupwise/e-gw-item.[ch]: new class for managing items - to be sent to the server. - - * backends/groupwise/e-gw-connection.[ch] (e_gw_connection_send_item, - e_gw_connection_send_appointment): new functions. - (e_gw_connection_get_container_list): made it public. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_create_object): finished implementation. - (e_cal_backend_groupwise_modify_object): implemented. - (get_rid_string): removed. - (populate_cache): adapted to changes in ECalBackendCache, and use - e_cal_component_get_recurid_as_string instead of the local - get_rid_string(). - - * backends/groupwise/Makefile.am: added new files. - - * backends/file/e-cal-backend-file.c (get_rid_string): removed. - (add_component, e_cal_backend_file_modify_object): use - e_cal_component_get_recurid_as_string instead of the local - get_rid_string(). - -2004-01-13 Harish K <kharish@novell.com> - - * calendar/backends/groupwise/e-cal-backend-groupwise.c - (populate_cache): fixed memory leaks. - (e_cal_backend_groupwise_open): return function with success when - invoked again after the cache has been created already. - (e_cal_backend_groupwise_get_object_list): implemented. - (e_cal_backend_groupwise_start_query): implemented. - - * calendar/backends/groupwise/e-gw-connection.c - (get_e_cal_component_from_soap_parameter): modification to strip - date and time separators in argument before calling - icaltime_from_string. - - * calendar/backends/groupwise/e-gw-connection.h - (e_gw_connection_get_delta): - Added declaration. - - * calendar/libedata-cal/e-cal-backend-cache.c - (e_cal_backend_cache_constructor): Added the function and updated - class_init to use it. - (e_cal_backend_cache_get_components): Added method to wrap - e_file_cache_get_objects for better abstraction. - (e_cal_backend_cache_set_property): fixed NULL termination to argument - list. - -2004-01-12 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_open): - * backends/http/e-cal-backend-http.c (e_cal_backend_http_open): made - the backends start online always, until we fix the online/offline - handling via the shell. - -2004-01-12 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.[ch] - (e_gw_connection_get_user_name, e_gw_connection_get_user_uuid): new - functions. - -2004-01-12 Rodrigo Moya <rodrigo@ximian.com> - - * backends/http/e-cal-backend-http.c (uri_to_cache_dir): fixed leak. - -2004-01-10 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-sexp.c (func_occur_in_time_range): - don't leak the dates retrieved with e_cal_component_get_dtstart/dtend. - - * libedata-cal/e-cal-backend-sync.c (_e_cal_backend_get_timezone): - free the 'object' string returned by the provider's get_timezone - method. - - * libedata-cal/e-data-cal-factory.c - (e_data_cal_factory_register_method): - g_free the string returned by g_ascii_strdown(). - -2004-01-10 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_get_timezone): fixed copy/paste typo. - (e_cal_backend_groupwise_remove, e_cal_backend_groupwise_add_timezone, - e_cal_backend_groupwise_set_default_timezone, - e_cal_backend_groupwise_get_object_list, - e_cal_backend_groupwise_get_free_busy, - e_cal_backend_groupwise_get_changes, - e_cal_backend_groupwise_discard_alarm, - e_cal_backend_groupwise_modify_object, - e_cal_backend_groupwise_remove_object, - e_cal_backend_groupwise_receive_objects, - e_cal_backend_groupwise_send_objects): - fixed compilation warnings. - - * backends/groupwise/Makefile.am: - * backends/groupwise/groupwise-config-listener.c: removed unused file. - -2004-01-09 Harish K <kharish@novell.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (populate_cache): implemented. - - * backends/groupwise/e-gw-connection.h: - added declaration for e_gw_connection_get_items. - - * backends/groupwise/e-gw-connection.c: - (e-gw-connection-get-items) :implementation to obtain - calendar data from GW using SOAP. - -2004-01-08 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c (convert_type): kill warning - (e_cal_get_timezone): fix preconditions, tzid being NULL is valid, - set *zone to NULL if we short circuit on a local time - -2004-01-07 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_open): keep the username and password - passed from the client, and don't open the connection here. - (e_cal_backend_groupwise_set_mode): ...do it here, when we change - mode to 'online'. - (e_cal_backend_groupwise_get_mode): implemented. - (e_cal_backend_groupwise_is_loaded): check the cache, not the - connection, since we can be loaded without being online. - (populate_cache): made it static. - - * backends/http/e-cal-backend-http.c (begin_retrieval_cb): only - begin the retrieval if we are online. - - * libecal/e-cal-util.h: added cal_mode_to_corba macro from - e-cal-backend-http.c. - -2004-01-07 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (convert_type): removed g_assert_not_reached. - -2004-01-07 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (e_cal_get_alarms_for_object): pass the correct - callback data for e_cal_resolve_tzid_cb(). - -2004-01-07 JP Rosevear <jpr@ximian.com> - - * libedata-cal/Makefile.am: remove DISABLE_DEPRECATED flags - - * libecal/Makefile.am: ditto - -2004-01-07 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (build_component_alarms_list): clone the icalcomponent - to avoid having a pointer to an object that is freed afterwards, in - e_cal_get_alarms_in_range. - (e_cal_get_alarms_in_range): use icalcomponent_free to free the objects - in the list returned by e_cal_get_object_list. - -2004-01-07 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (build_component_alarms_list): pass the correct - data (an ECal, not an icalcomponent) to e_cal_resolve_tzid_cb. - -2004-01-06 JP Rosevear <jpr@ximian.com> - - * libedata-cal/e-cal-backend-sexp.c (func_uid): implement uid - checking for sexps - (e_cal_backend_sexp_new): use nice glib macro to count sexp - elements - - * libedata-cal/e-cal-backend-cache.c: guard config.h include and - include string.h to kill warning - -2004-01-06 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.c (build_component_alarms_list): the list returned - by e_cal_get_object_list() contains icalcomponent's already, - so no need to parse them as strings. - (e_cal_open): fixed warning. - -2004-01-05 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-message.[ch] - (e_gw_message_write_string_parameter): added 'prefix' argument, for - not hard-coding all parameters to the "types" prefix. - - * backends/groupwise/e-gw-connection.c (logout, e_gw_connection_new, - e_gw_connection_get_items): pass the XML prefix to - e_gw_message_write_string_parameter(). - -2004-01-05 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-cache.[ch] (e_cal_backend_cache_put_object): - merged _add_component and _replace_component into a single function. - - * backends/groupwise/e-cal-backend-groupwise.c (populate_cache): - use e_cal_backend_cache_put_object, and let the cache deal with - additions/replacements. - -2004-01-05 Sivaiah Nallagatla <snallagatla@novell.com> - - * backends/groupwise/groupwise-config-listener.[ch] : new class implementing addition, - removal, modification of e-sources for calender and tasks for groupwise accounts. - - * backends/groupwise/Makefile.am : added above two files in Makefile.am - -2004-01-05 Christian Neumair <chris@gnome-de.org> - - * libedata-cal/e-cal-backend-sexp.c: Generalize some strings. - -2003-12-24 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c (e_gw_connection_get_items): - fixed warning. - -2003-12-24 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-message.[ch] (e_gw_message_new_with_header): - added 'session_id' argument, to add the <Header> SOAP part if not NULL. - - * backends/groupwise/e-gw-connection.c (e_gw_connection_get_items): use - e_gw_message_new_with_header to create the SOAP message. Also, unref - the correct object if we don't get a response from - e_gw_connection_send_message, or we when we can't find a parameter in - the response. - (logout): pass session ID to e_gw_message_new_with_header(). - (e_gw_connection_new): ditto. - - * backends/groupwise/e-cal-backend-groupwise.c: removed 'icalcomp' - field from the ECalBackendGroupwisePrivate structure. - (e_cal_backend_groupwise_get_timezone): don't use priv->icalcomp - to retrieve timezones, since that object is empty, use the libical's - built-in timezones. - (populate_cache): fixed C99'isms and re-enabled g_mutex_lock/_unlock - calls. - -2003-12-24 Harish Krishnaswamy <kharish@novell.com> - - * backends/groupwise/e-gw-connection.[ch] (e_gw_connection_get_items): - new function. - - * backends/groupwise/e-cal-backend-groupwise.c (populate_cache): new - function to populate the cache with all objects from the server. - (e_cal_backend_groupwise_open): call populate_cache when opening the - connection, to get all objects from the server. - (e_cal_backend_groupwise_get_default_object): implemented. - (e_cal_backend_groupwise_get_timezone): implemented. - -2003-12-22 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-sexp.c (func_has_alarms): removed useless - 'has_to_have_alarms' variable. - -2003-12-22 JP Rosevear <jpr@ximian.com> - - * backends/file/e-cal-backend-file.c - (e_cal_backend_file_modify_object): check the kind with the parent - (e_cal_backend_file_create_object): ditto - -2003-12-21 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.h: update protos - - * libecal/e-cal.c: use ECalSourceType - (convert_type): convert and ECalSourceType to a corba equivalent - (fetch_corba_cal): use ECalSourceType - (e_cal_new): ditto - (e_cal_new_from_uri): ditto - (e_cal_generate_instances): does not need a type arg - - * libecal/e-cal-util.h: remove CalObjType - - * libecal/client-test.c (create_client): use ECalSourceType - (main): ditto - -2003-12-21 JP Rosevear <jpr@ximian.com> - - * backends/file/e-cal-backend-file.c (open_cal): set the uri - before scanning the vcalendar because we may have to fix duplicate - UIDs (and hence save the calendar) - -2003-12-19 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c (e_cal_get_alarms_in_range): create a valid sexp - -2003-12-19 Rodrigo Moya <rodrigo@ximian.com> - - * libecal/e-cal.[ch] (e_cal_class_init): removed 'forget_password' - signal, since it's not used anywhere. - -2003-12-19 Rodrigo Moya <rodrigo@ximian.com> - - * idl/Evolution-DataServer-Calendar.idl: added 'username' and 'password' - arguments to Cal::open method, so that we can send authentication - from the clients. - - * libedata-cal/e-cal-backend.[ch] (e_cal_backend_open): - * libedata-cal/e-cal-backend-sync.[ch] (e_cal_backend_sync_open, - _e_cal_backend_open): - * libedata-cal/e-data-cal.c (impl_Cal_open): - * backends/http/e-cal-backend-http.c (e_cal_backend_http_open): - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_open): - * backends/file/e-cal-backend-file.c (e_cal_backend_file_open): adapted - to changes in above method. - - * libecal/e-cal.[ch]: added E_CAL_LOAD_AUTHENTICATING to LoadState enum. - (e_cal_open): check with the ESource if the server needs authentication - or not, and if so, ask the client's provided auth function. Call - GNOME_Evolution_Calendar_Cal_Open with the new arguments. - -2003-12-18 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c: use a GMutex for - thread safety. - (e_cal_backend_groupwise_init): create the GMutex. - (e_cal_backend_groupwise_finalize): free the GMutex. - (e_cal_backend_groupwise_open): use the mutex. - -2003-12-17 JP Rosevear <jpr@ximian.com> - - * backends/groupwise/e-gw-connection.c (e_gw_connection_init): - create a synchronous session - -2003-12-17 Hans Petter Jansson <hpj@ximian.com> - - * libecal/e-cal.c (e_cal_finalize): Unref source. - (fetch_corba_cal): Ref and keep source. - (e_cal_get_source): Implement. - -2003-12-17 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/create-account.c: added support for specifying - a password, since we need one to connect to the server. - -2003-12-16 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c (e_gw_connection_new): no need to - set the namespace for "types:", it's already set in - e_gw_message_new_with_header(). - -2003-12-16 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-message.c (e_gw_message_new_with_header): - added the namespace for the SOAP types. - - * backends/groupwise/e-gw-connection.c (logout): fixed copy-paste typo. - - * backends/groupwise/soap-test.c (idle_cb): unref the EGwConnection - object, so that the logout message is sent to the server. - -2003-12-16 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_open): return an AuthenticationFailed error - when we can't open the connection. - -2003-12-16 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c (e_cal_get_free_busy): the info is already in - ECalComponent form, no need to process it again, from Gary Ekker - <gekker@novell.com> - - Fixes #52218 - -2003-12-16 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c (parse_response_status): map - some error codes. - (e_gw_connection_new): retrieve all the info returned in the UserInfo - type (name, email and uuid). - (e_gw_connection_disposee): free new private fields. - -2003-12-16 Sivaiah Nallagatla <snallagatla@novell.com> - - * backends/groupwise/e-gw-connection.h - * backends/groupwise/e-gw-connection.c (e_gw_connection_new, - e_gw_connection_get_user_email) - * backends/groupwise/e-cal-backend-groupwise.c (e_cal_backend_groupwise_get_ldap_attribute, - e_cal_backend_groupwise_get_cal_address, e_cal_backend_groupwise_is_read_only, - e_cal_backend_groupwise_get_alarm_email_address, e_cal_backend_groupwise_get_static_capabilities - e_cal_backend_groupwise_open ): added implementation for all the apis listed above - -2003-12-15 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal-listener.c (e_cal_listener_class_init): fix the - number of parameters for get free busy and get_changes - -2003-12-15 Rodrigo Moya <rodrigo@ximian.com> - - * backends/e-cal-backend-sync.c (_e_cal_backend_sync_get_ldap_attribute, - _e_cal_backend_sync_get_static_capabilities, - _e_cal_backend_sync_get_alarm_email_address): call the correct - e_cal_backend_sync_* functions, typo pointed out by Siva. - -2003-12-15 Rodrigo Moya <rodrigo@ximian.com> - - * backends/file/e-cal-backend-file.c - (e_cal_backend_file_get_static_capabilities): g_strdup the - 'capabilities' argument, since it is expected to be freed in - e-cal-backend-sync.c. - - * backends/http/e-cal-backend-http.c - (e_cal_backend_http_get_static_capabilities): ditto. - -2003-12-14 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal-component.c (set_datetime): don't remove and then - free the param, lest we double free it - - Fixes #51633 - -2003-12-14 JP Rosevear <jpr@ximian.com> - - * libedata-cal/e-data-cal.c (e_data_cal_notify_free_busy): call - the correct notification method - -2003-12-13 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/Makefile.am: set the correct G_LOG_DOMAIN. - -2003-12-12 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-message.c (e_gw_message_new_with_header): - added SOAPAction header to the request. - -2003-12-12 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-message.c (e_gw_message_write_footer): write - the request's content here. - (e_gw_message_new_with_header): add the Content-Type header. - - * backends/groupwise/e-gw-connection.c (e_gw_connection_send_message): - no need to write the request here, it's written in - e_gw_message_write_footer(). - -2003-12-12 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-message.c (setup_debug): fixed typo. - - * backends/groupwise/Makefile.am: use $DEBUG_CFLAGS. - -2003-12-12 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-message.c (setup_debug, print_header, - debug_handler): new functions for adding debugging of the SOAP messages. - (e_gw_message_new_with_header): if G_ENABLE_DEBUG is defined, setup - debugging for the message. Also, use POST to send the messages. - - * doc/gw-soap-methods.xsd: - * doc/gw-soap-types.xsd: added new versions of SOAP interfaces. - -2003-12-11 Rodrigo Moya <rodrigo@ximian.com> - - Fixes #52013 - - * backends/file/e-cal-backend-file.c (create_user_free_busy): pass - the TIME arguments correctly. - -2003-12-10 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c: use a SoupSession per - EGwConnection, not one for all. - (e_gw_connection_dispose): unref the SoupSession here. - (e_gw_connection_init): create the SoupSession here. - (e_gw_connection_send_message): use the private SoupSession. - -2003-12-10 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/soap-test.c: added support for specifying a - password in the command line. - - * backends/groupwise/e-gw-connection.c (e_gw_connection_new): dont - unref the response when we havent got one. - -2003-12-10 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c (e_gw_connection_finalize): - only try to remove the connection from the hash table if the hash - table has been created. - -2003-12-10 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/soap-test.c: new test program to test the - SOAP interface to the GW server. - - * backends/groupwise/Makefile.am: compile new test program. - -2003-12-10 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c (e_cal_get_default_object): don't preload the - timezones into the cache, its problematic because we don't want to - have multiple operations at the same time and we don't do this for - views for instance - (e_cal_get_object): ditto - - Fixes #51225 - -2003-12-09 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal-listener.c (impl_notifyStaticCapabilities): - actually emit the capabilities string - - Fixes #51747 - -2003-12-09 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.[ch]: made the connections be - shared. - (e_gw_connection_new): get the uri, username and password here, and - before trying to login again to the server, see if we have already - the same connection request in the loaded connections hash table. - (e_gw_connection_login): removed. - (e_gw_connection_logout): just unref the connection, the logout code - moved to... - (logout): ...here. - (e_gw_connection_dispose): free new members. - (e_gw_connection_finalize): remove the connection from the hash table, - and destroy the hash table when there are no more connections on it. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_open): use the new EGwConnection interface. - -2003-12-08 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-cache.h: the class structure derives - from EFileCacheClass, not EFileCache. - - * libedata-cal/e-cal-backend-cache.c (get_filename_from_uri): iterate - correctly over the characters in the URI. - -2003-12-08 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-cache.[ch]: use EFileCache instead - of ECache. - -2003-12-08 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c (convert_uri): - new function to convert "groupwise://" URIs to "http://". - (e_cal_backend_groupwise_open): call the above function to - get a GnomeVFSURI, and use it as a temporary hack to get - username and password. - -2003-12-07 JP Rosevear <jpr@ximian.com> - - * libedata-cal/e-data-cal-factory.c: version the oafiid - - * libecal/e-cal.c (get_factories): update the repo id - -2003-12-07 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c (get_factories): use the versioned repo id - -2003-12-04 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/create-account.c (add_account): add the username - in the source URI, and use e_source_list_sync, to give it time to - sync the GConf changes. - -2003-12-04 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/create-account.c: changed to use a main loop, - or saving to GConf seems not to work ?? - -2003-12-04 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/create-account.c (add_account): add the source - to the group. - -2003-12-04 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/create-account.c: make it use a username also. - -2003-12-04 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/create-account.c: added simple program to - add accounts to the calendar sources until we a GUI to configure - them. - - * backends/groupwise/Makefile.am: added noinst program. - -2003-12-03 Christian Kellnerc <gicmo@xatom.net> - - * libedata-cal/e-cal-backend-sexp.c: added has-recurrences sexp - function - -2003-12-03 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-cal-backend-groupwise.c: use a cache - to keep the objects from the server. - (e_cal_backend_groupwise_finalize): unref the cache object. - (e_cal_backend_groupwise_open): load/create the local cache. - (e_cal_backend_groupwise_get_object): look for the object in - the cache. - (e_cal_backend_groupwise_class_init): fixed warning. - -2003-12-01 William Jon McCann <mccann@jhu.edu> - - * libecal/e-cal.c (e_cal_generate_instances): Fix query and - get object list as components. - -2003-12-01 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-cache.[ch]: changed to be based on the - new ECache class. - (get_filename_from_uri): new function to get a unique filename for a - calendar/tasks URI. - (e_cal_backend_cache_set_property): get the filename for the given URI - and set the "filename" property on the cache, which will load/create - the cache file. - (e_cal_backend_cache_finalize): dont free removed fields. - (e_cal_backend_cache_get_component, e_cal_backend_cache_add_component, - e_cal_backend_cache_replace_component, e_cal_backend_cache_remove_component): - new functions. - - * backends/groupwise/e-gw-connection.c (e_gw_connection_login): retrieve - the session from the response, not the username. - -2003-11-28 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.c (parse_response_status): new - function to parse the "status" field returned in the SOAP response. - (e_gw_connection_login, e_gw_connection_logout): call above function - to get the status, and return that to the caller. - - * backends/groupwise/TODO: updated with more tasks. - -2003-11-27 Rodrigo Moya <rodrigo@ximian.com> - - * libedata-cal/e-cal-backend-cache.[ch]: new class implementing a - cache of calendar/tasks objects. - - * libedata-cal/Makefile.am: added new files. - -2003-11-26 Hans Petter Jansson <hpj@ximian.com> - - * idl/Evolution-DataServer-Calendar.idl (getCal): Take source XML - instead of URI. - - * libecal/client-test.c (create_client): Adapt to API changes. - (main): Ditto. - - * libecal/e-cal.c (fetch_corba_cal): Move to ESource. - (e_cal_new): Take ESource. - (e_cal_new_from_uri): Implement convenience call that takes URI. - - * libedata-cal/e-cal-backend.c (e_cal_backend_set_property): - Implement PROP_SOURCE. - (e_cal_backend_get_property): Same. - (e_cal_backend_class_init): Same. - (e_cal_backend_get_source): Same. - - * libedata-cal/e-data-cal-factory.c (impl_CalFactory_getCal): Take - source XML and construct an ESource. Init backend with that. - -2003-11-25 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-message.[ch]: new files to contain utility - functions for easily creating SOAP messages. - - * backends/groupwise/e-gw-connection.[ch] (e_gw_connection_logout): - new function. - (e_gw_connection_finalize): if we're already connected, call - e_gw_connection_logout(). - (e_gw_connection_login): implement response parsing. - (e_gw_connection_send_message): new function. - - * backends/groupwise/e-cal-backend-groupwise.c - (e_cal_backend_groupwise_is_loaded): implemented. - - * backends/groupwise/Makefile.am: added new files. - -2003-11-20 Harry Lu <harry.lu@sun.com> - - * backends/file/e-cal-backend-file.c: - (e_cal_backend_file_internal_get_default_timezone): move to the front - to avoid a compile warning. - (e_cal_backend_file_internal_get_timezone): ditto. - (sanitize_component): new function. If the component's timezone is not - included in buildin timezone list, convert it to local default timezone. - (e_cal_backend_file_create_object): call sanitize_component. - (e_cal_backend_file_modify_object): ditto. - (e_cal_backend_file_receive_objects): ditto. - -2003-11-18 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/e-gw-connection.h: fixed typo. - - * backends/groupwise/e-gw-connection.c: base it on GObject, not - SoupConnection. - (e_gw_connection_login): new functions. - (e_gw_connection_init): create the SoupSession here if it's not - created, or ref it if it's already created. - (e_gw_connection_finalize): unref the SoupSession here. - (session_weak_ref_cb): callback to detect when the SoupSession dies. - - * backends/groupwise/e-cal-backend-groupwise.c: make it use - EGwConnection's. - (e_cal_backend_groupwise_finalize): unref the EGwConnection. - (e_cal_backend_groupwise_open): create the EGwConnection here. - -2003-11-17 Rodrigo Moya <rodrigo@ximian.com> - - * backends/groupwise/gw-connection.[ch]: new class for managing - connections to Groupwise servers. - - * backends/groupwise/Makefile.am: added new files and needed - CFLAGS and LIBS. - -2003-11-17 Dan Winship <danw@ximian.com> - - * libecal/e-cal-util.c (e_cal_util_new_component): New - icalcomponent-based replacement for - e_cal_component_new/e_cal_component_set_vtype. - - * libedata-cal/e-data-cal.c: fix up some broken indentation - (e_data_cal_notify_default_object, e_data_cal_notify_object): - constify the object arg - -2003-11-14 Rodrigo Moya <rodrigo@ximian.com> - - * backends/Makefile.am: added groupwise backend directory to build. - - * backends/groupwise/Makefile.am: - * backends/groupwise/e-cal-backend-groupwise.[ch]: Groupwise backend - skeleton. - -2003-11-11 ChangeLog <jpr@ximian.com> - - * libecal/e-cal.c (e_cal_class_init): emit the status - - * libecal/e-cal.h: remove open status enums, use calendar status - instead - - * libecal/client-test.c (create_client): just directly open the - calendar, no need to be async - -2003-11-11 Dan Winship <danw@ximian.com> - - * libedata-cal/e-cal-backend-sexp.c: Make the time-related sexp - function handlers (eg, time-now, make-time, etc) be non-static, so - they can be reused by backend-specific calendar sexp parsers. - -2003-11-10 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.h: remove dead enums - -2003-11-10 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.h: mark struct as private - - * libecal/e-cal.c: fix documentation headers - - * libecal/e-cal-view.h: fix cast macros and typedef the structs - separately - - * libecal/e-cal-view.c: use correct type check macro, fix some - documentation headers - - * libecal/e-cal-view-listener.h: typedef the structs separately - and tidy up class macros - - * libecal/e-cal-util.c: fix a documentation header - - * libecal/e-cal-listener.h: mark parts of the struct as private - - * libecal/e-cal-listener.c: fix a few documentation headers - - * libecal/e-cal-component.h: remove extraneous comma and mark - parts of struct as private - - * libecal/e-cal-component.c: fix a couple of documentation headers - -2003-11-10 Dan Winship <danw@ximian.com> - - * libedata-cal/e-cal-backend-sexp.c: Remove get-vtype from the - query language, since it is redundant now. - (func_has_alarms): Remove the boolean arg from has-alarms. You can - just say (not (has-alarms?)). - -2003-11-10 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.h: add proto - - * libecal/e-cal.c (e_cal_free_change_list): this belongs here - - * libecal/e-cal-types.h: remove proto - - * libecal/Makefile.am: don't build dead file - -2003-11-07 Dan Winship <danw@ximian.com> - - * libecal/Makefile.am (libecal_la_LDFLAGS): Remove -no-undefined - - * libedata-cal/Makefile.am (libedata_cal_la_LDFLAGS): Likewise - -2003-11-06 <jpr@ximian.com> - - * libecal/e-cal-view-listener.h: match the signals better - - * libecal/e-cal-view-listener.c (e_cal_view_listener_class_init): - ditto - -2003-11-06 JP Rosevear <jpr@ximian.com> - - * libecal/e-cal.c: replace e_mutex stuff with gthread stuff - -2003-11-06 JP Rosevear <jpr@ximian.com> - - * Makefile.am: build new subdirs - - * backends/*: build the http and file backends here - - * libedata-cal/Makefile.am: no longer build them here - -2003-11-05 JP Rosevear <jpr@ximian.com> - - * rename libedatacal to libedata-cal - -2003-11-05 JP Rosvear <jpr@ximian.com> - - * libecal/Makefile.am: use privincludedir - - * libedatacal/Makefile.am: ditto - - * libecal/libecal-1.0.pc.in: ditto - - * libedatacal/libedatacal-1.0.pc.in: use privincludedir; remove - gal - -2003-11-05 JP Rosevear <jpr@ximian.com> - - * libecal/Makefile.am: LIBADD all the relevant libical libs - - * libecal/libecal-1.0.pc.in: no need to explicitly link - libical-evolution - - * libedatacal/libedatacal-1.0.pc.in: ditto; fix include dir - -2003-11-05 Rodrigo Moya <rodrigo@ximian.com> - - * libedatacal/e-cal-backend-sexp.c: removed GAL dependency. - -2003-11-04 JP Rosevear <jpr@ximian.com> - - * libedatacal/e-data-cal-factory.c: use properly name spaced - default id - -2003-11-04 JP Rosevear <jpr@ximian.com> - - * libecal/libecal-1.0.pc.in (prefix): include priv dir stuff for - libical - - * libedatacal/libedatacal-1.0.pc.in (prefix): ditto - - * libecal/e-cal-component.[hc]: properly name space alarm action - enum - - * libecal/e-cal-types.h: properly name space change types - -2003-11-04 JP Rosevear <jpr@ximian.com> - - * libedatacal/e-data-cal-factory.c: remove corba header include - - * libedatacal/e-cal-backend-sync.h: include corba header properly - - * libedatacal/e-data-cal.h: ditto - - * libedatacal/e-data-cal-view.h: ditto - - * libedatacal/e-data-cal-factory.h: ditto - - * libedatacal/e-cal-backend.h: ditto - - * libedatacal/Makefile.am: reflect idl name change - - * libecal/e-cal-listener.h: include corba header properly - - * libecal/e-cal-view.h: ditto - - * libecal/e-cal-view-listener.h: ditto - - * libecal/Makefile.am: reflect idl name change - - * idl/Makefile.am: rename the idl to Evolution-DataServer-Calendar.idl - -2003-11-03 Hans Petter Jansson <hpj@ximian.com> - - * calendar/libedatacal/e-cal-backend-file.c (free_calendar_components) - (free_calendar_data): Implement. - (e_cal_backend_file_dispose): Use above freers. - (get_uri_string_for_gnome_vfs): Implement. - (open_cal): Set priv->uri to be escaped, GnomeVFS-friendly. - (notify_removals_cb) - (notify_adds_modifies_cb) - (notify_changes) - (reload_cal): Implement. - (create_cal): Set priv->uri to be escaped, GnomeVFS-friendly. - (get_uri_string): Implement - unescapes once. - (e_cal_backend_file_compute_changes): Unescape DB URI once, don't make - like it's in a subdirectory. - (e_cal_backend_file_reload): Implement. - - * calendar/libedatacal/e-cal-backend-http.c - (e_cal_backend_http_finalize): Cancel potential retrieval and free - slave backend. - (e_cal_backend_http_is_read_only): Clean up. - (webcal_to_http_method) - (uri_to_cache_dir) - (ensure_cache_dir) - (retrieval_done) - (retrieval_progress_cb) - (begin_retrieval_cb): Implement. - (e_cal_backend_http_open): Set up slave backend. - (e_cal_backend_http_remove) - (e_cal_backend_http_is_loaded) - (e_cal_backend_http_get_default_object) - (e_cal_backend_http_get_object) - (e_cal_backend_http_get_timezone) - (e_cal_backend_http_add_timezone) - (e_cal_backend_http_set_default_timezone) - (e_cal_backend_http_get_object_list) - (e_cal_backend_http_get_free_busy) - (e_cal_backend_http_get_changes) - (e_cal_backend_http_discard_alarm) - (e_cal_backend_http_modify_object) - (e_cal_backend_http_remove_object) - (e_cal_backend_http_receive_objects) - (e_cal_backend_http_send_objects) - (e_cal_backend_http_internal_get_default_timezone) - (e_cal_backend_http_internal_get_timezone): Implement with fallthrough - to slave backend. - (e_cal_backend_http_init): Remove cruft. - - * calendar/libedatacal/e-cal-backend-sync.c - (e_cal_backend_sync_open): Use per-instance mutex. - (e_cal_backend_sync_init): Set up per-instance mutex. - (e_cal_backend_sync_dispose): Free per-instance mutex. - - * calendar/libedatacal/e-cal-backend.c - (e_cal_backend_set_notification_proxy): Implement. - (e_cal_backend_notify_object_created) - (e_cal_backend_notify_object_modified) - (e_cal_backend_notify_object_removed) - (e_cal_backend_notify_mode) - (e_cal_backend_notify_error): Use notification proxy if set. diff --git a/calendar/Makefile.am b/calendar/Makefile.am deleted file mode 100644 index 98feadd94..000000000 --- a/calendar/Makefile.am +++ /dev/null @@ -1 +0,0 @@ -SUBDIRS = libical idl libecal libedata-cal backends tests
\ No newline at end of file diff --git a/calendar/backends/.cvsignore b/calendar/backends/.cvsignore deleted file mode 100644 index c038ed786..000000000 --- a/calendar/backends/.cvsignore +++ /dev/null @@ -1,2 +0,0 @@ -Makefile -Makefile.in
\ No newline at end of file diff --git a/calendar/backends/Makefile.am b/calendar/backends/Makefile.am deleted file mode 100644 index a5174ca52..000000000 --- a/calendar/backends/Makefile.am +++ /dev/null @@ -1 +0,0 @@ -SUBDIRS = file groupwise http contacts diff --git a/calendar/backends/contacts/.cvsignore b/calendar/backends/contacts/.cvsignore deleted file mode 100644 index c038ed786..000000000 --- a/calendar/backends/contacts/.cvsignore +++ /dev/null @@ -1,2 +0,0 @@ -Makefile -Makefile.in
\ No newline at end of file diff --git a/calendar/backends/contacts/Makefile.am b/calendar/backends/contacts/Makefile.am deleted file mode 100644 index cb3506cb6..000000000 --- a/calendar/backends/contacts/Makefile.am +++ /dev/null @@ -1,23 +0,0 @@ -INCLUDES = \ - -DG_LOG_DOMAIN=\"libecalbackendcontact\" \ - -I$(top_srcdir) \ - -I$(top_builddir) \ - -I$(top_srcdir)/calendar \ - -I$(top_builddir)/calendar \ - -I$(top_srcdir)/calendar/libical/src \ - -I$(top_builddir)/calendar/libical/src \ - -I$(top_srcdir)/calendar/libical/src/libical \ - -I$(top_builddir)/calendar/libical/src/libical \ - -I$(top_srcdir)/addressbook \ - -I$(top_builddir)/addressbook \ - $(EVOLUTION_CALENDAR_CFLAGS) - -noinst_LTLIBRARIES = libecalbackendcontacts.la - -libecalbackendcontacts_la_SOURCES = \ - e-cal-backend-contacts.c \ - e-cal-backend-contacts.h - -libecalbackendcontacts_la_LIBADD = \ - $(top_builddir)/calendar/libedata-cal/libedata-cal.la - diff --git a/calendar/backends/contacts/e-cal-backend-contacts.c b/calendar/backends/contacts/e-cal-backend-contacts.c deleted file mode 100644 index 2dad0b092..000000000 --- a/calendar/backends/contacts/e-cal-backend-contacts.c +++ /dev/null @@ -1,1007 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* Evolution calendar - iCalendar file backend - * - * Copyright (C) 2000-2003 Ximian, Inc. - * Copyright (C) 2003 Gergõ Érdi - * - * Authors: Federico Mena-Quintero <federico@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * Gergõ Érdi <cactus@cactus.rulez.org> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <string.h> -#include <bonobo/bonobo-i18n.h> - -#include "e-cal-backend-contacts.h" - -#include <libedataserver/e-xml-hash-utils.h> -#include <libecal/e-cal-recur.h> -#include <libecal/e-cal-util.h> -#include <libedata-cal/e-cal-backend-util.h> -#include <libedata-cal/e-cal-backend-sexp.h> - -#include <libebook/e-book.h> - -#include <libedataserver/e-source-list.h> - -static ECalBackendSyncClass *parent_class; - -/* Private part of the ECalBackendContacts structure */ -struct _ECalBackendContactsPrivate { - ESourceList *addressbook_sources; - - GHashTable *addressbooks; /* UID -> BookRecord */ - gboolean addressbook_loaded; - - EBookView *book_view; - GHashTable *tracked_contacts; /* UID -> ContactRecord */ - - GHashTable *zones; - icaltimezone *default_zone; -}; - -typedef struct _BookRecord { - EBook *book; - EBookView *book_view; -} BookRecord; - -typedef struct _ContactRecord { - ECalBackendContacts *cbc; - EContact *contact; - ECalComponent *comp_birthday, *comp_anniversary; -} ContactRecord; - -#define d(x) - -#define ANNIVERSARY_UID_EXT "-anniversary" -#define BIRTHDAY_UID_EXT "-birthday" - -static ECalComponent * create_birthday (ECalBackendContacts *cbc, EContact *contact); -static ECalComponent * create_anniversary (ECalBackendContacts *cbc, EContact *contact); - -static void contacts_changed_cb (EBookView *book_view, const GList *contacts, gpointer user_data); -static void contacts_added_cb (EBookView *book_view, const GList *contacts, gpointer user_data); -static void contacts_removed_cb (EBookView *book_view, const GList *contact_ids, gpointer user_data); - -/* BookRecord methods */ -static BookRecord * -book_record_new (ECalBackendContacts *cbc, ESource *source) -{ - EBook *book; - GList *fields = 0; - EBookQuery *query; - EBookView *book_view; - BookRecord *br; - - book = e_book_new (source, NULL); - e_book_open (book, TRUE, NULL); - - /* Create book view */ - fields = g_list_append (fields, (char*)e_contact_field_name (E_CONTACT_FILE_AS)); - fields = g_list_append (fields, (char*)e_contact_field_name (E_CONTACT_BIRTH_DATE)); - fields = g_list_append (fields, (char*)e_contact_field_name (E_CONTACT_ANNIVERSARY)); - query = e_book_query_any_field_contains (""); - - if (!e_book_get_book_view (book, query, fields, -1, &book_view, NULL)) { - g_list_free (fields); - e_book_query_unref (query); - return NULL; - } - e_book_query_unref (query); - g_list_free (fields); - - g_signal_connect (book_view, "contacts_added", G_CALLBACK (contacts_added_cb), cbc); - g_signal_connect (book_view, "contacts_removed", G_CALLBACK (contacts_removed_cb), cbc); - g_signal_connect (book_view, "contacts_changed", G_CALLBACK (contacts_changed_cb), cbc); - - e_book_view_start (book_view); - - br = g_new (BookRecord, 1); - br->book = book; - br->book_view = book_view; - - return br; -} - -static void -book_record_free (BookRecord *br) -{ - if (!br) - return; - - g_object_unref (br->book_view); - g_object_unref (br->book); - - g_free (br); -} - -/* ContactRecord methods */ -static ContactRecord * -contact_record_new (ECalBackendContacts *cbc, EContact *contact) -{ - ContactRecord *cr = g_new0 (ContactRecord, 1); - char *comp_str; - - cr->cbc = cbc; - cr->contact = contact; - cr->comp_birthday = create_birthday (cbc, contact); - cr->comp_anniversary = create_anniversary (cbc, contact); - - if (cr->comp_birthday) { - comp_str = e_cal_component_get_as_string (cr->comp_birthday); - e_cal_backend_notify_object_created (E_CAL_BACKEND (cbc), - comp_str); - g_free (comp_str); - } - - if (cr->comp_anniversary) { - - comp_str = e_cal_component_get_as_string (cr->comp_anniversary); - e_cal_backend_notify_object_created (E_CAL_BACKEND (cbc), - comp_str); - g_free (comp_str); - } - - g_object_ref (G_OBJECT (contact)); - - return cr; -} - -static void -contact_record_free (ContactRecord *cr) -{ - char *comp_str; - const char *uid; - - g_object_unref (G_OBJECT (cr->contact)); - - /* Remove the birthday event */ - if (cr->comp_birthday) { - comp_str = e_cal_component_get_as_string (cr->comp_birthday); - e_cal_component_get_uid (cr->comp_birthday, &uid); - e_cal_backend_notify_object_removed (E_CAL_BACKEND (cr->cbc), uid, comp_str); - g_free (comp_str); - g_object_unref (G_OBJECT (cr->comp_birthday)); - } - - /* Remove the anniversary event */ - if (cr->comp_anniversary) { - comp_str = e_cal_component_get_as_string (cr->comp_anniversary); - e_cal_component_get_uid (cr->comp_anniversary, &uid); - e_cal_backend_notify_object_removed (E_CAL_BACKEND (cr->cbc), uid, comp_str); - g_free (comp_str); - g_object_unref (G_OBJECT (cr->comp_anniversary)); - } - - g_free (cr); -} - -/* ContactRecordCB methods */ -typedef struct _ContactRecordCB { - ECalBackendContacts *cbc; - ECalBackendSExp *sexp; - GList *result; -} ContactRecordCB; - -static ContactRecordCB * -contact_record_cb_new (ECalBackendContacts *cbc, ECalBackendSExp *sexp) -{ - ContactRecordCB *cb_data = g_new (ContactRecordCB, 1); - - cb_data->cbc = cbc; - cb_data->sexp = sexp; - cb_data->result = 0; - - return cb_data; -} - -static void -contact_record_cb_free (ContactRecordCB *cb_data) -{ - g_list_foreach (cb_data->result, (GFunc) g_free, 0); - g_list_free (cb_data->result); - - g_free (cb_data); -} - -static void -contact_record_cb (gpointer key, gpointer value, gpointer user_data) -{ - ContactRecordCB *cb_data = user_data; - ContactRecord *record = value; - - if (record->comp_birthday && e_cal_backend_sexp_match_comp (cb_data->sexp, record->comp_birthday, E_CAL_BACKEND (cb_data->cbc))) { - char * comp_str = e_cal_component_get_as_string (record->comp_birthday); - cb_data->result = g_list_append (cb_data->result, comp_str); - } - - if (record->comp_anniversary && e_cal_backend_sexp_match_comp (cb_data->sexp, record->comp_anniversary, E_CAL_BACKEND (cb_data->cbc))) { - char * comp_str = e_cal_component_get_as_string (record->comp_anniversary); - cb_data->result = g_list_append (cb_data->result, comp_str); - } -} - -/* SourceList callbacks */ -static void -add_source (ECalBackendContacts *cbc, ESource *source) -{ - BookRecord *br = book_record_new (cbc, source); - const char *uid = e_source_peek_uid (source); - - g_hash_table_insert (cbc->priv->addressbooks, g_strdup (uid), br); -} - -static void -source_added_cb (ESourceGroup *group, ESource *source, gpointer user_data) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (user_data); - - g_return_if_fail (cbc); - - add_source (cbc, source); -} - -static void -source_removed_cb (ESourceGroup *group, ESource *source, gpointer user_data) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (user_data); - const char *uid = e_source_peek_uid (source); - - g_return_if_fail (cbc); - - g_hash_table_remove (cbc->priv->addressbooks, uid); -} - -static void -source_group_added_cb (ESourceList *source_list, ESourceGroup *group, gpointer user_data) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (user_data); - GSList *i; - - g_return_if_fail (cbc); - - /* Load all address books from this group */ - for (i = e_source_group_peek_sources (group); i; i = i->next) - { - ESource *source = E_SOURCE (i->data); - add_source (cbc, source); - } - - /* Watch for future changes */ - g_signal_connect (group, "source_added", G_CALLBACK (source_added_cb), cbc); - g_signal_connect (group, "source_removed", G_CALLBACK (source_removed_cb), cbc); -} - -static void -source_group_removed_cb (ESourceList *source_list, ESourceGroup *group, gpointer user_data) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (user_data); - GSList *i = 0; - - g_return_if_fail (cbc); - - /* Unload all address books from this group */ - for (i = e_source_group_peek_sources (group); i; i = i->next) - { - ESource *source = E_SOURCE (i->data); - const char *uid = e_source_peek_uid (source); - - g_hash_table_remove (cbc->priv->addressbooks, uid); - } -} - -/************************************************************************************/ - -static void -contacts_changed_cb (EBookView *book_view, const GList *contacts, gpointer user_data) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (user_data); - const GList *i; - - for (i = contacts; i; i = i->next) - { - EContact *contact = E_CONTACT (i->data); - char *uid = e_contact_get_const (contact, E_CONTACT_UID); - - /* If no date is set, remove from list of tracked contacts */ - if (!e_contact_get (contact, E_CONTACT_BIRTH_DATE) && - !e_contact_get (contact, E_CONTACT_ANNIVERSARY)) { - g_hash_table_remove (cbc->priv->tracked_contacts, uid); - } else { - ContactRecord *cr = contact_record_new (cbc, contact); - g_hash_table_insert (cbc->priv->tracked_contacts, g_strdup (uid), cr); - } - } -} - -static void -contacts_added_cb (EBookView *book_view, const GList *contacts, gpointer user_data) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (user_data); - const GList *i; - - /* See if any new contacts have BIRTHDAY or ANNIVERSARY fields */ - for (i = contacts; i; i = i->next) - { - EContact *contact = E_CONTACT (i->data); - - if (e_contact_get (contact, E_CONTACT_BIRTH_DATE) || - e_contact_get (contact, E_CONTACT_ANNIVERSARY)) { - ContactRecord *cr = contact_record_new (cbc, contact); - const char *uid = e_contact_get_const (contact, E_CONTACT_UID); - - g_hash_table_insert (cbc->priv->tracked_contacts, g_strdup (uid), cr); - } - } -} - -static void -contacts_removed_cb (EBookView *book_view, const GList *contact_ids, gpointer user_data) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (user_data); - const GList *i; - - /* Stop tracking these */ - for (i = contact_ids; i; i = i->next) - g_hash_table_remove (cbc->priv->tracked_contacts, i->data); -} - -/************************************************************************************/ -static struct icaltimetype -cdate_to_icaltime (EContactDate *cdate) -{ - struct icaltimetype ret; - -/*FIXME: this is a really _ugly_ (temporary) hack - * since several functions are still depending on the epoch, - * let entries start (earliest) at 19700101 - */ - ret.year = cdate->year >= 1970 ? cdate->year : 1970; - ret.month = cdate->month; - ret.day = cdate->day; - ret.is_date = TRUE; - ret.zone = icaltimezone_get_utc_timezone (); - - ret.hour = ret.minute = ret.second = 0; - - return ret; -} - -/* Contact -> Event creator */ -static ECalComponent * -create_component (ECalBackendContacts *cbc, const char *uid, EContactDate *cdate, const char *summary) -{ - ECalComponent *cal_comp; - ECalComponentText comp_summary; - icalcomponent *ical_comp; - struct icaltimetype itt; - ECalComponentDateTime dt; - struct icalrecurrencetype r; - GSList recur_list; - - g_return_val_if_fail (E_IS_CAL_BACKEND_CONTACTS (cbc), 0); - - if (!cdate) - return NULL; - - ical_comp = icalcomponent_new (ICAL_VEVENT_COMPONENT); - - /* Create the event object */ - cal_comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (cal_comp, ical_comp); - - /* Set uid */ - d(g_message ("Creating UID: %s", uid)); - e_cal_component_set_uid (cal_comp, uid); - - /* Set all-day event's date from contact data */ - itt = cdate_to_icaltime (cdate); - dt.value = &itt; - dt.tzid = 0; - e_cal_component_set_dtstart (cal_comp, &dt); - - itt = cdate_to_icaltime (cdate); - icaltime_adjust (&itt, 1, 0, 0, 0); - dt.value = &itt; - dt.tzid = 0; - /* We have to add 1 day to DTEND, as it is not inclusive. */ - e_cal_component_set_dtend (cal_comp, &dt); - - /* Create yearly recurrence */ - icalrecurrencetype_clear (&r); - r.freq = ICAL_YEARLY_RECURRENCE; - r.interval = 1; - recur_list.data = &r; - recur_list.next = 0; - e_cal_component_set_rrule_list (cal_comp, &recur_list); - - /* Create summary */ - comp_summary.value = summary; - comp_summary.altrep = 0; - e_cal_component_set_summary (cal_comp, &comp_summary); - - /* Set category and visibility */ - e_cal_component_set_categories (cal_comp, _("Birthday")); - e_cal_component_set_classification (cal_comp, E_CAL_COMPONENT_CLASS_PRIVATE); - - /* Birthdays/anniversaries are shown as free time */ - e_cal_component_set_transparency (cal_comp, E_CAL_COMPONENT_TRANSP_TRANSPARENT); - - /* Don't forget to call commit()! */ - e_cal_component_commit_sequence (cal_comp); - - return cal_comp; -} - -static ECalComponent * -create_birthday (ECalBackendContacts *cbc, EContact *contact) -{ - EContactDate *cdate; - ECalComponent *cal_comp; - char *summary; - const char *name, *uid; - - cdate = e_contact_get (contact, E_CONTACT_BIRTH_DATE); - name = e_contact_get_const (contact, E_CONTACT_FILE_AS); - - uid = g_strdup_printf ("%s%s", (char *) e_contact_get (contact, E_CONTACT_UID), BIRTHDAY_UID_EXT); - summary = g_strdup_printf (_("Birthday: %s"), name); - - cal_comp = create_component (cbc, uid, cdate, summary); - - g_free (summary); - - return cal_comp; -} - -static ECalComponent * -create_anniversary (ECalBackendContacts *cbc, EContact *contact) -{ - EContactDate *cdate; - ECalComponent *cal_comp; - char *summary; - const char *name, *uid; - - cdate = e_contact_get (contact, E_CONTACT_ANNIVERSARY); - name = e_contact_get_const (contact, E_CONTACT_FILE_AS); - - uid = g_strdup_printf ("%s%s", (char *) e_contact_get (contact, E_CONTACT_UID), ANNIVERSARY_UID_EXT); - summary = g_strdup_printf (_("Anniversary: %s"), name); - - cal_comp = create_component (cbc, uid, cdate, summary); - - g_free (summary); - - return cal_comp; -} - -/************************************************************************************/ -/* Calendar backend method implementations */ - -/* First the empty stubs */ - -static ECalBackendSyncStatus -e_cal_backend_contacts_get_cal_address (ECalBackendSync *backend, EDataCal *cal, - char **address) -{ - /* A contact backend has no particular email address associated - * with it (although that would be a useful feature some day). - */ - *address = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_get_ldap_attribute (ECalBackendSync *backend, EDataCal *cal, - char **attribute) -{ - *attribute = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_get_alarm_email_address (ECalBackendSync *backend, EDataCal *cal, - char **address) -{ - /* A contact backend has no particular email address associated - * with it (although that would be a useful feature some day). - */ - *address = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_get_static_capabilities (ECalBackendSync *backend, EDataCal *cal, - char **capabilities) -{ - *capabilities = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_remove (ECalBackendSync *backend, EDataCal *cal) -{ - /* WRITE ME */ - return GNOME_Evolution_Calendar_PermissionDenied; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_get_default_object (ECalBackendSync *backend, EDataCal *cal, - char **object) -{ - return GNOME_Evolution_Calendar_UnsupportedMethod; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_get_object (ECalBackendSync *backend, EDataCal *cal, - const char *uid, const char *rid, - char **object) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (backend); - ECalBackendContactsPrivate *priv = cbc->priv; - ContactRecord *record; - char *real_uid; - - if (!uid) - return GNOME_Evolution_Calendar_ObjectNotFound; - else if (g_str_has_suffix (uid, ANNIVERSARY_UID_EXT)) - real_uid = g_strndup (uid, strlen (uid) - strlen (ANNIVERSARY_UID_EXT)); - else if (g_str_has_suffix (uid, BIRTHDAY_UID_EXT)) - real_uid = g_strndup (uid, strlen (uid) - strlen (BIRTHDAY_UID_EXT)); - else - return GNOME_Evolution_Calendar_ObjectNotFound; - - record = g_hash_table_lookup (priv->tracked_contacts, real_uid); - g_free (real_uid); - - if (!record) - return GNOME_Evolution_Calendar_ObjectNotFound; - - if (record->comp_birthday) { - *object = e_cal_component_get_as_string (record->comp_birthday); - - d(g_message ("Return birthday: %s", *object)); - return GNOME_Evolution_Calendar_Success; - } - - if (record->comp_anniversary) { - *object = e_cal_component_get_as_string (record->comp_anniversary); - - d(g_message ("Return anniversary: %s", *object)); - return GNOME_Evolution_Calendar_Success; - } - - d(g_message ("Returning nothing for uid: %s", uid)); - - return GNOME_Evolution_Calendar_ObjectNotFound; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_get_free_busy (ECalBackendSync *backend, EDataCal *cal, - GList *users, time_t start, time_t end, - GList **freebusy) -{ - /* Birthdays/anniversaries don't count as busy time */ - - icalcomponent *vfb = icalcomponent_new_vfreebusy (); - icaltimezone *utc_zone = icaltimezone_get_utc_timezone (); - char *calobj; - -#if 0 - icalproperty *prop; - icalparameter *param; - - prop = icalproperty_new_organizer (address); - if (prop != NULL && cn != NULL) { - param = icalparameter_new_cn (cn); - icalproperty_add_parameter (prop, param); - } - if (prop != NULL) - icalcomponent_add_property (vfb, prop); -#endif - - icalcomponent_set_dtstart (vfb, icaltime_from_timet_with_zone (start, FALSE, utc_zone)); - icalcomponent_set_dtend (vfb, icaltime_from_timet_with_zone (end, FALSE, utc_zone)); - - calobj = icalcomponent_as_ical_string (vfb); - *freebusy = g_list_append (NULL, g_strdup (calobj)); - icalcomponent_free (vfb); - - /* WRITE ME */ - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_get_changes (ECalBackendSync *backend, EDataCal *cal, - const char *change_id, - GList **adds, GList **modifies, GList **deletes) -{ - /* WRITE ME */ - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_discard_alarm (ECalBackendSync *backend, EDataCal *cal, - const char *uid, const char *auid) -{ - /* WRITE ME */ - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_receive_objects (ECalBackendSync *backend, EDataCal *cal, - const char *calobj) -{ - return GNOME_Evolution_Calendar_PermissionDenied; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_send_objects (ECalBackendSync *backend, EDataCal *cal, - const char *calobj, GList **users, char **modified_calobj) -{ - *users = NULL; - *modified_calobj = NULL; - /* TODO: Investigate this */ - return GNOME_Evolution_Calendar_PermissionDenied; -} - -/* Then the real implementations */ - -static CalMode -e_cal_backend_contacts_get_mode (ECalBackend *backend) -{ - return CAL_MODE_LOCAL; -} - -static void -e_cal_backend_contacts_set_mode (ECalBackend *backend, CalMode mode) -{ - e_cal_backend_notify_mode (backend, - GNOME_Evolution_Calendar_CalListener_MODE_NOT_SUPPORTED, - GNOME_Evolution_Calendar_MODE_LOCAL); - -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_is_read_only (ECalBackendSync *backend, EDataCal *cal, - gboolean *read_only) -{ - *read_only = TRUE; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_open (ECalBackendSync *backend, EDataCal *cal, - gboolean only_if_exists, - const char *username, const char *password) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (backend); - ECalBackendContactsPrivate *priv = cbc->priv; - - GSList *i; - - if (priv->addressbook_loaded) - return GNOME_Evolution_Calendar_Success; - - /* Create address books for existing sources */ - for (i = e_source_list_peek_groups (priv->addressbook_sources); i; i = i->next) - { - ESourceGroup *source_group = E_SOURCE_GROUP (i->data); - - source_group_added_cb (priv->addressbook_sources, source_group, cbc); - } - - /* Listen for source list changes */ - g_signal_connect (priv->addressbook_sources, "group_added", G_CALLBACK (source_group_added_cb), cbc); - g_signal_connect (priv->addressbook_sources, "group_removed", G_CALLBACK (source_group_removed_cb), cbc); - - priv->addressbook_loaded = TRUE; - return GNOME_Evolution_Calendar_Success; -} - -static gboolean -e_cal_backend_contacts_is_loaded (ECalBackend *backend) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (backend); - ECalBackendContactsPrivate *priv = cbc->priv; - - return priv->addressbook_loaded; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_get_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid, char **object) -{ - ECalBackendContacts *cbcontacts; - ECalBackendContactsPrivate *priv; - icaltimezone *zone; - icalcomponent *icalcomp; - - cbcontacts = E_CAL_BACKEND_CONTACTS (backend); - priv = cbcontacts->priv; - - g_return_val_if_fail (tzid != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - zone = e_cal_backend_internal_get_timezone (E_CAL_BACKEND (backend), tzid); - if (!zone) - return GNOME_Evolution_Calendar_ObjectNotFound; - - icalcomp = icaltimezone_get_component (zone); - if (!icalcomp) - return GNOME_Evolution_Calendar_InvalidObject; - - *object = g_strdup (icalcomponent_as_ical_string (icalcomp)); - - return GNOME_Evolution_Calendar_Success; -} - -/* Add_timezone handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_contacts_add_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzobj) -{ - ECalBackendContacts *cbcontacts; - ECalBackendContactsPrivate *priv; - icalcomponent *tz_comp; - icaltimezone *zone; - char *tzid; - - cbcontacts = (ECalBackendContacts *) backend; - - g_return_val_if_fail (E_IS_CAL_BACKEND_CONTACTS (cbcontacts), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (tzobj != NULL, GNOME_Evolution_Calendar_OtherError); - - priv = cbcontacts->priv; - - tz_comp = icalparser_parse_string (tzobj); - if (!tz_comp) - return GNOME_Evolution_Calendar_InvalidObject; - - if (icalcomponent_isa (tz_comp) != ICAL_VTIMEZONE_COMPONENT) - return GNOME_Evolution_Calendar_InvalidObject; - - zone = icaltimezone_new (); - icaltimezone_set_component (zone, tz_comp); - tzid = icaltimezone_get_tzid (zone); - - if (g_hash_table_lookup (priv->zones, tzid)) { - icaltimezone_free (zone, TRUE); - - return GNOME_Evolution_Calendar_Success; - } - - g_hash_table_insert (priv->zones, g_strdup (tzid), zone); - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_set_default_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid) -{ - ECalBackendContacts *cbcontacts; - ECalBackendContactsPrivate *priv; - - cbcontacts = E_CAL_BACKEND_CONTACTS (backend); - priv = cbcontacts->priv; - - priv->default_zone = e_cal_backend_internal_get_timezone (E_CAL_BACKEND (backend), tzid); - if (priv->default_zone) { - priv->default_zone = icaltimezone_get_utc_timezone (); - - return GNOME_Evolution_Calendar_ObjectNotFound; - } - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_contacts_get_object_list (ECalBackendSync *backend, EDataCal *cal, - const char *sexp_string, GList **objects) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (backend); - ECalBackendContactsPrivate *priv = cbc->priv; - ECalBackendSExp *sexp = e_cal_backend_sexp_new (sexp_string); - ContactRecordCB *cb_data; - - if (!sexp) - return GNOME_Evolution_Calendar_InvalidQuery; - - cb_data = contact_record_cb_new (cbc, sexp); - g_hash_table_foreach (priv->tracked_contacts, contact_record_cb, cb_data); - *objects = cb_data->result; - - /* Don't call cb_data_free as that would destroy the results - * in *objects */ - g_free (cb_data); - - return GNOME_Evolution_Calendar_Success; -} - -static void -e_cal_backend_contacts_start_query (ECalBackend *backend, EDataCalView *query) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (backend); - ECalBackendContactsPrivate *priv = cbc->priv; - ECalBackendSExp *sexp; - ContactRecordCB *cb_data; - - sexp = e_data_cal_view_get_object_sexp (query); - if (!sexp) { - e_data_cal_view_notify_done (query, GNOME_Evolution_Calendar_InvalidQuery); - return; - } - - cb_data = contact_record_cb_new (cbc, sexp); - - g_hash_table_foreach (priv->tracked_contacts, contact_record_cb, cb_data); - e_data_cal_view_notify_objects_added (query, cb_data->result); - - contact_record_cb_free (cb_data); - - e_data_cal_view_notify_done (query, GNOME_Evolution_Calendar_Success); -} - -static icaltimezone * -e_cal_backend_contacts_internal_get_default_timezone (ECalBackend *backend) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (backend); - - return cbc->priv->default_zone; -} - -static icaltimezone * -e_cal_backend_contacts_internal_get_timezone (ECalBackend *backend, const char *tzid) -{ - ECalBackendContacts *cbc = E_CAL_BACKEND_CONTACTS (backend); - - return cbc->priv->default_zone; -} - -/*********************************************************************************** - */ - -static void -free_zone (gpointer data) -{ - icaltimezone_free (data, TRUE); -} - -/* Finalize handler for the contacts backend */ -static void -e_cal_backend_contacts_finalize (GObject *object) -{ - ECalBackendContacts *cbc; - ECalBackendContactsPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL_BACKEND_CONTACTS (object)); - - cbc = E_CAL_BACKEND_CONTACTS (object); - priv = cbc->priv; - - g_hash_table_destroy (priv->tracked_contacts); - g_hash_table_destroy (priv->zones); - - g_free (priv); - cbc->priv = NULL; - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - -/* Object initialization function for the contacts backend */ -static void -e_cal_backend_contacts_init (ECalBackendContacts *cbc, ECalBackendContactsClass *class) -{ - ECalBackendContactsPrivate *priv; - - priv = g_new0 (ECalBackendContactsPrivate, 1); - - e_book_get_addressbooks (&priv->addressbook_sources, NULL); - - priv->addressbooks = g_hash_table_new_full (g_str_hash, g_str_equal, - g_free, (GDestroyNotify)book_record_free); - priv->tracked_contacts = g_hash_table_new_full (g_str_hash, g_str_equal, - g_free, (GDestroyNotify)contact_record_free); - - priv->zones = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, free_zone); - priv->default_zone = icaltimezone_get_utc_timezone (); - - cbc->priv = priv; -} - -/* Class initialization function for the contacts backend */ -static void -e_cal_backend_contacts_class_init (ECalBackendContactsClass *class) -{ - GObjectClass *object_class; - ECalBackendClass *backend_class; - ECalBackendSyncClass *sync_class; - - object_class = (GObjectClass *) class; - backend_class = (ECalBackendClass *) class; - sync_class = (ECalBackendSyncClass *) class; - - parent_class = (ECalBackendSyncClass *) g_type_class_peek_parent (class); - - object_class->finalize = e_cal_backend_contacts_finalize; - - sync_class->is_read_only_sync = e_cal_backend_contacts_is_read_only; - sync_class->get_cal_address_sync = e_cal_backend_contacts_get_cal_address; - sync_class->get_alarm_email_address_sync = e_cal_backend_contacts_get_alarm_email_address; - sync_class->get_ldap_attribute_sync = e_cal_backend_contacts_get_ldap_attribute; - sync_class->get_static_capabilities_sync = e_cal_backend_contacts_get_static_capabilities; - sync_class->open_sync = e_cal_backend_contacts_open; - sync_class->remove_sync = e_cal_backend_contacts_remove; - sync_class->discard_alarm_sync = e_cal_backend_contacts_discard_alarm; - sync_class->receive_objects_sync = e_cal_backend_contacts_receive_objects; - sync_class->send_objects_sync = e_cal_backend_contacts_send_objects; - sync_class->get_default_object_sync = e_cal_backend_contacts_get_default_object; - sync_class->get_object_sync = e_cal_backend_contacts_get_object; - sync_class->get_object_list_sync = e_cal_backend_contacts_get_object_list; - sync_class->get_timezone_sync = e_cal_backend_contacts_get_timezone; - sync_class->add_timezone_sync = e_cal_backend_contacts_add_timezone; - sync_class->set_default_timezone_sync = e_cal_backend_contacts_set_default_timezone; - sync_class->get_freebusy_sync = e_cal_backend_contacts_get_free_busy; - sync_class->get_changes_sync = e_cal_backend_contacts_get_changes; - backend_class->is_loaded = e_cal_backend_contacts_is_loaded; - backend_class->start_query = e_cal_backend_contacts_start_query; - backend_class->get_mode = e_cal_backend_contacts_get_mode; - backend_class->set_mode = e_cal_backend_contacts_set_mode; - - backend_class->internal_get_default_timezone = e_cal_backend_contacts_internal_get_default_timezone; - backend_class->internal_get_timezone = e_cal_backend_contacts_internal_get_timezone; -} - - -/** - * e_cal_backend_contacts_get_type: - * @void: - * - * Registers the #ECalBackendContacts class if necessary, and returns - * the type ID associated to it. - * - * Return value: The type ID of the #ECalBackendContacts class. - **/ -GType -e_cal_backend_contacts_get_type (void) -{ - static GType e_cal_backend_contacts_type = 0; - - if (!e_cal_backend_contacts_type) { - static GTypeInfo info = { - sizeof (ECalBackendContactsClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_backend_contacts_class_init, - NULL, NULL, - sizeof (ECalBackendContacts), - 0, - (GInstanceInitFunc) e_cal_backend_contacts_init - }; - e_cal_backend_contacts_type = g_type_register_static (E_TYPE_CAL_BACKEND_SYNC, - "ECalBackendContacts", &info, 0); - } - - return e_cal_backend_contacts_type; -} diff --git a/calendar/backends/contacts/e-cal-backend-contacts.h b/calendar/backends/contacts/e-cal-backend-contacts.h deleted file mode 100644 index 8d5092ed3..000000000 --- a/calendar/backends/contacts/e-cal-backend-contacts.h +++ /dev/null @@ -1,62 +0,0 @@ -/* Evolution calendar - iCalendar file backend - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2003 Gergõ Érdi - * - * Authors: Federico Mena-Quintero <federico@ximian.com>, - * Gergõ Érdi <cactus@cactus.rulez.org> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_BACKEND_CONTACTS_H -#define E_CAL_BACKEND_CONTACTS_H - -#include <libedata-cal/e-cal-backend-sync.h> - -G_BEGIN_DECLS - - - -#define E_TYPE_CAL_BACKEND_CONTACTS (e_cal_backend_contacts_get_type ()) -#define E_CAL_BACKEND_CONTACTS(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_BACKEND_CONTACTS, \ - ECalBackendContacts)) -#define E_CAL_BACKEND_CONTACTS_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_BACKEND_CONTACTS, \ - ECalBackendContactsClass)) -#define E_IS_CAL_BACKEND_CONTACTS(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_BACKEND_CONTACTS)) -#define E_IS_CAL_BACKEND_CONTACTS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_BACKEND_CONTACTS)) - -typedef struct _ECalBackendContacts ECalBackendContacts; -typedef struct _ECalBackendContactsClass ECalBackendContactsClass; - -typedef struct _ECalBackendContactsPrivate ECalBackendContactsPrivate; - -struct _ECalBackendContacts { - ECalBackendSync backend; - - /* Private data */ - ECalBackendContactsPrivate *priv; -}; - -struct _ECalBackendContactsClass { - ECalBackendSyncClass parent_class; -}; - -GType e_cal_backend_contacts_get_type (void); - - - -G_END_DECLS - -#endif diff --git a/calendar/backends/file/.cvsignore b/calendar/backends/file/.cvsignore deleted file mode 100644 index c038ed786..000000000 --- a/calendar/backends/file/.cvsignore +++ /dev/null @@ -1,2 +0,0 @@ -Makefile -Makefile.in
\ No newline at end of file diff --git a/calendar/backends/file/Makefile.am b/calendar/backends/file/Makefile.am deleted file mode 100644 index c5a767940..000000000 --- a/calendar/backends/file/Makefile.am +++ /dev/null @@ -1,25 +0,0 @@ -INCLUDES = \ - -DG_LOG_DOMAIN=\"libecalbackendfile\" \ - -I$(top_srcdir) \ - -I$(top_builddir) \ - -I$(top_srcdir)/calendar \ - -I$(top_builddir)/calendar \ - -I$(top_srcdir)/calendar/libical/src \ - -I$(top_builddir)/calendar/libical/src \ - -I$(top_srcdir)/calendar/libical/src/libical \ - -I$(top_builddir)/calendar/libical/src/libical \ - $(EVOLUTION_CALENDAR_CFLAGS) - -noinst_LTLIBRARIES = libecalbackendfile.la - -libecalbackendfile_la_SOURCES = \ - e-cal-backend-file-events.c\ - e-cal-backend-file-events.h\ - e-cal-backend-file-todos.c\ - e-cal-backend-file-todos.h\ - e-cal-backend-file.c \ - e-cal-backend-file.h - -libecalbackendfile_la_LIBADD = \ - $(top_builddir)/calendar/libedata-cal/libedata-cal.la - diff --git a/calendar/backends/file/e-cal-backend-file-events.c b/calendar/backends/file/e-cal-backend-file-events.c deleted file mode 100644 index 73c3aee13..000000000 --- a/calendar/backends/file/e-cal-backend-file-events.c +++ /dev/null @@ -1,138 +0,0 @@ -/* Evolution calendar - iCalendar file backend - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Authors: Federico Mena-Quintero <federico@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include "e-cal-backend-file-events.h" - - - -/* Private part of the CalBackendFileEvents structure */ -struct _ECalBackendFileEventsPrivate { -}; - - - -static void e_cal_backend_file_events_class_init (ECalBackendFileEventsClass *class); -static void e_cal_backend_file_events_init (ECalBackendFileEvents *cbfile, ECalBackendFileEventsClass *class); -static void e_cal_backend_file_events_dispose (GObject *object); -static void e_cal_backend_file_events_finalize (GObject *object); - -static GObjectClass *parent_class; - - - -/** - * e_cal_backend_file_events_get_type: - * @void: - * - * Registers the #ECalBackendFileEvents class if necessary, and returns the type ID - * associated to it. - * - * Return value: The type ID of the #ECalBackendFileEvents class. - **/ -GType -e_cal_backend_file_events_get_type (void) -{ - static GType e_cal_backend_file_events_type = 0; - - if (!e_cal_backend_file_events_type) { - static GTypeInfo info = { - sizeof (ECalBackendFileEventsClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_backend_file_events_class_init, - NULL, NULL, - sizeof (ECalBackendFileEvents), - 0, - (GInstanceInitFunc) e_cal_backend_file_events_init - }; - e_cal_backend_file_events_type = g_type_register_static (E_TYPE_CAL_BACKEND_FILE, - "ECalBackendFileEvents", &info, 0); - } - - return e_cal_backend_file_events_type; -} - -/* Class initialization function for the file backend */ -static void -e_cal_backend_file_events_class_init (ECalBackendFileEventsClass *klass) -{ - GObjectClass *object_class; - ECalBackendClass *backend_class; - - object_class = G_OBJECT_CLASS (klass); - backend_class = E_CAL_BACKEND_CLASS (klass); - - parent_class = g_type_class_peek_parent (klass); - - object_class->dispose = e_cal_backend_file_events_dispose; - object_class->finalize = e_cal_backend_file_events_finalize; - -// backend_class->get_uri = e_cal_backend_file_events_get_uri; -} - -/* Object initialization function for the file backend */ -static void -e_cal_backend_file_events_init (ECalBackendFileEvents *cbfile, ECalBackendFileEventsClass *class) -{ - ECalBackendFileEventsPrivate *priv; - - priv = g_new0 (ECalBackendFileEventsPrivate, 1); - cbfile->priv = priv; - - e_cal_backend_file_set_file_name (E_CAL_BACKEND_FILE (cbfile), "calendar.ics"); -} - -/* Dispose handler for the file backend */ -static void -e_cal_backend_file_events_dispose (GObject *object) -{ - ECalBackendFileEvents *cbfile; - ECalBackendFileEventsPrivate *priv; - - cbfile = E_CAL_BACKEND_FILE_EVENTS (object); - priv = cbfile->priv; - - if (G_OBJECT_CLASS (parent_class)->dispose) - (* G_OBJECT_CLASS (parent_class)->dispose) (object); -} - -/* Finalize handler for the file backend */ -static void -e_cal_backend_file_events_finalize (GObject *object) -{ - ECalBackendFileEvents *cbfile; - ECalBackendFileEventsPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL_BACKEND_FILE_EVENTS (object)); - - cbfile = E_CAL_BACKEND_FILE_EVENTS (object); - priv = cbfile->priv; - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - diff --git a/calendar/backends/file/e-cal-backend-file-events.h b/calendar/backends/file/e-cal-backend-file-events.h deleted file mode 100644 index 58aff4019..000000000 --- a/calendar/backends/file/e-cal-backend-file-events.h +++ /dev/null @@ -1,61 +0,0 @@ -/* Evolution calendar - iCalendar file backend - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_BACKEND_FILE_EVENTS_H -#define E_CAL_BACKEND_FILE_EVENTS_H - -#include "e-cal-backend-file.h" - -G_BEGIN_DECLS - - - -#define E_TYPE_CAL_BACKEND_FILE_EVENTS (e_cal_backend_file_events_get_type ()) -#define E_CAL_BACKEND_FILE_EVENTS(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_BACKEND_FILE_EVENTS, \ - ECalBackendFileEvents)) -#define E_CAL_BACKEND_FILE_EVENTS_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_BACKEND_FILE_EVENTS, \ - ECalBackendFileEventsClass)) -#define E_IS_CAL_BACKEND_FILE_EVENTS(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_BACKEND_FILE_EVENTS)) -#define E_IS_CAL_BACKEND_FILE_EVENTS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_BACKEND_FILE_EVENTS)) - -typedef struct _ECalBackendFileEvents ECalBackendFileEvents; -typedef struct _ECalBackendFileEventsClass ECalBackendFileEventsClass; - -typedef struct _ECalBackendFileEventsPrivate ECalBackendFileEventsPrivate; - -struct _ECalBackendFileEvents { - ECalBackendFile backend; - - /* Private data */ - ECalBackendFileEventsPrivate *priv; -}; - -struct _ECalBackendFileEventsClass { - ECalBackendFileClass parent_class; -}; - -GType e_cal_backend_file_events_get_type (void); - - - -G_END_DECLS - -#endif diff --git a/calendar/backends/file/e-cal-backend-file-todos.c b/calendar/backends/file/e-cal-backend-file-todos.c deleted file mode 100644 index 89ce4f3f1..000000000 --- a/calendar/backends/file/e-cal-backend-file-todos.c +++ /dev/null @@ -1,134 +0,0 @@ -/* Evolution calendar - iCalendar file backend for tasks - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Authors: Federico Mena-Quintero <federico@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#include "e-cal-backend-file-todos.h" - - - -/* Private part of the ECalBackendFileTodos structure */ -struct _ECalBackendFileTodosPrivate { -}; - - - -static void e_cal_backend_file_todos_class_init (ECalBackendFileTodosClass *class); -static void e_cal_backend_file_todos_init (ECalBackendFileTodos *cbfile, ECalBackendFileTodosClass *class); -static void e_cal_backend_file_todos_dispose (GObject *object); -static void e_cal_backend_file_todos_finalize (GObject *object); - -static ECalBackendFileClass *parent_class; - - - -/** - * e_cal_backend_file_todos_get_type: - * @void: - * - * Registers the #ECalBackendFileTodos class if necessary, and returns the type ID - * associated to it. - * - * Return value: The type ID of the #ECalBackendFileTodos class. - **/ -GType -e_cal_backend_file_todos_get_type (void) -{ - static GType e_cal_backend_file_todos_type = 0; - - if (!e_cal_backend_file_todos_type) { - static GTypeInfo info = { - sizeof (ECalBackendFileTodosClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_backend_file_todos_class_init, - NULL, NULL, - sizeof (ECalBackendFileTodos), - 0, - (GInstanceInitFunc) e_cal_backend_file_todos_init - }; - e_cal_backend_file_todos_type = g_type_register_static (E_TYPE_CAL_BACKEND_FILE, - "ECalBackendFileTodos", &info, 0); - } - - return e_cal_backend_file_todos_type; -} - -/* Class initialization function for the file backend */ -static void -e_cal_backend_file_todos_class_init (ECalBackendFileTodosClass *klass) -{ - GObjectClass *object_class; - ECalBackendClass *backend_class; - - object_class = G_OBJECT_CLASS (klass); - backend_class = E_CAL_BACKEND_CLASS (klass); - - parent_class = g_type_class_peek_parent (klass); - - object_class->dispose = e_cal_backend_file_todos_dispose; - object_class->finalize = e_cal_backend_file_todos_finalize; - -// backend_class->get_uri = e_cal_backend_file_todos_get_uri; -} - -/* Object initialization function for the file backend */ -static void -e_cal_backend_file_todos_init (ECalBackendFileTodos *cbfile, ECalBackendFileTodosClass *class) -{ - ECalBackendFileTodosPrivate *priv; - - priv = g_new0 (ECalBackendFileTodosPrivate, 1); - cbfile->priv = priv; - - e_cal_backend_file_set_file_name (E_CAL_BACKEND_FILE (cbfile), "tasks.ics"); -} - -/* Dispose handler for the file backend */ -static void -e_cal_backend_file_todos_dispose (GObject *object) -{ - ECalBackendFileTodos *cbfile; - ECalBackendFileTodosPrivate *priv; - - cbfile = E_CAL_BACKEND_FILE_TODOS (object); - priv = cbfile->priv; - - if (G_OBJECT_CLASS (parent_class)->dispose) - (* G_OBJECT_CLASS (parent_class)->dispose) (object); -} - -/* Finalize handler for the file backend */ -static void -e_cal_backend_file_todos_finalize (GObject *object) -{ - ECalBackendFileTodos *cbfile; - ECalBackendFileTodosPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL_BACKEND_FILE_TODOS (object)); - - cbfile = E_CAL_BACKEND_FILE_TODOS (object); - priv = cbfile->priv; - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - diff --git a/calendar/backends/file/e-cal-backend-file-todos.h b/calendar/backends/file/e-cal-backend-file-todos.h deleted file mode 100644 index a4171d141..000000000 --- a/calendar/backends/file/e-cal-backend-file-todos.h +++ /dev/null @@ -1,61 +0,0 @@ -/* Evolution calendar - iCalendar file backend - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_BACKEND_FILE_TODOS_H -#define E_CAL_BACKEND_FILE_TODOS_H - -#include "e-cal-backend-file.h" - -G_BEGIN_DECLS - - - -#define E_TYPE_CAL_BACKEND_FILE_TODOS (e_cal_backend_file_todos_get_type ()) -#define E_CAL_BACKEND_FILE_TODOS(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_BACKEND_FILE_TODOS, \ - ECalBackendFileTodos)) -#define E_CAL_BACKEND_FILE_TODOS_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_BACKEND_FILE_TODOS, \ - ECalBackendFileTodosClass)) -#define E_IS_CAL_BACKEND_FILE_TODOS(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_BACKEND_FILE_TODOS)) -#define E_IS_CAL_BACKEND_FILE_TODOS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_BACKEND_FILE_TODOS)) - -typedef struct _ECalBackendFileTodos ECalBackendFileTodos; -typedef struct _ECalBackendFileTodosClass ECalBackendFileTodosClass; - -typedef struct _ECalBackendFileTodosPrivate ECalBackendFileTodosPrivate; - -struct _ECalBackendFileTodos { - ECalBackendFile backend; - - /* Private data */ - ECalBackendFileTodosPrivate *priv; -}; - -struct _ECalBackendFileTodosClass { - ECalBackendFileClass parent_class; -}; - -GType e_cal_backend_file_todos_get_type (void); - - - -G_END_DECLS - -#endif diff --git a/calendar/backends/file/e-cal-backend-file.c b/calendar/backends/file/e-cal-backend-file.c deleted file mode 100644 index f7408cd05..000000000 --- a/calendar/backends/file/e-cal-backend-file.c +++ /dev/null @@ -1,2364 +0,0 @@ -/* Evolution calendar - iCalendar file backend - * - * Copyright (C) 2000-2003 Ximian, Inc. - * - * Authors: Federico Mena-Quintero <federico@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <string.h> -#include <unistd.h> -#include <bonobo/bonobo-exception.h> -#include <bonobo/bonobo-moniker-util.h> -#include <libgnome/gnome-i18n.h> -#include <libgnomevfs/gnome-vfs.h> -#include <libedataserver/e-util.h> -#include <libedataserver/e-xml-hash-utils.h> -#include <libecal/e-cal-recur.h> -#include <libecal/e-cal-time-util.h> -#include <libecal/e-cal-util.h> -#include <libedata-cal/e-cal-backend-util.h> -#include <libedata-cal/e-cal-backend-sexp.h> -#include "e-cal-backend-file-events.h" - - - -/* Placeholder for each component and its recurrences */ -typedef struct { - ECalComponent *full_object; - GHashTable *recurrences; - GList *recurrences_list; -} ECalBackendFileObject; - -/* Private part of the ECalBackendFile structure */ -struct _ECalBackendFilePrivate { - /* URI where the calendar data is stored */ - char *uri; - - /* Filename in the dir */ - char *file_name; - gboolean read_only; - - /* Toplevel VCALENDAR component */ - icalcomponent *icalcomp; - - /* All the objects in the calendar, hashed by UID. The - * hash key *is* the uid returned by cal_component_get_uid(); it is not - * copied, so don't free it when you remove an object from the hash - * table. Each item in the hash table is a ECalBackendFileObject. - */ - GHashTable *comp_uid_hash; - - GList *comp; - - /* The calendar's default timezone, used for resolving DATE and - floating DATE-TIME values. */ - icaltimezone *default_zone; - - /* The list of live queries */ - GList *queries; -}; - - - -#define d(x) - -static void e_cal_backend_file_dispose (GObject *object); -static void e_cal_backend_file_finalize (GObject *object); - -static ECalBackendSyncClass *parent_class; - - - -/* g_hash_table_foreach() callback to destroy recurrences in the hash table */ -static void -free_recurrence (gpointer key, gpointer value, gpointer data) -{ - char *rid = key; - ECalComponent *comp = value; - - g_free (rid); - g_object_unref (comp); -} - -/* g_hash_table_foreach() callback to destroy a ECalBackendFileObject */ -static void -free_object (gpointer key, gpointer value, gpointer data) -{ - ECalBackendFileObject *obj_data = value; - - g_object_unref (obj_data->full_object); - g_hash_table_foreach (obj_data->recurrences, (GHFunc) free_recurrence, NULL); - g_hash_table_destroy (obj_data->recurrences); - g_list_free (obj_data->recurrences_list); - - g_free (obj_data); -} - -/* Saves the calendar data */ -static void -save (ECalBackendFile *cbfile) -{ - ECalBackendFilePrivate *priv; - GnomeVFSURI *uri, *backup_uri; - GnomeVFSHandle *handle = NULL; - GnomeVFSResult result = GNOME_VFS_ERROR_BAD_FILE; - GnomeVFSFileSize out; - gchar *tmp, *backup_uristr; - char *buf; - - priv = cbfile->priv; - g_assert (priv->uri != NULL); - g_assert (priv->icalcomp != NULL); - - uri = gnome_vfs_uri_new (priv->uri); - if (!uri) - goto error_malformed_uri; - - /* save calendar to backup file */ - tmp = gnome_vfs_uri_to_string (uri, GNOME_VFS_URI_HIDE_NONE); - if (!tmp) { - gnome_vfs_uri_unref (uri); - goto error_malformed_uri; - } - - backup_uristr = g_strconcat (tmp, "~", NULL); - backup_uri = gnome_vfs_uri_new (backup_uristr); - - g_free (tmp); - g_free (backup_uristr); - - if (!backup_uri) { - gnome_vfs_uri_unref (uri); - goto error_malformed_uri; - } - - result = gnome_vfs_create_uri (&handle, backup_uri, - GNOME_VFS_OPEN_WRITE, - FALSE, 0666); - if (result != GNOME_VFS_OK) { - gnome_vfs_uri_unref (uri); - gnome_vfs_uri_unref (backup_uri); - goto error; - } - - buf = icalcomponent_as_ical_string (priv->icalcomp); - result = gnome_vfs_write (handle, buf, strlen (buf) * sizeof (char), &out); - gnome_vfs_close (handle); - if (result != GNOME_VFS_OK) { - gnome_vfs_uri_unref (uri); - gnome_vfs_uri_unref (backup_uri); - goto error; - } - - /* now copy the temporary file to the real file */ - result = gnome_vfs_move_uri (backup_uri, uri, TRUE); - - gnome_vfs_uri_unref (uri); - gnome_vfs_uri_unref (backup_uri); - if (result != GNOME_VFS_OK) - goto error; - - return; - - error_malformed_uri: - e_cal_backend_notify_error (E_CAL_BACKEND (cbfile), - _("Can't save calendar data: Malformed URI.")); - return; - - error: - e_cal_backend_notify_error (E_CAL_BACKEND (cbfile), gnome_vfs_result_to_string (result)); - return; -} - -static void -free_calendar_components (GHashTable *comp_uid_hash, icalcomponent *top_icomp) -{ - if (comp_uid_hash) { - g_hash_table_foreach (comp_uid_hash, (GHFunc) free_object, NULL); - g_hash_table_destroy (comp_uid_hash); - } - - if (top_icomp) { - icalcomponent_free (top_icomp); - } -} - -static void -free_calendar_data (ECalBackendFile *cbfile) -{ - ECalBackendFilePrivate *priv; - - priv = cbfile->priv; - - free_calendar_components (priv->comp_uid_hash, priv->icalcomp); - priv->comp_uid_hash = NULL; - priv->icalcomp = NULL; - - g_list_free (priv->comp); - priv->comp = NULL; -} - -/* Dispose handler for the file backend */ -static void -e_cal_backend_file_dispose (GObject *object) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - - cbfile = E_CAL_BACKEND_FILE (object); - priv = cbfile->priv; - - /* Save if necessary */ - - free_calendar_data (cbfile); - - if (G_OBJECT_CLASS (parent_class)->dispose) - (* G_OBJECT_CLASS (parent_class)->dispose) (object); -} - -/* Finalize handler for the file backend */ -static void -e_cal_backend_file_finalize (GObject *object) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL_BACKEND_FILE (object)); - - cbfile = E_CAL_BACKEND_FILE (object); - priv = cbfile->priv; - - /* Clean up */ - - if (priv->uri) { - g_free (priv->uri); - priv->uri = NULL; - } - - g_free (priv); - cbfile->priv = NULL; - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - - - -/* Looks up a component by its UID on the backend's component hash table */ -static ECalComponent * -lookup_component (ECalBackendFile *cbfile, const char *uid) -{ - ECalBackendFilePrivate *priv; - ECalBackendFileObject *obj_data; - - priv = cbfile->priv; - - obj_data = g_hash_table_lookup (priv->comp_uid_hash, uid); - return obj_data ? obj_data->full_object : NULL; -} - - - -/* Calendar backend methods */ - -/* Is_read_only handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_is_read_only (ECalBackendSync *backend, EDataCal *cal, gboolean *read_only) -{ - ECalBackendFile *cbfile = (ECalBackendFile *) backend; - - *read_only = cbfile->priv->read_only; - - return GNOME_Evolution_Calendar_Success; -} - -/* Get_email_address handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_get_cal_address (ECalBackendSync *backend, EDataCal *cal, char **address) -{ - /* A file backend has no particular email address associated - * with it (although that would be a useful feature some day). - */ - *address = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_file_get_ldap_attribute (ECalBackendSync *backend, EDataCal *cal, char **attribute) -{ - *attribute = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_file_get_alarm_email_address (ECalBackendSync *backend, EDataCal *cal, char **address) -{ - /* A file backend has no particular email address associated - * with it (although that would be a useful feature some day). - */ - *address = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_file_get_static_capabilities (ECalBackendSync *backend, EDataCal *cal, char **capabilities) -{ - *capabilities = g_strdup (CAL_STATIC_CAPABILITY_NO_EMAIL_ALARMS); - - return GNOME_Evolution_Calendar_Success; -} - -/* function to resolve timezones */ -static icaltimezone * -resolve_tzid (const char *tzid, gpointer user_data) -{ - icalcomponent *vcalendar_comp = user_data; - - if (!tzid || !tzid[0]) - return NULL; - else if (!strcmp (tzid, "UTC")) - return icaltimezone_get_utc_timezone (); - - return icalcomponent_get_timezone (vcalendar_comp, tzid); -} - -/* Checks if the specified component has a duplicated UID and if so changes it */ -static void -check_dup_uid (ECalBackendFile *cbfile, ECalComponent *comp) -{ - ECalBackendFilePrivate *priv; - ECalBackendFileObject *obj_data; - const char *uid; - char *new_uid; - - priv = cbfile->priv; - - e_cal_component_get_uid (comp, &uid); - - obj_data = g_hash_table_lookup (priv->comp_uid_hash, uid); - if (!obj_data) - return; /* Everything is fine */ - - d(g_message (G_STRLOC ": Got object with duplicated UID `%s', changing it...", uid)); - - new_uid = e_cal_component_gen_uid (); - e_cal_component_set_uid (comp, new_uid); - g_free (new_uid); - - /* FIXME: I think we need to reset the SEQUENCE property and reset the - * CREATED/DTSTAMP/LAST-MODIFIED. - */ - - save (cbfile); -} - -static struct icaltimetype -get_rid_icaltime (ECalComponent *comp) -{ - ECalComponentRange range; - struct icaltimetype tt; - - e_cal_component_get_recurid (comp, &range); - if (!range.datetime.value) - return icaltime_null_time (); - tt = *range.datetime.value; - e_cal_component_free_range (&range); - - return tt; -} - -/* Tries to add an icalcomponent to the file backend. We only store the objects - * of the types we support; all others just remain in the toplevel component so - * that we don't lose them. - */ -static void -add_component (ECalBackendFile *cbfile, ECalComponent *comp, gboolean add_to_toplevel) -{ - ECalBackendFilePrivate *priv; - ECalBackendFileObject *obj_data; - const char *uid; - GSList *categories; - - priv = cbfile->priv; - - e_cal_component_get_uid (comp, &uid); - obj_data = g_hash_table_lookup (priv->comp_uid_hash, uid); - if (e_cal_component_is_instance (comp)) { - const char *rid; - - rid = e_cal_component_get_recurid_as_string (comp); - if (obj_data) { - if (g_hash_table_lookup (obj_data->recurrences, rid)) { - g_warning (G_STRLOC ": Tried to add an already existing recurrence"); - return; - } - } else { - obj_data = g_new0 (ECalBackendFileObject, 1); - obj_data->full_object = NULL; - obj_data->recurrences = g_hash_table_new (g_str_hash, g_str_equal); - g_hash_table_insert (priv->comp_uid_hash, (gpointer) uid, obj_data); - } - - g_hash_table_insert (obj_data->recurrences, g_strdup (rid), comp); - obj_data->recurrences_list = g_list_append (obj_data->recurrences_list, comp); - } else { - /* Ensure that the UID is unique; some broken implementations spit - * components with duplicated UIDs. - */ - check_dup_uid (cbfile, comp); - - if (obj_data) { - if (obj_data->full_object) { - g_warning (G_STRLOC ": Tried to add an already existing object"); - return; - } - - obj_data->full_object = comp; - } else { - obj_data = g_new0 (ECalBackendFileObject, 1); - obj_data->full_object = comp; - obj_data->recurrences = g_hash_table_new (g_str_hash, g_str_equal); - - g_hash_table_insert (priv->comp_uid_hash, (gpointer) uid, obj_data); - } - } - - priv->comp = g_list_prepend (priv->comp, comp); - - /* Put the object in the toplevel component if required */ - - if (add_to_toplevel) { - icalcomponent *icalcomp; - - icalcomp = e_cal_component_get_icalcomponent (comp); - g_assert (icalcomp != NULL); - - icalcomponent_add_component (priv->icalcomp, icalcomp); - } - - /* Update the set of categories */ - e_cal_component_get_categories_list (comp, &categories); - e_cal_backend_ref_categories (E_CAL_BACKEND (cbfile), categories); - e_cal_component_free_categories_list (categories); -} - -/* g_hash_table_foreach() callback to remove recurrences from the calendar */ -static void -remove_recurrence_cb (gpointer key, gpointer value, gpointer data) -{ - GList *l; - GSList *categories; - icalcomponent *icalcomp; - ECalBackendFilePrivate *priv; - ECalComponent *comp = value; - ECalBackendFile *cbfile = data; - - priv = cbfile->priv; - - /* remove the recurrence from the top-level calendar */ - icalcomp = e_cal_component_get_icalcomponent (comp); - g_assert (icalcomp != NULL); - - icalcomponent_remove_component (priv->icalcomp, icalcomp); - - /* remove it from our mapping */ - l = g_list_find (priv->comp, comp); - priv->comp = g_list_delete_link (priv->comp, l); - - /* update the set of categories */ - e_cal_component_get_categories_list (comp, &categories); - e_cal_backend_unref_categories (E_CAL_BACKEND (cbfile), categories); - e_cal_component_free_categories_list (categories); -} - -/* Removes a component from the backend's hash and lists. Does not perform - * notification on the clients. Also removes the component from the toplevel - * icalcomponent. - */ -static void -remove_component (ECalBackendFile *cbfile, ECalComponent *comp) -{ - ECalBackendFilePrivate *priv; - icalcomponent *icalcomp; - const char *uid; - GList *l; - GSList *categories; - ECalBackendFileObject *obj_data; - - priv = cbfile->priv; - - /* Remove the icalcomp from the toplevel */ - - icalcomp = e_cal_component_get_icalcomponent (comp); - g_assert (icalcomp != NULL); - - icalcomponent_remove_component (priv->icalcomp, icalcomp); - - /* Remove it from our mapping */ - - e_cal_component_get_uid (comp, &uid); - obj_data = g_hash_table_lookup (priv->comp_uid_hash, uid); - if (!obj_data) - return; - - g_hash_table_remove (priv->comp_uid_hash, uid); - - l = g_list_find (priv->comp, comp); - g_assert (l != NULL); - priv->comp = g_list_delete_link (priv->comp, l); - - /* remove the recurrences also */ - g_hash_table_foreach (obj_data->recurrences, (GHFunc) remove_recurrence_cb, cbfile); - - /* Update the set of categories */ - e_cal_component_get_categories_list (comp, &categories); - e_cal_backend_unref_categories (E_CAL_BACKEND (cbfile), categories); - e_cal_component_free_categories_list (categories); - - free_object ((gpointer) uid, (gpointer) obj_data, NULL); -} - -/* Scans the toplevel VCALENDAR component and stores the objects it finds */ -static void -scan_vcalendar (ECalBackendFile *cbfile) -{ - ECalBackendFilePrivate *priv; - icalcompiter iter; - - priv = cbfile->priv; - g_assert (priv->icalcomp != NULL); - g_assert (priv->comp_uid_hash != NULL); - - for (iter = icalcomponent_begin_component (priv->icalcomp, ICAL_ANY_COMPONENT); - icalcompiter_deref (&iter) != NULL; - icalcompiter_next (&iter)) { - icalcomponent *icalcomp; - icalcomponent_kind kind; - ECalComponent *comp; - - icalcomp = icalcompiter_deref (&iter); - - kind = icalcomponent_isa (icalcomp); - - if (!(kind == ICAL_VEVENT_COMPONENT - || kind == ICAL_VTODO_COMPONENT - || kind == ICAL_VJOURNAL_COMPONENT)) - continue; - - comp = e_cal_component_new (); - - if (!e_cal_component_set_icalcomponent (comp, icalcomp)) - continue; - - add_component (cbfile, comp, FALSE); - } -} - -static char * -get_uri_string_for_gnome_vfs (ECalBackend *backend) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - const char *master_uri; - char *full_uri, *str_uri; - GnomeVFSURI *uri; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - master_uri = e_cal_backend_get_uri (backend); - - /* FIXME Check the error conditions a little more elegantly here */ - if (g_strrstr ("tasks.ics", master_uri) || g_strrstr ("calendar.ics", master_uri)) { - g_warning (G_STRLOC ": Existing file name %s", master_uri); - - return NULL; - } - - full_uri = g_strdup_printf ("%s%s%s", master_uri, G_DIR_SEPARATOR_S, priv->file_name); - uri = gnome_vfs_uri_new (full_uri); - g_free (full_uri); - - if (!uri) - return NULL; - - str_uri = gnome_vfs_uri_to_string (uri, - (GNOME_VFS_URI_HIDE_USER_NAME - | GNOME_VFS_URI_HIDE_PASSWORD - | GNOME_VFS_URI_HIDE_HOST_NAME - | GNOME_VFS_URI_HIDE_HOST_PORT - | GNOME_VFS_URI_HIDE_TOPLEVEL_METHOD)); - gnome_vfs_uri_unref (uri); - - if (!str_uri || !strlen (str_uri)) { - g_free (str_uri); - - return NULL; - } - - return str_uri; -} - -/* Parses an open iCalendar file and loads it into the backend */ -static ECalBackendSyncStatus -open_cal (ECalBackendFile *cbfile, const char *uristr) -{ - ECalBackendFilePrivate *priv; - icalcomponent *icalcomp; - - priv = cbfile->priv; - - icalcomp = e_cal_util_parse_ics_file (uristr); - if (!icalcomp) - return GNOME_Evolution_Calendar_OtherError; - - /* FIXME: should we try to demangle XROOT components and - * individual components as well? - */ - - if (icalcomponent_isa (icalcomp) != ICAL_VCALENDAR_COMPONENT) { - icalcomponent_free (icalcomp); - - return GNOME_Evolution_Calendar_OtherError; - } - - priv->icalcomp = icalcomp; - priv->uri = get_uri_string_for_gnome_vfs (E_CAL_BACKEND (cbfile)); - - priv->comp_uid_hash = g_hash_table_new (g_str_hash, g_str_equal); - scan_vcalendar (cbfile); - - return GNOME_Evolution_Calendar_Success; -} - -typedef struct -{ - ECalBackend *backend; - GHashTable *old_uid_hash; - GHashTable *new_uid_hash; -} -BackendDeltaContext; - -static void -notify_removals_cb (gpointer key, gpointer value, gpointer data) -{ - BackendDeltaContext *context = data; - const gchar *uid = key; - ECalBackendFileObject *old_obj_data = value; - - if (!g_hash_table_lookup (context->new_uid_hash, uid)) { - icalcomponent *old_icomp; - gchar *old_obj_str; - - /* Object was removed */ - - old_icomp = e_cal_component_get_icalcomponent (old_obj_data->full_object); - if (!old_icomp) - return; - - old_obj_str = icalcomponent_as_ical_string (old_icomp); - if (!old_obj_str) - return; - - e_cal_backend_notify_object_removed (context->backend, uid, old_obj_str); - } -} - -static void -notify_adds_modifies_cb (gpointer key, gpointer value, gpointer data) -{ - BackendDeltaContext *context = data; - const gchar *uid = key; - ECalBackendFileObject *new_obj_data = value; - ECalBackendFileObject *old_obj_data; - icalcomponent *old_icomp, *new_icomp; - gchar *old_obj_str, *new_obj_str; - - old_obj_data = g_hash_table_lookup (context->old_uid_hash, uid); - - if (!old_obj_data) { - /* Object was added */ - - new_icomp = e_cal_component_get_icalcomponent (new_obj_data->full_object); - if (!new_icomp) - return; - - new_obj_str = icalcomponent_as_ical_string (new_icomp); - if (!new_obj_str) - return; - - e_cal_backend_notify_object_created (context->backend, new_obj_str); - } else { - old_icomp = e_cal_component_get_icalcomponent (old_obj_data->full_object); - new_icomp = e_cal_component_get_icalcomponent (new_obj_data->full_object); - if (!old_icomp || !new_icomp) - return; - - old_obj_str = icalcomponent_as_ical_string (old_icomp); - new_obj_str = icalcomponent_as_ical_string (new_icomp); - if (!old_obj_str || !new_obj_str) - return; - - if (strcmp (old_obj_str, new_obj_str)) { - /* Object was modified */ - - e_cal_backend_notify_object_modified (context->backend, old_obj_str, new_obj_str); - } - } -} - -static void -notify_changes (ECalBackendFile *cbfile, GHashTable *old_uid_hash, GHashTable *new_uid_hash) -{ - BackendDeltaContext context; - - context.backend = E_CAL_BACKEND (cbfile); - context.old_uid_hash = old_uid_hash; - context.new_uid_hash = new_uid_hash; - - g_hash_table_foreach (old_uid_hash, (GHFunc) notify_removals_cb, &context); - g_hash_table_foreach (new_uid_hash, (GHFunc) notify_adds_modifies_cb, &context); -} - -static ECalBackendSyncStatus -reload_cal (ECalBackendFile *cbfile, const char *uristr) -{ - ECalBackendFilePrivate *priv; - icalcomponent *icalcomp, *icalcomp_old; - GHashTable *comp_uid_hash_old; - - priv = cbfile->priv; - - icalcomp = e_cal_util_parse_ics_file (uristr); - if (!icalcomp) - return GNOME_Evolution_Calendar_OtherError; - - /* FIXME: should we try to demangle XROOT components and - * individual components as well? - */ - - if (icalcomponent_isa (icalcomp) != ICAL_VCALENDAR_COMPONENT) { - icalcomponent_free (icalcomp); - - return GNOME_Evolution_Calendar_OtherError; - } - - /* Keep old data for comparison - free later */ - - icalcomp_old = priv->icalcomp; - priv->icalcomp = NULL; - - comp_uid_hash_old = priv->comp_uid_hash; - priv->comp_uid_hash = NULL; - - /* Load new calendar */ - - free_calendar_data (cbfile); - - priv->icalcomp = icalcomp; - - priv->comp_uid_hash = g_hash_table_new (g_str_hash, g_str_equal); - scan_vcalendar (cbfile); - - priv->uri = get_uri_string_for_gnome_vfs (E_CAL_BACKEND (cbfile)); - - /* Compare old and new versions of calendar */ - - notify_changes (cbfile, comp_uid_hash_old, priv->comp_uid_hash); - - /* Free old data */ - - free_calendar_components (comp_uid_hash_old, icalcomp_old); - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -create_cal (ECalBackendFile *cbfile, const char *uristr) -{ - char *dirname; - ECalBackendFilePrivate *priv; - - priv = cbfile->priv; - - /* Create the directory to contain the file */ - dirname = g_path_get_dirname (uristr); - if (e_util_mkdir_hier (dirname, 0700) != 0) { - g_free (dirname); - return GNOME_Evolution_Calendar_NoSuchCal; - } - - g_free (dirname); - - /* Create the new calendar information */ - priv->icalcomp = e_cal_util_new_top_level (); - - /* Create our internal data */ - priv->comp_uid_hash = g_hash_table_new (g_str_hash, g_str_equal); - - priv->uri = get_uri_string_for_gnome_vfs (E_CAL_BACKEND (cbfile)); - - save (cbfile); - - return GNOME_Evolution_Calendar_Success; -} - -static char * -get_uri_string (ECalBackend *backend) -{ - gchar *str_uri, *full_uri; - - str_uri = get_uri_string_for_gnome_vfs (backend); - full_uri = gnome_vfs_unescape_string (str_uri, ""); - g_free (str_uri); - - return full_uri; -} - -/* Open handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_open (ECalBackendSync *backend, EDataCal *cal, gboolean only_if_exists, - const char *username, const char *password) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - char *str_uri; - ECalBackendSyncStatus status; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - /* Claim a succesful open if we are already open */ - if (priv->uri && priv->comp_uid_hash) - return GNOME_Evolution_Calendar_Success; - - str_uri = get_uri_string (E_CAL_BACKEND (backend)); - if (!str_uri) - return GNOME_Evolution_Calendar_OtherError; - - if (access (str_uri, R_OK) == 0) { - status = open_cal (cbfile, str_uri); - if (access (str_uri, W_OK) != 0) - priv->read_only = TRUE; - } else { - if (only_if_exists) - status = GNOME_Evolution_Calendar_NoSuchCal; - else - status = create_cal (cbfile, str_uri); - } - - g_free (str_uri); - - return status; -} - -static ECalBackendSyncStatus -e_cal_backend_file_remove (ECalBackendSync *backend, EDataCal *cal) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - char *str_uri, *dirname; - const char *fname; - GDir *dir; - GError *error = NULL; - gboolean success; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - str_uri = get_uri_string (E_CAL_BACKEND (backend)); - if (!str_uri) - return GNOME_Evolution_Calendar_OtherError; - - if (access (str_uri, W_OK) != 0) { - g_free (str_uri); - - return GNOME_Evolution_Calendar_PermissionDenied; - } - - /* remove all files in the directory */ - dirname = g_path_get_dirname (str_uri); - dir = g_dir_open (dirname, 0, &error); - if (!dir) { - g_free (str_uri); - g_free (dirname); - - return GNOME_Evolution_Calendar_PermissionDenied; - } - - while ((fname = g_dir_read_name (dir))) { - char *full_path; - - full_path = g_build_filename (dirname, fname, NULL); - if (unlink (full_path) != 0) { - g_free (full_path); - g_free (str_uri); - g_free (dirname); - g_dir_close (dir); - - return GNOME_Evolution_Calendar_OtherError; - } - - g_free (full_path); - } - - /* remove the directory itself */ - success = rmdir (dirname) == 0; - - g_dir_close (dir); - g_free (str_uri); - g_free (dirname); - - return success ? GNOME_Evolution_Calendar_Success : GNOME_Evolution_Calendar_OtherError; -} - -/* is_loaded handler for the file backend */ -static gboolean -e_cal_backend_file_is_loaded (ECalBackend *backend) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - return (priv->icalcomp != NULL); -} - -/* is_remote handler for the file backend */ -static CalMode -e_cal_backend_file_get_mode (ECalBackend *backend) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - return CAL_MODE_LOCAL; -} - -/* Set_mode handler for the file backend */ -static void -e_cal_backend_file_set_mode (ECalBackend *backend, CalMode mode) -{ - e_cal_backend_notify_mode (backend, - GNOME_Evolution_Calendar_CalListener_MODE_NOT_SUPPORTED, - GNOME_Evolution_Calendar_MODE_LOCAL); - -} - -static ECalBackendSyncStatus -e_cal_backend_file_get_default_object (ECalBackendSync *backend, EDataCal *cal, char **object) -{ - ECalComponent *comp; - - comp = e_cal_component_new (); - - switch (e_cal_backend_get_kind (E_CAL_BACKEND (backend))) { - case ICAL_VEVENT_COMPONENT: - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_EVENT); - break; - case ICAL_VTODO_COMPONENT: - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_TODO); - break; - case ICAL_VJOURNAL_COMPONENT: - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_JOURNAL); - break; - default: - g_object_unref (comp); - return GNOME_Evolution_Calendar_ObjectNotFound; - } - - *object = e_cal_component_get_as_string (comp); - g_object_unref (comp); - - return GNOME_Evolution_Calendar_Success; -} - -/* Get_object_component handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_get_object (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *rid, char **object) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - ECalBackendFileObject *obj_data; - ECalComponent *comp = NULL; - gboolean free_comp = FALSE; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, GNOME_Evolution_Calendar_InvalidObject); - g_return_val_if_fail (uid != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - g_assert (priv->comp_uid_hash != NULL); - - obj_data = g_hash_table_lookup (priv->comp_uid_hash, uid); - if (!obj_data) - return GNOME_Evolution_Calendar_ObjectNotFound; - - if (rid && *rid) { - comp = g_hash_table_lookup (obj_data->recurrences, rid); - if (!comp) { - icalcomponent *icalcomp; - struct icaltimetype itt; - - itt = icaltime_from_string (rid); - icalcomp = e_cal_util_construct_instance ( - e_cal_component_get_icalcomponent (obj_data->full_object), - itt); - if (!icalcomp) - return GNOME_Evolution_Calendar_ObjectNotFound; - - comp = e_cal_component_new (); - free_comp = TRUE; - e_cal_component_set_icalcomponent (comp, icalcomp); - } - } else - comp = obj_data->full_object; - - if (!comp) - return GNOME_Evolution_Calendar_ObjectNotFound; - - *object = e_cal_component_get_as_string (comp); - - if (free_comp) - g_object_unref (comp); - - return GNOME_Evolution_Calendar_Success; -} - -/* Get_timezone_object handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_get_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid, char **object) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - icaltimezone *zone; - icalcomponent *icalcomp; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, GNOME_Evolution_Calendar_NoSuchCal); - g_return_val_if_fail (tzid != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - if (!strcmp (tzid, "UTC")) { - zone = icaltimezone_get_utc_timezone (); - } else { - zone = icalcomponent_get_timezone (priv->icalcomp, tzid); - if (!zone) { - zone = icaltimezone_get_builtin_timezone_from_tzid (tzid); - if (!zone) - return GNOME_Evolution_Calendar_ObjectNotFound; - } - } - - icalcomp = icaltimezone_get_component (zone); - if (!icalcomp) - return GNOME_Evolution_Calendar_InvalidObject; - - *object = g_strdup (icalcomponent_as_ical_string (icalcomp)); - - return GNOME_Evolution_Calendar_Success; -} - -/* Add_timezone handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_add_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzobj) -{ - icalcomponent *tz_comp; - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - - cbfile = (ECalBackendFile *) backend; - - g_return_val_if_fail (E_IS_CAL_BACKEND_FILE (cbfile), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (tzobj != NULL, GNOME_Evolution_Calendar_OtherError); - - priv = cbfile->priv; - - tz_comp = icalparser_parse_string (tzobj); - if (!tz_comp) - return GNOME_Evolution_Calendar_InvalidObject; - - if (icalcomponent_isa (tz_comp) == ICAL_VTIMEZONE_COMPONENT) { - icaltimezone *zone; - - zone = icaltimezone_new (); - icaltimezone_set_component (zone, tz_comp); - if (!icalcomponent_get_timezone (priv->icalcomp, - icaltimezone_get_tzid (zone))) { - icalcomponent_add_component (priv->icalcomp, tz_comp); - save (cbfile); - } - - icaltimezone_free (zone, 1); - } - - return GNOME_Evolution_Calendar_Success; -} - - -static ECalBackendSyncStatus -e_cal_backend_file_set_default_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - icaltimezone *zone; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, GNOME_Evolution_Calendar_NoSuchCal); - - /* Look up the VTIMEZONE in our icalcomponent. */ - zone = icalcomponent_get_timezone (priv->icalcomp, tzid); - if (!zone) - return GNOME_Evolution_Calendar_ObjectNotFound; - - /* Set the default timezone to it. */ - priv->default_zone = zone; - - return GNOME_Evolution_Calendar_Success; -} - -typedef struct { - GList *obj_list; - gboolean search_needed; - const char *query; - ECalBackendSExp *obj_sexp; - ECalBackend *backend; - icaltimezone *default_zone; -} MatchObjectData; - -static void -match_recurrence_sexp (gpointer key, gpointer value, gpointer data) -{ - ECalComponent *comp = value; - MatchObjectData *match_data = data; - - if ((!match_data->search_needed) || - (e_cal_backend_sexp_match_comp (match_data->obj_sexp, comp, match_data->backend))) { - match_data->obj_list = g_list_append (match_data->obj_list, - e_cal_component_get_as_string (comp)); - } -} - -static void -match_object_sexp (gpointer key, gpointer value, gpointer data) -{ - ECalBackendFileObject *obj_data = value; - MatchObjectData *match_data = data; - - if (obj_data->full_object) { - if ((!match_data->search_needed) || - (e_cal_backend_sexp_match_comp (match_data->obj_sexp, obj_data->full_object, match_data->backend))) { - match_data->obj_list = g_list_append (match_data->obj_list, - e_cal_component_get_as_string (obj_data->full_object)); - } - } - - /* match also recurrences */ - g_hash_table_foreach (obj_data->recurrences, - (GHFunc) match_recurrence_sexp, - match_data); -} - -/* Get_objects_in_range handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_get_object_list (ECalBackendSync *backend, EDataCal *cal, const char *sexp, GList **objects) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - MatchObjectData match_data; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - d(g_message (G_STRLOC ": Getting object list (%s)", sexp)); - - match_data.search_needed = TRUE; - match_data.query = sexp; - match_data.obj_list = NULL; - match_data.backend = E_CAL_BACKEND (backend); - match_data.default_zone = priv->default_zone; - - if (!strcmp (sexp, "#t")) - match_data.search_needed = FALSE; - - match_data.obj_sexp = e_cal_backend_sexp_new (sexp); - if (!match_data.obj_sexp) - return GNOME_Evolution_Calendar_InvalidQuery; - - g_hash_table_foreach (priv->comp_uid_hash, (GHFunc) match_object_sexp, &match_data); - - *objects = match_data.obj_list; - - return GNOME_Evolution_Calendar_Success; -} - -/* get_query handler for the file backend */ -static void -e_cal_backend_file_start_query (ECalBackend *backend, EDataCalView *query) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - MatchObjectData match_data; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - d(g_message (G_STRLOC ": Starting query (%s)", e_data_cal_view_get_text (query))); - - /* try to match all currently existing objects */ - match_data.search_needed = TRUE; - match_data.query = e_data_cal_view_get_text (query); - match_data.obj_list = NULL; - match_data.backend = backend; - match_data.default_zone = priv->default_zone; - - if (!strcmp (match_data.query, "#t")) - match_data.search_needed = FALSE; - - match_data.obj_sexp = e_data_cal_view_get_object_sexp (query); - if (!match_data.obj_sexp) { - e_data_cal_view_notify_done (query, GNOME_Evolution_Calendar_InvalidQuery); - return; - } - - g_hash_table_foreach (priv->comp_uid_hash, (GHFunc) match_object_sexp, &match_data); - - /* notify listeners of all objects */ - if (match_data.obj_list) { - e_data_cal_view_notify_objects_added (query, (const GList *) match_data.obj_list); - - /* free memory */ - g_list_foreach (match_data.obj_list, (GFunc) g_free, NULL); - g_list_free (match_data.obj_list); - } - - e_data_cal_view_notify_done (query, GNOME_Evolution_Calendar_Success); -} - -static gboolean -free_busy_instance (ECalComponent *comp, - time_t instance_start, - time_t instance_end, - gpointer data) -{ - icalcomponent *vfb = data; - icalproperty *prop; - icalparameter *param; - struct icalperiodtype ipt; - icaltimezone *utc_zone; - - utc_zone = icaltimezone_get_utc_timezone (); - - ipt.start = icaltime_from_timet_with_zone (instance_start, FALSE, utc_zone); - ipt.end = icaltime_from_timet_with_zone (instance_end, FALSE, utc_zone); - ipt.duration = icaldurationtype_null_duration (); - - /* add busy information to the vfb component */ - prop = icalproperty_new (ICAL_FREEBUSY_PROPERTY); - icalproperty_set_freebusy (prop, ipt); - - param = icalparameter_new_fbtype (ICAL_FBTYPE_BUSY); - icalproperty_add_parameter (prop, param); - - icalcomponent_add_property (vfb, prop); - - return TRUE; -} - -static icalcomponent * -create_user_free_busy (ECalBackendFile *cbfile, const char *address, const char *cn, - time_t start, time_t end) -{ - ECalBackendFilePrivate *priv; - GList *l; - icalcomponent *vfb; - icaltimezone *utc_zone; - ECalBackendSExp *obj_sexp; - char *query, *iso_start, *iso_end; - - priv = cbfile->priv; - - /* create the (unique) VFREEBUSY object that we'll return */ - vfb = icalcomponent_new_vfreebusy (); - if (address != NULL) { - icalproperty *prop; - icalparameter *param; - - prop = icalproperty_new_organizer (address); - if (prop != NULL && cn != NULL) { - param = icalparameter_new_cn (cn); - icalproperty_add_parameter (prop, param); - } - if (prop != NULL) - icalcomponent_add_property (vfb, prop); - } - utc_zone = icaltimezone_get_utc_timezone (); - icalcomponent_set_dtstart (vfb, icaltime_from_timet_with_zone (start, FALSE, utc_zone)); - icalcomponent_set_dtend (vfb, icaltime_from_timet_with_zone (end, FALSE, utc_zone)); - - /* add all objects in the given interval */ - iso_start = isodate_from_time_t (start); - iso_end = isodate_from_time_t (end); - query = g_strdup_printf ("occur-in-time-range? (make-time \"%s\") (make-time \"%s\")", - iso_start, iso_end); - obj_sexp = e_cal_backend_sexp_new (query); - g_free (query); - g_free (iso_start); - g_free (iso_end); - - if (!obj_sexp) - return vfb; - - for (l = priv->comp; l; l = l->next) { - ECalComponent *comp = l->data; - icalcomponent *icalcomp, *vcalendar_comp; - icalproperty *prop; - - icalcomp = e_cal_component_get_icalcomponent (comp); - if (!icalcomp) - continue; - - /* If the event is TRANSPARENT, skip it. */ - prop = icalcomponent_get_first_property (icalcomp, - ICAL_TRANSP_PROPERTY); - if (prop) { - icalproperty_transp transp_val = icalproperty_get_transp (prop); - if (transp_val == ICAL_TRANSP_TRANSPARENT || - transp_val == ICAL_TRANSP_TRANSPARENTNOCONFLICT) - continue; - } - - if (!e_cal_backend_sexp_match_comp (obj_sexp, l->data, E_CAL_BACKEND (cbfile))) - continue; - - vcalendar_comp = icalcomponent_get_parent (icalcomp); - e_cal_recur_generate_instances (comp, start, end, - free_busy_instance, - vfb, - resolve_tzid, - vcalendar_comp, - priv->default_zone); - } - - return vfb; -} - -/* Get_free_busy handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_get_free_busy (ECalBackendSync *backend, EDataCal *cal, GList *users, - time_t start, time_t end, GList **freebusy) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - gchar *address, *name; - icalcomponent *vfb; - char *calobj; - GList *l; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, GNOME_Evolution_Calendar_NoSuchCal); - g_return_val_if_fail (start != -1 && end != -1, GNOME_Evolution_Calendar_InvalidRange); - g_return_val_if_fail (start <= end, GNOME_Evolution_Calendar_InvalidRange); - - *freebusy = NULL; - - if (users == NULL) { - if (e_cal_backend_mail_account_get_default (&address, &name)) { - vfb = create_user_free_busy (cbfile, address, name, start, end); - calobj = icalcomponent_as_ical_string (vfb); - *freebusy = g_list_append (*freebusy, g_strdup (calobj)); - icalcomponent_free (vfb); - g_free (address); - g_free (name); - } - } else { - for (l = users; l != NULL; l = l->next ) { - address = l->data; - if (e_cal_backend_mail_account_is_valid (address, &name)) { - vfb = create_user_free_busy (cbfile, address, name, start, end); - calobj = icalcomponent_as_ical_string (vfb); - *freebusy = g_list_append (*freebusy, g_strdup (calobj)); - icalcomponent_free (vfb); - g_free (name); - } - } - } - - return GNOME_Evolution_Calendar_Success; -} - -typedef struct -{ - ECalBackendFile *backend; - icalcomponent_kind kind; - GList *deletes; - EXmlHash *ehash; -} ECalBackendFileComputeChangesData; - -static void -e_cal_backend_file_compute_changes_foreach_key (const char *key, gpointer value, gpointer data) -{ - ECalBackendFileComputeChangesData *be_data = data; - - if (!lookup_component (be_data->backend, key)) { - ECalComponent *comp; - - comp = e_cal_component_new (); - if (be_data->kind == ICAL_VTODO_COMPONENT) - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_TODO); - else - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_EVENT); - - e_cal_component_set_uid (comp, key); - be_data->deletes = g_list_prepend (be_data->deletes, e_cal_component_get_as_string (comp)); - - e_xmlhash_remove (be_data->ehash, key); - } -} - -static ECalBackendSyncStatus -e_cal_backend_file_compute_changes (ECalBackendFile *cbfile, const char *change_id, - GList **adds, GList **modifies, GList **deletes) -{ - ECalBackendFilePrivate *priv; - char *filename; - EXmlHash *ehash; - ECalBackendFileComputeChangesData be_data; - GList *i; - gchar *unescaped_uri; - - priv = cbfile->priv; - - /* FIXME Will this always work? */ - unescaped_uri = gnome_vfs_unescape_string (priv->uri, ""); - filename = g_strdup_printf ("%s-%s.db", unescaped_uri, change_id); - g_free (unescaped_uri); - if (!(ehash = e_xmlhash_new (filename))) { - g_free (filename); - return GNOME_Evolution_Calendar_OtherError; - } - - g_free (filename); - - /* Calculate adds and modifies */ - for (i = priv->comp; i != NULL; i = i->next) { - const char *uid; - char *calobj; - - e_cal_component_get_uid (i->data, &uid); - calobj = e_cal_component_get_as_string (i->data); - - g_assert (calobj != NULL); - - /* check what type of change has occurred, if any */ - switch (e_xmlhash_compare (ehash, uid, calobj)) { - case E_XMLHASH_STATUS_SAME: - break; - case E_XMLHASH_STATUS_NOT_FOUND: - *adds = g_list_prepend (*adds, g_strdup (calobj)); - e_xmlhash_add (ehash, uid, calobj); - break; - case E_XMLHASH_STATUS_DIFFERENT: - *modifies = g_list_prepend (*modifies, g_strdup (calobj)); - e_xmlhash_add (ehash, uid, calobj); - break; - } - - g_free (calobj); - } - - /* Calculate deletions */ - be_data.backend = cbfile; - be_data.kind = e_cal_backend_get_kind (E_CAL_BACKEND (cbfile)); - be_data.deletes = NULL; - be_data.ehash = ehash; - - e_xmlhash_foreach_key (ehash, (EXmlHashFunc)e_cal_backend_file_compute_changes_foreach_key, &be_data); - - *deletes = be_data.deletes; - - e_xmlhash_write (ehash); - e_xmlhash_destroy (ehash); - - return GNOME_Evolution_Calendar_Success; -} - -/* Get_changes handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_get_changes (ECalBackendSync *backend, EDataCal *cal, const char *change_id, - GList **adds, GList **modifies, GList **deletes) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, GNOME_Evolution_Calendar_NoSuchCal); - g_return_val_if_fail (change_id != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - return e_cal_backend_file_compute_changes (cbfile, change_id, adds, modifies, deletes); -} - -/* Discard_alarm handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_discard_alarm (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *auid) -{ - /* we just do nothing with the alarm */ - return GNOME_Evolution_Calendar_Success; -} - -static icaltimezone * -e_cal_backend_file_internal_get_default_timezone (ECalBackend *backend) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, NULL); - - return priv->default_zone; -} - -static icaltimezone * -e_cal_backend_file_internal_get_timezone (ECalBackend *backend, const char *tzid) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - icaltimezone *zone; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, NULL); - - if (!strcmp (tzid, "UTC")) - zone = icaltimezone_get_utc_timezone (); - else { - zone = icalcomponent_get_timezone (priv->icalcomp, tzid); - if (!zone) - zone = icaltimezone_get_builtin_timezone_from_tzid (tzid); - } - - return zone; -} - -static void -sanitize_component (ECalBackendFile *cbfile, ECalComponent *comp) -{ - ECalComponentDateTime dt; - icaltimezone *zone, *default_zone; - - /* Check dtstart, dtend and due's timezone, and convert it to local - * default timezone if the timezone is not in our builtin timezone - * list */ - e_cal_component_get_dtstart (comp, &dt); - if (dt.value && dt.tzid) { - zone = e_cal_backend_file_internal_get_timezone ((ECalBackend *)cbfile, dt.tzid); - if (!zone) { - default_zone = e_cal_backend_file_internal_get_default_timezone ((ECalBackend *)cbfile); - g_free ((char *)dt.tzid); - dt.tzid = g_strdup (icaltimezone_get_tzid (default_zone)); - e_cal_component_set_dtstart (comp, &dt); - } - } - e_cal_component_free_datetime (&dt); - - e_cal_component_get_dtend (comp, &dt); - if (dt.value && dt.tzid) { - zone = e_cal_backend_file_internal_get_timezone ((ECalBackend *)cbfile, dt.tzid); - if (!zone) { - default_zone = e_cal_backend_file_internal_get_default_timezone ((ECalBackend *)cbfile); - g_free ((char *)dt.tzid); - dt.tzid = g_strdup (icaltimezone_get_tzid (default_zone)); - e_cal_component_set_dtend (comp, &dt); - } - } - e_cal_component_free_datetime (&dt); - - e_cal_component_get_due (comp, &dt); - if (dt.value && dt.tzid) { - zone = e_cal_backend_file_internal_get_timezone ((ECalBackend *)cbfile, dt.tzid); - if (!zone) { - default_zone = e_cal_backend_file_internal_get_default_timezone ((ECalBackend *)cbfile); - g_free ((char *)dt.tzid); - dt.tzid = g_strdup (icaltimezone_get_tzid (default_zone)); - e_cal_component_set_due (comp, &dt); - } - } - e_cal_component_free_datetime (&dt); - e_cal_component_abort_sequence (comp); - -} - - -static ECalBackendSyncStatus -e_cal_backend_file_create_object (ECalBackendSync *backend, EDataCal *cal, char **calobj, char **uid) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - icalcomponent *icalcomp; - ECalComponent *comp; - const char *comp_uid; - struct icaltimetype current; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, GNOME_Evolution_Calendar_NoSuchCal); - g_return_val_if_fail (*calobj != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - /* Parse the icalendar text */ - icalcomp = icalparser_parse_string (*calobj); - if (!icalcomp) - return GNOME_Evolution_Calendar_InvalidObject; - - /* Check kind with the parent */ - if (icalcomponent_isa (icalcomp) != e_cal_backend_get_kind (E_CAL_BACKEND (backend))) { - icalcomponent_free (icalcomp); - return GNOME_Evolution_Calendar_InvalidObject; - } - - /* Get the UID */ - comp_uid = icalcomponent_get_uid (icalcomp); - - /* check the object is not in our cache */ - if (lookup_component (cbfile, comp_uid)) { - icalcomponent_free (icalcomp); - return GNOME_Evolution_Calendar_ObjectIdAlreadyExists; - } - - /* Create the cal component */ - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, icalcomp); - - /* Set the created and last modified times on the component */ - current = icaltime_from_timet (time (NULL), 0); - e_cal_component_set_created (comp, ¤t); - e_cal_component_set_last_modified (comp, ¤t); - - /* sanitize the component*/ - sanitize_component (cbfile, comp); - - /* Add the object */ - add_component (cbfile, comp, TRUE); - - /* Save the file */ - save (cbfile); - - /* Return the UID and the modified component */ - if (uid) - *uid = g_strdup (comp_uid); - *calobj = e_cal_component_get_as_string (comp); - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_file_modify_object (ECalBackendSync *backend, EDataCal *cal, const char *calobj, - CalObjModType mod, char **old_object) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - icalcomponent *icalcomp; - const char *comp_uid, *rid; - char *real_rid; - ECalComponent *comp, *recurrence; - ECalBackendFileObject *obj_data; - struct icaltimetype current; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, GNOME_Evolution_Calendar_NoSuchCal); - g_return_val_if_fail (calobj != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - /* Parse the icalendar text */ - icalcomp = icalparser_parse_string ((char *) calobj); - if (!icalcomp) - return GNOME_Evolution_Calendar_InvalidObject; - - /* Check kind with the parent */ - if (icalcomponent_isa (icalcomp) != e_cal_backend_get_kind (E_CAL_BACKEND (backend))) { - icalcomponent_free (icalcomp); - return GNOME_Evolution_Calendar_InvalidObject; - } - - /* Get the uid */ - comp_uid = icalcomponent_get_uid (icalcomp); - - /* Get the object from our cache */ - if (!(obj_data = g_hash_table_lookup (priv->comp_uid_hash, comp_uid))) { - icalcomponent_free (icalcomp); - return GNOME_Evolution_Calendar_ObjectNotFound; - } - - /* Create the cal component */ - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, icalcomp); - - /* Set the last modified time on the component */ - current = icaltime_from_timet (time (NULL), 0); - e_cal_component_set_last_modified (comp, ¤t); - - /* sanitize the component*/ - sanitize_component (cbfile, comp); - - /* handle mod_type */ - switch (mod) { - case CALOBJ_MOD_THIS : - rid = e_cal_component_get_recurid_as_string (comp); - if (!rid || !*rid) { - if (old_object) - *old_object = e_cal_component_get_as_string (obj_data->full_object); - - /* replace only the full object */ - icalcomponent_remove_component (priv->icalcomp, - e_cal_component_get_icalcomponent (obj_data->full_object)); - priv->comp = g_list_remove (priv->comp, obj_data->full_object); - - /* add the new object */ - g_object_unref (obj_data->full_object); - obj_data->full_object = comp; - - icalcomponent_add_component (priv->icalcomp, - e_cal_component_get_icalcomponent (obj_data->full_object)); - priv->comp = g_list_prepend (priv->comp, obj_data->full_object); - - save (cbfile); - - return GNOME_Evolution_Calendar_Success; - } - - if (g_hash_table_lookup_extended (obj_data->recurrences, rid, - (void **) &real_rid, (void **) &recurrence)) { - if (old_object) - *old_object = e_cal_component_get_as_string (recurrence); - - /* remove the component from our data */ - icalcomponent_remove_component (priv->icalcomp, - e_cal_component_get_icalcomponent (recurrence)); - priv->comp = g_list_remove (priv->comp, recurrence); - g_hash_table_remove (obj_data->recurrences, rid); - obj_data->recurrences_list = g_list_remove (obj_data->recurrences_list, recurrence); - - /* free memory */ - g_free (real_rid); - g_object_unref (recurrence); - } else { - char *old, *new; - - old = e_cal_component_get_as_string (obj_data->full_object); - - e_cal_util_remove_instances (e_cal_component_get_icalcomponent (obj_data->full_object), - get_rid_icaltime (comp), - mod); - - new = e_cal_component_get_as_string (obj_data->full_object); - - e_cal_backend_notify_object_modified (E_CAL_BACKEND (backend), old, new); - - if (old_object) - *old_object = old; - else - g_free (old); - g_free (new); - } - - /* add the detached instance */ - g_hash_table_insert (obj_data->recurrences, - g_strdup (e_cal_component_get_recurid_as_string (comp)), - comp); - obj_data->recurrences_list = g_list_append (obj_data->recurrences_list, comp); - break; - case CALOBJ_MOD_THISANDPRIOR : - break; - case CALOBJ_MOD_THISANDFUTURE : - break; - case CALOBJ_MOD_ALL : - /* in this case, we blow away all recurrences, and start over - with a clean component */ - /* Remove the old version */ - if (old_object) - *old_object = e_cal_component_get_as_string (obj_data->full_object); - - remove_component (cbfile, obj_data->full_object); - - /* Add the new object */ - add_component (cbfile, comp, TRUE); - break; - } - - save (cbfile); - - return GNOME_Evolution_Calendar_Success; -} - -static void -remove_instance (ECalBackendFile *cbfile, ECalBackendFileObject *obj_data, const char *rid) -{ - char *hash_rid; - ECalComponent *comp; - GSList *categories; - - if (!rid || !*rid) - return; - - if (g_hash_table_lookup_extended (obj_data->recurrences, rid, (void **) &hash_rid, (void **) &comp)) { - /* remove the component from our data */ - icalcomponent_remove_component (cbfile->priv->icalcomp, - e_cal_component_get_icalcomponent (comp)); - cbfile->priv->comp = g_list_remove (cbfile->priv->comp, comp); - g_hash_table_remove (obj_data->recurrences, rid); - obj_data->recurrences_list = g_list_remove (obj_data->recurrences_list, comp); - - /* update the set of categories */ - e_cal_component_get_categories_list (comp, &categories); - e_cal_backend_unref_categories (E_CAL_BACKEND (cbfile), categories); - e_cal_component_free_categories_list (categories); - - /* free memory */ - g_free (hash_rid); - g_object_unref (comp); - - return; - } - - /* remove the component from our data, temporarily */ - icalcomponent_remove_component (cbfile->priv->icalcomp, - e_cal_component_get_icalcomponent (obj_data->full_object)); - cbfile->priv->comp = g_list_remove (cbfile->priv->comp, obj_data->full_object); - - e_cal_util_remove_instances (e_cal_component_get_icalcomponent (obj_data->full_object), - icaltime_from_string (rid), CALOBJ_MOD_THIS); - - /* add the modified object to the beginning of the list, - so that it's always before any detached instance we - might have */ - icalcomponent_add_component (cbfile->priv->icalcomp, - e_cal_component_get_icalcomponent (obj_data->full_object)); - cbfile->priv->comp = g_list_prepend (cbfile->priv->comp, obj_data->full_object); -} - -typedef struct { - ECalBackendFile *cbfile; - ECalBackendFileObject *obj_data; - const char *rid; - CalObjModType mod; -} RemoveRecurrenceData; - -static gboolean -remove_object_instance_cb (gpointer key, gpointer value, gpointer user_data) -{ - time_t fromtt, instancett; - GSList *categories; - char *rid = key; - ECalComponent *instance = value; - RemoveRecurrenceData *rrdata = user_data; - - fromtt = icaltime_as_timet (icaltime_from_string (rrdata->rid)); - instancett = icaltime_as_timet (get_rid_icaltime (instance)); - - if (fromtt > 0 && instancett > 0) { - if ((rrdata->mod == CALOBJ_MOD_THISANDPRIOR && instancett <= fromtt) || - (rrdata->mod == CALOBJ_MOD_THISANDFUTURE && instancett >= fromtt)) { - /* remove the component from our data */ - icalcomponent_remove_component (rrdata->cbfile->priv->icalcomp, - e_cal_component_get_icalcomponent (instance)); - rrdata->cbfile->priv->comp = g_list_remove (rrdata->cbfile->priv->comp, instance); - - rrdata->obj_data->recurrences_list = g_list_remove (rrdata->obj_data->recurrences_list, instance); - - /* update the set of categories */ - e_cal_component_get_categories_list (instance, &categories); - e_cal_backend_unref_categories (E_CAL_BACKEND (rrdata->cbfile), categories); - e_cal_component_free_categories_list (categories); - - /* free memory */ - g_free (rid); - g_object_unref (instance); - - return TRUE; - } - } - - return FALSE; -} - -/* Remove_object handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_file_remove_object (ECalBackendSync *backend, EDataCal *cal, - const char *uid, const char *rid, - CalObjModType mod, char **object) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - ECalBackendFileObject *obj_data; - ECalComponent *comp; - GSList *categories; - RemoveRecurrenceData rrdata; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, GNOME_Evolution_Calendar_NoSuchCal); - g_return_val_if_fail (uid != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - obj_data = g_hash_table_lookup (priv->comp_uid_hash, uid); - if (!obj_data) - return GNOME_Evolution_Calendar_ObjectNotFound; - - comp = obj_data->full_object; - - switch (mod) { - case CALOBJ_MOD_ALL : - *object = e_cal_component_get_as_string (comp); - remove_component (cbfile, comp); - break; - case CALOBJ_MOD_THIS : - if (!rid || !*rid) - remove_component (cbfile, comp); - else - remove_instance (cbfile, obj_data, rid); - break; - case CALOBJ_MOD_THISANDPRIOR : - case CALOBJ_MOD_THISANDFUTURE : - if (!rid || !*rid) - return GNOME_Evolution_Calendar_ObjectNotFound; - - /* remove the component from our data, temporarily */ - icalcomponent_remove_component (priv->icalcomp, - e_cal_component_get_icalcomponent (comp)); - priv->comp = g_list_remove (priv->comp, comp); - - e_cal_util_remove_instances (e_cal_component_get_icalcomponent (comp), - icaltime_from_string (rid), mod); - - /* now remove all detached instances */ - rrdata.cbfile = cbfile; - rrdata.obj_data = obj_data; - rrdata.rid = rid; - rrdata.mod = mod; - g_hash_table_foreach_remove (obj_data->recurrences, (GHRFunc) remove_object_instance_cb, &rrdata); - - /* add the modified object to the beginning of the list, - so that it's always before any detached instance we - might have */ - priv->comp = g_list_prepend (priv->comp, comp); - break; - } - - save (cbfile); - - return GNOME_Evolution_Calendar_Success; -} - -static gboolean -cancel_received_object (ECalBackendFile *cbfile, icalcomponent *icalcomp) -{ - ECalComponent *old_comp; - - /* Find the old version of the component. */ - old_comp = lookup_component (cbfile, icalcomponent_get_uid (icalcomp)); - if (!old_comp) - return FALSE; - - /* And remove it */ - remove_component (cbfile, old_comp); - - return TRUE; -} - -typedef struct { - GHashTable *zones; - - gboolean found; -} ECalBackendFileTzidData; - -static void -check_tzids (icalparameter *param, void *data) -{ - ECalBackendFileTzidData *tzdata = data; - const char *tzid; - - tzid = icalparameter_get_tzid (param); - if (!tzid || g_hash_table_lookup (tzdata->zones, tzid)) - tzdata->found = FALSE; -} - -/* Update_objects handler for the file backend. */ -static ECalBackendSyncStatus -e_cal_backend_file_receive_objects (ECalBackendSync *backend, EDataCal *cal, const char *calobj) -{ - ECalBackendFile *cbfile; - ECalBackendFilePrivate *priv; - icalcomponent *toplevel_comp, *icalcomp = NULL; - icalcomponent_kind kind; - icalproperty_method method; - icalcomponent *subcomp; - GList *comps, *del_comps, *l; - ECalComponent *comp; - struct icaltimetype current; - ECalBackendFileTzidData tzdata; - ECalBackendSyncStatus status = GNOME_Evolution_Calendar_Success; - - cbfile = E_CAL_BACKEND_FILE (backend); - priv = cbfile->priv; - - g_return_val_if_fail (priv->icalcomp != NULL, GNOME_Evolution_Calendar_InvalidObject); - g_return_val_if_fail (calobj != NULL, GNOME_Evolution_Calendar_InvalidObject); - - /* Pull the component from the string and ensure that it is sane */ - toplevel_comp = icalparser_parse_string ((char *) calobj); - if (!toplevel_comp) - return GNOME_Evolution_Calendar_InvalidObject; - - kind = icalcomponent_isa (toplevel_comp); - if (kind != ICAL_VCALENDAR_COMPONENT) { - /* If its not a VCALENDAR, make it one to simplify below */ - icalcomp = toplevel_comp; - toplevel_comp = e_cal_util_new_top_level (); - icalcomponent_add_component (toplevel_comp, icalcomp); - } - - method = icalcomponent_get_method (toplevel_comp); - - /* Build a list of timezones so we can make sure all the objects have valid info */ - tzdata.zones = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); - - subcomp = icalcomponent_get_first_component (toplevel_comp, ICAL_VTIMEZONE_COMPONENT); - while (subcomp) { - icaltimezone *zone; - - zone = icaltimezone_new (); - if (icaltimezone_set_component (zone, subcomp)) - g_hash_table_insert (tzdata.zones, g_strdup (icaltimezone_get_tzid (zone)), NULL); - - subcomp = icalcomponent_get_next_component (toplevel_comp, ICAL_VTIMEZONE_COMPONENT); - } - - /* First we make sure all the components are usuable */ - comps = del_comps = NULL; - kind = e_cal_backend_get_kind (E_CAL_BACKEND (backend)); - - subcomp = icalcomponent_get_first_component (toplevel_comp, ICAL_ANY_COMPONENT); - while (subcomp) { - icalcomponent_kind child_kind = icalcomponent_isa (subcomp); - - if (child_kind != kind) { - /* remove the component from the toplevel VCALENDAR */ - if (child_kind != ICAL_VTIMEZONE_COMPONENT) - del_comps = g_list_prepend (del_comps, subcomp); - - subcomp = icalcomponent_get_next_component (toplevel_comp, ICAL_ANY_COMPONENT); - continue; - } - - tzdata.found = TRUE; - icalcomponent_foreach_tzid (subcomp, check_tzids, &tzdata); - - if (!tzdata.found) { - status = GNOME_Evolution_Calendar_InvalidObject; - goto error; - } - - if (!icalcomponent_get_uid (subcomp)) { - status = GNOME_Evolution_Calendar_InvalidObject; - goto error; - } - - comps = g_list_prepend (comps, subcomp); - subcomp = icalcomponent_get_next_component (toplevel_comp, ICAL_ANY_COMPONENT); - } - - /* Now we manipulate the components we care about */ - for (l = comps; l; l = l->next) { - const char *uid, *rid; - char *object, *old_object; - ECalComponent *old_comp; - - subcomp = l->data; - - /* Create the cal component */ - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, subcomp); - - /* Set the created and last modified times on the component */ - current = icaltime_from_timet (time (NULL), 0); - e_cal_component_set_created (comp, ¤t); - e_cal_component_set_last_modified (comp, ¤t); - - e_cal_component_get_uid (comp, &uid); - rid = e_cal_component_get_recurid_as_string (comp); - - switch (method) { - case ICAL_METHOD_PUBLISH: - case ICAL_METHOD_REQUEST: - case ICAL_METHOD_REPLY: - old_comp = lookup_component (cbfile, uid); - if (old_comp) { - old_object = e_cal_component_get_as_string (old_comp); - remove_component (cbfile, old_comp); - add_component (cbfile, comp, FALSE); - - object = e_cal_component_get_as_string (comp); - e_cal_backend_notify_object_modified (E_CAL_BACKEND (backend), old_object, object); - g_free (object); - g_free (old_object); - } else { - add_component (cbfile, comp, FALSE); - - object = e_cal_component_get_as_string (comp); - e_cal_backend_notify_object_created (E_CAL_BACKEND (backend), object); - g_free (object); - } - break; - case ICAL_METHOD_ADD: - /* FIXME This should be doable once all the recurid stuff is done */ - status = GNOME_Evolution_Calendar_UnsupportedMethod; - goto error; - break; - case ICAL_METHOD_COUNTER: - status = GNOME_Evolution_Calendar_UnsupportedMethod; - goto error; - break; - case ICAL_METHOD_DECLINECOUNTER: - status = GNOME_Evolution_Calendar_UnsupportedMethod; - goto error; - break; - case ICAL_METHOD_CANCEL: - if (cancel_received_object (cbfile, subcomp)) { - object = (char *) icalcomponent_as_ical_string (subcomp); - e_cal_backend_notify_object_removed (E_CAL_BACKEND (backend), uid, object); - - /* remove the component from the toplevel VCALENDAR */ - icalcomponent_remove_component (toplevel_comp, subcomp); - icalcomponent_free (subcomp); - } - break; - default: - status = GNOME_Evolution_Calendar_UnsupportedMethod; - goto error; - } - } - - g_list_free (comps); - - /* Now we remove the components we don't care about */ - for (l = del_comps; l; l = l->next) { - subcomp = l->data; - - icalcomponent_remove_component (toplevel_comp, subcomp); - icalcomponent_free (subcomp); - } - - g_list_free (del_comps); - - /* Merge the iCalendar components with our existing VCALENDAR, - resolving any conflicting TZIDs. */ - icalcomponent_merge_component (priv->icalcomp, toplevel_comp); - - save (cbfile); - - error: - g_hash_table_destroy (tzdata.zones); - - return status; -} - -static ECalBackendSyncStatus -e_cal_backend_file_send_objects (ECalBackendSync *backend, EDataCal *cal, const char *calobj, GList **users, - char **modified_calobj) -{ - *users = NULL; - *modified_calobj = g_strdup (calobj); - - return GNOME_Evolution_Calendar_Success; -} - -/* Object initialization function for the file backend */ -static void -e_cal_backend_file_init (ECalBackendFile *cbfile, ECalBackendFileClass *class) -{ - ECalBackendFilePrivate *priv; - - priv = g_new0 (ECalBackendFilePrivate, 1); - cbfile->priv = priv; - - priv->uri = NULL; - priv->file_name = g_strdup ("calendar.ics"); - priv->read_only = FALSE; - priv->icalcomp = NULL; - priv->comp_uid_hash = NULL; - priv->comp = NULL; - - /* The timezone defaults to UTC. */ - priv->default_zone = icaltimezone_get_utc_timezone (); -} - -/* Class initialization function for the file backend */ -static void -e_cal_backend_file_class_init (ECalBackendFileClass *class) -{ - GObjectClass *object_class; - ECalBackendClass *backend_class; - ECalBackendSyncClass *sync_class; - - object_class = (GObjectClass *) class; - backend_class = (ECalBackendClass *) class; - sync_class = (ECalBackendSyncClass *) class; - - parent_class = (ECalBackendSyncClass *) g_type_class_peek_parent (class); - - object_class->dispose = e_cal_backend_file_dispose; - object_class->finalize = e_cal_backend_file_finalize; - - sync_class->is_read_only_sync = e_cal_backend_file_is_read_only; - sync_class->get_cal_address_sync = e_cal_backend_file_get_cal_address; - sync_class->get_alarm_email_address_sync = e_cal_backend_file_get_alarm_email_address; - sync_class->get_ldap_attribute_sync = e_cal_backend_file_get_ldap_attribute; - sync_class->get_static_capabilities_sync = e_cal_backend_file_get_static_capabilities; - sync_class->open_sync = e_cal_backend_file_open; - sync_class->remove_sync = e_cal_backend_file_remove; - sync_class->create_object_sync = e_cal_backend_file_create_object; - sync_class->modify_object_sync = e_cal_backend_file_modify_object; - sync_class->remove_object_sync = e_cal_backend_file_remove_object; - sync_class->discard_alarm_sync = e_cal_backend_file_discard_alarm; - sync_class->receive_objects_sync = e_cal_backend_file_receive_objects; - sync_class->send_objects_sync = e_cal_backend_file_send_objects; - sync_class->get_default_object_sync = e_cal_backend_file_get_default_object; - sync_class->get_object_sync = e_cal_backend_file_get_object; - sync_class->get_object_list_sync = e_cal_backend_file_get_object_list; - sync_class->get_timezone_sync = e_cal_backend_file_get_timezone; - sync_class->add_timezone_sync = e_cal_backend_file_add_timezone; - sync_class->set_default_timezone_sync = e_cal_backend_file_set_default_timezone; - sync_class->get_freebusy_sync = e_cal_backend_file_get_free_busy; - sync_class->get_changes_sync = e_cal_backend_file_get_changes; - - backend_class->is_loaded = e_cal_backend_file_is_loaded; - backend_class->start_query = e_cal_backend_file_start_query; - backend_class->get_mode = e_cal_backend_file_get_mode; - backend_class->set_mode = e_cal_backend_file_set_mode; - - backend_class->internal_get_default_timezone = e_cal_backend_file_internal_get_default_timezone; - backend_class->internal_get_timezone = e_cal_backend_file_internal_get_timezone; -} - - -/** - * e_cal_backend_file_get_type: - * @void: - * - * Registers the #ECalBackendFile class if necessary, and returns the type ID - * associated to it. - * - * Return value: The type ID of the #ECalBackendFile class. - **/ -GType -e_cal_backend_file_get_type (void) -{ - static GType e_cal_backend_file_type = 0; - - if (!e_cal_backend_file_type) { - static GTypeInfo info = { - sizeof (ECalBackendFileClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_backend_file_class_init, - NULL, NULL, - sizeof (ECalBackendFile), - 0, - (GInstanceInitFunc) e_cal_backend_file_init - }; - e_cal_backend_file_type = g_type_register_static (E_TYPE_CAL_BACKEND_SYNC, - "ECalBackendFile", &info, 0); - } - - return e_cal_backend_file_type; -} - -void -e_cal_backend_file_set_file_name (ECalBackendFile *cbfile, const char *file_name) -{ - ECalBackendFilePrivate *priv; - - g_return_if_fail (cbfile != NULL); - g_return_if_fail (E_IS_CAL_BACKEND_FILE (cbfile)); - g_return_if_fail (file_name != NULL); - - priv = cbfile->priv; - - if (priv->file_name) - g_free (priv->file_name); - - priv->file_name = g_strdup (file_name); -} - -const char * -e_cal_backend_file_get_file_name (ECalBackendFile *cbfile) -{ - ECalBackendFilePrivate *priv; - - g_return_val_if_fail (cbfile != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_BACKEND_FILE (cbfile), NULL); - - priv = cbfile->priv; - - return priv->file_name; -} - -ECalBackendSyncStatus -e_cal_backend_file_reload (ECalBackendFile *cbfile) -{ - ECalBackendFilePrivate *priv; - char *str_uri; - ECalBackendSyncStatus status; - - priv = cbfile->priv; - - str_uri = get_uri_string (E_CAL_BACKEND (cbfile)); - if (!str_uri) - return GNOME_Evolution_Calendar_OtherError; - - if (access (str_uri, R_OK) == 0) { - status = reload_cal (cbfile, str_uri); - if (access (str_uri, W_OK) != 0) - priv->read_only = TRUE; - } else { - status = GNOME_Evolution_Calendar_NoSuchCal; - } - - g_free (str_uri); - return status; -} diff --git a/calendar/backends/file/e-cal-backend-file.h b/calendar/backends/file/e-cal-backend-file.h deleted file mode 100644 index 482059d13..000000000 --- a/calendar/backends/file/e-cal-backend-file.h +++ /dev/null @@ -1,67 +0,0 @@ -/* Evolution calendar - iCalendar file backend - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_BACKEND_FILE_H -#define E_CAL_BACKEND_FILE_H - -#include <libedata-cal/e-cal-backend-sync.h> - -G_BEGIN_DECLS - - - -#define E_TYPE_CAL_BACKEND_FILE (e_cal_backend_file_get_type ()) -#define E_CAL_BACKEND_FILE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_BACKEND_FILE, \ - ECalBackendFile)) -#define E_CAL_BACKEND_FILE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_BACKEND_FILE, \ - ECalBackendFileClass)) -#define E_IS_CAL_BACKEND_FILE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_BACKEND_FILE)) -#define E_IS_CAL_BACKEND_FILE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_BACKEND_FILE)) - -typedef struct _ECalBackendFile ECalBackendFile; -typedef struct _ECalBackendFileClass ECalBackendFileClass; - -typedef struct _ECalBackendFilePrivate ECalBackendFilePrivate; - -struct _ECalBackendFile { - ECalBackendSync backend; - - /* Private data */ - ECalBackendFilePrivate *priv; -}; - -struct _ECalBackendFileClass { - ECalBackendSyncClass parent_class; -}; - -GType e_cal_backend_file_get_type (void); - -void e_cal_backend_file_set_file_name (ECalBackendFile *cbfile, - const char *file_name); -const char *e_cal_backend_file_get_file_name (ECalBackendFile *cbfile); - -ECalBackendSyncStatus e_cal_backend_file_reload (ECalBackendFile *cbfile); - - - -G_END_DECLS - -#endif diff --git a/calendar/backends/groupwise/.cvsignore b/calendar/backends/groupwise/.cvsignore deleted file mode 100644 index 19c6c0c2a..000000000 --- a/calendar/backends/groupwise/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -Makefile -Makefile.in -create-account -soap-test
\ No newline at end of file diff --git a/calendar/backends/groupwise/Makefile.am b/calendar/backends/groupwise/Makefile.am deleted file mode 100644 index 4cfd28966..000000000 --- a/calendar/backends/groupwise/Makefile.am +++ /dev/null @@ -1,31 +0,0 @@ -INCLUDES = \ - -DG_LOG_DOMAIN=\"libecalbackendgroupwise\" \ - -I$(top_srcdir) \ - -I$(top_builddir) \ - -I$(top_srcdir)/calendar \ - -I$(top_builddir)/calendar \ - -I$(top_srcdir)/calendar/backends/file \ - -I$(top_builddir)/calendar/backends/file \ - -I$(top_srcdir)/calendar/libical/src \ - -I$(top_builddir)/calendar/libical/src \ - -I$(top_srcdir)/calendar/libical/src/libical \ - -I$(top_builddir)/calendar/libical/src/libical \ - -I$(top_srcdir)/servers/groupwise \ - -I$(top_builddir)/servers/groupwise \ - $(EVOLUTION_CALENDAR_CFLAGS) \ - $(SOUP_CFLAGS) \ - $(DEBUG_CFLAGS) - -noinst_LTLIBRARIES = libecalbackendgroupwise.la - -libecalbackendgroupwise_la_SOURCES = \ - e-cal-backend-groupwise.c \ - e-cal-backend-groupwise.h \ - e-cal-backend-groupwise-utils.c \ - e-cal-backend-groupwise-utils.h - -libecalbackendgroupwise_la_LIBADD = \ - $(top_builddir)/calendar/libedata-cal/libedata-cal.la \ - $(top_builddir)/calendar/backends/file/libecalbackendfile.la \ - $(top_builddir)/servers/groupwise/libegroupwise.la \ - $(SOUP_LIBS) diff --git a/calendar/backends/groupwise/TODO b/calendar/backends/groupwise/TODO deleted file mode 100644 index 15726f86f..000000000 --- a/calendar/backends/groupwise/TODO +++ /dev/null @@ -1,141 +0,0 @@ -Things to do and people working on it -------------------------------------- - -Step 1 - Infrastructure - - 1.1 DONE - Create SOAP management API in libsoup, in soup-soap-message.[ch] - to manage messages, and soup-soap-response.[ch] to manage responses - from the server. - - 1.2 DONE - Implement interface to Groupwise server, in - e-d-s/calendar/backends/groupwise/e-gw-connection.[ch], to manage - the connections to the server, and e-gw-message.[ch] for utility - functions to easily create SOAP messages to be sent to the server. - - 1.3 DONE - Implement login/logout to server, e_gw_connection_login and - e_gw_connection_logout, being called from e_cal_backend_groupwise_open - - 1.4 Map error codes returned in the "status" SOAP type to our - EGwConnectionStatus. This is in e-gw-connection.c#parse_response_status. - We need the list of status codes returned by the server from the GW team. - - 1.5 DONE - Write script/program to easily add an account until we have the configuration - GUI - -Step 2 - Basic functionality - - 2.1 DONE - Make the ECalBackendGroupwise class use ECalBackendCache, so that after - first connecting to a server we can keep the calendar in the cache - - 2.2 DONE - Implement retrieval of objects, that will be saved to the cache. This is - probably best done by listening to modifications on the server, and updating - the cache whenever a change is made on the server. On the first connection, - we should probably retrieve all objects, or at least their UIDs. - This involves implementing the following methods on the backend: - - Implement e_cal_backend_groupwise_get_default_object, which - should return an empty object with the minimal required fields - (if any) the server might need. - - Implement e_cal_backend_groupwise_get_object, which must - retrieve the specified object from the cache, or from the server - if it's still not in the cache. - - Implement e_cal_backend_groupwise_get_timezone, which must - return a VTIMEZONE object representing the required timezone. - The server should have a list of available timezones, if not, - we can use libical's built-in timezones. - - 2.3 DONE - Retrieve information about connection : when loging to the server, we get, in - the loginResponse response, some information about the user being connected. - From that we can retrieve some information needed to implement the following - backend methods: - - Implement e_cal_backend_groupwise_is_read_only, which tells the - caller whether the given calendar is read only or not. If read only, - the GUI will disable all modifications-related options. - - Implement e_cal_backend_groupwise_get_cal_address, which returns - the associated email address with this calendar. This is the email - address of the user that opened the calendar. - - Implement e_cal_backend_groupwise_get_ldap_attribute - - Implement e_cal_backend_groupwise_get_alarm_email_address, which - returns the email address to use when sending alarms. - - Implement e_cal_backend_groupwise_get_static_capabilities, which - returns a list of the capabilities of the backend. Those capabilities - are listed in e-cal-backend.h - - 2.4 Implement modification of objects on the server. This involves adding, - removing and updating objects (either tasks, events or timezones) and - implementing the following methods on the backend: - - Implement e_cal_backend_groupwise_add_timezone, which adds - a VTIMEZONE to the calendar/tasks folder. - - Implement e_cal_backend_groupwise_set_default_timezone, which - sets the default timezone to use when no timezone is given. This - should probably also change the default timezone on the server, not - only locally. - - Implement e_cal_backend_groupwise_discard_alarm, which is used - to let the backend do whatever it needs to do in order to discard - an alarm. We probably need to do nothing here, apart from updating - the object on the server with the alarm removed (already removed by - the GUI). - - Implement e_cal_backend_groupwise_create_object, which is used - by clients to add new objects to the calendar/tasks folder. - - Implement e_cal_backend_groupwise_modify_object, used to modify - an already existing object on the server. If the object does not - exist, it must return an error, and not try to add the object. - - Implement e_cal_backend_groupwise_remove_object, which removes - an object from the server. - - Implement e_cal_backend_groupwise_receive_objects, used for iMIP/iTIP. - It should act more or less like modify/create_object. If it's an - external invitation, the event should be added to the calendar. If - it's a reply to an existing meeting, the related event should be - updated. - - Implement e_cal_backend_groupwise_send_objects, which lets the - server send a meeting invitation in whatever means it's got. - When sending modifications to the server, only deltas (the fields that have - been modified) are sent, so we should compare the objects with the cache - and get the deltas out of that. When a successful update is made to the - server, the cache must be updated. - - 2.5 DONE - Implement queries to the server. This involves implementing the following - backend methods: - - Implement e_cal_backend_groupwise_get_object_list, which returns - a list of objects that match a given regular expression. - - Implement e_cal_backend_groupwise_start_query, which makes the - backend start a query asynchronously. - - Implement e_cal_backend_groupwise_get_changes, which returns - a list of changes done to the calendar since a given date. For - this, we should probably use the same method the file backend - uses. - The question remaining here is what to do with the queries. Since we are - keeping a cache, I guess we should make all queries against the cache, instead - of contacting the server for each query, or making a cache of queries, like we - had in Evolution 1.4. - - 2.6 Free/Busy. This is the implementation of the e_cal_backend_groupwise_get_free_busy - method on the backend. - - 2.7 DONE - Addition/removal of calendars. The backend should be able to create new calendars - when the _open method is called with 'only_if_exists' set to FALSE. In that case, - it should create the new calendar, and add the new source to the calendar sources - tree. Make sure the new-calendar dialog should call that method (e_cal_open) to tell the - backend to create the calendar. - Also, the e_cal_backend_groupwise_remove method should be implemented to allow the - removal of those calendars. - - 2.8 Implement configuration of GW accounts. - -Step 3 - Extra - - 3.1 DONE - Offline/Online mode: - - Implement e_cal_backend_groupwise_get_mode, which returns the current - online/offline mode of the backend. - - Implement e_cal_backend_groupwise_set_mode, used by clients to - change the online/offline status of the backend. When going offline, - the backend should synchronize its local copy, and when going back - online, synchronize back all changes made to the local cache. To - determine the set of changes, we can use a similar method to the one - used for the get_changes method. - - 3.2 Folder properties. Each calendar/tasks folder should be configurable from the - UI. The source selector widget will display a 'Properties' menu item in the - popup menu which will show up a dialog that allows the user to change the folder - properties (name, permissions, whatever). We need to decide on how this is done, - since the GUI should not know anything about Groupwise. - diff --git a/calendar/backends/groupwise/e-cal-backend-groupwise-utils.c b/calendar/backends/groupwise/e-cal-backend-groupwise-utils.c deleted file mode 100644 index 4ac916c89..000000000 --- a/calendar/backends/groupwise/e-cal-backend-groupwise-utils.c +++ /dev/null @@ -1,824 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - * Authors : - * JP Rosevear <jpr@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * Copyright 2003, Novell, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - * USA - */ - -#include <string.h> -#include <e-gw-connection.h> -#include <e-gw-message.h> -#include "e-cal-backend-groupwise-utils.h" - -static EGwItem * -set_properties_from_cal_component (EGwItem *item, ECalComponent *comp, const icaltimezone *default_zone) -{ - const char *uid, *location; - ECalComponentDateTime dt; - ECalComponentClassification classif; - ECalComponentTransparency transp; - ECalComponentText text; - int *priority; - GSList *slist, *sl; - icalproperty *prop; - struct icaltimetype itt_utc; - - /* first set specific properties */ - switch (e_cal_component_get_vtype (comp)) { - case E_CAL_COMPONENT_EVENT : - e_gw_item_set_item_type (item, E_GW_ITEM_TYPE_APPOINTMENT); - - /* transparency */ - e_cal_component_get_transparency (comp, &transp); - if (transp == E_CAL_COMPONENT_TRANSP_OPAQUE) - e_gw_item_set_accept_level (item, E_GW_ITEM_ACCEPT_LEVEL_BUSY); - else - e_gw_item_set_accept_level (item, NULL); - - /* location */ - e_cal_component_get_location (comp, &location); - e_gw_item_set_place (item, location); - - /* alarms */ - if (e_cal_component_has_alarms (comp)) { - ECalComponentAlarm *alarm; - ECalComponentAlarmTrigger trigger; - int duration; - GList *l = e_cal_component_get_alarm_uids (comp); - - alarm = e_cal_component_get_alarm (comp, l->data); - e_cal_component_alarm_get_trigger (alarm, &trigger); - duration = abs (icaldurationtype_as_int (trigger.u.rel_duration)); - e_gw_item_set_trigger (item, duration); - } - - /* get_attendee_list from cal comp and convert into - * egwitemrecipient and set it on recipient_list*/ - if (e_cal_component_has_attendees (comp)) { - GSList *attendee_list, *recipient_list = NULL, *al; - - e_cal_component_get_attendee_list (comp, &attendee_list); - for (al = attendee_list; al != NULL; al = al->next) { - ECalComponentAttendee *attendee = (ECalComponentAttendee *) al->data; - EGwItemRecipient *recipient = g_new0 (EGwItemRecipient, 1); - - /* len (MAILTO:) + 1 = 7 */ - recipient->email = g_strdup (attendee->value + 7); - if (attendee->cn != NULL) - recipient->display_name = g_strdup (attendee->cn); - if (attendee->role == ICAL_ROLE_REQPARTICIPANT) - recipient->type = E_GW_ITEM_RECIPIENT_TO; - else if (attendee->role == ICAL_ROLE_OPTPARTICIPANT) - recipient->type = E_GW_ITEM_RECIPIENT_CC; - else recipient->type = E_GW_ITEM_RECIPIENT_NONE; - - recipient_list = g_slist_append (recipient_list, recipient); - } - e_gw_item_set_recipient_list (item, recipient_list); - } - - /* end date */ - e_cal_component_get_dtend (comp, &dt); - if (dt.value) { - if (!icaltime_get_timezone (*dt.value)) - icaltime_set_timezone (dt.value, default_zone); - itt_utc = icaltime_convert_to_zone (*dt.value, icaltimezone_get_utc_timezone ()); - e_gw_item_set_end_date (item, icaltime_as_ical_string (itt_utc)); - } - - break; - - case E_CAL_COMPONENT_TODO : - e_gw_item_set_item_type (item, E_GW_ITEM_TYPE_TASK); - - /* due date */ - e_cal_component_get_due (comp, &dt); - if (dt.value) { - if (!icaltime_get_timezone (*dt.value)) - icaltime_set_timezone (dt.value, default_zone); - itt_utc = icaltime_convert_to_zone (*dt.value, icaltimezone_get_utc_timezone ()); - e_gw_item_set_due_date (item, icaltime_as_ical_string (itt_utc)); - } - - /* priority */ - priority = NULL; - e_cal_component_get_priority (comp, &priority); - if (priority && *priority) { - if (*priority >= 7) - e_gw_item_set_priority (item, E_GW_ITEM_PRIORITY_LOW); - else if (*priority >= 5) - e_gw_item_set_priority (item, E_GW_ITEM_PRIORITY_STANDARD); - else if (*priority >= 3) - e_gw_item_set_priority (item, E_GW_ITEM_PRIORITY_HIGH); - else - e_gw_item_set_priority (item, NULL); - - e_cal_component_free_priority (priority); - } - - /* completed */ - e_cal_component_get_completed (comp, &dt.value); - if (dt.value) { - e_gw_item_set_completed (item, TRUE); - } else - e_gw_item_set_completed (item, FALSE); - - break; - - default : - g_object_unref (item); - return NULL; - } - - /* set common properties */ - /* GW server ID */ - prop = icalcomponent_get_first_property (e_cal_component_get_icalcomponent (comp), - ICAL_X_PROPERTY); - while (prop) { - const char *x_name, *x_val; - - x_name = icalproperty_get_x_name (prop); - x_val = icalproperty_get_x (prop); - if (!strcmp (x_name, "X-EVOLUTION-GROUPWISE-ID")) { - e_gw_item_set_id (item, x_val); - break; - } - - prop = icalcomponent_get_next_property (e_cal_component_get_icalcomponent (comp), - ICAL_X_PROPERTY); - } - - /* UID */ - e_cal_component_get_uid (comp, &uid); - e_gw_item_set_icalid (item, uid); - - /* subject */ - e_cal_component_get_summary (comp, &text); - e_gw_item_set_subject (item, text.value); - - /* description */ - e_cal_component_get_description_list (comp, &slist); - if (slist) { - GString *str = g_string_new (""); - - for (sl = slist; sl != NULL; sl = sl->next) { - ECalComponentText *pt = sl->data; - - if (pt && pt->value) - str = g_string_append (str, pt->value); - } - - e_gw_item_set_message (item, (const char *) str->str); - - g_string_free (str, TRUE); - e_cal_component_free_text_list (slist); - } - - /* start date */ - e_cal_component_get_dtstart (comp, &dt); - if (dt.value) { - if (!icaltime_get_timezone (*dt.value)) - icaltime_set_timezone (dt.value, default_zone); - itt_utc = icaltime_convert_to_zone (*dt.value, icaltimezone_get_utc_timezone ()); - e_gw_item_set_start_date (item, icaltime_as_ical_string (itt_utc)); - } else if (e_gw_item_get_item_type (item) == E_GW_ITEM_TYPE_APPOINTMENT) { - /* appointments need the start date property */ - g_object_unref (item); - return NULL; - } - - /* creation date */ - e_cal_component_get_created (comp, &dt.value); - if (dt.value) { - if (!icaltime_get_timezone (*dt.value)) - icaltime_set_timezone (dt.value, default_zone); - itt_utc = icaltime_convert_to_zone (*dt.value, icaltimezone_get_utc_timezone ()); - e_gw_item_set_creation_date (item, icaltime_as_ical_string (itt_utc)); - } else { - struct icaltimetype itt; - - e_cal_component_get_dtstamp (comp, &itt); - e_gw_item_set_creation_date (item, icaltime_as_ical_string (itt)); - } - - /* classification */ - e_cal_component_get_classification (comp, &classif); - switch (classif) { - case E_CAL_COMPONENT_CLASS_PUBLIC : - e_gw_item_set_classification (item, E_GW_ITEM_CLASSIFICATION_PUBLIC); - break; - case E_CAL_COMPONENT_CLASS_PRIVATE : - e_gw_item_set_classification (item, E_GW_ITEM_CLASSIFICATION_PRIVATE); - break; - case E_CAL_COMPONENT_CLASS_CONFIDENTIAL : - e_gw_item_set_classification (item, E_GW_ITEM_CLASSIFICATION_CONFIDENTIAL); - break; - default : - e_gw_item_set_classification (item, NULL); - } - - return item; -} - -EGwItem * -e_gw_item_new_from_cal_component (const char *container, const icaltimezone *default_zone, ECalComponent *comp) -{ - EGwItem *item; - - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), NULL); - - item = e_gw_item_new_empty (); - e_gw_item_set_container_id (item, container); - - return set_properties_from_cal_component (item, comp, default_zone); -} - -ECalComponent * -e_gw_item_to_cal_component (EGwItem *item, icaltimezone *default_zone) -{ - ECalComponent *comp; - ECalComponentText text; - ECalComponentDateTime dt; - const char *description; - char *t; - struct icaltimetype itt, itt_utc; - int priority; - int alarm_duration; - GSList *recipient_list, *rl, *attendee_list = NULL; - EGwItemType item_type; - - g_return_val_if_fail (E_IS_GW_ITEM (item), NULL); - - comp = e_cal_component_new (); - - item_type = e_gw_item_get_item_type (item); - - if (item_type == E_GW_ITEM_TYPE_APPOINTMENT) - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_EVENT); - else if (item_type == E_GW_ITEM_TYPE_TASK) - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_TODO); - else { - g_object_unref (comp); - return NULL; - } - - /* set common properties */ - /* GW server ID */ - description = e_gw_item_get_id (item); - if (description) { - icalproperty *icalprop; - - icalprop = icalproperty_new_x (description); - icalproperty_set_x_name (icalprop, "X-EVOLUTION-GROUPWISE-ID"); - icalcomponent_add_property (e_cal_component_get_icalcomponent (comp), icalprop); - } - - /* UID */ - e_cal_component_set_uid (comp, e_gw_item_get_icalid (item)); - - /* summary */ - text.value = e_gw_item_get_subject (item); - text.altrep = NULL; - e_cal_component_set_summary (comp, &text); - - /* description */ - description = e_gw_item_get_message (item); - if (description) { - GSList l; - - text.value = description; - text.altrep = NULL; - l.data = &text; - l.next = NULL; - - e_cal_component_set_description_list (comp, &l); - } - - /* creation date */ - t = e_gw_item_get_creation_date (item); - itt_utc = icaltime_from_string (t); - if (!icaltime_get_timezone (itt_utc)) - icaltime_set_timezone (&itt_utc, icaltimezone_get_utc_timezone()); - if (default_zone) { - itt = icaltime_convert_to_zone (itt_utc, default_zone); - icaltime_set_timezone (&itt, default_zone); - e_cal_component_set_created (comp, &itt); - e_cal_component_set_dtstamp (comp, &itt); - - } else { - e_cal_component_set_created (comp, &itt_utc); - e_cal_component_set_dtstamp (comp, &itt_utc); - } - g_free (t); - - - - /* start date */ - /* should i duplicate here ? */ - t = e_gw_item_get_start_date (item); - if (t) { - itt_utc = icaltime_from_string (t); - if (!icaltime_get_timezone (itt_utc)) - icaltime_set_timezone (&itt_utc, icaltimezone_get_utc_timezone()); - if (default_zone) { - itt = icaltime_convert_to_zone (itt_utc, default_zone); - icaltime_set_timezone (&itt, default_zone); - dt.value = &itt; - dt.tzid = icaltimezone_get_tzid (default_zone); - } else { - dt.value = &itt_utc; - dt.tzid = g_strdup ("UTC"); - } - e_cal_component_set_dtstart (comp, &dt); - g_free (t); - } - else - return NULL; - - - /* classification */ - description = e_gw_item_get_classification (item); - if (description) { - if (strcmp (description, E_GW_ITEM_CLASSIFICATION_PUBLIC) == 0) - e_cal_component_set_classification (comp, E_CAL_COMPONENT_CLASS_PUBLIC); - else if (strcmp (description, E_GW_ITEM_CLASSIFICATION_PRIVATE) == 0) - e_cal_component_set_classification (comp, E_CAL_COMPONENT_CLASS_PRIVATE); - else if (strcmp (description, E_GW_ITEM_CLASSIFICATION_CONFIDENTIAL) == 0) - e_cal_component_set_classification (comp, E_CAL_COMPONENT_CLASS_CONFIDENTIAL); - else - e_cal_component_set_classification (comp, E_CAL_COMPONENT_CLASS_NONE); - } else - e_cal_component_set_classification (comp, E_CAL_COMPONENT_CLASS_NONE); - - /* set specific properties */ - switch (item_type) { - case E_GW_ITEM_TYPE_APPOINTMENT : - /* transparency */ - description = e_gw_item_get_accept_level (item); - if (description && - (!strcmp (description, E_GW_ITEM_ACCEPT_LEVEL_BUSY) || - !strcmp (description, E_GW_ITEM_ACCEPT_LEVEL_OUT_OF_OFFICE))) - e_cal_component_set_transparency (comp, E_CAL_COMPONENT_TRANSP_OPAQUE); - else - e_cal_component_set_transparency (comp, E_CAL_COMPONENT_TRANSP_TRANSPARENT); - - /* location */ - e_cal_component_set_location (comp, e_gw_item_get_place (item)); - - /* end date */ - t = e_gw_item_get_end_date (item); - if (t) { - itt_utc = icaltime_from_string (t); - if (!icaltime_get_timezone (itt_utc)) - icaltime_set_timezone (&itt_utc, icaltimezone_get_utc_timezone()); - if (default_zone) { - itt = icaltime_convert_to_zone (itt_utc, default_zone); - icaltime_set_timezone (&itt, default_zone); - dt.value = &itt; - dt.tzid = icaltimezone_get_tzid (default_zone); - } else { - dt.value = &itt_utc; - dt.tzid = g_strdup ("UTC"); - } - - e_cal_component_set_dtend (comp, &dt); - } - - - /* alarms*/ - /* we negate the value as GW supports only "before" the start of event alarms */ - alarm_duration = 0 - e_gw_item_get_trigger (item); - if (alarm_duration != 0) { - ECalComponentAlarm *alarm; - ECalComponentAlarmTrigger trigger; - - alarm = e_cal_component_alarm_new (); - e_cal_component_alarm_set_action (alarm, E_CAL_COMPONENT_ALARM_DISPLAY); - trigger.type = E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_START; - trigger.u.rel_duration = (struct icaldurationtype) icaldurationtype_from_int (alarm_duration); - e_cal_component_alarm_set_trigger (alarm, trigger); - e_cal_component_add_alarm (comp, alarm); - } - - recipient_list = e_gw_item_get_recipient_list (item); - if (recipient_list != NULL) { - for (rl = recipient_list; rl != NULL; rl = rl->next) { - EGwItemRecipient *recipient = (EGwItemRecipient *) rl->data; - ECalComponentAttendee *attendee = g_new0 (ECalComponentAttendee, 1); - - attendee->cn = g_strdup (recipient->display_name); - attendee->value = g_strconcat("MAILTO:", recipient->email, NULL); - if (recipient->type == E_GW_ITEM_RECIPIENT_TO) - attendee->role = ICAL_ROLE_REQPARTICIPANT; - else if (recipient->type == E_GW_ITEM_RECIPIENT_CC) - attendee->role = ICAL_ROLE_OPTPARTICIPANT; - else - attendee->role = ICAL_ROLE_NONE; - /* FIXME needs a server fix on the interface - * for getting cutype and the status */ - attendee->cutype = ICAL_CUTYPE_INDIVIDUAL; - attendee->status = ICAL_PARTSTAT_NEEDSACTION; - attendee_list = g_slist_append (attendee_list, attendee); - } - - e_cal_component_set_attendee_list (comp, attendee_list); - } - - break; - case E_GW_ITEM_TYPE_TASK : - /* due date */ - t = e_gw_item_get_due_date (item); - if (!t) - break; - itt_utc = icaltime_from_string (t); - if (!icaltime_get_timezone (itt_utc)) - icaltime_set_timezone (&itt_utc, icaltimezone_get_utc_timezone()); - if (default_zone) { - itt = icaltime_convert_to_zone (itt_utc, default_zone); - icaltime_set_timezone (&itt, default_zone); - dt.value = &itt; - dt.tzid = icaltimezone_get_tzid (default_zone); - } else { - dt.value = &itt_utc; - dt.tzid = g_strdup ("UTC"); - } - e_cal_component_set_due (comp, &dt); - break; - - /* priority */ - description = e_gw_item_get_priority (item); - if (description) { - if (!strcmp (description, E_GW_ITEM_PRIORITY_STANDARD)) - priority = 5; - else if (!strcmp (description, E_GW_ITEM_PRIORITY_HIGH)) - priority = 3; - else - priority = 7; - } else - priority = 7; - - e_cal_component_set_priority (comp, &priority); - - /* FIXME: EGwItem's completed is a boolean */ - break; - default : - return NULL; - } - - return comp; -} - -EGwConnectionStatus -e_gw_connection_send_appointment (EGwConnection *cnc, const char *container, icaltimezone *default_zone, ECalComponent *comp, char **id) -{ - EGwItem *item; - EGwConnectionStatus status; - - g_return_val_if_fail (E_IS_GW_CONNECTION (cnc), E_GW_CONNECTION_STATUS_INVALID_CONNECTION); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), E_GW_CONNECTION_STATUS_INVALID_OBJECT); - - item = e_gw_item_new_from_cal_component (container, default_zone, comp); - e_gw_item_set_container_id (item, container); - status = e_gw_connection_send_item (cnc, item, id); - g_object_unref (item); - - return status; -} - -static EGwConnectionStatus -start_freebusy_session (EGwConnection *cnc, GList *users, - time_t start, time_t end, const char **session) -{ - SoupSoapMessage *msg; - SoupSoapResponse *response; - EGwConnectionStatus status; - SoupSoapParameter *param; - GList *l; - icaltimetype icaltime; - icaltimezone *utc; - const char *start_date, *end_date; - - if (users == NULL) - return E_GW_CONNECTION_STATUS_INVALID_OBJECT; - - /* build the SOAP message */ - msg = e_gw_message_new_with_header (e_gw_connection_get_uri (cnc), - e_gw_connection_get_session_id (cnc), - "startFreeBusySessionRequest"); - /* FIXME users is just a buch of user names - associate it with uid, - * email id apart from the name*/ - - soup_soap_message_start_element (msg, "users", NULL, NULL); - for ( l = users; l != NULL; l = g_list_next (l)) { - soup_soap_message_start_element (msg, "user", NULL, NULL); - e_gw_message_write_string_parameter (msg, "email", NULL, l->data); - soup_soap_message_end_element (msg); - } - - soup_soap_message_end_element (msg); - - - utc = icaltimezone_get_utc_timezone (); - icaltime = icaltime_from_timet_with_zone (start, FALSE, utc); - start_date = icaltime_as_ical_string (icaltime); - - icaltime = icaltime_from_timet_with_zone (end, FALSE, utc); - end_date = icaltime_as_ical_string (icaltime); - - e_gw_message_write_string_parameter (msg, "startDate", NULL, start_date); - e_gw_message_write_string_parameter (msg, "endDate", NULL, end_date); - - e_gw_message_write_footer (msg); - - /* send message to server */ - response = e_gw_connection_send_message (cnc, msg); - if (!response) { - g_object_unref (msg); - return E_GW_CONNECTION_STATUS_INVALID_RESPONSE; - } - - status = e_gw_connection_parse_response_status (response); - if (status != E_GW_CONNECTION_STATUS_OK) - { - g_object_unref (msg); - g_object_unref (response); - return status; - } - - /* if status is OK - parse result, return the list */ - param = soup_soap_response_get_first_parameter_by_name (response, "freeBusySessionId"); - if (!param) { - g_object_unref (response); - g_object_unref (msg); - return E_GW_CONNECTION_STATUS_INVALID_RESPONSE; - } - - *session = soup_soap_parameter_get_string_value (param); - /* free memory */ - g_object_unref (response); - g_object_unref (msg); - - return status; -} - -static EGwConnectionStatus -close_freebusy_session (EGwConnection *cnc, const char *session) -{ - SoupSoapMessage *msg; - SoupSoapResponse *response; - EGwConnectionStatus status; - - /* build the SOAP message */ - msg = e_gw_message_new_with_header (e_gw_connection_get_uri (cnc), - e_gw_connection_get_session_id (cnc), - "closeFreeBusySessionRequest"); - e_gw_message_write_string_parameter (msg, "freeBusySessionId", NULL, session); - e_gw_message_write_footer (msg); - - /* send message to server */ - response = e_gw_connection_send_message (cnc, msg); - if (!response) { - g_object_unref (msg); - return E_GW_CONNECTION_STATUS_INVALID_RESPONSE; - } - - status = e_gw_connection_parse_response_status (response); - - g_object_unref (msg); - g_object_unref (response); - return status; -} - -EGwConnectionStatus -e_gw_connection_get_freebusy_info (EGwConnection *cnc, GList *users, time_t start, time_t end, GList **freebusy) -{ - SoupSoapMessage *msg; - SoupSoapResponse *response; - EGwConnectionStatus status; - SoupSoapParameter *param, *subparam; - const char *session; - - g_return_val_if_fail (E_IS_GW_CONNECTION (cnc), E_GW_CONNECTION_STATUS_INVALID_CONNECTION); - - /* Perform startFreeBusySession */ - status = start_freebusy_session (cnc, users, start, end, &session); - /*FIXME log error messages */ - if (status != E_GW_CONNECTION_STATUS_OK) - return status; - - /* getFreeBusy */ - /* build the SOAP message */ - msg = e_gw_message_new_with_header (e_gw_connection_get_uri (cnc), - e_gw_connection_get_session_id (cnc), - "getFreeBusyRequest"); - e_gw_message_write_string_parameter (msg, "freeBusySessionId", NULL, session); - e_gw_message_write_footer (msg); - - /* send message to server */ - response = e_gw_connection_send_message (cnc, msg); - if (!response) { - g_object_unref (msg); - return E_GW_CONNECTION_STATUS_INVALID_RESPONSE; - } - - status = e_gw_connection_parse_response_status (response); - if (status != E_GW_CONNECTION_STATUS_OK) { - g_object_unref (msg); - g_object_unref (response); - return status; - } - - /* FIXME the FreeBusyStats are not used currently. */ - param = soup_soap_response_get_first_parameter_by_name (response, "freeBusyInfo"); - if (!param) { - g_object_unref (response); - g_object_unref (msg); - return E_GW_CONNECTION_STATUS_INVALID_RESPONSE; - } - - for (subparam = soup_soap_parameter_get_first_child_by_name (param, "user"); - subparam != NULL; - subparam = soup_soap_parameter_get_next_child_by_name (subparam, "user")) { - SoupSoapParameter *param_blocks, *subparam_block, *tmp; - const char *uuid = NULL, *email = NULL, *name = NULL; - ECalComponent *comp; - ECalComponentAttendee attendee; - GSList *attendee_list = NULL; - icalcomponent *icalcomp = NULL; - - tmp = soup_soap_parameter_get_first_child_by_name (subparam, "email"); - if (tmp) - email = soup_soap_parameter_get_string_value (tmp); - tmp = soup_soap_parameter_get_first_child_by_name (subparam, "uuid"); - if (tmp) - uuid = soup_soap_parameter_get_string_value (tmp); - tmp = soup_soap_parameter_get_first_child_by_name (subparam, "displayName"); - if (tmp) - name = soup_soap_parameter_get_string_value (tmp); - - comp = e_cal_component_new (); - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_FREEBUSY); - e_cal_component_commit_sequence (comp); - icalcomp = e_cal_component_get_icalcomponent (comp); - - memset (&attendee, 0, sizeof (ECalComponentAttendee)); - if (name) - attendee.cn = name; - if (email) - attendee.value = email; - - attendee.cutype = ICAL_CUTYPE_INDIVIDUAL; - attendee.role = ICAL_ROLE_REQPARTICIPANT; - attendee.status = ICAL_PARTSTAT_NEEDSACTION; - - /* XXX the uuid is not currently used. hence it is - * discarded */ - - attendee_list = g_slist_append (attendee_list, &attendee); - - e_cal_component_set_attendee_list (comp, attendee_list); - - - param_blocks = soup_soap_parameter_get_first_child_by_name (subparam, "blocks"); - if (!param_blocks) { - g_object_unref (response); - g_object_unref (msg); - return E_GW_CONNECTION_STATUS_INVALID_RESPONSE; - } - - for (subparam_block = soup_soap_parameter_get_first_child_by_name (param_blocks, "block"); - subparam_block != NULL; - subparam_block = soup_soap_parameter_get_next_child_by_name (subparam_block, "block")) { - - /* process each block and create ECal free/busy components.*/ - SoupSoapParameter *tmp; - struct icalperiodtype ipt; - icalproperty *icalprop; - icaltimetype itt; - time_t t; - const char *start, *end, *accept_level; - - memset (&ipt, 0, sizeof (struct icalperiodtype)); - tmp = soup_soap_parameter_get_first_child_by_name (subparam_block, "startDate"); - if (tmp) { - start = soup_soap_parameter_get_string_value (tmp); - t = e_gw_connection_get_date_from_string (start); - itt = icaltime_from_timet (t, 0); - ipt.start = itt; - } - - tmp = soup_soap_parameter_get_first_child_by_name (subparam_block, "endDate"); - if (tmp) { - end = soup_soap_parameter_get_string_value (tmp); - t = e_gw_connection_get_date_from_string (end); - itt = icaltime_from_timet (t, 0); - ipt.end = itt; - } - icalprop = icalproperty_new_freebusy (ipt); - - tmp = soup_soap_parameter_get_first_child_by_name (subparam_block, "acceptLevel"); - if (tmp) { - accept_level = soup_soap_parameter_get_string_value (tmp); - if (!strcmp (accept_level, "Busy")) - icalproperty_set_parameter_from_string (icalprop, "FBTYPE", "BUSY"); - else if (!strcmp (accept_level, "Tentative")) - icalproperty_set_parameter_from_string (icalprop, "FBTYPE", "BUSYTENTATIVE"); - else if (!strcmp (accept_level, "OutOfOffice")) - icalproperty_set_parameter_from_string (icalprop, "FBTYPE", "BUSYUNAVAILABLE"); - else if (!strcmp (accept_level, "Free")) - icalproperty_set_parameter_from_string (icalprop, "FBTYPE", "FREE"); - } - icalcomponent_add_property(icalcomp, icalprop); - - } - - e_cal_component_commit_sequence (comp); - *freebusy = g_list_append (*freebusy, g_strdup (e_cal_component_get_as_string (comp))); - g_object_unref (comp); - } - - g_object_unref (msg); - g_object_unref (response); - - /* closeFreeBusySession*/ - return close_freebusy_session (cnc, session); -} - -#define SET_DELTA(fieldname) G_STMT_START{ \ - fieldname = e_gw_item_get_##fieldname (item); \ - cache_##fieldname = e_gw_item_get_##fieldname (cache_item); \ - if ( cache_##fieldname ) { \ - if (!fieldname ) \ - e_gw_item_set_change (item, E_GW_ITEM_CHANGE_TYPE_DELETE, #fieldname, cache_##fieldname );\ - else if (strcmp ( fieldname, cache_##fieldname )) \ - e_gw_item_set_change (item, E_GW_ITEM_CHANGE_TYPE_UPDATE, #fieldname, fieldname );\ - } \ - else if ( fieldname ) \ - e_gw_item_set_change (item, E_GW_ITEM_CHANGE_TYPE_ADD, #fieldname, fieldname ); \ - }G_STMT_END - -void -e_gw_item_set_changes (EGwItem *item, EGwItem *cache_item) -{ - char *subject, *cache_subject; - char *message, *cache_message; - const char *classification, *cache_classification; - char *accept_level, *cache_accept_level; - char *place, *cache_place; - char *priority, *cache_priority; - int trigger, cache_trigger; - - /* TODO assert the types of the items are the same */ - - SET_DELTA(subject); - SET_DELTA(message); - SET_DELTA(classification); - - if (strcmp (e_gw_item_get_start_date (item), e_gw_item_get_start_date (cache_item))) - e_gw_item_set_change (item, E_GW_ITEM_CHANGE_TYPE_UPDATE, "startDate", e_gw_item_get_start_date (item)); - - if ( e_gw_item_get_item_type (item) == E_GW_ITEM_TYPE_APPOINTMENT) { - - if (strcmp (e_gw_item_get_end_date (item), e_gw_item_get_end_date (cache_item))) - e_gw_item_set_change (item, E_GW_ITEM_CHANGE_TYPE_UPDATE, "endDate", e_gw_item_get_end_date (item)); - SET_DELTA(accept_level); - SET_DELTA(place); - trigger = e_gw_item_get_trigger (item); - cache_trigger = e_gw_item_get_trigger (cache_item); - if (cache_trigger) { - if (!trigger) - e_gw_item_set_change (item, E_GW_ITEM_CHANGE_TYPE_DELETE, "alarm", &cache_trigger); - else if (trigger != cache_trigger) - e_gw_item_set_change (item, E_GW_ITEM_CHANGE_TYPE_UPDATE, "alarm", &trigger); - } - else if (trigger) - e_gw_item_set_change (item, E_GW_ITEM_CHANGE_TYPE_ADD, "alarm", &trigger); - } - else if ( e_gw_item_get_item_type (item) == E_GW_ITEM_TYPE_TASK) { - gboolean completed, cache_completed; - - if (strcmp (e_gw_item_get_due_date (item), e_gw_item_get_due_date (cache_item))) - e_gw_item_set_change (item, E_GW_ITEM_CHANGE_TYPE_UPDATE, "dueDate", e_gw_item_get_due_date (item)); - completed = e_gw_item_get_completed (item); - cache_completed = e_gw_item_get_completed (cache_item); - if ((completed && !cache_completed) || (!completed && cache_completed)) - e_gw_item_set_change (item, E_GW_ITEM_CHANGE_TYPE_UPDATE, "completed", &completed); - SET_DELTA (priority); - } -} diff --git a/calendar/backends/groupwise/e-cal-backend-groupwise-utils.h b/calendar/backends/groupwise/e-cal-backend-groupwise-utils.h deleted file mode 100644 index c44b30092..000000000 --- a/calendar/backends/groupwise/e-cal-backend-groupwise-utils.h +++ /dev/null @@ -1,48 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - * Authors : - * JP Rosevear <jpr@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * Copyright 2003, Novell, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - * USA - */ - -#ifndef E_CAL_BACKEND_GROUPWISE_UTILS_H -#define E_CAL_BACKEND_GROUPWISE_UTILS_H - -#include <e-gw-connection.h> -#include <libecal/e-cal-component.h> - -G_BEGIN_DECLS - -/* - * Items management - */ -EGwItem *e_gw_item_new_from_cal_component (const char *container, const icaltimezone *default_zone, ECalComponent *comp); -ECalComponent *e_gw_item_to_cal_component (EGwItem *item, icaltimezone *default_zone); -void e_gw_item_set_changes (EGwItem *item, EGwItem *cached_item); - -/* - * Connection-related utility functions - */ -EGwConnectionStatus e_gw_connection_send_appointment (EGwConnection *cnc, const char *container, icaltimezone *default_zone, ECalComponent *comp, char **id); -EGwConnectionStatus e_gw_connection_get_freebusy_info (EGwConnection *cnc, GList *users, - time_t start, time_t end, GList **freebusy); - -G_END_DECLS - -#endif diff --git a/calendar/backends/groupwise/e-cal-backend-groupwise.c b/calendar/backends/groupwise/e-cal-backend-groupwise.c deleted file mode 100644 index 623943f39..000000000 --- a/calendar/backends/groupwise/e-cal-backend-groupwise.c +++ /dev/null @@ -1,1421 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - * Authors : - * JP Rosevear <jpr@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * Copyright 2003, Novell, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - * USA - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <string.h> -#include <libgnomevfs/gnome-vfs-uri.h> -#include <libgnomevfs/gnome-vfs.h> -#include <bonobo/bonobo-i18n.h> -#include <libedataserver/e-xml-hash-utils.h> -#include <libedataserver/e-url.h> -#include <libedata-cal/e-cal-backend-cache.h> -#include <libedata-cal/e-cal-backend-util.h> -#include <libecal/e-cal-component.h> -#include <libecal/e-cal-time-util.h> -#include "e-cal-backend-groupwise.h" -#include "e-cal-backend-groupwise-utils.h" -#include "e-gw-connection.h" - -/* Private part of the CalBackendGroupwise structure */ -struct _ECalBackendGroupwisePrivate { - /* A mutex to control access to the private structure */ - GMutex *mutex; - EGwConnection *cnc; - ECalBackendCache *cache; - gboolean read_only; - char *uri; - char *username; - char *password; - char *container_id; - CalMode mode; - icaltimezone *default_zone; - - /* fields for storing info while offline */ - char *user_email; -}; - -static void e_cal_backend_groupwise_dispose (GObject *object); -static void e_cal_backend_groupwise_finalize (GObject *object); - -#define PARENT_TYPE E_TYPE_CAL_BACKEND_SYNC -static ECalBackendClass *parent_class = NULL; - -/* Time interval in milliseconds for obtaining changes from server and refresh the cache. */ -#define CACHE_REFRESH_INTERVAL 600000 - -/* Initialy populate the cache from the server */ -static EGwConnectionStatus -populate_cache (ECalBackendGroupwise *cbgw) -{ - ECalBackendGroupwisePrivate *priv; - EGwConnectionStatus status; - ECalComponent *comp; - const char *uid; - char *rid; - GList *list = NULL, *l; - - priv = cbgw->priv; - - /* get all the objects from the server */ - status = e_gw_connection_get_items (priv->cnc, priv->container_id, "recipients message", NULL, &list); - if (status != E_GW_CONNECTION_STATUS_OK) { - g_list_free (list); - e_cal_backend_groupwise_notify_error_code (cbgw, status); - return status; - } - - for (l = list; l != NULL; l = g_list_next(l)) { - EGwItem *item; - - item = E_GW_ITEM (l->data); - comp = e_gw_item_to_cal_component (item, priv->default_zone); - g_object_unref (item); - if (E_IS_CAL_COMPONENT (comp)) { - e_cal_component_commit_sequence (comp); - e_cal_component_get_uid (comp, &uid); - rid = g_strdup (e_cal_component_get_recurid_as_string (comp)); - e_cal_backend_cache_put_component (priv->cache, comp); - g_free (rid); - g_object_unref (comp); - } - } - - g_list_free (list); - - return E_GW_CONNECTION_STATUS_OK; -} - -static GnomeVFSURI * -convert_uri (const char *gw_uri) -{ - char *real_uri; - GnomeVFSURI *vuri; - - if (strncmp ("groupwise://", gw_uri, sizeof ("groupwise://") - 1)) - return NULL; - - real_uri = g_strconcat ("http://", gw_uri + sizeof ("groupwise://") - 1, NULL); - vuri = gnome_vfs_uri_new ((const char *) real_uri); - - g_free (real_uri); - - return vuri; -} - -static EGwConnectionStatus -get_deltas (gpointer handle) -{ - ECalBackendGroupwise *cbgw; - EGwConnection *cnc; - ECalBackendCache *cache; - EGwConnectionStatus status; - GSList *deletes = NULL, *updates = NULL, *adds = NULL, *l; - - cbgw = (ECalBackendGroupwise *) handle; - cnc = cbgw->priv->cnc; - cache = cbgw->priv->cache; - - /* Call e-gw-connection_get_deltas*/ - status = e_gw_connection_get_deltas (cnc, &adds, &deletes, &updates); - - if (status != E_GW_CONNECTION_STATUS_OK) { - e_cal_backend_groupwise_notify_error_code (cbgw, status); - return status; - } - - if (deletes) { - for (l = deletes; l != NULL; l = g_slist_next(l)) { - if (!e_cal_backend_cache_remove_component (cache, (char *)l->data, NULL)) - g_message ("Could not remove %s", (char *)l->data); - } - } - - if (adds) { - for (l = adds; l != NULL; l = g_slist_next (l)) { - EGwItem *item = (EGwItem *) l->data; - ECalComponent *comp = e_gw_item_to_cal_component (item, cbgw->priv->default_zone); - if (!comp) - g_message ("Invalid component returned"); - else if (!e_cal_backend_cache_put_component (cache, comp)) - g_message ("Could not add the component"); - } - } - - if (updates) { - for (l = updates; l != NULL; l = g_slist_next (l)) { - EGwItem *item = (EGwItem *) l->data; - ECalComponent *comp = e_cal_backend_cache_get_component (cache, e_gw_item_get_id (item), NULL); - if (!comp) /* FIXME Error in updates. Skipping the element*/ - continue; - /* FIXME currently, just overwrite the fields with the - * update.*/ - e_cal_backend_cache_remove_component (cache, e_gw_item_get_id (item), NULL); - e_cal_backend_cache_put_component (cache, e_gw_item_to_cal_component (item, cbgw->priv->default_zone)); - } - } - - return E_GW_CONNECTION_STATUS_OK; -} - - -static char* -form_uri (ESource *source) -{ - char *uri; - const char *port; - char *formed_uri; - EUri *parsed_uri; - - uri = e_source_get_uri (source); - if (uri == NULL) - return NULL; - - parsed_uri = e_uri_new (uri); - if (parsed_uri == NULL) - return NULL; - - port = e_source_get_property (source, "port"); - if (port == NULL) - port = "7181"; - - formed_uri = g_strconcat ("http://", parsed_uri->host,":", port, "/soap", NULL ); - - g_free (uri); - e_uri_free (parsed_uri); - return formed_uri; - -} - -static ECalBackendSyncStatus -connect_to_server (ECalBackendGroupwise *cbgw) -{ - char *real_uri; - ECalBackendGroupwisePrivate *priv; - EGwConnectionStatus cnc_status; - ESource *source; - - priv = cbgw->priv; - - source = e_cal_backend_get_source (E_CAL_BACKEND (cbgw)); - real_uri = NULL; - if (source) - real_uri = form_uri (source); - - if (!real_uri) { - e_cal_backend_notify_error (E_CAL_BACKEND (cbgw), _("Invalid server URI")); - return GNOME_Evolution_Calendar_NoSuchCal; - } else { - /* create connection to server */ - priv->cnc = e_gw_connection_new ( - real_uri, - priv->username, - priv->password); - - g_free (real_uri); - - /* As of now we are assuming that logged in user has write rights to calender */ - /* we need to read actual rights from server when we implement proxy user access */ - cbgw->priv->read_only = FALSE; - - if (E_IS_GW_CONNECTION (priv->cnc)) { - icalcomponent_kind kind; - - /* get the ID for the container */ - if (priv->container_id) - g_free (priv->container_id); - - kind = e_cal_backend_get_kind (E_CAL_BACKEND (cbgw)); - if (kind == ICAL_VEVENT_COMPONENT) { - priv->container_id = g_strdup (e_gw_connection_get_container_id (priv->cnc, "Calendar")); - e_source_set_name (e_cal_backend_get_source (E_CAL_BACKEND (cbgw)), _("Calendar")); - } else if (kind == ICAL_VTODO_COMPONENT) { - priv->container_id = g_strdup (e_gw_connection_get_container_id (priv->cnc, "Calendar")); - e_source_set_name (e_cal_backend_get_source (E_CAL_BACKEND (cbgw)), _("Calendar")); - } else - priv->container_id = NULL; - - - /* Populate the cache for the first time.*/ - /* start a timed polling thread set to 10 minutes*/ - cnc_status = populate_cache (cbgw); - if (cnc_status != E_GW_CONNECTION_STATUS_OK) { - g_object_unref (priv->cnc); - priv->cnc = NULL; - g_warning (G_STRLOC ": Could not populate the cache"); - return GNOME_Evolution_Calendar_PermissionDenied; - } else { - g_object_ref (priv->cnc); - g_object_ref (priv->cache); - g_timeout_add (CACHE_REFRESH_INTERVAL, (GSourceFunc) get_deltas, (gpointer) cbgw); - priv->mode = CAL_MODE_REMOTE; - return GNOME_Evolution_Calendar_Success; - } - } else { - e_cal_backend_notify_error (E_CAL_BACKEND (cbgw), _("Authentication failed")); - return GNOME_Evolution_Calendar_AuthenticationFailed; - } - } - - return GNOME_Evolution_Calendar_Success; -} - -/* Dispose handler for the file backend */ -static void -e_cal_backend_groupwise_dispose (GObject *object) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - - cbgw = E_CAL_BACKEND_GROUPWISE (object); - priv = cbgw->priv; - - if (G_OBJECT_CLASS (parent_class)->dispose) - (* G_OBJECT_CLASS (parent_class)->dispose) (object); -} - -/* Finalize handler for the file backend */ -static void -e_cal_backend_groupwise_finalize (GObject *object) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL_BACKEND_GROUPWISE (object)); - - cbgw = E_CAL_BACKEND_GROUPWISE (object); - priv = cbgw->priv; - - /* Clean up */ - if (priv->mutex) { - g_mutex_free (priv->mutex); - priv->mutex = NULL; - } - - if (priv->cnc) { - g_object_unref (priv->cnc); - priv->cnc = NULL; - } - - if (priv->cache) { - g_object_unref (priv->cache); - priv->cache = NULL; - } - - if (priv->username) { - g_free (priv->username); - priv->username = NULL; - } - - if (priv->password) { - g_free (priv->password); - priv->password = NULL; - } - - if (priv->container_id) { - g_free (priv->container_id); - priv->container_id = NULL; - } - - if (priv->user_email) { - g_free (priv->user_email); - priv->user_email = NULL; - } - - g_free (priv); - cbgw->priv = NULL; - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - -/* Calendar backend methods */ - -/* Is_read_only handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_is_read_only (ECalBackendSync *backend, EDataCal *cal, gboolean *read_only) -{ - ECalBackendGroupwise *cbgw; - - cbgw = E_CAL_BACKEND_GROUPWISE(backend); - *read_only = cbgw->priv->read_only; - - return GNOME_Evolution_Calendar_Success; -} - -/* return email address of the person who opened the calender */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_get_cal_address (ECalBackendSync *backend, EDataCal *cal, char **address) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - - cbgw = E_CAL_BACKEND_GROUPWISE(backend); - priv = cbgw->priv; - - if (priv->mode == CAL_MODE_REMOTE) { - if (priv->user_email) - g_free (priv->user_email); - - priv->user_email = g_strdup (e_gw_connection_get_user_email (cbgw->priv->cnc)); - } - - *address = g_strdup (priv->user_email); - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_groupwise_get_ldap_attribute (ECalBackendSync *backend, EDataCal *cal, char **attribute) -{ - /* ldap attribute is specific to Sun ONE connector to get free busy information*/ - /* retun NULL here as group wise backend know how to get free busy information */ - - *attribute = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_groupwise_get_alarm_email_address (ECalBackendSync *backend, EDataCal *cal, char **address) -{ - /*group wise does not support email based alarms */ - - *address = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_groupwise_get_static_capabilities (ECalBackendSync *backend, EDataCal *cal, char **capabilities) -{ - *capabilities = g_strdup (CAL_STATIC_CAPABILITY_NO_EMAIL_ALARMS "," \ - CAL_STATIC_CAPABILITY_ONE_ALARM_ONLY "," \ - CAL_STATIC_CAPABILITY_REMOVE_ALARMS "," \ - CAL_STATIC_CAPABILITY_NO_THISANDPRIOR "," \ - CAL_STATIC_CAPABILITY_NO_THISANDFUTURE "," \ - CAL_STATIC_CAPABILITY_SAVE_SCHEDULES); - - return GNOME_Evolution_Calendar_Success; -} - - - -/* Open handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_open (ECalBackendSync *backend, EDataCal *cal, gboolean only_if_exists, - const char *username, const char *password) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - ECalBackendSyncStatus status; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - g_mutex_lock (priv->mutex); - - /* create the local cache */ - /* FIXME: if the cache already exists - read it and get deltas. */ - if (priv->cache) { - g_mutex_unlock (priv->mutex); - g_object_ref (priv->cnc); - g_object_ref (priv->cache); - g_timeout_add (CACHE_REFRESH_INTERVAL, (GSourceFunc) get_deltas, (gpointer) cbgw); - priv->mode = CAL_MODE_REMOTE; - - return GNOME_Evolution_Calendar_Success; - } - - priv->cache = e_cal_backend_cache_new (e_cal_backend_get_uri (E_CAL_BACKEND (backend))); - if (!priv->cache) { - g_mutex_unlock (priv->mutex); - e_cal_backend_notify_error (E_CAL_BACKEND (cbgw), _("Could not create cache file")); - return GNOME_Evolution_Calendar_OtherError; - } - - cbgw->priv->read_only = FALSE; - priv->mode = CAL_MODE_LOCAL; - priv->username = g_strdup (username); - priv->password = g_strdup (password); - - - /* read the default timezone*/ - priv->default_zone = e_cal_backend_cache_get_default_timezone (priv->cache); - /* FIXME: no need to set it online here when we implement the online/offline stuff correctly */ - status = connect_to_server (cbgw); - - g_mutex_unlock (priv->mutex); - - return status; -} - -static ECalBackendSyncStatus -e_cal_backend_groupwise_remove (ECalBackendSync *backend, EDataCal *cal) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - g_mutex_lock (priv->mutex); - - /* remove the cache */ - if (priv->cache) - e_file_cache_remove (E_FILE_CACHE (priv->cache)); - - g_mutex_unlock (priv->mutex); - - return GNOME_Evolution_Calendar_Success; -} - -/* is_loaded handler for the file backend */ -static gboolean -e_cal_backend_groupwise_is_loaded (ECalBackend *backend) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - return priv->cache ? TRUE : FALSE; -} - -/* is_remote handler for the file backend */ -static CalMode -e_cal_backend_groupwise_get_mode (ECalBackend *backend) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - return priv->mode; -} - -/* Set_mode handler for the file backend */ -static void -e_cal_backend_groupwise_set_mode (ECalBackend *backend, CalMode mode) -{ - ECalBackendSyncStatus status; - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - if (priv->mode == mode) { - e_cal_backend_notify_mode (backend, GNOME_Evolution_Calendar_CalListener_MODE_SET, - cal_mode_to_corba (mode)); - return; - } - - g_mutex_lock (priv->mutex); - - switch (mode) { - case CAL_MODE_REMOTE :/* go online */ - status = connect_to_server (cbgw); - if (status == GNOME_Evolution_Calendar_Success) - e_cal_backend_notify_mode (backend, - GNOME_Evolution_Calendar_CalListener_MODE_SET, - GNOME_Evolution_Calendar_MODE_REMOTE); - else - e_cal_backend_notify_mode (backend, - GNOME_Evolution_Calendar_CalListener_MODE_NOT_SET, - GNOME_Evolution_Calendar_MODE_REMOTE); - break; - case CAL_MODE_LOCAL : /* go offline */ - /* FIXME: make sure we update the cache before closing the connection */ - g_object_unref (priv->cnc); - priv->cnc = NULL; - priv->mode = CAL_MODE_LOCAL; - - e_cal_backend_notify_mode (backend, GNOME_Evolution_Calendar_CalListener_MODE_SET, - GNOME_Evolution_Calendar_MODE_LOCAL); - break; - default : - e_cal_backend_notify_mode (backend, GNOME_Evolution_Calendar_CalListener_MODE_NOT_SUPPORTED, - cal_mode_to_corba (mode)); - } - - g_mutex_unlock (priv->mutex); -} - -static ECalBackendSyncStatus -e_cal_backend_groupwise_get_default_object (ECalBackendSync *backend, EDataCal *cal, char **object) -{ - - ECalComponent *comp; - - comp = e_cal_component_new (); - - switch (e_cal_backend_get_kind (E_CAL_BACKEND (backend))) { - case ICAL_VEVENT_COMPONENT: - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_EVENT); - break; - case ICAL_VTODO_COMPONENT: - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_TODO); - break; - default: - g_object_unref (comp); - return GNOME_Evolution_Calendar_ObjectNotFound; - } - - *object = e_cal_component_get_as_string (comp); - g_object_unref (comp); - - return GNOME_Evolution_Calendar_Success; -} - -/* Get_object_component handler for the groupwise backend */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_get_object (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *rid, char **object) -{ - ECalComponent *comp; - ECalBackendGroupwisePrivate *priv; - ECalBackendGroupwise *cbgw = (ECalBackendGroupwise *) backend; - - g_return_val_if_fail (E_IS_CAL_BACKEND_GROUPWISE (cbgw), GNOME_Evolution_Calendar_OtherError); - - priv = cbgw->priv; - - g_mutex_lock (priv->mutex); - - /* search the object in the cache */ - comp = e_cal_backend_cache_get_component (priv->cache, uid, rid); - if (comp) { - g_mutex_unlock (priv->mutex); - if (e_cal_backend_get_kind (E_CAL_BACKEND (backend)) == - icalcomponent_isa (e_cal_component_get_icalcomponent (comp))) - *object = e_cal_component_get_as_string (comp); - else - *object = NULL; - - g_object_unref (comp); - - return *object ? GNOME_Evolution_Calendar_Success : GNOME_Evolution_Calendar_ObjectNotFound; - } - - g_mutex_unlock (priv->mutex); - - /* callers will never have a uuid that is in server but not in cache */ - return GNOME_Evolution_Calendar_ObjectNotFound; -} - -/* Get_timezone_object handler for the groupwise backend */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_get_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid, char **object) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - icaltimezone *zone; - icalcomponent *icalcomp; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - g_return_val_if_fail (tzid != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - if (!strcmp (tzid, "UTC")) { - zone = icaltimezone_get_utc_timezone (); - } else { - zone = icaltimezone_get_builtin_timezone_from_tzid (tzid); - if (!zone) - return GNOME_Evolution_Calendar_ObjectNotFound; - } - - icalcomp = icaltimezone_get_component (zone); - if (!icalcomp) - return GNOME_Evolution_Calendar_InvalidObject; - - *object = g_strdup (icalcomponent_as_ical_string (icalcomp)); - - return GNOME_Evolution_Calendar_Success; -} - -/* Add_timezone handler for the groupwise backend */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_add_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzobj) -{ - icalcomponent *tz_comp; - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - - cbgw = (ECalBackendGroupwise *) backend; - - g_return_val_if_fail (E_IS_CAL_BACKEND_GROUPWISE (cbgw), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (tzobj != NULL, GNOME_Evolution_Calendar_OtherError); - - priv = cbgw->priv; - - tz_comp = icalparser_parse_string (tzobj); - if (!tz_comp) - return GNOME_Evolution_Calendar_InvalidObject; - - if (icalcomponent_isa (tz_comp) == ICAL_VTIMEZONE_COMPONENT) { - icaltimezone *zone; - - zone = icaltimezone_new (); - icaltimezone_set_component (zone, tz_comp); - if (e_cal_backend_cache_put_timezone (priv->cache, zone) == FALSE) { - icaltimezone_free (zone, 1); - return GNOME_Evolution_Calendar_OtherError; - } - icaltimezone_free (zone, 1); - } - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_groupwise_set_default_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - /* Set the default timezone to it. */ - priv->default_zone = icaltimezone_get_builtin_timezone_from_tzid (tzid); - - /* FIXME write it into the cache*/ - e_cal_backend_cache_put_default_timezone (priv->cache, priv->default_zone); - - return GNOME_Evolution_Calendar_Success; -} - -/* Get_objects_in_range handler for the groupwise backend */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_get_object_list (ECalBackendSync *backend, EDataCal *cal, const char *sexp, GList **objects) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - GList *components, *l; - ECalBackendSExp *cbsexp; - gboolean search_needed = TRUE; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - g_mutex_lock (priv->mutex); - - g_message (G_STRLOC ": Getting object list (%s)", sexp); - - if (!strcmp (sexp, "#t")) - search_needed = FALSE; - - cbsexp = e_cal_backend_sexp_new (sexp); - if (!cbsexp) { - g_mutex_unlock (priv->mutex); - return GNOME_Evolution_Calendar_InvalidQuery; - } - - *objects = NULL; - components = e_cal_backend_cache_get_components (priv->cache); - for (l = components; l != NULL; l = l->next) { - ECalComponent *comp = E_CAL_COMPONENT (l->data); - - if (e_cal_backend_get_kind (E_CAL_BACKEND (backend)) == - icalcomponent_isa (e_cal_component_get_icalcomponent (comp))) { - if ((!search_needed) || - (e_cal_backend_sexp_match_comp (cbsexp, comp, E_CAL_BACKEND (backend)))) { - *objects = g_list_append (*objects, e_cal_component_get_as_string (comp)); - } - } - } - - g_list_foreach (components, (GFunc) g_object_unref, NULL); - g_list_free (components); - - g_mutex_unlock (priv->mutex); - - return GNOME_Evolution_Calendar_Success; -} - -/* get_query handler for the groupwise backend */ -static void -e_cal_backend_groupwise_start_query (ECalBackend *backend, EDataCalView *query) -{ - ECalBackendSyncStatus status; - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - GList *objects = NULL; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - g_message (G_STRLOC ": Starting query (%s)", e_data_cal_view_get_text (query)); - - status = e_cal_backend_groupwise_get_object_list (E_CAL_BACKEND_SYNC (backend), NULL, - e_data_cal_view_get_text (query), &objects); - if (status != GNOME_Evolution_Calendar_Success) { - e_data_cal_view_notify_done (query, status); - return; - } - - /* notify listeners of all objects */ - if (objects) { - e_data_cal_view_notify_objects_added (query, (const GList *) objects); - - /* free memory */ - g_list_foreach (objects, (GFunc) g_free, NULL); - g_list_free (objects); - } - - e_data_cal_view_notify_done (query, GNOME_Evolution_Calendar_Success); -} - -/* Get_free_busy handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_get_free_busy (ECalBackendSync *backend, EDataCal *cal, GList *users, - time_t start, time_t end, GList **freebusy) -{ - EGwConnectionStatus status; - ECalBackendGroupwise *cbgw; - EGwConnection *cnc; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - cnc = cbgw->priv->cnc; - - status = e_gw_connection_get_freebusy_info (cnc, users, start, end, freebusy); - if (status != E_GW_CONNECTION_STATUS_OK) - return GNOME_Evolution_Calendar_OtherError; - return GNOME_Evolution_Calendar_Success; -} - -typedef struct { - ECalBackendGroupwise *backend; - icalcomponent_kind kind; - GList *deletes; - EXmlHash *ehash; -} ECalBackendGroupwiseComputeChangesData; - -static void -e_cal_backend_groupwise_compute_changes_foreach_key (const char *key, gpointer data) -{ - ECalBackendGroupwiseComputeChangesData *be_data = data; - - if (!e_cal_backend_cache_get_component (be_data->backend->priv->cache, key, NULL)) { - ECalComponent *comp; - - comp = e_cal_component_new (); - if (be_data->kind == ICAL_VTODO_COMPONENT) - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_TODO); - else - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_EVENT); - - e_cal_component_set_uid (comp, key); - be_data->deletes = g_list_prepend (be_data->deletes, e_cal_component_get_as_string (comp)); - - e_xmlhash_remove (be_data->ehash, key); - } -} - -static ECalBackendSyncStatus -e_cal_backend_groupwise_compute_changes (ECalBackendGroupwise *cbgw, const char *change_id, - GList **adds, GList **modifies, GList **deletes) -{ - ECalBackendSyncStatus status; - ECalBackendCache *cache; - char *filename; - EXmlHash *ehash; - ECalBackendGroupwiseComputeChangesData be_data; - GList *i, *list = NULL; - gchar *unescaped_uri; - - cache = cbgw->priv->cache; - - /* FIXME Will this always work? */ - unescaped_uri = gnome_vfs_unescape_string (cbgw->priv->uri, ""); - filename = g_strdup_printf ("%s-%s.db", unescaped_uri, change_id); - ehash = e_xmlhash_new (filename); - g_free (filename); - g_free (unescaped_uri); - - status = e_cal_backend_groupwise_get_object_list (E_CAL_BACKEND_SYNC (cbgw), NULL, NULL, &list); - if (status != GNOME_Evolution_Calendar_Success) - return status; - - /* Calculate adds and modifies */ - for (i = list; i != NULL; i = g_list_next (i)) { - const char *uid; - char *calobj; - - e_cal_component_get_uid (i->data, &uid); - calobj = e_cal_component_get_as_string (i->data); - - g_assert (calobj != NULL); - - /* check what type of change has occurred, if any */ - switch (e_xmlhash_compare (ehash, uid, calobj)) { - case E_XMLHASH_STATUS_SAME: - break; - case E_XMLHASH_STATUS_NOT_FOUND: - *adds = g_list_prepend (*adds, g_strdup (calobj)); - e_xmlhash_add (ehash, uid, calobj); - break; - case E_XMLHASH_STATUS_DIFFERENT: - *modifies = g_list_prepend (*modifies, g_strdup (calobj)); - e_xmlhash_add (ehash, uid, calobj); - break; - } - - g_free (calobj); - } - - /* Calculate deletions */ - be_data.backend = cbgw; - be_data.kind = e_cal_backend_get_kind (E_CAL_BACKEND (cbgw)); - be_data.deletes = NULL; - be_data.ehash = ehash; - e_xmlhash_foreach_key (ehash, (EXmlHashFunc)e_cal_backend_groupwise_compute_changes_foreach_key, &be_data); - - *deletes = be_data.deletes; - - e_xmlhash_write (ehash); - e_xmlhash_destroy (ehash); - - return GNOME_Evolution_Calendar_Success; -} - -/* Get_changes handler for the groupwise backend */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_get_changes (ECalBackendSync *backend, EDataCal *cal, const char *change_id, - GList **adds, GList **modifies, GList **deletes) -{ - ECalBackendGroupwise *cbgw; - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - - g_return_val_if_fail (E_IS_CAL_BACKEND_GROUPWISE (cbgw), GNOME_Evolution_Calendar_InvalidObject); - g_return_val_if_fail (change_id != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - return e_cal_backend_groupwise_compute_changes (cbgw, change_id, adds, modifies, deletes); - -} - -/* Discard_alarm handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_discard_alarm (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *auid) -{ - return GNOME_Evolution_Calendar_OtherError; -} - -static icaltimezone * -e_cal_backend_groupwise_internal_get_default_timezone (ECalBackend *backend) -{ - /* Groupwise server maintains data in UTC */ - return icaltimezone_get_utc_timezone (); -} - -static icaltimezone * -e_cal_backend_groupwise_internal_get_timezone (ECalBackend *backend, const char *tzid) -{ - return icaltimezone_get_utc_timezone (); -} - -static ECalBackendSyncStatus -e_cal_backend_groupwise_create_object (ECalBackendSync *backend, EDataCal *cal, char **calobj, char **uid) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - icalcomponent *icalcomp; - ECalComponent *comp; - EGwConnectionStatus status; - char *server_uid = NULL; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - g_return_val_if_fail (E_IS_CAL_BACKEND_GROUPWISE (cbgw), GNOME_Evolution_Calendar_InvalidObject); - g_return_val_if_fail (calobj != NULL && *calobj != NULL, GNOME_Evolution_Calendar_InvalidObject); - - /* check the component for validity */ - icalcomp = icalparser_parse_string (*calobj); - if (!icalcomp) - return GNOME_Evolution_Calendar_InvalidObject; - - if (e_cal_backend_get_kind (E_CAL_BACKEND (backend)) != icalcomponent_isa (icalcomp)) { - icalcomponent_free (icalcomp); - return GNOME_Evolution_Calendar_InvalidObject; - } - - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, icalcomp); - - /* check if the object exists */ - switch (priv->mode) { - case CAL_MODE_ANY : - case CAL_MODE_REMOTE : - /* when online, send the item to the server */ - status = e_gw_connection_send_appointment (priv->cnc, priv->container_id, priv->default_zone, comp, &server_uid); - if (status != E_GW_CONNECTION_STATUS_OK) { - g_object_unref (comp); - return GNOME_Evolution_Calendar_OtherError; - } - - if (server_uid) { - icalproperty *icalprop; - int i; - GString *str = g_string_new ("");; - - /* the ID returned by sendItemResponse includes the container ID of the - inbox folder, so we need to replace that with our container ID */ - for (i = 0; i < strlen (server_uid); i++) { - str = g_string_append_c (str, server_uid[i]); - if (server_uid[i] == ':') { - str = g_string_append (str, priv->container_id); - break; - } - } - - /* add the extra property to the component */ - icalprop = icalproperty_new_x (str->str); - icalproperty_set_x_name (icalprop, "X-EVOLUTION-GROUPWISE-ID"); - icalcomponent_add_property (e_cal_component_get_icalcomponent (comp), icalprop); - - g_string_free (str, TRUE); - g_free (server_uid); - } - - /* if successful, update the cache */ - case CAL_MODE_LOCAL : - /* in offline mode, we just update the cache */ - e_cal_backend_cache_put_component (priv->cache, comp); - break; - default : - break; - } - - *calobj = e_cal_component_get_as_string (comp); - - g_object_unref (comp); - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_groupwise_modify_object (ECalBackendSync *backend, EDataCal *cal, const char *calobj, - CalObjModType mod, char **old_object) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - icalcomponent *icalcomp; - ECalComponent *comp, *cache_comp; - EGwConnectionStatus status; - EGwItem *item, *cache_item; - - *old_object = NULL; - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - g_return_val_if_fail (E_IS_CAL_BACKEND_GROUPWISE (cbgw), GNOME_Evolution_Calendar_InvalidObject); - g_return_val_if_fail (calobj != NULL, GNOME_Evolution_Calendar_InvalidObject); - - /* check the component for validity */ - icalcomp = icalparser_parse_string (calobj); - if (!icalcomp) - return GNOME_Evolution_Calendar_InvalidObject; - - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, icalcomp); - item = e_gw_item_new_from_cal_component (priv->container_id, priv->default_zone, comp); - - /* check if the object exists */ - switch (priv->mode) { - case CAL_MODE_ANY : - case CAL_MODE_REMOTE : - /* when online, send the item to the server */ - cache_comp = e_cal_backend_cache_get_component (priv->cache, e_gw_item_get_icalid (item), NULL); - if (!cache_comp) { - g_message ("CRITICAL : Could not find the object in cache"); - return GNOME_Evolution_Calendar_ObjectNotFound; - } - - cache_item = e_gw_item_new_from_cal_component (priv->container_id, priv->default_zone, cache_comp); - e_gw_item_set_changes (item, cache_item); - g_object_unref (cache_comp); - - /* the second argument is redundant */ - status = e_gw_connection_modify_item (priv->cnc, e_gw_item_get_id (item), item); - if (status != E_GW_CONNECTION_STATUS_OK) { - g_object_unref (comp); - return GNOME_Evolution_Calendar_OtherError; - } - /* if successful, update the cache */ - - case CAL_MODE_LOCAL : - /* in offline mode, we just update the cache */ - e_cal_backend_cache_put_component (priv->cache, comp); - break; - default : - break; - } - - g_object_unref (comp); - - *old_object = g_strdup (calobj); - return GNOME_Evolution_Calendar_Success; -} - -/* Remove_object handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_remove_object (ECalBackendSync *backend, EDataCal *cal, - const char *uid, const char *rid, - CalObjModType mod, char **object) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - char *calobj = NULL; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - /* if online, remove the item from the server */ - if (priv->mode == CAL_MODE_REMOTE) { - ECalBackendSyncStatus status; - char *id_to_remove = NULL; - icalproperty *icalprop; - icalcomponent *icalcomp; - - status = e_cal_backend_groupwise_get_object (backend, cal, uid, rid, &calobj); - if (status != GNOME_Evolution_Calendar_Success) - return status; - - icalcomp = icalparser_parse_string (calobj); - if (!icalcomp) { - g_free (calobj); - return GNOME_Evolution_Calendar_InvalidObject; - } - - /* search the component for the X-EVOLUTION-GROUPWISE-ID property */ - icalprop = icalcomponent_get_first_property (icalcomp, ICAL_X_PROPERTY); - while (icalprop) { - const char *x_name, *x_val; - - x_name = icalproperty_get_x_name (icalprop); - x_val = icalproperty_get_x (icalprop); - if (!strcmp (x_name, "X-EVOLUTION-GROUPWISE-ID")) { - id_to_remove = x_val; - break; - } - - icalprop = icalcomponent_get_next_property (icalcomp, ICAL_X_PROPERTY); - } - - if (!id_to_remove) { - /* use the iCalId to remove the object */ - id_to_remove = uid; - } - - /* remove the object */ - status = e_gw_connection_remove_item (priv->cnc, priv->container_id, id_to_remove); - - icalcomponent_free (icalcomp); - if (status == E_GW_CONNECTION_STATUS_OK) { - /* remove the component from the cache */ - if (!e_cal_backend_cache_remove_component (priv->cache, uid, rid)) { - g_free (calobj); - return GNOME_Evolution_Calendar_ObjectNotFound; - } - *object = g_strdup (calobj); - g_free (calobj); - return GNOME_Evolution_Calendar_Success; - } else { - g_free (calobj); - return GNOME_Evolution_Calendar_OtherError; - } - } - - /* remove the component from the cache */ - if (!e_cal_backend_cache_remove_component (priv->cache, uid, rid)) { - g_free (calobj); - return GNOME_Evolution_Calendar_ObjectNotFound; - } - - *object = g_strdup (calobj); - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -receive_object (ECalBackendGroupwise *cbgw, EDataCal *cal, icalcomponent *icalcomp) -{ - ECalComponent *comp, *found_comp; - ECalBackendGroupwisePrivate *priv; - const char *uid, *rid; - char *comp_str; - ECalBackendSyncStatus status = GNOME_Evolution_Calendar_Success; - - priv = cbgw->priv; - - /* search the object in the cache */ - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, icalcomponent_new_clone (icalcomp)); - e_cal_component_get_uid (comp, &uid); - rid = e_cal_component_get_recurid_as_string (comp); - - comp_str = e_cal_component_get_as_string (comp); - - found_comp = e_cal_backend_cache_get_component (priv->cache, uid, rid); - if (found_comp) { - status = e_cal_backend_groupwise_modify_object (E_CAL_BACKEND_SYNC (cbgw), cal, comp_str, - CALOBJ_MOD_THIS, NULL); - } else - status = e_cal_backend_groupwise_create_object (E_CAL_BACKEND_SYNC (cbgw), cal, &comp_str, NULL); - - g_free (comp_str); - g_object_unref (comp); - - return status; -} - -/* Update_objects handler for the file backend. */ -static ECalBackendSyncStatus -e_cal_backend_groupwise_receive_objects (ECalBackendSync *backend, EDataCal *cal, const char *calobj) -{ - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - icalcomponent *icalcomp, *subcomp; - icalcomponent_kind kind; - ECalBackendSyncStatus status = GNOME_Evolution_Calendar_Success; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - icalcomp = icalparser_parse_string (calobj); - if (!icalcomp) - return GNOME_Evolution_Calendar_InvalidObject; - - kind = icalcomponent_isa (icalcomp); - if (kind == ICAL_VCALENDAR_COMPONENT) { - subcomp = icalcomponent_get_first_component (icalcomp, - e_cal_backend_get_kind (E_CAL_BACKEND (backend))); - while (subcomp) { - status = receive_object (cbgw, cal, subcomp); - if (status != GNOME_Evolution_Calendar_Success) - break; - subcomp = icalcomponent_get_next_component (icalcomp, - e_cal_backend_get_kind (E_CAL_BACKEND (backend))); - } - } else if (kind == e_cal_backend_get_kind (E_CAL_BACKEND (backend))) { - status = receive_object (cbgw, cal, icalcomp); - } else - status = GNOME_Evolution_Calendar_InvalidObject; - - icalcomponent_free (icalcomp); - - return status; -} - -static ECalBackendSyncStatus -send_object (ECalBackendGroupwise *cbgw, EDataCal *cal, icalcomponent *icalcomp) -{ - ECalComponent *comp; - ECalBackendGroupwisePrivate *priv; - ECalBackendSyncStatus status = GNOME_Evolution_Calendar_Success; - - priv = cbgw->priv; - - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, icalcomponent_new_clone (icalcomp)); - - switch (priv->mode) { - case CAL_MODE_ANY : - case CAL_MODE_REMOTE : - /* when online, send the item to the server */ - status = e_gw_connection_send_appointment (priv->cnc, priv->container_id, priv->default_zone, comp, NULL); - break; - case CAL_MODE_LOCAL : - /* in offline mode, we just update the cache */ - e_cal_backend_cache_put_component (priv->cache, comp); - break; - } - - g_object_unref (comp); - - return status; -} - -static ECalBackendSyncStatus -e_cal_backend_groupwise_send_objects (ECalBackendSync *backend, EDataCal *cal, const char *calobj, GList **users, - char **modified_calobj) -{ - ECalBackendSyncStatus status = GNOME_Evolution_Calendar_OtherError; - icalcomponent *icalcomp, *subcomp; - icalcomponent_kind kind; - ECalBackendGroupwise *cbgw; - ECalBackendGroupwisePrivate *priv; - - *users = NULL; - *modified_calobj = NULL; - - cbgw = E_CAL_BACKEND_GROUPWISE (backend); - priv = cbgw->priv; - - icalcomp = icalparser_parse_string (calobj); - if (!icalcomp) - return GNOME_Evolution_Calendar_InvalidObject; - - kind = icalcomponent_isa (icalcomp); - if (kind == ICAL_VCALENDAR_COMPONENT) { - subcomp = icalcomponent_get_first_component (icalcomp, - e_cal_backend_get_kind (E_CAL_BACKEND (backend))); - while (subcomp) { - status = send_object (cbgw, cal, subcomp); - if (status != GNOME_Evolution_Calendar_Success) - break; - subcomp = icalcomponent_get_next_component (icalcomp, - e_cal_backend_get_kind (E_CAL_BACKEND (backend))); - } - } else if (kind == e_cal_backend_get_kind (E_CAL_BACKEND (backend))) { - status = send_object (cbgw, cal, icalcomp); - } else - status = GNOME_Evolution_Calendar_InvalidObject; - - if (status == GNOME_Evolution_Calendar_Success) { - ECalComponent *comp; - - comp = e_cal_component_new (); - - if (e_cal_component_set_icalcomponent (comp, icalcomp)) { - e_cal_component_get_attendee_list (comp, users); - g_object_unref (comp); - } - *modified_calobj = g_strdup (calobj); - } - icalcomponent_free (icalcomp); - - return status; -} - - -/* Object initialization function for the file backend */ -static void -e_cal_backend_groupwise_init (ECalBackendGroupwise *cbgw, ECalBackendGroupwiseClass *class) -{ - ECalBackendGroupwisePrivate *priv; - - priv = g_new0 (ECalBackendGroupwisePrivate, 1); - - /* create the mutex for thread safety */ - priv->mutex = g_mutex_new (); - - cbgw->priv = priv; -} - -/* Class initialization function for the file backend */ -static void -e_cal_backend_groupwise_class_init (ECalBackendGroupwiseClass *class) -{ - GObjectClass *object_class; - ECalBackendClass *backend_class; - ECalBackendSyncClass *sync_class; - - object_class = (GObjectClass *) class; - backend_class = (ECalBackendClass *) class; - sync_class = (ECalBackendSyncClass *) class; - - parent_class = g_type_class_peek_parent (class); - - object_class->dispose = e_cal_backend_groupwise_dispose; - object_class->finalize = e_cal_backend_groupwise_finalize; - - sync_class->is_read_only_sync = e_cal_backend_groupwise_is_read_only; - sync_class->get_cal_address_sync = e_cal_backend_groupwise_get_cal_address; - sync_class->get_alarm_email_address_sync = e_cal_backend_groupwise_get_alarm_email_address; - sync_class->get_ldap_attribute_sync = e_cal_backend_groupwise_get_ldap_attribute; - sync_class->get_static_capabilities_sync = e_cal_backend_groupwise_get_static_capabilities; - sync_class->open_sync = e_cal_backend_groupwise_open; - sync_class->remove_sync = e_cal_backend_groupwise_remove; - sync_class->create_object_sync = e_cal_backend_groupwise_create_object; - sync_class->modify_object_sync = e_cal_backend_groupwise_modify_object; - sync_class->remove_object_sync = e_cal_backend_groupwise_remove_object; - sync_class->discard_alarm_sync = e_cal_backend_groupwise_discard_alarm; - sync_class->receive_objects_sync = e_cal_backend_groupwise_receive_objects; - sync_class->send_objects_sync = e_cal_backend_groupwise_send_objects; - sync_class->get_default_object_sync = e_cal_backend_groupwise_get_default_object; - sync_class->get_object_sync = e_cal_backend_groupwise_get_object; - sync_class->get_object_list_sync = e_cal_backend_groupwise_get_object_list; - sync_class->get_timezone_sync = e_cal_backend_groupwise_get_timezone; - sync_class->add_timezone_sync = e_cal_backend_groupwise_add_timezone; - sync_class->set_default_timezone_sync = e_cal_backend_groupwise_set_default_timezone; - sync_class->get_freebusy_sync = e_cal_backend_groupwise_get_free_busy; - sync_class->get_changes_sync = e_cal_backend_groupwise_get_changes; - - backend_class->is_loaded = e_cal_backend_groupwise_is_loaded; - backend_class->start_query = e_cal_backend_groupwise_start_query; - backend_class->get_mode = e_cal_backend_groupwise_get_mode; - backend_class->set_mode = e_cal_backend_groupwise_set_mode; - backend_class->internal_get_default_timezone = e_cal_backend_groupwise_internal_get_default_timezone; - backend_class->internal_get_timezone = e_cal_backend_groupwise_internal_get_timezone; -} - - -/** - * e_cal_backend_groupwise_get_type: - * @void: - * - * Registers the #ECalBackendGroupwise class if necessary, and returns the type ID - * associated to it. - * - * Return value: The type ID of the #ECalBackendGroupwise class. - **/ -GType -e_cal_backend_groupwise_get_type (void) -{ - static GType e_cal_backend_groupwise_type = 0; - - if (!e_cal_backend_groupwise_type) { - static GTypeInfo info = { - sizeof (ECalBackendGroupwiseClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_backend_groupwise_class_init, - NULL, NULL, - sizeof (ECalBackendGroupwise), - 0, - (GInstanceInitFunc) e_cal_backend_groupwise_init - }; - e_cal_backend_groupwise_type = g_type_register_static (E_TYPE_CAL_BACKEND_SYNC, - "ECalBackendGroupwise", &info, 0); - } - - return e_cal_backend_groupwise_type; -} - -void -e_cal_backend_groupwise_notify_error_code (ECalBackendGroupwise *cbgw, EGwConnectionStatus status) -{ - const char *msg; - - g_return_if_fail (E_IS_CAL_BACKEND_GROUPWISE (cbgw)); - - msg = e_gw_connection_get_error_message (status); - if (msg) - e_cal_backend_notify_error (E_CAL_BACKEND (cbgw), msg); -} diff --git a/calendar/backends/groupwise/e-cal-backend-groupwise.h b/calendar/backends/groupwise/e-cal-backend-groupwise.h deleted file mode 100644 index 6ec656e89..000000000 --- a/calendar/backends/groupwise/e-cal-backend-groupwise.h +++ /dev/null @@ -1,59 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - * Authors : - * JP Rosevear <jpr@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * Copyright 2003, Novell, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - * USA - */ - -#ifndef E_CAL_BACKEND_GROUPWISE_H -#define E_CAL_BACKEND_GROUPWISE_H - -#include <libedata-cal/e-cal-backend-sync.h> -#include <servers/groupwise/e-gw-connection.h> - -G_BEGIN_DECLS - -#define E_TYPE_CAL_BACKEND_GROUPWISE (e_cal_backend_groupwise_get_type ()) -#define E_CAL_BACKEND_GROUPWISE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_BACKEND_GROUPWISE, ECalBackendGroupwise)) -#define E_CAL_BACKEND_GROUPWISE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_BACKEND_GROUPWISE, ECalBackendGroupwiseClass)) -#define E_IS_CAL_BACKEND_GROUPWISE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_BACKEND_GROUPWISE)) -#define E_IS_CAL_BACKEND_GROUPWISE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_BACKEND_GROUPWISE)) - -typedef struct _ECalBackendGroupwise ECalBackendGroupwise; -typedef struct _ECalBackendGroupwiseClass ECalBackendGroupwiseClass; - -typedef struct _ECalBackendGroupwisePrivate ECalBackendGroupwisePrivate; - -struct _ECalBackendGroupwise { - ECalBackendSync backend; - - /* Private data */ - ECalBackendGroupwisePrivate *priv; -}; - -struct _ECalBackendGroupwiseClass { - ECalBackendSyncClass parent_class; -}; - -GType e_cal_backend_groupwise_get_type (void); -void e_cal_backend_groupwise_notify_error_code (ECalBackendGroupwise *cbgw, EGwConnectionStatus status); - -G_END_DECLS - -#endif diff --git a/calendar/backends/http/.cvsignore b/calendar/backends/http/.cvsignore deleted file mode 100644 index c038ed786..000000000 --- a/calendar/backends/http/.cvsignore +++ /dev/null @@ -1,2 +0,0 @@ -Makefile -Makefile.in
\ No newline at end of file diff --git a/calendar/backends/http/Makefile.am b/calendar/backends/http/Makefile.am deleted file mode 100644 index aa31ad783..000000000 --- a/calendar/backends/http/Makefile.am +++ /dev/null @@ -1,25 +0,0 @@ -INCLUDES = \ - -DG_LOG_DOMAIN=\"libecalbackendhttp\" \ - -I$(top_srcdir) \ - -I$(top_builddir) \ - -I$(top_srcdir)/calendar \ - -I$(top_builddir)/calendar \ - -I$(top_srcdir)/calendar/backends/file \ - -I$(top_builddir)/calendar/backends/file \ - -I$(top_srcdir)/calendar/libical/src \ - -I$(top_builddir)/calendar/libical/src \ - -I$(top_srcdir)/calendar/libical/src/libical \ - -I$(top_builddir)/calendar/libical/src/libical \ - $(EVOLUTION_CALENDAR_CFLAGS) \ - $(SOUP_CFLAGS) - -noinst_LTLIBRARIES = libecalbackendhttp.la - -libecalbackendhttp_la_SOURCES = \ - e-cal-backend-http.c \ - e-cal-backend-http.h - -libecalbackendhttp_la_LIBADD = \ - $(top_builddir)/calendar/libedata-cal/libedata-cal.la \ - $(top_builddir)/calendar/backends/file/libecalbackendfile.la \ - $(SOUP_LIBS) diff --git a/calendar/backends/http/e-cal-backend-http.c b/calendar/backends/http/e-cal-backend-http.c deleted file mode 100644 index 8a2c70744..000000000 --- a/calendar/backends/http/e-cal-backend-http.c +++ /dev/null @@ -1,918 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* Evolution calendar - iCalendar http backend - * - * Copyright (C) 2003 Novell, Inc. - * - * Authors: Hans Petter Jansson <hpj@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - * - * Based in part on the file backend. - */ - -#include <config.h> -#include <string.h> -#include <unistd.h> -#include <bonobo/bonobo-exception.h> -#include <bonobo/bonobo-moniker-util.h> -#include <libgnome/gnome-i18n.h> -#include <libedataserver/e-xml-hash-utils.h> -#include <libecal/e-cal-recur.h> -#include <libecal/e-cal-util.h> -#include <libedata-cal/e-cal-backend-cache.h> -#include <libedata-cal/e-cal-backend-util.h> -#include <libedata-cal/e-cal-backend-sexp.h> -#include <libsoup/soup-session-async.h> -#include <libsoup/soup-uri.h> -#include "e-cal-backend-http.h" - - - -/* Private part of the ECalBackendHttp structure */ -struct _ECalBackendHttpPrivate { - /* URI to get remote calendar data from */ - char *uri; - - /* Local/remote mode */ - CalMode mode; - - /* The file cache */ - ECalBackendCache *cache; - - /* The calendar's default timezone, used for resolving DATE and - floating DATE-TIME values. */ - icaltimezone *default_zone; - - /* The list of live queries */ - GList *queries; - - /* Soup handles for remote file */ - SoupSession *soup_session; - - /* Reload */ - guint reload_timeout_id; - guint is_loading : 1; - - /* Flags */ - gboolean opened; -}; - - - -#define d(x) - -static void e_cal_backend_http_dispose (GObject *object); -static void e_cal_backend_http_finalize (GObject *object); -static gboolean begin_retrieval_cb (ECalBackendHttp *cbhttp); - -static ECalBackendSyncClass *parent_class; - - - -/* Dispose handler for the file backend */ -static void -e_cal_backend_http_dispose (GObject *object) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (object); - priv = cbhttp->priv; - - if (G_OBJECT_CLASS (parent_class)->dispose) - (* G_OBJECT_CLASS (parent_class)->dispose) (object); -} - -/* Finalize handler for the file backend */ -static void -e_cal_backend_http_finalize (GObject *object) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL_BACKEND_HTTP (object)); - - cbhttp = E_CAL_BACKEND_HTTP (object); - priv = cbhttp->priv; - - /* Clean up */ - - if (priv->cache) { - g_object_unref (priv->cache); - priv->cache = NULL; - } - - if (priv->uri) { - g_free (priv->uri); - priv->uri = NULL; - } - - if (priv->soup_session) { - soup_session_abort (priv->soup_session); - g_object_unref (priv->soup_session); - priv->soup_session = NULL; - } - - g_free (priv); - cbhttp->priv = NULL; - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - - - -/* Calendar backend methods */ - -/* Is_read_only handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_http_is_read_only (ECalBackendSync *backend, EDataCal *cal, gboolean *read_only) -{ - *read_only = TRUE; - - return GNOME_Evolution_Calendar_Success; -} - -/* Get_email_address handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_http_get_cal_address (ECalBackendSync *backend, EDataCal *cal, char **address) -{ - /* A HTTP backend has no particular email address associated - * with it (although that would be a useful feature some day). - */ - *address = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_http_get_ldap_attribute (ECalBackendSync *backend, EDataCal *cal, char **attribute) -{ - *attribute = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_http_get_alarm_email_address (ECalBackendSync *backend, EDataCal *cal, char **address) -{ - /* A HTTP backend has no particular email address associated - * with it (although that would be a useful feature some day). - */ - *address = NULL; - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_http_get_static_capabilities (ECalBackendSync *backend, EDataCal *cal, char **capabilities) -{ - *capabilities = g_strdup (CAL_STATIC_CAPABILITY_NO_EMAIL_ALARMS); - - return GNOME_Evolution_Calendar_Success; -} - -static gchar * -webcal_to_http_method (const gchar *webcal_str) -{ - if (strncmp ("webcal://", webcal_str, sizeof ("webcal://") - 1)) - return g_strdup (webcal_str); - - return g_strconcat ("http://", webcal_str + sizeof ("webcal://") - 1, NULL); -} - -static void -retrieval_done (SoupMessage *msg, ECalBackendHttp *cbhttp) -{ - ECalBackendHttpPrivate *priv; - icalcomponent *icalcomp, *subcomp; - icalcomponent_kind kind; - const char *newuri; - char *str; - - priv = cbhttp->priv; - - priv->is_loading = FALSE; - d(g_message ("Retrieval done.\n")); - - /* Handle redirection ourselves */ - if (SOUP_STATUS_IS_REDIRECTION (msg->status_code)) { - newuri = soup_message_get_header (msg->response_headers, - "Location"); - - d(g_message ("Redirected to %s\n", newuri)); - - if (newuri) { - g_free (priv->uri); - - priv->uri = webcal_to_http_method (newuri); - begin_retrieval_cb (cbhttp); - } else { - if (!priv->opened) { - e_cal_backend_notify_error (E_CAL_BACKEND (cbhttp), - _("Redirected to Invalid URI")); - } - } - - return; - } - - /* check status code */ - if (!SOUP_STATUS_IS_SUCCESSFUL (msg->status_code)) { - if (!priv->opened) { - e_cal_backend_notify_error (E_CAL_BACKEND (cbhttp), - soup_status_get_phrase (msg->status_code)); - } - return; - } - - /* get the calendar from the response */ - str = g_malloc0 (msg->response.length + 1); - strncpy (str, msg->response.body, msg->response.length); - icalcomp = icalparser_parse_string (str); - g_free (str); - - if (!icalcomp) { - if (!priv->opened) - e_cal_backend_notify_error (E_CAL_BACKEND (cbhttp), _("Bad file format.")); - return; - } - - if (icalcomponent_isa (icalcomp) != ICAL_VCALENDAR_COMPONENT) { - if (!priv->opened) - e_cal_backend_notify_error (E_CAL_BACKEND (cbhttp), _("Not a calendar.")); - icalcomponent_free (icalcomp); - return; - } - - /* Update cache */ - e_file_cache_clean (E_FILE_CACHE (priv->cache)); - - kind = e_cal_backend_get_kind (E_CAL_BACKEND (cbhttp)); - subcomp = icalcomponent_get_first_component (icalcomp, ICAL_ANY_COMPONENT); - while (subcomp) { - ECalComponent *comp; - icalcomponent_kind subcomp_kind; - - subcomp_kind = icalcomponent_isa (subcomp); - if (subcomp_kind == kind) { - comp = e_cal_component_new (); - if (e_cal_component_set_icalcomponent (comp, subcomp)) { - e_cal_backend_cache_put_component (priv->cache, comp); - e_cal_backend_notify_object_created (E_CAL_BACKEND (cbhttp), - icalcomponent_as_ical_string (subcomp)); - } - - g_object_unref (comp); - } else if (subcomp_kind == ICAL_VTIMEZONE_COMPONENT) { - icaltimezone *zone; - - zone = icaltimezone_new (); - icaltimezone_set_component (zone, subcomp); - e_cal_backend_cache_put_timezone (priv->cache, (const icaltimezone *) zone); - - icaltimezone_free (zone, 1); - } - - subcomp = icalcomponent_get_next_component (icalcomp, kind); - } - - /* free memory */ - icalcomponent_free (icalcomp); - - d(g_message ("Retrieval really done.\n")); -} - -static gboolean reload_cb (ECalBackendHttp *cbhttp); -static void maybe_start_reload_timeout (ECalBackendHttp *cbhttp); - -static gboolean -begin_retrieval_cb (ECalBackendHttp *cbhttp) -{ - ECalBackendHttpPrivate *priv; - SoupMessage *soup_message; - - priv = cbhttp->priv; - - if (priv->mode != CAL_MODE_REMOTE) - return TRUE; - - maybe_start_reload_timeout (cbhttp); - - d(g_message ("Starting retrieval...\n")); - - if (priv->is_loading) - return FALSE; - - priv->is_loading = TRUE; - - /* create the Soup session if not already created */ - if (!priv->soup_session) { - priv->soup_session = soup_session_async_new (); - } - - if (priv->uri == NULL) - priv->uri = webcal_to_http_method (e_cal_backend_get_uri (E_CAL_BACKEND (cbhttp))); - - /* create message to be sent to server */ - soup_message = soup_message_new (SOUP_METHOD_GET, priv->uri); - soup_message_set_flags (soup_message, SOUP_MESSAGE_NO_REDIRECT); - - soup_session_queue_message (priv->soup_session, soup_message, - (SoupMessageCallbackFn) retrieval_done, cbhttp); - - d(g_message ("Retrieval started.\n")); - return FALSE; -} - -static gboolean -reload_cb (ECalBackendHttp *cbhttp) -{ - ECalBackendHttpPrivate *priv; - - priv = cbhttp->priv; - - if (priv->is_loading) - return TRUE; - - d(g_message ("Reload!\n")); - - priv->reload_timeout_id = 0; - priv->opened = TRUE; - begin_retrieval_cb (cbhttp); - return FALSE; -} - -static void -maybe_start_reload_timeout (ECalBackendHttp *cbhttp) -{ - ECalBackendHttpPrivate *priv; - ESource *source; - const gchar *refresh_str; - - priv = cbhttp->priv; - - d(g_message ("Setting reload timeout.\n")); - - if (priv->reload_timeout_id) - return; - - source = e_cal_backend_get_source (E_CAL_BACKEND (cbhttp)); - if (!source) { - g_warning ("Could not get source for ECalBackendHttp reload."); - return; - } - - refresh_str = e_source_get_property (source, "refresh"); - - priv->reload_timeout_id = g_timeout_add ((refresh_str ? atoi (refresh_str) : 30) * 60000, - (GSourceFunc) reload_cb, cbhttp); -} - -/* Open handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_http_open (ECalBackendSync *backend, EDataCal *cal, gboolean only_if_exists, - const char *username, const char *password) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - if (!priv->cache) { - priv->cache = e_cal_backend_cache_new (e_cal_backend_get_uri (E_CAL_BACKEND (backend))); - - /* FIXME: no need to set it online here when we implement the online/offline stuff correctly */ - priv->mode = CAL_MODE_REMOTE; - g_idle_add ((GSourceFunc) begin_retrieval_cb, cbhttp); - } - - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_http_remove (ECalBackendSync *backend, EDataCal *cal) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - if (!priv->cache) - return GNOME_Evolution_Calendar_OtherError; - - e_file_cache_remove (E_FILE_CACHE (priv->cache)); - return GNOME_Evolution_Calendar_Success; -} - -/* is_loaded handler for the file backend */ -static gboolean -e_cal_backend_http_is_loaded (ECalBackend *backend) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - if (!priv->cache) - return FALSE; - - return TRUE; -} - -/* is_remote handler for the http backend */ -static CalMode -e_cal_backend_http_get_mode (ECalBackend *backend) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - return priv->mode; -} - -/* Set_mode handler for the http backend */ -static void -e_cal_backend_http_set_mode (ECalBackend *backend, CalMode mode) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - GNOME_Evolution_Calendar_CalMode set_mode; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - switch (mode) { - case CAL_MODE_LOCAL: - case CAL_MODE_REMOTE: - priv->mode = mode; - set_mode = cal_mode_to_corba (mode); - break; - case CAL_MODE_ANY: - priv->mode = CAL_MODE_REMOTE; - set_mode = GNOME_Evolution_Calendar_MODE_REMOTE; - break; - default: - set_mode = GNOME_Evolution_Calendar_MODE_ANY; - break; - } - - if (set_mode == GNOME_Evolution_Calendar_MODE_ANY) - e_cal_backend_notify_mode (backend, - GNOME_Evolution_Calendar_CalListener_MODE_NOT_SUPPORTED, - cal_mode_to_corba (priv->mode)); - else - e_cal_backend_notify_mode (backend, - GNOME_Evolution_Calendar_CalListener_MODE_SET, - set_mode); -} - -static ECalBackendSyncStatus -e_cal_backend_http_get_default_object (ECalBackendSync *backend, EDataCal *cal, char **object) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - icalcomponent *icalcomp; - icalcomponent_kind kind; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - kind = e_cal_backend_get_kind (E_CAL_BACKEND (backend)); - icalcomp = e_cal_util_new_component (kind); - *object = g_strdup (icalcomponent_as_ical_string (icalcomp)); - icalcomponent_free (icalcomp); - - return GNOME_Evolution_Calendar_Success; -} - -/* Get_object_component handler for the http backend */ -static ECalBackendSyncStatus -e_cal_backend_http_get_object (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *rid, char **object) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - ECalComponent *comp; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - g_return_val_if_fail (uid != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - if (!priv->cache) - return GNOME_Evolution_Calendar_ObjectNotFound; - - comp = e_cal_backend_cache_get_component (priv->cache, uid, rid); - if (!comp) - return GNOME_Evolution_Calendar_ObjectNotFound; - - *object = e_cal_component_get_as_string (comp); - g_free (comp); - - return GNOME_Evolution_Calendar_Success; -} - -/* Get_timezone_object handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_http_get_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid, char **object) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - icaltimezone *zone; - icalcomponent *icalcomp; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - g_return_val_if_fail (tzid != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - zone = icaltimezone_get_builtin_timezone_from_tzid (tzid); - if (!zone) - return GNOME_Evolution_Calendar_ObjectNotFound; - - icalcomp = icaltimezone_get_component (zone); - if (!icalcomp) - return GNOME_Evolution_Calendar_InvalidObject; - - *object = g_strdup (icalcomponent_as_ical_string (icalcomp)); - - return GNOME_Evolution_Calendar_Success; -} - -/* Add_timezone handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_http_add_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzobj) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = (ECalBackendHttp *) backend; - - g_return_val_if_fail (E_IS_CAL_BACKEND_HTTP (cbhttp), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (tzobj != NULL, GNOME_Evolution_Calendar_OtherError); - - priv = cbhttp->priv; - - /* FIXME: add the timezone to the cache */ - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_http_set_default_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - /* FIXME */ - return GNOME_Evolution_Calendar_Success; -} - -/* Get_objects_in_range handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_http_get_object_list (ECalBackendSync *backend, EDataCal *cal, const char *sexp, GList **objects) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - GList *components, *l; - ECalBackendSExp *cbsexp; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - if (!priv->cache) - return GNOME_Evolution_Calendar_NoSuchCal; - - /* process all components in the cache */ - cbsexp = e_cal_backend_sexp_new (sexp); - - *objects = NULL; - components = e_cal_backend_cache_get_components (priv->cache); - for (l = components; l != NULL; l = l->next) { - if (e_cal_backend_sexp_match_comp (cbsexp, E_CAL_COMPONENT (l->data), E_CAL_BACKEND (backend))) { - *objects = g_list_append (*objects, e_cal_component_get_as_string (l->data)); - } - } - - g_list_foreach (components, (GFunc) g_object_unref, NULL); - g_list_free (components); - g_object_unref (cbsexp); - - return GNOME_Evolution_Calendar_Success; -} - -/* get_query handler for the file backend */ -static void -e_cal_backend_http_start_query (ECalBackend *backend, EDataCalView *query) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - GList *components, *l, *objects = NULL; - ECalBackendSExp *cbsexp; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - d(g_message (G_STRLOC ": Starting query (%s)", e_data_cal_view_get_text (query))); - - if (!priv->cache) { - e_data_cal_view_notify_done (query, GNOME_Evolution_Calendar_NoSuchCal); - return; - } - - /* process all components in the cache */ - cbsexp = e_cal_backend_sexp_new (e_data_cal_view_get_text (query)); - - objects = NULL; - components = e_cal_backend_cache_get_components (priv->cache); - for (l = components; l != NULL; l = l->next) { - if (e_cal_backend_sexp_match_comp (cbsexp, E_CAL_COMPONENT (l->data), E_CAL_BACKEND (backend))) { - objects = g_list_append (objects, e_cal_component_get_as_string (l->data)); - } - } - - e_data_cal_view_notify_objects_added (query, (const GList *) objects); - - g_list_foreach (components, (GFunc) g_object_unref, NULL); - g_list_free (components); - g_list_foreach (objects, (GFunc) g_free, NULL); - g_list_free (objects); - g_object_unref (cbsexp); - - e_data_cal_view_notify_done (query, GNOME_Evolution_Calendar_Success); -} - -/* Get_free_busy handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_http_get_free_busy (ECalBackendSync *backend, EDataCal *cal, GList *users, - time_t start, time_t end, GList **freebusy) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - g_return_val_if_fail (start != -1 && end != -1, GNOME_Evolution_Calendar_InvalidRange); - g_return_val_if_fail (start <= end, GNOME_Evolution_Calendar_InvalidRange); - - if (!priv->cache) - return GNOME_Evolution_Calendar_NoSuchCal; - - /* FIXME */ - return GNOME_Evolution_Calendar_Success; -} - -/* Get_changes handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_http_get_changes (ECalBackendSync *backend, EDataCal *cal, const char *change_id, - GList **adds, GList **modifies, GList **deletes) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - g_return_val_if_fail (change_id != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - /* FIXME */ - return GNOME_Evolution_Calendar_Success; -} - -/* Discard_alarm handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_http_discard_alarm (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *auid) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - /* FIXME */ - return GNOME_Evolution_Calendar_Success; -} - -static ECalBackendSyncStatus -e_cal_backend_http_create_object (ECalBackendSync *backend, EDataCal *cal, char **calobj, char **uid) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - return GNOME_Evolution_Calendar_PermissionDenied; -} - -static ECalBackendSyncStatus -e_cal_backend_http_modify_object (ECalBackendSync *backend, EDataCal *cal, const char *calobj, - CalObjModType mod, char **old_object) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - g_return_val_if_fail (calobj != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - return GNOME_Evolution_Calendar_PermissionDenied; -} - -/* Remove_object handler for the file backend */ -static ECalBackendSyncStatus -e_cal_backend_http_remove_object (ECalBackendSync *backend, EDataCal *cal, - const char *uid, const char *rid, - CalObjModType mod, char **object) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - g_return_val_if_fail (uid != NULL, GNOME_Evolution_Calendar_ObjectNotFound); - - return GNOME_Evolution_Calendar_PermissionDenied; -} - -/* Update_objects handler for the file backend. */ -static ECalBackendSyncStatus -e_cal_backend_http_receive_objects (ECalBackendSync *backend, EDataCal *cal, const char *calobj) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - g_return_val_if_fail (calobj != NULL, GNOME_Evolution_Calendar_InvalidObject); - - return GNOME_Evolution_Calendar_PermissionDenied; -} - -static ECalBackendSyncStatus -e_cal_backend_http_send_objects (ECalBackendSync *backend, EDataCal *cal, const char *calobj, GList **users, - char **modified_calobj) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - *users = NULL; - *modified_calobj = NULL; - - return GNOME_Evolution_Calendar_PermissionDenied; -} - -static icaltimezone * -e_cal_backend_http_internal_get_default_timezone (ECalBackend *backend) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - if (!priv->cache) - return NULL; - - return NULL; -} - -static icaltimezone * -e_cal_backend_http_internal_get_timezone (ECalBackend *backend, const char *tzid) -{ - ECalBackendHttp *cbhttp; - ECalBackendHttpPrivate *priv; - icaltimezone *zone; - - cbhttp = E_CAL_BACKEND_HTTP (backend); - priv = cbhttp->priv; - - if (!strcmp (tzid, "UTC")) - zone = icaltimezone_get_utc_timezone (); - else { - zone = icaltimezone_get_builtin_timezone_from_tzid (tzid); - } - - return zone; -} - -/* Object initialization function for the file backend */ -static void -e_cal_backend_http_init (ECalBackendHttp *cbhttp, ECalBackendHttpClass *class) -{ - ECalBackendHttpPrivate *priv; - - priv = g_new0 (ECalBackendHttpPrivate, 1); - cbhttp->priv = priv; - - priv->uri = NULL; - priv->reload_timeout_id = 0; - priv->opened = FALSE; -} - -/* Class initialization function for the file backend */ -static void -e_cal_backend_http_class_init (ECalBackendHttpClass *class) -{ - GObjectClass *object_class; - ECalBackendClass *backend_class; - ECalBackendSyncClass *sync_class; - - object_class = (GObjectClass *) class; - backend_class = (ECalBackendClass *) class; - sync_class = (ECalBackendSyncClass *) class; - - parent_class = (ECalBackendSyncClass *) g_type_class_peek_parent (class); - - object_class->dispose = e_cal_backend_http_dispose; - object_class->finalize = e_cal_backend_http_finalize; - - sync_class->is_read_only_sync = e_cal_backend_http_is_read_only; - sync_class->get_cal_address_sync = e_cal_backend_http_get_cal_address; - sync_class->get_alarm_email_address_sync = e_cal_backend_http_get_alarm_email_address; - sync_class->get_ldap_attribute_sync = e_cal_backend_http_get_ldap_attribute; - sync_class->get_static_capabilities_sync = e_cal_backend_http_get_static_capabilities; - sync_class->open_sync = e_cal_backend_http_open; - sync_class->remove_sync = e_cal_backend_http_remove; - sync_class->create_object_sync = e_cal_backend_http_create_object; - sync_class->modify_object_sync = e_cal_backend_http_modify_object; - sync_class->remove_object_sync = e_cal_backend_http_remove_object; - sync_class->discard_alarm_sync = e_cal_backend_http_discard_alarm; - sync_class->receive_objects_sync = e_cal_backend_http_receive_objects; - sync_class->send_objects_sync = e_cal_backend_http_send_objects; - sync_class->get_default_object_sync = e_cal_backend_http_get_default_object; - sync_class->get_object_sync = e_cal_backend_http_get_object; - sync_class->get_object_list_sync = e_cal_backend_http_get_object_list; - sync_class->get_timezone_sync = e_cal_backend_http_get_timezone; - sync_class->add_timezone_sync = e_cal_backend_http_add_timezone; - sync_class->set_default_timezone_sync = e_cal_backend_http_set_default_timezone; - sync_class->get_freebusy_sync = e_cal_backend_http_get_free_busy; - sync_class->get_changes_sync = e_cal_backend_http_get_changes; - - backend_class->is_loaded = e_cal_backend_http_is_loaded; - backend_class->start_query = e_cal_backend_http_start_query; - backend_class->get_mode = e_cal_backend_http_get_mode; - backend_class->set_mode = e_cal_backend_http_set_mode; - - backend_class->internal_get_default_timezone = e_cal_backend_http_internal_get_default_timezone; - backend_class->internal_get_timezone = e_cal_backend_http_internal_get_timezone; -} - - -/** - * e_cal_backend_http_get_type: - * @void: - * - * Registers the #ECalBackendHttp class if necessary, and returns the type ID - * associated to it. - * - * Return value: The type ID of the #ECalBackendHttp class. - **/ -GType -e_cal_backend_http_get_type (void) -{ - static GType e_cal_backend_http_type = 0; - - if (!e_cal_backend_http_type) { - static GTypeInfo info = { - sizeof (ECalBackendHttpClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_backend_http_class_init, - NULL, NULL, - sizeof (ECalBackendHttp), - 0, - (GInstanceInitFunc) e_cal_backend_http_init - }; - e_cal_backend_http_type = g_type_register_static (E_TYPE_CAL_BACKEND_SYNC, - "ECalBackendHttp", &info, 0); - } - - return e_cal_backend_http_type; -} diff --git a/calendar/backends/http/e-cal-backend-http.h b/calendar/backends/http/e-cal-backend-http.h deleted file mode 100644 index 44a7cf351..000000000 --- a/calendar/backends/http/e-cal-backend-http.h +++ /dev/null @@ -1,61 +0,0 @@ -/* Evolution calendar - iCalendar file backend - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_BACKEND_HTTP_H -#define E_CAL_BACKEND_HTTP_H - -#include <libedata-cal/e-cal-backend-sync.h> - -G_BEGIN_DECLS - - - -#define E_TYPE_CAL_BACKEND_HTTP (e_cal_backend_http_get_type ()) -#define E_CAL_BACKEND_HTTP(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_BACKEND_HTTP, \ - ECalBackendHttp)) -#define E_CAL_BACKEND_HTTP_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_BACKEND_HTTP, \ - ECalBackendHttpClass)) -#define E_IS_CAL_BACKEND_HTTP(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_BACKEND_HTTP)) -#define E_IS_CAL_BACKEND_HTTP_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_BACKEND_HTTP)) - -typedef struct _ECalBackendHttp ECalBackendHttp; -typedef struct _ECalBackendHttpClass ECalBackendHttpClass; - -typedef struct _ECalBackendHttpPrivate ECalBackendHttpPrivate; - -struct _ECalBackendHttp { - ECalBackendSync backend; - - /* Private data */ - ECalBackendHttpPrivate *priv; -}; - -struct _ECalBackendHttpClass { - ECalBackendSyncClass parent_class; -}; - -GType e_cal_backend_http_get_type (void); - - - -G_END_DECLS - -#endif diff --git a/calendar/idl/.cvsignore b/calendar/idl/.cvsignore deleted file mode 100644 index c038ed786..000000000 --- a/calendar/idl/.cvsignore +++ /dev/null @@ -1,2 +0,0 @@ -Makefile -Makefile.in
\ No newline at end of file diff --git a/calendar/idl/Evolution-DataServer-Calendar.idl b/calendar/idl/Evolution-DataServer-Calendar.idl deleted file mode 100644 index 228ea1078..000000000 --- a/calendar/idl/Evolution-DataServer-Calendar.idl +++ /dev/null @@ -1,275 +0,0 @@ -/* Evolution calendar interface - * - * Copyright (C) 2000 Eskil Heyn Olsen - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Authors: Eskil Heyn Olsen <deity@eskil.dk> - * Federico Mena-Quintero <federico@ximian.com> - */ - -#ifndef _EVOLUTION_CALENDAR_IDL_ -#define _EVOLUTION_CALENDAR_IDL_ - -#include <Bonobo.idl> - -module GNOME { -module Evolution { - -module Calendar { - /* A calendar component (event/todo/journal/etc), represented as an - * iCalendar string. - */ - typedef string CalObj; - typedef sequence<CalObj> CalObjSeq; - - typedef sequence<string> stringlist; - - /* A unique identifier for a calendar component */ - typedef string CalObjUID; - - /* A unique identified for an event recurrence */ - typedef string CalRecurID; - - /* Simple sequence of strings */ - typedef sequence<string> StringSeq; - - /* Sequence of unique identifiers */ - typedef sequence<CalObjUID> CalObjUIDSeq; - - /* A VTIMEZONE component, represented as an iCalendar string. */ - typedef string CalTimezoneObj; - - /* A unique identifier for a VTIMEZONE component, i.e. its TZID. */ - typedef string CalTimezoneObjUID; - - /* A unique identifier for an alarm subcomponent */ - typedef string CalAlarmUID; - - /* Flags for getting UID sequences */ - typedef long CalObjType; - const CalObjType TYPE_EVENT = 1 << 0; - const CalObjType TYPE_TODO = 1 << 1; - const CalObjType TYPE_JOURNAL = 1 << 2; - const CalObjType TYPE_ANY = 0x07; - - /* Flags for getting UID sequences */ - typedef long CalObjModType; - const CalObjModType MOD_THIS = 1 << 0; - const CalObjModType MOD_THISANDPRIOR = 1 << 1; - const CalObjModType MOD_THISANDFUTURE = 1 << 2; - const CalObjModType MOD_ALL = 0x07; - - /* Flags for getting URI sequences */ - typedef long CalMode; - const CalMode MODE_LOCAL = 1 << 0; - const CalMode MODE_REMOTE = 1 << 1; - const CalMode MODE_ANY = 0x07; - - /* Types of object changes made */ - typedef long CalObjChangeType; - const CalObjChangeType ADDED = 1 << 0; - const CalObjChangeType MODIFIED = 1 << 1; - const CalObjChangeType DELETED = 1 << 2; - - /* Used to store a time_t */ - typedef unsigned long Time_t; - - /* An instance of a calendar component that actually occurs. These are - * "virtual" objects in that they are used to represent instances of - * recurring events and alarms. "Real" objects just contain the - * information required to figure out the times at which they recur or - * trigger. - */ - struct CalObjInstance { - CalObjUID uid; - Time_t start; - Time_t end; - }; - - /* Used to transfer a list of component occurrences */ - typedef sequence<CalObjInstance> CalObjInstanceSeq; - - /* An object change */ - struct CalObjChange { - CalObj calobj; - CalObjChangeType type; - }; - - /* Used to transfer a list of changed components */ - typedef sequence<CalObjChange> CalObjChangeSeq; - - /* Used to represent users and lists of users */ - typedef string User; - typedef sequence<User> UserList; - - enum CallStatus { - Success, - RepositoryOffline, - PermissionDenied, - InvalidRange, - ObjectNotFound, - InvalidObject, - ObjectIdAlreadyExists, - AuthenticationFailed, - AuthenticationRequired, - UnsupportedField, - UnsupportedMethod, - UnsupportedAuthenticationMethod, - TLSNotAvailable, - NoSuchCal, - - /* These can be returned for successful searches, but - indicate the result set was truncated */ - SearchSizeLimitExceeded, - SearchTimeLimitExceeded, - - InvalidQuery, - QueryRefused, - - CouldNotCancel, - - OtherError - }; - - /* Handle to a live query on a calendar */ - interface CalView : Bonobo::Unknown { - oneway void start (); - }; - - /* Listener for changes in a query of a calendar */ - interface CalViewListener : Bonobo::Unknown { - oneway void notifyObjectsAdded (in stringlist objects); - oneway void notifyObjectsModified (in stringlist objects); - oneway void notifyObjectsRemoved (in CalObjUIDSeq uids); - oneway void notifyQueryProgress (in string message, in short percent); - oneway void notifyQueryDone (in CallStatus status); - }; - - /* Calendar client interface */ - interface Cal : Bonobo::Unknown { - exception NotFound {}; - exception InvalidRange {}; - - /* A calendar is identified by its URI */ - readonly attribute string uri; - - oneway void open (in boolean only_if_exists, in string username, in string password); - oneway void remove (); - - /* Check write permissions for calendar */ - oneway void isReadOnly (); - - /* Information on the backend's capabilities */ - oneway void getStaticCapabilities (); - - /* Return the cal address associated with this calendar, if any. */ - oneway void getCalAddress (); - - oneway void getAlarmEmailAddress (); - - /* Returns the LDAP attribute to get attendees from */ - oneway void getLdapAttribute (); - - /* For going online/offline */ - void setMode (in CalMode mode); - - /* Get a default object of the backend's type */ - oneway void getDefaultObject (); - - /* Gets a component based on its URI */ - oneway void getObject (in CalObjUID uid, in CalRecurID rid); - - oneway void getObjectList (in string query); - - /* Methods for manipulating timezones */ - oneway void getTimezone (in CalTimezoneObjUID tzid); - oneway void addTimezone (in CalTimezoneObj tz); - /* The timezone used to resolve DATE and floating DATE-TIME values. */ - oneway void setDefaultTimezone (in CalTimezoneObjUID tzid); - - /* Gets a list of components that changed */ - oneway void getChanges (in string change_id); - - /* Returns free/busy objects for the given interval */ - oneway void getFreeBusy (in UserList users, in Time_t start, in Time_t end); - - /* Discards an alarm from a given component */ - oneway void discardAlarm (in CalObjUID uid, in CalAlarmUID auid); - - /* Methods for manipulating iCalendar objects */ - oneway void createObject (in CalObj calobj); - oneway void modifyObject (in CalObj calobj, in CalObjModType mod); - oneway void removeObject (in CalObjUID uid, in CalRecurID rid, in CalObjModType mod); - - /* Methods for getting/sending iCalendar VCALENDARS via iTip/iMip */ - oneway void receiveObjects (in CalObj calobj); - oneway void sendObjects (in CalObj calobj); - - /* Query methods */ - oneway void getQuery (in string sexp, in CalViewListener ql); - }; - - /* Listener for changes in a calendar */ - interface CalListener : Bonobo::Unknown { - /* Return status when setting calendar mode */ - enum SetModeStatus { - MODE_SET, /* All OK */ - MODE_NOT_SET, /* Generic error */ - MODE_NOT_SUPPORTED /* Mode not supported */ - }; - - oneway void notifyReadOnly (in CallStatus status, in boolean read_only); - oneway void notifyCalAddress (in CallStatus status, in string address); - oneway void notifyAlarmEmailAddress (in CallStatus status, in string address); - oneway void notifyLDAPAttribute (in CallStatus status, in string ldap_attribute); - oneway void notifyStaticCapabilities (in CallStatus status, in string capabilities); - - oneway void notifyCalOpened (in CallStatus status); - oneway void notifyCalRemoved (in CallStatus status); - - oneway void notifyObjectCreated (in CallStatus status, in string uid); - oneway void notifyObjectModified (in CallStatus status); - oneway void notifyObjectRemoved (in CallStatus status); - - oneway void notifyAlarmDiscarded (in CallStatus status); - - oneway void notifyObjectsReceived (in CallStatus status); - oneway void notifyObjectsSent (in CallStatus status, in UserList users, in CalObj calobj); - - oneway void notifyDefaultObjectRequested (in CallStatus status, in CalObj object); - oneway void notifyObjectRequested (in CallStatus status, in CalObj object); - oneway void notifyObjectListRequested (in CallStatus status, in stringlist objects); - oneway void notifyQuery (in CallStatus status, in CalView query); - - oneway void notifyTimezoneRequested (in CallStatus status, in CalTimezoneObj tz); - oneway void notifyTimezoneAdded (in CallStatus status, in CalTimezoneObjUID tzid); - oneway void notifyDefaultTimezoneSet (in CallStatus status); - - oneway void notifyChanges (in CallStatus status, in CalObjChangeSeq changes); - oneway void notifyFreeBusy (in CallStatus status, in CalObjSeq freebusy); - - /* Called from a Calendar when the mode is changed */ - oneway void notifyCalSetMode (in SetModeStatus status, in CalMode mode); - - /* Called from a Calendar when the list of categories changes */ - oneway void notifyCategoriesChanged (in StringSeq categories); - - /* Called from a Calendar when there is an error not notified otherwise */ - oneway void notifyErrorOccurred (in string message); - }; - - /* A calendar factory, can load and create calendars */ - interface CalFactory : Bonobo::Unknown { - exception NilListener {}; - exception InvalidURI {}; - exception UnsupportedMethod {}; - - Cal getCal (in string source, in CalObjType type, in CalListener listener) - raises (NilListener, InvalidURI, UnsupportedMethod); - }; -}; -}; -}; - -#endif diff --git a/calendar/idl/Makefile.am b/calendar/idl/Makefile.am deleted file mode 100644 index fdd56ad62..000000000 --- a/calendar/idl/Makefile.am +++ /dev/null @@ -1,5 +0,0 @@ -idl_DATA = \ - Evolution-DataServer-Calendar.idl - -EXTRA_DIST = \ - $(idl_DATA) diff --git a/calendar/libecal/.cvsignore b/calendar/libecal/.cvsignore deleted file mode 100644 index cff61f2da..000000000 --- a/calendar/libecal/.cvsignore +++ /dev/null @@ -1,10 +0,0 @@ -Makefile -Makefile.in -Evolution-DataServer-Calendar-common.c -Evolution-DataServer-Calendar-skels.c -Evolution-DataServer-Calendar-stubs.c -Evolution-DataServer-Calendar.h -client-test -e-cal-marshal.c -e-cal-marshal.h -libecal-1.0.pc diff --git a/calendar/libecal/Makefile.am b/calendar/libecal/Makefile.am deleted file mode 100644 index ffbce1d13..000000000 --- a/calendar/libecal/Makefile.am +++ /dev/null @@ -1,88 +0,0 @@ -INCLUDES = \ - -DEVOLUTION_LOCALEDIR=\""$(localedir)"\" \ - -DG_LOG_DOMAIN=\"libecal\" \ - -I$(top_srcdir)/calendar \ - -I$(srcdir) -I$(top_srcdir) \ - -I. \ - -I.. \ - -I$(top_builddir) \ - -I$(top_srcdir)/calendar/libical/src \ - -I$(top_builddir)/calendar/libical/src \ - -I$(top_srcdir)/calendar/libical/src/libical \ - -I$(top_builddir)/calendar/libical/src/libical \ - $(EVOLUTION_CALENDAR_CFLAGS) - -# The corba stubs and skels -CORBA_GENERATED_C = \ - Evolution-DataServer-Calendar-common.c \ - Evolution-DataServer-Calendar-skels.c \ - Evolution-DataServer-Calendar-stubs.c -CORBA_GENERATED_H = \ - Evolution-DataServer-Calendar.h - -CORBA_GENERATED = $(CORBA_GENERATED_C) $(CORBA_GENERATED_H) - -idls = \ - $(srcdir)/../idl/Evolution-DataServer-Calendar.idl - -idl_flags = $(IDL_INCLUDES) - -$(CORBA_GENERATED_H): $(idls) - $(ORBIT_IDL) $(idl_flags) $(srcdir)/../idl/Evolution-DataServer-Calendar.idl -$(CORBA_GENERATED_C): $(CORBA_GENERATED_H) - -# The marshallers -MARSHAL_GENERATED = e-cal-marshal.c e-cal-marshal.h -@EVO_MARSHAL_RULE@ - -# The library -lib_LTLIBRARIES = libecal.la - -libecal_la_SOURCES = \ - $(CORBA_GENERATED_C) \ - $(MARSHAL_GENERATED) \ - e-cal.c \ - e-cal-component.c \ - e-cal-listener.c \ - e-cal-recur.c \ - e-cal-time-util.c \ - e-cal-util.c \ - e-cal-view.c \ - e-cal-view-listener.c - -libecal_la_LIBADD = \ - $(EVOLUTION_CALENDAR_LIBS) \ - $(top_builddir)/calendar/libical/src/libical/libical-evolution.la \ - $(top_builddir)/calendar/libical/src/libicalvcal/libicalvcal-evolution.la \ - $(top_builddir)/calendar/libical/src/libicalss/libicalss-evolution.la \ - $(top_builddir)/libedataserver/libedataserver.la - -libecal_la_LDFLAGS = \ - -version-info $(LIBECAL_CURRENT):$(LIBECAL_REVISION):$(LIBECAL_AGE) - -libecalincludedir = $(privincludedir)/libecal - -libecalinclude_HEADERS = \ - $(CORBA_GENERATED_H) \ - e-cal.h \ - e-cal-component.h \ - e-cal-listener.h \ - e-cal-recur.h \ - e-cal-time-util.h \ - e-cal-types.h \ - e-cal-util.h \ - e-cal-view.h \ - e-cal-view-listener.h - -pkgconfigdir = $(libdir)/pkgconfig -pkgconfig_DATA = libecal-1.0.pc - -BUILT_SOURCES = $(CORBA_GENERATED) $(MARSHAL_GENERATED) -CLEANFILES = $(BUILT_SOURCES) - -EXTRA_DIST = \ - e-cal-marshal.list \ - $(pkgconfig_DATA:.pc=.pc.in) - -dist-hook: - cd $(distdir); rm -f $(BUILT_SOURCES) diff --git a/calendar/libecal/e-cal-component.c b/calendar/libecal/e-cal-component.c deleted file mode 100644 index ea226525c..000000000 --- a/calendar/libecal/e-cal-component.c +++ /dev/null @@ -1,5530 +0,0 @@ -/* Evolution calendar - iCalendar component object - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#include <config.h> -#include <string.h> -#include <stdlib.h> -#include <unistd.h> -#include <glib.h> -#include <libgnome/gnome-i18n.h> -#include "e-cal-component.h" -#include "e-cal-time-util.h" - - - -/* Extension property for alarm components so that we can reference them by UID */ -#define EVOLUTION_ALARM_UID_PROPERTY "X-EVOLUTION-ALARM-UID" - - -struct attendee { - icalproperty *prop; - icalparameter *cutype_param; - icalparameter *member_param; - icalparameter *role_param; - icalparameter *partstat_param; - icalparameter *rsvp_param; - icalparameter *delto_param; - icalparameter *delfrom_param; - icalparameter *sentby_param; - icalparameter *cn_param; - icalparameter *language_param; -}; - -/* Private part of the CalComponent structure */ -struct _ECalComponentPrivate { - /* The icalcomponent we wrap */ - icalcomponent *icalcomp; - - /* Properties */ - - icalproperty *uid; - - icalproperty *status; - GSList *attendee_list; - - icalproperty *categories; - - icalproperty *classification; - - struct text { - icalproperty *prop; - icalparameter *altrep_param; - }; - - GSList *comment_list; /* list of struct text */ - - icalproperty *completed; - - GSList *contact_list; /* list of struct text */ - - icalproperty *created; - - GSList *description_list; /* list of struct text */ - - struct datetime { - icalproperty *prop; - icalparameter *tzid_param; - }; - - struct datetime dtstart; - struct datetime dtend; - - icalproperty *dtstamp; - - /* The DURATION property can be used instead of the VEVENT DTEND or - the VTODO DUE dates. We do not use it directly ourselves, but we - must be able to handle it from incoming data. If a DTEND or DUE - is requested, we convert the DURATION if necessary. If DTEND or - DUE is set, we remove any DURATION. */ - icalproperty *duration; - - struct datetime due; - - GSList *exdate_list; /* list of struct datetime */ - GSList *exrule_list; /* list of icalproperty objects */ - - struct organizer { - icalproperty *prop; - icalparameter *sentby_param; - icalparameter *cn_param; - icalparameter *language_param; - }; - - struct organizer organizer; - - icalproperty *geo; - icalproperty *last_modified; - icalproperty *percent; - icalproperty *priority; - - struct period { - icalproperty *prop; - icalparameter *value_param; - }; - - struct recur_id { - struct datetime recur_time; - - icalparameter *range_param; - }; - - struct recur_id recur_id; - - GSList *rdate_list; /* list of struct period */ - - GSList *rrule_list; /* list of icalproperty objects */ - - icalproperty *sequence; - - struct { - icalproperty *prop; - icalparameter *altrep_param; - } summary; - - icalproperty *transparency; - icalproperty *url; - icalproperty *location; - - /* Subcomponents */ - - GHashTable *alarm_uid_hash; - - /* Whether we should increment the sequence number when piping the - * object over the wire. - */ - guint need_sequence_inc : 1; -}; - -/* Private structure for alarms */ -struct _ECalComponentAlarm { - /* Alarm icalcomponent we wrap */ - icalcomponent *icalcomp; - - /* Our extension UID property */ - icalproperty *uid; - - /* Properties */ - - icalproperty *action; - icalproperty *attach; /* FIXME: see scan_alarm_property() below */ - - struct { - icalproperty *prop; - icalparameter *altrep_param; - } description; - - icalproperty *duration; - icalproperty *repeat; - icalproperty *trigger; - - GSList *attendee_list; -}; - - - -static void e_cal_component_class_init (ECalComponentClass *klass); -static void e_cal_component_init (ECalComponent *comp, ECalComponentClass *klass); -static void e_cal_component_finalize (GObject *object); - -static GObjectClass *parent_class; - - - -/** - * e_cal_component_get_type: - * - * Registers the #ECalComponent class if necessary, and returns the type ID - * associated to it. - * - * Return value: The type ID of the #ECalComponent class. - **/ -GType -e_cal_component_get_type (void) -{ - static GType e_cal_component_type = 0; - - if (!e_cal_component_type) { - static GTypeInfo info = { - sizeof (ECalComponentClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_component_class_init, - NULL, NULL, - sizeof (ECalComponent), - 0, - (GInstanceInitFunc) e_cal_component_init - }; - e_cal_component_type = g_type_register_static (G_TYPE_OBJECT, "ECalComponent", &info, 0); - } - - return e_cal_component_type; -} - -/* Class initialization function for the calendar component object */ -static void -e_cal_component_class_init (ECalComponentClass *klass) -{ - GObjectClass *object_class; - - object_class = (GObjectClass *) klass; - - parent_class = g_type_class_peek_parent (klass); - - object_class->finalize = e_cal_component_finalize; -} - -/* Object initialization function for the calendar component object */ -static void -e_cal_component_init (ECalComponent *comp, ECalComponentClass *klass) -{ - ECalComponentPrivate *priv; - - priv = g_new0 (ECalComponentPrivate, 1); - comp->priv = priv; - - priv->alarm_uid_hash = g_hash_table_new (g_str_hash, g_str_equal); -} - -/* Does a simple g_free() of the elements of a GSList and then frees the list - * itself. Returns NULL. - */ -static GSList * -free_slist (GSList *slist) -{ - GSList *l; - - for (l = slist; l; l = l->next) - g_free (l->data); - - g_slist_free (slist); - return NULL; -} - -/* Used from g_hash_table_foreach_remove() to free the alarm UIDs hash table. - * We do not need to do anything to individual elements since we were storing - * the UID pointers inside the icalproperties themselves. - */ -static gboolean -free_alarm_cb (gpointer key, gpointer value, gpointer data) -{ - return TRUE; -} - -/* Frees the internal icalcomponent only if it does not have a parent. If it - * does, it means we don't own it and we shouldn't free it. - */ -static void -free_icalcomponent (ECalComponent *comp, gboolean free) -{ - ECalComponentPrivate *priv; - GSList *l; - - priv = comp->priv; - - if (!priv->icalcomp) - return; - - /* Free the icalcomponent */ - - if (free && icalcomponent_get_parent (priv->icalcomp) == NULL) { - icalcomponent_free (priv->icalcomp); - priv->icalcomp = NULL; - } - - /* Free the mappings */ - - priv->uid = NULL; - - priv->status = NULL; - - for (l = priv->attendee_list; l != NULL; l = l->next) - g_free (l->data); - g_slist_free (priv->attendee_list); - priv->attendee_list = NULL; - - priv->categories = NULL; - - priv->classification = NULL; - priv->comment_list = NULL; - priv->completed = NULL; - priv->contact_list = NULL; - priv->created = NULL; - - priv->description_list = free_slist (priv->description_list); - - priv->dtend.prop = NULL; - priv->dtend.tzid_param = NULL; - - priv->dtstamp = NULL; - - priv->dtstart.prop = NULL; - priv->dtstart.tzid_param = NULL; - - priv->due.prop = NULL; - priv->due.tzid_param = NULL; - - priv->duration = NULL; - - priv->exdate_list = free_slist (priv->exdate_list); - - g_slist_free (priv->exrule_list); - priv->exrule_list = NULL; - - priv->geo = NULL; - priv->last_modified = NULL; - priv->percent = NULL; - priv->priority = NULL; - - priv->rdate_list = free_slist (priv->rdate_list); - - g_slist_free (priv->rrule_list); - priv->rrule_list = NULL; - - priv->sequence = NULL; - - priv->summary.prop = NULL; - priv->summary.altrep_param = NULL; - - priv->transparency = NULL; - priv->url = NULL; - priv->location = NULL; - - /* Free the subcomponents */ - - g_hash_table_foreach_remove (priv->alarm_uid_hash, free_alarm_cb, NULL); - - /* Clean up */ - - priv->need_sequence_inc = FALSE; -} - -/* Finalize handler for the calendar component object */ -static void -e_cal_component_finalize (GObject *object) -{ - ECalComponent *comp; - ECalComponentPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (object)); - - comp = E_CAL_COMPONENT (object); - priv = comp->priv; - - free_icalcomponent (comp, TRUE); - g_hash_table_destroy (priv->alarm_uid_hash); - priv->alarm_uid_hash = NULL; - - g_free (priv); - comp->priv = NULL; - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - - - -/** - * e_cal_component_gen_uid: - * - * Generates a unique identifier suitable for calendar components. - * - * Return value: A unique identifier string. Every time this function is called - * a different string is returned. - **/ -char * -e_cal_component_gen_uid (void) -{ - char *iso, *ret; - static char *hostname; - time_t t = time (NULL); - static int serial; - - if (!hostname) { - static char buffer [512]; - - if ((gethostname (buffer, sizeof (buffer) - 1) == 0) && - (buffer [0] != 0)) - hostname = buffer; - else - hostname = "localhost"; - } - - iso = isodate_from_time_t (t); - ret = g_strdup_printf ("%s-%d-%d-%d-%d@%s", - iso, - getpid (), - getgid (), - getppid (), - serial++, - hostname); - g_free (iso); - - return ret; -} - -/** - * e_cal_component_new: - * - * Creates a new empty calendar component object. You should set it from an - * #icalcomponent structure by using e_cal_component_set_icalcomponent() or with a - * new empty component type by using e_cal_component_set_new_vtype(). - * - * Return value: A newly-created calendar component object. - **/ -ECalComponent * -e_cal_component_new (void) -{ - return E_CAL_COMPONENT (g_object_new (E_TYPE_CAL_COMPONENT, NULL)); -} - -/** - * e_cal_component_clone: - * @comp: A calendar component object. - * - * Creates a new calendar component object by copying the information from - * another one. - * - * Return value: A newly-created calendar component with the same values as the - * original one. - **/ -ECalComponent * -e_cal_component_clone (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - ECalComponent *new_comp; - icalcomponent *new_icalcomp; - - g_return_val_if_fail (comp != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), NULL); - - priv = comp->priv; - g_return_val_if_fail (priv->need_sequence_inc == FALSE, NULL); - - new_comp = e_cal_component_new (); - - if (priv->icalcomp) { - new_icalcomp = icalcomponent_new_clone (priv->icalcomp); - e_cal_component_set_icalcomponent (new_comp, new_icalcomp); - } - - return new_comp; -} - -/* Scans an attendee property */ -static void -scan_attendee (GSList **attendee_list, icalproperty *prop) -{ - struct attendee *attendee; - - attendee = g_new (struct attendee, 1); - attendee->prop = prop; - - attendee->cutype_param = icalproperty_get_first_parameter (prop, ICAL_CUTYPE_PARAMETER); - attendee->member_param = icalproperty_get_first_parameter (prop, ICAL_MEMBER_PARAMETER); - attendee->role_param = icalproperty_get_first_parameter (prop, ICAL_ROLE_PARAMETER); - attendee->partstat_param = icalproperty_get_first_parameter (prop, ICAL_PARTSTAT_PARAMETER); - attendee->rsvp_param = icalproperty_get_first_parameter (prop, ICAL_RSVP_PARAMETER); - attendee->delto_param = icalproperty_get_first_parameter (prop, ICAL_DELEGATEDTO_PARAMETER); - attendee->delfrom_param = icalproperty_get_first_parameter (prop, ICAL_DELEGATEDFROM_PARAMETER); - attendee->sentby_param = icalproperty_get_first_parameter (prop, ICAL_SENTBY_PARAMETER); - attendee->cn_param = icalproperty_get_first_parameter (prop, ICAL_CN_PARAMETER); - attendee->language_param = icalproperty_get_first_parameter (prop, ICAL_LANGUAGE_PARAMETER); - - *attendee_list = g_slist_append (*attendee_list, attendee); -} - -/* Scans a date/time and timezone pair property */ -static void -scan_datetime (ECalComponent *comp, struct datetime *datetime, icalproperty *prop) -{ - ECalComponentPrivate *priv; - - priv = comp->priv; - - datetime->prop = prop; - datetime->tzid_param = icalproperty_get_first_parameter (prop, ICAL_TZID_PARAMETER); -} - -/* Scans an exception date property */ -static void -scan_exdate (ECalComponent *comp, icalproperty *prop) -{ - ECalComponentPrivate *priv; - struct datetime *dt; - - priv = comp->priv; - - dt = g_new (struct datetime, 1); - dt->prop = prop; - dt->tzid_param = icalproperty_get_first_parameter (prop, ICAL_TZID_PARAMETER); - - priv->exdate_list = g_slist_append (priv->exdate_list, dt); -} - -/* Scans and attendee property */ -static void -scan_organizer (ECalComponent *comp, struct organizer *organizer, icalproperty *prop) -{ - organizer->prop = prop; - - organizer->sentby_param = icalproperty_get_first_parameter (prop, ICAL_SENTBY_PARAMETER); - organizer->cn_param = icalproperty_get_first_parameter (prop, ICAL_CN_PARAMETER); - organizer->language_param = icalproperty_get_first_parameter (prop, ICAL_LANGUAGE_PARAMETER); -} - -/* Scans an icalperiodtype property */ -static void -scan_period (ECalComponent *comp, GSList **list, icalproperty *prop) -{ - struct period *period; - - period = g_new (struct period, 1); - period->prop = prop; - period->value_param = icalproperty_get_first_parameter (prop, ICAL_VALUE_PARAMETER); - - *list = g_slist_append (*list, period); -} - - -/* Scans an icalrecurtype property */ -static void -scan_recur_id (ECalComponent *comp, struct recur_id *recur_id, icalproperty *prop) -{ - scan_datetime (comp, &recur_id->recur_time, prop); - - recur_id->range_param = icalproperty_get_first_parameter (prop, ICAL_RANGE_PARAMETER); -} - -/* Scans an icalrecurtype property */ -static void -scan_recur (ECalComponent *comp, GSList **list, icalproperty *prop) -{ - *list = g_slist_append (*list, prop); -} - -/* Scans the summary property */ -static void -scan_summary (ECalComponent *comp, icalproperty *prop) -{ - ECalComponentPrivate *priv; - - priv = comp->priv; - - priv->summary.prop = prop; - priv->summary.altrep_param = icalproperty_get_first_parameter (prop, ICAL_ALTREP_PARAMETER); -} - -/* Scans a text (i.e. text + altrep) property */ -static void -scan_text (ECalComponent *comp, GSList **text_list, icalproperty *prop) -{ - struct text *text; - - text = g_new (struct text, 1); - text->prop = prop; - text->altrep_param = icalproperty_get_first_parameter (prop, ICAL_ALTREP_PARAMETER); - - *text_list = g_slist_append (*text_list, text); -} - -/* Scans an icalproperty and adds its mapping to the component */ -static void -scan_property (ECalComponent *comp, icalproperty *prop) -{ - ECalComponentPrivate *priv; - icalproperty_kind kind; - - priv = comp->priv; - - kind = icalproperty_isa (prop); - - switch (kind) { - case ICAL_STATUS_PROPERTY: - priv->status = prop; - break; - - case ICAL_ATTENDEE_PROPERTY: - scan_attendee (&priv->attendee_list, prop); - break; - - case ICAL_CATEGORIES_PROPERTY: - priv->categories = prop; - break; - - case ICAL_CLASS_PROPERTY: - priv->classification = prop; - break; - - case ICAL_COMMENT_PROPERTY: - scan_text (comp, &priv->comment_list, prop); - break; - - case ICAL_COMPLETED_PROPERTY: - priv->completed = prop; - break; - - case ICAL_CONTACT_PROPERTY: - scan_text (comp, &priv->contact_list, prop); - break; - - case ICAL_CREATED_PROPERTY: - priv->created = prop; - break; - - case ICAL_DESCRIPTION_PROPERTY: - scan_text (comp, &priv->description_list, prop); - break; - - case ICAL_DTEND_PROPERTY: - scan_datetime (comp, &priv->dtend, prop); - break; - - case ICAL_DTSTAMP_PROPERTY: - priv->dtstamp = prop; - break; - - case ICAL_DTSTART_PROPERTY: - scan_datetime (comp, &priv->dtstart, prop); - break; - - case ICAL_DUE_PROPERTY: - scan_datetime (comp, &priv->due, prop); - break; - - case ICAL_DURATION_PROPERTY: - priv->duration = prop; - break; - - case ICAL_EXDATE_PROPERTY: - scan_exdate (comp, prop); - break; - - case ICAL_EXRULE_PROPERTY: - scan_recur (comp, &priv->exrule_list, prop); - break; - - case ICAL_GEO_PROPERTY: - priv->geo = prop; - break; - - case ICAL_LASTMODIFIED_PROPERTY: - priv->last_modified = prop; - break; - - case ICAL_ORGANIZER_PROPERTY: - scan_organizer (comp, &priv->organizer, prop); - break; - - case ICAL_PERCENTCOMPLETE_PROPERTY: - priv->percent = prop; - break; - - case ICAL_PRIORITY_PROPERTY: - priv->priority = prop; - break; - - case ICAL_RECURRENCEID_PROPERTY: - scan_recur_id (comp, &priv->recur_id, prop); - break; - - case ICAL_RDATE_PROPERTY: - scan_period (comp, &priv->rdate_list, prop); - break; - - case ICAL_RRULE_PROPERTY: - scan_recur (comp, &priv->rrule_list, prop); - break; - - case ICAL_SEQUENCE_PROPERTY: - priv->sequence = prop; - break; - - case ICAL_SUMMARY_PROPERTY: - scan_summary (comp, prop); - break; - - case ICAL_TRANSP_PROPERTY: - priv->transparency = prop; - break; - - case ICAL_UID_PROPERTY: - priv->uid = prop; - break; - - case ICAL_URL_PROPERTY: - priv->url = prop; - break; - - case ICAL_LOCATION_PROPERTY : - priv->location = prop; - break; - - default: - break; - } -} - -/* Gets our alarm UID string from a property that is known to contain it */ -static const char * -alarm_uid_from_prop (icalproperty *prop) -{ - const char *xstr; - - g_assert (icalproperty_isa (prop) == ICAL_X_PROPERTY); - - xstr = icalproperty_get_x (prop); - g_assert (xstr != NULL); - - return xstr; -} - -/* Sets our alarm UID extension property on an alarm component. Returns a - * pointer to the UID string inside the property itself. - */ -static const char * -set_alarm_uid (icalcomponent *alarm, const char *auid) -{ - icalproperty *prop; - const char *inprop_auid; - - /* Create the new property */ - - prop = icalproperty_new_x ((char *) auid); - icalproperty_set_x_name (prop, EVOLUTION_ALARM_UID_PROPERTY); - - icalcomponent_add_property (alarm, prop); - - inprop_auid = alarm_uid_from_prop (prop); - return inprop_auid; -} - -/* Removes any alarm UID extension properties from an alarm subcomponent */ -static void -remove_alarm_uid (icalcomponent *alarm) -{ - icalproperty *prop; - GSList *list, *l; - - list = NULL; - - for (prop = icalcomponent_get_first_property (alarm, ICAL_X_PROPERTY); - prop; - prop = icalcomponent_get_next_property (alarm, ICAL_X_PROPERTY)) { - const char *xname; - - xname = icalproperty_get_x_name (prop); - g_assert (xname != NULL); - - if (strcmp (xname, EVOLUTION_ALARM_UID_PROPERTY) == 0) - list = g_slist_prepend (list, prop); - } - - for (l = list; l; l = l->next) { - prop = l->data; - icalcomponent_remove_property (alarm, prop); - icalproperty_free (prop); - } - - g_slist_free (list); -} - -/* Adds an alarm subcomponent to the calendar component's mapping table. The - * actual UID with which it gets added may not be the same as the specified one; - * this function will change it if the table already had an alarm subcomponent - * with the specified UID. Returns the actual UID used. - */ -static const char * -add_alarm (ECalComponent *comp, icalcomponent *alarm, const char *auid) -{ - ECalComponentPrivate *priv; - icalcomponent *old_alarm; - - priv = comp->priv; - - /* First we see if we already have an alarm with the requested UID. In - * that case, we need to change the new UID to something else. This - * should never happen, but who knows. - */ - - old_alarm = g_hash_table_lookup (priv->alarm_uid_hash, auid); - if (old_alarm != NULL) { - char *new_auid; - - g_message ("add_alarm(): Got alarm with duplicated UID `%s', changing it...", auid); - - remove_alarm_uid (alarm); - - new_auid = e_cal_component_gen_uid (); - auid = set_alarm_uid (alarm, new_auid); - g_free (new_auid); - } - - g_hash_table_insert (priv->alarm_uid_hash, (char *) auid, alarm); - return auid; -} - -/* Scans an alarm subcomponent, adds an UID extension property to it (so that we - * can reference alarms by unique IDs), and adds its mapping to the component. */ -static void -scan_alarm (ECalComponent *comp, icalcomponent *alarm) -{ - ECalComponentPrivate *priv; - icalproperty *prop; - const char *auid; - char *new_auid; - - priv = comp->priv; - - for (prop = icalcomponent_get_first_property (alarm, ICAL_X_PROPERTY); - prop; - prop = icalcomponent_get_next_property (alarm, ICAL_X_PROPERTY)) { - const char *xname; - - xname = icalproperty_get_x_name (prop); - g_assert (xname != NULL); - - if (strcmp (xname, EVOLUTION_ALARM_UID_PROPERTY) == 0) { - auid = alarm_uid_from_prop (prop); - add_alarm (comp, alarm, auid); - return; - } - } - - /* The component has no alarm UID property, so we create one. */ - - new_auid = e_cal_component_gen_uid (); - auid = set_alarm_uid (alarm, new_auid); - g_free (new_auid); - - add_alarm (comp, alarm, auid); -} - -/* Scans an icalcomponent for its properties so that we can provide - * random-access to them. It also builds a hash table of the component's alarm - * subcomponents. - */ -static void -scan_icalcomponent (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - icalproperty *prop; - icalcompiter iter; - - priv = comp->priv; - - g_assert (priv->icalcomp != NULL); - - /* Scan properties */ - - for (prop = icalcomponent_get_first_property (priv->icalcomp, ICAL_ANY_PROPERTY); - prop; - prop = icalcomponent_get_next_property (priv->icalcomp, ICAL_ANY_PROPERTY)) - scan_property (comp, prop); - - /* Scan subcomponents */ - - for (iter = icalcomponent_begin_component (priv->icalcomp, ICAL_VALARM_COMPONENT); - icalcompiter_deref (&iter) != NULL; - icalcompiter_next (&iter)) { - icalcomponent *subcomp; - - subcomp = icalcompiter_deref (&iter); - scan_alarm (comp, subcomp); - } -} - -/* Ensures that the mandatory calendar component properties (uid, dtstamp) do - * exist. If they don't exist, it creates them automatically. - */ -static void -ensure_mandatory_properties (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - priv = comp->priv; - g_assert (priv->icalcomp != NULL); - - if (!priv->uid) { - char *uid; - - uid = e_cal_component_gen_uid (); - priv->uid = icalproperty_new_uid (uid); - g_free (uid); - - icalcomponent_add_property (priv->icalcomp, priv->uid); - } - - if (!priv->dtstamp) { - struct icaltimetype t; - - t = icaltime_current_time_with_zone (icaltimezone_get_utc_timezone ()); - - priv->dtstamp = icalproperty_new_dtstamp (t); - icalcomponent_add_property (priv->icalcomp, priv->dtstamp); - } -} - -/** - * e_cal_component_set_new_vtype: - * @comp: A calendar component object. - * @type: Type of calendar component to create. - * - * Clears any existing component data from a calendar component object and - * creates a new #icalcomponent of the specified type for it. The only property - * that will be set in the new component will be its unique identifier. - **/ -void -e_cal_component_set_new_vtype (ECalComponent *comp, ECalComponentVType type) -{ - ECalComponentPrivate *priv; - icalcomponent *icalcomp; - icalcomponent_kind kind; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - - free_icalcomponent (comp, TRUE); - - if (type == E_CAL_COMPONENT_NO_TYPE) - return; - - /* Figure out the kind and create the icalcomponent */ - - switch (type) { - case E_CAL_COMPONENT_EVENT: - kind = ICAL_VEVENT_COMPONENT; - break; - - case E_CAL_COMPONENT_TODO: - kind = ICAL_VTODO_COMPONENT; - break; - - case E_CAL_COMPONENT_JOURNAL: - kind = ICAL_VJOURNAL_COMPONENT; - break; - - case E_CAL_COMPONENT_FREEBUSY: - kind = ICAL_VFREEBUSY_COMPONENT; - break; - - case E_CAL_COMPONENT_TIMEZONE: - kind = ICAL_VTIMEZONE_COMPONENT; - break; - - default: - g_assert_not_reached (); - kind = ICAL_NO_COMPONENT; - } - - icalcomp = icalcomponent_new (kind); - if (!icalcomp) { - g_message ("e_cal_component_set_new_vtype(): Could not create the icalcomponent!"); - return; - } - - /* Scan the component to build our mapping table */ - - priv->icalcomp = icalcomp; - scan_icalcomponent (comp); - - /* Add missing stuff */ - - ensure_mandatory_properties (comp); -} - -/** - * e_cal_component_set_icalcomponent: - * @comp: A calendar component object. - * @icalcomp: An #icalcomponent. - * - * Sets the contents of a calendar component object from an #icalcomponent - * structure. If the @comp already had an #icalcomponent set into it, it will - * will be freed automatically if the #icalcomponent does not have a parent - * component itself. - * - * Supported component types are VEVENT, VTODO, VJOURNAL, VFREEBUSY, and VTIMEZONE. - * - * Return value: TRUE on success, FALSE if @icalcomp is an unsupported component - * type. - **/ -gboolean -e_cal_component_set_icalcomponent (ECalComponent *comp, icalcomponent *icalcomp) -{ - ECalComponentPrivate *priv; - icalcomponent_kind kind; - - g_return_val_if_fail (comp != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE); - - priv = comp->priv; - - if (priv->icalcomp == icalcomp) - return TRUE; - - free_icalcomponent (comp, TRUE); - - if (!icalcomp) { - priv->icalcomp = NULL; - return TRUE; - } - - kind = icalcomponent_isa (icalcomp); - - if (!(kind == ICAL_VEVENT_COMPONENT - || kind == ICAL_VTODO_COMPONENT - || kind == ICAL_VJOURNAL_COMPONENT - || kind == ICAL_VFREEBUSY_COMPONENT - || kind == ICAL_VTIMEZONE_COMPONENT)) - return FALSE; - - priv->icalcomp = icalcomp; - - scan_icalcomponent (comp); - ensure_mandatory_properties (comp); - - return TRUE; -} - -/** - * e_cal_component_get_icalcomponent: - * @comp: A calendar component object. - * - * Queries the #icalcomponent structure that a calendar component object is - * wrapping. - * - * Return value: An #icalcomponent structure, or NULL if the @comp has no - * #icalcomponent set to it. - **/ -icalcomponent * -e_cal_component_get_icalcomponent (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_val_if_fail (comp != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), NULL); - - priv = comp->priv; - g_return_val_if_fail (priv->need_sequence_inc == FALSE, NULL); - - return priv->icalcomp; -} - -void -e_cal_component_rescan (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - - /* Clear everything out */ - free_icalcomponent (comp, FALSE); - - /* Rescan */ - scan_icalcomponent (comp); - ensure_mandatory_properties (comp); -} - -void -e_cal_component_strip_errors (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - - icalcomponent_strip_errors (priv->icalcomp); -} - -/** - * e_cal_component_get_vtype: - * @comp: A calendar component object. - * - * Queries the type of a calendar component object. - * - * Return value: The type of the component, as defined by RFC 2445. - **/ -ECalComponentVType -e_cal_component_get_vtype (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - icalcomponent_kind kind; - - g_return_val_if_fail (comp != NULL, E_CAL_COMPONENT_NO_TYPE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), E_CAL_COMPONENT_NO_TYPE); - - priv = comp->priv; - g_return_val_if_fail (priv->icalcomp != NULL, E_CAL_COMPONENT_NO_TYPE); - - kind = icalcomponent_isa (priv->icalcomp); - switch (kind) { - case ICAL_VEVENT_COMPONENT: - return E_CAL_COMPONENT_EVENT; - - case ICAL_VTODO_COMPONENT: - return E_CAL_COMPONENT_TODO; - - case ICAL_VJOURNAL_COMPONENT: - return E_CAL_COMPONENT_JOURNAL; - - case ICAL_VFREEBUSY_COMPONENT: - return E_CAL_COMPONENT_FREEBUSY; - - case ICAL_VTIMEZONE_COMPONENT: - return E_CAL_COMPONENT_TIMEZONE; - - default: - /* We should have been loaded with a supported type! */ - g_assert_not_reached (); - return E_CAL_COMPONENT_NO_TYPE; - } -} - -/** - * e_cal_component_get_as_string: - * @comp: A calendar component. - * - * Gets the iCalendar string representation of a calendar component. You should - * call e_cal_component_commit_sequence() before this function to ensure that the - * component's sequence number is consistent with the state of the object. - * - * Return value: String representation of the calendar component according to - * RFC 2445. - **/ -char * -e_cal_component_get_as_string (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - char *str, *buf; - - g_return_val_if_fail (comp != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), NULL); - - priv = comp->priv; - g_return_val_if_fail (priv->icalcomp != NULL, NULL); - - /* Ensure that the user has committed the new SEQUENCE */ - g_return_val_if_fail (priv->need_sequence_inc == FALSE, NULL); - - /* We dup the string; libical owns that memory */ - - str = icalcomponent_as_ical_string (priv->icalcomp); - - if (str) - buf = g_strdup (str); - else - buf = NULL; - - return buf; -} - -/* Used from g_hash_table_foreach(); ensures that an alarm subcomponent - * has the mandatory properties it needs. - */ -static void -ensure_alarm_properties_cb (gpointer key, gpointer value, gpointer data) -{ - ECalComponent *comp; - ECalComponentPrivate *priv; - icalcomponent *alarm; - icalproperty *prop; - enum icalproperty_action action; - const char *str; - - alarm = value; - - comp = E_CAL_COMPONENT (data); - priv = comp->priv; - - prop = icalcomponent_get_first_property (alarm, ICAL_ACTION_PROPERTY); - if (!prop) - return; - - action = icalproperty_get_action (prop); - - switch (action) { - case ICAL_ACTION_DISPLAY: - /* Ensure we have a DESCRIPTION property */ - prop = icalcomponent_get_first_property (alarm, ICAL_DESCRIPTION_PROPERTY); - if (prop) - break; - - if (!priv->summary.prop) - str = _("Untitled appointment"); - else - str = icalproperty_get_summary (priv->summary.prop); - - prop = icalproperty_new_description (str); - icalcomponent_add_property (alarm, prop); - - break; - - default: - break; - /* FIXME: add other action types here */ - } -} - -/* Ensures that alarm subcomponents have the mandatory properties they need, - * even when clients may not have set them properly. - */ -static void -ensure_alarm_properties (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - priv = comp->priv; - - g_hash_table_foreach (priv->alarm_uid_hash, ensure_alarm_properties_cb, comp); -} - -/** - * e_cal_component_commit_sequence: - * @comp: - * - * Increments the sequence number property in a calendar component object if it - * needs it. This needs to be done when any of a number of properties listed in - * RFC 2445 change values, such as the start and end dates of a component. - * - * This function must be called before calling e_cal_component_get_as_string() to - * ensure that the component is fully consistent. - **/ -void -e_cal_component_commit_sequence (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - ensure_alarm_properties (comp); - - if (!priv->need_sequence_inc) - return; - - if (priv->sequence) { - int seq; - - seq = icalproperty_get_sequence (priv->sequence); - icalproperty_set_sequence (priv->sequence, seq + 1); - } else { - /* The component had no SEQUENCE property, so assume that the - * default would have been zero. Since it needed incrementing - * anyways, we use a value of 1 here. - */ - priv->sequence = icalproperty_new_sequence (1); - icalcomponent_add_property (priv->icalcomp, priv->sequence); - } - - priv->need_sequence_inc = FALSE; -} - -void -e_cal_component_abort_sequence (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - - priv->need_sequence_inc = FALSE; -} - -/** - * e_cal_component_get_uid: - * @comp: A calendar component object. - * @uid: Return value for the UID string. - * - * Queries the unique identifier of a calendar component object. - **/ -void -e_cal_component_get_uid (ECalComponent *comp, const char **uid) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (uid != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - /* This MUST exist, since we ensured that it did */ - g_assert (priv->uid != NULL); - - *uid = icalproperty_get_uid (priv->uid); -} - -/** - * e_cal_component_set_uid: - * @comp: A calendar component object. - * @uid: Unique identifier. - * - * Sets the unique identifier string of a calendar component object. - **/ -void -e_cal_component_set_uid (ECalComponent *comp, const char *uid) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (uid != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - /* This MUST exist, since we ensured that it did */ - g_assert (priv->uid != NULL); - - icalproperty_set_uid (priv->uid, (char *) uid); -} - -/** - * e_cal_component_get_categories: - * @comp: A calendar component object. - * @categories: - * - * - **/ -void -e_cal_component_get_categories (ECalComponent *comp, const char **categories) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (categories != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (priv->categories) - *categories = icalproperty_get_categories (priv->categories); - else - *categories = NULL; -} - -/** - * e_cal_component_set_categories: - * @comp: A calendar component object. - * @categories: - * - * - **/ -void -e_cal_component_set_categories (ECalComponent *comp, const char *categories) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!categories || !(*categories)) { - if (priv->categories) { - icalcomponent_remove_property (priv->icalcomp, priv->categories); - icalproperty_free (priv->categories); - priv->url = NULL; - } - - return; - } - - if (priv->categories) - icalproperty_set_categories (priv->categories, (char *) categories); - else { - priv->categories = icalproperty_new_categories ((char *) categories); - icalcomponent_add_property (priv->icalcomp, priv->categories); - } -} - - -/** - * e_cal_component_get_categories_list: - * @comp: A calendar component object. - * @categ_list: Return value for the list of strings, where each string is a - * category. This should be freed using e_cal_component_free_categories_list(). - * - * Queries the list of categories of a calendar component object. Each element - * in the returned categ_list is a string with the corresponding category. - **/ -void -e_cal_component_get_categories_list (ECalComponent *comp, GSList **categ_list) -{ - ECalComponentPrivate *priv; - const char *categories; - const char *p; - const char *cat_start; - char *str; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (categ_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!priv->categories) { - *categ_list = NULL; - return; - } - - categories = icalproperty_get_categories (priv->categories); - g_assert (categories != NULL); - - cat_start = categories; - *categ_list = NULL; - - for (p = categories; *p; p++) - if (*p == ',') { - str = g_strndup (cat_start, p - cat_start); - *categ_list = g_slist_prepend (*categ_list, str); - - cat_start = p + 1; - } - - str = g_strndup (cat_start, p - cat_start); - *categ_list = g_slist_prepend (*categ_list, str); - - *categ_list = g_slist_reverse (*categ_list); -} - -/* Creates a comma-delimited string of categories */ -static char * -stringify_categories (GSList *categ_list) -{ - GString *s; - GSList *l; - char *str; - - s = g_string_new (NULL); - - for (l = categ_list; l; l = l->next) { - g_string_append (s, l->data); - - if (l->next != NULL) - g_string_append (s, ","); - } - - str = s->str; - g_string_free (s, FALSE); - - return str; -} - -/** - * e_cal_component_set_categories_list: - * @comp: A calendar component object. - * @categ_list: List of strings, one for each category. - * - * Sets the list of categories of a calendar component object. - **/ -void -e_cal_component_set_categories_list (ECalComponent *comp, GSList *categ_list) -{ - ECalComponentPrivate *priv; - char *categories_str; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!categ_list) { - if (priv->categories) { - icalcomponent_remove_property (priv->icalcomp, priv->categories); - icalproperty_free (priv->categories); - } - - return; - } - - /* Create a single string of categories */ - categories_str = stringify_categories (categ_list); - - /* Set the categories */ - priv->categories = icalproperty_new_categories (categories_str); - g_free (categories_str); - - icalcomponent_add_property (priv->icalcomp, priv->categories); -} - -/** - * e_cal_component_get_classification: - * @comp: A calendar component object. - * @classif: Return value for the classification. - * - * Queries the classification of a calendar component object. If the - * classification property is not set on this component, this function returns - * #E_CAL_COMPONENT_CLASS_NONE. - **/ -void -e_cal_component_get_classification (ECalComponent *comp, ECalComponentClassification *classif) -{ - ECalComponentPrivate *priv; - icalproperty_class class; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (classif != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!priv->classification) { - *classif = E_CAL_COMPONENT_CLASS_NONE; - return; - } - - class = icalproperty_get_class (priv->classification); - - switch (class) - { - case ICAL_CLASS_PUBLIC: - *classif = E_CAL_COMPONENT_CLASS_PUBLIC; - break; - case ICAL_CLASS_PRIVATE: - *classif = E_CAL_COMPONENT_CLASS_PRIVATE; - break; - case ICAL_CLASS_CONFIDENTIAL: - *classif = E_CAL_COMPONENT_CLASS_CONFIDENTIAL; - break; - default: - *classif = E_CAL_COMPONENT_CLASS_UNKNOWN; - break; - } -} - -/** - * e_cal_component_set_classification: - * @comp: A calendar component object. - * @classif: Classification to use. - * - * Sets the classification property of a calendar component object. To unset - * the property, specify E_CAL_COMPONENT_CLASS_NONE for @classif. - **/ -void -e_cal_component_set_classification (ECalComponent *comp, ECalComponentClassification classif) -{ - ECalComponentPrivate *priv; - icalproperty_class class; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (classif != E_CAL_COMPONENT_CLASS_UNKNOWN); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (classif == E_CAL_COMPONENT_CLASS_NONE) { - if (priv->classification) { - icalcomponent_remove_property (priv->icalcomp, priv->classification); - icalproperty_free (priv->classification); - priv->classification = NULL; - } - - return; - } - - switch (classif) { - case E_CAL_COMPONENT_CLASS_PUBLIC: - class = ICAL_CLASS_PUBLIC; - break; - - case E_CAL_COMPONENT_CLASS_PRIVATE: - class = ICAL_CLASS_PRIVATE; - break; - - case E_CAL_COMPONENT_CLASS_CONFIDENTIAL: - class = ICAL_CLASS_CONFIDENTIAL; - break; - - default: - g_assert_not_reached (); - class = ICAL_CLASS_NONE; - } - - if (priv->classification) - icalproperty_set_class (priv->classification, class); - else { - priv->classification = icalproperty_new_class (class); - icalcomponent_add_property (priv->icalcomp, priv->classification); - } -} - -/* Gets a text list value */ -static void -get_text_list (GSList *text_list, - const char *(* get_prop_func) (const icalproperty *prop), - GSList **tl) -{ - GSList *l; - - *tl = NULL; - - if (!text_list) - return; - - for (l = text_list; l; l = l->next) { - struct text *text; - ECalComponentText *t; - - text = l->data; - g_assert (text->prop != NULL); - - t = g_new (ECalComponentText, 1); - t->value = (* get_prop_func) (text->prop); - - if (text->altrep_param) - t->altrep = icalparameter_get_altrep (text->altrep_param); - else - t->altrep = NULL; - - *tl = g_slist_prepend (*tl, t); - } - - *tl = g_slist_reverse (*tl); -} - -/* Sets a text list value */ -static void -set_text_list (ECalComponent *comp, - icalproperty *(* new_prop_func) (const char *value), - GSList **text_list, - GSList *tl) -{ - ECalComponentPrivate *priv; - GSList *l; - - priv = comp->priv; - - /* Remove old texts */ - - for (l = *text_list; l; l = l->next) { - struct text *text; - - text = l->data; - g_assert (text->prop != NULL); - - icalcomponent_remove_property (priv->icalcomp, text->prop); - icalproperty_free (text->prop); - g_free (text); - } - - g_slist_free (*text_list); - *text_list = NULL; - - /* Add in new texts */ - - for (l = tl; l; l = l->next) { - ECalComponentText *t; - struct text *text; - - t = l->data; - g_return_if_fail (t->value != NULL); - - text = g_new (struct text, 1); - - text->prop = (* new_prop_func) ((char *) t->value); - icalcomponent_add_property (priv->icalcomp, text->prop); - - if (t->altrep) { - text->altrep_param = icalparameter_new_altrep ((char *) t->altrep); - icalproperty_add_parameter (text->prop, text->altrep_param); - } else - text->altrep_param = NULL; - - *text_list = g_slist_prepend (*text_list, text); - } - - *text_list = g_slist_reverse (*text_list); -} - -/** - * e_cal_component_get_comment_list: - * @comp: A calendar component object. - * @text_list: Return value for the comment properties and their parameters, as - * a list of #ECalComponentText structures. This should be freed using the - * e_cal_component_free_text_list() function. - * - * Queries the comment of a calendar component object. The comment property can - * appear several times inside a calendar component, and so a list of - * #ECalComponentText is returned. - **/ -void -e_cal_component_get_comment_list (ECalComponent *comp, GSList **text_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (text_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_text_list (priv->comment_list, icalproperty_get_comment, text_list); -} - -/** - * e_cal_component_set_comment_list: - * @comp: A calendar component object. - * @text_list: List of #ECalComponentText structures. - * - * Sets the comment of a calendar component object. The comment property can - * appear several times inside a calendar component, and so a list of - * #ECalComponentText structures is used. - **/ -void -e_cal_component_set_comment_list (ECalComponent *comp, GSList *text_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_text_list (comp, icalproperty_new_comment, &priv->comment_list, text_list); -} - -/** - * e_cal_component_get_contact_list: - * @comp: A calendar component object. - * @text_list: Return value for the contact properties and their parameters, as - * a list of #ECalComponentText structures. This should be freed using the - * e_cal_component_free_text_list() function. - * - * Queries the contact of a calendar component object. The contact property can - * appear several times inside a calendar component, and so a list of - * #ECalComponentText is returned. - **/ -void -e_cal_component_get_contact_list (ECalComponent *comp, GSList **text_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (text_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_text_list (priv->contact_list, icalproperty_get_contact, text_list); -} - -/** - * e_cal_component_set_contact_list: - * @comp: A calendar component object. - * @text_list: List of #ECalComponentText structures. - * - * Sets the contact of a calendar component object. The contact property can - * appear several times inside a calendar component, and so a list of - * #ECalComponentText structures is used. - **/ -void -e_cal_component_set_contact_list (ECalComponent *comp, GSList *text_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_text_list (comp, icalproperty_new_contact, &priv->contact_list, text_list); -} - -/* Gets a struct icaltimetype value */ -static void -get_icaltimetype (icalproperty *prop, - struct icaltimetype (* get_prop_func) (const icalproperty *prop), - struct icaltimetype **t) -{ - if (!prop) { - *t = NULL; - return; - } - - *t = g_new (struct icaltimetype, 1); - **t = (* get_prop_func) (prop); -} - -/* Sets a struct icaltimetype value */ -static void -set_icaltimetype (ECalComponent *comp, icalproperty **prop, - icalproperty *(* prop_new_func) (struct icaltimetype v), - void (* prop_set_func) (icalproperty *prop, struct icaltimetype v), - struct icaltimetype *t) -{ - ECalComponentPrivate *priv; - - priv = comp->priv; - - if (!t) { - if (*prop) { - icalcomponent_remove_property (priv->icalcomp, *prop); - icalproperty_free (*prop); - *prop = NULL; - } - - return; - } - - if (*prop) - (* prop_set_func) (*prop, *t); - else { - *prop = (* prop_new_func) (*t); - icalcomponent_add_property (priv->icalcomp, *prop); - } -} - -/** - * e_cal_component_get_completed: - * @comp: A calendar component object. - * @t: Return value for the completion date. This should be freed using the - * e_cal_component_free_icaltimetype() function. - * - * Queries the date at which a calendar compoment object was completed. - **/ -void -e_cal_component_get_completed (ECalComponent *comp, struct icaltimetype **t) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (t != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_icaltimetype (priv->completed, icalproperty_get_completed, t); -} - -/** - * e_cal_component_set_completed: - * @comp: A calendar component object. - * @t: Value for the completion date. - * - * Sets the date at which a calendar component object was completed. - **/ -void -e_cal_component_set_completed (ECalComponent *comp, struct icaltimetype *t) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_icaltimetype (comp, &priv->completed, - icalproperty_new_completed, - icalproperty_set_completed, - t); -} - - -/** - * e_cal_component_get_created: - * @comp: A calendar component object. - * @t: Return value for the creation date. This should be freed using the - * e_cal_component_free_icaltimetype() function. - * - * Queries the date in which a calendar component object was created in the - * calendar store. - **/ -void -e_cal_component_get_created (ECalComponent *comp, struct icaltimetype **t) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (t != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_icaltimetype (priv->created, icalproperty_get_created, t); -} - -/** - * e_cal_component_set_created: - * @comp: A calendar component object. - * @t: Value for the creation date. - * - * Sets the date in which a calendar component object is created in the calendar - * store. This should only be used inside a calendar store application, i.e. - * not by calendar user agents. - **/ -void -e_cal_component_set_created (ECalComponent *comp, struct icaltimetype *t) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_icaltimetype (comp, &priv->created, - icalproperty_new_created, - icalproperty_set_created, - t); -} - -/** - * e_cal_component_get_description_list: - * @comp: A calendar component object. - * @text_list: Return value for the description properties and their parameters, - * as a list of #ECalComponentText structures. This should be freed using the - * e_cal_component_free_text_list() function. - * - * Queries the description of a calendar component object. Journal components - * may have more than one description, and as such this function returns a list - * of #ECalComponentText structures. All other types of components can have at - * most one description. - **/ -void -e_cal_component_get_description_list (ECalComponent *comp, GSList **text_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (text_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_text_list (priv->description_list, icalproperty_get_description, text_list); -} - -/** - * e_cal_component_set_description_list: - * @comp: A calendar component object. - * @text_list: List of #ECalComponentSummary structures. - * - * Sets the description of a calendar component object. Journal components may - * have more than one description, and as such this function takes in a list of - * #ECalComponentDescription structures. All other types of components can have - * at most one description. - **/ -void -e_cal_component_set_description_list (ECalComponent *comp, GSList *text_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_text_list (comp, icalproperty_new_description, &priv->description_list, text_list); -} - -/* Gets a date/time and timezone pair */ -static void -get_datetime (struct datetime *datetime, - struct icaltimetype (* get_prop_func) (const icalproperty *prop), - ECalComponentDateTime *dt) -{ - if (datetime->prop) { - dt->value = g_new (struct icaltimetype, 1); - *dt->value = (* get_prop_func) (datetime->prop); - } else - dt->value = NULL; - - /* If the icaltimetype has is_utc set, we set "UTC" as the TZID. - This makes the timezone code simpler. */ - if (datetime->tzid_param) - dt->tzid = g_strdup (icalparameter_get_tzid (datetime->tzid_param)); - else if (dt->value && dt->value->is_utc) - dt->tzid = g_strdup ("UTC"); - else - dt->tzid = NULL; -} - -/* Sets a date/time and timezone pair */ -static void -set_datetime (ECalComponent *comp, struct datetime *datetime, - icalproperty *(* prop_new_func) (struct icaltimetype v), - void (* prop_set_func) (icalproperty * prop, struct icaltimetype v), - ECalComponentDateTime *dt) -{ - ECalComponentPrivate *priv; - - priv = comp->priv; - - /* If we are setting the property to NULL (i.e. removing it), then - we remove it if it exists. */ - if (!dt) { - if (datetime->prop) { - icalcomponent_remove_property (priv->icalcomp, datetime->prop); - icalproperty_free (datetime->prop); - - datetime->prop = NULL; - datetime->tzid_param = NULL; - } - - return; - } - - g_return_if_fail (dt->value != NULL); - - /* If the TZID is set to "UTC", we set the is_utc flag. */ - if (dt->tzid && !strcmp (dt->tzid, "UTC")) - dt->value->is_utc = 1; - else - dt->value->is_utc = 0; - - if (datetime->prop) { - (* prop_set_func) (datetime->prop, *dt->value); - } else { - datetime->prop = (* prop_new_func) (*dt->value); - icalcomponent_add_property (priv->icalcomp, datetime->prop); - } - - /* If the TZID is set to "UTC", we don't want to save the TZID. */ - if (dt->tzid && strcmp (dt->tzid, "UTC")) { - g_assert (datetime->prop != NULL); - - if (datetime->tzid_param) { - icalparameter_set_tzid (datetime->tzid_param, (char *) dt->tzid); - } else { - datetime->tzid_param = icalparameter_new_tzid ((char *) dt->tzid); - icalproperty_add_parameter (datetime->prop, datetime->tzid_param); - } - } else if (datetime->tzid_param) { - icalproperty_remove_parameter (datetime->prop, ICAL_TZID_PARAMETER); - datetime->tzid_param = NULL; - } -} - - -/* This tries to get the DTSTART + DURATION for a VEVENT or VTODO. In a - VEVENT this is used for the DTEND if no DTEND exists, In a VTOTO it is - used for the DUE date if DUE doesn't exist. */ -static void -e_cal_component_get_start_plus_duration (ECalComponent *comp, - ECalComponentDateTime *dt) -{ - ECalComponentPrivate *priv; - struct icaldurationtype duration; - - priv = comp->priv; - - if (!priv->duration) - return; - - /* Get the DTSTART time. */ - get_datetime (&priv->dtstart, icalproperty_get_dtstart, dt); - if (!dt->value) - return; - - duration = icalproperty_get_duration (priv->duration); - - /* The DURATION shouldn't be negative, but just return DTSTART if it - is, i.e. assume it is 0. */ - if (duration.is_neg) - return; - - /* If DTSTART is a DATE value, then we need to check if the DURATION - includes any hours, minutes or seconds. If it does, we need to - make the DTEND/DUE a DATE-TIME value. */ - duration.days += duration.weeks * 7; - if (dt->value->is_date) { - if (duration.hours != 0 || duration.minutes != 0 - || duration.seconds != 0) { - dt->value->is_date = 0; - } - } - - /* Add on the DURATION. */ - icaltime_adjust (dt->value, duration.days, duration.hours, - duration.minutes, duration.seconds); -} - - -/** - * e_cal_component_get_dtend: - * @comp: A calendar component object. - * @dt: Return value for the date/time end. This should be freed with the - * e_cal_component_free_datetime() function. - * - * Queries the date/time end of a calendar component object. - **/ -void -e_cal_component_get_dtend (ECalComponent *comp, ECalComponentDateTime *dt) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (dt != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_datetime (&priv->dtend, icalproperty_get_dtend, dt); - - /* If we don't have a DTEND property, then we try to get DTSTART - + DURATION. */ - if (!dt->value) - e_cal_component_get_start_plus_duration (comp, dt); -} - -/** - * e_cal_component_set_dtend: - * @comp: A calendar component object. - * @dt: End date/time. - * - * Sets the date/time end property of a calendar component object. - **/ -void -e_cal_component_set_dtend (ECalComponent *comp, ECalComponentDateTime *dt) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_datetime (comp, &priv->dtend, - icalproperty_new_dtend, - icalproperty_set_dtend, - dt); - - /* Make sure we remove any existing DURATION property, as it can't be - used with a DTEND. If DTEND is set to NULL, i.e. removed, we also - want to remove any DURATION. */ - if (priv->duration) { - icalcomponent_remove_property (priv->icalcomp, priv->duration); - icalproperty_free (priv->duration); - priv->duration = NULL; - } - - priv->need_sequence_inc = TRUE; -} - -/** - * e_cal_component_get_dtstamp: - * @comp: A calendar component object. - * @t: A value for the date/timestamp. - * - * Queries the date/timestamp property of a calendar component object, which is - * the last time at which the object was modified by a calendar user agent. - **/ -void -e_cal_component_get_dtstamp (ECalComponent *comp, struct icaltimetype *t) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (t != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - /* This MUST exist, since we ensured that it did */ - g_assert (priv->dtstamp != NULL); - - *t = icalproperty_get_dtstamp (priv->dtstamp); -} - -/** - * e_cal_component_set_dtstamp: - * @comp: A calendar component object. - * @t: Date/timestamp value. - * - * Sets the date/timestamp of a calendar component object. This should be - * called whenever a calendar user agent makes a change to a component's - * properties. - **/ -void -e_cal_component_set_dtstamp (ECalComponent *comp, struct icaltimetype *t) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (t != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - /* This MUST exist, since we ensured that it did */ - g_assert (priv->dtstamp != NULL); - - icalproperty_set_dtstamp (priv->dtstamp, *t); -} - -/** - * e_cal_component_get_dtstart: - * @comp: A calendar component object. - * @dt: Return value for the date/time start. This should be freed with the - * e_cal_component_free_datetime() function. - * - * Queries the date/time start of a calendar component object. - **/ -void -e_cal_component_get_dtstart (ECalComponent *comp, ECalComponentDateTime *dt) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (dt != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_datetime (&priv->dtstart, icalproperty_get_dtstart, dt); -} - -/** - * e_cal_component_set_dtstart: - * @comp: A calendar component object. - * @dt: Start date/time. - * - * Sets the date/time start property of a calendar component object. - **/ -void -e_cal_component_set_dtstart (ECalComponent *comp, ECalComponentDateTime *dt) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_datetime (comp, &priv->dtstart, - icalproperty_new_dtstart, - icalproperty_set_dtstart, - dt); - - priv->need_sequence_inc = TRUE; -} - -/** - * e_cal_component_get_due: - * @comp: A calendar component object. - * @dt: Return value for the due date/time. This should be freed with the - * e_cal_component_free_datetime() function. - * - * Queries the due date/time of a calendar component object. - **/ -void -e_cal_component_get_due (ECalComponent *comp, ECalComponentDateTime *dt) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (dt != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_datetime (&priv->due, icalproperty_get_due, dt); - - /* If we don't have a DTEND property, then we try to get DTSTART - + DURATION. */ - if (!dt->value) - e_cal_component_get_start_plus_duration (comp, dt); -} - -/** - * e_cal_component_set_due: - * @comp: A calendar component object. - * @dt: End date/time. - * - * Sets the due date/time property of a calendar component object. - **/ -void -e_cal_component_set_due (ECalComponent *comp, ECalComponentDateTime *dt) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_datetime (comp, &priv->due, - icalproperty_new_due, - icalproperty_set_due, - dt); - - /* Make sure we remove any existing DURATION property, as it can't be - used with a DTEND. If DTEND is set to NULL, i.e. removed, we also - want to remove any DURATION. */ - if (priv->duration) { - icalcomponent_remove_property (priv->icalcomp, priv->duration); - icalproperty_free (priv->duration); - priv->duration = NULL; - } - - priv->need_sequence_inc = TRUE; -} - -/* Builds a list of ECalComponentPeriod structures based on a list of icalproperties */ -static void -get_period_list (GSList *period_list, - struct icaldatetimeperiodtype (* get_prop_func) (const icalproperty *prop), - GSList **list) -{ - GSList *l; - - *list = NULL; - - if (!period_list) - return; - - for (l = period_list; l; l = l->next) { - struct period *period; - ECalComponentPeriod *p; - struct icaldatetimeperiodtype ip; - - period = l->data; - g_assert (period->prop != NULL); - - p = g_new (ECalComponentPeriod, 1); - - /* Get value parameter */ - - if (period->value_param) { - icalparameter_value value_type; - - value_type = icalparameter_get_value (period->value_param); - - if (value_type == ICAL_VALUE_DATE || value_type == ICAL_VALUE_DATETIME) - p->type = E_CAL_COMPONENT_PERIOD_DATETIME; - else if (value_type == ICAL_VALUE_DURATION) - p->type = E_CAL_COMPONENT_PERIOD_DURATION; - else { - g_message ("get_period_list(): Unknown value for period %d; " - "using DATETIME", value_type); - p->type = E_CAL_COMPONENT_PERIOD_DATETIME; - } - } else - p->type = E_CAL_COMPONENT_PERIOD_DATETIME; - - /* Get start and end/duration */ - - ip = (* get_prop_func) (period->prop); - - p->start = ip.period.start; - - if (p->type == E_CAL_COMPONENT_PERIOD_DATETIME) - p->u.end = ip.period.end; - else if (p->type == E_CAL_COMPONENT_PERIOD_DURATION) - p->u.duration = ip.period.duration; - else - g_assert_not_reached (); - - /* Put in list */ - - *list = g_slist_prepend (*list, p); - } - - *list = g_slist_reverse (*list); -} - -/* Sets a period list value */ -static void -set_period_list (ECalComponent *comp, - icalproperty *(* new_prop_func) (struct icaldatetimeperiodtype period), - GSList **period_list, - GSList *pl) -{ - ECalComponentPrivate *priv; - GSList *l; - - priv = comp->priv; - - /* Remove old periods */ - - for (l = *period_list; l; l = l->next) { - struct period *period; - - period = l->data; - g_assert (period->prop != NULL); - - icalcomponent_remove_property (priv->icalcomp, period->prop); - icalproperty_free (period->prop); - g_free (period); - } - - g_slist_free (*period_list); - *period_list = NULL; - - /* Add in new periods */ - - for (l = pl; l; l = l->next) { - ECalComponentPeriod *p; - struct period *period; - struct icaldatetimeperiodtype ip; - icalparameter_value value_type; - - g_assert (l->data != NULL); - p = l->data; - - /* Create libical value */ - - ip.period.start = p->start; - - if (p->type == E_CAL_COMPONENT_PERIOD_DATETIME) { - value_type = ICAL_VALUE_DATETIME; - ip.period.end = p->u.end; - } else if (p->type == E_CAL_COMPONENT_PERIOD_DURATION) { - value_type = ICAL_VALUE_DURATION; - ip.period.duration = p->u.duration; - } else { - g_assert_not_reached (); - return; - } - - /* Create property */ - - period = g_new (struct period, 1); - - period->prop = (* new_prop_func) (ip); - period->value_param = icalparameter_new_value (value_type); - icalproperty_add_parameter (period->prop, period->value_param); - - /* Add to list */ - - *period_list = g_slist_prepend (*period_list, period); - } - - *period_list = g_slist_reverse (*period_list); -} - -/** - * e_cal_component_get_exdate_list: - * @comp: A calendar component object. - * @exdate_list: Return value for the list of exception dates, as a list of - * #ECalComponentDateTime structures. This should be freed using the - * e_cal_component_free_exdate_list() function. - * - * Queries the list of exception date properties in a calendar component object. - **/ -void -e_cal_component_get_exdate_list (ECalComponent *comp, GSList **exdate_list) -{ - ECalComponentPrivate *priv; - GSList *l; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (exdate_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - *exdate_list = NULL; - - for (l = priv->exdate_list; l; l = l->next) { - struct datetime *dt; - ECalComponentDateTime *cdt; - - dt = l->data; - - cdt = g_new (ECalComponentDateTime, 1); - cdt->value = g_new (struct icaltimetype, 1); - - *cdt->value = icalproperty_get_exdate (dt->prop); - - if (dt->tzid_param) - cdt->tzid = g_strdup (icalparameter_get_tzid (dt->tzid_param)); - else - cdt->tzid = NULL; - - *exdate_list = g_slist_prepend (*exdate_list, cdt); - } - - *exdate_list = g_slist_reverse (*exdate_list); -} - -/** - * e_cal_component_set_exdate_list: - * @comp: A calendar component object. - * @exdate_list: List of #ECalComponentDateTime structures. - * - * Sets the list of exception dates in a calendar component object. - **/ -void -e_cal_component_set_exdate_list (ECalComponent *comp, GSList *exdate_list) -{ - ECalComponentPrivate *priv; - GSList *l; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - /* Remove old exception dates */ - - for (l = priv->exdate_list; l; l = l->next) { - struct datetime *dt; - - dt = l->data; - - /* Removing the DATE or DATE-TIME property will also remove - any TZID parameter. */ - icalcomponent_remove_property (priv->icalcomp, dt->prop); - icalproperty_free (dt->prop); - g_free (dt); - } - - g_slist_free (priv->exdate_list); - priv->exdate_list = NULL; - - /* Add in new exception dates */ - - for (l = exdate_list; l; l = l->next) { - ECalComponentDateTime *cdt; - struct datetime *dt; - - g_assert (l->data != NULL); - cdt = l->data; - - g_assert (cdt->value != NULL); - - dt = g_new (struct datetime, 1); - dt->prop = icalproperty_new_exdate (*cdt->value); - - if (cdt->tzid) { - dt->tzid_param = icalparameter_new_tzid ((char *) cdt->tzid); - icalproperty_add_parameter (dt->prop, dt->tzid_param); - } else - dt->tzid_param = NULL; - - icalcomponent_add_property (priv->icalcomp, dt->prop); - priv->exdate_list = g_slist_prepend (priv->exdate_list, dt); - } - - priv->exdate_list = g_slist_reverse (priv->exdate_list); - - priv->need_sequence_inc = TRUE; -} - -/** - * e_cal_component_has_exdates: - * @comp: A calendar component object. - * - * Queries whether a calendar component object has any exception dates defined - * for it. - * - * Return value: TRUE if the component has exception dates, FALSE otherwise. - **/ -gboolean -e_cal_component_has_exdates (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_val_if_fail (comp != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE); - - priv = comp->priv; - g_return_val_if_fail (priv->icalcomp != NULL, FALSE); - - return (priv->exdate_list != NULL); -} - -/* Gets a list of recurrence rules */ -static void -get_recur_list (GSList *recur_list, - struct icalrecurrencetype (* get_prop_func) (const icalproperty *prop), - GSList **list) -{ - GSList *l; - - *list = NULL; - - for (l = recur_list; l; l = l->next) { - icalproperty *prop; - struct icalrecurrencetype *r; - - prop = l->data; - - r = g_new (struct icalrecurrencetype, 1); - *r = (* get_prop_func) (prop); - - *list = g_slist_prepend (*list, r); - } - - *list = g_slist_reverse (*list); -} - -/* Sets a list of recurrence rules */ -static void -set_recur_list (ECalComponent *comp, - icalproperty *(* new_prop_func) (struct icalrecurrencetype recur), - GSList **recur_list, - GSList *rl) -{ - ECalComponentPrivate *priv; - GSList *l; - - priv = comp->priv; - - /* Remove old recurrences */ - - for (l = *recur_list; l; l = l->next) { - icalproperty *prop; - - prop = l->data; - icalcomponent_remove_property (priv->icalcomp, prop); - icalproperty_free (prop); - } - - g_slist_free (*recur_list); - *recur_list = NULL; - - /* Add in new recurrences */ - - for (l = rl; l; l = l->next) { - icalproperty *prop; - struct icalrecurrencetype *recur; - - g_assert (l->data != NULL); - recur = l->data; - - prop = (* new_prop_func) (*recur); - icalcomponent_add_property (priv->icalcomp, prop); - - *recur_list = g_slist_prepend (*recur_list, prop); - } - - *recur_list = g_slist_reverse (*recur_list); -} - -/** - * e_cal_component_get_exrule_list: - * @comp: A calendar component object. - * @recur_list: List of exception rules as struct #icalrecurrencetype - * structures. This should be freed using the e_cal_component_free_recur_list() - * function. - * - * Queries the list of exception rule properties of a calendar component - * object. - **/ -void -e_cal_component_get_exrule_list (ECalComponent *comp, GSList **recur_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (recur_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_recur_list (priv->exrule_list, icalproperty_get_exrule, recur_list); -} - -/** - * e_cal_component_get_exrule_property_list: - * @comp: A calendar component object. - * @recur_list: Returns a list of exception rule properties. - * - * Queries the list of exception rule properties of a calendar component object. - **/ -void -e_cal_component_get_exrule_property_list (ECalComponent *comp, GSList **recur_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (recur_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - *recur_list = priv->exrule_list; -} - -/** - * e_cal_component_set_exrule_list: - * @comp: A calendar component object. - * @recur_list: List of struct #icalrecurrencetype structures. - * - * Sets the list of exception rules in a calendar component object. - **/ -void -e_cal_component_set_exrule_list (ECalComponent *comp, GSList *recur_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_recur_list (comp, icalproperty_new_exrule, &priv->exrule_list, recur_list); - - priv->need_sequence_inc = TRUE; -} - -/** - * e_cal_component_has_exrules: - * @comp: A calendar component object. - * - * Queries whether a calendar component object has any exception rules defined - * for it. - * - * Return value: TRUE if the component has exception rules, FALSE otherwise. - **/ -gboolean -e_cal_component_has_exrules (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_val_if_fail (comp != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE); - - priv = comp->priv; - g_return_val_if_fail (priv->icalcomp != NULL, FALSE); - - return (priv->exrule_list != NULL); -} - -/** - * e_cal_component_has_exceptions: - * @comp: A calendar component object - * - * Queries whether a calendar component object has any exception dates - * or exception rules. - * - * Return value: TRUE if the component has exceptions, FALSE otherwise. - **/ -gboolean -e_cal_component_has_exceptions (ECalComponent *comp) -{ - return e_cal_component_has_exdates (comp) || e_cal_component_has_exrules (comp); -} - -/** - * e_cal_component_get_geo: - * @comp: A calendar component object. - * @geo: Return value for the geographic position property. This should be - * freed using the e_cal_component_free_geo() function. - * - * Sets the geographic position property of a calendar component object. - **/ -void -e_cal_component_get_geo (ECalComponent *comp, struct icalgeotype **geo) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (geo != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (priv->geo) { - *geo = g_new (struct icalgeotype, 1); - **geo = icalproperty_get_geo (priv->geo); - } else - *geo = NULL; -} - -/** - * e_cal_component_set_geo: - * @comp: A calendar component object. - * @geo: Value for the geographic position property. - * - * Sets the geographic position property on a calendar component object. - **/ -void -e_cal_component_set_geo (ECalComponent *comp, struct icalgeotype *geo) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!geo) { - if (priv->geo) { - icalcomponent_remove_property (priv->icalcomp, priv->geo); - icalproperty_free (priv->geo); - priv->geo = NULL; - } - - return; - } - - if (priv->geo) - icalproperty_set_geo (priv->geo, *geo); - else { - priv->geo = icalproperty_new_geo (*geo); - icalcomponent_add_property (priv->icalcomp, priv->geo); - } -} - -/** - * e_cal_component_get_last_modified: - * @comp: A calendar component object. - * @t: Return value for the last modified time value. - * - * Queries the time at which a calendar component object was last modified in - * the calendar store. - **/ -void -e_cal_component_get_last_modified (ECalComponent *comp, struct icaltimetype **t) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (t != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_icaltimetype (priv->last_modified, icalproperty_get_lastmodified, t); -} - -/** - * e_cal_component_set_last_modified: - * @comp: A calendar component object. - * @t: Value for the last time modified. - * - * Sets the time at which a calendar component object was last stored in the - * calendar store. This should not be called by plain calendar user agents. - **/ -void -e_cal_component_set_last_modified (ECalComponent *comp, struct icaltimetype *t) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_icaltimetype (comp, &priv->last_modified, - icalproperty_new_lastmodified, - icalproperty_set_lastmodified, - t); -} - -/** - * e_cal_component_get_organizer: - * @comp: A calendar component object - * @organizer: A value for the organizer - * - * Queries the organizer property of a calendar component object - **/ -void -e_cal_component_get_organizer (ECalComponent *comp, ECalComponentOrganizer *organizer) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (organizer != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (priv->organizer.prop) - organizer->value = icalproperty_get_organizer (priv->organizer.prop); - else - organizer->value = NULL; - - if (priv->organizer.sentby_param) - organizer->sentby = icalparameter_get_sentby (priv->organizer.sentby_param); - else - organizer->sentby = NULL; - - if (priv->organizer.cn_param) - organizer->cn = icalparameter_get_sentby (priv->organizer.cn_param); - else - organizer->cn = NULL; - - if (priv->organizer.language_param) - organizer->language = icalparameter_get_sentby (priv->organizer.language_param); - else - organizer->language = NULL; - -} - -/** - * e_cal_component_set_organizer: - * @comp: A calendar component object. - * @organizer: Value for the organizer property - * - * Sets the organizer of a calendar component object - **/ -void -e_cal_component_set_organizer (ECalComponent *comp, ECalComponentOrganizer *organizer) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!organizer) { - if (priv->organizer.prop) { - icalcomponent_remove_property (priv->icalcomp, priv->organizer.prop); - icalproperty_free (priv->organizer.prop); - - priv->organizer.prop = NULL; - priv->organizer.sentby_param = NULL; - priv->organizer.cn_param = NULL; - priv->organizer.language_param = NULL; - } - - return; - } - - g_return_if_fail (organizer->value != NULL); - - if (priv->organizer.prop) - icalproperty_set_organizer (priv->organizer.prop, (char *) organizer->value); - else { - priv->organizer.prop = icalproperty_new_organizer ((char *) organizer->value); - icalcomponent_add_property (priv->icalcomp, priv->organizer.prop); - } - - if (organizer->sentby) { - g_assert (priv->organizer.prop != NULL); - - if (priv->organizer.sentby_param) - icalparameter_set_sentby (priv->organizer.sentby_param, - (char *) organizer->sentby); - else { - priv->organizer.sentby_param = icalparameter_new_sentby ( - (char *) organizer->sentby); - icalproperty_add_parameter (priv->organizer.prop, - priv->organizer.sentby_param); - } - } else if (priv->organizer.sentby_param) { - icalproperty_remove_parameter (priv->organizer.prop, ICAL_SENTBY_PARAMETER); - priv->organizer.sentby_param = NULL; - } - - if (organizer->cn) { - g_assert (priv->organizer.prop != NULL); - - if (priv->organizer.cn_param) - icalparameter_set_cn (priv->organizer.cn_param, - (char *) organizer->cn); - else { - priv->organizer.cn_param = icalparameter_new_cn ( - (char *) organizer->cn); - icalproperty_add_parameter (priv->organizer.prop, - priv->organizer.cn_param); - } - } else if (priv->organizer.cn_param) { - icalproperty_remove_parameter (priv->organizer.prop, ICAL_CN_PARAMETER); - priv->organizer.cn_param = NULL; - } - - if (organizer->language) { - g_assert (priv->organizer.prop != NULL); - - if (priv->organizer.language_param) - icalparameter_set_language (priv->organizer.language_param, - (char *) organizer->language); - else { - priv->organizer.language_param = icalparameter_new_language ( - (char *) organizer->language); - icalproperty_add_parameter (priv->organizer.prop, - priv->organizer.language_param); - } - } else if (priv->organizer.language_param) { - icalproperty_remove_parameter (priv->organizer.prop, ICAL_LANGUAGE_PARAMETER); - priv->organizer.language_param = NULL; - } - - -} - - -/** - * e_cal_component_has_organizer: - * @comp: - * - * - * - * Return value: - **/ -gboolean -e_cal_component_has_organizer (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_val_if_fail (comp != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE); - - priv = comp->priv; - - return priv->organizer.prop != NULL; -} - -/** - * e_cal_component_get_percent: - * @comp: A calendar component object. - * @percent: Return value for the percent-complete property. This should be - * freed using the e_cal_component_free_percent() function. - * - * Queries the percent-complete property of a calendar component object. - **/ -void -e_cal_component_get_percent (ECalComponent *comp, int **percent) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (percent != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (priv->percent) { - *percent = g_new (int, 1); - **percent = icalproperty_get_percentcomplete (priv->percent); - } else - *percent = NULL; -} - -/** - * e_cal_component_set_percent: - * @comp: A calendar component object. - * @percent: Value for the percent-complete property. - * - * Sets the percent-complete property of a calendar component object. - **/ -void -e_cal_component_set_percent (ECalComponent *comp, int *percent) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!percent) { - if (priv->percent) { - icalcomponent_remove_property (priv->icalcomp, priv->percent); - icalproperty_free (priv->percent); - priv->percent = NULL; - } - - return; - } - - g_return_if_fail (*percent >= 0 && *percent <= 100); - - if (priv->percent) - icalproperty_set_percentcomplete (priv->percent, *percent); - else { - priv->percent = icalproperty_new_percentcomplete (*percent); - icalcomponent_add_property (priv->icalcomp, priv->percent); - } -} - -/** - * e_cal_component_get_priority: - * @comp: A calendar component object. - * @priority: Return value for the priority property. This should be freed using - * the e_cal_component_free_priority() function. - * - * Queries the priority property of a calendar component object. - **/ -void -e_cal_component_get_priority (ECalComponent *comp, int **priority) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (priority != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (priv->priority) { - *priority = g_new (int, 1); - **priority = icalproperty_get_priority (priv->priority); - } else - *priority = NULL; -} - -/** - * e_cal_component_set_priority: - * @comp: A calendar component object. - * @priority: Value for the priority property. - * - * Sets the priority property of a calendar component object. - **/ -void -e_cal_component_set_priority (ECalComponent *comp, int *priority) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!priority) { - if (priv->priority) { - icalcomponent_remove_property (priv->icalcomp, priv->priority); - icalproperty_free (priv->priority); - priv->priority = NULL; - } - - return; - } - - g_return_if_fail (*priority >= 0 && *priority <= 9); - - if (priv->priority) - icalproperty_set_priority (priv->priority, *priority); - else { - priv->priority = icalproperty_new_priority (*priority); - icalcomponent_add_property (priv->icalcomp, priv->priority); - } -} - -/** - * e_cal_component_get_recurid: - * @comp: A calendar component object. - * @recur_id: Return value for the recurrence id property - * - * Queries the recurrence id property of a calendar component object - **/ -void -e_cal_component_get_recurid (ECalComponent *comp, ECalComponentRange *recur_id) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (recur_id != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_datetime (&priv->recur_id.recur_time, - icalproperty_get_recurrenceid, - &recur_id->datetime); -} - -/** - * e_cal_component_get_recurid_as_string: - * @comp: A calendar component object. - * - * Gets the recurrence ID property as a string. - */ -const char * -e_cal_component_get_recurid_as_string (ECalComponent *comp) -{ - ECalComponentRange range; - struct icaltimetype tt; - - if (!e_cal_component_is_instance (comp)) - return NULL; - - e_cal_component_get_recurid (comp, &range); - if (!range.datetime.value) - return "0"; - tt = *range.datetime.value; - e_cal_component_free_range (&range); - - return icaltime_is_valid_time (tt) && !icaltime_is_null_time (tt) ? - icaltime_as_ical_string (tt) : "0"; -} - -/** - * e_cal_component_set_recurid: - * @comp: A calendar component object. - * @recur_id: Value for the recurrence id property. - * - * Sets the recurrence id property of a calendar component object. - **/ -void -e_cal_component_set_recurid (ECalComponent *comp, ECalComponentRange *recur_id) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_datetime (comp, &priv->recur_id.recur_time, - icalproperty_new_recurrenceid, - icalproperty_set_recurrenceid, - recur_id ? &recur_id->datetime : NULL); -} - -/** - * e_cal_component_get_rdate_list: - * @comp: A calendar component object. - * @period_list: Return value for the list of recurrence dates, as a list of - * #ECalComponentPeriod structures. This should be freed using the - * e_cal_component_free_period_list() function. - * - * Queries the list of recurrence date properties in a calendar component - * object. - **/ -void -e_cal_component_get_rdate_list (ECalComponent *comp, GSList **period_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (period_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_period_list (priv->rdate_list, icalproperty_get_rdate, period_list); -} - -/** - * e_cal_component_set_rdate_list: - * @comp: A calendar component object. - * @period_list: List of #ECalComponentPeriod structures. - * - * Sets the list of recurrence dates in a calendar component object. - **/ -void -e_cal_component_set_rdate_list (ECalComponent *comp, GSList *period_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_period_list (comp, icalproperty_new_rdate, &priv->rdate_list, period_list); - - priv->need_sequence_inc = TRUE; -} - -/** - * e_cal_component_has_rdates: - * @comp: A calendar component object. - * - * Queries whether a calendar component object has any recurrence dates defined - * for it. - * - * Return value: TRUE if the component has recurrence dates, FALSE otherwise. - **/ -gboolean -e_cal_component_has_rdates (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_val_if_fail (comp != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE); - - priv = comp->priv; - g_return_val_if_fail (priv->icalcomp != NULL, FALSE); - - return (priv->rdate_list != NULL); -} - -/** - * e_cal_component_get_rrule_list: - * @comp: A calendar component object. - * @recur_list: List of recurrence rules as struct #icalrecurrencetype - * structures. This should be freed using the e_cal_component_free_recur_list() - * function. - * - * Queries the list of recurrence rule properties of a calendar component - * object. - **/ -void -e_cal_component_get_rrule_list (ECalComponent *comp, GSList **recur_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (recur_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_recur_list (priv->rrule_list, icalproperty_get_rrule, recur_list); -} - -/** - * e_cal_component_get_rrule_property_list: - * @comp: A calendar component object. - * @recur_list: Returns a list of recurrence rule properties. - * - * Queries a list of recurrence rule properties of a calendar component object. - **/ -void -e_cal_component_get_rrule_property_list (ECalComponent *comp, GSList **recur_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (recur_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - *recur_list = priv->rrule_list; -} - -/** - * e_cal_component_set_rrule_list: - * @comp: A calendar component object. - * @recur_list: List of struct #icalrecurrencetype structures. - * - * Sets the list of recurrence rules in a calendar component object. - **/ -void -e_cal_component_set_rrule_list (ECalComponent *comp, GSList *recur_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_recur_list (comp, icalproperty_new_rrule, &priv->rrule_list, recur_list); - - priv->need_sequence_inc = TRUE; -} - -/** - * e_cal_component_has_rrules: - * @comp: A calendar component object. - * - * Queries whether a calendar component object has any recurrence rules defined - * for it. - * - * Return value: TRUE if the component has recurrence rules, FALSE otherwise. - **/ -gboolean -e_cal_component_has_rrules (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_val_if_fail (comp != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE); - - priv = comp->priv; - g_return_val_if_fail (priv->icalcomp != NULL, FALSE); - - return (priv->rrule_list != NULL); -} - -/** - * e_cal_component_has_recurrences: - * @comp: A calendar component object - * - * Queries whether a calendar component object has any recurrence dates or - * recurrence rules. - * - * Return value: TRUE if the component has recurrences, FALSE otherwise. - **/ -gboolean -e_cal_component_has_recurrences (ECalComponent *comp) -{ - return e_cal_component_has_rdates (comp) || e_cal_component_has_rrules (comp); -} - -/* Counts the elements in the by_xxx fields of an icalrecurrencetype */ -static int -count_by_xxx (short *field, int max_elements) -{ - int i; - - for (i = 0; i < max_elements; i++) - if (field[i] == ICAL_RECURRENCE_ARRAY_MAX) - break; - - return i; -} - -gboolean -e_cal_component_has_simple_recurrence (ECalComponent *comp) -{ - GSList *rrule_list; - struct icalrecurrencetype *r; - int n_by_second, n_by_minute, n_by_hour; - int n_by_day, n_by_month_day, n_by_year_day; - int n_by_week_no, n_by_month, n_by_set_pos; - int len, i; - gboolean simple = FALSE; - - if (!e_cal_component_has_recurrences (comp)) - return TRUE; - - e_cal_component_get_rrule_list (comp, &rrule_list); - len = g_slist_length (rrule_list); - if (len > 1 - || e_cal_component_has_rdates (comp) - || e_cal_component_has_exrules (comp)) - goto cleanup; - - /* Down to one rule, so test that one */ - r = rrule_list->data; - - /* Any funky frequency? */ - if (r->freq == ICAL_SECONDLY_RECURRENCE - || r->freq == ICAL_MINUTELY_RECURRENCE - || r->freq == ICAL_HOURLY_RECURRENCE) - goto cleanup; - - /* Any funky BY_* */ -#define N_HAS_BY(field) (count_by_xxx (field, sizeof (field) / sizeof (field[0]))) - - n_by_second = N_HAS_BY (r->by_second); - n_by_minute = N_HAS_BY (r->by_minute); - n_by_hour = N_HAS_BY (r->by_hour); - n_by_day = N_HAS_BY (r->by_day); - n_by_month_day = N_HAS_BY (r->by_month_day); - n_by_year_day = N_HAS_BY (r->by_year_day); - n_by_week_no = N_HAS_BY (r->by_week_no); - n_by_month = N_HAS_BY (r->by_month); - n_by_set_pos = N_HAS_BY (r->by_set_pos); - - if (n_by_second != 0 - || n_by_minute != 0 - || n_by_hour != 0) - goto cleanup; - - switch (r->freq) { - case ICAL_DAILY_RECURRENCE: - if (n_by_day != 0 - || n_by_month_day != 0 - || n_by_year_day != 0 - || n_by_week_no != 0 - || n_by_month != 0 - || n_by_set_pos != 0) - goto cleanup; - - simple = TRUE; - break; - - case ICAL_WEEKLY_RECURRENCE: - if (n_by_month_day != 0 - || n_by_year_day != 0 - || n_by_week_no != 0 - || n_by_month != 0 - || n_by_set_pos != 0) - goto cleanup; - - for (i = 0; i < 8 && r->by_day[i] != ICAL_RECURRENCE_ARRAY_MAX; i++) { - int pos; - pos = icalrecurrencetype_day_position (r->by_day[i]); - - if (pos != 0) - goto cleanup; - } - - simple = TRUE; - break; - - case ICAL_MONTHLY_RECURRENCE: - if (n_by_year_day != 0 - || n_by_week_no != 0 - || n_by_month != 0 - || n_by_set_pos > 1) - goto cleanup; - - if (n_by_month_day == 1) { - int nth; - - if (n_by_set_pos != 0) - goto cleanup; - - nth = r->by_month_day[0]; - if (nth < 1 && nth != -1) - goto cleanup; - - simple = TRUE; - - } else if (n_by_day == 1) { - enum icalrecurrencetype_weekday weekday; - int pos; - - /* Outlook 2000 uses BYDAY=TU;BYSETPOS=2, and will not - accept BYDAY=2TU. So we now use the same as Outlook - by default. */ - - weekday = icalrecurrencetype_day_day_of_week (r->by_day[0]); - pos = icalrecurrencetype_day_position (r->by_day[0]); - - if (pos == 0) { - if (n_by_set_pos != 1) - goto cleanup; - pos = r->by_set_pos[0]; - } else if (pos < 0) { - goto cleanup; - } - - switch (weekday) { - case ICAL_MONDAY_WEEKDAY: - case ICAL_TUESDAY_WEEKDAY: - case ICAL_WEDNESDAY_WEEKDAY: - case ICAL_THURSDAY_WEEKDAY: - case ICAL_FRIDAY_WEEKDAY: - case ICAL_SATURDAY_WEEKDAY: - case ICAL_SUNDAY_WEEKDAY: - break; - - default: - goto cleanup; - } - } else { - goto cleanup; - } - - simple = TRUE; - break; - - case ICAL_YEARLY_RECURRENCE: - if (n_by_day != 0 - || n_by_month_day != 0 - || n_by_year_day != 0 - || n_by_week_no != 0 - || n_by_month != 0 - || n_by_set_pos != 0) - goto cleanup; - - simple = TRUE; - break; - - default: - goto cleanup; - } - - cleanup: - e_cal_component_free_recur_list (rrule_list); - - return simple; -} - -gboolean -e_cal_component_is_instance (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_val_if_fail (comp != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE); - - priv = comp->priv; - - return !(priv->recur_id.recur_time.prop == NULL); -} - -/** - * e_cal_component_get_sequence: - * @comp: A calendar component object. - * @sequence: Return value for the sequence number. This should be freed using - * e_cal_component_free_sequence(). - * - * Queries the sequence number of a calendar component object. - **/ -void -e_cal_component_get_sequence (ECalComponent *comp, int **sequence) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (sequence != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!priv->sequence) { - *sequence = NULL; - return; - } - - *sequence = g_new (int, 1); - **sequence = icalproperty_get_sequence (priv->sequence); -} - -/** - * e_cal_component_set_sequence: - * @comp: A calendar component object. - * @sequence: Sequence number value. - * - * Sets the sequence number of a calendar component object. Normally this - * function should not be called, since the sequence number is incremented - * automatically at the proper times. - **/ -void -e_cal_component_set_sequence (ECalComponent *comp, int *sequence) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - priv->need_sequence_inc = FALSE; - - if (!sequence) { - if (priv->sequence) { - icalcomponent_remove_property (priv->icalcomp, priv->sequence); - icalproperty_free (priv->sequence); - priv->sequence = NULL; - } - - return; - } - - if (priv->sequence) - icalproperty_set_sequence (priv->sequence, *sequence); - else { - priv->sequence = icalproperty_new_sequence (*sequence); - icalcomponent_add_property (priv->icalcomp, priv->sequence); - } -} - -/** - * e_cal_component_get_status: - * @comp: A calendar component object. - * @status: Return value for the status value. It is set to #ICAL_STATUS_NONE - * if the component has no status property. - * - * Queries the status property of a calendar component object. - **/ -void -e_cal_component_get_status (ECalComponent *comp, icalproperty_status *status) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (status != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!priv->status) { - *status = ICAL_STATUS_NONE; - return; - } - - *status = icalproperty_get_status (priv->status); -} - -/** - * e_cal_component_set_status: - * @comp: A calendar component object. - * @status: Status value. You should use #ICAL_STATUS_NONE if you want to unset - * this property. - * - * Sets the status property of a calendar component object. - **/ -void -e_cal_component_set_status (ECalComponent *comp, icalproperty_status status) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - priv->need_sequence_inc = TRUE; - - if (status == ICAL_STATUS_NONE) { - if (priv->status) { - icalcomponent_remove_property (priv->icalcomp, priv->status); - icalproperty_free (priv->status); - priv->status = NULL; - } - - return; - } - - if (priv->status) { - icalproperty_set_status (priv->status, status); - } else { - priv->status = icalproperty_new_status (status); - icalcomponent_add_property (priv->icalcomp, priv->status); - } -} - -/** - * e_cal_component_get_summary: - * @comp: A calendar component object. - * @summary: Return value for the summary property and its parameters. - * - * Queries the summary of a calendar component object. - **/ -void -e_cal_component_get_summary (ECalComponent *comp, ECalComponentText *summary) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (summary != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (priv->summary.prop) - summary->value = icalproperty_get_summary (priv->summary.prop); - else - summary->value = NULL; - - if (priv->summary.altrep_param) - summary->altrep = icalparameter_get_altrep (priv->summary.altrep_param); - else - summary->altrep = NULL; -} - -/** - * e_cal_component_set_summary: - * @comp: A calendar component object. - * @summary: Summary property and its parameters. - * - * Sets the summary of a calendar component object. - **/ -void -e_cal_component_set_summary (ECalComponent *comp, ECalComponentText *summary) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!summary) { - if (priv->summary.prop) { - icalcomponent_remove_property (priv->icalcomp, priv->summary.prop); - icalproperty_free (priv->summary.prop); - - priv->summary.prop = NULL; - priv->summary.altrep_param = NULL; - } - - return; - } - - g_return_if_fail (summary->value != NULL); - - if (priv->summary.prop) - icalproperty_set_summary (priv->summary.prop, (char *) summary->value); - else { - priv->summary.prop = icalproperty_new_summary ((char *) summary->value); - icalcomponent_add_property (priv->icalcomp, priv->summary.prop); - } - - if (summary->altrep) { - g_assert (priv->summary.prop != NULL); - - if (priv->summary.altrep_param) - icalparameter_set_altrep (priv->summary.altrep_param, - (char *) summary->altrep); - else { - priv->summary.altrep_param = icalparameter_new_altrep ( - (char *) summary->altrep); - icalproperty_add_parameter (priv->summary.prop, - priv->summary.altrep_param); - } - } else if (priv->summary.altrep_param) { - icalproperty_remove_parameter (priv->summary.prop, ICAL_ALTREP_PARAMETER); - priv->summary.altrep_param = NULL; - } -} - -/** - * e_cal_component_get_transparency: - * @comp: A calendar component object. - * @transp: Return value for the time transparency. - * - * Queries the time transparency of a calendar component object. - **/ -void -e_cal_component_get_transparency (ECalComponent *comp, ECalComponentTransparency *transp) -{ - ECalComponentPrivate *priv; - icalproperty_transp ical_transp; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (transp != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!priv->transparency) { - *transp = E_CAL_COMPONENT_TRANSP_NONE; - return; - } - - ical_transp = icalproperty_get_transp (priv->transparency); - - switch (ical_transp) - { - case ICAL_TRANSP_TRANSPARENT: - case ICAL_TRANSP_TRANSPARENTNOCONFLICT: - *transp = E_CAL_COMPONENT_TRANSP_TRANSPARENT; - break; - - case ICAL_TRANSP_OPAQUE: - case ICAL_TRANSP_OPAQUENOCONFLICT: - *transp = E_CAL_COMPONENT_TRANSP_OPAQUE; - break; - - default: - *transp = E_CAL_COMPONENT_TRANSP_UNKNOWN; - break; - } -} - -/** - * e_cal_component_set_transparency: - * @comp: A calendar component object. - * @transp: Time transparency value. - * - * Sets the time transparency of a calendar component object. - **/ -void -e_cal_component_set_transparency (ECalComponent *comp, ECalComponentTransparency transp) -{ - ECalComponentPrivate *priv; - icalproperty_transp ical_transp; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (transp != E_CAL_COMPONENT_TRANSP_UNKNOWN); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - - if (transp == E_CAL_COMPONENT_TRANSP_NONE) { - if (priv->transparency) { - icalcomponent_remove_property (priv->icalcomp, priv->transparency); - icalproperty_free (priv->transparency); - priv->transparency = NULL; - } - - return; - } - - switch (transp) { - case E_CAL_COMPONENT_TRANSP_TRANSPARENT: - ical_transp = ICAL_TRANSP_TRANSPARENT; - break; - - case E_CAL_COMPONENT_TRANSP_OPAQUE: - ical_transp = ICAL_TRANSP_OPAQUE; - break; - - default: - g_assert_not_reached (); - ical_transp = ICAL_TRANSP_NONE; - } - - if (priv->transparency) - icalproperty_set_transp (priv->transparency, ical_transp); - else { - priv->transparency = icalproperty_new_transp (ical_transp); - icalcomponent_add_property (priv->icalcomp, priv->transparency); - } -} - -/** - * e_cal_component_get_url: - * @comp: A calendar component object. - * @url: Return value for the URL. - * - * Queries the uniform resource locator property of a calendar component object. - **/ -void -e_cal_component_get_url (ECalComponent *comp, const char **url) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (url != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (priv->url) - *url = icalproperty_get_url (priv->url); - else - *url = NULL; -} - -/** - * e_cal_component_set_url: - * @comp: A calendar component object. - * @url: URL value. - * - * Sets the uniform resource locator property of a calendar component object. - **/ -void -e_cal_component_set_url (ECalComponent *comp, const char *url) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!url || !(*url)) { - if (priv->url) { - icalcomponent_remove_property (priv->icalcomp, priv->url); - icalproperty_free (priv->url); - priv->url = NULL; - } - - return; - } - - if (priv->url) - icalproperty_set_url (priv->url, (char *) url); - else { - priv->url = icalproperty_new_url ((char *) url); - icalcomponent_add_property (priv->icalcomp, priv->url); - } -} - -/* Gets a text list value */ -static void -get_attendee_list (GSList *attendee_list, GSList **al) -{ - GSList *l; - - *al = NULL; - - if (!attendee_list) - return; - - for (l = attendee_list; l; l = l->next) { - struct attendee *attendee; - ECalComponentAttendee *a; - - attendee = l->data; - g_assert (attendee->prop != NULL); - - a = g_new0 (ECalComponentAttendee, 1); - a->value = icalproperty_get_attendee (attendee->prop); - - if (attendee->member_param) - a->member = icalparameter_get_member (attendee->member_param); - if (attendee->cutype_param) - a->cutype = icalparameter_get_cutype (attendee->cutype_param); - else - a->cutype = ICAL_CUTYPE_UNKNOWN; - if (attendee->role_param) - a->role = icalparameter_get_role (attendee->role_param); - else - a->role = ICAL_ROLE_REQPARTICIPANT; - if (attendee->partstat_param) - a->status = icalparameter_get_partstat (attendee->partstat_param); - else - a->status = ICAL_PARTSTAT_NEEDSACTION; - if (attendee->rsvp_param && icalparameter_get_rsvp (attendee->rsvp_param) == ICAL_RSVP_TRUE) - a->rsvp = TRUE; - else - a->rsvp = FALSE; - if (attendee->delfrom_param) - a->delfrom = icalparameter_get_delegatedfrom (attendee->delfrom_param); - if (attendee->delto_param) - a->delto = icalparameter_get_delegatedto (attendee->delto_param); - if (attendee->sentby_param) - a->sentby = icalparameter_get_sentby (attendee->sentby_param); - if (attendee->cn_param) - a->cn = icalparameter_get_cn (attendee->cn_param); - if (attendee->language_param) - a->language = icalparameter_get_language (attendee->language_param); - - *al = g_slist_prepend (*al, a); - } - - *al = g_slist_reverse (*al); -} - - -/* Sets a text list value */ -static void -set_attendee_list (icalcomponent *icalcomp, - GSList **attendee_list, - GSList *al) -{ - GSList *l; - - /* Remove old attendees */ - - for (l = *attendee_list; l; l = l->next) { - struct attendee *attendee; - - attendee = l->data; - g_assert (attendee->prop != NULL); - - icalcomponent_remove_property (icalcomp, attendee->prop); - icalproperty_free (attendee->prop); - g_free (attendee); - } - - g_slist_free (*attendee_list); - *attendee_list = NULL; - - /* Add in new attendees */ - - for (l = al; l; l = l->next) { - ECalComponentAttendee *a; - struct attendee *attendee; - - a = l->data; - g_return_if_fail (a->value != NULL); - - attendee = g_new0 (struct attendee, 1); - - attendee->prop = icalproperty_new_attendee (a->value); - icalcomponent_add_property (icalcomp, attendee->prop); - - if (a->member) { - attendee->member_param = icalparameter_new_member (a->member); - icalproperty_add_parameter (attendee->prop, attendee->member_param); - } - - attendee->cutype_param = icalparameter_new_cutype (a->cutype); - icalproperty_add_parameter (attendee->prop, attendee->cutype_param); - - attendee->role_param = icalparameter_new_role (a->role); - icalproperty_add_parameter (attendee->prop, attendee->role_param); - - attendee->partstat_param = icalparameter_new_partstat (a->status); - icalproperty_add_parameter (attendee->prop, attendee->partstat_param); - - if (a->rsvp) - attendee->rsvp_param = icalparameter_new_rsvp (ICAL_RSVP_TRUE); - else - attendee->rsvp_param = icalparameter_new_rsvp (ICAL_RSVP_FALSE); - icalproperty_add_parameter (attendee->prop, attendee->rsvp_param); - - if (a->delfrom) { - attendee->delfrom_param = icalparameter_new_delegatedfrom (a->delfrom); - icalproperty_add_parameter (attendee->prop, attendee->delfrom_param); - } - if (a->delto) { - attendee->delto_param = icalparameter_new_delegatedto (a->delto); - icalproperty_add_parameter (attendee->prop, attendee->delto_param); - } - if (a->sentby) { - attendee->sentby_param = icalparameter_new_sentby (a->sentby); - icalproperty_add_parameter (attendee->prop, attendee->sentby_param); - } - if (a->cn) { - attendee->cn_param = icalparameter_new_cn (a->cn); - icalproperty_add_parameter (attendee->prop, attendee->cn_param); - } - if (a->language) { - attendee->language_param = icalparameter_new_language (a->language); - icalproperty_add_parameter (attendee->prop, attendee->language_param); - } - - *attendee_list = g_slist_prepend (*attendee_list, attendee); - } - - *attendee_list = g_slist_reverse (*attendee_list); -} - -/** - * e_cal_component_get_attendee_list: - * @comp: A calendar component object. - * @attendee_list: Return value for the attendee property. - * This should be freed using the e_cal_component_free_attendee_list () - * function. - * - * Queries the attendee properties of the calendar component object - **/ -void -e_cal_component_get_attendee_list (ECalComponent *comp, GSList **attendee_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (attendee_list != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - get_attendee_list (priv->attendee_list, attendee_list); -} - -/** - * e_cal_component_set_attendee_list: - * @comp: A calendar component object. - * @attendee_list: Values for attendee properties - * - * Sets the attendees of a calendar component object - **/ -void -e_cal_component_set_attendee_list (ECalComponent *comp, GSList *attendee_list) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - set_attendee_list (priv->icalcomp, &priv->attendee_list, attendee_list); -} - -gboolean -e_cal_component_has_attendees (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_val_if_fail (comp != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE); - - priv = comp->priv; - - if (g_slist_length (priv->attendee_list) > 0) - return TRUE; - - return FALSE; -} - -/** - * e_cal_component_get_location: - * @comp: A calendar component object - * @location: Return value for the location. - * - * Queries the location property of a calendar component object. - **/ -void -e_cal_component_get_location (ECalComponent *comp, const char **location) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (location != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (priv->location) - *location = icalproperty_get_location (priv->location); - else - *location = NULL; -} - -/** - * e_cal_component_set_location: - * @comp: A calendar component object. - * @location: Location value. - * - * Sets the location property of a calendar component object. - **/ -void -e_cal_component_set_location (ECalComponent *comp, const char *location) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - if (!location || !(*location)) { - if (priv->location) { - icalcomponent_remove_property (priv->icalcomp, priv->location); - icalproperty_free (priv->location); - priv->location = NULL; - } - - return; - } - - if (priv->location) - icalproperty_set_location (priv->location, (char *) location); - else { - priv->location = icalproperty_new_location ((char *) location); - icalcomponent_add_property (priv->icalcomp, priv->location); - } -} - - - -/** - * e_cal_component_free_categories_list: - * @categ_list: List of category strings. - * - * Frees a list of category strings. - **/ -void -e_cal_component_free_categories_list (GSList *categ_list) -{ - GSList *l; - - for (l = categ_list; l; l = l->next) - g_free (l->data); - - g_slist_free (categ_list); -} - -/** - * e_cal_component_free_datetime: - * @dt: A date/time structure. - * - * Frees a date/time structure. - **/ -void -e_cal_component_free_datetime (ECalComponentDateTime *dt) -{ - g_return_if_fail (dt != NULL); - - g_free (dt->value); - g_free ((char*)dt->tzid); -} - -void -e_cal_component_free_range (ECalComponentRange *range) -{ - g_return_if_fail (range != NULL); - - e_cal_component_free_datetime (&range->datetime); -} - -/** - * e_cal_component_free_exdate_list: - * @exdate_list: List of #ECalComponentDateTime structures. - * - * Frees a list of #ECalComponentDateTime structures as returned by the - * e_cal_component_get_exdate_list() function. - **/ -void -e_cal_component_free_exdate_list (GSList *exdate_list) -{ - GSList *l; - - for (l = exdate_list; l; l = l->next) { - ECalComponentDateTime *cdt; - - g_assert (l->data != NULL); - cdt = l->data; - - g_assert (cdt->value != NULL); - g_free (cdt->value); - g_free ((char*)cdt->tzid); - - g_free (cdt); - } - - g_slist_free (exdate_list); -} - -/** - * e_cal_component_free_geo: - * @geo: An #icalgeotype structure. - * - * Frees a struct #icalgeotype structure as returned by the calendar component - * functions. - **/ -void -e_cal_component_free_geo (struct icalgeotype *geo) -{ - g_return_if_fail (geo != NULL); - - g_free (geo); -} - -/** - * e_cal_component_free_icaltimetype: - * @t: An #icaltimetype structure. - * - * Frees a struct #icaltimetype value as returned by the calendar component - * functions. - **/ -void -e_cal_component_free_icaltimetype (struct icaltimetype *t) -{ - g_return_if_fail (t != NULL); - - g_free (t); -} - -/** - * e_cal_component_free_percent: - * @percent: Percent value. - * - * Frees a percent value as returned by the e_cal_component_get_percent() - * function. - **/ -void -e_cal_component_free_percent (int *percent) -{ - g_return_if_fail (percent != NULL); - - g_free (percent); -} - -/** - * e_cal_component_free_priority: - * @priority: Priority value. - * - * Frees a priority value as returned by the e_cal_component_get_priority() - * function. - **/ -void -e_cal_component_free_priority (int *priority) -{ - g_return_if_fail (priority != NULL); - - g_free (priority); -} - -/** - * e_cal_component_free_period_list: - * @period_list: List of #ECalComponentPeriod structures. - * - * Frees a list of #ECalComponentPeriod structures. - **/ -void -e_cal_component_free_period_list (GSList *period_list) -{ - GSList *l; - - for (l = period_list; l; l = l->next) { - ECalComponentPeriod *period; - - g_assert (l->data != NULL); - - period = l->data; - g_free (period); - } - - g_slist_free (period_list); -} - -/** - * e_cal_component_free_recur_list: - * @recur_list: List of struct #icalrecurrencetype structures. - * - * Frees a list of struct #icalrecurrencetype structures. - **/ -void -e_cal_component_free_recur_list (GSList *recur_list) -{ - GSList *l; - - for (l = recur_list; l; l = l->next) { - struct icalrecurrencetype *r; - - g_assert (l->data != NULL); - r = l->data; - - g_free (r); - } - - g_slist_free (recur_list); -} - -/** - * e_cal_component_free_sequence: - * @sequence: Sequence number value. - * - * Frees a sequence number value. - **/ -void -e_cal_component_free_sequence (int *sequence) -{ - g_return_if_fail (sequence != NULL); - - g_free (sequence); -} - -/** - * e_cal_component_free_text_list: - * @text_list: List of #ECalComponentText structures. - * - * Frees a list of #ECalComponentText structures. This function should only be - * used to free lists of text values as returned by the other getter functions - * of #ECalComponent. - **/ -void -e_cal_component_free_text_list (GSList *text_list) -{ - GSList *l; - - for (l = text_list; l; l = l->next) { - ECalComponentText *text; - - g_assert (l->data != NULL); - - text = l->data; - g_return_if_fail (text != NULL); - g_free (text); - } - - g_slist_free (text_list); -} - -/** - * e_cal_component_free_attendee_list: - * @attendee_list: - * - * - **/ -void -e_cal_component_free_attendee_list (GSList *attendee_list) -{ - GSList *l; - - for (l = attendee_list; l; l = l->next) { - ECalComponentAttendee *attendee; - - g_assert (l->data != NULL); - - attendee = l->data; - g_return_if_fail (attendee != NULL); - g_free (attendee); - } - - g_slist_free (attendee_list); -} - - - -/** - * e_cal_component_has_alarms: - * @comp: A calendar component object. - * - * Checks whether the component has any alarms. - * - * Return value: TRUE if the component has any alarms. - **/ -gboolean -e_cal_component_has_alarms (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_val_if_fail (comp != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE); - - priv = comp->priv; - g_return_val_if_fail (priv->icalcomp != NULL, FALSE); - - return g_hash_table_size (priv->alarm_uid_hash) != 0; -} - -/** - * e_cal_component_add_alarm: - * @comp: A calendar component. - * @alarm: An alarm. - * - * Adds an alarm subcomponent to a calendar component. You should have created - * the @alarm by using e_cal_component_alarm_new(); it is invalid to use a - * #ECalComponentAlarm structure that came from e_cal_component_get_alarm(). After - * adding the alarm, the @alarm structure is no longer valid because the - * internal structures may change and you should get rid of it by using - * e_cal_component_alarm_free(). - **/ -void -e_cal_component_add_alarm (ECalComponent *comp, ECalComponentAlarm *alarm) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (alarm != NULL); - - priv = comp->priv; - - add_alarm (comp, alarm->icalcomp, icalproperty_get_x (alarm->uid)); - icalcomponent_add_component (priv->icalcomp, alarm->icalcomp); -} - -/** - * e_cal_component_remove_alarm: - * @comp: A calendar component. - * @auid: UID of the alarm to remove. - * - * Removes an alarm subcomponent from a calendar component. If the alarm that - * corresponds to the specified @auid had been fetched with - * e_cal_component_get_alarm(), then those alarm structures will be invalid; you - * should get rid of them with e_cal_component_alarm_free() before using this - * function. - **/ -void -e_cal_component_remove_alarm (ECalComponent *comp, const char *auid) -{ - ECalComponentPrivate *priv; - icalcomponent *alarm; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - g_return_if_fail (auid != NULL); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - alarm = g_hash_table_lookup (priv->alarm_uid_hash, auid); - if (!alarm) - return; - - g_hash_table_remove (priv->alarm_uid_hash, auid); - icalcomponent_remove_component (priv->icalcomp, alarm); - icalcomponent_free (alarm); -} - -static gboolean -for_each_remove_all_alarms (gpointer key, gpointer value, gpointer data) -{ - ECalComponent *comp = E_CAL_COMPONENT (data); - ECalComponentPrivate *priv; - icalcomponent *alarm = value; - - priv = comp->priv; - - icalcomponent_remove_component (priv->icalcomp, alarm); - icalcomponent_free (alarm); - - return TRUE; -} - -/** - * e_cal_component_remove_all_alarms: - * @comp: A calendar component - * - * Remove all alarms from the calendar component - **/ -void -e_cal_component_remove_all_alarms (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - - g_return_if_fail (comp != NULL); - g_return_if_fail (E_IS_CAL_COMPONENT (comp)); - - priv = comp->priv; - g_return_if_fail (priv->icalcomp != NULL); - - g_hash_table_foreach_remove (priv->alarm_uid_hash, for_each_remove_all_alarms, comp); -} - - -/* Scans an icalproperty from a calendar component and adds its mapping to our - * own alarm structure. - */ -static void -scan_alarm_property (ECalComponentAlarm *alarm, icalproperty *prop) -{ - icalproperty_kind kind; - const char *xname; - - kind = icalproperty_isa (prop); - - switch (kind) { - case ICAL_ACTION_PROPERTY: - alarm->action = prop; - break; - - case ICAL_ATTACH_PROPERTY: - /* FIXME: mail alarms may have any number of these, not just one */ - alarm->attach = prop; - break; - - case ICAL_DESCRIPTION_PROPERTY: - alarm->description.prop = prop; - alarm->description.altrep_param = icalproperty_get_first_parameter ( - prop, ICAL_ALTREP_PARAMETER); - break; - - case ICAL_DURATION_PROPERTY: - alarm->duration = prop; - break; - - case ICAL_REPEAT_PROPERTY: - alarm->repeat = prop; - break; - - case ICAL_TRIGGER_PROPERTY: - alarm->trigger = prop; - break; - - case ICAL_ATTENDEE_PROPERTY: - scan_attendee (&alarm->attendee_list, prop); - break; - - case ICAL_X_PROPERTY: - xname = icalproperty_get_x_name (prop); - g_assert (xname != NULL); - - if (strcmp (xname, EVOLUTION_ALARM_UID_PROPERTY) == 0) - alarm->uid = prop; - - break; - - default: - break; - } -} - -/* Creates a ECalComponentAlarm from a libical alarm subcomponent */ -static ECalComponentAlarm * -make_alarm (icalcomponent *subcomp) -{ - ECalComponentAlarm *alarm; - icalproperty *prop; - - alarm = g_new (ECalComponentAlarm, 1); - - alarm->icalcomp = subcomp; - alarm->uid = NULL; - - alarm->action = NULL; - alarm->attach = NULL; - alarm->description.prop = NULL; - alarm->description.altrep_param = NULL; - alarm->duration = NULL; - alarm->repeat = NULL; - alarm->trigger = NULL; - alarm->attendee_list = NULL; - - for (prop = icalcomponent_get_first_property (subcomp, ICAL_ANY_PROPERTY); - prop; - prop = icalcomponent_get_next_property (subcomp, ICAL_ANY_PROPERTY)) - scan_alarm_property (alarm, prop); - - g_assert (alarm->uid != NULL); - - return alarm; -} - -/** - * e_cal_component_get_alarm_uids: - * @comp: A calendar component. - * - * Builds a list of the unique identifiers of the alarm subcomponents inside a - * calendar component. - * - * Return value: List of unique identifiers for alarms. This should be freed - * using cal_obj_uid_list_free(). - **/ -GList * -e_cal_component_get_alarm_uids (ECalComponent *comp) -{ - ECalComponentPrivate *priv; - icalcompiter iter; - GList *l; - - g_return_val_if_fail (comp != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), NULL); - - priv = comp->priv; - g_return_val_if_fail (priv->icalcomp != NULL, NULL); - - l = NULL; - for (iter = icalcomponent_begin_component (priv->icalcomp, ICAL_VALARM_COMPONENT); - icalcompiter_deref (&iter) != NULL; - icalcompiter_next (&iter)) { - icalcomponent *subcomp; - icalproperty *prop; - - subcomp = icalcompiter_deref (&iter); - for (prop = icalcomponent_get_first_property (subcomp, ICAL_X_PROPERTY); - prop; - prop = icalcomponent_get_next_property (subcomp, ICAL_X_PROPERTY)) { - const char *xname; - - xname = icalproperty_get_x_name (prop); - g_assert (xname != NULL); - - if (strcmp (xname, EVOLUTION_ALARM_UID_PROPERTY) == 0) { - const char *auid; - - auid = alarm_uid_from_prop (prop); - l = g_list_append (l, g_strdup (auid)); - } - } - } - - return l; -} - -/** - * e_cal_component_get_alarm: - * @comp: A calendar component. - * @auid: Unique identifier for the sought alarm subcomponent. - * - * Queries a particular alarm subcomponent of a calendar component. - * - * Return value: The alarm subcomponent that corresponds to the specified @auid, - * or #NULL if no alarm exists with that UID. This should be freed using - * e_cal_component_alarm_free(). - **/ -ECalComponentAlarm * -e_cal_component_get_alarm (ECalComponent *comp, const char *auid) -{ - ECalComponentPrivate *priv; - icalcomponent *alarm; - - g_return_val_if_fail (comp != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), NULL); - - priv = comp->priv; - g_return_val_if_fail (priv->icalcomp != NULL, NULL); - - g_return_val_if_fail (auid != NULL, NULL); - - alarm = g_hash_table_lookup (priv->alarm_uid_hash, auid); - - if (alarm) - return make_alarm (alarm); - else - return NULL; -} - -/** - * e_cal_component_alarms_free: - * @alarms: Component alarms structure. - * - * Frees a #ECalComponentAlarms structure. - **/ -void -e_cal_component_alarms_free (ECalComponentAlarms *alarms) -{ - GSList *l; - - g_return_if_fail (alarms != NULL); - - g_assert (alarms->comp != NULL); - g_object_unref (G_OBJECT (alarms->comp)); - - for (l = alarms->alarms; l; l = l->next) { - ECalComponentAlarmInstance *instance; - - instance = l->data; - g_assert (instance != NULL); - g_free (instance); - } - - g_slist_free (alarms->alarms); - g_free (alarms); -} - -/** - * e_cal_component_alarm_new: - * - * - * - * Return value: a new alarm component - **/ -ECalComponentAlarm * -e_cal_component_alarm_new (void) -{ - ECalComponentAlarm *alarm; - char *new_auid ; - - alarm = g_new (ECalComponentAlarm, 1); - - alarm->icalcomp = icalcomponent_new (ICAL_VALARM_COMPONENT); - - new_auid = e_cal_component_gen_uid (); - alarm->uid = icalproperty_new_x (new_auid); - icalproperty_set_x_name (alarm->uid, EVOLUTION_ALARM_UID_PROPERTY); - icalcomponent_add_property (alarm->icalcomp, alarm->uid); - g_free (new_auid); - - alarm->action = NULL; - alarm->attach = NULL; - alarm->description.prop = NULL; - alarm->description.altrep_param = NULL; - alarm->duration = NULL; - alarm->repeat = NULL; - alarm->trigger = NULL; - alarm->attendee_list = NULL; - - return alarm; -} - -/** - * e_cal_component_alarm_clone: - * @alarm: An alarm subcomponent. - * - * Creates a new alarm subcomponent by copying the information from another one. - * - * Return value: A newly-created alarm subcomponent with the same values as the - * original one. Should be freed with e_cal_component_alarm_free(). - **/ -ECalComponentAlarm * -e_cal_component_alarm_clone (ECalComponentAlarm *alarm) -{ - icalcomponent *icalcomp; - - g_return_val_if_fail (alarm != NULL, NULL); - - icalcomp = icalcomponent_new_clone (alarm->icalcomp); - return make_alarm (icalcomp); -} - -/** - * e_cal_component_alarm_free: - * @alarm: A calendar alarm. - * - * Frees an alarm structure. - **/ -void -e_cal_component_alarm_free (ECalComponentAlarm *alarm) -{ - GSList *l; - - g_return_if_fail (alarm != NULL); - - g_assert (alarm->icalcomp != NULL); - - if (icalcomponent_get_parent (alarm->icalcomp) == NULL) - icalcomponent_free (alarm->icalcomp); - - alarm->icalcomp = NULL; - alarm->uid = NULL; - alarm->action = NULL; - alarm->attach = NULL; - alarm->description.prop = NULL; - alarm->description.altrep_param = NULL; - alarm->duration = NULL; - alarm->repeat = NULL; - alarm->trigger = NULL; - - for (l = alarm->attendee_list; l != NULL; l = l->next) - g_free (l->data); - g_slist_free (alarm->attendee_list); - alarm->attendee_list = NULL; - - g_free (alarm); -} - -/** - * e_cal_component_alarm_get_uid: - * @alarm: An alarm subcomponent. - * - * Queries the unique identifier of an alarm subcomponent. - * - * Return value: UID of the alarm. - **/ -const char * -e_cal_component_alarm_get_uid (ECalComponentAlarm *alarm) -{ - g_return_val_if_fail (alarm != NULL, NULL); - - return alarm_uid_from_prop (alarm->uid); -} - -/** - * e_cal_component_alarm_get_action: - * @alarm: An alarm. - * @action: Return value for the alarm's action type. - * - * Queries the action type of an alarm. - **/ -void -e_cal_component_alarm_get_action (ECalComponentAlarm *alarm, ECalComponentAlarmAction *action) -{ - enum icalproperty_action ipa; - - g_return_if_fail (alarm != NULL); - g_return_if_fail (action != NULL); - - g_assert (alarm->icalcomp != NULL); - - if (!alarm->action) { - *action = E_CAL_COMPONENT_ALARM_NONE; - return; - } - - ipa = icalproperty_get_action (alarm->action); - - switch (ipa) { - case ICAL_ACTION_AUDIO: - *action = E_CAL_COMPONENT_ALARM_AUDIO; - break; - - case ICAL_ACTION_DISPLAY: - *action = E_CAL_COMPONENT_ALARM_DISPLAY; - break; - - case ICAL_ACTION_EMAIL: - *action = E_CAL_COMPONENT_ALARM_EMAIL; - break; - - case ICAL_ACTION_PROCEDURE: - *action = E_CAL_COMPONENT_ALARM_PROCEDURE; - break; - - case ICAL_ACTION_NONE: - *action = E_CAL_COMPONENT_ALARM_NONE; - break; - - default: - *action = E_CAL_COMPONENT_ALARM_UNKNOWN; - } -} - -/** - * e_cal_component_alarm_set_action: - * @alarm: An alarm. - * @action: Action type. - * - * Sets the action type for an alarm. - **/ -void -e_cal_component_alarm_set_action (ECalComponentAlarm *alarm, ECalComponentAlarmAction action) -{ - enum icalproperty_action ipa; - - g_return_if_fail (alarm != NULL); - g_return_if_fail (action != E_CAL_COMPONENT_ALARM_NONE); - g_return_if_fail (action != E_CAL_COMPONENT_ALARM_UNKNOWN); - - g_assert (alarm->icalcomp != NULL); - - switch (action) { - case E_CAL_COMPONENT_ALARM_AUDIO: - ipa = ICAL_ACTION_AUDIO; - break; - - case E_CAL_COMPONENT_ALARM_DISPLAY: - ipa = ICAL_ACTION_DISPLAY; - break; - - case E_CAL_COMPONENT_ALARM_EMAIL: - ipa = ICAL_ACTION_EMAIL; - break; - - case E_CAL_COMPONENT_ALARM_PROCEDURE: - ipa = ICAL_ACTION_PROCEDURE; - break; - - default: - g_assert_not_reached (); - ipa = ICAL_ACTION_NONE; - } - - if (alarm->action) - icalproperty_set_action (alarm->action, ipa); - else { - alarm->action = icalproperty_new_action (ipa); - icalcomponent_add_property (alarm->icalcomp, alarm->action); - } -} - -/** - * e_cal_component_alarm_get_attach: - * @alarm: An alarm. - * @attach: Return value for the attachment; should be freed using icalattach_unref(). - * - * Queries the attachment property of an alarm. - **/ -void -e_cal_component_alarm_get_attach (ECalComponentAlarm *alarm, icalattach **attach) -{ - g_return_if_fail (alarm != NULL); - g_return_if_fail (attach != NULL); - - g_assert (alarm->icalcomp != NULL); - - if (alarm->attach) { - *attach = icalproperty_get_attach (alarm->attach); - icalattach_ref (*attach); - } else - *attach = NULL; -} - -/** - * e_cal_component_alarm_set_attach: - * @alarm: An alarm. - * @attach: Attachment property or NULL to remove an existing property. - * - * Sets the attachment property of an alarm. - **/ -void -e_cal_component_alarm_set_attach (ECalComponentAlarm *alarm, icalattach *attach) -{ - g_return_if_fail (alarm != NULL); - - g_assert (alarm->icalcomp != NULL); - - if (alarm->attach) { - icalcomponent_remove_property (alarm->icalcomp, alarm->attach); - icalproperty_free (alarm->attach); - alarm->attach = NULL; - } - - if (attach) { - alarm->attach = icalproperty_new_attach (attach); - icalcomponent_add_property (alarm->icalcomp, alarm->attach); - } -} - -/** - * e_cal_component_alarm_get_description: - * @alarm: An alarm. - * @description: Return value for the description property and its parameters. - * - * Queries the description property of an alarm. - **/ -void -e_cal_component_alarm_get_description (ECalComponentAlarm *alarm, ECalComponentText *description) -{ - g_return_if_fail (alarm != NULL); - g_return_if_fail (description != NULL); - - g_assert (alarm->icalcomp != NULL); - - if (alarm->description.prop) - description->value = icalproperty_get_description (alarm->description.prop); - else - description->value = NULL; - - if (alarm->description.altrep_param) - description->altrep = icalparameter_get_altrep (alarm->description.altrep_param); - else - description->altrep = NULL; -} - -/** - * e_cal_component_alarm_set_description: - * @alarm: An alarm. - * @description: Description property and its parameters, or NULL for no description. - * - * Sets the description property of an alarm. - **/ -void -e_cal_component_alarm_set_description (ECalComponentAlarm *alarm, ECalComponentText *description) -{ - g_return_if_fail (alarm != NULL); - - g_assert (alarm->icalcomp != NULL); - - if (alarm->description.prop) { - icalcomponent_remove_property (alarm->icalcomp, alarm->description.prop); - icalproperty_free (alarm->description.prop); - - alarm->description.prop = NULL; - alarm->description.altrep_param = NULL; - } - - if (!description) - return; - - g_return_if_fail (description->value != NULL); - - alarm->description.prop = icalproperty_new_description (description->value); - icalcomponent_add_property (alarm->icalcomp, alarm->description.prop); - - if (description->altrep) { - alarm->description.altrep_param = icalparameter_new_altrep ( - (char *) description->altrep); - icalproperty_add_parameter (alarm->description.prop, - alarm->description.altrep_param); - } -} - -/** - * e_cal_component_alarm_get_repeat: - * @alarm: An alarm. - * @repeat: Return value for the repeat/duration properties. - * - * Queries the repeat/duration properties of an alarm. - **/ -void -e_cal_component_alarm_get_repeat (ECalComponentAlarm *alarm, ECalComponentAlarmRepeat *repeat) -{ - g_return_if_fail (alarm != NULL); - g_return_if_fail (repeat != NULL); - - g_assert (alarm->icalcomp != NULL); - - if (!(alarm->repeat && alarm->duration)) { - repeat->repetitions = 0; - memset (&repeat->duration, 0, sizeof (repeat->duration)); - return; - } - - repeat->repetitions = icalproperty_get_repeat (alarm->repeat); - repeat->duration = icalproperty_get_duration (alarm->duration); -} - -/** - * e_cal_component_alarm_set_repeat: - * @alarm: An alarm. - * @repeat: Repeat/duration values. To remove any repetitions from the alarm, - * set the @repeat.repetitions to 0. - * - * Sets the repeat/duration values for an alarm. - **/ -void -e_cal_component_alarm_set_repeat (ECalComponentAlarm *alarm, ECalComponentAlarmRepeat repeat) -{ - g_return_if_fail (alarm != NULL); - g_return_if_fail (repeat.repetitions >= 0); - - g_assert (alarm->icalcomp != NULL); - - /* Delete old properties */ - - if (alarm->repeat) { - icalcomponent_remove_property (alarm->icalcomp, alarm->repeat); - icalproperty_free (alarm->repeat); - alarm->repeat = NULL; - } - - if (alarm->duration) { - icalcomponent_remove_property (alarm->icalcomp, alarm->duration); - icalproperty_free (alarm->duration); - alarm->duration = NULL; - } - - /* Set the new properties */ - - if (repeat.repetitions == 0) - return; /* For zero extra repetitions the properties should not exist */ - - alarm->repeat = icalproperty_new_repeat (repeat.repetitions); - icalcomponent_add_property (alarm->icalcomp, alarm->repeat); - - alarm->duration = icalproperty_new_duration (repeat.duration); - icalcomponent_add_property (alarm->icalcomp, alarm->duration); -} - -/** - * e_cal_component_alarm_get_trigger: - * @alarm: An alarm. - * @trigger: Return value for the trigger time. - * - * Queries the trigger time for an alarm. - **/ -void -e_cal_component_alarm_get_trigger (ECalComponentAlarm *alarm, ECalComponentAlarmTrigger *trigger) -{ - icalparameter *param; - struct icaltriggertype t; - gboolean relative; - - g_return_if_fail (alarm != NULL); - g_return_if_fail (trigger != NULL); - - g_assert (alarm->icalcomp != NULL); - - if (!alarm->trigger) { - trigger->type = E_CAL_COMPONENT_ALARM_TRIGGER_NONE; - return; - } - - /* Get trigger type */ - - param = icalproperty_get_first_parameter (alarm->trigger, ICAL_VALUE_PARAMETER); - if (param) { - icalparameter_value value; - - value = icalparameter_get_value (param); - - switch (value) { - case ICAL_VALUE_DURATION: - relative = TRUE; - break; - - case ICAL_VALUE_DATETIME: - relative = FALSE; - break; - - default: - g_message ("e_cal_component_alarm_get_trigger(): Unknown value for trigger " - "value %d; using RELATIVE", value); - - relative = TRUE; - break; - } - } else - relative = TRUE; - - /* Get trigger value and the RELATED parameter */ - - t = icalproperty_get_trigger (alarm->trigger); - - if (relative) { - trigger->u.rel_duration = t.duration; - - param = icalproperty_get_first_parameter (alarm->trigger, ICAL_RELATED_PARAMETER); - if (param) { - icalparameter_related rel; - - rel = icalparameter_get_related (param); - - switch (rel) { - case ICAL_RELATED_START: - trigger->type = E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_START; - break; - - case ICAL_RELATED_END: - trigger->type = E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_END; - break; - - default: - g_assert_not_reached (); - } - } else - trigger->type = E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_START; - } else { - trigger->u.abs_time = t.time; - trigger->type = E_CAL_COMPONENT_ALARM_TRIGGER_ABSOLUTE; - } -} - -/** - * e_cal_component_alarm_set_trigger: - * @alarm: An alarm. - * @trigger: Trigger time structure. - * - * Sets the trigger time of an alarm. - **/ -void -e_cal_component_alarm_set_trigger (ECalComponentAlarm *alarm, ECalComponentAlarmTrigger trigger) -{ - struct icaltriggertype t; - icalparameter *param; - icalparameter_value value_type; - icalparameter_related related; - - g_return_if_fail (alarm != NULL); - g_return_if_fail (trigger.type != E_CAL_COMPONENT_ALARM_TRIGGER_NONE); - - g_assert (alarm->icalcomp != NULL); - - /* Delete old trigger */ - - if (alarm->trigger) { - icalcomponent_remove_property (alarm->icalcomp, alarm->trigger); - icalproperty_free (alarm->trigger); - alarm->trigger = NULL; - } - - /* Set the value */ - - related = ICAL_RELATED_START; /* Keep GCC happy */ - - t.time = icaltime_null_time (); - t.duration = icaldurationtype_null_duration (); - switch (trigger.type) { - case E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_START: - t.duration = trigger.u.rel_duration; - value_type = ICAL_VALUE_DURATION; - related = ICAL_RELATED_START; - break; - - case E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_END: - t.duration = trigger.u.rel_duration; - value_type = ICAL_VALUE_DURATION; - related = ICAL_RELATED_END; - break; - - case E_CAL_COMPONENT_ALARM_TRIGGER_ABSOLUTE: - t.time = trigger.u.abs_time; - value_type = ICAL_VALUE_DATETIME; - break; - - default: - g_assert_not_reached (); - return; - } - - alarm->trigger = icalproperty_new_trigger (t); - icalcomponent_add_property (alarm->icalcomp, alarm->trigger); - - /* Value parameters */ - - param = icalproperty_get_first_parameter (alarm->trigger, ICAL_VALUE_PARAMETER); - if (param) - icalparameter_set_value (param, value_type); - else { - param = icalparameter_new_value (value_type); - icalproperty_add_parameter (alarm->trigger, param); - } - - /* Related parameter */ - - if (trigger.type != E_CAL_COMPONENT_ALARM_TRIGGER_ABSOLUTE) { - param = icalproperty_get_first_parameter (alarm->trigger, ICAL_RELATED_PARAMETER); - - if (param) - icalparameter_set_related (param, related); - else { - param = icalparameter_new_related (related); - icalproperty_add_parameter (alarm->trigger, param); - } - } -} - -void -e_cal_component_alarm_get_attendee_list (ECalComponentAlarm *alarm, GSList **attendee_list) -{ - g_return_if_fail (alarm != NULL); - - get_attendee_list (alarm->attendee_list, attendee_list); -} - -void -e_cal_component_alarm_set_attendee_list (ECalComponentAlarm *alarm, GSList *attendee_list) -{ - g_return_if_fail (alarm != NULL); - - set_attendee_list (alarm->icalcomp, &alarm->attendee_list, attendee_list); -} - -gboolean -e_cal_component_alarm_has_attendees (ECalComponentAlarm *alarm) -{ - - g_return_val_if_fail (alarm != NULL, FALSE); - - if (g_slist_length (alarm->attendee_list) > 0) - return TRUE; - - return FALSE; -} - - -/** - * e_cal_component_alarm_get_icalcomponent - * @alarm: An alarm. - * - * Get the icalcomponent associated with the given #ECalComponentAlarm. - * - * Returns: the icalcomponent. - */ -icalcomponent * -e_cal_component_alarm_get_icalcomponent (ECalComponentAlarm *alarm) -{ - g_return_val_if_fail (alarm != NULL, NULL); - return alarm->icalcomp; -} - -/* Returns TRUE if both strings match, i.e. they are both NULL or the - strings are equal. */ -static gboolean -e_cal_component_strings_match (const gchar *string1, - const gchar *string2) -{ - if (string1 == NULL || string2 == NULL) - return (string1 == string2) ? TRUE : FALSE; - - if (!strcmp (string1, string2)) - return TRUE; - - return FALSE; -} - - -/** - * e_cal_component_event_dates_match: - * @comp1: A calendar component object. - * @comp2: A calendar component object. - * - * Checks if the DTSTART and DTEND properties of the 2 components match. - * Note that the events may have different recurrence properties which are not - * taken into account here. - * - * Returns: TRUE if the DTSTART and DTEND properties of the 2 components match. - **/ -gboolean -e_cal_component_event_dates_match (ECalComponent *comp1, - ECalComponent *comp2) -{ - ECalComponentDateTime comp1_dtstart, comp1_dtend; - ECalComponentDateTime comp2_dtstart, comp2_dtend; - gboolean retval = TRUE; - - e_cal_component_get_dtstart (comp1, &comp1_dtstart); - e_cal_component_get_dtend (comp1, &comp1_dtend); - e_cal_component_get_dtstart (comp2, &comp2_dtstart); - e_cal_component_get_dtend (comp2, &comp2_dtend); - - /* If either value is NULL they must both be NULL to match. */ - if (comp1_dtstart.value == NULL || comp2_dtstart.value == NULL) { - if (comp1_dtstart.value != comp2_dtstart.value) { - retval = FALSE; - goto out; - } - } else { - if (icaltime_compare (*comp1_dtstart.value, - *comp2_dtstart.value)) { - retval = FALSE; - goto out; - } - } - - if (comp1_dtend.value == NULL || comp2_dtend.value == NULL) { - if (comp1_dtend.value != comp2_dtend.value) { - retval = FALSE; - goto out; - } - } else { - if (icaltime_compare (*comp1_dtend.value, - *comp2_dtend.value)) { - retval = FALSE; - goto out; - } - } - - /* Now check the timezones. */ - if (!e_cal_component_strings_match (comp1_dtstart.tzid, - comp2_dtstart.tzid)) { - retval = FALSE; - goto out; - } - - if (!e_cal_component_strings_match (comp1_dtend.tzid, - comp2_dtend.tzid)) { - retval = FALSE; - } - - out: - - e_cal_component_free_datetime (&comp1_dtstart); - e_cal_component_free_datetime (&comp1_dtend); - e_cal_component_free_datetime (&comp2_dtstart); - e_cal_component_free_datetime (&comp2_dtend); - - return retval; -} - - diff --git a/calendar/libecal/e-cal-component.h b/calendar/libecal/e-cal-component.h deleted file mode 100644 index 41f23a28d..000000000 --- a/calendar/libecal/e-cal-component.h +++ /dev/null @@ -1,448 +0,0 @@ -/* Evolution calendar - iCalendar component object - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_COMPONENT_H -#define E_CAL_COMPONENT_H - -#include <glib/gmacros.h> -#include <time.h> -#include <glib-object.h> -#include <libical/ical.h> - -G_BEGIN_DECLS - - - -#define E_TYPE_CAL_COMPONENT (e_cal_component_get_type ()) -#define E_CAL_COMPONENT(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_COMPONENT, ECalComponent)) -#define E_CAL_COMPONENT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_COMPONENT, \ - ECalComponentClass)) -#define E_IS_CAL_COMPONENT(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_COMPONENT)) -#define E_IS_CAL_COMPONENT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_COMPONENT)) - -/* Types of calendar components to be stored by a ECalComponent, as per RFC 2445. - * We don't put the alarm component type here since we store alarms as separate - * structures inside the other "real" components. - */ -typedef enum { - E_CAL_COMPONENT_NO_TYPE, - E_CAL_COMPONENT_EVENT, - E_CAL_COMPONENT_TODO, - E_CAL_COMPONENT_JOURNAL, - E_CAL_COMPONENT_FREEBUSY, - E_CAL_COMPONENT_TIMEZONE -} ECalComponentVType; - -/* Field identifiers for a calendar component; these are used by the data model - * for ETable. - * - * NOTE: These are also used in the ETable specification, and the column - * numbers are saved in the user settings file. So don't reorder them! - */ -typedef enum { - E_CAL_COMPONENT_FIELD_CATEGORIES, /* concatenation of the categories list */ - E_CAL_COMPONENT_FIELD_CLASSIFICATION, - E_CAL_COMPONENT_FIELD_COMPLETED, - E_CAL_COMPONENT_FIELD_DTEND, - E_CAL_COMPONENT_FIELD_DTSTART, - E_CAL_COMPONENT_FIELD_DUE, - E_CAL_COMPONENT_FIELD_GEO, - E_CAL_COMPONENT_FIELD_PERCENT, - E_CAL_COMPONENT_FIELD_PRIORITY, - E_CAL_COMPONENT_FIELD_SUMMARY, - E_CAL_COMPONENT_FIELD_TRANSPARENCY, - E_CAL_COMPONENT_FIELD_URL, - E_CAL_COMPONENT_FIELD_HAS_ALARMS, /* not a real field */ - E_CAL_COMPONENT_FIELD_ICON, /* not a real field */ - E_CAL_COMPONENT_FIELD_COMPLETE, /* not a real field */ - E_CAL_COMPONENT_FIELD_RECURRING, /* not a real field */ - E_CAL_COMPONENT_FIELD_OVERDUE, /* not a real field */ - E_CAL_COMPONENT_FIELD_COLOR, /* not a real field */ - E_CAL_COMPONENT_FIELD_STATUS, - E_CAL_COMPONENT_FIELD_COMPONENT, /* not a real field */ - E_CAL_COMPONENT_FIELD_LOCATION, - E_CAL_COMPONENT_FIELD_NUM_FIELDS -} ECalComponentField; - -/* Structures and enumerations to return properties and their parameters */ - -/* CLASSIFICATION property */ -typedef enum { - E_CAL_COMPONENT_CLASS_NONE, - E_CAL_COMPONENT_CLASS_PUBLIC, - E_CAL_COMPONENT_CLASS_PRIVATE, - E_CAL_COMPONENT_CLASS_CONFIDENTIAL, - E_CAL_COMPONENT_CLASS_UNKNOWN -} ECalComponentClassification; - -/* Properties that have time and timezone information */ -typedef struct { - /* Actual date/time value */ - struct icaltimetype *value; - - /* Timezone ID */ - const char *tzid; -} ECalComponentDateTime; - -/* Way in which a period of time is specified */ -typedef enum { - E_CAL_COMPONENT_PERIOD_DATETIME, - E_CAL_COMPONENT_PERIOD_DURATION -} ECalComponentPeriodType; - -/* Period of time, can have explicit start/end times or start/duration instead */ -typedef struct { - ECalComponentPeriodType type; - - struct icaltimetype start; - - union { - struct icaltimetype end; - struct icaldurationtype duration; - } u; -} ECalComponentPeriod; - -/* The type of range */ -typedef enum { - E_CAL_COMPONENT_RANGE_SINGLE, - E_CAL_COMPONENT_RANGE_THISPRIOR, - E_CAL_COMPONENT_RANGE_THISFUTURE -} ECalComponentRangeType; - -typedef struct { - ECalComponentRangeType type; - - ECalComponentDateTime datetime; -} ECalComponentRange; - -/* Text properties */ -typedef struct { - /* Description string */ - const char *value; - - /* Alternate representation URI */ - const char *altrep; -} ECalComponentText; - -/* Time transparency */ -typedef enum { - E_CAL_COMPONENT_TRANSP_NONE, - E_CAL_COMPONENT_TRANSP_TRANSPARENT, - E_CAL_COMPONENT_TRANSP_OPAQUE, - E_CAL_COMPONENT_TRANSP_UNKNOWN -} ECalComponentTransparency; - -/* Organizer & Attendee */ -typedef struct { - const char *value; - - const char *member; - icalparameter_cutype cutype; - icalparameter_role role; - icalparameter_partstat status; - gboolean rsvp; - - const char *delto; - const char *delfrom; - const char *sentby; - const char *cn; - const char *language; -} ECalComponentAttendee; - -typedef struct { - const char *value; - const char *sentby; - const char *cn; - const char *language; -} ECalComponentOrganizer; - -/* Main calendar component object */ - -typedef struct _ECalComponent ECalComponent; -typedef struct _ECalComponentClass ECalComponentClass; - -typedef struct _ECalComponentPrivate ECalComponentPrivate; - -struct _ECalComponent { - GObject object; - - /*< private >*/ - ECalComponentPrivate *priv; -}; - -struct _ECalComponentClass { - GObjectClass parent_class; -}; - -/* Calendar component */ - -GType e_cal_component_get_type (void); - -char *e_cal_component_gen_uid (void); - -ECalComponent *e_cal_component_new (void); - -ECalComponent *e_cal_component_clone (ECalComponent *comp); - -void e_cal_component_set_new_vtype (ECalComponent *comp, ECalComponentVType type); - -gboolean e_cal_component_set_icalcomponent (ECalComponent *comp, icalcomponent *icalcomp); -icalcomponent *e_cal_component_get_icalcomponent (ECalComponent *comp); -void e_cal_component_rescan (ECalComponent *comp); -void e_cal_component_strip_errors (ECalComponent *comp); - -ECalComponentVType e_cal_component_get_vtype (ECalComponent *comp); - -char *e_cal_component_get_as_string (ECalComponent *comp); - -void e_cal_component_commit_sequence (ECalComponent *comp); -void e_cal_component_abort_sequence (ECalComponent *comp); - -void e_cal_component_get_uid (ECalComponent *comp, const char **uid); -void e_cal_component_set_uid (ECalComponent *comp, const char *uid); - -void e_cal_component_get_categories (ECalComponent *comp, const char **categories); -void e_cal_component_set_categories (ECalComponent *comp, const char *categories); -void e_cal_component_get_categories_list (ECalComponent *comp, GSList **categ_list); -void e_cal_component_set_categories_list (ECalComponent *comp, GSList *categ_list); - -void e_cal_component_get_classification (ECalComponent *comp, ECalComponentClassification *classif); -void e_cal_component_set_classification (ECalComponent *comp, ECalComponentClassification classif); - -void e_cal_component_get_comment_list (ECalComponent *comp, GSList **text_list); -void e_cal_component_set_comment_list (ECalComponent *comp, GSList *text_list); - -void e_cal_component_get_completed (ECalComponent *comp, struct icaltimetype **t); -void e_cal_component_set_completed (ECalComponent *comp, struct icaltimetype *t); - -void e_cal_component_get_contact_list (ECalComponent *comp, GSList **text_list); -void e_cal_component_set_contact_list (ECalComponent *comp, GSList *text_list); - -void e_cal_component_get_created (ECalComponent *comp, struct icaltimetype **t); -void e_cal_component_set_created (ECalComponent *comp, struct icaltimetype *t); - -void e_cal_component_get_description_list (ECalComponent *comp, GSList **text_list); -void e_cal_component_set_description_list (ECalComponent *comp, GSList *text_list); - -void e_cal_component_get_dtend (ECalComponent *comp, ECalComponentDateTime *dt); -void e_cal_component_set_dtend (ECalComponent *comp, ECalComponentDateTime *dt); - -void e_cal_component_get_dtstamp (ECalComponent *comp, struct icaltimetype *t); -void e_cal_component_set_dtstamp (ECalComponent *comp, struct icaltimetype *t); - -void e_cal_component_get_dtstart (ECalComponent *comp, ECalComponentDateTime *dt); -void e_cal_component_set_dtstart (ECalComponent *comp, ECalComponentDateTime *dt); - -void e_cal_component_get_due (ECalComponent *comp, ECalComponentDateTime *dt); -void e_cal_component_set_due (ECalComponent *comp, ECalComponentDateTime *dt); - -void e_cal_component_get_exdate_list (ECalComponent *comp, GSList **exdate_list); -void e_cal_component_set_exdate_list (ECalComponent *comp, GSList *exdate_list); -gboolean e_cal_component_has_exdates (ECalComponent *comp); - -void e_cal_component_get_exrule_list (ECalComponent *comp, GSList **recur_list); -void e_cal_component_get_exrule_property_list (ECalComponent *comp, GSList **recur_list); -void e_cal_component_set_exrule_list (ECalComponent *comp, GSList *recur_list); -gboolean e_cal_component_has_exrules (ECalComponent *comp); - -gboolean e_cal_component_has_exceptions (ECalComponent *comp); - -void e_cal_component_get_geo (ECalComponent *comp, struct icalgeotype **geo); -void e_cal_component_set_geo (ECalComponent *comp, struct icalgeotype *geo); - -void e_cal_component_get_last_modified (ECalComponent *comp, struct icaltimetype **t); -void e_cal_component_set_last_modified (ECalComponent *comp, struct icaltimetype *t); - -void e_cal_component_get_organizer (ECalComponent *comp, ECalComponentOrganizer *organizer); -void e_cal_component_set_organizer (ECalComponent *comp, ECalComponentOrganizer *organizer); -gboolean e_cal_component_has_organizer (ECalComponent *comp); - -void e_cal_component_get_percent (ECalComponent *comp, int **percent); -void e_cal_component_set_percent (ECalComponent *comp, int *percent); - -void e_cal_component_get_priority (ECalComponent *comp, int **priority); -void e_cal_component_set_priority (ECalComponent *comp, int *priority); - -void e_cal_component_get_recurid (ECalComponent *comp, ECalComponentRange *recur_id); -const char *e_cal_component_get_recurid_as_string (ECalComponent *comp); -void e_cal_component_set_recurid (ECalComponent *comp, ECalComponentRange *recur_id); - -void e_cal_component_get_rdate_list (ECalComponent *comp, GSList **period_list); -void e_cal_component_set_rdate_list (ECalComponent *comp, GSList *period_list); -gboolean e_cal_component_has_rdates (ECalComponent *comp); - -void e_cal_component_get_rrule_list (ECalComponent *comp, GSList **recur_list); -void e_cal_component_get_rrule_property_list (ECalComponent *comp, GSList **recur_list); -void e_cal_component_set_rrule_list (ECalComponent *comp, GSList *recur_list); -gboolean e_cal_component_has_rrules (ECalComponent *comp); - -gboolean e_cal_component_has_recurrences (ECalComponent *comp); -gboolean e_cal_component_has_simple_recurrence (ECalComponent *comp); -gboolean e_cal_component_is_instance (ECalComponent *comp); - -void e_cal_component_get_sequence (ECalComponent *comp, int **sequence); -void e_cal_component_set_sequence (ECalComponent *comp, int *sequence); - -void e_cal_component_get_status (ECalComponent *comp, icalproperty_status *status); -void e_cal_component_set_status (ECalComponent *comp, icalproperty_status status); - -void e_cal_component_get_summary (ECalComponent *comp, ECalComponentText *summary); -void e_cal_component_set_summary (ECalComponent *comp, ECalComponentText *summary); - -void e_cal_component_get_transparency (ECalComponent *comp, ECalComponentTransparency *transp); -void e_cal_component_set_transparency (ECalComponent *comp, ECalComponentTransparency transp); - -void e_cal_component_get_url (ECalComponent *comp, const char **url); -void e_cal_component_set_url (ECalComponent *comp, const char *url); - -void e_cal_component_get_attendee_list (ECalComponent *comp, GSList **attendee_list); -void e_cal_component_set_attendee_list (ECalComponent *comp, GSList *attendee_list); -gboolean e_cal_component_has_attendees (ECalComponent *comp); - -void e_cal_component_get_location (ECalComponent *comp, const char **location); -void e_cal_component_set_location (ECalComponent *comp, const char *location); - -gboolean e_cal_component_event_dates_match (ECalComponent *comp1, ECalComponent *comp2); - - -/* Functions to free returned values */ - -void e_cal_component_free_categories_list (GSList *categ_list); -void e_cal_component_free_datetime (ECalComponentDateTime *dt); -void e_cal_component_free_range (ECalComponentRange *range); -void e_cal_component_free_exdate_list (GSList *exdate_list); -void e_cal_component_free_geo (struct icalgeotype *geo); -void e_cal_component_free_icaltimetype (struct icaltimetype *t); -void e_cal_component_free_percent (int *percent); -void e_cal_component_free_priority (int *priority); -void e_cal_component_free_period_list (GSList *period_list); -void e_cal_component_free_recur_list (GSList *recur_list); -void e_cal_component_free_sequence (int *sequence); -void e_cal_component_free_text_list (GSList *text_list); -void e_cal_component_free_attendee_list (GSList *attendee_list); - -/* Alarms */ - -/* Opaque structure used to represent alarm subcomponents */ -typedef struct _ECalComponentAlarm ECalComponentAlarm; - -/* An alarm occurrence, i.e. a trigger instance */ -typedef struct { - /* UID of the alarm that triggered */ - const char *auid; - - /* Trigger time, i.e. "5 minutes before the appointment" */ - time_t trigger; - - /* Actual event occurrence to which this trigger corresponds */ - time_t occur_start; - time_t occur_end; -} ECalComponentAlarmInstance; - -/* Alarm trigger instances for a particular component */ -typedef struct { - /* The actual component */ - ECalComponent *comp; - - /* List of ECalComponentAlarmInstance structures */ - GSList *alarms; -} ECalComponentAlarms; - -/* Alarm types */ -typedef enum { - E_CAL_COMPONENT_ALARM_NONE, - E_CAL_COMPONENT_ALARM_AUDIO, - E_CAL_COMPONENT_ALARM_DISPLAY, - E_CAL_COMPONENT_ALARM_EMAIL, - E_CAL_COMPONENT_ALARM_PROCEDURE, - E_CAL_COMPONENT_ALARM_UNKNOWN -} ECalComponentAlarmAction; - -/* Whether a trigger is relative to the start or end of an event occurrence, or - * whether it is specified to occur at an absolute time. - */ -typedef enum { - E_CAL_COMPONENT_ALARM_TRIGGER_NONE, - E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_START, - E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_END, - E_CAL_COMPONENT_ALARM_TRIGGER_ABSOLUTE -} ECalComponentAlarmTriggerType; - -typedef struct { - ECalComponentAlarmTriggerType type; - - union { - struct icaldurationtype rel_duration; - struct icaltimetype abs_time; - } u; -} ECalComponentAlarmTrigger; - -typedef struct { - /* Number of extra repetitions, zero for none */ - int repetitions; - - /* Interval between repetitions */ - struct icaldurationtype duration; -} ECalComponentAlarmRepeat; - -gboolean e_cal_component_has_alarms (ECalComponent *comp); -void e_cal_component_add_alarm (ECalComponent *comp, ECalComponentAlarm *alarm); -void e_cal_component_remove_alarm (ECalComponent *comp, const char *auid); -void e_cal_component_remove_all_alarms (ECalComponent *comp); - -GList *e_cal_component_get_alarm_uids (ECalComponent *comp); -ECalComponentAlarm *e_cal_component_get_alarm (ECalComponent *comp, const char *auid); - -void e_cal_component_alarms_free (ECalComponentAlarms *alarms); - -/* ECalComponentAlarms */ -ECalComponentAlarm *e_cal_component_alarm_new (void); -ECalComponentAlarm *e_cal_component_alarm_clone (ECalComponentAlarm *alarm); -void e_cal_component_alarm_free (ECalComponentAlarm *alarm); - -const char *e_cal_component_alarm_get_uid (ECalComponentAlarm *alarm); - -void e_cal_component_alarm_get_action (ECalComponentAlarm *alarm, ECalComponentAlarmAction *action); -void e_cal_component_alarm_set_action (ECalComponentAlarm *alarm, ECalComponentAlarmAction action); - -void e_cal_component_alarm_get_attach (ECalComponentAlarm *alarm, icalattach **attach); -void e_cal_component_alarm_set_attach (ECalComponentAlarm *alarm, icalattach *attach); - -void e_cal_component_alarm_get_description (ECalComponentAlarm *alarm, ECalComponentText *description); -void e_cal_component_alarm_set_description (ECalComponentAlarm *alarm, ECalComponentText *description); - -void e_cal_component_alarm_get_repeat (ECalComponentAlarm *alarm, ECalComponentAlarmRepeat *repeat); -void e_cal_component_alarm_set_repeat (ECalComponentAlarm *alarm, ECalComponentAlarmRepeat repeat); - -void e_cal_component_alarm_get_trigger (ECalComponentAlarm *alarm, ECalComponentAlarmTrigger *trigger); -void e_cal_component_alarm_set_trigger (ECalComponentAlarm *alarm, ECalComponentAlarmTrigger trigger); - -void e_cal_component_alarm_get_attendee_list (ECalComponentAlarm *alarm, GSList **attendee_list); -void e_cal_component_alarm_set_attendee_list (ECalComponentAlarm *alarm, GSList *attendee_list); -gboolean e_cal_component_alarm_has_attendees (ECalComponentAlarm *alarm); - -icalcomponent *e_cal_component_alarm_get_icalcomponent (ECalComponentAlarm *alarm); - - - -G_END_DECLS - -#endif diff --git a/calendar/libecal/e-cal-listener.c b/calendar/libecal/e-cal-listener.c deleted file mode 100644 index 8657f28f6..000000000 --- a/calendar/libecal/e-cal-listener.c +++ /dev/null @@ -1,1006 +0,0 @@ -/* Evolution calendar listener - * - * Copyright (C) 2001 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#include <config.h> - -#include <bonobo/bonobo-main.h> -#include "e-cal-marshal.h" -#include "e-cal-listener.h" - - - -/* Private part of the CalListener structure */ -struct ECalListenerPrivate { - /* Notification functions and their closure data */ - ECalListenerCalSetModeFn cal_set_mode_fn; - gpointer fn_data; - - /* Whether notification is desired */ - gboolean notify : 1; -}; - -/* Signal IDs */ -enum { - READ_ONLY, - CAL_ADDRESS, - ALARM_ADDRESS, - LDAP_ATTRIBUTE, - STATIC_CAPABILITIES, - OPEN, - REMOVE, - CREATE_OBJECT, - MODIFY_OBJECT, - REMOVE_OBJECT, - DISCARD_ALARM, - RECEIVE_OBJECTS, - SEND_OBJECTS, - DEFAULT_OBJECT, - OBJECT, - OBJECT_LIST, - GET_TIMEZONE, - ADD_TIMEZONE, - SET_DEFAULT_TIMEZONE, - GET_CHANGES, - GET_FREE_BUSY, - QUERY, - CATEGORIES_CHANGED, - BACKEND_ERROR, - LAST_SIGNAL -}; - -static guint signals[LAST_SIGNAL] = { 0 }; - -static BonoboObjectClass *parent_class; - -static ECalendarStatus -convert_status (const GNOME_Evolution_Calendar_CallStatus status) -{ - switch (status) { - case GNOME_Evolution_Calendar_Success: - return E_CALENDAR_STATUS_OK; - case GNOME_Evolution_Calendar_RepositoryOffline: - return E_CALENDAR_STATUS_REPOSITORY_OFFLINE; - case GNOME_Evolution_Calendar_PermissionDenied: - return E_CALENDAR_STATUS_PERMISSION_DENIED; - case GNOME_Evolution_Calendar_ObjectNotFound: - return E_CALENDAR_STATUS_OBJECT_NOT_FOUND; - case GNOME_Evolution_Calendar_InvalidObject: - return E_CALENDAR_STATUS_INVALID_OBJECT; - case GNOME_Evolution_Calendar_ObjectIdAlreadyExists: - return E_CALENDAR_STATUS_OBJECT_ID_ALREADY_EXISTS; - case GNOME_Evolution_Calendar_AuthenticationFailed: - return E_CALENDAR_STATUS_AUTHENTICATION_FAILED; - case GNOME_Evolution_Calendar_AuthenticationRequired: - return E_CALENDAR_STATUS_AUTHENTICATION_REQUIRED; - case GNOME_Evolution_Calendar_OtherError: - default: - return E_CALENDAR_STATUS_OTHER_ERROR; - } -} - -static void -impl_notifyReadOnly (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - const CORBA_boolean read_only, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[READ_ONLY], 0, convert_status (status), read_only); -} - -static void -impl_notifyCalAddress (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - const CORBA_char *address, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[CAL_ADDRESS], 0, convert_status (status), address); -} - -static void -impl_notifyAlarmEmailAddress (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - const CORBA_char *address, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[ALARM_ADDRESS], 0, convert_status (status), address); -} - -static void -impl_notifyLDAPAttribute (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - const CORBA_char *ldap_attribute, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[LDAP_ATTRIBUTE], 0, convert_status (status), ldap_attribute); -} - -static void -impl_notifyStaticCapabilities (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - const CORBA_char *capabilities, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[STATIC_CAPABILITIES], 0, convert_status (status), capabilities); -} - -/* ::notifyCalOpened method */ -static void -impl_notifyCalOpened (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[OPEN], 0, convert_status (status)); -} - -static void -impl_notifyCalRemoved (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[REMOVE], 0, convert_status (status)); -} - -static void -impl_notifyObjectCreated (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - const CORBA_char *uid, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[CREATE_OBJECT], 0, convert_status (status), uid); -} - -static void -impl_notifyObjectModified (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[MODIFY_OBJECT], 0, convert_status (status)); -} - -static void -impl_notifyObjectRemoved (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[REMOVE_OBJECT], 0, convert_status (status)); -} - -static void -impl_notifyAlarmDiscarded (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[DISCARD_ALARM], 0, convert_status (status)); -} - -static void -impl_notifyObjectsReceived (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CallStatus status, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[RECEIVE_OBJECTS], 0, convert_status (status)); -} - -static void -impl_notifyObjectsSent (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - const GNOME_Evolution_Calendar_UserList *user_list, - const CORBA_char *calobj, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - GList *users = NULL; - int i; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - for (i = 0; i < user_list->_length; i++) - users = g_list_append (users, g_strdup (user_list->_buffer[i])); - - g_signal_emit (G_OBJECT (listener), signals[SEND_OBJECTS], 0, convert_status (status), users, calobj); - - g_list_foreach (users, (GFunc) g_free, NULL); - g_list_free (users); -} - -static void -impl_notifyDefaultObjectRequested (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - const CORBA_char *object, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[DEFAULT_OBJECT], 0, convert_status (status), object); -} - -static void -impl_notifyObjectRequested (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - const CORBA_char *object, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[OBJECT], 0, convert_status (status), object); -} - -static GList * -build_object_list (const GNOME_Evolution_Calendar_stringlist *seq) -{ - GList *list; - int i; - - list = NULL; - for (i = 0; i < seq->_length; i++) { - icalcomponent *comp; - - comp = icalcomponent_new_from_string (seq->_buffer[i]); - if (!comp) - continue; - - list = g_list_prepend (list, comp); - } - - return list; -} - -static void -impl_notifyObjectListRequested (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - const GNOME_Evolution_Calendar_stringlist *objects, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - GList *object_list, *l; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - object_list = build_object_list (objects); - - g_signal_emit (G_OBJECT (listener), signals[OBJECT_LIST], 0, convert_status (status), object_list); - - for (l = object_list; l; l = l->next) - icalcomponent_free (l->data); - g_list_free (object_list); -} - -static void -impl_notifyTimezoneRequested (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - const CORBA_char *object, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[GET_TIMEZONE], 0, convert_status (status), object); -} - -static void -impl_notifyTimezoneAdded (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - const CORBA_char *tzid, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[ADD_TIMEZONE], 0, convert_status (status), tzid); -} - -static void -impl_notifyDefaultTimezoneSet (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[SET_DEFAULT_TIMEZONE], 0, convert_status (status)); -} - -static GList * -build_change_list (const GNOME_Evolution_Calendar_CalObjChangeSeq *seq) -{ - GList *list = NULL; - icalcomponent *icalcomp; - int i; - - /* Create the list in reverse order */ - for (i = 0; i < seq->_length; i++) { - GNOME_Evolution_Calendar_CalObjChange *corba_coc; - ECalChange *ccc; - - corba_coc = &seq->_buffer[i]; - ccc = g_new (ECalChange, 1); - - icalcomp = icalparser_parse_string (corba_coc->calobj); - if (!icalcomp) - continue; - - ccc->comp = e_cal_component_new (); - if (!e_cal_component_set_icalcomponent (ccc->comp, icalcomp)) { - icalcomponent_free (icalcomp); - g_object_unref (G_OBJECT (ccc->comp)); - continue; - } - ccc->type = corba_coc->type; - - list = g_list_prepend (list, ccc); - } - - list = g_list_reverse (list); - - return list; -} - -static void -impl_notifyChanges (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - const GNOME_Evolution_Calendar_CalObjChangeSeq *seq, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - GList *changes, *l; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - changes = build_change_list (seq); - - g_signal_emit (G_OBJECT (listener), signals[GET_CHANGES], 0, convert_status (status), changes); - - for (l = changes; l; l = l->next) - g_free (l->data); - g_list_free (changes); -} - -static GList * -build_free_busy_list (const GNOME_Evolution_Calendar_CalObjSeq *seq) -{ - GList *list = NULL; - int i; - - /* Create the list in reverse order */ - for (i = 0; i < seq->_length; i++) { - ECalComponent *comp; - icalcomponent *icalcomp; - icalcomponent_kind kind; - - icalcomp = icalcomponent_new_from_string (seq->_buffer[i]); - if (!icalcomp) - continue; - - kind = icalcomponent_isa (icalcomp); - if (kind == ICAL_VFREEBUSY_COMPONENT) { - comp = e_cal_component_new (); - if (!e_cal_component_set_icalcomponent (comp, icalcomp)) { - icalcomponent_free (icalcomp); - g_object_unref (G_OBJECT (comp)); - continue; - } - - list = g_list_append (list, comp); - } else { - icalcomponent_free (icalcomp); - } - } - - return list; -} - -static void -impl_notifyFreeBusy (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - const GNOME_Evolution_Calendar_CalObjSeq *seq, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - GList *freebusy, *l; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - freebusy = build_free_busy_list (seq); - - g_signal_emit (G_OBJECT (listener), signals[GET_FREE_BUSY], 0, convert_status (status), freebusy); - - for (l = freebusy; l; l = l->next) - g_free (l->data); - g_list_free (freebusy); -} - -static void -impl_notifyQuery (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - const GNOME_Evolution_Calendar_CalView query, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[QUERY], 0, convert_status (status), query); -} - -/* ::notifyCalSetMode method */ -static void -impl_notifyCalSetMode (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CalListener_SetModeStatus status, - GNOME_Evolution_Calendar_CalMode mode, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_assert (priv->cal_set_mode_fn != NULL); - (* priv->cal_set_mode_fn) (listener, status, mode, priv->fn_data); -} - - -/* ::notifyErrorOccurred method */ -static void -impl_notifyErrorOccurred (PortableServer_Servant servant, - const CORBA_char *message, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[BACKEND_ERROR], 0, message); -} - -/* ::notifyCategoriesChanged method */ -static void -impl_notifyCategoriesChanged (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_StringSeq *categories, - CORBA_Environment *ev) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - listener = E_CAL_LISTENER (bonobo_object_from_servant (servant)); - priv = listener->priv; - - if (!priv->notify) - return; - - g_signal_emit (G_OBJECT (listener), signals[CATEGORIES_CHANGED], 0, categories); -} - - - -/* Object initialization function for the calendar listener */ -static void -e_cal_listener_init (ECalListener *listener, ECalListenerClass *klass) -{ - ECalListenerPrivate *priv; - - priv = g_new0 (ECalListenerPrivate, 1); - listener->priv = priv; - - priv->notify = TRUE; -} - -/* Finalize handler for the calendar listener */ -static void -e_cal_listener_finalize (GObject *object) -{ - ECalListener *listener; - ECalListenerPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL_LISTENER (object)); - - listener = E_CAL_LISTENER (object); - priv = listener->priv; - - priv->fn_data = NULL; - - priv->notify = FALSE; - - g_free (priv); - listener->priv = NULL; - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - -/* Class initialization function for the calendar listener */ -static void -e_cal_listener_class_init (ECalListenerClass *klass) -{ - GObjectClass *object_class; - - object_class = (GObjectClass *) klass; - - parent_class = g_type_class_peek_parent (klass); - - klass->epv.notifyReadOnly = impl_notifyReadOnly; - klass->epv.notifyCalAddress = impl_notifyCalAddress; - klass->epv.notifyAlarmEmailAddress = impl_notifyAlarmEmailAddress; - klass->epv.notifyLDAPAttribute = impl_notifyLDAPAttribute; - klass->epv.notifyStaticCapabilities = impl_notifyStaticCapabilities; - klass->epv.notifyCalOpened = impl_notifyCalOpened; - klass->epv.notifyCalRemoved = impl_notifyCalRemoved; - klass->epv.notifyObjectCreated = impl_notifyObjectCreated; - klass->epv.notifyObjectModified = impl_notifyObjectModified; - klass->epv.notifyObjectRemoved = impl_notifyObjectRemoved; - klass->epv.notifyAlarmDiscarded = impl_notifyAlarmDiscarded; - klass->epv.notifyObjectsReceived = impl_notifyObjectsReceived; - klass->epv.notifyObjectsSent = impl_notifyObjectsSent; - klass->epv.notifyDefaultObjectRequested = impl_notifyDefaultObjectRequested; - klass->epv.notifyObjectRequested = impl_notifyObjectRequested; - klass->epv.notifyObjectListRequested = impl_notifyObjectListRequested; - klass->epv.notifyTimezoneRequested = impl_notifyTimezoneRequested; - klass->epv.notifyTimezoneAdded = impl_notifyTimezoneAdded; - klass->epv.notifyDefaultTimezoneSet = impl_notifyDefaultTimezoneSet; - klass->epv.notifyChanges = impl_notifyChanges; - klass->epv.notifyFreeBusy = impl_notifyFreeBusy; - klass->epv.notifyQuery = impl_notifyQuery; - klass->epv.notifyCalSetMode = impl_notifyCalSetMode; - klass->epv.notifyErrorOccurred = impl_notifyErrorOccurred; - klass->epv.notifyCategoriesChanged = impl_notifyCategoriesChanged; - - object_class->finalize = e_cal_listener_finalize; - - signals[READ_ONLY] = - g_signal_new ("read_only", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, read_only), - NULL, NULL, - e_cal_marshal_VOID__INT_BOOLEAN, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_BOOLEAN); - signals[CAL_ADDRESS] = - g_signal_new ("cal_address", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, cal_address), - NULL, NULL, - e_cal_marshal_VOID__INT_STRING, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_STRING); - signals[ALARM_ADDRESS] = - g_signal_new ("alarm_address", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, alarm_address), - NULL, NULL, - e_cal_marshal_VOID__INT_STRING, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_STRING); - signals[LDAP_ATTRIBUTE] = - g_signal_new ("ldap_attribute", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, ldap_attribute), - NULL, NULL, - e_cal_marshal_VOID__INT_STRING, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_STRING); - signals[STATIC_CAPABILITIES] = - g_signal_new ("static_capabilities", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, static_capabilities), - NULL, NULL, - e_cal_marshal_VOID__INT_STRING, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_STRING); - signals[OPEN] = - g_signal_new ("open", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, open), - NULL, NULL, - e_cal_marshal_VOID__INT, - G_TYPE_NONE, 1, G_TYPE_INT); - signals[REMOVE] = - g_signal_new ("remove", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, remove), - NULL, NULL, - e_cal_marshal_VOID__INT, - G_TYPE_NONE, 1, G_TYPE_INT); - signals[CREATE_OBJECT] = - g_signal_new ("create_object", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, create_object), - NULL, NULL, - e_cal_marshal_VOID__INT_STRING, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_STRING); - signals[MODIFY_OBJECT] = - g_signal_new ("modify_object", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, modify_object), - NULL, NULL, - e_cal_marshal_VOID__INT, - G_TYPE_NONE, 1, G_TYPE_INT); - signals[REMOVE_OBJECT] = - g_signal_new ("remove_object", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, remove_object), - NULL, NULL, - e_cal_marshal_VOID__INT, - G_TYPE_NONE, 1, G_TYPE_INT); - signals[DISCARD_ALARM] = - g_signal_new ("discard_alarm", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, discard_alarm), - NULL, NULL, - e_cal_marshal_VOID__INT, - G_TYPE_NONE, 1, G_TYPE_INT); - signals[RECEIVE_OBJECTS] = - g_signal_new ("receive_objects", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, receive_objects), - NULL, NULL, - e_cal_marshal_VOID__INT, - G_TYPE_NONE, 1, G_TYPE_INT); - signals[SEND_OBJECTS] = - g_signal_new ("send_objects", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, send_objects), - NULL, NULL, - e_cal_marshal_VOID__INT_POINTER_STRING, - G_TYPE_NONE, 3, G_TYPE_INT, G_TYPE_POINTER, G_TYPE_STRING); - signals[DEFAULT_OBJECT] = - g_signal_new ("default_object", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, default_object), - NULL, NULL, - e_cal_marshal_VOID__INT_STRING, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_STRING); - signals[OBJECT] = - g_signal_new ("object", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, object), - NULL, NULL, - e_cal_marshal_VOID__INT_STRING, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_STRING); - signals[OBJECT_LIST] = - g_signal_new ("object_list", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, object_list), - NULL, NULL, - e_cal_marshal_VOID__INT_POINTER, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_POINTER); - signals[GET_TIMEZONE] = - g_signal_new ("get_timezone", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, get_timezone), - NULL, NULL, - e_cal_marshal_VOID__INT_STRING, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_STRING); - signals[ADD_TIMEZONE] = - g_signal_new ("add_timezone", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, add_timezone), - NULL, NULL, - e_cal_marshal_VOID__INT_STRING, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_STRING); - signals[SET_DEFAULT_TIMEZONE] = - g_signal_new ("set_default_timezone", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, set_default_timezone), - NULL, NULL, - e_cal_marshal_VOID__INT, - G_TYPE_NONE, 1, G_TYPE_INT); - signals[GET_CHANGES] = - g_signal_new ("get_changes", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, get_changes), - NULL, NULL, - e_cal_marshal_VOID__INT_POINTER, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_POINTER); - signals[GET_FREE_BUSY] = - g_signal_new ("get_free_busy", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, get_free_busy), - NULL, NULL, - e_cal_marshal_VOID__INT_POINTER, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_POINTER); - signals[QUERY] = - g_signal_new ("query", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, query), - NULL, NULL, - e_cal_marshal_VOID__INT_POINTER, - G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_POINTER); - signals[CATEGORIES_CHANGED] = - g_signal_new ("categories_changed", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, categories_changed), - NULL, NULL, - e_cal_marshal_VOID__POINTER, - G_TYPE_NONE, 1, G_TYPE_POINTER); - signals[BACKEND_ERROR] = - g_signal_new ("backend_error", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (ECalListenerClass, backend_error), - NULL, NULL, - e_cal_marshal_VOID__STRING, - G_TYPE_NONE, 1, G_TYPE_STRING); -} - -BONOBO_TYPE_FUNC_FULL (ECalListener, - GNOME_Evolution_Calendar_CalListener, - BONOBO_TYPE_OBJECT, - e_cal_listener); - -ECalListener * -e_cal_listener_construct (ECalListener *listener, - ECalListenerCalSetModeFn cal_set_mode_fn, - gpointer fn_data) -{ - ECalListenerPrivate *priv; - - g_return_val_if_fail (listener != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_LISTENER (listener), NULL); - g_return_val_if_fail (cal_set_mode_fn != NULL, NULL); - - priv = listener->priv; - - priv->cal_set_mode_fn = cal_set_mode_fn; - priv->fn_data = fn_data; - - return listener; -} - -/** - * e_cal_listener_new: - * @cal_set_mode_fn: Function callback for notification that a - * calendar changed modes - * @fn_data: losure data pointer that will be passed to the notification - * functions. - * - * Creates a new #ECalListener object. - * - * Return value: A newly-created #ECalListener object. - **/ -ECalListener * -e_cal_listener_new (ECalListenerCalSetModeFn cal_set_mode_fn, - gpointer fn_data) -{ - ECalListener *listener; - - g_return_val_if_fail (cal_set_mode_fn != NULL, NULL); - - listener = g_object_new (E_TYPE_CAL_LISTENER, - "poa", bonobo_poa_get_threaded (ORBIT_THREAD_HINT_PER_REQUEST, NULL), - NULL); - - return e_cal_listener_construct (listener, - cal_set_mode_fn, - fn_data); -} - -/** - * e_cal_listener_stop_notification: - * @listener: A calendar listener. - * - * Informs a calendar listener that no further notification is desired. The - * callbacks specified when the listener was created will no longer be invoked - * after this function is called. - **/ -void -e_cal_listener_stop_notification (ECalListener *listener) -{ - ECalListenerPrivate *priv; - - g_return_if_fail (listener != NULL); - g_return_if_fail (E_IS_CAL_LISTENER (listener)); - - priv = listener->priv; - g_return_if_fail (priv->notify != FALSE); - - priv->notify = FALSE; -} diff --git a/calendar/libecal/e-cal-listener.h b/calendar/libecal/e-cal-listener.h deleted file mode 100644 index bca55b17b..000000000 --- a/calendar/libecal/e-cal-listener.h +++ /dev/null @@ -1,110 +0,0 @@ -/* Evolution calendar listener - * - * Copyright (C) 2001 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_LISTENER_H -#define E_CAL_LISTENER_H - -#include <bonobo/bonobo-object.h> -#include <libecal/Evolution-DataServer-Calendar.h> -#include <libecal/e-cal-types.h> - -G_BEGIN_DECLS - - - -#define E_TYPE_CAL_LISTENER (e_cal_listener_get_type ()) -#define E_CAL_LISTENER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_LISTENER, ECalListener)) -#define E_CAL_LISTENER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_LISTENER, \ - ECalListenerClass)) -#define E_IS_CAL_LISTENER(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_LISTENER)) -#define E_IS_CAL_LISTENER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_LISTENER)) - -typedef struct ECalListenerPrivate ECalListenerPrivate; - -typedef struct { - BonoboObject xobject; - - /*< private >*/ - ECalListenerPrivate *priv; -} ECalListener; - -typedef struct { - BonoboObjectClass parent_class; - - POA_GNOME_Evolution_Calendar_CalListener__epv epv; - - /* Signals */ - void (*read_only) (ECalListener *listener, ECalendarStatus status, gboolean read_only); - void (*cal_address) (ECalListener *listener, ECalendarStatus status, const char *address); - void (*alarm_address) (ECalListener *listener, ECalendarStatus status, const char *address); - void (*ldap_attribute) (ECalListener *listener, ECalendarStatus status, const char *ldap_attribute); - void (*static_capabilities) (ECalListener *listener, ECalendarStatus status, const char *capabilities); - - void (*open) (ECalListener *listener, ECalendarStatus status); - void (*remove) (ECalListener *listener, ECalendarStatus status); - - void (*create_object) (ECalListener *listener, ECalendarStatus status, const char *id); - void (*modify_object) (ECalListener *listener, ECalendarStatus status); - void (*remove_object) (ECalListener *listener, ECalendarStatus status); - - void (*discard_alarm) (ECalListener *listener, ECalendarStatus status); - - void (*receive_objects) (ECalListener *listener, ECalendarStatus status); - void (*send_objects) (ECalListener *listener, ECalendarStatus status, GList *users, const char *object); - - void (*default_object) (ECalListener *listener, ECalendarStatus status, const char *object); - void (*object) (ECalListener *listener, ECalendarStatus status, const char *object); - void (*object_list) (ECalListener *listener, ECalendarStatus status, GList **objects); - - void (*get_timezone) (ECalListener *listener, ECalendarStatus status, const char *object); - void (*add_timezone) (ECalListener *listener, ECalendarStatus status, const char *tzid); - void (*set_default_timezone) (ECalListener *listener, ECalendarStatus status, const char *tzid); - - void (*get_changes) (ECalListener *listener, ECalendarStatus status, GList *changes); - void (*get_free_busy) (ECalListener *listener, ECalendarStatus status, GList *freebusy); - - void (*query) (ECalListener *listener, ECalendarStatus status, GNOME_Evolution_Calendar_CalView query); - - void (*categories_changed) (ECalListener *listener, ECalendarStatus status, GPtrArray *categories); - void (*backend_error) (ECalListener *listener, ECalendarStatus status, const char *message); -} ECalListenerClass; - -/* Notification functions */ -typedef void (* ECalListenerCalSetModeFn) (ECalListener *listener, - GNOME_Evolution_Calendar_CalListener_SetModeStatus status, - GNOME_Evolution_Calendar_CalMode mode, - gpointer data); - -GType e_cal_listener_get_type (void); - -ECalListener *e_cal_listener_construct (ECalListener *listener, - ECalListenerCalSetModeFn cal_set_mode_fn, - gpointer fn_data); - -ECalListener *e_cal_listener_new (ECalListenerCalSetModeFn cal_set_mode_fn, - gpointer fn_data); - -void e_cal_listener_stop_notification (ECalListener *listener); - - - -G_END_DECLS - -#endif diff --git a/calendar/libecal/e-cal-marshal.list b/calendar/libecal/e-cal-marshal.list deleted file mode 100644 index 0da6996fe..000000000 --- a/calendar/libecal/e-cal-marshal.list +++ /dev/null @@ -1,17 +0,0 @@ -NONE:INT -NONE:POINTER -NONE:STRING -NONE:INT,STRING -NONE:INT,BOOL -NONE:INT,POINTER -NONE:INT,POINTER,STRING -NONE:STRING,INT -NONE:INT,INT -NONE:ENUM,ENUM -NONE:ENUM,STRING -NONE:STRING,BOOL,INT,INT -NONE:STRING,STRING -NONE:STRING,STRING,STRING -NONE:POINTER,ENUM -NONE:POINTER,STRING -NONE:POINTER,POINTER diff --git a/calendar/libecal/e-cal-recur.c b/calendar/libecal/e-cal-recur.c deleted file mode 100644 index ccac755e9..000000000 --- a/calendar/libecal/e-cal-recur.c +++ /dev/null @@ -1,4028 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - * Evolution calendar recurrence rule functions - * - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Damon Chaplin <damon@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <stdlib.h> -#include <string.h> -#include <glib.h> -#include <libgnome/gnome-i18n.h> -#include "e-cal-recur.h" -#include "e-cal-time-util.h" - - -/* - * Introduction to The Recurrence Generation Functions: - * - * Note: This is pretty complicated. See the iCalendar spec (RFC 2445) for - * the specification of the recurrence rules and lots of examples - * (sections 4.3.10 & 4.8.5). We also want to support the older - * vCalendar spec, though this should be easy since it is basically a - * subset of iCalendar. - * - * o An iCalendar event can have any number of recurrence rules specifying - * occurrences of the event, as well as dates & times of specific - * occurrences. It can also have any number of recurrence rules and - * specific dates & times specifying exceptions to the occurrences. - * So we first merge all the occurrences generated, eliminating any - * duplicates, then we generate all the exceptions and remove these to - * form the final set of occurrences. - * - * o There are 7 frequencies of occurrences: YEARLY, MONTHLY, WEEKLY, DAILY, - * HOURLY, MINUTELY & SECONDLY. The 'interval' property specifies the - * multiples of the frequency which we step by. We generate a 'set' of - * occurrences for each period defined by the frequency & interval. - * So for a YEARLY frequency with an interval of 3, we generate a set of - * occurrences for every 3rd year. We use complete years here - any - * generated occurrences that occur before the event's start (or after its - * end) are just discarded. - * - * o There are 8 frequency modifiers: BYMONTH, BYWEEKNO, BYYEARDAY, BYMONTHDAY, - * BYDAY, BYHOUR, BYMINUTE & BYSECOND. These can either add extra occurrences - * or filter out occurrences. For example 'FREQ=YEARLY;BYMONTH=1,2' produces - * 2 occurrences for each year rather than the default 1. And - * 'FREQ=DAILY;BYMONTH=1' filters out all occurrences except those in Jan. - * If the modifier works on periods which are less than the recurrence - * frequency, then extra occurrences are added, otherwise occurrences are - * filtered. So we have 2 functions for each modifier - one to expand events - * and the other to filter. We use a table of functions for each frequency - * which points to the appropriate function to use for each modifier. - * - * o Any number of frequency modifiers can be used in a recurrence rule. - * (Though the iCalendar spec says that BYWEEKNO can only be used in a YEARLY - * rule, and some modifiers aren't appropriate for some frequencies - e.g. - * BYMONTHDAY is not really useful in a WEEKLY frequency, and BYYEARDAY is - * not useful in a MONTHLY or WEEKLY frequency). - * The frequency modifiers are applied in the order given above. The first 5 - * modifier rules (BYMONTH, BYWEEKNO, BYYEARDAY, BYMONTHDAY & BYDAY) all - * produce the days on which the occurrences take place, and so we have to - * compute some of these in parallel rather than sequentially, or we may end - * up with too many days. - * - * o Note that some expansion functions may produce days which are invalid, - * e.g. 31st September, 30th Feb. These invalid days are removed before the - * BYHOUR, BYMINUTE & BYSECOND modifier functions are applied. - * - * o After the set of occurrences for the frequency interval are generated, - * the BYSETPOS property is used to select which of the occurrences are - * finally output. If BYSETPOS is not specified then all the occurrences are - * output. - * - * - * FIXME: I think there are a few errors in this code: - * - * 1) I'm not sure it should be generating events in parallel like it says - * above. That needs to be checked. - * - * 2) I didn't think about timezone changes when implementing this. I just - * assumed all the occurrences of the event would be in local time. - * But when clocks go back or forwards due to daylight-saving time, some - * special handling may be needed, especially for the shorter frequencies. - * e.g. for a MINUTELY frequency it should probably iterate over all the - * minutes before and after clocks go back (i.e. some may be the same local - * time but have different UTC offsets). For longer frequencies, if an - * occurrence lands on the overlapping or non-existant time when clocks - * go back/forward, then it may need to choose which of the times to use - * or move the time forward or something. I'm not sure this is clear in the - * spec. - */ - -/* This is the maximum year we will go up to (inclusive). Since we use time_t - values we can't go past 2037 anyway, and some of our VTIMEZONEs may stop - at 2037 as well. */ -#define MAX_YEAR 2037 - -/* Define this for some debugging output. */ -#if 0 -#define CAL_OBJ_DEBUG 1 -#endif - -/* We will use icalrecurrencetype instead of this eventually. */ -typedef struct { - icalrecurrencetype_frequency freq; - - int interval; - - /* Specifies the end of the recurrence, inclusive. No occurrences are - generated after this date. If it is 0, the event recurs forever. */ - time_t enddate; - - /* WKST property - the week start day: 0 = Monday to 6 = Sunday. */ - gint week_start_day; - - - /* NOTE: I've used GList's here, but it doesn't matter if we use - other data structures like arrays. The code should be easy to - change. So long as it is easy to see if the modifier is set. */ - - /* For BYMONTH modifier. A list of GINT_TO_POINTERs, 0-11. */ - GList *bymonth; - - /* For BYWEEKNO modifier. A list of GINT_TO_POINTERs, [+-]1-53. */ - GList *byweekno; - - /* For BYYEARDAY modifier. A list of GINT_TO_POINTERs, [+-]1-366. */ - GList *byyearday; - - /* For BYMONTHDAY modifier. A list of GINT_TO_POINTERs, [+-]1-31. */ - GList *bymonthday; - - /* For BYDAY modifier. A list of GINT_TO_POINTERs, in pairs. - The first of each pair is the weekday, 0 = Monday to 6 = Sunday. - The second of each pair is the week number [+-]0-53. */ - GList *byday; - - /* For BYHOUR modifier. A list of GINT_TO_POINTERs, 0-23. */ - GList *byhour; - - /* For BYMINUTE modifier. A list of GINT_TO_POINTERs, 0-59. */ - GList *byminute; - - /* For BYSECOND modifier. A list of GINT_TO_POINTERs, 0-60. */ - GList *bysecond; - - /* For BYSETPOS modifier. A list of GINT_TO_POINTERs, +ve or -ve. */ - GList *bysetpos; -} ECalRecurrence; - -/* This is what we use to pass to all the filter functions. */ -typedef struct _RecurData RecurData; -struct _RecurData { - ECalRecurrence *recur; - - /* This is used for the WEEKLY frequency. It is the offset from the - week_start_day. */ - gint weekday_offset; - - /* This is used for fast lookup in BYMONTH filtering. */ - guint8 months[12]; - - /* This is used for fast lookup in BYYEARDAY filtering. */ - guint8 yeardays[367], neg_yeardays[367]; /* Days are 1 - 366. */ - - /* This is used for fast lookup in BYMONTHDAY filtering. */ - guint8 monthdays[32], neg_monthdays[32]; /* Days are 1 to 31. */ - - /* This is used for fast lookup in BYDAY filtering. */ - guint8 weekdays[7]; - - /* This is used for fast lookup in BYHOUR filtering. */ - guint8 hours[24]; - - /* This is used for fast lookup in BYMINUTE filtering. */ - guint8 minutes[60]; - - /* This is used for fast lookup in BYSECOND filtering. */ - guint8 seconds[62]; -}; - -/* This is what we use to represent a date & time. */ -typedef struct _CalObjTime CalObjTime; -struct _CalObjTime { - guint16 year; - guint8 month; /* 0 - 11 */ - guint8 day; /* 1 - 31 */ - guint8 hour; /* 0 - 23 */ - guint8 minute; /* 0 - 59 */ - guint8 second; /* 0 - 59 (maybe up to 61 for leap seconds) */ - guint8 flags; /* The meaning of this depends on where the - CalObjTime is used. In most cases this is - set to TRUE to indicate that this is an - RDATE with an end or a duration set. - In the exceptions code, this is set to TRUE - to indicate that this is an EXDATE with a - DATE value. */ -}; - -/* This is what we use to represent specific recurrence dates. - Note that we assume it starts with a CalObjTime when sorting. */ -typedef struct _CalObjRecurrenceDate CalObjRecurrenceDate; -struct _CalObjRecurrenceDate { - CalObjTime start; - ECalComponentPeriod *period; -}; - -/* The paramter we use to store the enddate in RRULE and EXRULE properties. */ -#define EVOLUTION_END_DATE_PARAMETER "X-EVOLUTION-ENDDATE" - -typedef gboolean (*CalObjFindStartFn) (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime); -typedef gboolean (*CalObjFindNextFn) (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end); -typedef GArray* (*CalObjFilterFn) (RecurData *recur_data, - GArray *occs); - -typedef struct _ECalRecurVTable ECalRecurVTable; -struct _ECalRecurVTable { - CalObjFindStartFn find_start_position; - CalObjFindNextFn find_next_position; - - CalObjFilterFn bymonth_filter; - CalObjFilterFn byweekno_filter; - CalObjFilterFn byyearday_filter; - CalObjFilterFn bymonthday_filter; - CalObjFilterFn byday_filter; - CalObjFilterFn byhour_filter; - CalObjFilterFn byminute_filter; - CalObjFilterFn bysecond_filter; -}; - - -/* This is used to specify which parts of the CalObjTime to compare in - cal_obj_time_compare(). */ -typedef enum { - CALOBJ_YEAR, - CALOBJ_MONTH, - CALOBJ_DAY, - CALOBJ_HOUR, - CALOBJ_MINUTE, - CALOBJ_SECOND -} CalObjTimeComparison; - -static void e_cal_recur_generate_instances_of_rule (ECalComponent *comp, - icalproperty *prop, - time_t start, - time_t end, - ECalRecurInstanceFn cb, - gpointer cb_data, - ECalRecurResolveTimezoneFn tz_cb, - gpointer tz_cb_data, - icaltimezone *default_timezone); - -static ECalRecurrence * e_cal_recur_from_icalproperty (icalproperty *prop, - gboolean exception, - icaltimezone *zone, - gboolean convert_end_date); -static gint e_cal_recur_ical_weekday_to_weekday (enum icalrecurrencetype_weekday day); -static void e_cal_recur_free (ECalRecurrence *r); - - -static gboolean cal_object_get_rdate_end (CalObjTime *occ, - GArray *rdate_periods); -static void cal_object_compute_duration (CalObjTime *start, - CalObjTime *end, - gint *days, - gint *seconds); - -static gboolean generate_instances_for_chunk (ECalComponent *comp, - time_t comp_dtstart, - icaltimezone *zone, - GSList *rrules, - GSList *rdates, - GSList *exrules, - GSList *exdates, - gboolean single_rule, - CalObjTime *event_start, - time_t interval_start, - CalObjTime *chunk_start, - CalObjTime *chunk_end, - gint duration_days, - gint duration_seconds, - gboolean convert_end_date, - ECalRecurInstanceFn cb, - gpointer cb_data); - -static GArray* cal_obj_expand_recurrence (CalObjTime *event_start, - icaltimezone *zone, - ECalRecurrence *recur, - CalObjTime *interval_start, - CalObjTime *interval_end, - gboolean *finished); - -static GArray* cal_obj_generate_set_yearly (RecurData *recur_data, - ECalRecurVTable *vtable, - CalObjTime *occ); -static GArray* cal_obj_generate_set_monthly (RecurData *recur_data, - ECalRecurVTable *vtable, - CalObjTime *occ); -static GArray* cal_obj_generate_set_default (RecurData *recur_data, - ECalRecurVTable *vtable, - CalObjTime *occ); - - -static ECalRecurVTable* cal_obj_get_vtable (icalrecurrencetype_frequency recur_type); -static void cal_obj_initialize_recur_data (RecurData *recur_data, - ECalRecurrence *recur, - CalObjTime *event_start); -static void cal_obj_sort_occurrences (GArray *occs); -static gint cal_obj_time_compare_func (const void *arg1, - const void *arg2); -static void cal_obj_remove_duplicates_and_invalid_dates (GArray *occs); -static void cal_obj_remove_exceptions (GArray *occs, - GArray *ex_occs); -static GArray* cal_obj_bysetpos_filter (ECalRecurrence *recur, - GArray *occs); - - -static gboolean cal_obj_yearly_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime); -static gboolean cal_obj_yearly_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end); - -static gboolean cal_obj_monthly_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime); -static gboolean cal_obj_monthly_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end); - -static gboolean cal_obj_weekly_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime); -static gboolean cal_obj_weekly_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end); - -static gboolean cal_obj_daily_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime); -static gboolean cal_obj_daily_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end); - -static gboolean cal_obj_hourly_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime); -static gboolean cal_obj_hourly_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end); - -static gboolean cal_obj_minutely_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime); -static gboolean cal_obj_minutely_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end); - -static gboolean cal_obj_secondly_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime); -static gboolean cal_obj_secondly_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end); - -static GArray* cal_obj_bymonth_expand (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_bymonth_filter (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_byweekno_expand (RecurData *recur_data, - GArray *occs); -#if 0 -/* This isn't used at present. */ -static GArray* cal_obj_byweekno_filter (RecurData *recur_data, - GArray *occs); -#endif -static GArray* cal_obj_byyearday_expand (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_byyearday_filter (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_bymonthday_expand (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_bymonthday_filter (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_byday_expand_yearly (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_byday_expand_monthly (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_byday_expand_weekly (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_byday_filter (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_byhour_expand (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_byhour_filter (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_byminute_expand (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_byminute_filter (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_bysecond_expand (RecurData *recur_data, - GArray *occs); -static GArray* cal_obj_bysecond_filter (RecurData *recur_data, - GArray *occs); - -static void cal_obj_time_add_months (CalObjTime *cotime, - gint months); -static void cal_obj_time_add_days (CalObjTime *cotime, - gint days); -static void cal_obj_time_add_hours (CalObjTime *cotime, - gint hours); -static void cal_obj_time_add_minutes (CalObjTime *cotime, - gint minutes); -static void cal_obj_time_add_seconds (CalObjTime *cotime, - gint seconds); -static gint cal_obj_time_compare (CalObjTime *cotime1, - CalObjTime *cotime2, - CalObjTimeComparison type); -static gint cal_obj_time_weekday (CalObjTime *cotime); -static gint cal_obj_time_weekday_offset (CalObjTime *cotime, - ECalRecurrence *recur); -static gint cal_obj_time_day_of_year (CalObjTime *cotime); -static void cal_obj_time_find_first_week (CalObjTime *cotime, - RecurData *recur_data); -static void cal_object_time_from_time (CalObjTime *cotime, - time_t t, - icaltimezone *zone); -static gint cal_obj_date_only_compare_func (const void *arg1, - const void *arg2); - - - -static gboolean e_cal_recur_ensure_end_dates (ECalComponent *comp, - gboolean refresh, - ECalRecurResolveTimezoneFn tz_cb, - gpointer tz_cb_data); -static gboolean e_cal_recur_ensure_rule_end_date (ECalComponent *comp, - icalproperty *prop, - gboolean exception, - gboolean refresh, - ECalRecurResolveTimezoneFn tz_cb, - gpointer tz_cb_data); -static gboolean e_cal_recur_ensure_rule_end_date_cb (ECalComponent *comp, - time_t instance_start, - time_t instance_end, - gpointer data); -static time_t e_cal_recur_get_rule_end_date (icalproperty *prop, - icaltimezone *default_timezone); -static void e_cal_recur_set_rule_end_date (icalproperty *prop, - time_t end_date); - - -#ifdef CAL_OBJ_DEBUG -static char* cal_obj_time_to_string (CalObjTime *cotime); -#endif - - -ECalRecurVTable cal_obj_yearly_vtable = { - cal_obj_yearly_find_start_position, - cal_obj_yearly_find_next_position, - - cal_obj_bymonth_expand, - cal_obj_byweekno_expand, - cal_obj_byyearday_expand, - cal_obj_bymonthday_expand, - cal_obj_byday_expand_yearly, - cal_obj_byhour_expand, - cal_obj_byminute_expand, - cal_obj_bysecond_expand -}; - -ECalRecurVTable cal_obj_monthly_vtable = { - cal_obj_monthly_find_start_position, - cal_obj_monthly_find_next_position, - - cal_obj_bymonth_filter, - NULL, /* BYWEEKNO is only applicable to YEARLY frequency. */ - NULL, /* BYYEARDAY is not useful in a MONTHLY frequency. */ - cal_obj_bymonthday_expand, - cal_obj_byday_expand_monthly, - cal_obj_byhour_expand, - cal_obj_byminute_expand, - cal_obj_bysecond_expand -}; - -ECalRecurVTable cal_obj_weekly_vtable = { - cal_obj_weekly_find_start_position, - cal_obj_weekly_find_next_position, - - cal_obj_bymonth_filter, - NULL, /* BYWEEKNO is only applicable to YEARLY frequency. */ - NULL, /* BYYEARDAY is not useful in a WEEKLY frequency. */ - NULL, /* BYMONTHDAY is not useful in a WEEKLY frequency. */ - cal_obj_byday_expand_weekly, - cal_obj_byhour_expand, - cal_obj_byminute_expand, - cal_obj_bysecond_expand -}; - -ECalRecurVTable cal_obj_daily_vtable = { - cal_obj_daily_find_start_position, - cal_obj_daily_find_next_position, - - cal_obj_bymonth_filter, - NULL, /* BYWEEKNO is only applicable to YEARLY frequency. */ - cal_obj_byyearday_filter, - cal_obj_bymonthday_filter, - cal_obj_byday_filter, - cal_obj_byhour_expand, - cal_obj_byminute_expand, - cal_obj_bysecond_expand -}; - -ECalRecurVTable cal_obj_hourly_vtable = { - cal_obj_hourly_find_start_position, - cal_obj_hourly_find_next_position, - - cal_obj_bymonth_filter, - NULL, /* BYWEEKNO is only applicable to YEARLY frequency. */ - cal_obj_byyearday_filter, - cal_obj_bymonthday_filter, - cal_obj_byday_filter, - cal_obj_byhour_filter, - cal_obj_byminute_expand, - cal_obj_bysecond_expand -}; - -ECalRecurVTable cal_obj_minutely_vtable = { - cal_obj_minutely_find_start_position, - cal_obj_minutely_find_next_position, - - cal_obj_bymonth_filter, - NULL, /* BYWEEKNO is only applicable to YEARLY frequency. */ - cal_obj_byyearday_filter, - cal_obj_bymonthday_filter, - cal_obj_byday_filter, - cal_obj_byhour_filter, - cal_obj_byminute_filter, - cal_obj_bysecond_expand -}; - -ECalRecurVTable cal_obj_secondly_vtable = { - cal_obj_secondly_find_start_position, - cal_obj_secondly_find_next_position, - - cal_obj_bymonth_filter, - NULL, /* BYWEEKNO is only applicable to YEARLY frequency. */ - cal_obj_byyearday_filter, - cal_obj_bymonthday_filter, - cal_obj_byday_filter, - cal_obj_byhour_filter, - cal_obj_byminute_filter, - cal_obj_bysecond_filter -}; - -/* - * Calls the given callback function for each occurrence of the event that - * intersects the range between the given start and end times (the end time is - * not included). Note that the occurrences may start before the given start - * time. - * - * If the callback routine returns FALSE the occurrence generation stops. - * - * Both start and end can be -1, in which case we start at the events first - * instance and continue until it ends, or forever if it has no enddate. - */ -void -e_cal_recur_generate_instances (ECalComponent *comp, - time_t start, - time_t end, - ECalRecurInstanceFn cb, - gpointer cb_data, - ECalRecurResolveTimezoneFn tz_cb, - gpointer tz_cb_data, - icaltimezone *default_timezone) -{ -#if 0 - g_print ("In e_cal_recur_generate_instances comp: %p\n", comp); - g_print (" start: %li - %s", start, ctime (&start)); - g_print (" end : %li - %s", end, ctime (&end)); -#endif - e_cal_recur_generate_instances_of_rule (comp, NULL, start, end, - cb, cb_data, tz_cb, tz_cb_data, - default_timezone); -} - - -/* - * Calls the given callback function for each occurrence of the given - * recurrence rule between the given start and end times. If the rule is NULL - * it uses all the rules from the component. - * - * If the callback routine returns FALSE the occurrence generation stops. - * - * The use of the specific rule is for determining the end of a rule when - * COUNT is set. The callback will count instances and store the enddate - * when COUNT is reached. - * - * Both start and end can be -1, in which case we start at the events first - * instance and continue until it ends, or forever if it has no enddate. - */ -static void -e_cal_recur_generate_instances_of_rule (ECalComponent *comp, - icalproperty *prop, - time_t start, - time_t end, - ECalRecurInstanceFn cb, - gpointer cb_data, - ECalRecurResolveTimezoneFn tz_cb, - gpointer tz_cb_data, - icaltimezone *default_timezone) -{ - ECalComponentDateTime dtstart, dtend; - time_t dtstart_time, dtend_time; - GSList *rrules = NULL, *rdates = NULL, elem; - GSList *exrules = NULL, *exdates = NULL; - CalObjTime interval_start, interval_end, event_start, event_end; - CalObjTime chunk_start, chunk_end; - gint days, seconds, year; - gboolean single_rule, convert_end_date = FALSE; - icaltimezone *start_zone = NULL, *end_zone = NULL; - - g_return_if_fail (comp != NULL); - g_return_if_fail (cb != NULL); - g_return_if_fail (tz_cb != NULL); - g_return_if_fail (start >= -1); - g_return_if_fail (end >= -1); - - /* Get dtstart, dtend, recurrences, and exceptions. Note that - cal_component_get_dtend() will convert a DURATION property to a - DTEND so we don't need to worry about that. */ - - e_cal_component_get_dtstart (comp, &dtstart); - e_cal_component_get_dtend (comp, &dtend); - - if (!dtstart.value) { - g_message ("e_cal_recur_generate_instances_of_rule(): bogus " - "component, does not have DTSTART. Skipping..."); - goto out; - } - - /* For DATE-TIME values with a TZID, we use the supplied callback to - resolve the TZID. For DATE values and DATE-TIME values without a - TZID (i.e. floating times) we use the default timezone. */ - if (dtstart.tzid && !dtstart.value->is_date) { - start_zone = (*tz_cb) (dtstart.tzid, tz_cb_data); - if (!start_zone) - start_zone = default_timezone; - } else { - start_zone = default_timezone; - - /* Flag that we need to convert the saved ENDDATE property - to the default timezone. */ - convert_end_date = TRUE; - } - - dtstart_time = icaltime_as_timet_with_zone (*dtstart.value, - start_zone); - if (start == -1) - start = dtstart_time; - - if (dtend.value) { - /* If both DTSTART and DTEND are DATE values, and they are the - same day, we add 1 day to DTEND. This means that most - events created with the old Evolution behavior will still - work OK. I'm not sure what Outlook does in this case. */ - if (dtstart.value->is_date && dtend.value->is_date) { - if (icaltime_compare_date_only (*dtstart.value, - *dtend.value) == 0) { - icaltime_adjust (dtend.value, 1, 0, 0, 0); - } - } - } else { - /* If there is no DTEND, then if DTSTART is a DATE-TIME value - we use the same time (so we have a single point in time). - If DTSTART is a DATE value we add 1 day. */ - dtend.value = g_new (struct icaltimetype, 1); - *dtend.value = *dtstart.value; - - if (dtstart.value->is_date) { - icaltime_adjust (dtend.value, 1, 0, 0, 0); - } - } - - if (dtend.tzid && !dtend.value->is_date) { - end_zone = (*tz_cb) (dtend.tzid, tz_cb_data); - if (!end_zone) - end_zone = default_timezone; - } else { - end_zone = default_timezone; - } - - /* We don't do this any more, since Outlook assumes that the DTEND - date is not included. */ -#if 0 - /* If DTEND is a DATE value, we add 1 day to it so that it includes - the entire day. */ - if (dtend.value->is_date) { - dtend.value->hour = 0; - dtend.value->minute = 0; - dtend.value->second = 0; - icaltime_adjust (dtend.value, 1, 0, 0, 0); - } -#endif - dtend_time = icaltime_as_timet_with_zone (*dtend.value, end_zone); - - /* If there is no recurrence, just call the callback if the event - intersects the given interval. */ - if (!(e_cal_component_has_recurrences (comp) - || e_cal_component_has_exceptions (comp))) { - if ((end == -1 || dtstart_time < end) && dtend_time > start) { - (* cb) (comp, dtstart_time, dtend_time, cb_data); - } - - goto out; - } - - /* If a specific recurrence rule is being used, set up a simple list, - else get the recurrence rules from the component. */ - if (prop) { - single_rule = TRUE; - - elem.data = prop; - elem.next = NULL; - rrules = &elem; - } else if (e_cal_component_is_instance (comp)) { - single_rule = FALSE; - } else { - single_rule = FALSE; - - /* Make sure all the enddates for the rules are set. */ - e_cal_recur_ensure_end_dates (comp, FALSE, tz_cb, tz_cb_data); - - e_cal_component_get_rrule_property_list (comp, &rrules); - e_cal_component_get_rdate_list (comp, &rdates); - e_cal_component_get_exrule_property_list (comp, &exrules); - e_cal_component_get_exdate_list (comp, &exdates); - } - - /* Convert the interval start & end to CalObjTime. Note that if end - is -1 interval_end won't be set, so don't use it! - Also note that we use end - 1 since we want the interval to be - inclusive as it makes the code simpler. We do all calculation - in the timezone of the DTSTART. */ - cal_object_time_from_time (&interval_start, start, start_zone); - if (end != -1) - cal_object_time_from_time (&interval_end, end - 1, start_zone); - - cal_object_time_from_time (&event_start, dtstart_time, start_zone); - cal_object_time_from_time (&event_end, dtend_time, start_zone); - - /* Calculate the duration of the event, which we use for all - occurrences. We can't just subtract start from end since that may - be affected by daylight-saving time. So we want a value of days - + seconds. */ - cal_object_compute_duration (&event_start, &event_end, - &days, &seconds); - - /* Take off the duration from interval_start, so we get occurrences - that start just before the start time but overlap it. But only do - that if the interval is after the event's start time. */ - if (start > dtstart_time) { - cal_obj_time_add_days (&interval_start, -days); - cal_obj_time_add_seconds (&interval_start, -seconds); - } - - /* Expand the recurrence for each year between start & end, or until - the callback returns 0 if end is 0. We do a year at a time to - give the callback function a chance to break out of the loop, and - so we don't get into problems with infinite recurrences. Since we - have to work on complete sets of occurrences, if there is a yearly - frequency it wouldn't make sense to break it into smaller chunks, - since we would then be calculating the same sets several times. - Though this does mean that we sometimes do a lot more work than - is necessary, e.g. if COUNT is set to something quite low. */ - for (year = interval_start.year; - (end == -1 || year <= interval_end.year) && year <= MAX_YEAR; - year++) { - chunk_start = interval_start; - chunk_start.year = year; - if (end != -1) - chunk_end = interval_end; - chunk_end.year = year; - - if (year != interval_start.year) { - chunk_start.month = 0; - chunk_start.day = 1; - chunk_start.hour = 0; - chunk_start.minute = 0; - chunk_start.second = 0; - } - if (end == -1 || year != interval_end.year) { - chunk_end.month = 11; - chunk_end.day = 31; - chunk_end.hour = 23; - chunk_end.minute = 59; - chunk_end.second = 61; - chunk_end.flags = FALSE; - } - - if (!generate_instances_for_chunk (comp, dtstart_time, - start_zone, - rrules, rdates, - exrules, exdates, - single_rule, - &event_start, - start, - &chunk_start, &chunk_end, - days, seconds, - convert_end_date, - cb, cb_data)) - break; - } - - if (!prop) { - e_cal_component_free_period_list (rdates); - e_cal_component_free_exdate_list (exdates); - } - - out: - e_cal_component_free_datetime (&dtstart); - e_cal_component_free_datetime (&dtend); -} - -/* Builds a list of GINT_TO_POINTER() elements out of a short array from a - * struct icalrecurrencetype. - */ -static GList * -array_to_list (short *array, int max_elements) -{ - GList *l; - int i; - - l = NULL; - - for (i = 0; i < max_elements && array[i] != ICAL_RECURRENCE_ARRAY_MAX; i++) - l = g_list_prepend (l, GINT_TO_POINTER ((int) (array[i]))); - return g_list_reverse (l); -} - -/** - * e_cal_recur_from_icalproperty: - * @prop: An RRULE or EXRULE #icalproperty. - * @exception: TRUE if this is an EXRULE rather than an RRULE. - * @zone: The DTSTART timezone, used for converting the UNTIL property if it - * is given as a DATE value. - * @convert_end_date: TRUE if the saved end date needs to be converted to the - * given @zone timezone. This is needed if the DTSTART is a DATE or floating - * time. - * - * Converts an #icalproperty to a #ECalRecurrence. This should be - * freed using the e_cal_recur_free() function. - * - * Return value: #ECalRecurrence structure. - **/ -static ECalRecurrence * -e_cal_recur_from_icalproperty (icalproperty *prop, gboolean exception, - icaltimezone *zone, gboolean convert_end_date) -{ - struct icalrecurrencetype ir; - ECalRecurrence *r; - gint max_elements, i; - GList *elem; - - g_return_val_if_fail (prop != NULL, NULL); - - r = g_new (ECalRecurrence, 1); - - if (exception) - ir = icalproperty_get_exrule (prop); - else - ir = icalproperty_get_rrule (prop); - - r->freq = ir.freq; - r->interval = ir.interval; - - if (ir.count != 0) { - /* If COUNT is set, we use the pre-calculated enddate. - Note that this can be 0 if the RULE doesn't actually - generate COUNT instances. */ - r->enddate = e_cal_recur_get_rule_end_date (prop, convert_end_date ? zone : NULL); - } else { - if (icaltime_is_null_time (ir.until)) { - /* If neither COUNT or UNTIL is set, the event - recurs forever. */ - r->enddate = 0; - } else if (ir.until.is_date) { - /* If UNTIL is a DATE, we stop at the end of - the day, in local time (with the DTSTART timezone). - Note that UNTIL is inclusive so we stop before - midnight. */ - ir.until.hour = 23; - ir.until.minute = 59; - ir.until.second = 59; - ir.until.is_date = FALSE; - - r->enddate = icaltime_as_timet_with_zone (ir.until, - zone); -#if 0 - g_print (" until: %li - %s", r->enddate, ctime (&r->enddate)); -#endif - - } else { - /* If UNTIL is a DATE-TIME, it must be in UTC. */ - icaltimezone *utc_zone; - utc_zone = icaltimezone_get_utc_timezone (); - r->enddate = icaltime_as_timet_with_zone (ir.until, - utc_zone); - } - } - - r->week_start_day = e_cal_recur_ical_weekday_to_weekday (ir.week_start); - - r->bymonth = array_to_list (ir.by_month, - sizeof (ir.by_month) / sizeof (ir.by_month[0])); - for (elem = r->bymonth; elem; elem = elem->next) { - /* We need to convert from 1-12 to 0-11, i.e. subtract 1. */ - int month = GPOINTER_TO_INT (elem->data) - 1; - elem->data = GINT_TO_POINTER (month); - } - - r->byweekno = array_to_list (ir.by_week_no, - sizeof (ir.by_week_no) / sizeof (ir.by_week_no[0])); - - r->byyearday = array_to_list (ir.by_year_day, - sizeof (ir.by_year_day) / sizeof (ir.by_year_day[0])); - - r->bymonthday = array_to_list (ir.by_month_day, - sizeof (ir.by_month_day) / sizeof (ir.by_month_day[0])); - - /* FIXME: libical only supports 8 values, out of possible 107 * 7. */ - r->byday = NULL; - max_elements = sizeof (ir.by_day) / sizeof (ir.by_day[0]); - for (i = 0; i < max_elements && ir.by_day[i] != ICAL_RECURRENCE_ARRAY_MAX; i++) { - enum icalrecurrencetype_weekday day; - gint weeknum, weekday; - - day = icalrecurrencetype_day_day_of_week (ir.by_day[i]); - weeknum = icalrecurrencetype_day_position (ir.by_day[i]); - - weekday = e_cal_recur_ical_weekday_to_weekday (day); - - r->byday = g_list_prepend (r->byday, - GINT_TO_POINTER (weeknum)); - r->byday = g_list_prepend (r->byday, - GINT_TO_POINTER (weekday)); - } - - r->byhour = array_to_list (ir.by_hour, - sizeof (ir.by_hour) / sizeof (ir.by_hour[0])); - - r->byminute = array_to_list (ir.by_minute, - sizeof (ir.by_minute) / sizeof (ir.by_minute[0])); - - r->bysecond = array_to_list (ir.by_second, - sizeof (ir.by_second) / sizeof (ir.by_second[0])); - - r->bysetpos = array_to_list (ir.by_set_pos, - sizeof (ir.by_set_pos) / sizeof (ir.by_set_pos[0])); - - return r; -} - - -static gint -e_cal_recur_ical_weekday_to_weekday (enum icalrecurrencetype_weekday day) -{ - gint weekday; - - switch (day) { - case ICAL_NO_WEEKDAY: /* Monday is the default in RFC2445. */ - case ICAL_MONDAY_WEEKDAY: - weekday = 0; - break; - case ICAL_TUESDAY_WEEKDAY: - weekday = 1; - break; - case ICAL_WEDNESDAY_WEEKDAY: - weekday = 2; - break; - case ICAL_THURSDAY_WEEKDAY: - weekday = 3; - break; - case ICAL_FRIDAY_WEEKDAY: - weekday = 4; - break; - case ICAL_SATURDAY_WEEKDAY: - weekday = 5; - break; - case ICAL_SUNDAY_WEEKDAY: - weekday = 6; - break; - default: - g_warning ("e_cal_recur_ical_weekday_to_weekday(): Unknown week day %d", - day); - weekday = 0; - } - - return weekday; -} - - -/** - * e_cal_recur_free: - * @r: A #ECalRecurrence structure. - * - * Frees a #ECalRecurrence structure. - **/ -static void -e_cal_recur_free (ECalRecurrence *r) -{ - g_return_if_fail (r != NULL); - - g_list_free (r->bymonth); - g_list_free (r->byweekno); - g_list_free (r->byyearday); - g_list_free (r->bymonthday); - g_list_free (r->byday); - g_list_free (r->byhour); - g_list_free (r->byminute); - g_list_free (r->bysecond); - g_list_free (r->bysetpos); - - g_free (r); -} - -/* Generates one year's worth of recurrence instances. Returns TRUE if all the - * callback invocations returned TRUE, or FALSE when any one of them returns - * FALSE, i.e. meaning that the instance generation should be stopped. - * - * This should only output instances whose start time is between chunk_start - * and chunk_end (inclusive), or we may generate duplicates when we do the next - * chunk. (This applies mainly to weekly recurrences, since weeks can span 2 - * years.) - * - * It should also only output instances that are on or after the event's - * DTSTART property and that intersect the required interval, between - * interval_start and interval_end. - */ -static gboolean -generate_instances_for_chunk (ECalComponent *comp, - time_t comp_dtstart, - icaltimezone *zone, - GSList *rrules, - GSList *rdates, - GSList *exrules, - GSList *exdates, - gboolean single_rule, - CalObjTime *event_start, - time_t interval_start, - CalObjTime *chunk_start, - CalObjTime *chunk_end, - gint duration_days, - gint duration_seconds, - gboolean convert_end_date, - ECalRecurInstanceFn cb, - gpointer cb_data) -{ - GArray *occs, *ex_occs, *tmp_occs, *rdate_periods; - CalObjTime cotime, *occ; - GSList *elem; - gint i; - time_t start_time, end_time; - struct icaltimetype start_tt, end_tt; - gboolean cb_status = TRUE, rule_finished, finished = TRUE; - -#if 0 - g_print ("In generate_instances_for_chunk rrules: %p\n" - " %i/%i/%i %02i:%02i:%02i - %i/%i/%i %02i:%02i:%02i\n", - rrules, - chunk_start->day, chunk_start->month + 1, - chunk_start->year, chunk_start->hour, - chunk_start->minute, chunk_start->second, - chunk_end->day, chunk_end->month + 1, - chunk_end->year, chunk_end->hour, - chunk_end->minute, chunk_end->second); -#endif - - occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - ex_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - rdate_periods = g_array_new (FALSE, FALSE, - sizeof (CalObjRecurrenceDate)); - - /* The original DTSTART property is included in the occurrence set, - but not if we are just generating occurrences for a single rule. */ - if (!single_rule) { - /* We add it if it is in this chunk. If it is after this chunk - we set finished to FALSE, since we know we aren't finished - yet. */ - if (cal_obj_time_compare_func (event_start, chunk_end) >= 0) - finished = FALSE; - else if (cal_obj_time_compare_func (event_start, chunk_start) >= 0) - g_array_append_vals (occs, event_start, 1); - } - - /* Expand each of the recurrence rules. */ - for (elem = rrules; elem; elem = elem->next) { - icalproperty *prop; - ECalRecurrence *r; - - prop = elem->data; - r = e_cal_recur_from_icalproperty (prop, FALSE, zone, - convert_end_date); - - tmp_occs = cal_obj_expand_recurrence (event_start, zone, r, - chunk_start, - chunk_end, - &rule_finished); - e_cal_recur_free (r); - - /* If any of the rules return FALSE for finished, we know we - have to carry on so we set finished to FALSE. */ - if (!rule_finished) - finished = FALSE; - - g_array_append_vals (occs, tmp_occs->data, tmp_occs->len); - g_array_free (tmp_occs, TRUE); - } - - /* Add on specific RDATE occurrence dates. If they have an end time - or duration set, flag them as RDATEs, and store a pointer to the - period in the rdate_periods array. Otherwise we can just treat them - as normal occurrences. */ - for (elem = rdates; elem; elem = elem->next) { - ECalComponentPeriod *p; - CalObjRecurrenceDate rdate; - - p = elem->data; - - /* FIXME: We currently assume RDATEs are in the same timezone - as DTSTART. We should get the RDATE timezone and convert - to the DTSTART timezone first. */ - cotime.year = p->start.year; - cotime.month = p->start.month - 1; - cotime.day = p->start.day; - cotime.hour = p->start.hour; - cotime.minute = p->start.minute; - cotime.second = p->start.second; - cotime.flags = FALSE; - - /* If the rdate is after the current chunk we set finished - to FALSE, and we skip it. */ - if (cal_obj_time_compare_func (&cotime, chunk_end) >= 0) { - finished = FALSE; - continue; - } - - /* Check if the end date or duration is set. If it is we need - to store it so we can get it later. (libical seems to set - second to -1 to denote an unset time. See icalvalue.c) - FIXME. */ - if (p->type != E_CAL_COMPONENT_PERIOD_DATETIME - || p->u.end.second != -1) { - cotime.flags = TRUE; - - rdate.start = cotime; - rdate.period = p; - g_array_append_val (rdate_periods, rdate); - } - - g_array_append_val (occs, cotime); - } - - /* Expand each of the exception rules. */ - for (elem = exrules; elem; elem = elem->next) { - icalproperty *prop; - ECalRecurrence *r; - - prop = elem->data; - r = e_cal_recur_from_icalproperty (prop, FALSE, zone, - convert_end_date); - - tmp_occs = cal_obj_expand_recurrence (event_start, zone, r, - chunk_start, - chunk_end, - &rule_finished); - e_cal_recur_free (r); - - g_array_append_vals (ex_occs, tmp_occs->data, tmp_occs->len); - g_array_free (tmp_occs, TRUE); - } - - /* Add on specific exception dates. */ - for (elem = exdates; elem; elem = elem->next) { - ECalComponentDateTime *cdt; - - cdt = elem->data; - - /* FIXME: We currently assume EXDATEs are in the same timezone - as DTSTART. We should get the EXDATE timezone and convert - to the DTSTART timezone first. */ - cotime.year = cdt->value->year; - cotime.month = cdt->value->month - 1; - cotime.day = cdt->value->day; - - /* If the EXDATE has a DATE value, set the time to the start - of the day and set flags to TRUE so we know to skip all - occurrences on that date. */ - if (cdt->value->is_date) { - cotime.hour = 0; - cotime.minute = 0; - cotime.second = 0; - cotime.flags = TRUE; - } else { - cotime.hour = cdt->value->hour; - cotime.minute = cdt->value->minute; - cotime.second = cdt->value->second; - cotime.flags = FALSE; - } - - g_array_append_val (ex_occs, cotime); - } - - - /* Sort all the arrays. */ - cal_obj_sort_occurrences (occs); - cal_obj_sort_occurrences (ex_occs); - - qsort (rdate_periods->data, rdate_periods->len, - sizeof (CalObjRecurrenceDate), cal_obj_time_compare_func); - - /* Create the final array, by removing the exceptions from the - occurrences, and removing any duplicates. */ - cal_obj_remove_exceptions (occs, ex_occs); - - /* Call the callback for each occurrence. If it returns 0 we break - out of the loop. */ - for (i = 0; i < occs->len; i++) { - /* Convert each CalObjTime into a start & end time_t, and - check it is within the bounds of the event & interval. */ - occ = &g_array_index (occs, CalObjTime, i); -#if 0 - g_print ("Checking occurrence: %s\n", - cal_obj_time_to_string (occ)); -#endif - start_tt = icaltime_null_time (); - start_tt.year = occ->year; - start_tt.month = occ->month + 1; - start_tt.day = occ->day; - start_tt.hour = occ->hour; - start_tt.minute = occ->minute; - start_tt.second = occ->second; - start_time = icaltime_as_timet_with_zone (start_tt, zone); - - if (start_time == -1) { - g_warning ("time_t out of range"); - finished = TRUE; - break; - } - - /* Check to ensure that the start time is at or after the - event's DTSTART time, and that it is inside the chunk that - we are currently working on. (Note that the chunk_end time - is never after the interval end time, so this also tests - that we don't go past the end of the required interval). */ - if (start_time < comp_dtstart - || cal_obj_time_compare_func (occ, chunk_start) < 0 - || cal_obj_time_compare_func (occ, chunk_end) > 0) { -#if 0 - g_print (" start time invalid\n"); -#endif - continue; - } - - if (occ->flags) { - /* If it is an RDATE, we see if the end date or - duration was set. If not, we use the same duration - as the original occurrence. */ - if (!cal_object_get_rdate_end (occ, rdate_periods)) { - cal_obj_time_add_days (occ, duration_days); - cal_obj_time_add_seconds (occ, - duration_seconds); - } - } else { - cal_obj_time_add_days (occ, duration_days); - cal_obj_time_add_seconds (occ, duration_seconds); - } - - end_tt = icaltime_null_time (); - end_tt.year = occ->year; - end_tt.month = occ->month + 1; - end_tt.day = occ->day; - end_tt.hour = occ->hour; - end_tt.minute = occ->minute; - end_tt.second = occ->second; - end_time = icaltime_as_timet_with_zone (end_tt, zone); - - if (end_time == -1) { - g_warning ("time_t out of range"); - finished = TRUE; - break; - } - - /* Check that the end time is after the interval start, so we - know that it intersects the required interval. */ - if (end_time <= interval_start) { -#if 0 - g_print (" end time invalid\n"); -#endif - continue; - } - - cb_status = (*cb) (comp, start_time, end_time, cb_data); - if (!cb_status) - break; - } - - g_array_free (occs, TRUE); - g_array_free (ex_occs, TRUE); - g_array_free (rdate_periods, TRUE); - - /* We return TRUE (i.e. carry on) only if the callback has always - returned TRUE and we know that we have more occurrences to generate - (i.e. finished is FALSE). */ - return cb_status && !finished; -} - - -/* This looks up the occurrence time in the sorted rdate_periods array, and - tries to compute the end time of the occurrence. If no end time or duration - is set it returns FALSE and the default duration will be used. */ -static gboolean -cal_object_get_rdate_end (CalObjTime *occ, - GArray *rdate_periods) -{ - CalObjRecurrenceDate *rdate = NULL; - ECalComponentPeriod *p; - gint lower, upper, middle, cmp = 0; - - lower = 0; - upper = rdate_periods->len; - - while (lower < upper) { - middle = (lower + upper) >> 1; - - rdate = &g_array_index (rdate_periods, CalObjRecurrenceDate, - middle); - - cmp = cal_obj_time_compare_func (occ, &rdate->start); - - if (cmp == 0) - break; - else if (cmp < 0) - upper = middle; - else - lower = middle + 1; - } - - /* This should never happen. */ - if (cmp == 0) { - g_warning ("Recurrence date not found"); - return FALSE; - } - - p = rdate->period; - if (p->type == E_CAL_COMPONENT_PERIOD_DATETIME) { - /* FIXME: We currently assume RDATEs are in the same timezone - as DTSTART. We should get the RDATE timezone and convert - to the DTSTART timezone first. */ - occ->year = p->u.end.year; - occ->month = p->u.end.month - 1; - occ->day = p->u.end.day; - occ->hour = p->u.end.hour; - occ->minute = p->u.end.minute; - occ->second = p->u.end.second; - occ->flags = FALSE; - } else { - cal_obj_time_add_days (occ, p->u.duration.weeks * 7 - + p->u.duration.days); - cal_obj_time_add_hours (occ, p->u.duration.hours); - cal_obj_time_add_minutes (occ, p->u.duration.minutes); - cal_obj_time_add_seconds (occ, p->u.duration.seconds); - } - - return TRUE; -} - - -static void -cal_object_compute_duration (CalObjTime *start, - CalObjTime *end, - gint *days, - gint *seconds) -{ - GDate start_date, end_date; - gint start_seconds, end_seconds; - - g_date_clear (&start_date, 1); - g_date_clear (&end_date, 1); - g_date_set_dmy (&start_date, start->day, start->month + 1, - start->year); - g_date_set_dmy (&end_date, end->day, end->month + 1, - end->year); - - *days = g_date_get_julian (&end_date) - g_date_get_julian (&start_date); - start_seconds = start->hour * 3600 + start->minute * 60 - + start->second; - end_seconds = end->hour * 3600 + end->minute * 60 + end->second; - - *seconds = end_seconds - start_seconds; - if (*seconds < 0) { - *days = *days - 1; - *seconds += 24 * 60 * 60; - } -} - - -/* Returns an unsorted GArray of CalObjTime's resulting from expanding the - given recurrence rule within the given interval. Note that it doesn't - clip the generated occurrences to the interval, i.e. if the interval - starts part way through the year this function still returns all the - occurrences for the year. Clipping is done later. - The finished flag is set to FALSE if there are more occurrences to generate - after the given interval.*/ -static GArray* -cal_obj_expand_recurrence (CalObjTime *event_start, - icaltimezone *zone, - ECalRecurrence *recur, - CalObjTime *interval_start, - CalObjTime *interval_end, - gboolean *finished) -{ - ECalRecurVTable *vtable; - CalObjTime *event_end = NULL, event_end_cotime; - RecurData recur_data; - CalObjTime occ, *cotime; - GArray *all_occs, *occs; - gint len; - - /* This is the resulting array of CalObjTime elements. */ - all_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - *finished = TRUE; - - vtable = cal_obj_get_vtable (recur->freq); - if (!vtable) - return all_occs; - - /* Calculate some useful data such as some fast lookup tables. */ - cal_obj_initialize_recur_data (&recur_data, recur, event_start); - - /* Compute the event_end, if the recur's enddate is set. */ - if (recur->enddate > 0) { - cal_object_time_from_time (&event_end_cotime, - recur->enddate, zone); - event_end = &event_end_cotime; - - /* If the enddate is before the requested interval return. */ - if (cal_obj_time_compare_func (event_end, interval_start) < 0) - return all_occs; - } - - /* Set finished to FALSE if we know there will be more occurrences to - do after this interval. */ - if (!interval_end || !event_end - || cal_obj_time_compare_func (event_end, interval_end) > 0) - *finished = FALSE; - - /* Get the first period based on the frequency and the interval that - intersects the interval between start and end. */ - if ((*vtable->find_start_position) (event_start, event_end, - &recur_data, - interval_start, interval_end, - &occ)) - return all_occs; - - /* Loop until the event ends or we go past the end of the required - interval. */ - for (;;) { - /* Generate the set of occurrences for this period. */ - switch (recur->freq) { - case ICAL_YEARLY_RECURRENCE: - occs = cal_obj_generate_set_yearly (&recur_data, - vtable, &occ); - break; - case ICAL_MONTHLY_RECURRENCE: - occs = cal_obj_generate_set_monthly (&recur_data, - vtable, &occ); - break; - default: - occs = cal_obj_generate_set_default (&recur_data, - vtable, &occ); - break; - } - - /* Sort the occurrences and remove duplicates. */ - cal_obj_sort_occurrences (occs); - cal_obj_remove_duplicates_and_invalid_dates (occs); - - /* Apply the BYSETPOS property. */ - occs = cal_obj_bysetpos_filter (recur, occs); - - /* Remove any occs after event_end. */ - len = occs->len - 1; - if (event_end) { - while (len >= 0) { - cotime = &g_array_index (occs, CalObjTime, - len); - if (cal_obj_time_compare_func (cotime, - event_end) <= 0) - break; - len--; - } - } - - /* Add the occurrences onto the main array. */ - if (len >= 0) - g_array_append_vals (all_occs, occs->data, len + 1); - - g_array_free (occs, TRUE); - - /* Skip to the next period, or exit the loop if finished. */ - if ((*vtable->find_next_position) (&occ, event_end, - &recur_data, interval_end)) - break; - } - - return all_occs; -} - - -static GArray* -cal_obj_generate_set_yearly (RecurData *recur_data, - ECalRecurVTable *vtable, - CalObjTime *occ) -{ - ECalRecurrence *recur = recur_data->recur; - GArray *occs_arrays[4], *occs, *occs2; - gint num_occs_arrays = 0, i; - - /* This is a bit complicated, since the iCalendar spec says that - several BYxxx modifiers can be used simultaneously. So we have to - be quite careful when determining the days of the occurrences. - The BYHOUR, BYMINUTE & BYSECOND modifiers are no problem at all. - - The modifiers we have to worry about are: BYMONTH, BYWEEKNO, - BYYEARDAY, BYMONTHDAY & BYDAY. We can't do these sequentially - since each filter will mess up the results of the previous one. - But they aren't all completely independant, e.g. BYMONTHDAY and - BYDAY are related to BYMONTH, and BYDAY is related to BYWEEKNO. - - BYDAY & BYMONTHDAY can also be applied independently, which makes - it worse. So we assume that if BYMONTH or BYWEEKNO is used, then - the BYDAY modifier applies to those, else it is applied - independantly. - - We expand the occurrences in parallel into the occs_arrays[] array, - and then merge them all into one GArray before expanding BYHOUR, - BYMINUTE & BYSECOND. */ - - if (recur->bymonth) { - occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - g_array_append_vals (occs, occ, 1); - - occs = (*vtable->bymonth_filter) (recur_data, occs); - - /* If BYMONTHDAY & BYDAY are both set we need to expand them - in parallel and add the results. */ - if (recur->bymonthday && recur->byday) { - /* Copy the occs array. */ - occs2 = g_array_new (FALSE, FALSE, - sizeof (CalObjTime)); - g_array_append_vals (occs2, occs->data, occs->len); - - occs = (*vtable->bymonthday_filter) (recur_data, occs); - /* Note that we explicitly call the monthly version - of the BYDAY expansion filter. */ - occs2 = cal_obj_byday_expand_monthly (recur_data, - occs2); - - /* Add the 2 resulting arrays together. */ - g_array_append_vals (occs, occs2->data, occs2->len); - g_array_free (occs2, TRUE); - } else { - occs = (*vtable->bymonthday_filter) (recur_data, occs); - /* Note that we explicitly call the monthly version - of the BYDAY expansion filter. */ - occs = cal_obj_byday_expand_monthly (recur_data, occs); - } - - occs_arrays[num_occs_arrays++] = occs; - } - - if (recur->byweekno) { - occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - g_array_append_vals (occs, occ, 1); - - occs = (*vtable->byweekno_filter) (recur_data, occs); - /* Note that we explicitly call the weekly version of the - BYDAY expansion filter. */ - occs = cal_obj_byday_expand_weekly (recur_data, occs); - - occs_arrays[num_occs_arrays++] = occs; - } - - if (recur->byyearday) { - occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - g_array_append_vals (occs, occ, 1); - - occs = (*vtable->byyearday_filter) (recur_data, occs); - - occs_arrays[num_occs_arrays++] = occs; - } - - /* If BYMONTHDAY is set, and BYMONTH is not set, we need to - expand BYMONTHDAY independantly. */ - if (recur->bymonthday && !recur->bymonth) { - occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - g_array_append_vals (occs, occ, 1); - - occs = (*vtable->bymonthday_filter) (recur_data, occs); - - occs_arrays[num_occs_arrays++] = occs; - } - - /* If BYDAY is set, and BYMONTH and BYWEEKNO are not set, we need to - expand BYDAY independantly. */ - if (recur->byday && !recur->bymonth && !recur->byweekno) { - occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - g_array_append_vals (occs, occ, 1); - - occs = (*vtable->byday_filter) (recur_data, occs); - - occs_arrays[num_occs_arrays++] = occs; - } - - /* Add all the arrays together. If no filters were used we just - create an array with one element. */ - if (num_occs_arrays > 0) { - occs = occs_arrays[0]; - for (i = 1; i < num_occs_arrays; i++) { - occs2 = occs_arrays[i]; - g_array_append_vals (occs, occs2->data, occs2->len); - g_array_free (occs2, TRUE); - } - } else { - occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - g_array_append_vals (occs, occ, 1); - } - - /* Now expand BYHOUR, BYMINUTE & BYSECOND. */ - occs = (*vtable->byhour_filter) (recur_data, occs); - occs = (*vtable->byminute_filter) (recur_data, occs); - occs = (*vtable->bysecond_filter) (recur_data, occs); - - return occs; -} - - -static GArray* -cal_obj_generate_set_monthly (RecurData *recur_data, - ECalRecurVTable *vtable, - CalObjTime *occ) -{ - GArray *occs, *occs2; - - /* We start with just the one time in each set. */ - occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - g_array_append_vals (occs, occ, 1); - - occs = (*vtable->bymonth_filter) (recur_data, occs); - - /* We need to combine the output of BYMONTHDAY & BYDAY, by doing them - in parallel rather than sequentially. If we did them sequentially - then we would lose the occurrences generated by BYMONTHDAY, and - instead have repetitions of the occurrences from BYDAY. */ - if (recur_data->recur->bymonthday && recur_data->recur->byday) { - occs2 = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - g_array_append_vals (occs2, occs->data, occs->len); - - occs = (*vtable->bymonthday_filter) (recur_data, occs); - occs2 = (*vtable->byday_filter) (recur_data, occs2); - - g_array_append_vals (occs, occs2->data, occs2->len); - g_array_free (occs2, TRUE); - } else { - occs = (*vtable->bymonthday_filter) (recur_data, occs); - occs = (*vtable->byday_filter) (recur_data, occs); - } - - occs = (*vtable->byhour_filter) (recur_data, occs); - occs = (*vtable->byminute_filter) (recur_data, occs); - occs = (*vtable->bysecond_filter) (recur_data, occs); - - return occs; -} - - -static GArray* -cal_obj_generate_set_default (RecurData *recur_data, - ECalRecurVTable *vtable, - CalObjTime *occ) -{ - GArray *occs; - -#if 0 - g_print ("Generating set for %i/%i/%i %02i:%02i:%02i\n", - occ->day, occ->month + 1, occ->year, occ->hour, occ->minute, - occ->second); -#endif - - /* We start with just the one time in the set. */ - occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - g_array_append_vals (occs, occ, 1); - - occs = (*vtable->bymonth_filter) (recur_data, occs); - if (vtable->byweekno_filter) - occs = (*vtable->byweekno_filter) (recur_data, occs); - if (vtable->byyearday_filter) - occs = (*vtable->byyearday_filter) (recur_data, occs); - if (vtable->bymonthday_filter) - occs = (*vtable->bymonthday_filter) (recur_data, occs); - occs = (*vtable->byday_filter) (recur_data, occs); - - occs = (*vtable->byhour_filter) (recur_data, occs); - occs = (*vtable->byminute_filter) (recur_data, occs); - occs = (*vtable->bysecond_filter) (recur_data, occs); - - return occs; -} - - - -/* Returns the function table corresponding to the recurrence frequency. */ -static ECalRecurVTable* cal_obj_get_vtable (icalrecurrencetype_frequency recur_type) -{ - ECalRecurVTable* vtable; - - switch (recur_type) { - case ICAL_YEARLY_RECURRENCE: - vtable = &cal_obj_yearly_vtable; - break; - case ICAL_MONTHLY_RECURRENCE: - vtable = &cal_obj_monthly_vtable; - break; - case ICAL_WEEKLY_RECURRENCE: - vtable = &cal_obj_weekly_vtable; - break; - case ICAL_DAILY_RECURRENCE: - vtable = &cal_obj_daily_vtable; - break; - case ICAL_HOURLY_RECURRENCE: - vtable = &cal_obj_hourly_vtable; - break; - case ICAL_MINUTELY_RECURRENCE: - vtable = &cal_obj_minutely_vtable; - break; - case ICAL_SECONDLY_RECURRENCE: - vtable = &cal_obj_secondly_vtable; - break; - default: - g_warning ("Unknown recurrence frequency"); - vtable = NULL; - } - - return vtable; -} - - -/* This creates a number of fast lookup tables used when filtering with the - modifier properties BYMONTH, BYYEARDAY etc. */ -static void -cal_obj_initialize_recur_data (RecurData *recur_data, - ECalRecurrence *recur, - CalObjTime *event_start) -{ - GList *elem; - gint month, yearday, monthday, weekday, week_num, hour, minute, second; - - /* Clear the entire RecurData. */ - memset (recur_data, 0, sizeof (RecurData)); - - recur_data->recur = recur; - - /* Set the weekday, used for the WEEKLY frequency and the BYWEEKNO - modifier. */ - recur_data->weekday_offset = cal_obj_time_weekday_offset (event_start, - recur); - - /* Create an array of months from bymonths for fast lookup. */ - elem = recur->bymonth; - while (elem) { - month = GPOINTER_TO_INT (elem->data); - recur_data->months[month] = 1; - elem = elem->next; - } - - /* Create an array of yeardays from byyearday for fast lookup. - We create a second array to handle the negative values. The first - element there corresponds to the last day of the year. */ - elem = recur->byyearday; - while (elem) { - yearday = GPOINTER_TO_INT (elem->data); - if (yearday >= 0) - recur_data->yeardays[yearday] = 1; - else - recur_data->neg_yeardays[-yearday] = 1; - elem = elem->next; - } - - /* Create an array of monthdays from bymonthday for fast lookup. - We create a second array to handle the negative values. The first - element there corresponds to the last day of the month. */ - elem = recur->bymonthday; - while (elem) { - monthday = GPOINTER_TO_INT (elem->data); - if (monthday >= 0) - recur_data->monthdays[monthday] = 1; - else - recur_data->neg_monthdays[-monthday] = 1; - elem = elem->next; - } - - /* Create an array of weekdays from byday for fast lookup. */ - elem = recur->byday; - while (elem) { - weekday = GPOINTER_TO_INT (elem->data); - elem = elem->next; - /* The week number is not used when filtering. */ - week_num = GPOINTER_TO_INT (elem->data); - elem = elem->next; - - recur_data->weekdays[weekday] = 1; - } - - /* Create an array of hours from byhour for fast lookup. */ - elem = recur->byhour; - while (elem) { - hour = GPOINTER_TO_INT (elem->data); - recur_data->hours[hour] = 1; - elem = elem->next; - } - - /* Create an array of minutes from byminutes for fast lookup. */ - elem = recur->byminute; - while (elem) { - minute = GPOINTER_TO_INT (elem->data); - recur_data->minutes[minute] = 1; - elem = elem->next; - } - - /* Create an array of seconds from byseconds for fast lookup. */ - elem = recur->bysecond; - while (elem) { - second = GPOINTER_TO_INT (elem->data); - recur_data->seconds[second] = 1; - elem = elem->next; - } -} - - -static void -cal_obj_sort_occurrences (GArray *occs) -{ - qsort (occs->data, occs->len, sizeof (CalObjTime), - cal_obj_time_compare_func); -} - - -static void -cal_obj_remove_duplicates_and_invalid_dates (GArray *occs) -{ - static const int days_in_month[12] = { - 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 - }; - - CalObjTime *occ, *prev_occ = NULL; - gint len, i, j = 0, year, month, days; - gboolean keep_occ; - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - keep_occ = TRUE; - - if (prev_occ && cal_obj_time_compare_func (occ, - prev_occ) == 0) - keep_occ = FALSE; - - year = occ->year; - month = occ->month; - days = days_in_month[occ->month]; - /* If it is february and a leap year, add a day. */ - if (month == 1 && (year % 4 == 0 - && (year % 100 != 0 - || year % 400 == 0))) - days++; - if (occ->day > days) - keep_occ = FALSE; - - if (keep_occ) { - if (i != j) - g_array_index (occs, CalObjTime, j) - = g_array_index (occs, CalObjTime, i); - j++; - } - - prev_occ = occ; - } - - g_array_set_size (occs, j); -} - - -/* Removes the exceptions from the ex_occs array from the occurrences in the - occs array, and removes any duplicates. Both arrays are sorted. */ -static void -cal_obj_remove_exceptions (GArray *occs, - GArray *ex_occs) -{ - CalObjTime *occ, *prev_occ = NULL, *ex_occ = NULL, *last_occ_kept; - gint i, j = 0, cmp, ex_index, occs_len, ex_occs_len; - gboolean keep_occ, current_time_is_exception = FALSE; - - if (occs->len == 0) - return; - - ex_index = 0; - occs_len = occs->len; - ex_occs_len = ex_occs->len; - - if (ex_occs_len > 0) - ex_occ = &g_array_index (ex_occs, CalObjTime, ex_index); - - for (i = 0; i < occs_len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - keep_occ = TRUE; - - /* If the occurrence is a duplicate of the previous one, skip - it. */ - if (prev_occ - && cal_obj_time_compare_func (occ, prev_occ) == 0) { - keep_occ = FALSE; - - /* If this occurrence is an RDATE with an end or - duration set, and the previous occurrence in the - array was kept, set the RDATE flag of the last one, - so we still use the end date or duration. */ - if (occ->flags && !current_time_is_exception) { - last_occ_kept = &g_array_index (occs, - CalObjTime, - j - 1); - last_occ_kept->flags = TRUE; - } - } else { - /* We've found a new occurrence time. Reset the flag - to indicate that it hasn't been found in the - exceptions array (yet). */ - current_time_is_exception = FALSE; - - if (ex_occ) { - /* Step through the exceptions until we come - to one that matches or follows this - occurrence. */ - while (ex_occ) { - /* If the exception is an EXDATE with - a DATE value, we only have to - compare the date. */ - if (ex_occ->flags) - cmp = cal_obj_date_only_compare_func (ex_occ, occ); - else - cmp = cal_obj_time_compare_func (ex_occ, occ); - - if (cmp > 0) - break; - - /* Move to the next exception, or set - ex_occ to NULL when we reach the - end of array. */ - ex_index++; - if (ex_index < ex_occs_len) - ex_occ = &g_array_index (ex_occs, CalObjTime, ex_index); - else - ex_occ = NULL; - - /* If the exception did match this - occurrence we remove it, and set the - flag to indicate that the current - time is an exception. */ - if (cmp == 0) { - current_time_is_exception = TRUE; - keep_occ = FALSE; - break; - } - } - } - } - - if (keep_occ) { - /* We are keeping this occurrence, so we move it to - the next free space, unless its position hasn't - changed (i.e. all previous occurrences were also - kept). */ - if (i != j) - g_array_index (occs, CalObjTime, j) - = g_array_index (occs, CalObjTime, i); - j++; - } - - prev_occ = occ; - } - - g_array_set_size (occs, j); -} - - - -static GArray* -cal_obj_bysetpos_filter (ECalRecurrence *recur, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - GList *elem; - gint len, pos; - - /* If BYSETPOS has not been specified, or the array is empty, just - return the array. */ - elem = recur->bysetpos; - if (!elem || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - /* Iterate over the indices given in bysetpos, adding the corresponding - element from occs to new_occs. */ - len = occs->len; - while (elem) { - pos = GPOINTER_TO_INT (elem->data); - - /* Negative values count back from the end of the array. */ - if (pos < 0) - pos += len; - /* Positive values need to be decremented since the array is - 0-based. */ - else - pos--; - - if (pos >= 0 && pos < len) { - occ = &g_array_index (occs, CalObjTime, pos); - g_array_append_vals (new_occs, occ, 1); - } - elem = elem->next; - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - - - -/* Finds the first year from the event_start, counting in multiples of the - recurrence interval, that intersects the given interval. It returns TRUE - if there is no intersection. */ -static gboolean -cal_obj_yearly_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime) -{ - *cotime = *event_start; - - /* Move on to the next interval, if the event starts before the - given interval. */ - if (cotime->year < interval_start->year) { - gint years = interval_start->year - cotime->year - + recur_data->recur->interval - 1; - years -= years % recur_data->recur->interval; - /* NOTE: The day may now be invalid, e.g. 29th Feb. */ - cotime->year += years; - } - - if ((event_end && cotime->year > event_end->year) - || (interval_end && cotime->year > interval_end->year)) - return TRUE; - - return FALSE; -} - - -static gboolean -cal_obj_yearly_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end) -{ - /* NOTE: The day may now be invalid, e.g. 29th Feb. */ - cotime->year += recur_data->recur->interval; - - if ((event_end && cotime->year > event_end->year) - || (interval_end && cotime->year > interval_end->year)) - return TRUE; - - return FALSE; -} - - - -static gboolean -cal_obj_monthly_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime) -{ - *cotime = *event_start; - - /* Move on to the next interval, if the event starts before the - given interval. */ - if (cal_obj_time_compare (cotime, interval_start, CALOBJ_MONTH) < 0) { - gint months = (interval_start->year - cotime->year) * 12 - + interval_start->month - cotime->month - + recur_data->recur->interval - 1; - months -= months % recur_data->recur->interval; - /* NOTE: The day may now be invalid, e.g. 31st Sep. */ - cal_obj_time_add_months (cotime, months); - } - - if (event_end && cal_obj_time_compare (cotime, event_end, - CALOBJ_MONTH) > 0) - return TRUE; - if (interval_end && cal_obj_time_compare (cotime, interval_end, - CALOBJ_MONTH) > 0) - return TRUE; - - return FALSE; -} - - -static gboolean -cal_obj_monthly_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end) -{ - /* NOTE: The day may now be invalid, e.g. 31st Sep. */ - cal_obj_time_add_months (cotime, recur_data->recur->interval); - - if (event_end && cal_obj_time_compare (cotime, event_end, - CALOBJ_MONTH) > 0) - return TRUE; - if (interval_end && cal_obj_time_compare (cotime, interval_end, - CALOBJ_MONTH) > 0) - return TRUE; - - return FALSE; -} - - - -static gboolean -cal_obj_weekly_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime) -{ - GDate event_start_date, interval_start_date; - guint32 event_start_julian, interval_start_julian; - gint interval_start_weekday_offset; - CalObjTime week_start; - - if (event_end && cal_obj_time_compare (event_end, interval_start, - CALOBJ_DAY) < 0) - return TRUE; - if (interval_end && cal_obj_time_compare (event_start, interval_end, - CALOBJ_DAY) > 0) - return TRUE; - - *cotime = *event_start; - - /* Convert the event start and interval start to GDates, so we can - easily find the number of days between them. */ - g_date_clear (&event_start_date, 1); - g_date_set_dmy (&event_start_date, event_start->day, - event_start->month + 1, event_start->year); - g_date_clear (&interval_start_date, 1); - g_date_set_dmy (&interval_start_date, interval_start->day, - interval_start->month + 1, interval_start->year); - - /* Calculate the start of the weeks corresponding to the event start - and interval start. */ - event_start_julian = g_date_get_julian (&event_start_date); - event_start_julian -= recur_data->weekday_offset; - - interval_start_julian = g_date_get_julian (&interval_start_date); - interval_start_weekday_offset = cal_obj_time_weekday_offset (interval_start, recur_data->recur); - interval_start_julian -= interval_start_weekday_offset; - - /* We want to find the first full week using the recurrence interval - that intersects the given interval dates. */ - if (event_start_julian < interval_start_julian) { - gint weeks = (interval_start_julian - event_start_julian) / 7; - weeks += recur_data->recur->interval - 1; - weeks -= weeks % recur_data->recur->interval; - cal_obj_time_add_days (cotime, weeks * 7); - } - - week_start = *cotime; - cal_obj_time_add_days (&week_start, -recur_data->weekday_offset); - - if (event_end && cal_obj_time_compare (&week_start, event_end, - CALOBJ_DAY) > 0) - return TRUE; - if (interval_end && cal_obj_time_compare (&week_start, interval_end, - CALOBJ_DAY) > 0) - return TRUE; - - return FALSE; -} - - -static gboolean -cal_obj_weekly_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end) -{ - CalObjTime week_start; - - cal_obj_time_add_days (cotime, recur_data->recur->interval * 7); - - /* Return TRUE if the start of this week is after the event finishes - or is after the end of the required interval. */ - week_start = *cotime; - cal_obj_time_add_days (&week_start, -recur_data->weekday_offset); - -#ifdef CAL_OBJ_DEBUG - g_print ("Next day: %s\n", cal_obj_time_to_string (cotime)); - g_print ("Week Start: %s\n", cal_obj_time_to_string (&week_start)); -#endif - - if (event_end && cal_obj_time_compare (&week_start, event_end, - CALOBJ_DAY) > 0) - return TRUE; - if (interval_end && cal_obj_time_compare (&week_start, interval_end, - CALOBJ_DAY) > 0) { -#ifdef CAL_OBJ_DEBUG - g_print ("Interval end reached: %s\n", - cal_obj_time_to_string (interval_end)); -#endif - return TRUE; - } - - return FALSE; -} - - -static gboolean -cal_obj_daily_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime) -{ - GDate event_start_date, interval_start_date; - guint32 event_start_julian, interval_start_julian, days; - - if (interval_end && cal_obj_time_compare (event_start, interval_end, - CALOBJ_DAY) > 0) - return TRUE; - if (event_end && cal_obj_time_compare (event_end, interval_start, - CALOBJ_DAY) < 0) - return TRUE; - - *cotime = *event_start; - - /* Convert the event start and interval start to GDates, so we can - easily find the number of days between them. */ - g_date_clear (&event_start_date, 1); - g_date_set_dmy (&event_start_date, event_start->day, - event_start->month + 1, event_start->year); - g_date_clear (&interval_start_date, 1); - g_date_set_dmy (&interval_start_date, interval_start->day, - interval_start->month + 1, interval_start->year); - - event_start_julian = g_date_get_julian (&event_start_date); - interval_start_julian = g_date_get_julian (&interval_start_date); - - if (event_start_julian < interval_start_julian) { - days = interval_start_julian - event_start_julian - + recur_data->recur->interval - 1; - days -= days % recur_data->recur->interval; - cal_obj_time_add_days (cotime, days); - } - - if (event_end && cal_obj_time_compare (cotime, event_end, - CALOBJ_DAY) > 0) - return TRUE; - if (interval_end && cal_obj_time_compare (cotime, interval_end, - CALOBJ_DAY) > 0) - return TRUE; - - return FALSE; -} - - -static gboolean -cal_obj_daily_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end) -{ - cal_obj_time_add_days (cotime, recur_data->recur->interval); - - if (event_end && cal_obj_time_compare (cotime, event_end, - CALOBJ_DAY) > 0) - return TRUE; - if (interval_end && cal_obj_time_compare (cotime, interval_end, - CALOBJ_DAY) > 0) - return TRUE; - - return FALSE; -} - - -static gboolean -cal_obj_hourly_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime) -{ - GDate event_start_date, interval_start_date; - guint32 event_start_julian, interval_start_julian, hours; - - if (interval_end && cal_obj_time_compare (event_start, interval_end, - CALOBJ_HOUR) > 0) - return TRUE; - if (event_end && cal_obj_time_compare (event_end, interval_start, - CALOBJ_HOUR) < 0) - return TRUE; - - *cotime = *event_start; - - if (cal_obj_time_compare (event_start, interval_start, - CALOBJ_HOUR) < 0) { - /* Convert the event start and interval start to GDates, so we - can easily find the number of days between them. */ - g_date_clear (&event_start_date, 1); - g_date_set_dmy (&event_start_date, event_start->day, - event_start->month + 1, event_start->year); - g_date_clear (&interval_start_date, 1); - g_date_set_dmy (&interval_start_date, interval_start->day, - interval_start->month + 1, - interval_start->year); - - event_start_julian = g_date_get_julian (&event_start_date); - interval_start_julian = g_date_get_julian (&interval_start_date); - - hours = (interval_start_julian - event_start_julian) * 24; - hours += interval_start->hour - event_start->hour; - hours += recur_data->recur->interval - 1; - hours -= hours % recur_data->recur->interval; - cal_obj_time_add_hours (cotime, hours); - } - - if (event_end && cal_obj_time_compare (cotime, event_end, - CALOBJ_HOUR) > 0) - return TRUE; - if (interval_end && cal_obj_time_compare (cotime, interval_end, - CALOBJ_HOUR) > 0) - return TRUE; - - return FALSE; -} - - -static gboolean -cal_obj_hourly_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end) -{ - cal_obj_time_add_hours (cotime, recur_data->recur->interval); - - if (event_end && cal_obj_time_compare (cotime, event_end, - CALOBJ_HOUR) > 0) - return TRUE; - if (interval_end && cal_obj_time_compare (cotime, interval_end, - CALOBJ_HOUR) > 0) - return TRUE; - - return FALSE; -} - - -static gboolean -cal_obj_minutely_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime) -{ - GDate event_start_date, interval_start_date; - guint32 event_start_julian, interval_start_julian, minutes; - - if (interval_end && cal_obj_time_compare (event_start, interval_end, - CALOBJ_MINUTE) > 0) - return TRUE; - if (event_end && cal_obj_time_compare (event_end, interval_start, - CALOBJ_MINUTE) < 0) - return TRUE; - - *cotime = *event_start; - - if (cal_obj_time_compare (event_start, interval_start, - CALOBJ_MINUTE) < 0) { - /* Convert the event start and interval start to GDates, so we - can easily find the number of days between them. */ - g_date_clear (&event_start_date, 1); - g_date_set_dmy (&event_start_date, event_start->day, - event_start->month + 1, event_start->year); - g_date_clear (&interval_start_date, 1); - g_date_set_dmy (&interval_start_date, interval_start->day, - interval_start->month + 1, - interval_start->year); - - event_start_julian = g_date_get_julian (&event_start_date); - interval_start_julian = g_date_get_julian (&interval_start_date); - - minutes = (interval_start_julian - event_start_julian) - * 24 * 60; - minutes += (interval_start->hour - event_start->hour) * 24; - minutes += interval_start->minute - event_start->minute; - minutes += recur_data->recur->interval - 1; - minutes -= minutes % recur_data->recur->interval; - cal_obj_time_add_minutes (cotime, minutes); - } - - if (event_end && cal_obj_time_compare (cotime, event_end, - CALOBJ_MINUTE) > 0) - return TRUE; - if (interval_end && cal_obj_time_compare (cotime, interval_end, - CALOBJ_MINUTE) > 0) - return TRUE; - - return FALSE; -} - - -static gboolean -cal_obj_minutely_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end) -{ - cal_obj_time_add_minutes (cotime, recur_data->recur->interval); - - if (event_end && cal_obj_time_compare (cotime, event_end, - CALOBJ_MINUTE) > 0) - return TRUE; - if (interval_end && cal_obj_time_compare (cotime, interval_end, - CALOBJ_MINUTE) > 0) - return TRUE; - - return FALSE; -} - - -static gboolean -cal_obj_secondly_find_start_position (CalObjTime *event_start, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_start, - CalObjTime *interval_end, - CalObjTime *cotime) -{ - GDate event_start_date, interval_start_date; - guint32 event_start_julian, interval_start_julian, seconds; - - if (interval_end && cal_obj_time_compare (event_start, interval_end, - CALOBJ_SECOND) > 0) - return TRUE; - if (event_end && cal_obj_time_compare (event_end, interval_start, - CALOBJ_SECOND) < 0) - return TRUE; - - *cotime = *event_start; - - if (cal_obj_time_compare (event_start, interval_start, - CALOBJ_SECOND) < 0) { - /* Convert the event start and interval start to GDates, so we - can easily find the number of days between them. */ - g_date_clear (&event_start_date, 1); - g_date_set_dmy (&event_start_date, event_start->day, - event_start->month + 1, event_start->year); - g_date_clear (&interval_start_date, 1); - g_date_set_dmy (&interval_start_date, interval_start->day, - interval_start->month + 1, - interval_start->year); - - event_start_julian = g_date_get_julian (&event_start_date); - interval_start_julian = g_date_get_julian (&interval_start_date); - - seconds = (interval_start_julian - event_start_julian) - * 24 * 60 * 60; - seconds += (interval_start->hour - event_start->hour) - * 24 * 60; - seconds += (interval_start->minute - event_start->minute) * 60; - seconds += interval_start->second - event_start->second; - seconds += recur_data->recur->interval - 1; - seconds -= seconds % recur_data->recur->interval; - cal_obj_time_add_seconds (cotime, seconds); - } - - if (event_end && cal_obj_time_compare (cotime, event_end, - CALOBJ_SECOND) >= 0) - return TRUE; - if (interval_end && cal_obj_time_compare (cotime, interval_end, - CALOBJ_SECOND) >= 0) - return TRUE; - - return FALSE; -} - - -static gboolean -cal_obj_secondly_find_next_position (CalObjTime *cotime, - CalObjTime *event_end, - RecurData *recur_data, - CalObjTime *interval_end) -{ - cal_obj_time_add_seconds (cotime, recur_data->recur->interval); - - if (event_end && cal_obj_time_compare (cotime, event_end, - CALOBJ_SECOND) >= 0) - return TRUE; - if (interval_end && cal_obj_time_compare (cotime, interval_end, - CALOBJ_SECOND) >= 0) - return TRUE; - - return FALSE; -} - - - - - -/* If the BYMONTH rule is specified it expands each occurrence in occs, by - using each of the months in the bymonth list. */ -static GArray* -cal_obj_bymonth_expand (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - GList *elem; - gint len, i; - - /* If BYMONTH has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->bymonth || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - - elem = recur_data->recur->bymonth; - while (elem) { - /* NOTE: The day may now be invalid, e.g. 31st Feb. */ - occ->month = GPOINTER_TO_INT (elem->data); - g_array_append_vals (new_occs, occ, 1); - elem = elem->next; - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - -/* If the BYMONTH rule is specified it filters out all occurrences in occs - which do not match one of the months in the bymonth list. */ -static GArray* -cal_obj_bymonth_filter (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - gint len, i; - - /* If BYMONTH has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->bymonth || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - if (recur_data->months[occ->month]) - g_array_append_vals (new_occs, occ, 1); - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - - -static GArray* -cal_obj_byweekno_expand (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ, year_start_cotime, year_end_cotime, cotime; - GList *elem; - gint len, i, weekno; - - /* If BYWEEKNO has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byweekno || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - - /* Find the day that would correspond to week 1 (note that - week 1 is the first week starting from the specified week - start day that has 4 days in the new year). */ - year_start_cotime = *occ; - cal_obj_time_find_first_week (&year_start_cotime, - recur_data); - - /* Find the day that would correspond to week 1 of the next - year, which we use for -ve week numbers. */ - year_end_cotime = *occ; - year_end_cotime.year++; - cal_obj_time_find_first_week (&year_end_cotime, - recur_data); - - /* Now iterate over the week numbers in byweekno, generating a - new occurrence for each one. */ - elem = recur_data->recur->byweekno; - while (elem) { - weekno = GPOINTER_TO_INT (elem->data); - if (weekno > 0) { - cotime = year_start_cotime; - cal_obj_time_add_days (&cotime, - (weekno - 1) * 7); - } else { - cotime = year_end_cotime; - cal_obj_time_add_days (&cotime, weekno * 7); - } - - /* Skip occurrences if they fall outside the year. */ - if (cotime.year == occ->year) - g_array_append_val (new_occs, cotime); - elem = elem->next; - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - -#if 0 -/* This isn't used at present. */ -static GArray* -cal_obj_byweekno_filter (RecurData *recur_data, - GArray *occs) -{ - - return occs; -} -#endif - - -static GArray* -cal_obj_byyearday_expand (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ, year_start_cotime, year_end_cotime, cotime; - GList *elem; - gint len, i, dayno; - - /* If BYYEARDAY has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byyearday || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - - /* Find the day that would correspond to day 1. */ - year_start_cotime = *occ; - year_start_cotime.month = 0; - year_start_cotime.day = 1; - - /* Find the day that would correspond to day 1 of the next - year, which we use for -ve day numbers. */ - year_end_cotime = *occ; - year_end_cotime.year++; - year_end_cotime.month = 0; - year_end_cotime.day = 1; - - /* Now iterate over the day numbers in byyearday, generating a - new occurrence for each one. */ - elem = recur_data->recur->byyearday; - while (elem) { - dayno = GPOINTER_TO_INT (elem->data); - if (dayno > 0) { - cotime = year_start_cotime; - cal_obj_time_add_days (&cotime, dayno - 1); - } else { - cotime = year_end_cotime; - cal_obj_time_add_days (&cotime, dayno); - } - - /* Skip occurrences if they fall outside the year. */ - if (cotime.year == occ->year) - g_array_append_val (new_occs, cotime); - elem = elem->next; - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - -/* Note: occs must not contain invalid dates, e.g. 31st September. */ -static GArray* -cal_obj_byyearday_filter (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - gint yearday, len, i, days_in_year; - - /* If BYYEARDAY has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byyearday || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - yearday = cal_obj_time_day_of_year (occ); - if (recur_data->yeardays[yearday]) { - g_array_append_vals (new_occs, occ, 1); - } else { - days_in_year = g_date_is_leap_year (occ->year) - ? 366 : 365; - if (recur_data->neg_yeardays[days_in_year + 1 - - yearday]) - g_array_append_vals (new_occs, occ, 1); - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - - -static GArray* -cal_obj_bymonthday_expand (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ, month_start_cotime, month_end_cotime, cotime; - GList *elem; - gint len, i, dayno; - - /* If BYMONTHDAY has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->bymonthday || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - - /* Find the day that would correspond to day 1. */ - month_start_cotime = *occ; - month_start_cotime.day = 1; - - /* Find the day that would correspond to day 1 of the next - month, which we use for -ve day numbers. */ - month_end_cotime = *occ; - month_end_cotime.month++; - month_end_cotime.day = 1; - - /* Now iterate over the day numbers in bymonthday, generating a - new occurrence for each one. */ - elem = recur_data->recur->bymonthday; - while (elem) { - dayno = GPOINTER_TO_INT (elem->data); - if (dayno > 0) { - cotime = month_start_cotime; - cal_obj_time_add_days (&cotime, dayno - 1); - } else { - cotime = month_end_cotime; - cal_obj_time_add_days (&cotime, dayno); - } - - /* Skip occurrences if they fall outside the month. */ - if (cotime.month == occ->month) - g_array_append_val (new_occs, cotime); - elem = elem->next; - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - -static GArray* -cal_obj_bymonthday_filter (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - gint len, i, days_in_month; - - /* If BYMONTHDAY has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->bymonthday || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - if (recur_data->monthdays[occ->day]) { - g_array_append_vals (new_occs, occ, 1); - } else { - days_in_month = time_days_in_month (occ->year, - occ->month); - if (recur_data->neg_monthdays[days_in_month + 1 - - occ->day]) - g_array_append_vals (new_occs, occ, 1); - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - - -static GArray* -cal_obj_byday_expand_yearly (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - GList *elem; - gint len, i, weekday, week_num; - gint first_weekday, last_weekday, offset; - guint16 year; - - /* If BYDAY has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byday || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - - elem = recur_data->recur->byday; - while (elem) { - weekday = GPOINTER_TO_INT (elem->data); - elem = elem->next; - week_num = GPOINTER_TO_INT (elem->data); - elem = elem->next; - - year = occ->year; - if (week_num == 0) { - /* Expand to every Mon/Tue/etc. in the year. */ - occ->month = 0; - occ->day = 1; - first_weekday = cal_obj_time_weekday (occ); - offset = (weekday + 7 - first_weekday) % 7; - cal_obj_time_add_days (occ, offset); - - while (occ->year == year) { - g_array_append_vals (new_occs, occ, 1); - cal_obj_time_add_days (occ, 7); - } - - } else if (week_num > 0) { - /* Add the nth Mon/Tue/etc. in the year. */ - occ->month = 0; - occ->day = 1; - first_weekday = cal_obj_time_weekday (occ); - offset = (weekday + 7 - first_weekday) % 7; - offset += (week_num - 1) * 7; - cal_obj_time_add_days (occ, offset); - if (occ->year == year) - g_array_append_vals (new_occs, occ, 1); - - } else { - /* Add the -nth Mon/Tue/etc. in the year. */ - occ->month = 11; - occ->day = 31; - last_weekday = cal_obj_time_weekday (occ); - offset = (last_weekday + 7 - weekday) % 7; - offset += (week_num - 1) * 7; - cal_obj_time_add_days (occ, -offset); - if (occ->year == year) - g_array_append_vals (new_occs, occ, 1); - } - - /* Reset the year, as we may have gone past the end. */ - occ->year = year; - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - -static GArray* -cal_obj_byday_expand_monthly (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - GList *elem; - gint len, i, weekday, week_num; - gint first_weekday, last_weekday, offset; - guint16 year; - guint8 month; - - /* If BYDAY has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byday || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - - elem = recur_data->recur->byday; - while (elem) { - weekday = GPOINTER_TO_INT (elem->data); - elem = elem->next; - week_num = GPOINTER_TO_INT (elem->data); - elem = elem->next; - - year = occ->year; - month = occ->month; - if (week_num == 0) { - /* Expand to every Mon/Tue/etc. in the month.*/ - occ->day = 1; - first_weekday = cal_obj_time_weekday (occ); - offset = (weekday + 7 - first_weekday) % 7; - cal_obj_time_add_days (occ, offset); - - while (occ->year == year - && occ->month == month) { - g_array_append_vals (new_occs, occ, 1); - cal_obj_time_add_days (occ, 7); - } - - } else if (week_num > 0) { - /* Add the nth Mon/Tue/etc. in the month. */ - occ->day = 1; - first_weekday = cal_obj_time_weekday (occ); - offset = (weekday + 7 - first_weekday) % 7; - offset += (week_num - 1) * 7; - cal_obj_time_add_days (occ, offset); - if (occ->year == year && occ->month == month) - g_array_append_vals (new_occs, occ, 1); - - } else { - /* Add the -nth Mon/Tue/etc. in the month. */ - occ->day = time_days_in_month (occ->year, - occ->month); - last_weekday = cal_obj_time_weekday (occ); - - /* This calculates the number of days to step - backwards from the last day of the month - to the weekday we want. */ - offset = (last_weekday + 7 - weekday) % 7; - - /* This adds on the weeks. */ - offset += (-week_num - 1) * 7; - - cal_obj_time_add_days (occ, -offset); - if (occ->year == year && occ->month == month) - g_array_append_vals (new_occs, occ, 1); - } - - /* Reset the year & month, as we may have gone past - the end. */ - occ->year = year; - occ->month = month; - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - -/* Note: occs must not contain invalid dates, e.g. 31st September. */ -static GArray* -cal_obj_byday_expand_weekly (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - GList *elem; - gint len, i, weekday, week_num; - gint weekday_offset, new_weekday_offset; - - /* If BYDAY has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byday || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - - elem = recur_data->recur->byday; - while (elem) { - weekday = GPOINTER_TO_INT (elem->data); - elem = elem->next; - - /* FIXME: Currently we just ignore this, but maybe we - should skip all elements where week_num != 0. - The spec isn't clear about this. */ - week_num = GPOINTER_TO_INT (elem->data); - elem = elem->next; - - weekday_offset = cal_obj_time_weekday_offset (occ, recur_data->recur); - new_weekday_offset = (weekday + 7 - recur_data->recur->week_start_day) % 7; - cal_obj_time_add_days (occ, new_weekday_offset - weekday_offset); - g_array_append_vals (new_occs, occ, 1); - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - -/* Note: occs must not contain invalid dates, e.g. 31st September. */ -static GArray* -cal_obj_byday_filter (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - gint len, i, weekday; - - /* If BYDAY has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byday || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - weekday = cal_obj_time_weekday (occ); - - /* See if the weekday on its own is set. */ - if (recur_data->weekdays[weekday]) - g_array_append_vals (new_occs, occ, 1); - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - - -/* If the BYHOUR rule is specified it expands each occurrence in occs, by - using each of the hours in the byhour list. */ -static GArray* -cal_obj_byhour_expand (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - GList *elem; - gint len, i; - - /* If BYHOUR has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byhour || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - - elem = recur_data->recur->byhour; - while (elem) { - occ->hour = GPOINTER_TO_INT (elem->data); - g_array_append_vals (new_occs, occ, 1); - elem = elem->next; - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - -/* If the BYHOUR rule is specified it filters out all occurrences in occs - which do not match one of the hours in the byhour list. */ -static GArray* -cal_obj_byhour_filter (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - gint len, i; - - /* If BYHOUR has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byhour || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - if (recur_data->hours[occ->hour]) - g_array_append_vals (new_occs, occ, 1); - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - - -/* If the BYMINUTE rule is specified it expands each occurrence in occs, by - using each of the minutes in the byminute list. */ -static GArray* -cal_obj_byminute_expand (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - GList *elem; - gint len, i; - - /* If BYMINUTE has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byminute || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - - elem = recur_data->recur->byminute; - while (elem) { - occ->minute = GPOINTER_TO_INT (elem->data); - g_array_append_vals (new_occs, occ, 1); - elem = elem->next; - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - -/* If the BYMINUTE rule is specified it filters out all occurrences in occs - which do not match one of the minutes in the byminute list. */ -static GArray* -cal_obj_byminute_filter (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - gint len, i; - - /* If BYMINUTE has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->byminute || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - if (recur_data->minutes[occ->minute]) - g_array_append_vals (new_occs, occ, 1); - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - - -/* If the BYSECOND rule is specified it expands each occurrence in occs, by - using each of the seconds in the bysecond list. */ -static GArray* -cal_obj_bysecond_expand (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - GList *elem; - gint len, i; - - /* If BYSECOND has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->bysecond || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - - elem = recur_data->recur->bysecond; - while (elem) { - occ->second = GPOINTER_TO_INT (elem->data); - g_array_append_vals (new_occs, occ, 1); - elem = elem->next; - } - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - -/* If the BYSECOND rule is specified it filters out all occurrences in occs - which do not match one of the seconds in the bysecond list. */ -static GArray* -cal_obj_bysecond_filter (RecurData *recur_data, - GArray *occs) -{ - GArray *new_occs; - CalObjTime *occ; - gint len, i; - - /* If BYSECOND has not been specified, or the array is empty, just - return the array. */ - if (!recur_data->recur->bysecond || occs->len == 0) - return occs; - - new_occs = g_array_new (FALSE, FALSE, sizeof (CalObjTime)); - - len = occs->len; - for (i = 0; i < len; i++) { - occ = &g_array_index (occs, CalObjTime, i); - if (recur_data->seconds[occ->second]) - g_array_append_vals (new_occs, occ, 1); - } - - g_array_free (occs, TRUE); - - return new_occs; -} - - - - - -/* Adds a positive or negative number of months to the given CalObjTime, - updating the year appropriately so we end up with a valid month. - Note that the day may be invalid, e.g. 30th Feb. */ -static void -cal_obj_time_add_months (CalObjTime *cotime, - gint months) -{ - guint month, years; - - /* We use a guint to avoid overflow on the guint8. */ - month = cotime->month + months; - cotime->month = month % 12; - if (month > 0) { - cotime->year += month / 12; - } else { - years = month / 12; - if (cotime->month != 0) { - cotime->month += 12; - years -= 1; - } - cotime->year += years; - } -} - - -/* Adds a positive or negative number of days to the given CalObjTime, - updating the month and year appropriately so we end up with a valid day. */ -static void -cal_obj_time_add_days (CalObjTime *cotime, - gint days) -{ - gint day, days_in_month; - - /* We use a guint to avoid overflow on the guint8. */ - day = cotime->day; - day += days; - - if (days >= 0) { - for (;;) { - days_in_month = time_days_in_month (cotime->year, - cotime->month); - if (day <= days_in_month) - break; - - cotime->month++; - if (cotime->month >= 12) { - cotime->year++; - cotime->month = 0; - } - - day -= days_in_month; - } - - cotime->day = (guint8) day; - } else { - while (day <= 0) { - if (cotime->month == 0) { - cotime->year--; - cotime->month = 11; - } else { - cotime->month--; - } - - days_in_month = time_days_in_month (cotime->year, - cotime->month); - day += days_in_month; - } - - cotime->day = (guint8) day; - } -} - - -/* Adds a positive or negative number of hours to the given CalObjTime, - updating the day, month & year appropriately so we end up with a valid - time. */ -static void -cal_obj_time_add_hours (CalObjTime *cotime, - gint hours) -{ - gint hour, days; - - /* We use a gint to avoid overflow on the guint8. */ - hour = cotime->hour + hours; - cotime->hour = hour % 24; - if (hour >= 0) { - if (hour >= 24) - cal_obj_time_add_days (cotime, hour / 24); - } else { - days = hour / 24; - if (cotime->hour != 0) { - cotime->hour += 24; - days -= 1; - } - cal_obj_time_add_days (cotime, days); - } -} - - -/* Adds a positive or negative number of minutes to the given CalObjTime, - updating the rest of the CalObjTime appropriately. */ -static void -cal_obj_time_add_minutes (CalObjTime *cotime, - gint minutes) -{ - gint minute, hours; - - /* We use a gint to avoid overflow on the guint8. */ - minute = cotime->minute + minutes; - cotime->minute = minute % 60; - if (minute >= 0) { - if (minute >= 60) - cal_obj_time_add_hours (cotime, minute / 60); - } else { - hours = minute / 60; - if (cotime->minute != 0) { - cotime->minute += 60; - hours -= 1; - } - cal_obj_time_add_hours (cotime, hours); - } -} - - -/* Adds a positive or negative number of seconds to the given CalObjTime, - updating the rest of the CalObjTime appropriately. */ -static void -cal_obj_time_add_seconds (CalObjTime *cotime, - gint seconds) -{ - gint second, minutes; - - /* We use a gint to avoid overflow on the guint8. */ - second = cotime->second + seconds; - cotime->second = second % 60; - if (second >= 0) { - if (second >= 60) - cal_obj_time_add_minutes (cotime, second / 60); - } else { - minutes = second / 60; - if (cotime->second != 0) { - cotime->second += 60; - minutes -= 1; - } - cal_obj_time_add_minutes (cotime, minutes); - } -} - - -/* Compares 2 CalObjTimes. Returns -1 if the cotime1 is before cotime2, 0 if - they are the same, or 1 if cotime1 is after cotime2. The comparison type - specifies which parts of the times we are interested in, e.g. if CALOBJ_DAY - is used we only want to know if the days are different. */ -static gint -cal_obj_time_compare (CalObjTime *cotime1, - CalObjTime *cotime2, - CalObjTimeComparison type) -{ - if (cotime1->year < cotime2->year) - return -1; - if (cotime1->year > cotime2->year) - return 1; - - if (type == CALOBJ_YEAR) - return 0; - - if (cotime1->month < cotime2->month) - return -1; - if (cotime1->month > cotime2->month) - return 1; - - if (type == CALOBJ_MONTH) - return 0; - - if (cotime1->day < cotime2->day) - return -1; - if (cotime1->day > cotime2->day) - return 1; - - if (type == CALOBJ_DAY) - return 0; - - if (cotime1->hour < cotime2->hour) - return -1; - if (cotime1->hour > cotime2->hour) - return 1; - - if (type == CALOBJ_HOUR) - return 0; - - if (cotime1->minute < cotime2->minute) - return -1; - if (cotime1->minute > cotime2->minute) - return 1; - - if (type == CALOBJ_MINUTE) - return 0; - - if (cotime1->second < cotime2->second) - return -1; - if (cotime1->second > cotime2->second) - return 1; - - return 0; -} - - -/* This is the same as the above function, but without the comparison type. - It is used for qsort(). */ -static gint -cal_obj_time_compare_func (const void *arg1, - const void *arg2) -{ - CalObjTime *cotime1, *cotime2; - gint retval; - - cotime1 = (CalObjTime*) arg1; - cotime2 = (CalObjTime*) arg2; - - if (cotime1->year < cotime2->year) - retval = -1; - else if (cotime1->year > cotime2->year) - retval = 1; - - else if (cotime1->month < cotime2->month) - retval = -1; - else if (cotime1->month > cotime2->month) - retval = 1; - - else if (cotime1->day < cotime2->day) - retval = -1; - else if (cotime1->day > cotime2->day) - retval = 1; - - else if (cotime1->hour < cotime2->hour) - retval = -1; - else if (cotime1->hour > cotime2->hour) - retval = 1; - - else if (cotime1->minute < cotime2->minute) - retval = -1; - else if (cotime1->minute > cotime2->minute) - retval = 1; - - else if (cotime1->second < cotime2->second) - retval = -1; - else if (cotime1->second > cotime2->second) - retval = 1; - - else - retval = 0; - -#if 0 - g_print ("%s - ", cal_obj_time_to_string (cotime1)); - g_print ("%s : %i\n", cal_obj_time_to_string (cotime2), retval); -#endif - - return retval; -} - - -static gint -cal_obj_date_only_compare_func (const void *arg1, - const void *arg2) -{ - CalObjTime *cotime1, *cotime2; - - cotime1 = (CalObjTime*) arg1; - cotime2 = (CalObjTime*) arg2; - - if (cotime1->year < cotime2->year) - return -1; - if (cotime1->year > cotime2->year) - return 1; - - if (cotime1->month < cotime2->month) - return -1; - if (cotime1->month > cotime2->month) - return 1; - - if (cotime1->day < cotime2->day) - return -1; - if (cotime1->day > cotime2->day) - return 1; - - return 0; -} - - -/* Returns the weekday of the given CalObjTime, from 0 (Mon) - 6 (Sun). */ -static gint -cal_obj_time_weekday (CalObjTime *cotime) -{ - GDate date; - gint weekday; - - g_date_clear (&date, 1); - g_date_set_dmy (&date, cotime->day, cotime->month + 1, cotime->year); - - /* This results in a value of 0 (Monday) - 6 (Sunday). */ - weekday = g_date_get_weekday (&date) - 1; - - return weekday; -} - - -/* Returns the weekday of the given CalObjTime, from 0 - 6. The week start - day is Monday by default, but can be set in the recurrence rule. */ -static gint -cal_obj_time_weekday_offset (CalObjTime *cotime, - ECalRecurrence *recur) -{ - GDate date; - gint weekday, offset; - - g_date_clear (&date, 1); - g_date_set_dmy (&date, cotime->day, cotime->month + 1, cotime->year); - - /* This results in a value of 0 (Monday) - 6 (Sunday). */ - weekday = g_date_get_weekday (&date) - 1; - - /* This calculates the offset of our day from the start of the week. - We just add on a week (to avoid any possible negative values) and - then subtract the specified week start day, then convert it into a - value from 0-6. */ - offset = (weekday + 7 - recur->week_start_day) % 7; - - return offset; -} - - -/* Returns the day of the year of the given CalObjTime, from 1 - 366. */ -static gint -cal_obj_time_day_of_year (CalObjTime *cotime) -{ - GDate date; - - g_date_clear (&date, 1); - g_date_set_dmy (&date, cotime->day, cotime->month + 1, cotime->year); - - return g_date_get_day_of_year (&date); -} - - -/* Finds the first week in the given CalObjTime's year, using the same weekday - as the event start day (i.e. from the RecurData). - The first week of the year is the first week starting from the specified - week start day that has 4 days in the new year. It may be in the previous - year. */ -static void -cal_obj_time_find_first_week (CalObjTime *cotime, - RecurData *recur_data) -{ - GDate date; - gint weekday, week_start_day, first_full_week_start_offset, offset; - - /* Find out the weekday of the 1st of the year, 0 (Mon) - 6 (Sun). */ - g_date_clear (&date, 1); - g_date_set_dmy (&date, 1, 1, cotime->year); - weekday = g_date_get_weekday (&date) - 1; - - /* Calculate the first day of the year that starts a new week, i.e. the - first week_start_day after weekday, using 0 = 1st Jan. - e.g. if the 1st Jan is a Tuesday (1) and week_start_day is a - Monday (0), the result will be (0 + 7 - 1) % 7 = 6 (7th Jan). */ - week_start_day = recur_data->recur->week_start_day; - first_full_week_start_offset = (week_start_day + 7 - weekday) % 7; - - /* Now see if we have to move backwards 1 week, i.e. if the week - starts on or after Jan 5th (since the previous week has 4 days in - this year and so will be the first week of the year). */ - if (first_full_week_start_offset >= 4) - first_full_week_start_offset -= 7; - - /* Now add the days to get to the event's weekday. */ - offset = first_full_week_start_offset + recur_data->weekday_offset; - - /* Now move the cotime to the appropriate day. */ - cotime->month = 0; - cotime->day = 1; - cal_obj_time_add_days (cotime, offset); -} - - -static void -cal_object_time_from_time (CalObjTime *cotime, - time_t t, - icaltimezone *zone) -{ - struct icaltimetype tt; - - if (zone) - tt = icaltime_from_timet_with_zone (t, FALSE, zone); - else - tt = icaltime_from_timet (t, FALSE); - - cotime->year = tt.year; - cotime->month = tt.month - 1; - cotime->day = tt.day; - cotime->hour = tt.hour; - cotime->minute = tt.minute; - cotime->second = tt.second; - cotime->flags = FALSE; -} - - -/* Debugging function to convert a CalObjTime to a string. It uses a static - buffer so beware. */ -#ifdef CAL_OBJ_DEBUG -static char* -cal_obj_time_to_string (CalObjTime *cotime) -{ - static char buffer[20]; - char *weekdays[] = { "Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun", - " " }; - gint weekday; - - weekday = cal_obj_time_weekday (cotime); - - sprintf (buffer, "%s %02i/%02i/%04i %02i:%02i:%02i", - weekdays[weekday], - cotime->day, cotime->month + 1, cotime->year, - cotime->hour, cotime->minute, cotime->second); - return buffer; -} -#endif - - -/* This recalculates the end dates for recurrence & exception rules which use - the COUNT property. If refresh is TRUE it will recalculate all enddates - for rules which use COUNT. If refresh is FALSE, it will only calculate - the enddate if it hasn't already been set. It returns TRUE if the component - was changed, i.e. if the component should be saved at some point. - We store the enddate in the "X-EVOLUTION-ENDDATE" parameter of the RRULE - or EXRULE. */ -static gboolean -e_cal_recur_ensure_end_dates (ECalComponent *comp, - gboolean refresh, - ECalRecurResolveTimezoneFn tz_cb, - gpointer tz_cb_data) -{ - GSList *rrules, *exrules, *elem; - gboolean changed = FALSE; - - /* Do the RRULEs. */ - e_cal_component_get_rrule_property_list (comp, &rrules); - for (elem = rrules; elem; elem = elem->next) { - changed |= e_cal_recur_ensure_rule_end_date (comp, elem->data, - FALSE, refresh, - tz_cb, tz_cb_data); - } - - /* Do the EXRULEs. */ - e_cal_component_get_exrule_property_list (comp, &exrules); - for (elem = exrules; elem; elem = elem->next) { - changed |= e_cal_recur_ensure_rule_end_date (comp, elem->data, - TRUE, refresh, - tz_cb, tz_cb_data); - } - - return changed; -} - - -typedef struct _ECalRecurEnsureEndDateData ECalRecurEnsureEndDateData; -struct _ECalRecurEnsureEndDateData { - gint count; - gint instances; - time_t end_date; -}; - - -static gboolean -e_cal_recur_ensure_rule_end_date (ECalComponent *comp, - icalproperty *prop, - gboolean exception, - gboolean refresh, - ECalRecurResolveTimezoneFn tz_cb, - gpointer tz_cb_data) -{ - struct icalrecurrencetype rule; - ECalRecurEnsureEndDateData cb_data; - - if (exception) - rule = icalproperty_get_exrule (prop); - else - rule = icalproperty_get_rrule (prop); - - /* If the rule doesn't use COUNT just return. */ - if (rule.count == 0) - return FALSE; - - /* If refresh is FALSE, we check if the enddate is already set, and - if it is we just return. */ - if (!refresh) { - if (e_cal_recur_get_rule_end_date (prop, NULL) != -1) - return FALSE; - } - - /* Calculate the end date. Note that we initialize end_date to 0, so - if the RULE doesn't generate COUNT instances we save a time_t of 0. - Also note that we use the UTC timezone as the default timezone. - In get_end_date() if the DTSTART is a DATE or floating time, we will - convert the ENDDATE to the current timezone. */ - cb_data.count = rule.count; - cb_data.instances = 0; - cb_data.end_date = 0; - e_cal_recur_generate_instances_of_rule (comp, prop, -1, -1, - e_cal_recur_ensure_rule_end_date_cb, - &cb_data, tz_cb, tz_cb_data, - icaltimezone_get_utc_timezone ()); - - /* Store the end date in the "X-EVOLUTION-ENDDATE" parameter of the - rule. */ - e_cal_recur_set_rule_end_date (prop, cb_data.end_date); - - return TRUE; -} - - -static gboolean -e_cal_recur_ensure_rule_end_date_cb (ECalComponent *comp, - time_t instance_start, - time_t instance_end, - gpointer data) -{ - ECalRecurEnsureEndDateData *cb_data; - - cb_data = (ECalRecurEnsureEndDateData*) data; - - cb_data->instances++; - - if (cb_data->instances == cb_data->count) { - cb_data->end_date = instance_start; - return FALSE; - } - - return TRUE; -} - - -/* If default_timezone is set, the saved ENDDATE parameter is assumed to be - in that timezone. This is used when the DTSTART is a DATE or floating - value, since the RRULE end date will change depending on the timezone that - it is evaluated in. */ -static time_t -e_cal_recur_get_rule_end_date (icalproperty *prop, - icaltimezone *default_timezone) -{ - icalparameter *param; - const char *xname, *xvalue; - icalvalue *value; - struct icaltimetype icaltime; - icaltimezone *zone; - - param = icalproperty_get_first_parameter (prop, ICAL_X_PARAMETER); - while (param) { - xname = icalparameter_get_xname (param); - if (xname && !strcmp (xname, EVOLUTION_END_DATE_PARAMETER)) { - xvalue = icalparameter_get_x (param); - value = icalvalue_new_from_string (ICAL_DATETIME_VALUE, - xvalue); - if (value) { - icaltime = icalvalue_get_datetime (value); - icalvalue_free (value); - - zone = default_timezone ? default_timezone : - icaltimezone_get_utc_timezone (); - return icaltime_as_timet_with_zone (icaltime, - zone); - } - } - - param = icalproperty_get_next_parameter (prop, - ICAL_X_PARAMETER); - } - - return -1; -} - - -static void -e_cal_recur_set_rule_end_date (icalproperty *prop, - time_t end_date) -{ - icalparameter *param; - icalvalue *value; - icaltimezone *utc_zone; - struct icaltimetype icaltime; - const char *end_date_string, *xname; - - /* We save the value as a UTC DATE-TIME. */ - utc_zone = icaltimezone_get_utc_timezone (); - icaltime = icaltime_from_timet_with_zone (end_date, FALSE, utc_zone); - value = icalvalue_new_datetime (icaltime); - end_date_string = icalvalue_as_ical_string (value); - icalvalue_free (value); - - /* If we already have an X-EVOLUTION-ENDDATE parameter, set the value - to the new date-time. */ - param = icalproperty_get_first_parameter (prop, ICAL_X_PARAMETER); - while (param) { - xname = icalparameter_get_xname (param); - if (xname && !strcmp (xname, EVOLUTION_END_DATE_PARAMETER)) { - icalparameter_set_x (param, end_date_string); - return; - } - param = icalproperty_get_next_parameter (prop, ICAL_X_PARAMETER); - } - - /* Create a new X-EVOLUTION-ENDDATE and add it to the property. */ - param = icalparameter_new_x (end_date_string); - icalparameter_set_xname (param, EVOLUTION_END_DATE_PARAMETER); - icalproperty_add_parameter (prop, param); -} - -const char *e_cal_recur_nth[31] = { - N_("1st"), - N_("2nd"), - N_("3rd"), - N_("4th"), - N_("5th"), - N_("6th"), - N_("7th"), - N_("8th"), - N_("9th"), - N_("10th"), - N_("11th"), - N_("12th"), - N_("13th"), - N_("14th"), - N_("15th"), - N_("16th"), - N_("17th"), - N_("18th"), - N_("19th"), - N_("20th"), - N_("21st"), - N_("22nd"), - N_("23rd"), - N_("24th"), - N_("25th"), - N_("26th"), - N_("27th"), - N_("28th"), - N_("29th"), - N_("30th"), - N_("31st") -}; - diff --git a/calendar/libecal/e-cal-recur.h b/calendar/libecal/e-cal-recur.h deleted file mode 100644 index a6c4c9a92..000000000 --- a/calendar/libecal/e-cal-recur.h +++ /dev/null @@ -1,71 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - * Evolution calendar recurrence rule functions - * - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Damon Chaplin <damon@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_RECUR_H -#define E_CAL_RECUR_H - -#include <glib.h> -#include <libecal/e-cal-component.h> - -G_BEGIN_DECLS - -typedef gboolean (* ECalRecurInstanceFn) (ECalComponent *comp, - time_t instance_start, - time_t instance_end, - gpointer data); - -typedef icaltimezone* (* ECalRecurResolveTimezoneFn) (const char *tzid, - gpointer data); - -/* - * Calls the given callback function for each occurrence of the event that - * intersects the range between the given start and end times (the end time is - * not included). Note that the occurrences may start before the given start - * time. - * - * If the callback routine returns FALSE the occurrence generation stops. - * - * Both start and end can be -1, in which case we start at the events first - * instance and continue until it ends, or forever if it has no enddate. - * - * The tz_cb is used to resolve references to timezones. It is passed a TZID - * and should return the icaltimezone* corresponding to that TZID. We need to - * do this as we access timezones in different ways on the client & server. - * - * The default_timezone argument is used for DTSTART or DTEND properties that - * are DATE values or do not have a TZID (i.e. floating times). - */ -void e_cal_recur_generate_instances (ECalComponent *comp, - time_t start, - time_t end, - ECalRecurInstanceFn cb, - gpointer cb_data, - ECalRecurResolveTimezoneFn tz_cb, - gpointer tz_cb_data, - icaltimezone *default_timezone); - -/* Localized nth-day-of-month strings. (Use with _() ) */ -extern const char *e_cal_recur_nth[31]; - -G_END_DECLS - -#endif diff --git a/calendar/libecal/e-cal-time-util.c b/calendar/libecal/e-cal-time-util.c deleted file mode 100644 index 9d1acb7f3..000000000 --- a/calendar/libecal/e-cal-time-util.c +++ /dev/null @@ -1,576 +0,0 @@ -/* Miscellaneous time-related utilities - * - * Copyright (C) 2000, 2001 Ximian, Inc. - * - * Authors: Federico Mena <federico@ximian.com> - * Miguel de Icaza <miguel@ximian.com> - * Damon Chaplin <damon@ximian.com> - */ - -#include <string.h> -#include <ctype.h> -#include <glib.h> -#include "e-cal-time-util.h" - - - -#define REFORMATION_DAY 639787 /* First day of the reformation, counted from 1 Jan 1 */ -#define MISSING_DAYS 11 /* They corrected out 11 days */ -#define THURSDAY 4 /* First day of reformation */ -#define SATURDAY 6 /* Offset value; 1 Jan 1 was a Saturday */ - - -/* Number of days in a month, using 0 (Jan) to 11 (Dec). For leap years, - add 1 to February (month 1). */ -static const int days_in_month[12] = { - 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 -}; - - - -/************************************************************************** - * time_t manipulation functions. - * - * NOTE: these use the Unix timezone functions like mktime() and localtime() - * and so should not be used in Evolution. New Evolution code should use - * icaltimetype values rather than time_t values wherever possible. - **************************************************************************/ - -/* Adds a day onto the time, using local time. - Note that if clocks go forward due to daylight savings time, there are - some non-existent local times, so the hour may be changed to make it a - valid time. This also means that it may not be wise to keep calling - time_add_day() to step through a certain period - if the hour gets changed - to make it valid time, any further calls to time_add_day() will also return - this hour, which may not be what you want. */ -time_t -time_add_day (time_t time, int days) -{ - struct tm *tm; - - tm = localtime (&time); - tm->tm_mday += days; - tm->tm_isdst = -1; - - return mktime (tm); -} - -time_t -time_add_week (time_t time, int weeks) -{ - return time_add_day (time, weeks * 7); -} - -/* Returns the start of the day, according to the local time. */ -time_t -time_day_begin (time_t t) -{ - struct tm tm; - - tm = *localtime (&t); - tm.tm_hour = tm.tm_min = tm.tm_sec = 0; - tm.tm_isdst = -1; - - return mktime (&tm); -} - -/* Returns the end of the day, according to the local time. */ -time_t -time_day_end (time_t t) -{ - struct tm tm; - - tm = *localtime (&t); - tm.tm_hour = tm.tm_min = tm.tm_sec = 0; - tm.tm_mday++; - tm.tm_isdst = -1; - - return mktime (&tm); -} - - -/************************************************************************** - * time_t manipulation functions, using timezones in libical. - * - * NOTE: these are only here to make the transition to the timezone - * functions easier. New code should use icaltimetype values rather than - * time_t values wherever possible. - **************************************************************************/ - - -/* Adds or subtracts a number of days to/from the given time_t value, using - the given timezone. - NOTE: this function is only here to make the transition to the timezone - functions easier. New code should use icaltimetype values and - icaltime_adjust() to add or subtract days, hours, minutes & seconds. */ -time_t -time_add_day_with_zone (time_t time, int days, icaltimezone *zone) -{ - struct icaltimetype tt; - - /* Convert to an icaltimetype. */ - tt = icaltime_from_timet_with_zone (time, FALSE, zone); - - /* Add/subtract the number of days. */ - icaltime_adjust (&tt, days, 0, 0, 0); - - /* Convert back to a time_t. */ - return icaltime_as_timet_with_zone (tt, zone); -} - - -/* Adds or subtracts a number of weeks to/from the given time_t value, using - the given timezone. - NOTE: this function is only here to make the transition to the timezone - functions easier. New code should use icaltimetype values and - icaltime_adjust() to add or subtract days, hours, minutes & seconds. */ -time_t -time_add_week_with_zone (time_t time, int weeks, icaltimezone *zone) -{ - return time_add_day_with_zone (time, weeks * 7, zone); -} - - -/* Adds or subtracts a number of months to/from the given time_t value, using - the given timezone. - - If the day would be off the end of the month (e.g. adding 1 month to - 30th January, would lead to an invalid day, 30th February), it moves it - down to the last day in the month, e.g. 28th Feb (or 29th in a leap year.) - - NOTE: this function is only here to make the transition to the timezone - functions easier. New code should use icaltimetype values and - icaltime_adjust() to add or subtract days, hours, minutes & seconds. */ -time_t -time_add_month_with_zone (time_t time, int months, icaltimezone *zone) -{ - struct icaltimetype tt; - int day, days_in_month; - - /* Convert to an icaltimetype. */ - tt = icaltime_from_timet_with_zone (time, FALSE, zone); - - /* Add on the number of months. */ - tt.month += months; - - /* Save the day, and set it to 1, so we don't overflow into the next - month. */ - day = tt.day; - tt.day = 1; - - /* Normalize it, fixing any month overflow. */ - tt = icaltime_normalize (tt); - - /* If we go past the end of a month, set it to the last day. */ - days_in_month = time_days_in_month (tt.year, tt.month - 1); - if (day > days_in_month) - day = days_in_month; - - tt.day = day; - - /* Convert back to a time_t. */ - return icaltime_as_timet_with_zone (tt, zone); -} - - -/* Returns the start of the year containing the given time_t, using the given - timezone. - NOTE: this function is only here to make the transition to the timezone - functions easier. New code should use icaltimetype values and - icaltime_adjust() to add or subtract days, hours, minutes & seconds. */ -time_t -time_year_begin_with_zone (time_t time, icaltimezone *zone) -{ - struct icaltimetype tt; - - /* Convert to an icaltimetype. */ - tt = icaltime_from_timet_with_zone (time, FALSE, zone); - - /* Set it to the start of the year. */ - tt.month = 1; - tt.day = 1; - tt.hour = 0; - tt.minute = 0; - tt.second = 0; - - /* Convert back to a time_t. */ - return icaltime_as_timet_with_zone (tt, zone); -} - - -/* Returns the start of the month containing the given time_t, using the given - timezone. - NOTE: this function is only here to make the transition to the timezone - functions easier. New code should use icaltimetype values and - icaltime_adjust() to add or subtract days, hours, minutes & seconds. */ -time_t -time_month_begin_with_zone (time_t time, icaltimezone *zone) -{ - struct icaltimetype tt; - - /* Convert to an icaltimetype. */ - tt = icaltime_from_timet_with_zone (time, FALSE, zone); - - /* Set it to the start of the month. */ - tt.day = 1; - tt.hour = 0; - tt.minute = 0; - tt.second = 0; - - /* Convert back to a time_t. */ - return icaltime_as_timet_with_zone (tt, zone); -} - - -/* Returns the start of the week containing the given time_t, using the given - timezone. week_start_day should use the same values as mktime(), - i.e. 0 (Sun) to 6 (Sat). - NOTE: this function is only here to make the transition to the timezone - functions easier. New code should use icaltimetype values and - icaltime_adjust() to add or subtract days, hours, minutes & seconds. */ -time_t -time_week_begin_with_zone (time_t time, int week_start_day, icaltimezone *zone) -{ - struct icaltimetype tt; - int weekday, offset; - - /* Convert to an icaltimetype. */ - tt = icaltime_from_timet_with_zone (time, FALSE, zone); - - /* Get the weekday. */ - weekday = time_day_of_week (tt.day, tt.month - 1, tt.year); - - /* Calculate the current offset from the week start day. */ - offset = (weekday + 7 - week_start_day) % 7; - - /* Set it to the start of the month. */ - tt.day -= offset; - tt.hour = 0; - tt.minute = 0; - tt.second = 0; - - /* Normalize it, to fix any overflow. */ - tt = icaltime_normalize (tt); - - /* Convert back to a time_t. */ - return icaltime_as_timet_with_zone (tt, zone); -} - - -/* Returns the start of the day containing the given time_t, using the given - timezone. - NOTE: this function is only here to make the transition to the timezone - functions easier. New code should use icaltimetype values and - icaltime_adjust() to add or subtract days, hours, minutes & seconds. */ -time_t -time_day_begin_with_zone (time_t time, icaltimezone *zone) -{ - struct icaltimetype tt; - - /* Convert to an icaltimetype. */ - tt = icaltime_from_timet_with_zone (time, FALSE, zone); - - /* Set it to the start of the day. */ - tt.hour = 0; - tt.minute = 0; - tt.second = 0; - - /* Convert back to a time_t. */ - return icaltime_as_timet_with_zone (tt, zone); -} - - -/* Returns the end of the day containing the given time_t, using the given - timezone. (The end of the day is the start of the next day.) - NOTE: this function is only here to make the transition to the timezone - functions easier. New code should use icaltimetype values and - icaltime_adjust() to add or subtract days, hours, minutes & seconds. */ -time_t -time_day_end_with_zone (time_t time, icaltimezone *zone) -{ - struct icaltimetype tt; - - /* Convert to an icaltimetype. */ - tt = icaltime_from_timet_with_zone (time, FALSE, zone); - - /* Set it to the start of the next day. */ - tt.day++; - tt.hour = 0; - tt.minute = 0; - tt.second = 0; - - /* Normalize it, to fix any overflow. */ - tt = icaltime_normalize (tt); - - /* Convert back to a time_t. */ - return icaltime_as_timet_with_zone (tt, zone); -} - -/** - * time_to_gdate_with_zone: - * @date: Destination #GDate value. - * @time: A time value. - * @zone: Desired timezone for destination @date, or NULL if the UTC timezone - * is desired. - * - * Converts a time_t value to a #GDate structure using the specified timezone. - * This is analogous to g_date_set_time() but takes the timezone into account. - **/ -void -time_to_gdate_with_zone (GDate *date, time_t time, icaltimezone *zone) -{ - struct icaltimetype tt; - - g_return_if_fail (date != NULL); - g_return_if_fail (time != -1); - - tt = icaltime_from_timet_with_zone (time, FALSE, - zone ? zone : icaltimezone_get_utc_timezone ()); - - g_date_set_dmy (date, tt.day, tt.month, tt.year); -} - - -/************************************************************************** - * General time functions. - **************************************************************************/ - - -/* Returns the number of days in the month. Year is the normal year, e.g. 2001. - Month is 0 (Jan) to 11 (Dec). */ -int -time_days_in_month (int year, int month) -{ - int days; - - g_return_val_if_fail (year >= 1900, 0); - g_return_val_if_fail ((month >= 0) && (month < 12), 0); - - days = days_in_month[month]; - if (month == 1 && time_is_leap_year (year)) - days++; - - return days; -} - - -/* Returns the 1-based day number within the year of the specified date. - Year is the normal year, e.g. 2001. Month is 0 to 11. */ -int -time_day_of_year (int day, int month, int year) -{ - int i; - - for (i = 0; i < month; i++) { - day += days_in_month[i]; - - if (i == 1 && time_is_leap_year (year)) - day++; - } - - return day; -} - - -/* Returns the day of the week for the specified date, 0 (Sun) to 6 (Sat). - For the days that were removed on the Gregorian reformation, it returns - Thursday. Year is the normal year, e.g. 2001. Month is 0 to 11. */ -int -time_day_of_week (int day, int month, int year) -{ - int n; - - n = (year - 1) * 365 + time_leap_years_up_to (year - 1) - + time_day_of_year (day, month, year); - - if (n < REFORMATION_DAY) - return (n - 1 + SATURDAY) % 7; - - if (n >= (REFORMATION_DAY + MISSING_DAYS)) - return (n - 1 + SATURDAY - MISSING_DAYS) % 7; - - return THURSDAY; -} - - -/* Returns whether the specified year is a leap year. Year is the normal year, - e.g. 2001. */ -gboolean -time_is_leap_year (int year) -{ - if (year <= 1752) - return !(year % 4); - else - return (!(year % 4) && (year % 100)) || !(year % 400); -} - - -/* Returns the number of leap years since year 1 up to (but not including) the - specified year. Year is the normal year, e.g. 2001. */ -int -time_leap_years_up_to (int year) -{ - /* There is normally a leap year every 4 years, except at the turn of - centuries since 1700. But there is a leap year on centuries since 1700 - which are divisible by 400. */ - return (year / 4 - - ((year > 1700) ? (year / 100 - 17) : 0) - + ((year > 1600) ? ((year - 1600) / 400) : 0)); -} - - -/** - * isodate_from_time_t: - * @t: A time value. - * - * Creates an ISO 8601 UTC representation from a time value. - * - * Return value: String with the ISO 8601 representation of the UTC time. - **/ -char * -isodate_from_time_t (time_t t) -{ - gchar *ret; - - ret = g_malloc (17); /* 4+2+2+1+2+2+2+1 + 1 */ - strftime (ret, 17, "%Y%m%dT%H%M%SZ", gmtime (&t)); - - return ret; -} - -/** - * time_from_isodate: - * @str: Date/time value in ISO 8601 format. - * - * Converts an ISO 8601 UTC time string into a time_t value. - * - * Return value: Time_t corresponding to the specified ISO string. - * Note that we only allow UTC times at present. - **/ -time_t -time_from_isodate (const char *str) -{ - struct icaltimetype tt = icaltime_null_time (); - icaltimezone *utc_zone; - int len, i; - - g_return_val_if_fail (str != NULL, -1); - - /* yyyymmdd[Thhmmss[Z]] */ - - len = strlen (str); - - if (!(len == 8 || len == 15 || len == 16)) - return -1; - - for (i = 0; i < len; i++) - if (!((i != 8 && i != 15 && isdigit (str[i])) - || (i == 8 && str[i] == 'T') - || (i == 15 && str[i] == 'Z'))) - return -1; - -#define digit_at(x,y) (x[y] - '0') - - tt.year = digit_at (str, 0) * 1000 - + digit_at (str, 1) * 100 - + digit_at (str, 2) * 10 - + digit_at (str, 3); - - tt.month = digit_at (str, 4) * 10 - + digit_at (str, 5); - - tt.day = digit_at (str, 6) * 10 - + digit_at (str, 7); - - if (len > 8) { - tt.hour = digit_at (str, 9) * 10 - + digit_at (str, 10); - tt.minute = digit_at (str, 11) * 10 - + digit_at (str, 12); - tt.second = digit_at (str, 13) * 10 - + digit_at (str, 14); - } - - utc_zone = icaltimezone_get_utc_timezone (); - - return icaltime_as_timet_with_zone (tt, utc_zone); -} - -struct tm -icaltimetype_to_tm (struct icaltimetype *itt) -{ - struct tm tm; - - memset (&tm, 0, sizeof (struct tm)); - - if (!itt->is_date) { - tm.tm_sec = itt->second; - tm.tm_min = itt->minute; - tm.tm_hour = itt->hour; - } - - tm.tm_mday = itt->day; - tm.tm_mon = itt->month - 1; - tm.tm_year = itt->year - 1900; - tm.tm_wday = time_day_of_week (itt->day, itt->month - 1, itt->year); - tm.tm_isdst = -1; - - return tm; -} - -/** - * icaltimetype_to_tm_with_zone: - * @itt: A time value. - * @from_zone: Source timezone. - * @to_zone: Destination timezone. - * - * Converts a time value from one timezone to another, and returns a struct tm - * representation of the time. - * - * Return value: The converted time as a struct tm. All fields will be - * set properly except for tm.tm_yday. - **/ -struct tm -icaltimetype_to_tm_with_zone (struct icaltimetype *itt, - icaltimezone *from_zone, - icaltimezone *to_zone) -{ - struct tm tm; - struct icaltimetype itt_copy; - - memset (&tm, 0, sizeof (tm)); - tm.tm_isdst = -1; - - g_return_val_if_fail (itt != NULL, tm); - - itt_copy = *itt; - - icaltimezone_convert_time (&itt_copy, from_zone, to_zone); - tm = icaltimetype_to_tm (&itt_copy); - - return tm; -} - -struct icaltimetype -tm_to_icaltimetype (struct tm *tm, gboolean is_date) -{ - struct icaltimetype itt; - - memset (&itt, 0, sizeof (struct icaltimetype)); - - if (!is_date) { - itt.second = tm->tm_sec; - itt.minute = tm->tm_min; - itt.hour = tm->tm_hour; - } - - itt.day = tm->tm_mday; - itt.month = tm->tm_mon + 1; - itt.year = tm->tm_year+ 1900; - - itt.is_utc = 0; - itt.is_date = is_date; - - return itt; -} - diff --git a/calendar/libecal/e-cal-time-util.h b/calendar/libecal/e-cal-time-util.h deleted file mode 100644 index 519e3a99a..000000000 --- a/calendar/libecal/e-cal-time-util.h +++ /dev/null @@ -1,125 +0,0 @@ -/* Miscellaneous time-related utilities - * - * Copyright (C) 1998 The Free Software Foundation - * Copyright (C) 2000 Ximian, Inc. - * - * Authors: Federico Mena <federico@ximian.com> - * Miguel de Icaza <miguel@ximian.com> - * Damon Chaplin <damon@ximian.com> - */ - -#ifndef TIMEUTIL_H -#define TIMEUTIL_H - - -#include <time.h> -#include <libical/ical.h> -#include <glib.h> - -G_BEGIN_DECLS - -/************************************************************************** - * General time functions. - **************************************************************************/ - -/* Returns the number of days in the month. Year is the normal year, e.g. 2001. - Month is 0 (Jan) to 11 (Dec). */ -int time_days_in_month (int year, int month); - -/* Returns the 1-based day number within the year of the specified date. - Year is the normal year, e.g. 2001. Month is 0 to 11. */ -int time_day_of_year (int day, int month, int year); - -/* Returns the day of the week for the specified date, 0 (Sun) to 6 (Sat). - For the days that were removed on the Gregorian reformation, it returns - Thursday. Year is the normal year, e.g. 2001. Month is 0 to 11. */ -int time_day_of_week (int day, int month, int year); - -/* Returns whether the specified year is a leap year. Year is the normal year, - e.g. 2001. */ -gboolean time_is_leap_year (int year); - -/* Returns the number of leap years since year 1 up to (but not including) the - specified year. Year is the normal year, e.g. 2001. */ -int time_leap_years_up_to (int year); - -/* Convert to or from an ISO 8601 representation of a time, in UTC, - e.g. "20010708T183000Z". */ -char *isodate_from_time_t (time_t t); -time_t time_from_isodate (const char *str); - - -/************************************************************************** - * time_t manipulation functions. - * - * NOTE: these use the Unix timezone functions like mktime() and localtime() - * and so should not be used in Evolution. New Evolution code should use - * icaltimetype values rather than time_t values wherever possible. - **************************************************************************/ - -/* Add or subtract a number of days, weeks or months. */ -time_t time_add_day (time_t time, int days); -time_t time_add_week (time_t time, int weeks); - -/* Returns the beginning or end of the day. */ -time_t time_day_begin (time_t t); -time_t time_day_end (time_t t); - - -/************************************************************************** - * time_t manipulation functions, using timezones in libical. - * - * NOTE: these are only here to make the transition to the timezone - * functions easier. New code should use icaltimetype values rather than - * time_t values wherever possible. - **************************************************************************/ - -/* Adds or subtracts a number of days to/from the given time_t value, using - the given timezone. */ -time_t time_add_day_with_zone (time_t time, int days, icaltimezone *zone); - -/* Adds or subtracts a number of weeks to/from the given time_t value, using - the given timezone. */ -time_t time_add_week_with_zone (time_t time, int weeks, icaltimezone *zone); - -/* Adds or subtracts a number of months to/from the given time_t value, using - the given timezone. */ -time_t time_add_month_with_zone (time_t time, int months, icaltimezone *zone); - -/* Returns the start of the year containing the given time_t, using the given - timezone. */ -time_t time_year_begin_with_zone (time_t time, icaltimezone *zone); - -/* Returns the start of the month containing the given time_t, using the given - timezone. */ -time_t time_month_begin_with_zone (time_t time, icaltimezone *zone); - -/* Returns the start of the week containing the given time_t, using the given - timezone. week_start_day should use the same values as mktime(), - i.e. 0 (Sun) to 6 (Sat). */ -time_t time_week_begin_with_zone (time_t time, int week_start_day, - icaltimezone *zone); - -/* Returns the start of the day containing the given time_t, using the given - timezone. */ -time_t time_day_begin_with_zone (time_t time, icaltimezone *zone); - -/* Returns the end of the day containing the given time_t, using the given - timezone. (The end of the day is the start of the next day.) */ -time_t time_day_end_with_zone (time_t time, icaltimezone *zone); - -void time_to_gdate_with_zone (GDate *date, time_t time, icaltimezone *zone); - -/************************************************************************** - * struct tm manipulation - **************************************************************************/ - -struct tm icaltimetype_to_tm (struct icaltimetype *itt); -struct tm icaltimetype_to_tm_with_zone (struct icaltimetype *itt, - icaltimezone *from_zone, - icaltimezone *to_zone); -struct icaltimetype tm_to_icaltimetype (struct tm *tm, gboolean is_date); - -G_END_DECLS - -#endif diff --git a/calendar/libecal/e-cal-types.h b/calendar/libecal/e-cal-types.h deleted file mode 100644 index 00a04b279..000000000 --- a/calendar/libecal/e-cal-types.h +++ /dev/null @@ -1,73 +0,0 @@ -/* Evolution calendar utilities and types - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Authors: Federico Mena-Quintero <federico@ximian.com> - * JP Rosevear <jpr@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_TYPES_H -#define E_CAL_TYPES_H - -#include <libecal/e-cal-component.h> - -G_BEGIN_DECLS - - - -#define E_CALENDAR_ERROR e_calendar_error_quark() - -GQuark e_calendar_error_quark (void) G_GNUC_CONST; - -typedef enum { - E_CAL_CHANGE_ADDED = 1 << 0, - E_CAL_CHANGE_MODIFIED = 1 << 1, - E_CAL_CHANGE_DELETED = 1 << 2 -} ECalChangeType; - -typedef struct -{ - ECalComponent *comp; - ECalChangeType type; -} ECalChange; - -typedef enum { - E_CALENDAR_STATUS_OK, - E_CALENDAR_STATUS_INVALID_ARG, - E_CALENDAR_STATUS_BUSY, - E_CALENDAR_STATUS_REPOSITORY_OFFLINE, - E_CALENDAR_STATUS_NO_SUCH_CALENDAR, - E_CALENDAR_STATUS_OBJECT_NOT_FOUND, - E_CALENDAR_STATUS_INVALID_OBJECT, - E_CALENDAR_STATUS_URI_NOT_LOADED, - E_CALENDAR_STATUS_URI_ALREADY_LOADED, - E_CALENDAR_STATUS_PERMISSION_DENIED, - E_CALENDAR_STATUS_OBJECT_ID_ALREADY_EXISTS, - E_CALENDAR_STATUS_PROTOCOL_NOT_SUPPORTED, - E_CALENDAR_STATUS_CANCELLED, - E_CALENDAR_STATUS_COULD_NOT_CANCEL, - E_CALENDAR_STATUS_AUTHENTICATION_FAILED, - E_CALENDAR_STATUS_AUTHENTICATION_REQUIRED, - E_CALENDAR_STATUS_UNABLE_TO_BOOK, - E_CALENDAR_STATUS_CORBA_EXCEPTION, - E_CALENDAR_STATUS_OTHER_ERROR -} ECalendarStatus; - -G_END_DECLS - -#endif - diff --git a/calendar/libecal/e-cal-util.c b/calendar/libecal/e-cal-util.c deleted file mode 100644 index 59813a285..000000000 --- a/calendar/libecal/e-cal-util.c +++ /dev/null @@ -1,944 +0,0 @@ -/* Evolution calendar utilities and types - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#include <config.h> -#include <stdlib.h> -#include <string.h> -#include <glib.h> -#include <glib/gstrfuncs.h> -#include <libgnome/gnome-i18n.h> -#include <libgnome/gnome-util.h> -#include "e-cal-util.h" - - - -/** - * cal_obj_instance_list_free: - * @list: List of #CalObjInstance structures. - * - * Frees a list of #CalObjInstance structures. - **/ -void -cal_obj_instance_list_free (GList *list) -{ - CalObjInstance *i; - GList *l; - - for (l = list; l; l = l->next) { - i = l->data; - - g_assert (i != NULL); - g_assert (i->uid != NULL); - - g_free (i->uid); - g_free (i); - } - - g_list_free (list); -} - -/** - * cal_obj_uid_list_free: - * @list: List of strings with unique identifiers. - * - * Frees a list of unique identifiers for calendar objects. - **/ -void -cal_obj_uid_list_free (GList *list) -{ - GList *l; - - for (l = list; l; l = l->next) { - char *uid; - - uid = l->data; - - g_assert (uid != NULL); - g_free (uid); - } - - g_list_free (list); -} - -icalcomponent * -e_cal_util_new_top_level (void) -{ - icalcomponent *icalcomp; - icalproperty *prop; - - icalcomp = icalcomponent_new (ICAL_VCALENDAR_COMPONENT); - - /* RFC 2445, section 4.7.1 */ - prop = icalproperty_new_calscale ("GREGORIAN"); - icalcomponent_add_property (icalcomp, prop); - - /* RFC 2445, section 4.7.3 */ - prop = icalproperty_new_prodid ("-//Ximian//NONSGML Evolution Calendar//EN"); - icalcomponent_add_property (icalcomp, prop); - - /* RFC 2445, section 4.7.4. This is the iCalendar spec version, *NOT* - * the product version! Do not change this! - */ - prop = icalproperty_new_version ("2.0"); - icalcomponent_add_property (icalcomp, prop); - - return icalcomp; -} - -icalcomponent * -e_cal_util_new_component (icalcomponent_kind kind) -{ - icalcomponent *comp; - struct icaltimetype dtstamp; - - comp = icalcomponent_new (kind); - icalcomponent_set_uid (comp, e_cal_component_gen_uid ()); - dtstamp = icaltime_current_time_with_zone (icaltimezone_get_utc_timezone ()); - icalcomponent_set_dtstamp (comp, dtstamp); - - return comp; -} - -static char * -get_line_fn (char *buf, size_t size, void *file) -{ - return fgets (buf, size, file); -} - -icalcomponent * -e_cal_util_parse_ics_file (const char *filename) -{ - icalparser *parser; - icalcomponent *icalcomp; - FILE *file; - - file = fopen (filename, "r"); - if (!file) - return NULL; - - parser = icalparser_new (); - icalparser_set_gen_data (parser, file); - - icalcomp = icalparser_parse (parser, get_line_fn); - icalparser_free (parser); - fclose (file); - - return icalcomp; -} - -/* Computes the range of time in which recurrences should be generated for a - * component in order to compute alarm trigger times. - */ -static void -compute_alarm_range (ECalComponent *comp, GList *alarm_uids, time_t start, time_t end, - time_t *alarm_start, time_t *alarm_end) -{ - GList *l; - time_t repeat_time; - - *alarm_start = start; - *alarm_end = end; - - repeat_time = 0; - - for (l = alarm_uids; l; l = l->next) { - const char *auid; - ECalComponentAlarm *alarm; - ECalComponentAlarmTrigger trigger; - struct icaldurationtype *dur; - time_t dur_time; - ECalComponentAlarmRepeat repeat; - - auid = l->data; - alarm = e_cal_component_get_alarm (comp, auid); - g_assert (alarm != NULL); - - e_cal_component_alarm_get_trigger (alarm, &trigger); - e_cal_component_alarm_get_repeat (alarm, &repeat); - e_cal_component_alarm_free (alarm); - - switch (trigger.type) { - case E_CAL_COMPONENT_ALARM_TRIGGER_NONE: - case E_CAL_COMPONENT_ALARM_TRIGGER_ABSOLUTE: - break; - - case E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_START: - case E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_END: - dur = &trigger.u.rel_duration; - dur_time = icaldurationtype_as_int (*dur); - - if (repeat.repetitions != 0) { - int rdur; - - rdur = repeat.repetitions * icaldurationtype_as_int (repeat.duration); - repeat_time = MAX (repeat_time, rdur); - } - - if (dur->is_neg) - /* If the duration is negative then dur_time - * will be negative as well; that is why we - * subtract to expand the range. - */ - *alarm_end = MAX (*alarm_end, end - dur_time); - else - *alarm_start = MIN (*alarm_start, start - dur_time); - - break; - - default: - g_assert_not_reached (); - } - } - - *alarm_start -= repeat_time; - - g_assert (*alarm_start <= *alarm_end); -} - -/* Closure data to generate alarm occurrences */ -struct alarm_occurrence_data { - /* These are the info we have */ - GList *alarm_uids; - time_t start; - time_t end; - ECalComponentAlarmAction *omit; - - /* This is what we compute */ - GSList *triggers; - int n_triggers; -}; - -static void -add_trigger (struct alarm_occurrence_data *aod, const char *auid, time_t trigger, - time_t occur_start, time_t occur_end) -{ - ECalComponentAlarmInstance *instance; - - instance = g_new (ECalComponentAlarmInstance, 1); - instance->auid = auid; - instance->trigger = trigger; - instance->occur_start = occur_start; - instance->occur_end = occur_end; - - aod->triggers = g_slist_prepend (aod->triggers, instance); - aod->n_triggers++; -} - -/* Callback used from cal_recur_generate_instances(); generates triggers for all - * of a component's RELATIVE alarms. - */ -static gboolean -add_alarm_occurrences_cb (ECalComponent *comp, time_t start, time_t end, gpointer data) -{ - struct alarm_occurrence_data *aod; - GList *l; - - aod = data; - - for (l = aod->alarm_uids; l; l = l->next) { - const char *auid; - ECalComponentAlarm *alarm; - ECalComponentAlarmAction action; - ECalComponentAlarmTrigger trigger; - ECalComponentAlarmRepeat repeat; - struct icaldurationtype *dur; - time_t dur_time; - time_t occur_time, trigger_time; - int i; - - auid = l->data; - alarm = e_cal_component_get_alarm (comp, auid); - g_assert (alarm != NULL); - - e_cal_component_alarm_get_action (alarm, &action); - e_cal_component_alarm_get_trigger (alarm, &trigger); - e_cal_component_alarm_get_repeat (alarm, &repeat); - e_cal_component_alarm_free (alarm); - - for (i = 0; aod->omit[i] != -1; i++) { - if (aod->omit[i] == action) - break; - } - if (aod->omit[i] != -1) - continue; - - if (trigger.type != E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_START - && trigger.type != E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_END) - continue; - - dur = &trigger.u.rel_duration; - dur_time = icaldurationtype_as_int (*dur); - - if (trigger.type == E_CAL_COMPONENT_ALARM_TRIGGER_RELATIVE_START) - occur_time = start; - else - occur_time = end; - - /* If dur->is_neg is true then dur_time will already be - * negative. So we do not need to test for dur->is_neg here; we - * can simply add the dur_time value to the occur_time and get - * the correct result. - */ - - trigger_time = occur_time + dur_time; - - /* Add repeating alarms */ - - if (repeat.repetitions != 0) { - int i; - time_t repeat_time; - - repeat_time = icaldurationtype_as_int (repeat.duration); - - for (i = 0; i < repeat.repetitions; i++) { - time_t t; - - t = trigger_time + (i + 1) * repeat_time; - - if (t >= aod->start && t < aod->end) - add_trigger (aod, auid, t, start, end); - } - } - - /* Add the trigger itself */ - - if (trigger_time >= aod->start && trigger_time < aod->end) - add_trigger (aod, auid, trigger_time, start, end); - } - - return TRUE; -} - -/* Generates the absolute triggers for a component */ -static void -generate_absolute_triggers (ECalComponent *comp, struct alarm_occurrence_data *aod, - ECalRecurResolveTimezoneFn resolve_tzid, - gpointer user_data, - icaltimezone *default_timezone) -{ - GList *l; - ECalComponentDateTime dt_start, dt_end; - - e_cal_component_get_dtstart (comp, &dt_start); - e_cal_component_get_dtend (comp, &dt_end); - - for (l = aod->alarm_uids; l; l = l->next) { - const char *auid; - ECalComponentAlarm *alarm; - ECalComponentAlarmAction action; - ECalComponentAlarmRepeat repeat; - ECalComponentAlarmTrigger trigger; - time_t abs_time; - time_t occur_start, occur_end; - icaltimezone *zone; - int i; - - auid = l->data; - alarm = e_cal_component_get_alarm (comp, auid); - g_assert (alarm != NULL); - - e_cal_component_alarm_get_action (alarm, &action); - e_cal_component_alarm_get_trigger (alarm, &trigger); - e_cal_component_alarm_get_repeat (alarm, &repeat); - e_cal_component_alarm_free (alarm); - - for (i = 0; aod->omit[i] != -1; i++) { - if (aod->omit[i] == action) - break; - } - if (aod->omit[i] != -1) - continue; - - if (trigger.type != E_CAL_COMPONENT_ALARM_TRIGGER_ABSOLUTE) - continue; - - /* Absolute triggers are always in UTC; see RFC 2445 section 4.8.6.3 */ - zone = icaltimezone_get_utc_timezone (); - - abs_time = icaltime_as_timet_with_zone (trigger.u.abs_time, zone); - - /* No particular occurrence, so just use the times from the component */ - - if (dt_start.value) { - if (dt_start.tzid && !dt_start.value->is_date) - zone = (* resolve_tzid) (dt_start.tzid, user_data); - else - zone = default_timezone; - - occur_start = icaltime_as_timet_with_zone (*dt_start.value, zone); - } else - occur_start = -1; - - if (dt_end.value) { - if (dt_end.tzid && !dt_end.value->is_date) - zone = (* resolve_tzid) (dt_end.tzid, user_data); - else - zone = default_timezone; - - occur_end = icaltime_as_timet_with_zone (*dt_end.value, zone); - } else - occur_end = -1; - - /* Add repeating alarms */ - - if (repeat.repetitions != 0) { - int i; - time_t repeat_time; - - repeat_time = icaldurationtype_as_int (repeat.duration); - - for (i = 0; i < repeat.repetitions; i++) { - time_t t; - - t = abs_time + (i + 1) * repeat_time; - - if (t >= aod->start && t < aod->end) - add_trigger (aod, auid, t, occur_start, occur_end); - } - } - - /* Add the trigger itself */ - - if (abs_time >= aod->start && abs_time < aod->end) - add_trigger (aod, auid, abs_time, occur_start, occur_end); - } - - e_cal_component_free_datetime (&dt_start); - e_cal_component_free_datetime (&dt_end); -} - -/* Compares two alarm instances; called from g_slist_sort() */ -static gint -compare_alarm_instance (gconstpointer a, gconstpointer b) -{ - const ECalComponentAlarmInstance *aia, *aib; - - aia = a; - aib = b; - - if (aia->trigger < aib->trigger) - return -1; - else if (aia->trigger > aib->trigger) - return 1; - else - return 0; -} - -/** - * e_cal_util_generate_alarms_for_comp - * @comp: the ECalComponent to generate alarms from - * @start: start time - * @end: end time - * @omit: - * @resolve_tzid: callback for resolving timezones - * @user_data: data to be passed to the resolve_tzid callback - * @default_timezone: the timezone used to resolve DATE and floating DATE-TIME - * values. - * - * Generates alarm instances for a calendar component. Returns the instances - * structure, or NULL if no alarm instances occurred in the specified time - * range. - * - * Returns: - */ -ECalComponentAlarms * -e_cal_util_generate_alarms_for_comp (ECalComponent *comp, - time_t start, - time_t end, - ECalComponentAlarmAction *omit, - ECalRecurResolveTimezoneFn resolve_tzid, - gpointer user_data, - icaltimezone *default_timezone) -{ - GList *alarm_uids; - time_t alarm_start, alarm_end; - struct alarm_occurrence_data aod; - ECalComponentAlarms *alarms; - - if (!e_cal_component_has_alarms (comp)) - return NULL; - - alarm_uids = e_cal_component_get_alarm_uids (comp); - compute_alarm_range (comp, alarm_uids, start, end, &alarm_start, &alarm_end); - - aod.alarm_uids = alarm_uids; - aod.start = start; - aod.end = end; - aod.omit = omit; - aod.triggers = NULL; - aod.n_triggers = 0; - - e_cal_recur_generate_instances (comp, alarm_start, alarm_end, - add_alarm_occurrences_cb, &aod, - resolve_tzid, user_data, - default_timezone); - - /* We add the ABSOLUTE triggers separately */ - generate_absolute_triggers (comp, &aod, resolve_tzid, user_data, default_timezone); - - if (aod.n_triggers == 0) - return NULL; - - /* Create the component alarm instances structure */ - - alarms = g_new (ECalComponentAlarms, 1); - alarms->comp = comp; - g_object_ref (G_OBJECT (alarms->comp)); - alarms->alarms = g_slist_sort (aod.triggers, compare_alarm_instance); - - return alarms; -} - -/** - * e_cal_util_generate_alarms_for_list - * @comps: list of ECalComponent's - * @start: start time - * @end: end time - * @omit: - * @comp_alarms: list to be returned - * @resolve_tzid: callback for resolving timezones - * @user_data: data to be passed to the resolve_tzid callback - * @default_timezone: the timezone used to resolve DATE and floating DATE-TIME - * values. - * - * Iterates through all the components in the comps list and generates alarm - * instances for them; putting them in the comp_alarms list. - * - * Returns: the number of elements it added to that list. - */ -int -e_cal_util_generate_alarms_for_list (GList *comps, - time_t start, - time_t end, - ECalComponentAlarmAction *omit, - GSList **comp_alarms, - ECalRecurResolveTimezoneFn resolve_tzid, - gpointer user_data, - icaltimezone *default_timezone) -{ - GList *l; - int n; - - n = 0; - - for (l = comps; l; l = l->next) { - ECalComponent *comp; - ECalComponentAlarms *alarms; - - comp = E_CAL_COMPONENT (l->data); - alarms = e_cal_util_generate_alarms_for_comp (comp, start, end, omit, resolve_tzid, user_data, default_timezone); - - if (alarms) { - *comp_alarms = g_slist_prepend (*comp_alarms, alarms); - n++; - } - } - - return n; -} - - -/* Converts an iCalendar PRIORITY value to a translated string. Any unknown - priority value (i.e. not 0-9) will be returned as "" (undefined). */ -char * -e_cal_util_priority_to_string (int priority) -{ - char *retval; - - if (priority <= 0) - retval = ""; - else if (priority <= 4) - retval = _("High"); - else if (priority == 5) - retval = _("Normal"); - else if (priority <= 9) - retval = _("Low"); - else - retval = ""; - - return retval; -} - - -/* Converts a translated priority string to an iCalendar priority value. - Returns -1 if the priority string is not valid. */ -int -e_cal_util_priority_from_string (const char *string) -{ - int priority; - - /* An empty string is the same as 'None'. */ - if (!string || !string[0] || !g_strcasecmp (string, _("Undefined"))) - priority = 0; - else if (!g_strcasecmp (string, _("High"))) - priority = 3; - else if (!g_strcasecmp (string, _("Normal"))) - priority = 5; - else if (!g_strcasecmp (string, _("Low"))) - priority = 7; - else - priority = -1; - - return priority; -} - -char * -e_cal_util_expand_uri (char *uri, gboolean tasks) -{ - return g_strdup (uri); -} - -/* callback for icalcomponent_foreach_tzid */ -typedef struct { - icalcomponent *vcal_comp; - icalcomponent *icalcomp; -} ForeachTzidData; - -static void -add_timezone_cb (icalparameter *param, void *data) -{ - icaltimezone *tz; - const char *tzid; - icalcomponent *vtz_comp; - ForeachTzidData *f_data = (ForeachTzidData *) data; - - tzid = icalparameter_get_tzid (param); - if (!tzid) - return; - - tz = icalcomponent_get_timezone (f_data->vcal_comp, tzid); - if (tz) - return; - - tz = icalcomponent_get_timezone (f_data->icalcomp, tzid); - if (!tz) { - tz = icaltimezone_get_builtin_timezone_from_tzid (tzid); - if (!tz) - return; - } - - vtz_comp = icaltimezone_get_component (tz); - if (!vtz_comp) - return; - - icalcomponent_add_component (f_data->vcal_comp, - icalcomponent_new_clone (vtz_comp)); -} - -/* Adds VTIMEZONE components to a VCALENDAR for all tzid's - * in the given ECalComponent. */ -void -e_cal_util_add_timezones_from_component (icalcomponent *vcal_comp, - icalcomponent *icalcomp) -{ - ForeachTzidData f_data; - - g_return_if_fail (vcal_comp != NULL); - g_return_if_fail (icalcomp != NULL);; - - f_data.vcal_comp = vcal_comp; - f_data.icalcomp = icalcomp; - icalcomponent_foreach_tzid (icalcomp, add_timezone_cb, &f_data); -} - -gboolean -e_cal_util_component_is_instance (icalcomponent *icalcomp) -{ - icalproperty *prop; - - g_return_val_if_fail (icalcomp != NULL, FALSE); - - prop = icalcomponent_get_first_property (icalcomp, ICAL_RECURRENCEID_PROPERTY); - return prop ? TRUE : FALSE; -} - -gboolean -e_cal_util_component_has_alarms (icalcomponent *icalcomp) -{ - icalcomponent *alarm; - - g_return_val_if_fail (icalcomp != NULL, FALSE); - - alarm = icalcomponent_get_first_component (icalcomp, ICAL_VALARM_COMPONENT); - return alarm ? TRUE : FALSE; -} - -gboolean -e_cal_util_component_has_organizer (icalcomponent *icalcomp) -{ - icalproperty *prop; - - g_return_val_if_fail (icalcomp != NULL, FALSE); - - prop = icalcomponent_get_first_property (icalcomp, ICAL_ORGANIZER_PROPERTY); - return prop ? TRUE : FALSE; -} - -gboolean -e_cal_util_component_has_recurrences (icalcomponent *icalcomp) -{ - g_return_val_if_fail (icalcomp != NULL, FALSE); - - return e_cal_util_component_has_rdates (icalcomp) || e_cal_util_component_has_rrules (icalcomp); -} - -gboolean -e_cal_util_component_has_rdates (icalcomponent *icalcomp) -{ - icalproperty *prop; - - g_return_val_if_fail (icalcomp != NULL, FALSE); - - prop = icalcomponent_get_first_property (icalcomp, ICAL_RDATE_PROPERTY); - return prop ? TRUE : FALSE; -} - -gboolean -e_cal_util_component_has_rrules (icalcomponent *icalcomp) -{ - icalproperty *prop; - - g_return_val_if_fail (icalcomp != NULL, FALSE); - - prop = icalcomponent_get_first_property (icalcomp, ICAL_RRULE_PROPERTY); - return prop ? TRUE : FALSE; -} - -gboolean -e_cal_util_event_dates_match (icalcomponent *icalcomp1, icalcomponent *icalcomp2) -{ - struct icaltimetype c1_dtstart, c1_dtend, c2_dtstart, c2_dtend; - - g_return_val_if_fail (icalcomp1 != NULL, FALSE); - g_return_val_if_fail (icalcomp2 != NULL, FALSE); - - c1_dtstart = icalcomponent_get_dtstart (icalcomp1); - c1_dtend = icalcomponent_get_dtend (icalcomp1); - c2_dtstart = icalcomponent_get_dtstart (icalcomp2); - c2_dtend = icalcomponent_get_dtend (icalcomp2); - - /* if either value is NULL, they must both be NULL to match */ - if (icaltime_is_valid_time (c1_dtstart) || icaltime_is_valid_time (c2_dtstart)) { - if (!(icaltime_is_valid_time (c1_dtstart) && icaltime_is_valid_time (c2_dtstart))) - return FALSE; - } else { - if (icaltime_compare (c1_dtstart, c2_dtstart)) - return FALSE; - } - - if (icaltime_is_valid_time (c1_dtend) || icaltime_is_valid_time (c2_dtend)) { - if (!(icaltime_is_valid_time (c1_dtend) && icaltime_is_valid_time (c2_dtend))) - return FALSE; - } else { - if (icaltime_compare (c1_dtend, c2_dtend)) - return FALSE; - } - - - - /* now match the timezones */ - if (!(!c1_dtstart.zone && !c2_dtstart.zone) || - (c1_dtstart.zone && c2_dtstart.zone && - !strcmp (icaltimezone_get_tzid ((icaltimezone *) c1_dtstart.zone), - icaltimezone_get_tzid ((icaltimezone *) c2_dtstart.zone)))) - return FALSE; - - if (!(!c1_dtend.zone && !c2_dtend.zone) || - (c1_dtend.zone && c2_dtend.zone && - !strcmp (icaltimezone_get_tzid ((icaltimezone *) c1_dtend.zone), - icaltimezone_get_tzid ((icaltimezone *) c2_dtend.zone)))) - return FALSE; - - return TRUE; -} - -/* Individual instances management */ - -struct instance_data { - time_t start; - gboolean found; -}; - -static void -check_instance (icalcomponent *comp, struct icaltime_span span, void *data) -{ - struct instance_data *instance = data; - - if (span.start == instance->start) - instance->found = TRUE; -} - -/** - * e_cal_util_construct_instance: - * @icalcomp: a recurring #icalcomponent - * @rid: the RECURRENCE-ID to construct a component for - * - * This checks that @rid indicates a valid recurrence of @icalcomp, and - * if so, generates a copy of @comp containing a RECURRENCE-ID of @rid. - * - * Return value: the instance, or %NULL - **/ -icalcomponent * -e_cal_util_construct_instance (icalcomponent *icalcomp, - struct icaltimetype rid) -{ - struct instance_data instance; - struct icaltimetype start, end; - - g_return_val_if_fail (icalcomp != NULL, NULL); - - /* Make sure this is really recurring */ - if (!icalcomponent_get_first_property (icalcomp, ICAL_RRULE_PROPERTY) && - !icalcomponent_get_first_property (icalcomp, ICAL_RDATE_PROPERTY)) - return NULL; - - /* Make sure the specified instance really exists */ - /* FIXME: does the libical recurrence code work correctly now? */ - start = icaltime_convert_to_zone (rid, icaltimezone_get_utc_timezone ()); - end = start; - icaltime_adjust (&end, 0, 0, 0, 1); - - instance.start = icaltime_as_timet (start); - instance.found = FALSE; - icalcomponent_foreach_recurrence (icalcomp, start, end, - check_instance, &instance); - if (!instance.found) - return NULL; - - /* Make the instance */ - icalcomp = icalcomponent_new_clone (icalcomp); - icalcomponent_set_recurrenceid (icalcomp, rid); - - return icalcomp; -} - -static inline gboolean -time_matches_rid (struct icaltimetype itt, struct icaltimetype rid, CalObjModType mod) -{ - int compare; - - compare = icaltime_compare (itt, rid); - if (compare == 0) - return TRUE; - else if (compare < 0 && (mod & CALOBJ_MOD_THISANDPRIOR)) - return TRUE; - else if (compare > 0 && (mod & CALOBJ_MOD_THISANDFUTURE)) - return TRUE; - - return FALSE; -} - -/** - * e_cal_util_remove_instances: - * @icalcomp: a (recurring) #icalcomponent - * @rid: the base RECURRENCE-ID to remove - * @mod: how to interpret @rid - * - * Removes one or more instances from @comp according to @rid and @mod. - * - * FIXME: should probably have a return value indicating whether or not - * @icalcomp still has any instances - **/ -void -e_cal_util_remove_instances (icalcomponent *icalcomp, - struct icaltimetype rid, - CalObjModType mod) -{ - icalproperty *prop; - struct icaltimetype itt, recur; - struct icalrecurrencetype rule; - icalrecur_iterator *iter; - struct instance_data instance; - - g_return_if_fail (icalcomp != NULL); - g_return_if_fail (mod != CALOBJ_MOD_ALL); - - /* First remove RDATEs and EXDATEs in the indicated range. */ - for (prop = icalcomponent_get_first_property (icalcomp, ICAL_RDATE_PROPERTY); - prop; - prop = icalcomponent_get_next_property (icalcomp, ICAL_RDATE_PROPERTY)) { - struct icaldatetimeperiodtype period; - - period = icalproperty_get_rdate (prop); - if (time_matches_rid (period.time, rid, mod)) - icalcomponent_remove_property (icalcomp, prop); - } - for (prop = icalcomponent_get_first_property (icalcomp, ICAL_EXDATE_PROPERTY); - prop; - prop = icalcomponent_get_next_property (icalcomp, ICAL_EXDATE_PROPERTY)) { - itt = icalproperty_get_exdate (prop); - if (time_matches_rid (itt, rid, mod)) - icalcomponent_remove_property (icalcomp, prop); - } - - /* If we're only removing one instance, just add an EXDATE. */ - if (mod == CALOBJ_MOD_THIS) { - prop = icalproperty_new_exdate (rid); - icalcomponent_add_property (icalcomp, prop); - return; - } - - /* Otherwise, iterate through RRULEs */ - /* FIXME: this may generate duplicate EXRULEs */ - for (prop = icalcomponent_get_first_property (icalcomp, ICAL_RRULE_PROPERTY); - prop; - prop = icalcomponent_get_next_property (icalcomp, ICAL_RRULE_PROPERTY)) { - rule = icalproperty_get_rrule (prop); - - iter = icalrecur_iterator_new (rule, rid); - recur = icalrecur_iterator_next (iter); - - if (mod & CALOBJ_MOD_THISANDFUTURE) { - /* If there is a recurrence on or after rid, - * use the UNTIL parameter to truncate the rule - * at rid. - */ - if (!icaltime_is_null_time (recur)) { - rule.count = 0; - rule.until = rid; - icaltime_adjust (&rule.until, 0, 0, 0, -1); - icalproperty_set_rrule (prop, rule); - } - } else { - /* (If recur == rid, skip to the next occurrence) */ - if (icaltime_compare (recur, rid) == 0) - recur = icalrecur_iterator_next (iter); - - /* If there is a recurrence after rid, add - * an EXRULE to block instances up to rid. - * Otherwise, just remove the RRULE. - */ - if (!icaltime_is_null_time (recur)) { - rule.count = 0; - /* iCalendar says we should just use rid - * here, but Outlook/Exchange handle - * UNTIL incorrectly. - */ - rule.until = icaltime_add (rid, icalcomponent_get_duration (icalcomp)); - prop = icalproperty_new_exrule (rule); - icalcomponent_add_property (icalcomp, prop); - } else - icalcomponent_remove_property (icalcomp, prop); - } - - icalrecur_iterator_free (iter); - } -} diff --git a/calendar/libecal/e-cal-util.h b/calendar/libecal/e-cal-util.h deleted file mode 100644 index 64e14d5bb..000000000 --- a/calendar/libecal/e-cal-util.h +++ /dev/null @@ -1,135 +0,0 @@ -/* Evolution calendar utilities and types - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_UTIL_H -#define E_CAL_UTIL_H - -#include <libical/ical.h> -#include <time.h> -#include <glib.h> -#include <libecal/e-cal-component.h> -#include <libecal/e-cal-recur.h> - -G_BEGIN_DECLS - - - -/* Instance of a calendar object. This can be an actual occurrence, a - * recurrence, or an alarm trigger of a `real' calendar object. - */ -typedef struct { - char *uid; /* UID of the object */ - time_t start; /* Start time of instance */ - time_t end; /* End time of instance */ -} CalObjInstance; - -void cal_obj_instance_list_free (GList *list); - -/* Used for modifying objects */ -typedef enum { - CALOBJ_MOD_THIS = 1 << 0, - CALOBJ_MOD_THISANDPRIOR = 1 << 1, - CALOBJ_MOD_THISANDFUTURE = 1 << 2, - CALOBJ_MOD_ALL = 0x07 -} CalObjModType; - -/* Used for mode stuff */ -typedef enum { - CAL_MODE_INVALID = -1, - CAL_MODE_LOCAL = 1 << 0, - CAL_MODE_REMOTE = 1 << 1, - CAL_MODE_ANY = 0x07 -} CalMode; - -#define cal_mode_to_corba(mode) \ - (mode == CAL_MODE_LOCAL ? GNOME_Evolution_Calendar_MODE_LOCAL : \ - mode == CAL_MODE_REMOTE ? GNOME_Evolution_Calendar_MODE_REMOTE : \ - GNOME_Evolution_Calendar_MODE_ANY) - -void cal_obj_uid_list_free (GList *list); - -icalcomponent *e_cal_util_new_top_level (void); -icalcomponent *e_cal_util_new_component (icalcomponent_kind kind); - -icalcomponent *e_cal_util_parse_ics_file (const char *filename); - -ECalComponentAlarms *e_cal_util_generate_alarms_for_comp (ECalComponent *comp, - time_t start, - time_t end, - ECalComponentAlarmAction *omit, - ECalRecurResolveTimezoneFn resolve_tzid, - gpointer user_data, - icaltimezone *default_timezone); -int e_cal_util_generate_alarms_for_list (GList *comps, - time_t start, - time_t end, - ECalComponentAlarmAction *omit, - GSList **comp_alarms, - ECalRecurResolveTimezoneFn resolve_tzid, - gpointer user_data, - icaltimezone *default_timezone); - -icaltimezone *e_cal_util_resolve_tzid (const char *tzid, gpointer data); - -char *e_cal_util_priority_to_string (int priority); -int e_cal_util_priority_from_string (const char *string); - -char *e_cal_util_expand_uri (char *uri, gboolean tasks); - -void e_cal_util_add_timezones_from_component (icalcomponent *vcal_comp, - icalcomponent *icalcomp); - -gboolean e_cal_util_component_is_instance (icalcomponent *icalcomp); -gboolean e_cal_util_component_has_alarms (icalcomponent *icalcomp); -gboolean e_cal_util_component_has_organizer (icalcomponent *icalcomp); -gboolean e_cal_util_component_has_recurrences (icalcomponent *icalcomp); -gboolean e_cal_util_component_has_rdates (icalcomponent *icalcomp); -gboolean e_cal_util_component_has_rrules (icalcomponent *icalcomp); - -gboolean e_cal_util_event_dates_match (icalcomponent *icalcomp1, icalcomponent *icalcomp2); - -/* The static capabilities to be supported by backends */ -#define CAL_STATIC_CAPABILITY_NO_ALARM_REPEAT "no-alarm-repeat" -#define CAL_STATIC_CAPABILITY_NO_AUDIO_ALARMS "no-audio-alarms" -#define CAL_STATIC_CAPABILITY_NO_DISPLAY_ALARMS "no-display-alarms" -#define CAL_STATIC_CAPABILITY_NO_EMAIL_ALARMS "no-email-alarms" -#define CAL_STATIC_CAPABILITY_NO_PROCEDURE_ALARMS "no-procedure-alarms" -#define CAL_STATIC_CAPABILITY_NO_TASK_ASSIGNMENT "no-task-assignment" -#define CAL_STATIC_CAPABILITY_NO_THISANDFUTURE "no-thisandfuture" -#define CAL_STATIC_CAPABILITY_NO_THISANDPRIOR "no-thisandprior" -#define CAL_STATIC_CAPABILITY_NO_TRANSPARENCY "no-transparency" -#define CAL_STATIC_CAPABILITY_ONE_ALARM_ONLY "one-alarm-only" -#define CAL_STATIC_CAPABILITY_ORGANIZER_MUST_ATTEND "organizer-must-attend" -#define CAL_STATIC_CAPABILITY_ORGANIZER_NOT_EMAIL_ADDRESS "organizer-not-email-address" -#define CAL_STATIC_CAPABILITY_REMOVE_ALARMS "remove-alarms" -#define CAL_STATIC_CAPABILITY_SAVE_SCHEDULES "save-schedules" - -/* Recurrent events. Management for instances */ -icalcomponent *e_cal_util_construct_instance (icalcomponent *icalcomp, - struct icaltimetype rid); -void e_cal_util_remove_instances (icalcomponent *icalcomp, - struct icaltimetype rid, - CalObjModType mod); - -G_END_DECLS - -#endif - diff --git a/calendar/libecal/e-cal-view-listener.c b/calendar/libecal/e-cal-view-listener.c deleted file mode 100644 index fcaa2d3b9..000000000 --- a/calendar/libecal/e-cal-view-listener.c +++ /dev/null @@ -1,304 +0,0 @@ -/* Evolution calendar - Live search query listener convenience object - * - * Copyright (C) 2001 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include "e-cal-marshal.h" -#include "e-cal-view-listener.h" - - - -/* Private part of the CalViewListener structure */ - -struct _ECalViewListenerPrivate { - int dummy; -}; - -/* Signal IDs */ -enum { - OBJECTS_ADDED, - OBJECTS_MODIFIED, - OBJECTS_REMOVED, - VIEW_PROGRESS, - VIEW_DONE, - LAST_SIGNAL -}; - -static guint signals[LAST_SIGNAL] = { 0 }; - -static BonoboObjectClass *parent_class; - -/* CORBA method implementations */ -/* FIXME This is duplicated from cal-listener.c */ -static ECalendarStatus -convert_status (const GNOME_Evolution_Calendar_CallStatus status) -{ - switch (status) { - case GNOME_Evolution_Calendar_Success: - return E_CALENDAR_STATUS_OK; - case GNOME_Evolution_Calendar_RepositoryOffline: - return E_CALENDAR_STATUS_REPOSITORY_OFFLINE; - case GNOME_Evolution_Calendar_PermissionDenied: - return E_CALENDAR_STATUS_PERMISSION_DENIED; - case GNOME_Evolution_Calendar_ObjectNotFound: - return E_CALENDAR_STATUS_OBJECT_NOT_FOUND; - case GNOME_Evolution_Calendar_ObjectIdAlreadyExists: - return E_CALENDAR_STATUS_OBJECT_ID_ALREADY_EXISTS; - case GNOME_Evolution_Calendar_AuthenticationFailed: - return E_CALENDAR_STATUS_AUTHENTICATION_FAILED; - case GNOME_Evolution_Calendar_AuthenticationRequired: - return E_CALENDAR_STATUS_AUTHENTICATION_REQUIRED; - case GNOME_Evolution_Calendar_OtherError: - default: - return E_CALENDAR_STATUS_OTHER_ERROR; - } -} - -/* FIXME This is duplicated from cal-listener.c */ -static GList * -build_object_list (const GNOME_Evolution_Calendar_stringlist *seq) -{ - GList *list; - int i; - - list = NULL; - for (i = 0; i < seq->_length; i++) { - icalcomponent *comp; - - comp = icalcomponent_new_from_string (seq->_buffer[i]); - if (!comp) - continue; - - list = g_list_prepend (list, comp); - } - - return list; -} - -static GList * -build_uid_list (const GNOME_Evolution_Calendar_CalObjUIDSeq *seq) -{ - GList *list; - int i; - - list = NULL; - for (i = 0; i < seq->_length; i++) - list = g_list_prepend (list, g_strdup (seq->_buffer[i])); - - return list; -} - -static void -impl_notifyObjectsAdded (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_stringlist *objects, - CORBA_Environment *ev) -{ - ECalViewListener *ql; - ECalViewListenerPrivate *priv; - GList *object_list, *l; - - ql = E_CAL_VIEW_LISTENER (bonobo_object_from_servant (servant)); - priv = ql->priv; - - object_list = build_object_list (objects); - - g_signal_emit (G_OBJECT (ql), signals[OBJECTS_ADDED], 0, object_list); - - for (l = object_list; l; l = l->next) - icalcomponent_free (l->data); - g_list_free (object_list); -} - -static void -impl_notifyObjectsModified (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_stringlist *objects, - CORBA_Environment *ev) -{ - ECalViewListener *ql; - ECalViewListenerPrivate *priv; - GList *object_list, *l; - - ql = E_CAL_VIEW_LISTENER (bonobo_object_from_servant (servant)); - priv = ql->priv; - - object_list = build_object_list (objects); - - g_signal_emit (G_OBJECT (ql), signals[OBJECTS_MODIFIED], 0, object_list); - - for (l = object_list; l; l = l->next) - icalcomponent_free (l->data); - g_list_free (object_list); -} - -static void -impl_notifyObjectsRemoved (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CalObjUIDSeq *uids, - CORBA_Environment *ev) -{ - ECalViewListener *ql; - ECalViewListenerPrivate *priv; - GList *uid_list, *l; - - ql = E_CAL_VIEW_LISTENER (bonobo_object_from_servant (servant)); - priv = ql->priv; - - uid_list = build_uid_list (uids); - - g_signal_emit (G_OBJECT (ql), signals[OBJECTS_REMOVED], 0, uid_list); - - for (l = uid_list; l; l = l->next) - g_free (l->data); - g_list_free (uid_list); -} - -static void -impl_notifyQueryProgress (PortableServer_Servant servant, - const CORBA_char *message, - const CORBA_short percent, - CORBA_Environment *ev) -{ - ECalViewListener *ql; - ECalViewListenerPrivate *priv; - - ql = E_CAL_VIEW_LISTENER (bonobo_object_from_servant (servant)); - priv = ql->priv; - - g_signal_emit (G_OBJECT (ql), signals[VIEW_PROGRESS], 0, message, percent); -} - -static void -impl_notifyQueryDone (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_CallStatus status, - CORBA_Environment *ev) -{ - ECalViewListener *ql; - ECalViewListenerPrivate *priv; - - ql = E_CAL_VIEW_LISTENER (bonobo_object_from_servant (servant)); - priv = ql->priv; - - g_signal_emit (G_OBJECT (ql), signals[VIEW_DONE], 0, convert_status (status)); -} - -/* Object initialization function for the live search query listener */ -static void -e_cal_view_listener_init (ECalViewListener *ql, ECalViewListenerClass *class) -{ - ECalViewListenerPrivate *priv; - - priv = g_new0 (ECalViewListenerPrivate, 1); - ql->priv = priv; -} - -/* Finalize handler for the live search query listener */ -static void -e_cal_view_listener_finalize (GObject *object) -{ - ECalViewListener *ql; - ECalViewListenerPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL_VIEW_LISTENER (object)); - - ql = E_CAL_VIEW_LISTENER (object); - priv = ql->priv; - - g_free (priv); - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - -/* Class initialization function for the live search query listener */ -static void -e_cal_view_listener_class_init (ECalViewListenerClass *klass) -{ - GObjectClass *object_class; - - object_class = (GObjectClass *) klass; - - parent_class = g_type_class_peek_parent (klass); - - object_class->finalize = e_cal_view_listener_finalize; - - klass->epv.notifyObjectsAdded = impl_notifyObjectsAdded; - klass->epv.notifyObjectsModified = impl_notifyObjectsModified; - klass->epv.notifyObjectsRemoved = impl_notifyObjectsRemoved; - klass->epv.notifyQueryProgress = impl_notifyQueryProgress; - klass->epv.notifyQueryDone = impl_notifyQueryDone; - - signals[OBJECTS_ADDED] = - g_signal_new ("objects_added", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalViewListenerClass, objects_added), - NULL, NULL, - e_cal_marshal_VOID__POINTER, - G_TYPE_NONE, 1, G_TYPE_POINTER); - signals[OBJECTS_MODIFIED] = - g_signal_new ("objects_modified", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalViewListenerClass, objects_modified), - NULL, NULL, - e_cal_marshal_VOID__POINTER, - G_TYPE_NONE, 1, G_TYPE_POINTER); - signals[OBJECTS_REMOVED] = - g_signal_new ("objects_removed", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalViewListenerClass, objects_removed), - NULL, NULL, - e_cal_marshal_VOID__POINTER, - G_TYPE_NONE, 1, G_TYPE_POINTER); - signals[VIEW_PROGRESS] = - g_signal_new ("view_progress", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalViewListenerClass, view_progress), - NULL, NULL, - e_cal_marshal_VOID__POINTER, - G_TYPE_NONE, 2, G_TYPE_STRING, G_TYPE_INT); - signals[VIEW_DONE] = - g_signal_new ("view_done", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalViewListenerClass, view_done), - NULL, NULL, - e_cal_marshal_VOID__INT, - G_TYPE_NONE, 1, G_TYPE_INT); -} - -BONOBO_TYPE_FUNC_FULL (ECalViewListener, - GNOME_Evolution_Calendar_CalViewListener, - BONOBO_TYPE_OBJECT, - e_cal_view_listener); - -ECalViewListener * -e_cal_view_listener_new (void) -{ - ECalViewListener *ql; - - ql = g_object_new (E_TYPE_CAL_VIEW_LISTENER, NULL); - - return ql; -} diff --git a/calendar/libecal/e-cal-view-listener.h b/calendar/libecal/e-cal-view-listener.h deleted file mode 100644 index c90fa558e..000000000 --- a/calendar/libecal/e-cal-view-listener.h +++ /dev/null @@ -1,65 +0,0 @@ -/* Evolution calendar - Live search query listener implementation - * - * Copyright (C) 2001 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_VIEW_LISTENER_H -#define E_CAL_VIEW_LISTENER_H - -#include <bonobo/bonobo-object.h> -#include <libecal/Evolution-DataServer-Calendar.h> -#include <libecal/e-cal-types.h> - -G_BEGIN_DECLS - -#define E_TYPE_CAL_VIEW_LISTENER (e_cal_view_listener_get_type ()) -#define E_CAL_VIEW_LISTENER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_VIEW_LISTENER, ECalViewListener)) -#define E_CAL_VIEW_LISTENER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_VIEW_LISTENER, ECalViewListenerClass)) -#define E_IS_CAL_VIEW_LISTENER(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_VIEW_LISTENER)) -#define E_IS_CAL_VIEW_LISTENER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_VIEW_LISTENER)) -#define E_CAL_VIEW_LISTENER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), E_TYPE_CAL_VIEW_LISTENER, ECalViewListenerClass)) - -typedef struct _ECalViewListener ECalViewListener; -typedef struct _ECalViewListenerClass ECalViewListenerClass; -typedef struct _ECalViewListenerPrivate ECalViewListenerPrivate; - -struct _ECalViewListener { - BonoboObject xobject; - - /*< private >*/ - ECalViewListenerPrivate *priv; -}; - -struct _ECalViewListenerClass { - BonoboObjectClass parent_class; - - POA_GNOME_Evolution_Calendar_CalViewListener__epv epv; - - void (*objects_added) (ECalViewListener *listener, GList *objects); - void (*objects_modified) (ECalViewListener *listener, GList *objects); - void (*objects_removed) (ECalViewListener *listener, GList *uids); - void (*view_progress) (ECalViewListener *listener, const char *message, int percent); - void (*view_done) (ECalViewListener *listener, ECalendarStatus status); -}; - -GType e_cal_view_listener_get_type (void); -ECalViewListener *e_cal_view_listener_new (void); - -G_END_DECLS - -#endif diff --git a/calendar/libecal/e-cal-view.c b/calendar/libecal/e-cal-view.c deleted file mode 100644 index adcc16d7d..000000000 --- a/calendar/libecal/e-cal-view.c +++ /dev/null @@ -1,375 +0,0 @@ -/* Evolution calendar - Live view client object - * - * Copyright (C) 2001 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <string.h> -#include <bonobo/bonobo-exception.h> -#include "e-cal-marshal.h" -#include "e-cal.h" -#include "e-cal-view.h" -#include "e-cal-view-listener.h" - - - -/* Private part of the ECalView structure */ -struct _ECalViewPrivate { - /* Handle to the view in the server */ - GNOME_Evolution_Calendar_CalView view; - - /* Our view listener implementation */ - ECalViewListener *listener; - - /* The CalClient associated with this view */ - ECal *client; -}; - -/* Property IDs */ -enum props { - PROP_0, - PROP_VIEW, - PROP_LISTENER, - PROP_CLIENT -}; - -/* Signal IDs */ -enum { - OBJECTS_ADDED, - OBJECTS_MODIFIED, - OBJECTS_REMOVED, - VIEW_PROGRESS, - VIEW_DONE, - LAST_SIGNAL -}; - -static guint signals[LAST_SIGNAL]; - -static GObjectClass *parent_class; - - - -static void -objects_added_cb (ECalViewListener *listener, GList *objects, gpointer data) -{ - ECalView *view; - - view = E_CAL_VIEW (data); - - g_signal_emit (G_OBJECT (view), signals[OBJECTS_ADDED], 0, objects); -} - -static void -objects_modified_cb (ECalViewListener *listener, GList *objects, gpointer data) -{ - ECalView *view; - - view = E_CAL_VIEW (data); - - g_signal_emit (G_OBJECT (view), signals[OBJECTS_MODIFIED], 0, objects); -} - -static void -objects_removed_cb (ECalViewListener *listener, GList *uids, gpointer data) -{ - ECalView *view; - - view = E_CAL_VIEW (data); - - g_signal_emit (G_OBJECT (view), signals[OBJECTS_REMOVED], 0, uids); -} - -static void -view_progress_cb (ECalViewListener *listener, const char *message, int percent, gpointer data) -{ - ECalView *view; - - view = E_CAL_VIEW (data); - - g_signal_emit (G_OBJECT (view), signals[VIEW_PROGRESS], 0, message, percent); -} - -static void -view_done_cb (ECalViewListener *listener, ECalendarStatus status, gpointer data) -{ - ECalView *view; - - view = E_CAL_VIEW (data); - - g_signal_emit (G_OBJECT (view), signals[VIEW_DONE], 0, status); -} - -/* Object initialization function for the calendar view */ -static void -e_cal_view_init (ECalView *view, ECalViewClass *klass) -{ - ECalViewPrivate *priv; - - priv = g_new0 (ECalViewPrivate, 1); - view->priv = priv; - - priv->listener = NULL; - priv->view = CORBA_OBJECT_NIL; -} - -static void -e_cal_view_set_property (GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) -{ - ECalView *view; - ECalViewPrivate *priv; - - view = E_CAL_VIEW (object); - priv = view->priv; - - switch (property_id) { - case PROP_VIEW: - priv->view = bonobo_object_dup_ref (g_value_get_pointer (value), NULL); - break; - case PROP_LISTENER: - priv->listener = bonobo_object_ref (g_value_get_pointer (value)); - - g_signal_connect (G_OBJECT (priv->listener), "objects_added", - G_CALLBACK (objects_added_cb), view); - g_signal_connect (G_OBJECT (priv->listener), "objects_modified", - G_CALLBACK (objects_modified_cb), view); - g_signal_connect (G_OBJECT (priv->listener), "objects_removed", - G_CALLBACK (objects_removed_cb), view); - g_signal_connect (G_OBJECT (priv->listener), "view_progress", - G_CALLBACK (view_progress_cb), view); - g_signal_connect (G_OBJECT (priv->listener), "view_done", - G_CALLBACK (view_done_cb), view); - break; - case PROP_CLIENT: - priv->client = E_CAL (g_value_dup_object (value)); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); - break; - } -} - -static void -e_cal_view_get_property (GObject *object, guint property_id, GValue *value, GParamSpec *pspec) -{ - ECalView *view; - ECalViewPrivate *priv; - - view = E_CAL_VIEW (object); - priv = view->priv; - - switch (property_id) { - case PROP_VIEW: - g_value_set_pointer (value, priv->view); - break; - case PROP_LISTENER: - g_value_set_pointer (value, priv->listener); - break; - case PROP_CLIENT: - g_value_set_object (value, priv->client); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); - break; - } -} - - -/* Finalize handler for the calendar view */ -static void -e_cal_view_finalize (GObject *object) -{ - ECalView *view; - ECalViewPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL_VIEW (object)); - - view = E_CAL_VIEW (object); - priv = view->priv; - - /* The server keeps a copy of the view listener, so we must unref it */ - g_signal_handlers_disconnect_matched (priv->listener, G_SIGNAL_MATCH_DATA, 0, 0, NULL, NULL, view); - bonobo_object_unref (BONOBO_OBJECT (priv->listener)); - - if (priv->view != CORBA_OBJECT_NIL) - bonobo_object_release_unref (priv->view, NULL); - - g_free (priv); - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - -/* Class initialization function for the calendar view */ -static void -e_cal_view_class_init (ECalViewClass *klass) -{ - GObjectClass *object_class; - GParamSpec *param; - - object_class = (GObjectClass *) klass; - - parent_class = g_type_class_peek_parent (klass); - - object_class->set_property = e_cal_view_set_property; - object_class->get_property = e_cal_view_get_property; - object_class->finalize = e_cal_view_finalize; - - param = g_param_spec_pointer ("view", "The corba view object", NULL, - G_PARAM_READABLE | G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY); - g_object_class_install_property (object_class, PROP_VIEW, param); - /* FIXME type this property as object? */ - param = g_param_spec_pointer ("listener", "The view listener object to use", NULL, - G_PARAM_READABLE | G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY); - g_object_class_install_property (object_class, PROP_LISTENER, param); - param = g_param_spec_object ("client", "The e-cal for the view", NULL, E_TYPE_CAL, - G_PARAM_READABLE | G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY); - g_object_class_install_property (object_class, PROP_CLIENT, param); - - signals[OBJECTS_ADDED] = - g_signal_new ("objects_added", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalViewClass, objects_added), - NULL, NULL, - e_cal_marshal_VOID__POINTER, - G_TYPE_NONE, 1, G_TYPE_POINTER); - signals[OBJECTS_MODIFIED] = - g_signal_new ("objects_modified", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalViewClass, objects_modified), - NULL, NULL, - e_cal_marshal_VOID__POINTER, - G_TYPE_NONE, 1, G_TYPE_POINTER); - signals[OBJECTS_REMOVED] = - g_signal_new ("objects_removed", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalViewClass, objects_removed), - NULL, NULL, - e_cal_marshal_VOID__POINTER, - G_TYPE_NONE, 1, G_TYPE_POINTER); - signals[VIEW_PROGRESS] = - g_signal_new ("view_progress", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalViewClass, view_progress), - NULL, NULL, - e_cal_marshal_VOID__POINTER, - G_TYPE_NONE, 2, G_TYPE_STRING, G_TYPE_INT); - signals[VIEW_DONE] = - g_signal_new ("view_done", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalViewClass, view_done), - NULL, NULL, - e_cal_marshal_VOID__INT, - G_TYPE_NONE, 1, G_TYPE_INT); -} - -/** - * e_cal_view_get_type: - * - * Registers the #ECalView class if necessary, and returns the type ID assigned - * to it. - * - * Return value: The type ID of the #ECalView class. - **/ -GType -e_cal_view_get_type (void) -{ - static GType e_cal_view_type = 0; - - if (!e_cal_view_type) { - static GTypeInfo info = { - sizeof (ECalViewClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_view_class_init, - NULL, NULL, - sizeof (ECalView), - 0, - (GInstanceInitFunc) e_cal_view_init - }; - e_cal_view_type = g_type_register_static (G_TYPE_OBJECT, "ECalView", &info, 0); - } - - return e_cal_view_type; -} - -/** - * e_cal_view_new: - * @corba_view: - * @listener: - * @client: - * - * Creates a new view object by issuing the view creation request to the - * calendar server. - * - * Return value: A newly-created view object, or NULL if the request failed. - **/ -ECalView * -e_cal_view_new (GNOME_Evolution_Calendar_CalView corba_view, ECalViewListener *listener, ECal *client) -{ - ECalView *view; - - view = g_object_new (E_TYPE_CAL_VIEW, "view", corba_view, "listener", - listener, "client", client, NULL); - - return view; -} - -/** - * e_cal_view_get_client - * @view: A #ECalView object. - * - * Get the #ECal associated with this view. - * - * Returns: the associated client. - */ -ECal * -e_cal_view_get_client (ECalView *view) -{ - g_return_val_if_fail (E_IS_CAL_VIEW (view), NULL); - - return view->priv->client; -} - -void -e_cal_view_start (ECalView *view) -{ - ECalViewPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (view != NULL); - g_return_if_fail (E_IS_CAL_VIEW (view)); - - priv = view->priv; - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_CalView_start (priv->view, &ev); - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": Unable to start view"); - - CORBA_exception_free (&ev); -} diff --git a/calendar/libecal/e-cal-view.h b/calendar/libecal/e-cal-view.h deleted file mode 100644 index 7ccedfba1..000000000 --- a/calendar/libecal/e-cal-view.h +++ /dev/null @@ -1,68 +0,0 @@ -/* Evolution calendar - Live view client object - * - * Copyright (C) 2001 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_VIEW_H -#define E_CAL_VIEW_H - -#include <glib-object.h> -#include <libecal/Evolution-DataServer-Calendar.h> -#include <libecal/e-cal-types.h> -#include <libecal/e-cal-view-listener.h> - -G_BEGIN_DECLS - -#define E_TYPE_CAL_VIEW (e_cal_view_get_type ()) -#define E_CAL_VIEW(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_VIEW, ECalView)) -#define E_CAL_VIEW_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_VIEW, ECalViewClass)) -#define E_IS_CAL_VIEW(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_VIEW)) -#define E_IS_CAL_VIEW_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_VIEW)) - -typedef struct _ECalView ECalView; -typedef struct _ECalViewClass ECalViewClass; -typedef struct _ECalViewPrivate ECalViewPrivate; -struct _ECal; - -struct _ECalView { - GObject object; - - /*< private >*/ - ECalViewPrivate *priv; -}; - -struct _ECalViewClass { - GObjectClass parent_class; - - /* Notification signals */ - void (* objects_added) (ECalView *view, GList *objects); - void (* objects_modified) (ECalView *view, GList *objects); - void (* objects_removed) (ECalView *view, GList *uids); - void (* view_progress) (ECalView *view, char *message, int percent); - void (* view_done) (ECalView *view, ECalendarStatus status); -}; - -GType e_cal_view_get_type (void); - -ECalView *e_cal_view_new (GNOME_Evolution_Calendar_CalView corba_view, ECalViewListener *listener, struct _ECal *client); -struct _ECal *e_cal_view_get_client (ECalView *view); -void e_cal_view_start (ECalView *view); - -G_END_DECLS - -#endif diff --git a/calendar/libecal/e-cal.c b/calendar/libecal/e-cal.c deleted file mode 100644 index e5c25a823..000000000 --- a/calendar/libecal/e-cal.c +++ /dev/null @@ -1,4475 +0,0 @@ -/* Evolution calendar ecal - * - * Copyright (C) 2001 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <pthread.h> -#include <string.h> -#include <bonobo-activation/bonobo-activation.h> -#include <bonobo/bonobo-exception.h> -#include <bonobo/bonobo-i18n.h> -#include <libgnome/gnome-util.h> - -#include <libedataserver/e-component-listener.h> -#include <libedataserver/e-url.h> -#include "e-cal-marshal.h" -#include "e-cal-time-util.h" -#include "e-cal-listener.h" -#include "e-cal-view-listener.h" -#include "e-cal.h" - - - -typedef struct { - GMutex *mutex; - GCond *cond; - ECalendarStatus status; - - char *uid; - GList *list; - gboolean bool; - char *string; - - ECalView *query; - ECalViewListener *listener; -} ECalendarOp; - -/* Private part of the ECal structure */ -struct _ECalPrivate { - /* Load state to avoid multiple loads */ - ECalLoadState load_state; - - /* URI of the calendar that is being loaded or is already loaded, or - * NULL if we are not loaded. - */ - ESource *source; - char *uri; - ECalSourceType type; - - ECalendarOp *current_op; - - GMutex *mutex; - - /* Email address associated with this calendar, or NULL */ - char *cal_address; - char *alarm_email_address; - char *ldap_attribute; - - /* Scheduling info */ - char *capabilities; - - /* The calendar factories we are contacting */ - GList *factories; - - /* Our calendar listener implementation */ - ECalListener *listener; - - /* The calendar ecal interface object we are contacting */ - GNOME_Evolution_Calendar_Cal cal; - - /* The authentication function */ - ECalAuthFunc auth_func; - gpointer auth_user_data; - - /* A cache of timezones retrieved from the server, to avoid getting - them repeatedly for each get_object() call. */ - GHashTable *timezones; - - /* The default timezone to use to resolve DATE and floating DATE-TIME - values. */ - icaltimezone *default_zone; - - /* The component listener to keep track of the lifetime of backends */ - EComponentListener *comp_listener; -}; - - - -/* Signal IDs */ -enum { - CAL_OPENED, - CAL_SET_MODE, - BACKEND_ERROR, - CATEGORIES_CHANGED, - BACKEND_DIED, - LAST_SIGNAL -}; - -static guint e_cal_signals[LAST_SIGNAL]; - -static GObjectClass *parent_class; - -#define e_return_error_if_fail(expr,error_code) G_STMT_START{ \ - if G_LIKELY(expr) { } else \ - { \ - g_log (G_LOG_DOMAIN, \ - G_LOG_LEVEL_CRITICAL, \ - "file %s: line %d (%s): assertion `%s' failed", \ - __FILE__, \ - __LINE__, \ - __PRETTY_FUNCTION__, \ - #expr); \ - g_set_error (error, E_CALENDAR_ERROR, (error_code), \ - "file %s: line %d (%s): assertion `%s' failed", \ - __FILE__, \ - __LINE__, \ - __PRETTY_FUNCTION__, \ - #expr); \ - return FALSE; \ - }; }G_STMT_END - -#define E_CALENDAR_CHECK_STATUS(status,error) G_STMT_START{ \ - if ((status) == E_CALENDAR_STATUS_OK) { \ - return TRUE; \ - } \ - else { \ - const char *msg; \ - msg = e_cal_get_error_message ((status)); \ - g_set_error ((error), E_CALENDAR_ERROR, (status), msg, (status)); \ - return FALSE; \ - } }G_STMT_END - - - -/* Error quark */ -GQuark -e_calendar_error_quark (void) -{ - static GQuark q = 0; - if (q == 0) - q = g_quark_from_static_string ("e-calendar-error-quark"); - - return q; -} - -GType -e_cal_set_mode_status_enum_get_type (void) -{ - static GType e_cal_set_mode_status_enum_type = 0; - - if (!e_cal_set_mode_status_enum_type) { - static GEnumValue values [] = { - { E_CAL_SET_MODE_SUCCESS, "ECalSetModeSuccess", "success" }, - { E_CAL_SET_MODE_ERROR, "ECalSetModeError", "error" }, - { E_CAL_SET_MODE_NOT_SUPPORTED, "ECalSetModeNotSupported", "unsupported" }, - { -1, NULL, NULL } - }; - - e_cal_set_mode_status_enum_type = - g_enum_register_static ("ECalSetModeStatusEnum", values); - } - - return e_cal_set_mode_status_enum_type; -} - -GType -cal_mode_enum_get_type (void) -{ - static GType cal_mode_enum_type = 0; - - if (!cal_mode_enum_type) { - static GEnumValue values [] = { - { CAL_MODE_INVALID, "CalModeInvalid", "invalid" }, - { CAL_MODE_LOCAL, "CalModeLocal", "local" }, - { CAL_MODE_REMOTE, "CalModeRemote", "remote" }, - { CAL_MODE_ANY, "CalModeAny", "any" }, - { -1, NULL, NULL } - }; - - cal_mode_enum_type = g_enum_register_static ("CalModeEnum", values); - } - - return cal_mode_enum_type; -} - -static GNOME_Evolution_Calendar_CalObjType -convert_type (ECalSourceType type) -{ - switch (type){ - case E_CAL_SOURCE_TYPE_EVENT: - return GNOME_Evolution_Calendar_TYPE_EVENT; - case E_CAL_SOURCE_TYPE_TODO: - return GNOME_Evolution_Calendar_TYPE_TODO; - case E_CAL_SOURCE_TYPE_JOURNAL: - return GNOME_Evolution_Calendar_TYPE_JOURNAL; - default: - return GNOME_Evolution_Calendar_TYPE_ANY; - } - - return GNOME_Evolution_Calendar_TYPE_ANY; -} - -/* EBookOp calls */ - -static ECalendarOp* -e_calendar_new_op (ECal *ecal) -{ - ECalendarOp *op = g_new0 (ECalendarOp, 1); - - op->mutex = g_mutex_new (); - op->cond = g_cond_new (); - - ecal->priv->current_op = op; - - return op; -} - -static ECalendarOp* -e_calendar_get_op (ECal *ecal) -{ - if (!ecal->priv->current_op) { - g_warning (G_STRLOC ": Unexpected response"); - return NULL; - } - - return ecal->priv->current_op; -} - -static void -e_calendar_free_op (ECalendarOp *op) -{ - /* XXX more stuff here */ - g_cond_free (op->cond); - g_mutex_free (op->mutex); - g_free (op); -} - -static void -e_calendar_remove_op (ECal *ecal, ECalendarOp *op) -{ - if (ecal->priv->current_op != op) - g_warning (G_STRLOC ": Cannot remove op, it's not current"); - - ecal->priv->current_op = NULL; -} - -/* Gets rid of the factories that a ecal knows about */ -static void -destroy_factories (ECal *ecal) -{ - ECalPrivate *priv; - CORBA_Object factory; - CORBA_Environment ev; - int result; - GList *f; - - priv = ecal->priv; - - CORBA_exception_init (&ev); - - for (f = priv->factories; f; f = f->next) { - factory = f->data; - - result = CORBA_Object_is_nil (factory, &ev); - if (BONOBO_EX (&ev)) { - g_message (G_STRLOC ": could not see if a factory was nil"); - CORBA_exception_free (&ev); - - continue; - } - - if (result) - continue; - - CORBA_Object_release (factory, &ev); - if (BONOBO_EX (&ev)) { - g_message (G_STRLOC ": could not release a factory"); - CORBA_exception_free (&ev); - } - } - - g_list_free (priv->factories); - priv->factories = NULL; -} - -/* Gets rid of the calendar ecal interface object that a ecal knows about */ -static void -destroy_cal (ECal *ecal) -{ - ECalPrivate *priv; - CORBA_Environment ev; - int result; - - priv = ecal->priv; - - CORBA_exception_init (&ev); - result = CORBA_Object_is_nil (priv->cal, &ev); - if (BONOBO_EX (&ev)) { - g_message (G_STRLOC ": could not see if the " - "calendar ecal interface object was nil"); - priv->cal = CORBA_OBJECT_NIL; - CORBA_exception_free (&ev); - return; - } - CORBA_exception_free (&ev); - - if (result) - return; - - bonobo_object_release_unref (priv->cal, NULL); - priv->cal = CORBA_OBJECT_NIL; - -} - -static void -free_timezone (gpointer key, gpointer value, gpointer data) -{ - /* Note that the key comes from within the icaltimezone value, so we - don't free that. */ - icaltimezone_free (value, TRUE); -} - - - -static void -backend_died_cb (EComponentListener *cl, gpointer user_data) -{ - ECalPrivate *priv; - ECal *ecal = (ECal *) user_data; - - priv = ecal->priv; - priv->load_state = E_CAL_LOAD_NOT_LOADED; - g_signal_emit (G_OBJECT (ecal), e_cal_signals[BACKEND_DIED], 0); -} - -/* Signal handlers for the listener's signals */ -/* Handle the cal_opened notification from the listener */ - -static void -cal_read_only_cb (ECalListener *listener, ECalendarStatus status, gboolean read_only, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->bool = read_only; - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_cal_address_cb (ECalListener *listener, ECalendarStatus status, const char *address, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->string = g_strdup (address); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_alarm_address_cb (ECalListener *listener, ECalendarStatus status, const char *address, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->string = g_strdup (address); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_ldap_attribute_cb (ECalListener *listener, ECalendarStatus status, const char *attribute, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->string = g_strdup (attribute); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_static_capabilities_cb (ECalListener *listener, ECalendarStatus status, const char *capabilities, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->string = g_strdup (capabilities); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_opened_cb (ECalListener *listener, ECalendarStatus status, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_removed_cb (ECalListener *listener, ECalendarStatus status, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_object_created_cb (ECalListener *listener, ECalendarStatus status, const char *uid, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->uid = g_strdup (uid); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_object_modified_cb (ECalListener *listener, ECalendarStatus status, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_object_removed_cb (ECalListener *listener, ECalendarStatus status, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_alarm_discarded_cb (ECalListener *listener, ECalendarStatus status, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_objects_received_cb (ECalListener *listener, ECalendarStatus status, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_objects_sent_cb (ECalListener *listener, ECalendarStatus status, GList *users, const char *object, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->list = g_list_copy (users); - op->string = g_strdup (object); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_default_object_requested_cb (ECalListener *listener, ECalendarStatus status, const char *object, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->string = g_strdup (object); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_object_requested_cb (ECalListener *listener, ECalendarStatus status, const char *object, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->string = g_strdup (object); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_object_list_cb (ECalListener *listener, ECalendarStatus status, GList *objects, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - GList *l; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->list = g_list_copy (objects); - - for (l = op->list; l; l = l->next) - l->data = icalcomponent_new_clone (l->data); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_get_timezone_cb (ECalListener *listener, ECalendarStatus status, const char *object, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->string = g_strdup (object); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); - -} - -static void -cal_add_timezone_cb (ECalListener *listener, ECalendarStatus status, const char *tzid, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->uid = g_strdup (tzid); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); - -} - -static void -cal_set_default_timezone_cb (ECalListener *listener, ECalendarStatus status, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_get_changes_cb (ECalListener *listener, ECalendarStatus status, GList *changes, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - GList *l; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->list = g_list_copy (changes); - - for (l = op->list; l; l = l->next) { - ECalChange *ccc = l->data, *new_ccc; - - new_ccc = g_new (ECalChange, 1); - new_ccc->comp = e_cal_component_clone (ccc->comp); - new_ccc->type = ccc->type; - - l->data = new_ccc; - } - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_get_free_busy_cb (ECalListener *listener, ECalendarStatus status, GList *freebusy, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - GList *l; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->list = g_list_copy (freebusy); - - for (l = op->list; l; l = l->next) - l->data = e_cal_component_clone (l->data); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -static void -cal_query_cb (ECalListener *listener, ECalendarStatus status, GNOME_Evolution_Calendar_CalView query, gpointer data) -{ - ECal *ecal = data; - ECalendarOp *op; - - op = e_calendar_get_op (ecal); - - if (op == NULL) { - g_warning (G_STRLOC ": Cannot find operation "); - return; - } - - g_mutex_lock (op->mutex); - - op->status = status; - op->query = e_cal_view_new (query, op->listener, ecal); - - g_cond_signal (op->cond); - - g_mutex_unlock (op->mutex); -} - -/* Handle the cal_set_mode notification from the listener */ -static void -cal_set_mode_cb (ECalListener *listener, - GNOME_Evolution_Calendar_CalListener_SetModeStatus status, - GNOME_Evolution_Calendar_CalMode mode, - gpointer data) -{ - ECal *ecal; - ECalPrivate *priv; - ECalSetModeStatus ecal_status; - - ecal = E_CAL (data); - priv = ecal->priv; - - ecal_status = E_CAL_SET_MODE_ERROR; - - switch (status) { - case GNOME_Evolution_Calendar_CalListener_MODE_SET: - ecal_status = E_CAL_SET_MODE_SUCCESS; - break; - case GNOME_Evolution_Calendar_CalListener_MODE_NOT_SET: - ecal_status = E_CAL_SET_MODE_ERROR; - break; - case GNOME_Evolution_Calendar_CalListener_MODE_NOT_SUPPORTED: - ecal_status = E_CAL_SET_MODE_NOT_SUPPORTED; - break; - default: - g_assert_not_reached (); - } - - /* We are *not* inside a signal handler (this is just a simple callback - * called from the listener), so there is not a temporary reference to - * the ecal object. We ref() so that we can safely emit our own - * signal and clean up. - */ - - g_object_ref (G_OBJECT (ecal)); - - g_signal_emit (G_OBJECT (ecal), e_cal_signals[CAL_SET_MODE], - 0, ecal_status, mode); - - g_object_unref (G_OBJECT (ecal)); -} - -typedef struct -{ - ECal *ecal; - char *message; -} ECalErrorData; - -static gboolean -backend_error_idle_cb (gpointer data) -{ - ECalErrorData *error_data = data; - - g_signal_emit (G_OBJECT (error_data->ecal), e_cal_signals[BACKEND_ERROR], 0, error_data->message); - - g_object_unref (error_data->ecal); - g_free (error_data->message); - g_free (error_data); - - return FALSE; -} - -/* Handle the error_occurred signal from the listener */ -static void -backend_error_cb (ECalListener *listener, const char *message, gpointer data) -{ - ECalErrorData *error_data; - - error_data = g_new0 (ECalErrorData, 1); - - error_data->ecal = g_object_ref (data); - error_data->message = g_strdup (message); - - g_idle_add (backend_error_idle_cb, error_data); -} - -typedef struct -{ - ECal *ecal; - GPtrArray *categories; -} ECalCategoryData; - -static gboolean -categories_changed_idle_cb (gpointer data) -{ - ECalCategoryData *cat_data = data; - int i; - - g_signal_emit (G_OBJECT (cat_data->ecal), e_cal_signals[CATEGORIES_CHANGED], 0, cat_data->categories); - - g_object_unref (cat_data->ecal); - for (i = 0; i < cat_data->categories->len; i++) - g_free (cat_data->categories->pdata[i]); - g_ptr_array_free (cat_data->categories, TRUE); - g_free (cat_data); - - return FALSE; -} - -/* Handle the categories_changed signal from the listener */ -static void -categories_changed_cb (ECalListener *listener, const GNOME_Evolution_Calendar_StringSeq *categories, - gpointer data) -{ - ECalCategoryData *cat_data; - int i; - - cat_data = g_new0 (ECalCategoryData, 1); - - cat_data->ecal = g_object_ref (data); - cat_data->categories = g_ptr_array_new (); - g_ptr_array_set_size (cat_data->categories, categories->_length); - - for (i = 0; i < categories->_length; i++) - cat_data->categories->pdata[i] = g_strdup (categories->_buffer[i]); - - g_idle_add (categories_changed_idle_cb, cat_data); -} - - - -static gboolean -get_factories (const char *str_uri, GList **factories) -{ - GNOME_Evolution_Calendar_CalFactory factory; - Bonobo_ServerInfoList *servers; - EUri *uri; - char *query; - int i; - - - /* Determine the protocol and query for factory supporting that */ - uri = e_uri_new (str_uri); - if (!uri) { - g_warning (G_STRLOC ": Invalid uri string"); - - return FALSE; - } - - query = g_strdup_printf ("repo_ids.has ('IDL:GNOME/Evolution/DataServer/CalFactory:" BASE_VERSION "')" - " AND calendar:supported_protocols.has ('%s')", uri->protocol); - - - servers = bonobo_activation_query (query, NULL, NULL); - - g_free (query); - e_uri_free (uri); - - if (!servers) { - g_warning (G_STRLOC ": Unable to query for calendar factories"); - - return FALSE; - } - - /* Try to activate the servers for the protocol */ - for (i = 0; i < servers->_length; i++) { - const Bonobo_ServerInfo *info; - - info = servers->_buffer + i; - -#if 0 - g_message (G_STRLOC ": Activating calendar factory (%s)", info->iid); -#endif - factory = bonobo_activation_activate_from_id (info->iid, 0, NULL, NULL); - - if (factory == CORBA_OBJECT_NIL) - g_warning (G_STRLOC ": Could not activate calendar factory (%s)", info->iid); - else - *factories = g_list_append (*factories, factory); - } - - CORBA_free (servers); - - return TRUE; -} - -/* Object initialization function for the calendar ecal */ -static void -e_cal_init (ECal *ecal, ECalClass *klass) -{ - ECalPrivate *priv; - - priv = g_new0 (ECalPrivate, 1); - ecal->priv = priv; - - priv->load_state = E_CAL_LOAD_NOT_LOADED; - priv->uri = NULL; - priv->mutex = g_mutex_new (); - priv->listener = e_cal_listener_new (cal_set_mode_cb, ecal); - - priv->cal_address = NULL; - priv->alarm_email_address = NULL; - priv->ldap_attribute = NULL; - priv->capabilities = FALSE; - priv->factories = NULL; - priv->timezones = g_hash_table_new (g_str_hash, g_str_equal); - priv->default_zone = icaltimezone_get_utc_timezone (); - priv->comp_listener = NULL; - - g_signal_connect (G_OBJECT (priv->listener), "read_only", G_CALLBACK (cal_read_only_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "cal_address", G_CALLBACK (cal_cal_address_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "alarm_address", G_CALLBACK (cal_alarm_address_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "ldap_attribute", G_CALLBACK (cal_ldap_attribute_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "static_capabilities", G_CALLBACK (cal_static_capabilities_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "open", G_CALLBACK (cal_opened_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "remove", G_CALLBACK (cal_removed_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "create_object", G_CALLBACK (cal_object_created_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "modify_object", G_CALLBACK (cal_object_modified_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "remove_object", G_CALLBACK (cal_object_removed_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "discard_alarm", G_CALLBACK (cal_alarm_discarded_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "receive_objects", G_CALLBACK (cal_objects_received_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "send_objects", G_CALLBACK (cal_objects_sent_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "default_object", G_CALLBACK (cal_default_object_requested_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "object", G_CALLBACK (cal_object_requested_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "object_list", G_CALLBACK (cal_object_list_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "get_timezone", G_CALLBACK (cal_get_timezone_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "add_timezone", G_CALLBACK (cal_add_timezone_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "set_default_timezone", G_CALLBACK (cal_set_default_timezone_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "get_changes", G_CALLBACK (cal_get_changes_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "get_free_busy", G_CALLBACK (cal_get_free_busy_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "query", G_CALLBACK (cal_query_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "categories_changed", G_CALLBACK (categories_changed_cb), ecal); - g_signal_connect (G_OBJECT (priv->listener), "backend_error", G_CALLBACK (backend_error_cb), ecal); -} - -/* Finalize handler for the calendar ecal */ -static void -e_cal_finalize (GObject *object) -{ - ECal *ecal; - ECalPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_CAL (object)); - - ecal = E_CAL (object); - priv = ecal->priv; - - if (priv->listener) { - e_cal_listener_stop_notification (priv->listener); - bonobo_object_unref (priv->listener); - priv->listener = NULL; - } - - if (priv->comp_listener) { - g_signal_handlers_disconnect_matched (G_OBJECT (priv->comp_listener), - G_SIGNAL_MATCH_DATA, - 0, 0, NULL, NULL, - ecal); - g_object_unref (G_OBJECT (priv->comp_listener)); - priv->comp_listener = NULL; - } - - destroy_factories (ecal); - destroy_cal (ecal); - - priv->load_state = E_CAL_LOAD_NOT_LOADED; - - if (priv->source) { - g_object_unref (priv->source); - priv->source = NULL; - } - - if (priv->uri) { - g_free (priv->uri); - priv->uri = NULL; - } - - if (priv->mutex) { - g_mutex_free (priv->mutex); - priv->mutex = NULL; - } - - if (priv->cal_address) { - g_free (priv->cal_address); - priv->cal_address = NULL; - } - if (priv->alarm_email_address) { - g_free (priv->alarm_email_address); - priv->alarm_email_address = NULL; - } - if (priv->ldap_attribute) { - g_free (priv->ldap_attribute); - priv->ldap_attribute = NULL; - } - if (priv->capabilities) { - g_free (priv->capabilities); - priv->capabilities = NULL; - } - - g_hash_table_foreach (priv->timezones, free_timezone, NULL); - g_hash_table_destroy (priv->timezones); - priv->timezones = NULL; - - g_free (priv); - ecal->priv = NULL; - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - -/* Class initialization function for the calendar ecal */ -static void -e_cal_class_init (ECalClass *klass) -{ - GObjectClass *object_class; - - object_class = (GObjectClass *) klass; - - parent_class = g_type_class_peek_parent (klass); - - e_cal_signals[CAL_OPENED] = - g_signal_new ("cal_opened", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalClass, cal_opened), - NULL, NULL, - g_cclosure_marshal_VOID__INT, - G_TYPE_NONE, 1, G_TYPE_INT); - e_cal_signals[CAL_SET_MODE] = - g_signal_new ("cal_set_mode", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalClass, cal_set_mode), - NULL, NULL, - e_cal_marshal_VOID__ENUM_ENUM, - G_TYPE_NONE, 2, - E_CAL_SET_MODE_STATUS_ENUM_TYPE, - CAL_MODE_ENUM_TYPE); - e_cal_signals[BACKEND_ERROR] = - g_signal_new ("backend_error", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalClass, backend_error), - NULL, NULL, - g_cclosure_marshal_VOID__STRING, - G_TYPE_NONE, 1, - G_TYPE_STRING); - e_cal_signals[CATEGORIES_CHANGED] = - g_signal_new ("categories_changed", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalClass, categories_changed), - NULL, NULL, - g_cclosure_marshal_VOID__POINTER, - G_TYPE_NONE, 1, - G_TYPE_POINTER); - e_cal_signals[BACKEND_DIED] = - g_signal_new ("backend_died", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalClass, backend_died), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - - klass->cal_opened = NULL; - klass->categories_changed = NULL; - klass->backend_died = NULL; - - object_class->finalize = e_cal_finalize; -} - -/** - * e_cal_get_type: - * - * Registers the #ECal class if necessary, and returns the type ID assigned - * to it. - * - * Return value: The type ID of the #ECal class. - **/ -GType -e_cal_get_type (void) -{ - static GType e_cal_type = 0; - - if (!e_cal_type) { - static GTypeInfo info = { - sizeof (ECalClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_class_init, - NULL, NULL, - sizeof (ECal), - 0, - (GInstanceInitFunc) e_cal_init - }; - e_cal_type = g_type_register_static (G_TYPE_OBJECT, "ECal", &info, 0); - } - - return e_cal_type; -} - - -static gboolean -fetch_corba_cal (ECal *ecal, ESource *source, ECalSourceType type) -{ - ECalPrivate *priv; - GList *f; - CORBA_Environment ev; - gchar *source_xml; - gchar *str_uri; - gboolean result = FALSE; - - priv = ecal->priv; - g_return_val_if_fail (priv->load_state == E_CAL_LOAD_NOT_LOADED, FALSE); - g_assert (priv->uri == NULL); - g_return_val_if_fail (source != NULL, FALSE); - - str_uri = e_source_get_uri (source); - if (!str_uri) - return FALSE; - - if (!get_factories (str_uri, &priv->factories)) { - g_free (str_uri); - return FALSE; - } - - g_object_ref (source); - priv->source = source; - - priv->uri = g_strdup (str_uri); - priv->type = type; - - source_xml = e_source_to_standalone_xml (source); - - for (f = priv->factories; f; f = f->next) { - GNOME_Evolution_Calendar_Cal cal; - - CORBA_exception_init (&ev); - - cal = GNOME_Evolution_Calendar_CalFactory_getCal (f->data, source_xml, convert_type (priv->type), - BONOBO_OBJREF (priv->listener), &ev); - if (BONOBO_EX (&ev)) - continue; - - priv->cal = cal; - - result = TRUE; - break; - } - - g_free (str_uri); - g_free (source_xml); - return result; -} - -/** - * e_cal_new: - * @source: - * @type: - * - * Creates a new calendar ecal. It should be initialized by calling - * e_cal_open(). - * - * Return value: A newly-created calendar ecal, or NULL if the ecal could - * not be constructed because it could not contact the calendar server. - **/ -ECal * -e_cal_new (ESource *source, ECalSourceType type) -{ - ECal *ecal; - - ecal = g_object_new (E_TYPE_CAL, NULL); - - if (!fetch_corba_cal (ecal, source, type)) { - g_object_unref (ecal); - - return NULL; - } - - /* initialize component listener */ - ecal->priv->comp_listener = e_component_listener_new ((Bonobo_Unknown) ecal->priv->cal); - g_signal_connect (G_OBJECT (ecal->priv->comp_listener), "component_died", - G_CALLBACK (backend_died_cb), ecal); - - return ecal; -} - -/** - * e_cal_new_from_uri: - * @uri: - * @type: - * - * Creates a new calendar ecal. It should be initialized by calling - * e_cal_open(). - * - * Return value: A newly-created calendar ecal, or NULL if the ecal could - * not be constructed because it could not contact the calendar server. - **/ -ECal * -e_cal_new_from_uri (const gchar *uri, ECalSourceType type) -{ - ESourceGroup *group; - ESource *source; - ECal *cal; - - group = e_source_group_new ("", uri); - source = e_source_new ("", ""); - e_source_set_group (source, group); - - cal = e_cal_new (source, type); - - g_object_unref (source); - g_object_unref (group); - - return cal; -} - -ECal * -e_cal_new_system_calendar (void) -{ - ECal *ecal; - char *uri; - - uri = g_build_filename ("file://", g_get_home_dir (), ".evolution", "calendar", "local", "system", NULL); - ecal = e_cal_new_from_uri (uri, E_CAL_SOURCE_TYPE_EVENT); - g_free (uri); - - return ecal; -} - -ECal * -e_cal_new_system_tasks (void) -{ - ECal *ecal; - char *uri; - - uri = g_build_filename ("file://", g_get_home_dir (), ".evolution", "tasks", "local", "system", NULL); - ecal = e_cal_new_from_uri (uri, E_CAL_SOURCE_TYPE_EVENT); - g_free (uri); - - return ecal; -} - -/** - * e_cal_set_auth_func - * @ecal: A calendar ecal. - * @func: The authentication function - * @data: User data to be used when calling the authentication function - * - * Associates the given authentication function with a calendar ecal. This - * function will be called any time the calendar server needs a password - * from the ecal. So, calendar ecals should provide such authentication - * function, which, when called, should act accordingly (by showing a dialog - * box, for example, to ask the user for the password). - * - * The authentication function must have the following form: - * char * auth_func (ECal *ecal, - * const gchar *prompt, - * const gchar *key, - * gpointer user_data) - */ -void -e_cal_set_auth_func (ECal *ecal, ECalAuthFunc func, gpointer data) -{ - g_return_if_fail (ecal != NULL); - g_return_if_fail (E_IS_CAL (ecal)); - - ecal->priv->auth_func = func; - ecal->priv->auth_user_data = data; -} - -static gboolean -open_calendar (ECal *ecal, gboolean only_if_exists, GError **error, ECalendarStatus *status) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarOp *our_op; - const char *username = NULL; - char *password = NULL; - - g_return_val_if_fail (ecal != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL (ecal), FALSE); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - /* start the open operation */ - our_op = e_calendar_new_op (ecal); - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (priv->mutex); - - /* see if the backend needs authentication */ - if (e_source_get_property (priv->source, "auth")) { - char *prompt, *key; - - priv->load_state = E_CAL_LOAD_AUTHENTICATING; - - if (priv->auth_func == NULL) { - g_mutex_unlock (our_op->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_AUTHENTICATION_REQUIRED, error); - } - - username = e_source_get_property (priv->source, "username"); - if (!username) { - g_mutex_unlock (our_op->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_AUTHENTICATION_REQUIRED, error); - } - - /* actually ask the client for authentication */ - prompt = g_strdup_printf (_("Enter password for %s (user %s)"), - e_source_peek_name (priv->source), username); - key = e_source_get_uri (priv->source); - - password = priv->auth_func (ecal, prompt, key, priv->auth_user_data); - if (!password) { - g_mutex_unlock (our_op->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_AUTHENTICATION_REQUIRED, error); - } - - g_free (prompt); - g_free (key); - } - - - CORBA_exception_init (&ev); - - priv->load_state = E_CAL_LOAD_LOADING; - - GNOME_Evolution_Calendar_Cal_open (priv->cal, only_if_exists, - username ? username : "", - password ? password : "", - &ev); - if (password) - g_free (password); - - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - g_mutex_unlock (ecal->priv->mutex); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - *status = E_CALENDAR_STATUS_CORBA_EXCEPTION; - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - *status = our_op->status; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - if (*status == E_CALENDAR_STATUS_OK) - priv->load_state = E_CAL_LOAD_LOADED; - else - priv->load_state = E_CAL_LOAD_NOT_LOADED; - - E_CALENDAR_CHECK_STATUS (*status, error); -} - -/** - * e_cal_open - * @ecal: A calendar ecal. - * @only_if_exists: FALSE if the calendar should be opened even if there - * was no storage for it, i.e. to create a new calendar or load an existing - * one if it already exists. TRUE if it should only try to load calendars - * that already exist. - * @error: - * - * Makes a calendar ecal initiate a request to open a calendar. The calendar - * ecal will emit the "cal_opened" signal when the response from the server is - * received. - * - * Return value: TRUE on success, FALSE on failure to issue the open request. - **/ -gboolean -e_cal_open (ECal *ecal, gboolean only_if_exists, GError **error) -{ - ECalendarStatus status; - gboolean result; - - result = open_calendar (ecal, only_if_exists, error, &status); - g_signal_emit (G_OBJECT (ecal), e_cal_signals[CAL_OPENED], 0, status); - - return result; -} - -typedef struct { - ECal *ecal; - gboolean exists; - gboolean result; - ECalendarStatus status; - ECalAuthFunc real_auth_func; - gpointer real_auth_user_data; - const char *auth_prompt; - const char *auth_key; - char *password; - GMutex *mutex; - GCond *cond; -} ECalAsyncData; - -static gboolean -async_auth_idle_cb (gpointer data) -{ - ECalAsyncData *ccad = data; - - g_mutex_lock (ccad->mutex); - ccad->password = ccad->real_auth_func (ccad->ecal, ccad->auth_prompt, ccad->auth_key, ccad->real_auth_user_data); - g_cond_signal (ccad->cond); - g_mutex_unlock (ccad->mutex); - - return FALSE; -} - -static gboolean -async_signal_idle_cb (gpointer data) -{ - ECalAsyncData *ccad = data; - - g_signal_emit (G_OBJECT (ccad->ecal), e_cal_signals[CAL_OPENED], 0, ccad->status); - - ccad->ecal->priv->auth_func = ccad->real_auth_func; - ccad->ecal->priv->auth_user_data = ccad->real_auth_user_data; - g_mutex_free (ccad->mutex); - g_cond_free (ccad->cond); - - /* free memory */ - g_object_unref (ccad->ecal); - g_free (ccad); - - return FALSE; -} - -static char * -async_auth_func_cb (ECal *ecal, const char *prompt, const char *key, gpointer user_data) -{ - ECalAsyncData *ccad = user_data; - char * password; - - ccad->auth_prompt = prompt; - ccad->auth_key = key; - - g_idle_add ((GSourceFunc) async_auth_idle_cb, ccad); - - g_mutex_lock (ccad->mutex); - g_cond_wait (ccad->cond, ccad->mutex); - password = ccad->password; - ccad->password = NULL; - g_mutex_unlock (ccad->mutex); - - return password; -} - - -static gpointer -open_async (gpointer data) -{ - ECalAsyncData *ccad = data; - - ccad->mutex = g_mutex_new (); - ccad->cond = g_cond_new (); - - ccad->real_auth_func = ccad->ecal->priv->auth_func; - ccad->real_auth_user_data = ccad->ecal->priv->auth_user_data; - ccad->ecal->priv->auth_func = async_auth_func_cb; - ccad->ecal->priv->auth_user_data = ccad; - - ccad->result = open_calendar (ccad->ecal, ccad->exists, NULL, &ccad->status); - g_idle_add ((GSourceFunc) async_signal_idle_cb, ccad); - - return GINT_TO_POINTER (ccad->result); -} - -void -e_cal_open_async (ECal *ecal, gboolean only_if_exists) -{ - ECalAsyncData *ccad; - GThread *thread; - GError *error = NULL; - g_return_if_fail (ecal != NULL); - g_return_if_fail (E_IS_CAL (ecal)); - - ccad = g_new0 (ECalAsyncData, 1); - ccad->ecal = g_object_ref (ecal); - ccad->exists = only_if_exists; - - /* spawn a new thread for opening the calendar */ - thread = g_thread_create ((GThreadFunc) open_async, ccad, FALSE, &error); - if (!thread) { - g_warning (G_STRLOC ": %s", error->message); - g_error_free (error); - - /* notify listeners of the error */ - g_signal_emit (G_OBJECT (ecal), e_cal_signals[CAL_OPENED], 0, E_CALENDAR_STATUS_OTHER_ERROR); - } -} - -gboolean -e_cal_remove (ECal *ecal, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - g_return_val_if_fail (ecal != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL (ecal), FALSE); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_remove (priv->cal, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -#if 0 -/* Builds an URI list out of a CORBA string sequence */ -static GList * -build_uri_list (GNOME_Evolution_Calendar_StringSeq *seq) -{ - GList *uris = NULL; - int i; - - for (i = 0; i < seq->_length; i++) - uris = g_list_prepend (uris, g_strdup (seq->_buffer[i])); - - return uris; -} -#endif - -GList * -e_cal_uri_list (ECal *ecal, CalMode mode) -{ -#if 0 - ECalPrivate *priv; - GNOME_Evolution_Calendar_StringSeq *uri_seq; - GList *uris = NULL; - CORBA_Environment ev; - GList *f; - - g_return_val_if_fail (ecal != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL (ecal), FALSE); - - priv = ecal->priv; - - for (f = priv->factories; f; f = f->next) { - CORBA_exception_init (&ev); - uri_seq = GNOME_Evolution_Calendar_CalFactory_uriList (f->data, mode, &ev); - - if (BONOBO_EX (&ev)) { - g_message ("e_cal_uri_list(): request failed"); - - /* free memory and return */ - g_list_foreach (uris, (GFunc) g_free, NULL); - g_list_free (uris); - uris = NULL; - break; - } - else { - uris = g_list_concat (uris, build_uri_list (uri_seq)); - CORBA_free (uri_seq); - } - - CORBA_exception_free (&ev); - } - - return uris; -#endif - - return NULL; -} - -ECalSourceType -e_cal_get_source_type (ECal *ecal) -{ - ECalPrivate *priv; - - g_return_val_if_fail (ecal != NULL, E_CAL_SOURCE_TYPE_LAST); - g_return_val_if_fail (E_IS_CAL (ecal), E_CAL_SOURCE_TYPE_LAST); - - priv = ecal->priv; - - return priv->type; -} - -/** - * e_cal_get_load_state: - * @ecal: A calendar ecal. - * - * Queries the state of loading of a calendar ecal. - * - * Return value: A #ECalLoadState value indicating whether the ecal has - * not been loaded with e_cal_open_calendar() yet, whether it is being - * loaded, or whether it is already loaded. - **/ -ECalLoadState -e_cal_get_load_state (ECal *ecal) -{ - ECalPrivate *priv; - - g_return_val_if_fail (ecal != NULL, E_CAL_LOAD_NOT_LOADED); - g_return_val_if_fail (E_IS_CAL (ecal), E_CAL_LOAD_NOT_LOADED); - - priv = ecal->priv; - return priv->load_state; -} - -/** - * e_cal_get_source: - * @ecal: A calendar ecal. - * - * Queries the source that is open in a calendar ecal. - * - * Return value: The source of the calendar that is already loaded or is being - * loaded, or NULL if the ecal has not started a load request yet. - **/ -ESource * -e_cal_get_source (ECal *ecal) -{ - ECalPrivate *priv; - - g_return_val_if_fail (ecal != NULL, NULL); - g_return_val_if_fail (E_IS_CAL (ecal), NULL); - - priv = ecal->priv; - return priv->source; -} - -/** - * e_cal_get_uri: - * @ecal: A calendar ecal. - * - * Queries the URI that is open in a calendar ecal. - * - * Return value: The URI of the calendar that is already loaded or is being - * loaded, or NULL if the ecal has not started a load request yet. - **/ -const char * -e_cal_get_uri (ECal *ecal) -{ - ECalPrivate *priv; - - g_return_val_if_fail (ecal != NULL, NULL); - g_return_val_if_fail (E_IS_CAL (ecal), NULL); - - priv = ecal->priv; - return priv->uri; -} - -/** - * e_cal_is_read_only: - * @ecal: A calendar ecal. - * @read_only: - * @error: - * - * Queries whether the calendar ecal can perform modifications - * on the calendar or not. Whether the backend is read only or not - * is specified, on exit, in the @read_only argument. - * - * Return value: TRUE if the call was successful, FALSE if there was an error. - */ -gboolean -e_cal_is_read_only (ECal *ecal, gboolean *read_only, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_isReadOnly (priv->cal, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - *read_only = our_op->bool; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -/** - * e_cal_get_cal_address: - * @ecal: A calendar ecal. - * @cal_address: - * @error: - * - * Queries the calendar address associated with a calendar ecal. - * - * Return value: The calendar address associated with the calendar that - * is loaded or being loaded, or %NULL if the ecal has not started a - * load request yet or the calendar has no associated email address. - **/ -gboolean -e_cal_get_cal_address (ECal *ecal, char **cal_address, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_getCalAddress (priv->cal, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - *cal_address = our_op->string; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -gboolean -e_cal_get_alarm_email_address (ECal *ecal, char **alarm_address, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_getAlarmEmailAddress (priv->cal, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - *alarm_address = our_op->string; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -gboolean -e_cal_get_ldap_attribute (ECal *ecal, char **ldap_attribute, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_getLdapAttribute (priv->cal, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - *ldap_attribute = our_op->string; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -static gboolean -load_static_capabilities (ECal *ecal, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - char *cap; - - priv = ecal->priv; - - if (priv->capabilities) - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_OK, error); - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_getStaticCapabilities (priv->cal, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - priv->capabilities = our_op->string; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -static gboolean -check_capability (ECal *ecal, const char *cap) -{ - ECalPrivate *priv; - - priv = ecal->priv; - - /* FIXME Check result */ - load_static_capabilities (ecal, NULL); - if (priv->capabilities && strstr (priv->capabilities, cap)) - return TRUE; - - return FALSE; -} - -gboolean -e_cal_get_one_alarm_only (ECal *ecal) -{ - g_return_val_if_fail (ecal != NULL, FALSE); - g_return_val_if_fail (ecal && E_IS_CAL (ecal), FALSE); - - return check_capability (ecal, CAL_STATIC_CAPABILITY_ONE_ALARM_ONLY); -} - -gboolean -e_cal_get_organizer_must_attend (ECal *ecal) -{ - g_return_val_if_fail (ecal != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL (ecal), FALSE); - - return check_capability (ecal, CAL_STATIC_CAPABILITY_ORGANIZER_MUST_ATTEND); -} - -gboolean -e_cal_get_static_capability (ECal *ecal, const char *cap) -{ - g_return_val_if_fail (ecal != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL (ecal), FALSE); - - return check_capability (ecal, cap); -} - -gboolean -e_cal_get_save_schedules (ECal *ecal) -{ - g_return_val_if_fail (ecal != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL (ecal), FALSE); - - return check_capability (ecal, CAL_STATIC_CAPABILITY_SAVE_SCHEDULES); -} - -gboolean -e_cal_set_mode (ECal *ecal, CalMode mode) -{ - ECalPrivate *priv; - gboolean retval = TRUE; - CORBA_Environment ev; - - g_return_val_if_fail (ecal != NULL, -1); - g_return_val_if_fail (E_IS_CAL (ecal), -1); - - priv = ecal->priv; - g_return_val_if_fail (priv->load_state == E_CAL_LOAD_LOADED, -1); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_Cal_setMode (priv->cal, mode, &ev); - - if (BONOBO_EX (&ev)) - retval = FALSE; - - CORBA_exception_free (&ev); - - return retval; -} - - -/* This is used in the callback which fetches all the timezones needed for an - object. */ -typedef struct _ECalGetTimezonesData ECalGetTimezonesData; -struct _ECalGetTimezonesData { - ECal *ecal; - - /* This starts out at E_CALENDAR_STATUS_OK. If an error occurs this - contains the last error. */ - ECalendarStatus status; -}; - -gboolean -e_cal_get_default_object (ECal *ecal, icalcomponent **icalcomp, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_getDefaultObject (priv->cal, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - if (status != E_CALENDAR_STATUS_OK) { - *icalcomp = NULL; - } else { - *icalcomp = icalparser_parse_string (our_op->string); - if (!(*icalcomp)) - status = E_CALENDAR_STATUS_INVALID_OBJECT; - } - g_free (our_op->string); - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -/** - * e_cal_get_object: - * @ecal: A calendar ecal. - * @uid: Unique identifier for a calendar component. - * @rid: - * @icalcomp: Return value for the calendar component object. - * @error: - * - * Queries a calendar for a calendar component object based on its unique - * identifier. - * - * Return value: Result code based on the status of the operation. - **/ -gboolean -e_cal_get_object (ECal *ecal, const char *uid, const char *rid, icalcomponent **icalcomp, GError **error) -{ - - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_getObject (priv->cal, uid, rid ? rid : "", &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - if (status != E_CALENDAR_STATUS_OK){ - *icalcomp = NULL; - } else { - *icalcomp = icalparser_parse_string (our_op->string); - if (!(*icalcomp)) - status = E_CALENDAR_STATUS_INVALID_OBJECT; - } - g_free (our_op->string); - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -/* Resolves TZIDs for the recurrence generator. */ -icaltimezone* -e_cal_resolve_tzid_cb (const char *tzid, gpointer data) -{ - ECal *ecal; - icaltimezone *zone = NULL; - - g_return_val_if_fail (data != NULL, NULL); - g_return_val_if_fail (E_IS_CAL (data), NULL); - - ecal = E_CAL (data); - - /* FIXME: Handle errors. */ - e_cal_get_timezone (ecal, tzid, &zone, NULL); - - return zone; -} - -gboolean -e_cal_get_changes (ECal *ecal, const char *change_id, GList **changes, GError **error) -{ - CORBA_Environment ev; - ECalendarOp *our_op; - ECalendarStatus status; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (change_id, E_CALENDAR_STATUS_INVALID_ARG); - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_getChanges (ecal->priv->cal, change_id, &ev); - - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - *changes = our_op->list; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -void -e_cal_free_change_list (GList *list) -{ - ECalChange *c; - GList *l; - - for (l = list; l; l = l->next) { - c = l->data; - - g_assert (c != NULL); - g_assert (c->comp != NULL); - - g_object_unref (G_OBJECT (c->comp)); - g_free (c); - } - - g_list_free (list); -} - -/** - * e_cal_get_object_list: - * @ecal: - * @query: - * @objects: - * @error: - * - * - * - * Return value: - **/ -gboolean -e_cal_get_object_list (ECal *ecal, const char *query, GList **objects, GError **error) -{ - CORBA_Environment ev; - ECalendarOp *our_op; - ECalendarStatus status; - - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (query, E_CALENDAR_STATUS_INVALID_ARG); - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_getObjectList (ecal->priv->cal, query, &ev); - - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - *objects = our_op->list; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -gboolean -e_cal_get_object_list_as_comp (ECal *ecal, const char *query, GList **objects, GError **error) -{ - GList *ical_objects = NULL; - GList *l; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (query, E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (objects, E_CALENDAR_STATUS_INVALID_ARG); - - if (!e_cal_get_object_list (ecal, query, &ical_objects, error)) - return FALSE; - - *objects = NULL; - for (l = ical_objects; l; l = l->next) { - ECalComponent *comp; - - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, l->data); - *objects = g_list_prepend (*objects, comp); - } - - g_list_free (ical_objects); - - return TRUE; -} - -void -e_cal_free_object_list (GList *objects) -{ - GList *l; - - for (l = objects; l; l = l->next) - icalcomponent_free (l->data); - - g_list_free (objects); -} - -/** - * e_cal_get_free_busy - * @ecal: A calendar ecal. - * @users: List of users to retrieve free/busy information for. - * @start: Start time for query. - * @end: End time for query. - * @freebusy: - * @error: - * - * Gets free/busy information from the calendar server. - * - * Returns: a GList of VFREEBUSY ECalComponents - */ -gboolean -e_cal_get_free_busy (ECal *ecal, GList *users, time_t start, time_t end, - GList **freebusy, GError **error) -{ - CORBA_Environment ev; - ECalendarOp *our_op; - ECalendarStatus status; - GNOME_Evolution_Calendar_UserList corba_users; - GList *l; - int i, len; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - /* create the CORBA user list to be passed to the backend */ - len = g_list_length (users); - - corba_users._length = len; - corba_users._buffer = CORBA_sequence_GNOME_Evolution_Calendar_User_allocbuf (len); - - for (l = users, i = 0; l; l = l->next, i++) - corba_users._buffer[i] = CORBA_string_dup (l->data); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_getFreeBusy (ecal->priv->cal, &corba_users, start, end, &ev); - - CORBA_free (corba_users._buffer); - - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - *freebusy = our_op->list; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -struct comp_instance { - ECalComponent *comp; - time_t start; - time_t end; -}; - -/* Called from cal_recur_generate_instances(); adds an instance to the list */ -static gboolean -add_instance (ECalComponent *comp, time_t start, time_t end, gpointer data) -{ - GList **list; - struct comp_instance *ci; - struct icaltimetype itt, itt_start; - icalcomponent *icalcomp; - - list = data; - - ci = g_new (struct comp_instance, 1); - - icalcomp = icalcomponent_new_clone (e_cal_component_get_icalcomponent (comp)); - itt_start = icalcomponent_get_dtstart (icalcomp); - -#if 0 - /* set the RECUR-ID for the instance */ - if (e_cal_util_component_has_recurrences (icalcomp)) { - if (!(icalcomponent_get_first_property (icalcomp, ICAL_RECURRENCEID_PROPERTY))) { - itt = icaltime_from_timet (start, itt_start.is_date); - icalcomponent_set_recurrenceid (icalcomp, itt); - } - } -#endif - - /* add the instance to the list */ - ci->comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (ci->comp, icalcomp); - - - ci->start = start; - ci->end = end; - - *list = g_list_prepend (*list, ci); - - return TRUE; -} - -/* Used from g_list_sort(); compares two struct comp_instance structures */ -static gint -compare_comp_instance (gconstpointer a, gconstpointer b) -{ - const struct comp_instance *cia, *cib; - time_t diff; - - cia = a; - cib = b; - - diff = cia->start - cib->start; - return (diff < 0) ? -1 : (diff > 0) ? 1 : 0; -} - -static GList * -process_detached_instances (GList *instances, GList *detached_instances) -{ - struct comp_instance *ci, *cid; - GList *dl, *unprocessed_instances = NULL; - - for (dl = detached_instances; dl != NULL; dl = dl->next) { - GList *il; - const char *uid; - gboolean processed; - ECalComponentRange recur_id, instance_recur_id; - - processed = FALSE; - - cid = dl->data; - e_cal_component_get_uid (cid->comp, &uid); - e_cal_component_get_recurid (cid->comp, &recur_id); - - /* search for coincident instances already expanded */ - for (il = instances; il != NULL; il = il->next) { - const char *instance_uid; - int cmp; - - ci = il->data; - e_cal_component_get_uid (ci->comp, &instance_uid); - e_cal_component_get_recurid (ci->comp, &instance_recur_id); - if (strcmp (uid, instance_uid) == 0) { - if (strcmp (e_cal_component_get_recurid_as_string (ci->comp), - e_cal_component_get_recurid_as_string (cid->comp)) == 0) { - g_object_unref (ci->comp); - ci->comp = g_object_ref (cid->comp); - ci->start = cid->start; - ci->end = cid->end; - - processed = TRUE; - } else { - cmp = icaltime_compare (*instance_recur_id.datetime.value, - *recur_id.datetime.value); - if ((recur_id.type == E_CAL_COMPONENT_RANGE_THISPRIOR && cmp <= 0) || - (recur_id.type == E_CAL_COMPONENT_RANGE_THISFUTURE && cmp >= 0)) { - ECalComponent *comp; - - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent ( - comp, - icalcomponent_new_clone (e_cal_component_get_icalcomponent (cid->comp))); - e_cal_component_set_recurid (comp, &instance_recur_id); - - /* replace the generated instances */ - g_object_unref (ci->comp); - ci->comp = comp; - } - } - } - } - - if (!processed) - unprocessed_instances = g_list_prepend (unprocessed_instances, cid); - } - - /* add the unprocessed instances (ie, detached instances with no master object */ - while (unprocessed_instances != NULL) { - cid = unprocessed_instances->data; - ci = g_new0 (struct comp_instance, 1); - ci->comp = g_object_ref (cid->comp); - ci->start = cid->start; - ci->end = cid->end; - instances = g_list_append (instances, ci); - - unprocessed_instances = g_list_remove (unprocessed_instances, cid); - } - - return instances; -} - -/** - * e_cal_generate_instances: - * @ecal: A calendar ecal. - * @start: Start time for query. - * @end: End time for query. - * @cb: Callback for each generated instance. - * @cb_data: Closure data for the callback. - * - * Does a combination of e_cal_get_object_list () and - * cal_recur_generate_instances(). - * - * The callback function should do a g_object_ref() of the calendar component - * it gets passed if it intends to keep it around. - **/ -void -e_cal_generate_instances (ECal *ecal, time_t start, time_t end, - ECalRecurInstanceFn cb, gpointer cb_data) -{ - ECalPrivate *priv; - GList *objects; - GList *instances, *detached_instances = NULL; - GList *l; - char *query; - char *iso_start, *iso_end; - - g_return_if_fail (ecal != NULL); - g_return_if_fail (E_IS_CAL (ecal)); - - priv = ecal->priv; - g_return_if_fail (priv->load_state == E_CAL_LOAD_LOADED); - - g_return_if_fail (start != -1 && end != -1); - g_return_if_fail (start <= end); - g_return_if_fail (cb != NULL); - - iso_start = isodate_from_time_t (start); - if (!iso_start) - return; - - iso_end = isodate_from_time_t (end); - if (!iso_end) { - g_free (iso_start); - return; - } - - /* Generate objects */ - query = g_strdup_printf ("(occur-in-time-range? (make-time \"%s\") (make-time \"%s\"))", - iso_start, iso_end); - g_free (iso_start); - g_free (iso_end); - if (!e_cal_get_object_list_as_comp (ecal, query, &objects, NULL)) { - g_free (query); - return; - } - g_free (query); - - instances = NULL; - - for (l = objects; l; l = l->next) { - ECalComponent *comp; - icaltimezone *default_zone; - - if (priv->default_zone) - default_zone = priv->default_zone; - else - default_zone = icaltimezone_get_utc_timezone (); - - comp = l->data; - if (e_cal_component_is_instance (comp)) { - /* keep the detached instances apart */ - e_cal_recur_generate_instances (comp, start, end, add_instance, &detached_instances, - e_cal_resolve_tzid_cb, ecal, - default_zone); - - g_object_unref (comp); - } else { - e_cal_recur_generate_instances (comp, start, end, add_instance, &instances, - e_cal_resolve_tzid_cb, ecal, - default_zone); - - g_object_unref (comp); - } - } - - g_list_free (objects); - - /* Generate instances and spew them out */ - - instances = g_list_sort (instances, compare_comp_instance); - instances = process_detached_instances (instances, detached_instances); - - for (l = instances; l; l = l->next) { - struct comp_instance *ci; - gboolean result; - - ci = l->data; - - result = (* cb) (ci->comp, ci->start, ci->end, cb_data); - - if (!result) - break; - } - - /* Clean up */ - - for (l = instances; l; l = l->next) { - struct comp_instance *ci; - - ci = l->data; - g_object_unref (G_OBJECT (ci->comp)); - g_free (ci); - } - - g_list_free (instances); - - for (l = detached_instances; l; l = l->next) { - struct comp_instance *ci; - - ci = l->data; - g_object_unref (G_OBJECT (ci->comp)); - g_free (ci); - } - - g_list_free (detached_instances); -} - -/** - * e_cal_generate_instances_for_object: - * @ecal: A calendar ecal. - * @icalcomp: Object to generate instances from. - * @start: Start time for query. - * @end: End time for query. - * @cb: Callback for each generated instance. - * @cb_data: Closure data for the callback. - * - * Does a combination of e_cal_get_object_list () and - * cal_recur_generate_instances(), like e_cal_generate_instances(), but - * for a single object. - * - * The callback function should do a g_object_ref() of the calendar component - * it gets passed if it intends to keep it around. - **/ -void -e_cal_generate_instances_for_object (ECal *ecal, icalcomponent *icalcomp, - time_t start, time_t end, - ECalRecurInstanceFn cb, gpointer cb_data) -{ - ECalPrivate *priv; - ECalComponent *comp; - const char *uid, *rid; - gboolean result; - GList *instances = NULL; - - g_return_if_fail (E_IS_CAL (ecal)); - g_return_if_fail (start != -1 && end != -1); - g_return_if_fail (start <= end); - g_return_if_fail (cb != NULL); - - priv = ecal->priv; - - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, icalcomponent_new_clone (icalcomp)); - - /* generate all instances in the given time range */ - e_cal_generate_instances (ecal, start, end, add_instance, &instances); - - /* now only return back the instances for the given object */ - e_cal_component_get_uid (comp, &uid); - rid = e_cal_component_get_recurid_as_string (comp); - - result = TRUE; - while (instances != NULL) { - struct comp_instance *ci; - const char *instance_uid, *instance_rid; - - ci = instances->data; - - if (result) { - e_cal_component_get_uid (ci->comp, &instance_uid); - instance_rid = e_cal_component_get_recurid_as_string (ci->comp); - - if (instance_uid && strcmp (uid, instance_uid) == 0) { - if (rid && *rid) { - if (instance_rid && *instance_rid && strcmp (rid, instance_rid) == 0) - result = (* cb) (ci->comp, ci->start, ci->end, cb_data); - } else - result = (* cb) (ci->comp, ci->start, ci->end, cb_data); - } - } - - /* remove instance from list */ - instances = g_list_remove (instances, ci); - g_object_unref (ci->comp); - g_free (ci); - } - - /* clean up */ - g_object_unref (comp); -} - -/* Builds a list of ECalComponentAlarms structures */ -static GSList * -build_component_alarms_list (ECal *ecal, GList *object_list, time_t start, time_t end) -{ - GSList *comp_alarms; - GList *l; - - comp_alarms = NULL; - - for (l = object_list; l != NULL; l = l->next) { - ECalComponent *comp; - ECalComponentAlarms *alarms; - ECalComponentAlarmAction omit[] = {-1}; - - comp = e_cal_component_new (); - if (!e_cal_component_set_icalcomponent (comp, icalcomponent_new_clone (l->data))) { - g_object_unref (G_OBJECT (comp)); - continue; - } - - alarms = e_cal_util_generate_alarms_for_comp (comp, start, end, omit, e_cal_resolve_tzid_cb, - ecal, ecal->priv->default_zone); - if (alarms) - comp_alarms = g_slist_prepend (comp_alarms, alarms); - } - - return comp_alarms; -} - -/** - * e_cal_get_alarms_in_range: - * @ecal: A calendar ecal. - * @start: Start time for query. - * @end: End time for query. - * - * Queries a calendar for the alarms that trigger in the specified range of - * time. - * - * Return value: A list of #ECalComponentAlarms structures. This should be freed - * using the e_cal_free_alarms() function, or by freeing each element - * separately with e_cal_component_alarms_free() and then freeing the list with - * g_slist_free(). - **/ -GSList * -e_cal_get_alarms_in_range (ECal *ecal, time_t start, time_t end) -{ - ECalPrivate *priv; - GSList *alarms; - char *sexp; - GList *object_list = NULL; - - g_return_val_if_fail (ecal != NULL, NULL); - g_return_val_if_fail (E_IS_CAL (ecal), NULL); - - priv = ecal->priv; - g_return_val_if_fail (priv->load_state == E_CAL_LOAD_LOADED, NULL); - - g_return_val_if_fail (start != -1 && end != -1, NULL); - g_return_val_if_fail (start <= end, NULL); - - /* build the query string */ - sexp = g_strdup ("(has-alarms?)"); - - /* execute the query on the server */ - if (!e_cal_get_object_list (ecal, sexp, &object_list, NULL)) { - g_free (sexp); - return NULL; - } - - alarms = build_component_alarms_list (ecal, object_list, start, end); - - g_list_foreach (object_list, (GFunc) icalcomponent_free, NULL); - g_list_free (object_list); - g_free (sexp); - - return alarms; -} - -/** - * e_cal_free_alarms: - * @comp_alarms: A list of #ECalComponentAlarms structures. - * - * Frees a list of #ECalComponentAlarms structures as returned by - * e_cal_get_alarms_in_range(). - **/ -void -e_cal_free_alarms (GSList *comp_alarms) -{ - GSList *l; - - for (l = comp_alarms; l; l = l->next) { - ECalComponentAlarms *alarms; - - alarms = l->data; - g_assert (alarms != NULL); - - e_cal_component_alarms_free (alarms); - } - - g_slist_free (comp_alarms); -} - -/** - * e_cal_get_alarms_for_object: - * @ecal: A calendar ecal. - * @uid: Unique identifier for a calendar component. - * @start: Start time for query. - * @end: End time for query. - * @alarms: Return value for the component's alarm instances. Will return NULL - * if no instances occur within the specified time range. This should be freed - * using the e_cal_component_alarms_free() function. - * - * Queries a calendar for the alarms of a particular object that trigger in the - * specified range of time. - * - * Return value: TRUE on success, FALSE if the object was not found. - **/ -gboolean -e_cal_get_alarms_for_object (ECal *ecal, const char *uid, - time_t start, time_t end, - ECalComponentAlarms **alarms) -{ - ECalPrivate *priv; - icalcomponent *icalcomp; - ECalComponent *comp; - ECalComponentAlarmAction omit[] = {-1}; - - g_return_val_if_fail (ecal != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL (ecal), FALSE); - - priv = ecal->priv; - g_return_val_if_fail (priv->load_state == E_CAL_LOAD_LOADED, FALSE); - - g_return_val_if_fail (uid != NULL, FALSE); - g_return_val_if_fail (start != -1 && end != -1, FALSE); - g_return_val_if_fail (start <= end, FALSE); - g_return_val_if_fail (alarms != NULL, FALSE); - - *alarms = NULL; - - if (!e_cal_get_object (ecal, uid, NULL, &icalcomp, NULL)) - return FALSE; - if (!icalcomp) - return FALSE; - - comp = e_cal_component_new (); - if (!e_cal_component_set_icalcomponent (comp, icalcomp)) { - icalcomponent_free (icalcomp); - g_object_unref (G_OBJECT (comp)); - return FALSE; - } - - *alarms = e_cal_util_generate_alarms_for_comp (comp, start, end, omit, e_cal_resolve_tzid_cb, - ecal, priv->default_zone); - - return TRUE; -} - -/** - * e_cal_discard_alarm - * @ecal: A calendar ecal. - * @comp: The component to discard the alarm from. - * @auid: Unique identifier of the alarm to be discarded. - * @error: - * - * Tells the calendar backend to get rid of the alarm identified by the - * @auid argument in @comp. Some backends might remove the alarm or - * update internal information about the alarm be discarded, or, like - * the file backend does, ignore the operation. - * - * Return value: a #ECalResult value indicating the result of the - * operation. - */ -gboolean -e_cal_discard_alarm (ECal *ecal, ECalComponent *comp, const char *auid, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - const char *uid; - - g_return_val_if_fail (ecal != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL (ecal), FALSE); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - e_cal_component_get_uid (comp, &uid); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_discardAlarm (priv->cal, uid, auid, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -typedef struct _ForeachTZIDCallbackData ForeachTZIDCallbackData; -struct _ForeachTZIDCallbackData { - ECal *ecal; - GHashTable *timezone_hash; - gboolean include_all_timezones; - gboolean success; -}; - -/* This adds the VTIMEZONE given by the TZID parameter to the GHashTable in - data. */ -static void -foreach_tzid_callback (icalparameter *param, void *cbdata) -{ - ForeachTZIDCallbackData *data = cbdata; - ECalPrivate *priv; - const char *tzid; - icaltimezone *zone; - icalcomponent *vtimezone_comp; - char *vtimezone_as_string; - - priv = data->ecal->priv; - - /* Get the TZID string from the parameter. */ - tzid = icalparameter_get_tzid (param); - if (!tzid) - return; - - /* Check if we've already added it to the GHashTable. */ - if (g_hash_table_lookup (data->timezone_hash, tzid)) - return; - - if (data->include_all_timezones) { - if (!e_cal_get_timezone (data->ecal, tzid, &zone, NULL)) { - data->success = FALSE; - return; - } - } else { - /* Check if it is in our cache. If it is, it must already be - on the server so return. */ - if (g_hash_table_lookup (priv->timezones, tzid)) - return; - - /* Check if it is a builtin timezone. If it isn't, return. */ - zone = icaltimezone_get_builtin_timezone_from_tzid (tzid); - if (!zone) - return; - } - - /* Convert it to a string and add it to the hash. */ - vtimezone_comp = icaltimezone_get_component (zone); - if (!vtimezone_comp) - return; - - vtimezone_as_string = icalcomponent_as_ical_string (vtimezone_comp); - - g_hash_table_insert (data->timezone_hash, (char*) tzid, - g_strdup (vtimezone_as_string)); -} - -/* This appends the value string to the GString given in data. */ -static void -append_timezone_string (gpointer key, gpointer value, gpointer data) -{ - GString *vcal_string = data; - - g_string_append (vcal_string, value); - g_free (value); -} - - -/* This simply frees the hash values. */ -static void -free_timezone_string (gpointer key, gpointer value, gpointer data) -{ - g_free (value); -} - - -/* This converts the VEVENT/VTODO to a string. If include_all_timezones is - TRUE, it includes all the VTIMEZONE components needed for the VEVENT/VTODO. - If not, it only includes builtin timezones that may not be on the server. - - To do that we check every TZID in the component to see if it is a builtin - timezone. If it is, we see if it it in our cache. If it is in our cache, - then we know the server already has it and we don't need to send it. - If it isn't in our cache, then we need to send it to the server. - If we need to send any timezones to the server, then we have to create a - complete VCALENDAR object, otherwise we can just send a single VEVENT/VTODO - as before. */ -static char* -e_cal_get_component_as_string_internal (ECal *ecal, - icalcomponent *icalcomp, - gboolean include_all_timezones) -{ - GHashTable *timezone_hash; - GString *vcal_string; - int initial_vcal_string_len; - ForeachTZIDCallbackData cbdata; - char *obj_string; - ECalPrivate *priv; - - priv = ecal->priv; - - timezone_hash = g_hash_table_new (g_str_hash, g_str_equal); - - /* Add any timezones needed to the hash. We use a hash since we only - want to add each timezone once at most. */ - cbdata.ecal = ecal; - cbdata.timezone_hash = timezone_hash; - cbdata.include_all_timezones = include_all_timezones; - cbdata.success = TRUE; - icalcomponent_foreach_tzid (icalcomp, foreach_tzid_callback, &cbdata); - if (!cbdata.success) { - g_hash_table_foreach (timezone_hash, free_timezone_string, - NULL); - return NULL; - } - - /* Create the start of a VCALENDAR, to add the VTIMEZONES to, - and remember its length so we know if any VTIMEZONEs get added. */ - vcal_string = g_string_new (NULL); - g_string_append (vcal_string, - "BEGIN:VCALENDAR\n" - "PRODID:-//Ximian//NONSGML Evolution Calendar//EN\n" - "VERSION:2.0\n" - "METHOD:PUBLISH\n"); - initial_vcal_string_len = vcal_string->len; - - /* Now concatenate all the timezone strings. This also frees the - timezone strings as it goes. */ - g_hash_table_foreach (timezone_hash, append_timezone_string, - vcal_string); - - /* Get the string for the VEVENT/VTODO. */ - obj_string = g_strdup (icalcomponent_as_ical_string (icalcomp)); - - /* If there were any timezones to send, create a complete VCALENDAR, - else just send the VEVENT/VTODO string. */ - if (!include_all_timezones - && vcal_string->len == initial_vcal_string_len) { - g_string_free (vcal_string, TRUE); - } else { - g_string_append (vcal_string, obj_string); - g_string_append (vcal_string, "END:VCALENDAR\n"); - g_free (obj_string); - obj_string = vcal_string->str; - g_string_free (vcal_string, FALSE); - } - - g_hash_table_destroy (timezone_hash); - - return obj_string; -} - -/** - * e_cal_get_component_as_string: - * @ecal: A calendar ecal. - * @icalcomp: A calendar component object. - * - * Gets a calendar component as an iCalendar string, with a toplevel - * VCALENDAR component and all VTIMEZONEs needed for the component. - * - * Return value: the component as a complete iCalendar string, or NULL on - * failure. The string should be freed after use. - **/ -char* -e_cal_get_component_as_string (ECal *ecal, icalcomponent *icalcomp) -{ - return e_cal_get_component_as_string_internal (ecal, icalcomp, TRUE); -} - -gboolean -e_cal_create_object (ECal *ecal, icalcomponent *icalcomp, char **uid, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_createObject (priv->cal, icalcomponent_as_ical_string (icalcomp), &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - if (uid) - *uid = our_op->uid; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -gboolean -e_cal_modify_object (ECal *ecal, icalcomponent *icalcomp, CalObjModType mod, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (icalcomp, E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_modifyObject (priv->cal, icalcomponent_as_ical_string (icalcomp), mod, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -gboolean -e_cal_remove_object_with_mod (ECal *ecal, const char *uid, - const char *rid, CalObjModType mod, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (uid, E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_removeObject (priv->cal, uid, rid ? rid : "", mod, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -/** - * e_cal_remove_object: - * @ecal: A calendar ecal. - * @uid: Unique identifier of the calendar component to remove. - * @error: - * - * - * Asks a calendar to remove a component. If the server is able to remove the - * component, all ecals will be notified and they will emit the "obj_removed" - * signal. - * - * Return value: an #ECalResult value indicating the result of the - * operation. - **/ -gboolean -e_cal_remove_object (ECal *ecal, const char *uid, GError **error) -{ - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (uid, E_CALENDAR_STATUS_INVALID_ARG); - - return e_cal_remove_object_with_mod (ecal, uid, NULL, CALOBJ_MOD_ALL, error); -} - -gboolean -e_cal_receive_objects (ECal *ecal, icalcomponent *icalcomp, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_receiveObjects (priv->cal, icalcomponent_as_ical_string (icalcomp), &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -gboolean -e_cal_send_objects (ECal *ecal, icalcomponent *icalcomp, GList **users, icalcomponent **modified_icalcomp, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_sendObjects (priv->cal, icalcomponent_as_ical_string (icalcomp), &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - *users = our_op->list; - if (status != E_CALENDAR_STATUS_OK) { - *modified_icalcomp = NULL; - g_list_foreach (*users, (GFunc) g_free, NULL); - *users = NULL; - } else { - *modified_icalcomp = icalparser_parse_string (our_op->string); - if (!(*modified_icalcomp)) { - status = E_CALENDAR_STATUS_INVALID_OBJECT; - g_list_foreach (*users, (GFunc) g_free, NULL); - *users = NULL; - } - } - g_free (our_op->string); - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -gboolean -e_cal_get_timezone (ECal *ecal, const char *tzid, icaltimezone **zone, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - icalcomponent *icalcomp; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (zone, E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (priv->mutex); - - /* Check for well known zones and in the cache */ - *zone = NULL; - - /* If tzid is NULL or "" we return NULL, since it is a 'local time'. */ - if (!tzid || !tzid[0]) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - *zone = NULL; - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_OK, error); - } - - /* If it is UTC, we return the special UTC timezone. */ - if (!strcmp (tzid, "UTC")) { - *zone = icaltimezone_get_utc_timezone (); - } else { - /* See if we already have it in the cache. */ - *zone = g_hash_table_lookup (priv->timezones, tzid); - } - - if (*zone) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_OK, error); - } - - /* call the backend */ - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_getTimezone (priv->cal, tzid, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - if (status != E_CALENDAR_STATUS_OK){ - icalcomp = NULL; - } else { - icalcomp = icalparser_parse_string (our_op->string); - if (!icalcomp) - status = E_CALENDAR_STATUS_INVALID_OBJECT; - } - g_free (our_op->string); - - if (!icalcomp) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); - } - - *zone = icaltimezone_new (); - if (!icaltimezone_set_component (*zone, icalcomp)) { - icaltimezone_free (*zone, 1); - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_OBJECT_NOT_FOUND, error); - } - - /* Now add it to the cache, to avoid the server call in future. */ - g_hash_table_insert (priv->timezones, icaltimezone_get_tzid (*zone), *zone); - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -/** - * e_cal_add_timezone - * @ecal: A calendar ecal. - * @izone: The timezone to add. - * @error: Placeholder for error information. - * - * Add a VTIMEZONE object to the given calendar. - * - * Returns: TRUE if successful, FALSE otherwise. - */ -gboolean -e_cal_add_timezone (ECal *ecal, icaltimezone *izone, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - const char *tzobj; - icalcomponent *icalcomp; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (izone, E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - g_mutex_lock (priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (priv->mutex); - - /* Make sure we have a valid component - UTC doesn't, nor do - * we really have to add it */ - if (izone == icaltimezone_get_utc_timezone ()) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_OK, error); - } - - icalcomp = icaltimezone_get_component (izone); - if (!icalcomp) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_INVALID_ARG, error); - } - - /* convert icaltimezone into a string */ - tzobj = icalcomponent_as_ical_string (icalcomp); - - /* call the backend */ - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_addTimezone (priv->cal, tzobj, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -/** - * e_cal_get_query: - * @ecal: A calendar ecal. - * @sexp: S-expression representing the query. - * @query: - * @error: - * - * Creates a live query object from a loaded calendar. - * - * Return value: A query object that will emit notification signals as calendar - * components are added and removed from the query in the server. - **/ -gboolean -e_cal_get_query (ECal *ecal, const char *sexp, ECalView **query, GError **error) -{ - CORBA_Environment ev; - ECalendarOp *our_op; - ECalendarStatus status; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (query, E_CALENDAR_STATUS_INVALID_ARG); - - g_mutex_lock (ecal->priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (ecal->priv->mutex); - - CORBA_exception_init (&ev); - - our_op->listener = e_cal_view_listener_new (); - GNOME_Evolution_Calendar_Cal_getQuery (ecal->priv->cal, sexp, BONOBO_OBJREF (our_op->listener), &ev); - - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - *query = our_op->query; - - bonobo_object_unref (BONOBO_OBJECT (our_op->listener)); - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - - -/* This ensures that the given timezone is on the server. We use this to pass - the default timezone to the server, so it can resolve DATE and floating - DATE-TIME values into specific times. (Most of our IDL interface uses - time_t values to pass specific times from the server to the ecal.) */ -static gboolean -e_cal_ensure_timezone_on_server (ECal *ecal, icaltimezone *zone, GError **error) -{ - ECalPrivate *priv; - char *tzid; - icaltimezone *tmp_zone; - - priv = ecal->priv; - - /* FIXME This is highly broken since there is no locking */ - - /* If the zone is NULL or UTC we don't need to do anything. */ - if (!zone) - return TRUE; - - tzid = icaltimezone_get_tzid (zone); - - if (!strcmp (tzid, "UTC")) - return TRUE; - - /* See if we already have it in the cache. If we do, it must be on - the server already. */ - tmp_zone = g_hash_table_lookup (priv->timezones, tzid); - if (tmp_zone) - return TRUE; - - /* Now we have to send it to the server, in case it doesn't already - have it. */ - return e_cal_add_timezone (ecal, zone, error); -} - -gboolean -e_cal_set_default_timezone (ECal *ecal, icaltimezone *zone, GError **error) -{ - ECalPrivate *priv; - CORBA_Environment ev; - ECalendarStatus status; - ECalendarOp *our_op; - const char *tzid; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - e_return_error_if_fail (zone, E_CALENDAR_STATUS_INVALID_ARG); - - priv = ecal->priv; - - /* Make sure the server has the VTIMEZONE data. */ - if (!e_cal_ensure_timezone_on_server (ecal, zone, error)) - return FALSE; - - g_mutex_lock (priv->mutex); - - if (ecal->priv->load_state != E_CAL_LOAD_LOADED) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_URI_NOT_LOADED, error); - } - - if (ecal->priv->current_op != NULL) { - g_mutex_unlock (ecal->priv->mutex); - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_BUSY, error); - } - - our_op = e_calendar_new_op (ecal); - - g_mutex_lock (our_op->mutex); - - g_mutex_unlock (priv->mutex); - - /* FIXME Adding it to the server to change the tzid */ - tzid = icaltimezone_get_tzid (zone); - - /* call the backend */ - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_Cal_setDefaultTimezone (priv->cal, tzid, &ev); - if (BONOBO_EX (&ev)) { - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - CORBA_exception_free (&ev); - - g_warning (G_STRLOC ": Unable to contact backend"); - - E_CALENDAR_CHECK_STATUS (E_CALENDAR_STATUS_CORBA_EXCEPTION, error); - } - - CORBA_exception_free (&ev); - - /* wait for something to happen (both cancellation and a - successful response will notity us via our cv */ - g_cond_wait (our_op->cond, our_op->mutex); - - status = our_op->status; - - /* set the default timezone internally if successful */ - if (our_op->status == E_CALENDAR_STATUS_OK) { - g_mutex_lock (priv->mutex); - priv->default_zone = zone; - g_mutex_unlock (priv->mutex); - } - - e_calendar_remove_op (ecal, our_op); - g_mutex_unlock (our_op->mutex); - e_calendar_free_op (our_op); - - E_CALENDAR_CHECK_STATUS (status, error); -} - -/** - * e_cal_get_error_message - * @status: A status code. - * - * Get an error message for the given status code. - * - * Returns: the error message. - */ -const char * -e_cal_get_error_message (ECalendarStatus status) -{ - switch (status) { - case E_CALENDAR_STATUS_INVALID_ARG : - return _("Invalid argument"); - case E_CALENDAR_STATUS_BUSY : - return _("Backend is busy"); - case E_CALENDAR_STATUS_REPOSITORY_OFFLINE : - return _("Repository is offline"); - case E_CALENDAR_STATUS_NO_SUCH_CALENDAR : - return _("No such calendar"); - case E_CALENDAR_STATUS_OBJECT_NOT_FOUND : - return _("Object not found"); - case E_CALENDAR_STATUS_INVALID_OBJECT : - return _("Invalid object"); - case E_CALENDAR_STATUS_URI_NOT_LOADED : - return _("URI not loaded"); - case E_CALENDAR_STATUS_URI_ALREADY_LOADED : - return _("URI already loaded"); - case E_CALENDAR_STATUS_PERMISSION_DENIED : - return _("Permission denied"); - case E_CALENDAR_STATUS_OBJECT_ID_ALREADY_EXISTS : - return _("Object ID already exists"); - case E_CALENDAR_STATUS_PROTOCOL_NOT_SUPPORTED : - return _("Protocol not supported"); - case E_CALENDAR_STATUS_CANCELLED : - return _("Operation has been cancelled"); - case E_CALENDAR_STATUS_COULD_NOT_CANCEL : - return _("Could not cancel operation"); - case E_CALENDAR_STATUS_AUTHENTICATION_FAILED : - return _("Authentication failed"); - case E_CALENDAR_STATUS_AUTHENTICATION_REQUIRED : - return _("Authentication required"); - case E_CALENDAR_STATUS_UNABLE_TO_BOOK : - return _("Unable to book time"); - case E_CALENDAR_STATUS_CORBA_EXCEPTION : - return _("A CORBA exception has occurred"); - case E_CALENDAR_STATUS_OTHER_ERROR : - return _("Unknown error"); - case E_CALENDAR_STATUS_OK : - return _("No error"); - } - - return NULL; -} - -static gboolean -get_default (ECal **ecal, ESourceList *sources, ECalSourceType type, ECalAuthFunc func, gpointer data, GError **error) -{ - GSList *g; - GError *err = NULL; - ESource *default_source = NULL; - gboolean rv = TRUE; - - for (g = e_source_list_peek_groups (sources); g; g = g->next) { - ESourceGroup *group = E_SOURCE_GROUP (g->data); - GSList *s; - for (s = e_source_group_peek_sources (group); s; s = s->next) { - ESource *source = E_SOURCE (s->data); - - if (e_source_get_property (source, "default")) { - default_source = source; - break; - } - } - - if (default_source) - break; - } - - if (default_source) { - *ecal = e_cal_new (default_source, type); - if (!*ecal) { - g_propagate_error (error, err); - rv = FALSE; - goto done; - } - - e_cal_set_auth_func (*ecal, func, data); - if (!e_cal_open (*ecal, TRUE, &err)) { - g_propagate_error (error, err); - rv = FALSE; - goto done; - } - } else { - switch (type) { - case E_CAL_SOURCE_TYPE_EVENT: - *ecal = e_cal_new_system_calendar (); - break; - case E_CAL_SOURCE_TYPE_TODO: - *ecal = e_cal_new_system_tasks (); - break; - default: - break; - } - - if (!*ecal) { - g_propagate_error (error, err); - rv = FALSE; - goto done; - } - - e_cal_set_auth_func (*ecal, func, data); - if (!e_cal_open (*ecal, TRUE, &err)) { - g_propagate_error (error, err); - rv = FALSE; - goto done; - } - } - - done: - if (!rv && *ecal) { - g_object_unref (*ecal); - *ecal = NULL; - } - g_object_unref (sources); - - return rv; -} - -gboolean -e_cal_open_default (ECal **ecal, ECalSourceType type, ECalAuthFunc func, gpointer data, GError **error) -{ - ESourceList *sources; - GError *err = NULL; - - if (!e_cal_get_sources (&sources, type, &err)) { - g_propagate_error (error, err); - return FALSE; - } - - return get_default (ecal, sources, type, func, data, error); -} - -gboolean -e_cal_set_default (ECal *ecal, GError **error) -{ - ESource *source; - - e_return_error_if_fail (ecal && E_IS_CAL (ecal), E_CALENDAR_STATUS_INVALID_ARG); - - source = e_cal_get_source (ecal); - if (!source) { - /* XXX gerror */ - return FALSE; - } - - return e_cal_set_default_source (source, ecal->priv->type, error); -} - -static gboolean -set_default_source (ESourceList *sources, ESource *source, GError **error) -{ - const char *uid; - GError *err = NULL; - GSList *g; - - uid = e_source_peek_uid (source); - - /* make sure the source is actually in the ESourceList. if - it's not we don't bother adding it, just return an error */ - source = e_source_list_peek_source_by_uid (sources, uid); - if (!source) { - /* XXX gerror */ - g_object_unref (sources); - return FALSE; - } - - /* loop over all the sources clearing out any "default" - properties we find */ - for (g = e_source_list_peek_groups (sources); g; g = g->next) { - GSList *s; - for (s = e_source_group_peek_sources (E_SOURCE_GROUP (g->data)); - s; s = s->next) { - e_source_set_property (E_SOURCE (s->data), "default", NULL); - } - } - - /* set the "default" property on the source */ - e_source_set_property (source, "default", "true"); - - if (!e_source_list_sync (sources, &err)) { - g_propagate_error (error, err); - return FALSE; - } - - return TRUE; -} - -gboolean -e_cal_set_default_source (ESource *source, ECalSourceType type, GError **error) -{ - ESourceList *sources; - GError *err = NULL; - - if (!e_cal_get_sources (&sources, type, &err)) { - g_propagate_error (error, err); - return FALSE; - } - - return set_default_source (sources, source, error); -} - -static gboolean -get_sources (ESourceList **sources, const char *key, GError **error) -{ - GConfClient *gconf = gconf_client_get_default(); - - *sources = e_source_list_new_for_gconf (gconf, key); - g_object_unref (gconf); - - return TRUE; -} - -gboolean -e_cal_get_sources (ESourceList **sources, ECalSourceType type, GError **error) -{ - switch (type) { - case E_CAL_SOURCE_TYPE_EVENT: - return get_sources (sources, "/apps/evolution/calendar/sources", error); - break; - case E_CAL_SOURCE_TYPE_TODO: - return get_sources (sources, "/apps/evolution/tasks/sources", error); - break; - default: - /* FIXME Fill in error */ - return FALSE; - } - - /* FIXME Fill in error */ - return FALSE; -} diff --git a/calendar/libecal/e-cal.h b/calendar/libecal/e-cal.h deleted file mode 100644 index 090883dbe..000000000 --- a/calendar/libecal/e-cal.h +++ /dev/null @@ -1,201 +0,0 @@ -/* Evolution calendar ecal - * - * Copyright (C) 2001 Ximian, Inc. - * - * Authors: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_H -#define E_CAL_H - -#include <glib-object.h> -#include <libedataserver/e-source-list.h> -#include <libedataserver/e-source.h> -#include <libecal/e-cal-recur.h> -#include <libecal/e-cal-util.h> -#include <libecal/e-cal-view.h> -#include <libecal/e-cal-types.h> - -G_BEGIN_DECLS - - - -#define E_TYPE_CAL (e_cal_get_type ()) -#define E_CAL(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL, ECal)) -#define E_CAL_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL, ECalClass)) -#define E_IS_CAL(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL)) -#define E_IS_CAL_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL)) - -#define E_CAL_SET_MODE_STATUS_ENUM_TYPE (e_cal_set_mode_status_enum_get_type ()) -#define CAL_MODE_ENUM_TYPE (cal_mode_enum_get_type ()) - -typedef struct _ECal ECal; -typedef struct _ECalClass ECalClass; -typedef struct _ECalPrivate ECalPrivate; - -typedef enum { - E_CAL_SOURCE_TYPE_EVENT, - E_CAL_SOURCE_TYPE_TODO, - E_CAL_SOURCE_TYPE_JOURNAL, - E_CAL_SOURCE_TYPE_LAST -} ECalSourceType; - -/* Set mode status for the e_cal_set_mode function */ -typedef enum { - E_CAL_SET_MODE_SUCCESS, - E_CAL_SET_MODE_ERROR, - E_CAL_SET_MODE_NOT_SUPPORTED -} ECalSetModeStatus; - -/* Whether the ecal is not loaded, is being loaded, or is already loaded */ -typedef enum { - E_CAL_LOAD_NOT_LOADED, - E_CAL_LOAD_AUTHENTICATING, - E_CAL_LOAD_LOADING, - E_CAL_LOAD_LOADED -} ECalLoadState; - -struct _ECal { - GObject object; - - /*< private >*/ - ECalPrivate *priv; -}; - -struct _ECalClass { - GObjectClass parent_class; - - /* Notification signals */ - - void (* cal_opened) (ECal *ecal, ECalendarStatus status); - void (* cal_set_mode) (ECal *ecal, ECalSetModeStatus status, CalMode mode); - - void (* categories_changed) (ECal *ecal, GPtrArray *categories); - - void (* backend_error) (ECal *ecal, const char *message); - void (* backend_died) (ECal *ecal); -}; - -typedef char * (* ECalAuthFunc) (ECal *ecal, - const char *prompt, - const char *key, - gpointer user_data); - -GType e_cal_get_type (void); - -GType e_cal_open_status_enum_get_type (void); -GType e_cal_set_mode_status_enum_get_type (void); -GType cal_mode_enum_get_type (void); - -ECal *e_cal_new (ESource *source, ECalSourceType type); -ECal *e_cal_new_from_uri (const gchar *uri, ECalSourceType type); -ECal *e_cal_new_system_calendar (void); -ECal *e_cal_new_system_tasks (void); - -void e_cal_set_auth_func (ECal *ecal, ECalAuthFunc func, gpointer data); - -gboolean e_cal_open (ECal *ecal, gboolean only_if_exists, GError **error); -void e_cal_open_async (ECal *ecal, gboolean only_if_exists); -gboolean e_cal_remove (ECal *ecal, GError **error); - -GList *e_cal_uri_list (ECal *ecal, CalMode mode); - -ECalSourceType e_cal_get_source_type (ECal *ecal); -ECalLoadState e_cal_get_load_state (ECal *ecal); - -ESource *e_cal_get_source (ECal *ecal); -const char *e_cal_get_uri (ECal *ecal); - -gboolean e_cal_is_read_only (ECal *ecal, gboolean *read_only, GError **error); -gboolean e_cal_get_cal_address (ECal *ecal, char **cal_address, GError **error); -gboolean e_cal_get_alarm_email_address (ECal *ecal, char **alarm_address, GError **error); -gboolean e_cal_get_ldap_attribute (ECal *ecal, char **ldap_attribute, GError **error); - -gboolean e_cal_get_one_alarm_only (ECal *ecal); -gboolean e_cal_get_organizer_must_attend (ECal *ecal); -gboolean e_cal_get_save_schedules (ECal *ecal); -gboolean e_cal_get_static_capability (ECal *ecal, const char *cap); - -gboolean e_cal_set_mode (ECal *ecal, CalMode mode); - -gboolean e_cal_get_default_object (ECal *ecal, - icalcomponent **icalcomp, GError **error); - -gboolean e_cal_get_object (ECal *ecal, - const char *uid, - const char *rid, - icalcomponent **icalcomp, - GError **error); - -gboolean e_cal_get_changes (ECal *ecal, const char *change_id, GList **changes, GError **error); -void e_cal_free_change_list (GList *list); - -gboolean e_cal_get_object_list (ECal *ecal, const char *query, GList **objects, GError **error); -gboolean e_cal_get_object_list_as_comp (ECal *ecal, const char *query, GList **objects, GError **error); -void e_cal_free_object_list (GList *objects); - -gboolean e_cal_get_free_busy (ECal *ecal, GList *users, time_t start, time_t end, - GList **freebusy, GError **error); - -void e_cal_generate_instances (ECal *ecal, time_t start, time_t end, - ECalRecurInstanceFn cb, gpointer cb_data); - -GSList *e_cal_get_alarms_in_range (ECal *ecal, time_t start, time_t end); - -void e_cal_free_alarms (GSList *comp_alarms); - -gboolean e_cal_get_alarms_for_object (ECal *ecal, const char *uid, - time_t start, time_t end, - ECalComponentAlarms **alarms); - -gboolean e_cal_create_object (ECal *ecal, icalcomponent *icalcomp, char **uid, GError **error); -gboolean e_cal_modify_object (ECal *ecal, icalcomponent *icalcomp, CalObjModType mod, GError **error); -gboolean e_cal_remove_object (ECal *ecal, const char *uid, GError **error); -gboolean e_cal_remove_object_with_mod (ECal *ecal, const char *uid, const char *rid, CalObjModType mod, GError **error); - -gboolean e_cal_discard_alarm (ECal *ecal, ECalComponent *comp, const char *auid, GError **error); - -gboolean e_cal_receive_objects (ECal *ecal, icalcomponent *icalcomp, GError **error); -gboolean e_cal_send_objects (ECal *ecal, icalcomponent *icalcomp, GList **users, icalcomponent **modified_icalcomp, GError **error); - -gboolean e_cal_get_timezone (ECal *ecal, const char *tzid, icaltimezone **zone, GError **error); -gboolean e_cal_add_timezone (ECal *ecal, icaltimezone *izone, GError **error); -/* Sets the default timezone to use to resolve DATE and floating DATE-TIME - values. This will typically be from the user's timezone setting. Call this - before using any other functions. It will pass the default timezone on to - the server. Returns TRUE on success. */ -gboolean e_cal_set_default_timezone (ECal *ecal, icaltimezone *zone, GError **error); - -gboolean e_cal_get_query (ECal *ecal, const char *sexp, ECalView **query, GError **error); - -/* Resolves TZIDs for the recurrence generator. */ -icaltimezone *e_cal_resolve_tzid_cb (const char *tzid, gpointer data); - -/* Returns a complete VCALENDAR for a VEVENT/VTODO including all VTIMEZONEs - used by the component. It also includes a 'METHOD:PUBLISH' property. */ -char* e_cal_get_component_as_string (ECal *ecal, icalcomponent *icalcomp); - -const char * e_cal_get_error_message (ECalendarStatus status); - -/* Calendar/Tasks Discovery */ -gboolean e_cal_open_default (ECal **ecal, ECalSourceType type, ECalAuthFunc func, gpointer data, GError **error); -gboolean e_cal_set_default (ECal *ecal, GError **error); -gboolean e_cal_set_default_source (ESource *source, ECalSourceType type, GError **error); -gboolean e_cal_get_sources (ESourceList **sources, ECalSourceType type, GError **error); - -G_END_DECLS - -#endif diff --git a/calendar/libecal/libecal-1.0.pc.in b/calendar/libecal/libecal-1.0.pc.in deleted file mode 100644 index 8f57f6ced..000000000 --- a/calendar/libecal/libecal-1.0.pc.in +++ /dev/null @@ -1,16 +0,0 @@ -prefix=@prefix@ -exec_prefix=@exec_prefix@ -libdir=@libdir@ -includedir=@includedir@ - -idldir=@idldir@ -IDL_INCLUDES=-I ${idldir} @IDL_INCLUDES@ - -privincludedir=@privincludedir@ - -Name: libedatacal -Description: Backend library for evolution calendars -Version: @VERSION@ -Requires: libgnome-2.0 libbonobo-2.0 >= @LIBBONOBO_REQUIRED@ libedataserver-1.0 -Libs: -L${libdir} -lecal -Cflags: -I${privincludedir} diff --git a/calendar/libedata-cal/.cvsignore b/calendar/libedata-cal/.cvsignore deleted file mode 100644 index 5534bffaa..000000000 --- a/calendar/libedata-cal/.cvsignore +++ /dev/null @@ -1,7 +0,0 @@ -Makefile -Makefile.in -Evolution-DataServer-Calendar-common.c -Evolution-DataServer-Calendar-skels.c -Evolution-DataServer-Calendar-stubs.c -Evolution-DataServer-Calendar.h -libedata-cal-1.0.pc
\ No newline at end of file diff --git a/calendar/libedata-cal/Makefile.am b/calendar/libedata-cal/Makefile.am deleted file mode 100644 index dd87cb6a3..000000000 --- a/calendar/libedata-cal/Makefile.am +++ /dev/null @@ -1,80 +0,0 @@ -INCLUDES = \ - -DG_LOG_DOMAIN=\"libedata-cal\" \ - -I$(top_srcdir) \ - -I$(top_builddir) \ - -I$(top_srcdir)/calendar \ - -I$(top_builddir)/calendar \ - -I$(top_srcdir)/calendar/libical/src \ - -I$(top_builddir)/calendar/libical/src \ - -I$(top_srcdir)/calendar/libical/src/libical \ - -I$(top_builddir)/calendar/libical/src/libical \ - $(EVOLUTION_CALENDAR_CFLAGS) - -CORBA_GENERATED_H = \ - Evolution-DataServer-Calendar.h - -CORBA_GENERATED_C = \ - Evolution-DataServer-Calendar-common.c \ - Evolution-DataServer-Calendar-skels.c \ - Evolution-DataServer-Calendar-stubs.c - -CORBA_GENERATED = $(CORBA_GENERATED_H) $(CORBA_GENERATED_C) - -idls = \ - $(srcdir)/../idl/Evolution-DataServer-Calendar.idl - -idl_flags = -I $(srcdir) $(IDL_INCLUDES) - -$(CORBA_GENERATED_H): $(idls) - $(ORBIT_IDL) $(idl_flags) $(srcdir)/../idl/Evolution-DataServer-Calendar.idl - -$(CORBA_GENERATED_C): $(CORBA_GENERATED_H) - -# The libraray -lib_LTLIBRARIES = libedata-cal.la - -libedata_cal_la_SOURCES = \ - $(CORBA_GENERATED_C) \ - e-cal-backend.c \ - e-cal-backend-cache.c \ - e-cal-backend-sexp.c \ - e-cal-backend-sync.c \ - e-cal-backend-util.c \ - e-data-cal.c \ - e-data-cal-factory.c \ - e-data-cal-view.c - -libedata_cal_la_LIBADD = \ - $(EVOLUTION_CALENDAR_LIBS) \ - $(top_builddir)/calendar/libecal/libecal.la \ - $(top_builddir)/libedataserver/libedataserver.la - -libedata_cal_la_LDFLAGS = \ - -version-info $(LIBEDATACAL_CURRENT):$(LIBEDATACAL_REVISION):$(LIBEDATACAL_AGE) - -libedata_calincludedir = $(privincludedir)/libedata-cal - -libedata_calinclude_HEADERS = \ - $(CORBA_GENERATED_H) \ - e-cal-backend.h \ - e-cal-backend-cache.h \ - e-cal-backend-sync.h \ - e-cal-backend-util.h \ - e-cal-backend-sexp.h \ - e-data-cal.h \ - e-data-cal-common.h \ - e-data-cal-factory.h \ - e-data-cal-view.h - -pkgconfigdir = $(libdir)/pkgconfig -pkgconfig_DATA = libedata-cal-1.0.pc - -BUILT_SOURCES = $(CORBA_GENERATED) -CLEANFILES = $(BUILT_SOURCES) - -EXTRA_DIST = \ - $(pkgconfig_DATA:.pc=.pc.in) - -dist-hook: - cd $(distdir); rm -f $(BUILT_SOURCES) - diff --git a/calendar/libedata-cal/e-cal-backend-cache.c b/calendar/libedata-cal/e-cal-backend-cache.c deleted file mode 100644 index 4595c7a23..000000000 --- a/calendar/libedata-cal/e-cal-backend-cache.c +++ /dev/null @@ -1,584 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* Evolution calendar - generic backend class - * - * Copyright (C) 2003 Novell, Inc. - * - * Authors: Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <string.h> -#include <libecal/e-cal-util.h> -#include "e-cal-backend-cache.h" - -struct _ECalBackendCachePrivate { - char *uri; - GHashTable *timezones; -}; - -/* Property IDs */ -enum { - PROP_0, - PROP_URI -}; - -static GObjectClass *parent_class = NULL; - -static char * -get_filename_from_uri (const char *uri) -{ - char *mangled_uri, *filename; - int i; - - /* mangle the URI to not contain invalid characters */ - mangled_uri = g_strdup (uri); - for (i = 0; i < strlen (mangled_uri); i++) { - switch (mangled_uri[i]) { - case ':' : - case '/' : - mangled_uri[i] = '_'; - } - } - - /* generate the file name */ - filename = g_build_filename (g_get_home_dir (), ".evolution/cache/calendar", - mangled_uri, "cache.xml", NULL); - - /* free memory */ - g_free (mangled_uri); - - return filename; -} - -static void -e_cal_backend_cache_set_property (GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) -{ - ECalBackendCache *cache; - ECalBackendCachePrivate *priv; - char *cache_file; - - cache = E_CAL_BACKEND_CACHE (object); - priv = cache->priv; - - switch (property_id) { - case PROP_URI : - cache_file = get_filename_from_uri (g_value_get_string (value)); - if (!cache_file) - break; - - g_object_set (G_OBJECT (cache), "filename", cache_file, NULL); - g_free (cache_file); - - if (priv->uri) - g_free (priv->uri); - priv->uri = g_value_dup_string (value); - break; - default : - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); - } -} - -static void -e_cal_backend_cache_get_property (GObject *object, guint property_id, GValue *value, GParamSpec *pspec) -{ - ECalBackendCache *cache; - ECalBackendCachePrivate *priv; - - cache = E_CAL_BACKEND_CACHE (object); - priv = cache->priv; - - switch (property_id) { - case PROP_URI : - g_value_set_string (value, priv->uri); - break; - default : - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); - } -} - -static void -free_timezone_hash (gpointer key, gpointer value, gpointer user_data) -{ - g_free (key); - icaltimezone_free (value, 1); -} - -static void -e_cal_backend_cache_finalize (GObject *object) -{ - ECalBackendCache *cache; - ECalBackendCachePrivate *priv; - - cache = E_CAL_BACKEND_CACHE (object); - priv = cache->priv; - - if (priv) { - if (priv->uri) { - g_free (priv->uri); - priv->uri = NULL; - } - - if (priv->timezones) { - g_hash_table_foreach (priv->timezones, (GHFunc) free_timezone_hash, NULL); - g_hash_table_destroy (priv->timezones); - priv->timezones = NULL; - } - - g_free (priv); - cache->priv = NULL; - } - - parent_class->finalize (object); -} - -static GObject * -e_cal_backend_cache_constructor (GType type, - guint n_construct_properties, - GObjectConstructParam *construct_properties) -{ - GObject *obj; - const char *uri; - ECalBackendCacheClass *klass; - GObjectClass *parent_class; - - /* Invoke parent constructor. */ - klass = E_CAL_BACKEND_CACHE_CLASS (g_type_class_peek (E_TYPE_CAL_BACKEND_CACHE)); - parent_class = G_OBJECT_CLASS (g_type_class_peek_parent (klass)); - obj = parent_class->constructor (type, - n_construct_properties, - construct_properties); - - /* extract uid */ - if (!g_ascii_strcasecmp ( g_param_spec_get_name (construct_properties->pspec), "uri")) { - uri = g_value_get_string (construct_properties->value); - g_object_set (obj, "filename", get_filename_from_uri (uri), NULL); - } - - return obj; -} - -static void -e_cal_backend_cache_class_init (ECalBackendCacheClass *klass) -{ - GObjectClass *object_class; - - parent_class = g_type_class_peek_parent (klass); - - object_class = G_OBJECT_CLASS (klass); - object_class->finalize = e_cal_backend_cache_finalize; - object_class->set_property = e_cal_backend_cache_set_property; - object_class->get_property = e_cal_backend_cache_get_property; - - object_class->constructor = e_cal_backend_cache_constructor; - g_object_class_install_property (object_class, PROP_URI, - g_param_spec_string ("uri", NULL, NULL, "", - G_PARAM_READABLE | G_PARAM_WRITABLE - | G_PARAM_CONSTRUCT_ONLY)); -} - -static void -e_cal_backend_cache_init (ECalBackendCache *cache) -{ - ECalBackendCachePrivate *priv; - - priv = g_new0 (ECalBackendCachePrivate, 1); - priv->timezones = g_hash_table_new (g_str_hash, g_str_equal); - - cache->priv = priv; - -} - -/** - * e_cal_backend_cache_get_type: - * @void: - * - * Registers the #ECalBackendCache class if necessary, and returns the type ID - * associated to it. - * - * Return value: The type ID of the #ECalBackendCache class. - **/ -GType -e_cal_backend_cache_get_type (void) -{ - static GType type = 0; - - if (!type) { - static GTypeInfo info = { - sizeof (ECalBackendCacheClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_backend_cache_class_init, - NULL, NULL, - sizeof (ECalBackendCache), - 0, - (GInstanceInitFunc) e_cal_backend_cache_init, - }; - type = g_type_register_static (E_TYPE_FILE_CACHE, "ECalBackendCache", &info, 0); - } - - return type; -} - -/** - * e_cal_backend_cache_new - * @uri: URI of the backend to be cached. - * - * Creates a new #ECalBackendCache object, which implements a cache of - * calendar/tasks objects, very useful for remote backends. - * - * Return value: The newly created object. - */ -ECalBackendCache * -e_cal_backend_cache_new (const char *uri) -{ - ECalBackendCache *cache; - - cache = g_object_new (E_TYPE_CAL_BACKEND_CACHE, "uri", uri, NULL); - - return cache; -} - -static char * -get_key (const char *uid, const char *rid) -{ - GString *real_key; - char *retval; - - real_key = g_string_new (uid); - if (rid && *rid) { - real_key = g_string_append (real_key, "@"); - real_key = g_string_append (real_key, rid); - } - - retval = real_key->str; - g_string_free (real_key, FALSE); - - return retval; -} - -/** - * e_cal_backend_cache_get_component: - * @cache: A %ECalBackendCache object. - * @uid: The UID of the component to retrieve. - * @rid: Recurrence ID of the specific detached recurrence to retrieve, - * or NULL if the whole object is to be retrieved. - * - * Gets a component from the %ECalBackendCache object. - * - * Return value: The %ECalComponent representing the component found, - * or %NULL if it was not found in the cache. - */ -ECalComponent * -e_cal_backend_cache_get_component (ECalBackendCache *cache, const char *uid, const char *rid) -{ - char *real_key; - const char *comp_str; - icalcomponent *icalcomp; - ECalComponent *comp = NULL; - - g_return_val_if_fail (E_IS_CAL_BACKEND_CACHE (cache), NULL); - g_return_val_if_fail (uid != NULL, NULL); - - real_key = get_key (uid, rid); - - comp_str = e_file_cache_get_object (E_FILE_CACHE (cache), real_key); - if (comp_str) { - icalcomp = icalparser_parse_string (comp_str); - if (icalcomp) { - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, icalcomp); - } - } - - /* free memory */ - g_free (real_key); - - return comp; -} - -/** - * e_cal_backend_cache_put_component: - */ -gboolean -e_cal_backend_cache_put_component (ECalBackendCache *cache, - ECalComponent *comp) -{ - char *real_key, *uid, *comp_str; - const char *rid; - gboolean retval; - ECalBackendCachePrivate *priv; - - g_return_val_if_fail (E_IS_CAL_BACKEND_CACHE (cache), FALSE); - g_return_val_if_fail (E_IS_CAL_COMPONENT (comp), FALSE); - - priv = cache->priv; - - e_cal_component_get_uid (comp, (const char **) &uid); - if (e_cal_component_is_instance (comp)) { - rid = e_cal_component_get_recurid_as_string (comp); - } else - rid = NULL; - - comp_str = e_cal_component_get_as_string (comp); - real_key = get_key (uid, rid); - - if (e_file_cache_get_object (E_FILE_CACHE (cache), real_key)) - retval = e_file_cache_replace_object (E_FILE_CACHE (cache), real_key, comp_str); - else - retval = e_file_cache_add_object (E_FILE_CACHE (cache), real_key, comp_str); - - g_free (real_key); - g_free (comp_str); - - return retval; -} - -/** - * e_cal_backend_cache_remove_component: - */ -gboolean -e_cal_backend_cache_remove_component (ECalBackendCache *cache, - const char *uid, - const char *rid) -{ - char *real_key; - gboolean retval; - ECalBackendCachePrivate *priv; - - g_return_val_if_fail (E_IS_CAL_BACKEND_CACHE (cache), FALSE); - g_return_val_if_fail (uid != NULL, FALSE); - - priv = cache->priv; - - real_key = get_key (uid, rid); - if (!e_file_cache_get_object (E_FILE_CACHE (cache), real_key)) { - g_free (real_key); - return FALSE; - } - - retval = e_file_cache_remove_object (E_FILE_CACHE (cache), real_key); - g_free (real_key); - - return retval; -} - -GList * -e_cal_backend_cache_get_components (ECalBackendCache *cache) -{ - char *comp_str; - GSList *l; - GList *list = NULL; - icalcomponent *icalcomp; - ECalComponent *comp = NULL; - - /* return null if cache is not a valid Backend Cache. */ - g_return_val_if_fail (E_IS_CAL_BACKEND_CACHE (cache), NULL); - l = e_file_cache_get_objects (E_FILE_CACHE (cache)); - if (!l) - return NULL; - for ( ; l != NULL; l = g_slist_next (l)) { - comp_str = l->data; - if (comp_str) { - icalcomp = icalparser_parse_string (comp_str); - if (icalcomp) { - icalcomponent_kind kind; - - kind = icalcomponent_isa (icalcomp); - if (kind == ICAL_VEVENT_COMPONENT || kind == ICAL_VTODO_COMPONENT) { - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, icalcomp); - list = g_list_append (list, comp); - } else - icalcomponent_free (icalcomp); - } - } - - } - - return list; -} - -const icaltimezone * -e_cal_backend_cache_get_timezone (ECalBackendCache *cache, const char *tzid) -{ - icaltimezone *zone; - const char *comp_str; - ECalBackendCachePrivate *priv; - - g_return_val_if_fail (E_IS_CAL_BACKEND_CACHE (cache), NULL); - g_return_val_if_fail (tzid != NULL, NULL); - - priv = cache->priv; - - /* we first look for the timezone in the timezones hash table */ - zone = g_hash_table_lookup (priv->timezones, tzid); - if (zone) - return (const icaltimezone *) zone; - - /* if not found look for the timezone in the cache */ - comp_str = e_file_cache_get_object (E_FILE_CACHE (cache), tzid); - if (comp_str) { - icalcomponent *icalcomp; - - icalcomp = icalparser_parse_string (comp_str); - if (icalcomp) { - zone = icaltimezone_new (); - if (icaltimezone_set_component (zone, icalcomp) == 1) - g_hash_table_insert (priv->timezones, g_strdup (tzid), zone); - else { - icalcomponent_free (icalcomp); - icaltimezone_free (zone, 1); - } - } - } - - return (const icaltimezone *) zone; -} - -gboolean -e_cal_backend_cache_put_timezone (ECalBackendCache *cache, const icaltimezone *zone) -{ - ECalBackendCachePrivate *priv; - gpointer orig_key, orig_value; - icaltimezone *new_zone; - icalcomponent *icalcomp; - gboolean retval; - - g_return_val_if_fail (E_IS_CAL_BACKEND_CACHE (cache), FALSE); - g_return_val_if_fail (zone != NULL, FALSE); - - priv = cache->priv; - - /* add the timezone to the cache file */ - icalcomp = icaltimezone_get_component (zone); - if (!icalcomp) - return FALSE; - - if (e_file_cache_get_object (E_FILE_CACHE (cache), icaltimezone_get_tzid (zone))) { - retval = e_file_cache_replace_object (E_FILE_CACHE (cache), - icaltimezone_get_tzid (zone), - icalcomponent_as_ical_string (icalcomp)); - } else { - retval = e_file_cache_add_object (E_FILE_CACHE (cache), - icaltimezone_get_tzid (zone), - icalcomponent_as_ical_string (icalcomp)); - } - - if (!retval) - return FALSE; - - /* check if the timezone already exists */ - if (g_hash_table_lookup_extended (priv->timezones, icaltimezone_get_tzid (zone), - &orig_key, &orig_value)) { - /* remove the previous timezone */ - g_hash_table_remove (priv->timezones, orig_key); - g_free (orig_key); - icaltimezone_free (orig_value, 1); - } - - /* add the timezone to the hash table */ - new_zone = icaltimezone_new (); - icaltimezone_set_component (new_zone, icalcomponent_new_clone (icalcomp)); - g_hash_table_insert (priv->timezones, g_strdup (icaltimezone_get_tzid (new_zone)), new_zone); - - return TRUE; -} - -gboolean -e_cal_backend_cache_put_default_timezone (ECalBackendCache *cache, icaltimezone *default_zone) -{ - ECalBackendCachePrivate *priv; - icalcomponent *icalcomp; - gboolean retval; - - g_return_val_if_fail (E_IS_CAL_BACKEND_CACHE (cache), FALSE); - - priv = cache->priv; - - /* add the timezone to the cache file */ - icalcomp = icaltimezone_get_component (default_zone); - if (!icalcomp) - return FALSE; - - if (e_file_cache_get_object (E_FILE_CACHE (cache), "default_zone")) { - retval = e_file_cache_replace_object (E_FILE_CACHE (cache), "default_zone", - icalcomponent_as_ical_string (icalcomp)); - } else { - retval = e_file_cache_add_object (E_FILE_CACHE (cache), - "default_zone", - icalcomponent_as_ical_string (icalcomp)); - } - - if (!retval) - return FALSE; - - return TRUE; - -} - -icaltimezone * -e_cal_backend_cache_get_default_timezone (ECalBackendCache *cache) -{ - icaltimezone *zone; - const char *comp_str; - ECalBackendCachePrivate *priv; - - g_return_val_if_fail (E_IS_CAL_BACKEND_CACHE (cache), NULL); - - priv = cache->priv; - - /* look for the timezone in the cache */ - comp_str = e_file_cache_get_object (E_FILE_CACHE (cache), "default_zone"); - if (comp_str) { - icalcomponent *icalcomp; - - icalcomp = icalparser_parse_string (comp_str); - if (icalcomp) { - zone = icaltimezone_new (); - if (icaltimezone_set_component (zone, icalcomp) == 1) { - return zone; - } else { - icalcomponent_free (icalcomp); - icaltimezone_free (zone, 1); - } - } - } - - return NULL; -} - -gboolean -e_cal_backend_cache_remove_timezone (ECalBackendCache *cache, const char *tzid) -{ - gpointer orig_key, orig_value; - ECalBackendCachePrivate *priv; - - g_return_val_if_fail (E_IS_CAL_BACKEND_CACHE (cache), FALSE); - g_return_val_if_fail (tzid != NULL, FALSE); - - priv = cache->priv; - - if (g_hash_table_lookup_extended (priv->timezones, tzid, &orig_key, &orig_value)) { - g_hash_table_remove (priv->timezones, tzid); - g_free (orig_key); - icaltimezone_free (orig_value, 1); - } - - return e_file_cache_remove_object (E_FILE_CACHE (cache), tzid); -} diff --git a/calendar/libedata-cal/e-cal-backend-cache.h b/calendar/libedata-cal/e-cal-backend-cache.h deleted file mode 100644 index 3950781af..000000000 --- a/calendar/libedata-cal/e-cal-backend-cache.h +++ /dev/null @@ -1,69 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* Evolution calendar - generic backend class - * - * Copyright (C) 2003 Novell, Inc. - * - * Authors: Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_BACKEND_CACHE_H -#define E_CAL_BACKEND_CACHE_H - -#include <libedataserver/e-file-cache.h> -#include <libecal/e-cal-component.h> - -G_BEGIN_DECLS - -#define E_TYPE_CAL_BACKEND_CACHE (e_cal_backend_cache_get_type ()) -#define E_CAL_BACKEND_CACHE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_BACKEND_CACHE, ECalBackendCache)) -#define E_CAL_BACKEND_CACHE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_BACKEND_CACHE, ECalBackendCacheClass)) -#define E_IS_CAL_BACKEND_CACHE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_BACKEND_CACHE)) -#define E_IS_CAL_BACKEND_CACHE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_BACKEND_CACHE)) - -typedef struct _ECalBackendCachePrivate ECalBackendCachePrivate; - -typedef struct { - EFileCache parent; - ECalBackendCachePrivate *priv; -} ECalBackendCache; - -typedef struct { - EFileCacheClass parent_class; -} ECalBackendCacheClass; - -GType e_cal_backend_cache_get_type (void); - -ECalBackendCache *e_cal_backend_cache_new (const char *uri); -ECalComponent *e_cal_backend_cache_get_component (ECalBackendCache *cache, - const char *uid, - const char *rid); -gboolean e_cal_backend_cache_put_component (ECalBackendCache *cache, ECalComponent *comp); -gboolean e_cal_backend_cache_remove_component (ECalBackendCache *cache, - const char *uid, - const char *rid); -GList *e_cal_backend_cache_get_components (ECalBackendCache *cache); - -const icaltimezone *e_cal_backend_cache_get_timezone (ECalBackendCache *cache, const char *tzid); -gboolean e_cal_backend_cache_put_timezone (ECalBackendCache *cache, const icaltimezone *zone); -gboolean e_cal_backend_cache_remove_timezone (ECalBackendCache *cache, const char *tzid); - -gboolean e_cal_backend_cache_put_default_timezone (ECalBackendCache *cache, icaltimezone *default_zone); -icaltimezone *e_cal_backend_cache_get_default_timezone (ECalBackendCache *cache); - - -G_END_DECLS - -#endif diff --git a/calendar/libedata-cal/e-cal-backend-sexp.c b/calendar/libedata-cal/e-cal-backend-sexp.c deleted file mode 100644 index 815a8ee76..000000000 --- a/calendar/libedata-cal/e-cal-backend-sexp.c +++ /dev/null @@ -1,1070 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - * cal-backend-card-sexp.c - * Copyright 1999, 2000, 2001, Ximian, Inc. - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License, version 2, as published by the Free Software Foundation. - * - * This library is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA - * 02111-1307, USA. - */ - -#include <string.h> -#include <libgnome/gnome-i18n.h> -#include <libedataserver/e-util.h> -#include <libecal/e-cal-time-util.h> - -#include "e-cal-backend-sexp.h" - -static GObjectClass *parent_class; - -typedef struct _SearchContext SearchContext; - -struct _ECalBackendSExpPrivate { - ESExp *search_sexp; - char *text; - SearchContext *search_context; -}; - -struct _SearchContext { - ECalComponent *comp; - ECalBackend *backend; - gboolean occurs; -}; - -ESExpResult * -e_cal_backend_sexp_func_time_now (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - ESExpResult *result; - - if (argc != 0) { - e_sexp_fatal_error (esexp, _("\"%s\" expects no arguments"), - "time-now"); - return NULL; - } - - result = e_sexp_result_new (esexp, ESEXP_RES_TIME); - result->value.time = time (NULL); - - return result; -} - -/* (make-time ISODATE) - * - * ISODATE - string, ISO 8601 date/time representation - * - * Constructs a time_t value for the specified date. - */ -ESExpResult * -e_cal_backend_sexp_func_make_time (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - const char *str; - time_t t; - ESExpResult *result; - - if (argc != 1) { - e_sexp_fatal_error (esexp, _("\"%s\" expects one argument"), - "make-time"); - return NULL; - } - - if (argv[0]->type != ESEXP_RES_STRING) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be a string"), - "make-time"); - return NULL; - } - str = argv[0]->value.string; - if (!str || !*str) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be a string"), - "make-time"); - return NULL; - } - - t = time_from_isodate (str); - if (t == -1) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be an ISO 8601 " - "date/time string"), - "make-time"); - return NULL; - } - - result = e_sexp_result_new (esexp, ESEXP_RES_TIME); - result->value.time = t; - - return result; -} - -/* (time-add-day TIME N) - * - * TIME - time_t, base time - * N - int, number of days to add - * - * Adds the specified number of days to a time value. - * - * FIXME: TIMEZONES - need to use a timezone or daylight saving changes will - * make the result incorrect. - */ -ESExpResult * -e_cal_backend_sexp_func_time_add_day (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - ESExpResult *result; - time_t t; - int n; - - if (argc != 2) { - e_sexp_fatal_error (esexp, _("\"%s\" expects two arguments"), - "time-add-day"); - return NULL; - } - - if (argv[0]->type != ESEXP_RES_TIME) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be a time_t"), - "time-add-day"); - return NULL; - } - t = argv[0]->value.time; - - if (argv[1]->type != ESEXP_RES_INT) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the second " - "argument to be an integer"), - "time-add-day"); - return NULL; - } - n = argv[1]->value.number; - - result = e_sexp_result_new (esexp, ESEXP_RES_TIME); - result->value.time = time_add_day (t, n); - - return result; -} - -/* (time-day-begin TIME) - * - * TIME - time_t, base time - * - * Returns the start of the day, according to the local time. - * - * FIXME: TIMEZONES - this uses the current Unix timezone. - */ -ESExpResult * -e_cal_backend_sexp_func_time_day_begin (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - time_t t; - ESExpResult *result; - - if (argc != 1) { - e_sexp_fatal_error (esexp, _("\"%s\" expects one argument"), - "time-day-begin"); - return NULL; - } - - if (argv[0]->type != ESEXP_RES_TIME) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be a time_t"), - "time-day-begin"); - return NULL; - } - t = argv[0]->value.time; - - result = e_sexp_result_new (esexp, ESEXP_RES_TIME); - result->value.time = time_day_begin (t); - - return result; -} - -/* (time-day-end TIME) - * - * TIME - time_t, base time - * - * Returns the end of the day, according to the local time. - * - * FIXME: TIMEZONES - this uses the current Unix timezone. - */ -ESExpResult * -e_cal_backend_sexp_func_time_day_end (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - time_t t; - ESExpResult *result; - - if (argc != 1) { - e_sexp_fatal_error (esexp, _("\"%s\" expects one argument"), - "time-day-end"); - return NULL; - } - - if (argv[0]->type != ESEXP_RES_TIME) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be a time_t"), - "time-day-end"); - return NULL; - } - t = argv[0]->value.time; - - result = e_sexp_result_new (esexp, ESEXP_RES_TIME); - result->value.time = time_day_end (t); - - return result; -} - -/* (uid? UID) - * - * UID - the uid of the component - * - * Returns a boolean indicating whether the component has the given UID - */ -static ESExpResult * -func_uid (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - SearchContext *ctx = data; - const char *uid = NULL, *arg_uid; - gboolean equal; - ESExpResult *result; - - /* Check argument types */ - - if (argc != 1) { - e_sexp_fatal_error (esexp, _("\"%s\" expects one argument"), - "uid"); - return NULL; - } - - if (argv[0]->type != ESEXP_RES_STRING) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be a string"), - "uid"); - return NULL; - } - - arg_uid = argv[0]->value.string; - e_cal_component_get_uid (ctx->comp, &uid); - - if (!arg_uid && !uid) - equal = TRUE; - else if ((!arg_uid || !uid) && arg_uid != uid) - equal = FALSE; - else if (e_util_utf8_strstrcase (arg_uid, uid) != NULL && strlen (arg_uid) == strlen (uid)) - equal = TRUE; - else - equal = FALSE; - - result = e_sexp_result_new (esexp, ESEXP_RES_BOOL); - result->value.bool = equal; - - return result; -} - -static gboolean -check_instance_time_range_cb (ECalComponent *comp, time_t instance_start, time_t instance_end, gpointer data) -{ - SearchContext *ctx = data; - - /* if we get called, the event has an occurrence in the given time range */ - ctx->occurs = TRUE; - - return FALSE; -} - -static icaltimezone * -resolve_tzid_cb (const char *tzid, gpointer user_data) -{ - SearchContext *ctx = user_data; - - if (!tzid || !tzid[0]) - return NULL; - else if (!strcmp (tzid, "UTC")) - return icaltimezone_get_utc_timezone (); - - return e_cal_backend_internal_get_timezone (ctx->backend, tzid); -} - -/* (occur-in-time-range? START END) - * - * START - time_t, start of the time range - * END - time_t, end of the time range - * - * Returns a boolean indicating whether the component has any occurrences in the - * specified time range. - */ -static ESExpResult * -func_occur_in_time_range (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - SearchContext *ctx = data; - time_t start, end; - ESExpResult *result; - icaltimezone *default_zone; - - /* Check argument types */ - - if (argc != 2) { - e_sexp_fatal_error (esexp, _("\"%s\" expects two arguments"), - "occur-in-time-range"); - return NULL; - } - - if (argv[0]->type != ESEXP_RES_TIME) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be a time_t"), - "occur-in-time-range"); - return NULL; - } - start = argv[0]->value.time; - - if (argv[1]->type != ESEXP_RES_TIME) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the second " - "argument to be a time_t"), - "occur-in-time-range"); - return NULL; - } - end = argv[1]->value.time; - - /* See if the object occurs in the specified time range */ - default_zone = e_cal_backend_internal_get_default_timezone (ctx->backend); - if (!default_zone) - default_zone = icaltimezone_get_utc_timezone (); - - ctx->occurs = FALSE; - e_cal_recur_generate_instances (ctx->comp, start, end, - (ECalRecurInstanceFn) check_instance_time_range_cb, - ctx, resolve_tzid_cb, ctx, - default_zone); - - result = e_sexp_result_new (esexp, ESEXP_RES_BOOL); - result->value.bool = ctx->occurs; - - return result; -} - -/* Returns whether a list of ECalComponentText items matches the specified string */ -static gboolean -matches_text_list (GSList *text_list, const char *str) -{ - GSList *l; - gboolean matches; - - matches = FALSE; - - for (l = text_list; l; l = l->next) { - ECalComponentText *text; - - text = l->data; - g_assert (text->value != NULL); - - if (e_util_utf8_strstrcasedecomp (text->value, str) != NULL) { - matches = TRUE; - break; - } - } - - return matches; -} - -/* Returns whether the comments in a component matches the specified string */ -static gboolean -matches_comment (ECalComponent *comp, const char *str) -{ - GSList *list; - gboolean matches; - - e_cal_component_get_comment_list (comp, &list); - matches = matches_text_list (list, str); - e_cal_component_free_text_list (list); - - return matches; -} - -/* Returns whether the description in a component matches the specified string */ -static gboolean -matches_description (ECalComponent *comp, const char *str) -{ - GSList *list; - gboolean matches; - - e_cal_component_get_description_list (comp, &list); - matches = matches_text_list (list, str); - e_cal_component_free_text_list (list); - - return matches; -} - -/* Returns whether the summary in a component matches the specified string */ -static gboolean -matches_summary (ECalComponent *comp, const char *str) -{ - ECalComponentText text; - - e_cal_component_get_summary (comp, &text); - - if (!text.value) - return FALSE; - - return e_util_utf8_strstrcasedecomp (text.value, str) != NULL; -} - -/* Returns whether the location in a component matches the specified string */ -static gboolean -matches_location (ECalComponent *comp, const char *str) -{ - const char *location = NULL; - - e_cal_component_get_location (comp, &location); - - if (!location) - return FALSE; - - return e_util_utf8_strstrcasedecomp (location, str) != NULL; -} - -/* Returns whether any text field in a component matches the specified string */ -static gboolean -matches_any (ECalComponent *comp, const char *str) -{ - /* As an optimization, and to make life easier for the individual - * predicate functions, see if we are looking for the empty string right - * away. - */ - if (strlen (str) == 0) - return TRUE; - - return (matches_comment (comp, str) - || matches_description (comp, str) - || matches_summary (comp, str) - || matches_location (comp, str)); -} - -/* (contains? FIELD STR) - * - * FIELD - string, name of field to match (any, comment, description, summary, location) - * STR - string, match string - * - * Returns a boolean indicating whether the specified field contains the - * specified string. - */ -static ESExpResult * -func_contains (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - SearchContext *ctx = data; - const char *field; - const char *str; - gboolean matches; - ESExpResult *result; - - /* Check argument types */ - - if (argc != 2) { - e_sexp_fatal_error (esexp, _("\"%s\" expects two arguments"), - "contains"); - return NULL; - } - - if (argv[0]->type != ESEXP_RES_STRING) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be a string"), - "contains"); - return NULL; - } - field = argv[0]->value.string; - - if (argv[1]->type != ESEXP_RES_STRING) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the second " - "argument to be a string"), - "contains"); - return NULL; - } - str = argv[1]->value.string; - - /* See if it matches */ - - if (strcmp (field, "any") == 0) - matches = matches_any (ctx->comp, str); - else if (strcmp (field, "comment") == 0) - matches = matches_comment (ctx->comp, str); - else if (strcmp (field, "description") == 0) - matches = matches_description (ctx->comp, str); - else if (strcmp (field, "summary") == 0) - matches = matches_summary (ctx->comp, str); - else if (strcmp (field, "location") == 0) - matches = matches_location (ctx->comp, str); - else { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be either \"any\", " - "\"summary\", or \"description\", or \"location\""), - "contains"); - return NULL; - } - - result = e_sexp_result_new (esexp, ESEXP_RES_BOOL); - result->value.bool = matches; - - return result; -} - -/* (has-alarms?) - * - * A boolean value for components that have/dont have alarms. - * - * Returns: a boolean indicating whether the component has alarms or not. - */ -static ESExpResult * -func_has_alarms (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - SearchContext *ctx = data; - ESExpResult *result; - - /* Check argument types */ - - if (argc != 0) { - e_sexp_fatal_error (esexp, _("\"%s\" expects no arguments"), - "has-alarms"); - return NULL; - } - - result = e_sexp_result_new (esexp, ESEXP_RES_BOOL); - result->value.bool = e_cal_component_has_alarms (ctx->comp); - - return result; -} - -/* (has-categories? STR+) - * (has-categories? #f) - * - * STR - At least one string specifying a category - * Or you can specify a single #f (boolean false) value for components - * that have no categories assigned to them ("unfiled"). - * - * Returns a boolean indicating whether the component has all the specified - * categories. - */ -static ESExpResult * -func_has_categories (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - SearchContext *ctx = data; - gboolean unfiled; - int i; - GSList *categories; - gboolean matches; - ESExpResult *result; - - /* Check argument types */ - - if (argc < 1) { - e_sexp_fatal_error (esexp, _("\"%s\" expects at least one " - "argument"), - "has-categories"); - return NULL; - } - - if (argc == 1 && argv[0]->type == ESEXP_RES_BOOL) - unfiled = TRUE; - else - unfiled = FALSE; - - if (!unfiled) - for (i = 0; i < argc; i++) - if (argv[i]->type != ESEXP_RES_STRING) { - e_sexp_fatal_error (esexp, _("\"%s\" expects " - "all arguments to " - "be strings or " - "one and only one " - "argument to be a " - "boolean false " - "(#f)"), - "has-categories"); - return NULL; - } - - /* Search categories. First, if there are no categories we return - * whether unfiled components are supposed to match. - */ - - e_cal_component_get_categories_list (ctx->comp, &categories); - if (!categories) { - result = e_sexp_result_new (esexp, ESEXP_RES_BOOL); - result->value.bool = unfiled; - - return result; - } - - /* Otherwise, we *do* have categories but unfiled components were - * requested, so this component does not match. - */ - if (unfiled) { - result = e_sexp_result_new (esexp, ESEXP_RES_BOOL); - result->value.bool = FALSE; - - return result; - } - - matches = TRUE; - - for (i = 0; i < argc; i++) { - const char *sought; - GSList *l; - gboolean has_category; - - sought = argv[i]->value.string; - - has_category = FALSE; - - for (l = categories; l; l = l->next) { - const char *category; - - category = l->data; - - if (strcmp (category, sought) == 0) { - has_category = TRUE; - break; - } - } - - if (!has_category) { - matches = FALSE; - break; - } - } - - e_cal_component_free_categories_list (categories); - - result = e_sexp_result_new (esexp, ESEXP_RES_BOOL); - result->value.bool = matches; - - return result; -} - -/* (has-recurrences?) - * - * A boolean value for components that have/dont have recurrences. - * - * Returns: a boolean indicating whether the component has recurrences or not. - */ -static ESExpResult * -func_has_recurrences (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - SearchContext *ctx = data; - ESExpResult *result; - - /* Check argument types */ - - if (argc != 0) { - e_sexp_fatal_error (esexp, _("\"%s\" expects no arguments"), - "has-recurrences"); - return NULL; - } - - result = e_sexp_result_new (esexp, ESEXP_RES_BOOL); - result->value.bool = e_cal_component_has_recurrences (ctx->comp); - - return result; -} - -/* (is-completed?) - * - * Returns a boolean indicating whether the component is completed (i.e. has - * a COMPLETED property. This is really only useful for TODO components. - */ -static ESExpResult * -func_is_completed (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - SearchContext *ctx = data; - ESExpResult *result; - struct icaltimetype *t; - gboolean complete = FALSE; - - /* Check argument types */ - - if (argc != 0) { - e_sexp_fatal_error (esexp, _("\"%s\" expects no arguments"), - "is-completed"); - return NULL; - } - - e_cal_component_get_completed (ctx->comp, &t); - if (t) { - complete = TRUE; - e_cal_component_free_icaltimetype (t); - } - - result = e_sexp_result_new (esexp, ESEXP_RES_BOOL); - result->value.bool = complete; - - return result; -} - -/* (completed-before? TIME) - * - * TIME - time_t - * - * Returns a boolean indicating whether the component was completed on or - * before the given time (i.e. it checks the COMPLETED property). - * This is really only useful for TODO components. - */ -static ESExpResult * -func_completed_before (ESExp *esexp, int argc, ESExpResult **argv, void *data) -{ - SearchContext *ctx = data; - ESExpResult *result; - struct icaltimetype *tt; - icaltimezone *zone; - gboolean retval = FALSE; - time_t before_time, completed_time; - - /* Check argument types */ - - if (argc != 1) { - e_sexp_fatal_error (esexp, _("\"%s\" expects one argument"), - "completed-before"); - return NULL; - } - - if (argv[0]->type != ESEXP_RES_TIME) { - e_sexp_fatal_error (esexp, _("\"%s\" expects the first " - "argument to be a time_t"), - "completed-before"); - return NULL; - } - before_time = argv[0]->value.time; - - e_cal_component_get_completed (ctx->comp, &tt); - if (tt) { - /* COMPLETED must be in UTC. */ - zone = icaltimezone_get_utc_timezone (); - completed_time = icaltime_as_timet_with_zone (*tt, zone); - -#if 0 - g_print ("Query Time : %s", ctime (&before_time)); - g_print ("Completed Time: %s", ctime (&completed_time)); -#endif - - /* We want to return TRUE if before_time is after - completed_time. */ - if (difftime (before_time, completed_time) > 0) { -#if 0 - g_print (" Returning TRUE\n"); -#endif - retval = TRUE; - } - - e_cal_component_free_icaltimetype (tt); - } - - result = e_sexp_result_new (esexp, ESEXP_RES_BOOL); - result->value.bool = retval; - - return result; -} - -#if 0 -static struct prop_info { - ECardSimpleField field_id; - const char *query_prop; - const char *ecard_prop; -#define PROP_TYPE_NORMAL 0x01 -#define PROP_TYPE_LIST 0x02 -#define PROP_TYPE_LISTITEM 0x03 -#define PROP_TYPE_ID 0x04 - int prop_type; - gboolean (*list_compare)(ECardSimple *ecard, const char *str, - char *(*compare)(const char*, const char*)); - -} prop_info_table[] = { -#define NORMAL_PROP(f,q,e) {f, q, e, PROP_TYPE_NORMAL, NULL} -#define ID_PROP {0, "id", NULL, PROP_TYPE_ID, NULL} -#define LIST_PROP(q,e,c) {0, q, e, PROP_TYPE_LIST, c} - - /* query prop, ecard prop, type, list compare function */ - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_FILE_AS, "file_as", "file_as" ), - LIST_PROP ( "full_name", "full_name", compare_name), /* not really a list, but we need to compare both full and surname */ - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_URL, "url", "url" ), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_MAILER, "mailer", "mailer"), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_ORG, "org", "org"), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_ORG_UNIT, "org_unit", "org_unit"), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_OFFICE, "office", "office"), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_TITLE, "title", "title"), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_ROLE, "role", "role"), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_MANAGER, "manager", "manager"), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_ASSISTANT, "assistant", "assistant"), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_NICKNAME, "nickname", "nickname"), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_SPOUSE, "spouse", "spouse" ), - NORMAL_PROP ( E_CARD_SIMPLE_FIELD_NOTE, "note", "note"), - ID_PROP, - LIST_PROP ( "email", "email", compare_email ), - LIST_PROP ( "phone", "phone", compare_phone ), - LIST_PROP ( "address", "address", compare_address ), - LIST_PROP ( "category", "category", compare_category ), - LIST_PROP ( "arbitrary", "arbitrary", compare_arbitrary ) -}; -static int num_prop_infos = sizeof(prop_info_table) / sizeof(prop_info_table[0]); - -static ESExpResult * -entry_compare(SearchContext *ctx, struct _ESExp *f, - int argc, struct _ESExpResult **argv, - char *(*compare)(const char*, const char*)) -{ - ESExpResult *r; - int truth = FALSE; - - if (argc == 2 - && argv[0]->type == ESEXP_RES_STRING - && argv[1]->type == ESEXP_RES_STRING) { - char *propname; - struct prop_info *info = NULL; - int i; - gboolean any_field; - - propname = argv[0]->value.string; - - any_field = !strcmp(propname, "x-evolution-any-field"); - for (i = 0; i < num_prop_infos; i ++) { - if (any_field - || !strcmp (prop_info_table[i].query_prop, propname)) { - info = &prop_info_table[i]; - - if (info->prop_type == PROP_TYPE_NORMAL) { - char *prop = NULL; - /* searches where the query's property - maps directly to an ecard property */ - - prop = e_card_simple_get (ctx->card, info->field_id); - - if (prop && compare(prop, argv[1]->value.string)) { - truth = TRUE; - } - if ((!prop) && compare("", argv[1]->value.string)) { - truth = TRUE; - } - g_free (prop); - } else if (info->prop_type == PROP_TYPE_LIST) { - /* the special searches that match any of the list elements */ - truth = info->list_compare (ctx->card, argv[1]->value.string, compare); - } else if (info->prop_type == PROP_TYPE_ID) { - const char *prop = NULL; - /* searches where the query's property - maps directly to an ecard property */ - - prop = e_card_get_id (ctx->card->card); - - if (prop && compare(prop, argv[1]->value.string)) { - truth = TRUE; - } - if ((!prop) && compare("", argv[1]->value.string)) { - truth = TRUE; - } - } - - /* if we're looking at all fields and find a match, - or if we're just looking at this one field, - break. */ - if ((any_field && truth) - || !any_field) - break; - } - } - - } - r = e_sexp_result_new(f, ESEXP_RES_BOOL); - r->value.bool = truth; - - return r; -} -#endif - -/* 'builtin' functions */ -static struct { - char *name; - ESExpFunc *func; - int type; /* set to 1 if a function can perform shortcut evaluation, or - doesn't execute everything, 0 otherwise */ -} symbols[] = { - /* Time-related functions */ - { "time-now", e_cal_backend_sexp_func_time_now, 0 }, - { "make-time", e_cal_backend_sexp_func_make_time, 0 }, - { "time-add-day", e_cal_backend_sexp_func_time_add_day, 0 }, - { "time-day-begin", e_cal_backend_sexp_func_time_day_begin, 0 }, - { "time-day-end", e_cal_backend_sexp_func_time_day_end, 0 }, - - /* Component-related functions */ - { "uid?", func_uid, 0 }, - { "occur-in-time-range?", func_occur_in_time_range, 0 }, - { "contains?", func_contains, 0 }, - { "has-alarms?", func_has_alarms, 0 }, - { "has-recurrences?", func_has_recurrences, 0 }, - { "has-categories?", func_has_categories, 0 }, - { "is-completed?", func_is_completed, 0 }, - { "completed-before?", func_completed_before, 0 } -}; - -gboolean -e_cal_backend_sexp_match_comp (ECalBackendSExp *sexp, ECalComponent *comp, ECalBackend *backend) -{ - ESExpResult *r; - gboolean retval; - - sexp->priv->search_context->comp = g_object_ref (comp); - sexp->priv->search_context->backend = g_object_ref (backend); - - /* if it's not a valid vcard why is it in our db? :) */ - if (!sexp->priv->search_context->comp) - return FALSE; - - r = e_sexp_eval(sexp->priv->search_sexp); - - retval = (r && r->type == ESEXP_RES_BOOL && r->value.bool); - - g_object_unref (sexp->priv->search_context->comp); - g_object_unref (sexp->priv->search_context->backend); - - e_sexp_result_free(sexp->priv->search_sexp, r); - - return retval; -} - -gboolean -e_cal_backend_sexp_match_object (ECalBackendSExp *sexp, const char *object, ECalBackend *backend) -{ - ECalComponent *comp; - icalcomponent *icalcomp; - gboolean retval; - - icalcomp = icalcomponent_new_from_string ((char *) object); - if (!icalcomp) - return FALSE; - - comp = e_cal_component_new (); - e_cal_component_set_icalcomponent (comp, icalcomp); - - retval = e_cal_backend_sexp_match_comp (sexp, comp, backend); - - g_object_unref (comp); - - return retval; -} - - - -/** - * e_cal_backend_card_sexp_new: - */ -ECalBackendSExp * -e_cal_backend_sexp_new (const char *text) -{ - ECalBackendSExp *sexp = g_object_new (E_TYPE_CAL_BACKEND_SEXP, NULL); - int esexp_error; - int i; - - sexp->priv->search_sexp = e_sexp_new(); - sexp->priv->text = g_strdup (text); - - for (i = 0; i < G_N_ELEMENTS (symbols); i++) { - if (symbols[i].type == 1) { - e_sexp_add_ifunction(sexp->priv->search_sexp, 0, symbols[i].name, - (ESExpIFunc *)symbols[i].func, sexp->priv->search_context); - } else { - e_sexp_add_function(sexp->priv->search_sexp, 0, symbols[i].name, - symbols[i].func, sexp->priv->search_context); - } - } - - e_sexp_input_text(sexp->priv->search_sexp, text, strlen(text)); - esexp_error = e_sexp_parse(sexp->priv->search_sexp); - - if (esexp_error == -1) { - g_object_unref (sexp); - sexp = NULL; - } - - return sexp; -} - -const char * -e_cal_backend_sexp_text (ECalBackendSExp *sexp) -{ - ECalBackendSExpPrivate *priv; - - g_return_val_if_fail (sexp != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_BACKEND_SEXP (sexp), NULL); - - priv = sexp->priv; - - return priv->text; -} - -static void -e_cal_backend_sexp_dispose (GObject *object) -{ - ECalBackendSExp *sexp = E_CAL_BACKEND_SEXP (object); - - if (sexp->priv) { - e_sexp_unref(sexp->priv->search_sexp); - - g_free (sexp->priv->text); - - g_free (sexp->priv->search_context); - g_free (sexp->priv); - sexp->priv = NULL; - } - - if (G_OBJECT_CLASS (parent_class)->dispose) - G_OBJECT_CLASS (parent_class)->dispose (object); -} - -static void -e_cal_backend_sexp_class_init (ECalBackendSExpClass *klass) -{ - GObjectClass *object_class = G_OBJECT_CLASS (klass); - - parent_class = g_type_class_peek_parent (klass); - - /* Set the virtual methods. */ - - object_class->dispose = e_cal_backend_sexp_dispose; -} - -static void -e_cal_backend_sexp_init (ECalBackendSExp *sexp) -{ - ECalBackendSExpPrivate *priv; - - priv = g_new0 (ECalBackendSExpPrivate, 1); - - sexp->priv = priv; - priv->search_context = g_new (SearchContext, 1); -} - -/** - * e_cal_backend_sexp_get_type: - */ -GType -e_cal_backend_sexp_get_type (void) -{ - static GType type = 0; - - if (! type) { - GTypeInfo info = { - sizeof (ECalBackendSExpClass), - NULL, /* base_class_init */ - NULL, /* base_class_finalize */ - (GClassInitFunc) e_cal_backend_sexp_class_init, - NULL, /* class_finalize */ - NULL, /* class_data */ - sizeof (ECalBackendSExp), - 0, /* n_preallocs */ - (GInstanceInitFunc) e_cal_backend_sexp_init - }; - - type = g_type_register_static (G_TYPE_OBJECT, "ECalBackendSExp", &info, 0); - } - - return type; -} diff --git a/calendar/libedata-cal/e-cal-backend-sexp.h b/calendar/libedata-cal/e-cal-backend-sexp.h deleted file mode 100644 index df740b119..000000000 --- a/calendar/libedata-cal/e-cal-backend-sexp.h +++ /dev/null @@ -1,78 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - * cal-backend-card-sexp.h - * Copyright 2000, 2001, Ximian, Inc. - * - * Authors: - * Chris Lahey <clahey@ximian.com> - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License, version 2, as published by the Free Software Foundation. - * - * This library is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA - * 02111-1307, USA. - */ - -#ifndef __E_CAL_BACKEND_SEXP_H__ -#define __E_CAL_BACKEND_SEXP_H__ - -#include <glib.h> -#include <glib-object.h> -#include <libecal/e-cal-component.h> -#include <libedata-cal/e-cal-backend.h> -#include <libedataserver/e-sexp.h> - -G_BEGIN_DECLS - -#define E_TYPE_CAL_BACKEND_SEXP (e_cal_backend_sexp_get_type ()) -#define E_CAL_BACKEND_SEXP(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), E_TYPE_CAL_BACKEND_SEXP, ECalBackendSExp)) -#define E_CAL_BACKEND_SEXP_CLASS(k) (G_TYPE_CHECK_CLASS_CAST((k), E_CAL_BACKEND_TYPE, ECalBackendSExpClass)) -#define E_IS_CAL_BACKEND_SEXP(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), E_TYPE_CAL_BACKEND_SEXP)) -#define E_IS_CAL_BACKEND_SEXP_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), E_TYPE_CAL_BACKEND_SEXP)) -#define E_CAL_BACKEND_SEXP_GET_CLASS(k) (G_TYPE_INSTANCE_GET_CLASS ((obj), E_TYPE_CAL_BACKEND_SEXP, CALBackendSExpClass)) - -typedef struct _ECalBackendSExpPrivate ECalBackendSExpPrivate; - -struct _ECalBackendSExp { - GObject parent_object; - - ECalBackendSExpPrivate *priv; -}; - -struct _ECalBackendSExpClass { - GObjectClass parent_class; -}; - -GType e_cal_backend_sexp_get_type (void); - -ECalBackendSExp *e_cal_backend_sexp_new (const char *text); -const char *e_cal_backend_sexp_text (ECalBackendSExp *sexp); - -gboolean e_cal_backend_sexp_match_object (ECalBackendSExp *sexp, - const char *object, - ECalBackend *backend); -gboolean e_cal_backend_sexp_match_comp (ECalBackendSExp *sexp, - ECalComponent *comp, - ECalBackend *backend); - - -/* Default implementations of time functions for use by subclasses */ - -ESExpResult *e_cal_backend_sexp_func_time_now (ESExp *esexp, int argc, ESExpResult **argv, void *data); -ESExpResult *e_cal_backend_sexp_func_make_time (ESExp *esexp, int argc, ESExpResult **argv, void *data); -ESExpResult *e_cal_backend_sexp_func_time_add_day (ESExp *esexp, int argc, ESExpResult **argv, void *data); -ESExpResult *e_cal_backend_sexp_func_time_day_begin (ESExp *esexp, int argc, ESExpResult **argv, void *data); -ESExpResult *e_cal_backend_sexp_func_time_day_end (ESExp *esexp, int argc, ESExpResult **argv, void *data); - - -G_END_DECLS - -#endif /* __E_CAL_BACKEND_SEXP_H__ */ diff --git a/calendar/libedata-cal/e-cal-backend-sync.c b/calendar/libedata-cal/e-cal-backend-sync.c deleted file mode 100644 index c0127cdaf..000000000 --- a/calendar/libedata-cal/e-cal-backend-sync.c +++ /dev/null @@ -1,621 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - * Author: - * Chris Toshok (toshok@ximian.com) - * - * Copyright (C) 2003, Ximian, Inc. - */ - -#ifdef CONFIG_H -#include <config.h> -#endif - -#include "e-cal-backend-sync.h" - -struct _ECalBackendSyncPrivate { - int mumble; - GMutex *sync_mutex; -}; - -static GObjectClass *parent_class; - -ECalBackendSyncStatus -e_cal_backend_sync_is_read_only (ECalBackendSync *backend, EDataCal *cal, gboolean *read_only) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (read_only, GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->is_read_only_sync); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->is_read_only_sync) (backend, cal, read_only); -} - -ECalBackendSyncStatus -e_cal_backend_sync_get_cal_address (ECalBackendSync *backend, EDataCal *cal, char **address) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (address, GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_cal_address_sync); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_cal_address_sync) (backend, cal, address); -} - -ECalBackendSyncStatus -e_cal_backend_sync_get_alarm_email_address (ECalBackendSync *backend, EDataCal *cal, char **address) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (address, GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_alarm_email_address_sync); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_alarm_email_address_sync) (backend, cal, address); -} - -ECalBackendSyncStatus -e_cal_backend_sync_get_ldap_attribute (ECalBackendSync *backend, EDataCal *cal, char **attribute) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (attribute, GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_ldap_attribute_sync); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_ldap_attribute_sync) (backend, cal, attribute); -} - -ECalBackendSyncStatus -e_cal_backend_sync_get_static_capabilities (ECalBackendSync *backend, EDataCal *cal, char **capabilities) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (capabilities, GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_static_capabilities_sync); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_static_capabilities_sync) (backend, cal, capabilities); -} - -ECalBackendSyncStatus -e_cal_backend_sync_open (ECalBackendSync *backend, EDataCal *cal, gboolean only_if_exists, - const char *username, const char *password) -{ - ECalBackendSyncPrivate *priv; - ECalBackendSyncStatus status; - - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->open_sync); - priv = backend->priv; - - g_mutex_lock (priv->sync_mutex); - - status = (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->open_sync) (backend, cal, only_if_exists, username, password); - - g_mutex_unlock (priv->sync_mutex); - - return status; -} - -ECalBackendSyncStatus -e_cal_backend_sync_remove (ECalBackendSync *backend, EDataCal *cal) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->remove_sync); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->remove_sync) (backend, cal); -} - -ECalBackendSyncStatus -e_cal_backend_sync_create_object (ECalBackendSync *backend, EDataCal *cal, char **calobj, char **uid) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->create_object_sync != NULL, - GNOME_Evolution_Calendar_UnsupportedMethod); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->create_object_sync) (backend, cal, calobj, uid); -} - -ECalBackendSyncStatus -e_cal_backend_sync_modify_object (ECalBackendSync *backend, EDataCal *cal, const char *calobj, - CalObjModType mod, char **old_object) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->modify_object_sync != NULL, - GNOME_Evolution_Calendar_UnsupportedMethod); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->modify_object_sync) (backend, cal, - calobj, mod, old_object); -} - -ECalBackendSyncStatus -e_cal_backend_sync_remove_object (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *rid, - CalObjModType mod, char **object) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->remove_object_sync != NULL, - GNOME_Evolution_Calendar_UnsupportedMethod); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->remove_object_sync) (backend, cal, uid, rid, mod, object); -} - -ECalBackendSyncStatus -e_cal_backend_sync_discard_alarm (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *auid) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->discard_alarm_sync != NULL, - GNOME_Evolution_Calendar_UnsupportedMethod); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->discard_alarm_sync) (backend, cal, uid, auid); -} - -ECalBackendSyncStatus -e_cal_backend_sync_receive_objects (ECalBackendSync *backend, EDataCal *cal, const char *calobj) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->receive_objects_sync != NULL, - GNOME_Evolution_Calendar_UnsupportedMethod); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->receive_objects_sync) (backend, cal, calobj); -} - -ECalBackendSyncStatus -e_cal_backend_sync_send_objects (ECalBackendSync *backend, EDataCal *cal, const char *calobj, GList **users, - char **modified_calobj) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->send_objects_sync != NULL, - GNOME_Evolution_Calendar_UnsupportedMethod); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->send_objects_sync) (backend, cal, calobj, users, modified_calobj); -} - -ECalBackendSyncStatus -e_cal_backend_sync_get_default_object (ECalBackendSync *backend, EDataCal *cal, char **object) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (object, GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_default_object_sync); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_default_object_sync) (backend, cal, object); -} - -ECalBackendSyncStatus -e_cal_backend_sync_get_object (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *rid, char **object) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (object, GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_object_sync); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_object_sync) (backend, cal, uid, rid, object); -} - -ECalBackendSyncStatus -e_cal_backend_sync_get_object_list (ECalBackendSync *backend, EDataCal *cal, const char *sexp, GList **objects) -{ - g_return_val_if_fail (backend && E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - g_return_val_if_fail (objects, GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_object_list_sync); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_object_list_sync) (backend, cal, sexp, objects); -} - -ECalBackendSyncStatus -e_cal_backend_sync_get_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid, char **object) -{ - g_return_val_if_fail (E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_timezone_sync != NULL); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_timezone_sync) (backend, cal, tzid, object); -} - -ECalBackendSyncStatus -e_cal_backend_sync_add_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzobj) -{ - g_return_val_if_fail (E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->add_timezone_sync != NULL); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->add_timezone_sync) (backend, cal, tzobj); -} - -ECalBackendSyncStatus -e_cal_backend_sync_set_default_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid) -{ - g_return_val_if_fail (E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->set_default_timezone_sync != NULL); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->set_default_timezone_sync) (backend, cal, tzid); -} - - -ECalBackendSyncStatus -e_cal_backend_sync_get_changes (ECalBackendSync *backend, EDataCal *cal, const char *change_id, - GList **adds, GList **modifies, GList **deletes) -{ - g_return_val_if_fail (E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_changes_sync != NULL); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_changes_sync) (backend, cal, change_id, - adds, modifies, deletes); -} - -ECalBackendSyncStatus -e_cal_backend_sync_get_free_busy (ECalBackendSync *backend, EDataCal *cal, GList *users, - time_t start, time_t end, GList **freebusy) -{ - g_return_val_if_fail (E_IS_CAL_BACKEND_SYNC (backend), GNOME_Evolution_Calendar_OtherError); - - g_assert (E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_freebusy_sync != NULL); - - return (* E_CAL_BACKEND_SYNC_GET_CLASS (backend)->get_freebusy_sync) (backend, cal, users, - start, end, freebusy); -} - - -static void -_e_cal_backend_is_read_only (ECalBackend *backend, EDataCal *cal) -{ - ECalBackendSyncStatus status; - gboolean read_only = TRUE; - - status = e_cal_backend_sync_is_read_only (E_CAL_BACKEND_SYNC (backend), cal, &read_only); - - e_data_cal_notify_read_only (cal, status, read_only); -} - -static void -_e_cal_backend_get_cal_address (ECalBackend *backend, EDataCal *cal) -{ - ECalBackendSyncStatus status; - char *address = NULL; - - status = e_cal_backend_sync_get_cal_address (E_CAL_BACKEND_SYNC (backend), cal, &address); - - e_data_cal_notify_cal_address (cal, status, address); - - g_free (address); -} - -static void -_e_cal_backend_get_alarm_email_address (ECalBackend *backend, EDataCal *cal) -{ - ECalBackendSyncStatus status; - char *address = NULL; - - status = e_cal_backend_sync_get_alarm_email_address (E_CAL_BACKEND_SYNC (backend), cal, &address); - - e_data_cal_notify_alarm_email_address (cal, status, address); - - g_free (address); -} - -static void -_e_cal_backend_get_ldap_attribute (ECalBackend *backend, EDataCal *cal) -{ - ECalBackendSyncStatus status; - char *attribute = NULL; - - status = e_cal_backend_sync_get_ldap_attribute (E_CAL_BACKEND_SYNC (backend), cal, &attribute); - - e_data_cal_notify_ldap_attribute (cal, status, attribute); - - g_free (attribute); -} - -static void -_e_cal_backend_get_static_capabilities (ECalBackend *backend, EDataCal *cal) -{ - ECalBackendSyncStatus status; - char *capabilities = NULL; - - status = e_cal_backend_sync_get_static_capabilities (E_CAL_BACKEND_SYNC (backend), cal, &capabilities); - - e_data_cal_notify_static_capabilities (cal, status, capabilities); - - g_free (capabilities); -} - -static void -_e_cal_backend_open (ECalBackend *backend, EDataCal *cal, gboolean only_if_exists, - const char *username, const char *password) -{ - ECalBackendSyncStatus status; - - status = e_cal_backend_sync_open (E_CAL_BACKEND_SYNC (backend), cal, only_if_exists, username, password); - - e_data_cal_notify_open (cal, status); -} - -static void -_e_cal_backend_remove (ECalBackend *backend, EDataCal *cal) -{ - ECalBackendSyncStatus status; - - status = e_cal_backend_sync_remove (E_CAL_BACKEND_SYNC (backend), cal); - - e_data_cal_notify_remove (cal, status); -} - -static void -_e_cal_backend_create_object (ECalBackend *backend, EDataCal *cal, const char *calobj) -{ - ECalBackendSyncStatus status; - char *uid = NULL, *modified_calobj = (char *) calobj; - - status = e_cal_backend_sync_create_object (E_CAL_BACKEND_SYNC (backend), cal, &modified_calobj, &uid); - - e_data_cal_notify_object_created (cal, status, uid, modified_calobj); - - /* free memory */ - if (uid) - g_free (uid); - - if (modified_calobj != calobj) - g_free (modified_calobj); -} - -static void -_e_cal_backend_modify_object (ECalBackend *backend, EDataCal *cal, const char *calobj, CalObjModType mod) -{ - ECalBackendSyncStatus status; - char *old_object = NULL; - - status = e_cal_backend_sync_modify_object (E_CAL_BACKEND_SYNC (backend), cal, - calobj, mod, &old_object); - - e_data_cal_notify_object_modified (cal, status, old_object, calobj); -} - -static void -_e_cal_backend_remove_object (ECalBackend *backend, EDataCal *cal, const char *uid, const char *rid, CalObjModType mod) -{ - ECalBackendSyncStatus status; - char *object = NULL; - - status = e_cal_backend_sync_remove_object (E_CAL_BACKEND_SYNC (backend), cal, uid, rid, mod, &object); - - e_data_cal_notify_object_removed (cal, status, uid, object); -} - -static void -_e_cal_backend_discard_alarm (ECalBackend *backend, EDataCal *cal, const char *uid, const char *auid) -{ - ECalBackendSyncStatus status; - - status = e_cal_backend_sync_discard_alarm (E_CAL_BACKEND_SYNC (backend), cal, uid, auid); - - e_data_cal_notify_alarm_discarded (cal, status); -} - -static void -_e_cal_backend_receive_objects (ECalBackend *backend, EDataCal *cal, const char *calobj) -{ - ECalBackendSyncStatus status; - - status = e_cal_backend_sync_receive_objects (E_CAL_BACKEND_SYNC (backend), cal, calobj); - - e_data_cal_notify_objects_received (cal, status); -} - -static void -_e_cal_backend_send_objects (ECalBackend *backend, EDataCal *cal, const char *calobj) -{ - ECalBackendSyncStatus status; - GList *users = NULL; - char *modified_calobj = NULL; - - status = e_cal_backend_sync_send_objects (E_CAL_BACKEND_SYNC (backend), cal, calobj, &users, &modified_calobj); - e_data_cal_notify_objects_sent (cal, status, users, modified_calobj); - - g_list_foreach (users, (GFunc) g_free, NULL); - g_list_free (users); - g_free (modified_calobj); -} - -static void -_e_cal_backend_get_default_object (ECalBackend *backend, EDataCal *cal) -{ - ECalBackendSyncStatus status; - char *object = NULL; - - status = e_cal_backend_sync_get_default_object (E_CAL_BACKEND_SYNC (backend), cal, &object); - - e_data_cal_notify_default_object (cal, status, object); - - g_free (object); -} - -static void -_e_cal_backend_get_object (ECalBackend *backend, EDataCal *cal, const char *uid, const char *rid) -{ - ECalBackendSyncStatus status; - char *object = NULL; - - status = e_cal_backend_sync_get_object (E_CAL_BACKEND_SYNC (backend), cal, uid, rid, &object); - - e_data_cal_notify_object (cal, status, object); - - g_free (object); -} - -static void -_e_cal_backend_get_object_list (ECalBackend *backend, EDataCal *cal, const char *sexp) -{ - ECalBackendSyncStatus status; - GList *objects = NULL, *l; - - status = e_cal_backend_sync_get_object_list (E_CAL_BACKEND_SYNC (backend), cal, sexp, &objects); - - e_data_cal_notify_object_list (cal, status, objects); - - for (l = objects; l; l = l->next) - g_free (l->data); - g_list_free (objects); -} - -static void -_e_cal_backend_get_timezone (ECalBackend *backend, EDataCal *cal, const char *tzid) -{ - ECalBackendSyncStatus status; - char *object = NULL; - - status = e_cal_backend_sync_get_timezone (E_CAL_BACKEND_SYNC (backend), cal, tzid, &object); - - e_data_cal_notify_timezone_requested (cal, status, object); - - g_free (object); -} - -static void -_e_cal_backend_add_timezone (ECalBackend *backend, EDataCal *cal, const char *tzobj) -{ - ECalBackendSyncStatus status; - - status = e_cal_backend_sync_add_timezone (E_CAL_BACKEND_SYNC (backend), cal, tzobj); - - e_data_cal_notify_timezone_added (cal, status, tzobj); -} - -static void -_e_cal_backend_set_default_timezone (ECalBackend *backend, EDataCal *cal, const char *tzid) -{ - ECalBackendSyncStatus status; - - status = e_cal_backend_sync_set_default_timezone (E_CAL_BACKEND_SYNC (backend), cal, tzid); - - e_data_cal_notify_default_timezone_set (cal, status); -} - -static void -_e_cal_backend_get_changes (ECalBackend *backend, EDataCal *cal, const char *change_id) -{ - ECalBackendSyncStatus status; - GList *adds = NULL, *modifies = NULL, *deletes = NULL, *l; - - status = e_cal_backend_sync_get_changes (E_CAL_BACKEND_SYNC (backend), cal, change_id, - &adds, &modifies, &deletes); - - e_data_cal_notify_changes (cal, status, adds, modifies, deletes); - - for (l = adds; l; l = l->next) - g_free (l->data); - g_list_free (adds); - - for (l = modifies; l; l = l->next) - g_free (l->data); - g_list_free (modifies); - - for (l = deletes; l; l = l->next) - g_free (l->data); - g_list_free (deletes); -} - -static void -_e_cal_backend_get_free_busy (ECalBackend *backend, EDataCal *cal, GList *users, time_t start, time_t end) -{ - ECalBackendSyncStatus status; - GList *freebusy = NULL, *l; - - status = e_cal_backend_sync_get_free_busy (E_CAL_BACKEND_SYNC (backend), cal, users, start, end, &freebusy); - - e_data_cal_notify_free_busy (cal, status, freebusy); - - for (l = freebusy; l; l = l->next) - g_free (l->data); - g_list_free (freebusy); -} - -static void -e_cal_backend_sync_init (ECalBackendSync *backend) -{ - ECalBackendSyncPrivate *priv; - - priv = g_new0 (ECalBackendSyncPrivate, 1); - priv->sync_mutex = g_mutex_new (); - - backend->priv = priv; -} - -static void -e_cal_backend_sync_dispose (GObject *object) -{ - ECalBackendSync *backend; - - backend = E_CAL_BACKEND_SYNC (object); - - if (backend->priv) { - g_mutex_free (backend->priv->sync_mutex); - g_free (backend->priv); - - backend->priv = NULL; - } - - G_OBJECT_CLASS (parent_class)->dispose (object); -} - -static void -e_cal_backend_sync_class_init (ECalBackendSyncClass *klass) -{ - GObjectClass *object_class; - ECalBackendClass *backend_class = E_CAL_BACKEND_CLASS (klass); - - parent_class = g_type_class_peek_parent (klass); - - object_class = (GObjectClass *) klass; - - backend_class->is_read_only = _e_cal_backend_is_read_only; - backend_class->get_cal_address = _e_cal_backend_get_cal_address; - backend_class->get_alarm_email_address = _e_cal_backend_get_alarm_email_address; - backend_class->get_ldap_attribute = _e_cal_backend_get_ldap_attribute; - backend_class->get_static_capabilities = _e_cal_backend_get_static_capabilities; - backend_class->open = _e_cal_backend_open; - backend_class->remove = _e_cal_backend_remove; - backend_class->create_object = _e_cal_backend_create_object; - backend_class->modify_object = _e_cal_backend_modify_object; - backend_class->remove_object = _e_cal_backend_remove_object; - backend_class->discard_alarm = _e_cal_backend_discard_alarm; - backend_class->receive_objects = _e_cal_backend_receive_objects; - backend_class->send_objects = _e_cal_backend_send_objects; - backend_class->get_default_object = _e_cal_backend_get_default_object; - backend_class->get_object = _e_cal_backend_get_object; - backend_class->get_object_list = _e_cal_backend_get_object_list; - backend_class->get_timezone = _e_cal_backend_get_timezone; - backend_class->add_timezone = _e_cal_backend_add_timezone; - backend_class->set_default_timezone = _e_cal_backend_set_default_timezone; - backend_class->get_changes = _e_cal_backend_get_changes; - backend_class->get_free_busy = _e_cal_backend_get_free_busy; - - object_class->dispose = e_cal_backend_sync_dispose; -} - -/** - * e_cal_backend_get_type: - */ -GType -e_cal_backend_sync_get_type (void) -{ - static GType type = 0; - - if (! type) { - GTypeInfo info = { - sizeof (ECalBackendSyncClass), - NULL, /* base_class_init */ - NULL, /* base_class_finalize */ - (GClassInitFunc) e_cal_backend_sync_class_init, - NULL, /* class_finalize */ - NULL, /* class_data */ - sizeof (ECalBackendSync), - 0, /* n_preallocs */ - (GInstanceInitFunc) e_cal_backend_sync_init - }; - - type = g_type_register_static (E_TYPE_CAL_BACKEND, "ECalBackendSync", &info, 0); - } - - return type; -} diff --git a/calendar/libedata-cal/e-cal-backend-sync.h b/calendar/libedata-cal/e-cal-backend-sync.h deleted file mode 100644 index 47082d8ee..000000000 --- a/calendar/libedata-cal/e-cal-backend-sync.h +++ /dev/null @@ -1,148 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - */ - -#ifndef __E_CAL_BACKEND_SYNC_H__ -#define __E_CAL_BACKEND_SYNC_H__ - -#include <glib.h> -#include <libedata-cal/Evolution-DataServer-Calendar.h> -#include <libedata-cal/e-cal-backend.h> - -G_BEGIN_DECLS - -#define E_TYPE_CAL_BACKEND_SYNC (e_cal_backend_sync_get_type ()) -#define E_CAL_BACKEND_SYNC(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), E_TYPE_CAL_BACKEND_SYNC, ECalBackendSync)) -#define E_CAL_BACKEND_SYNC_CLASS(k) (G_TYPE_CHECK_CLASS_CAST((k), E_TYPE_CAL_BACKEND_SYNC, ECalBackendSyncClass)) -#define E_IS_CAL_BACKEND_SYNC(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), E_TYPE_CAL_BACKEND_SYNC)) -#define E_IS_CAL_BACKEND_SYNC_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), E_TYPE_CAL_BACKEND_SYNC)) -#define E_CAL_BACKEND_SYNC_GET_CLASS(k) (G_TYPE_INSTANCE_GET_CLASS ((k), E_TYPE_CAL_BACKEND_SYNC, ECalBackendSyncClass)) -typedef struct _ECalBackendSync ECalBackendSync; -typedef struct _ECalBackendSyncClass ECalBackendSyncClass; -typedef struct _ECalBackendSyncPrivate ECalBackendSyncPrivate; - -typedef GNOME_Evolution_Calendar_CallStatus ECalBackendSyncStatus; - -struct _ECalBackendSync { - ECalBackend parent_object; - - ECalBackendSyncPrivate *priv; -}; - -struct _ECalBackendSyncClass { - ECalBackendClass parent_class; - - /* Virtual methods */ - ECalBackendSyncStatus (*is_read_only_sync) (ECalBackendSync *backend, EDataCal *cal, gboolean *read_only); - ECalBackendSyncStatus (*get_cal_address_sync) (ECalBackendSync *backend, EDataCal *cal, char **address); - ECalBackendSyncStatus (*get_alarm_email_address_sync) (ECalBackendSync *backend, EDataCal *cal, char **address); - ECalBackendSyncStatus (*get_ldap_attribute_sync) (ECalBackendSync *backend, EDataCal *cal, char **attribute); - ECalBackendSyncStatus (*get_static_capabilities_sync) (ECalBackendSync *backend, EDataCal *cal, char **capabilities); - - ECalBackendSyncStatus (*open_sync) (ECalBackendSync *backend, EDataCal *cal, gboolean only_if_exists, const char *username, const char *password); - ECalBackendSyncStatus (*remove_sync) (ECalBackendSync *backend, EDataCal *cal); - - ECalBackendSyncStatus (*create_object_sync) (ECalBackendSync *backend, EDataCal *cal, char **calobj, char **uid); - ECalBackendSyncStatus (*modify_object_sync) (ECalBackendSync *backend, EDataCal *cal, const char *calobj, CalObjModType mod, char **old_object); - ECalBackendSyncStatus (*remove_object_sync) (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *rid, CalObjModType mod, char **object); - - ECalBackendSyncStatus (*discard_alarm_sync) (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *auid); - - ECalBackendSyncStatus (*receive_objects_sync) (ECalBackendSync *backend, EDataCal *cal, const char *calobj); - ECalBackendSyncStatus (*send_objects_sync) (ECalBackendSync *backend, EDataCal *cal, const char *calobj, GList **users, - char **modified_calobj); - - ECalBackendSyncStatus (*get_default_object_sync) (ECalBackendSync *backend, EDataCal *cal, char **object); - ECalBackendSyncStatus (*get_object_sync) (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *rid, char **object); - ECalBackendSyncStatus (*get_object_list_sync) (ECalBackendSync *backend, EDataCal *cal, const char *sexp, GList **objects); - - ECalBackendSyncStatus (*get_timezone_sync) (ECalBackendSync *backend, EDataCal *cal, const char *tzid, char **object); - ECalBackendSyncStatus (*add_timezone_sync) (ECalBackendSync *backend, EDataCal *cal, const char *tzobj); - ECalBackendSyncStatus (*set_default_timezone_sync) (ECalBackendSync *backend, EDataCal *cal, const char *tzid); - - ECalBackendSyncStatus (*get_changes_sync) (ECalBackendSync *backend, EDataCal *cal, const char *change_id, GList **adds, GList **modifies, GList **deletes); - ECalBackendSyncStatus (*get_freebusy_sync) (ECalBackendSync *backend, EDataCal *cal, GList *users, time_t start, time_t end, GList **freebusy); - - /* Padding for future expansion */ - void (*_cal_reserved0) (void); - void (*_cal_reserved1) (void); - void (*_cal_reserved2) (void); - void (*_cal_reserved3) (void); - void (*_cal_reserved4) (void); - -}; - -typedef ECalBackendSync * (*ECalBackendSyncFactoryFn) (void); -GType e_cal_backend_sync_get_type (void); -ECalBackendSyncStatus e_cal_backend_sync_is_read_only (ECalBackendSync *backend, - EDataCal *cal, - gboolean *read_only); -ECalBackendSyncStatus e_cal_backend_sync_get_cal_address (ECalBackendSync *backend, - EDataCal *cal, - char **address); -ECalBackendSyncStatus e_cal_backend_sync_get_alarm_email_address (ECalBackendSync *backend, - EDataCal *cal, - char **address); -ECalBackendSyncStatus e_cal_backend_sync_get_ldap_attribute (ECalBackendSync *backend, - EDataCal *cal, - char **attribute); -ECalBackendSyncStatus e_cal_backend_sync_get_static_capabilities (ECalBackendSync *backend, - EDataCal *cal, - char **capabiliites); -ECalBackendSyncStatus e_cal_backend_sync_open (ECalBackendSync *backend, - EDataCal *cal, - gboolean only_if_exists, - const char *username, - const char *password); -ECalBackendSyncStatus e_cal_backend_sync_remove (ECalBackendSync *backend, - EDataCal *cal); -ECalBackendSyncStatus e_cal_backend_sync_create_object (ECalBackendSync *backend, - EDataCal *cal, - char **calobj, - char **uid); -ECalBackendSyncStatus e_cal_backend_sync_modify_object (ECalBackendSync *backend, - EDataCal *cal, - const char *calobj, - CalObjModType mod, - char **old_object); -ECalBackendSyncStatus e_cal_backend_sync_remove_object (ECalBackendSync *backend, - EDataCal *cal, - const char *uid, - const char *rid, - CalObjModType mod, - char **object); -ECalBackendSyncStatus e_cal_backend_sync_discard_alarm (ECalBackendSync *backend, EDataCal *cal, const char *uid, const char *auid); - -ECalBackendSyncStatus e_cal_backend_sync_receive_objects (ECalBackendSync *backend, - EDataCal *cal, - const char *calobj); -ECalBackendSyncStatus e_cal_backend_sync_send_objects (ECalBackendSync *backend, - EDataCal *cal, - const char *calobj, - GList **users, - char **modified_calobj); -ECalBackendSyncStatus e_cal_backend_sync_get_default_object (ECalBackendSync *backend, - EDataCal *cal, - char **object); - -ECalBackendSyncStatus e_cal_backend_sync_get_object (ECalBackendSync *backend, - EDataCal *cal, - const char *uid, - const char *rid, - char **object); - -ECalBackendSyncStatus e_cal_backend_sync_get_object_list (ECalBackendSync *backend, - EDataCal *cal, - const char *sexp, - GList **objects); - -ECalBackendSyncStatus e_cal_backend_sync_get_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid, char **object); -ECalBackendSyncStatus e_cal_backend_sync_add_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzobj); -ECalBackendSyncStatus e_cal_backend_sync_set_default_timezone (ECalBackendSync *backend, EDataCal *cal, const char *tzid); - -ECalBackendSyncStatus e_cal_backend_sync_get_changes (ECalBackendSync *backend, EDataCal *cal, const char *change_id, GList **adds, GList **modifies, GList **deletes); -ECalBackendSyncStatus e_cal_backend_sync_get_free_busy (ECalBackendSync *backend, EDataCal *cal, GList *users, time_t start, time_t end, GList **freebusy); - -G_END_DECLS - -#endif /* ! __E_CAL_BACKEND_SYNC_H__ */ diff --git a/calendar/libedata-cal/e-cal-backend-util.c b/calendar/libedata-cal/e-cal-backend-util.c deleted file mode 100644 index c2c32b456..000000000 --- a/calendar/libedata-cal/e-cal-backend-util.c +++ /dev/null @@ -1,61 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* Evolution calendar - generic backend class - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2001 Ximian, Inc. - * - * Authors: Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#include <string.h> -#include "e-cal-backend-util.h" -#include <libedataserver/e-account-list.h> - -static EAccountList *accounts; - -gboolean -e_cal_backend_mail_account_get_default (char **address, char **name) -{ - const EAccount *account; - - /* FIXME I think this leaks the gconf client */ - if (accounts == NULL) - accounts = e_account_list_new(gconf_client_get_default()); - - account = e_account_list_get_default(accounts); - if (account) { - *address = g_strdup(account->id->address); - *name = g_strdup(account->id->name); - } - - return account != NULL; -} - -gboolean -e_cal_backend_mail_account_is_valid (char *user, char **name) -{ - const EAccount *account; - - /* FIXME I think this leaks the gconf client */ - if (accounts == NULL) - accounts = e_account_list_new(gconf_client_get_default()); - - account = e_account_list_find(accounts, E_ACCOUNT_FIND_ID_ADDRESS, user); - if (account) - *name = g_strdup(account->id->name); - - return account != NULL; -} diff --git a/calendar/libedata-cal/e-cal-backend-util.h b/calendar/libedata-cal/e-cal-backend-util.h deleted file mode 100644 index 3061ef46d..000000000 --- a/calendar/libedata-cal/e-cal-backend-util.h +++ /dev/null @@ -1,39 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* Evolution calendar - generic backend class - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2001 Ximian, Inc. - * - * Authors: Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_BACKEND_UTIL_H -#define E_CAL_BACKEND_UTIL_H - -#include <libedata-cal/e-cal-backend.h> - -G_BEGIN_DECLS - -/* - * Functions for accessing mail configuration - */ - -gboolean e_cal_backend_mail_account_get_default (char **address, char **name); -gboolean e_cal_backend_mail_account_is_valid (char *user, char **name); - -G_END_DECLS - -#endif diff --git a/calendar/libedata-cal/e-cal-backend.c b/calendar/libedata-cal/e-cal-backend.c deleted file mode 100644 index 4d3ac248b..000000000 --- a/calendar/libedata-cal/e-cal-backend.c +++ /dev/null @@ -1,1301 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* Evolution calendar - generic backend class - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Authors: Federico Mena-Quintero <federico@ximian.com> - * JP Rosevear <jpr@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#include <config.h> -#include <libxml/parser.h> -#include <libxml/parserInternals.h> -#include <libxml/xmlmemory.h> - -#include "e-cal-backend.h" - - - -/* A category that exists in some of the objects of the calendar */ -typedef struct { - /* Category name, also used as the key in the categories hash table */ - char *name; - - /* Number of objects that have this category */ - int refcount; -} ECalBackendCategory; - -/* Private part of the CalBackend structure */ -struct _ECalBackendPrivate { - /* The source for this backend */ - ESource *source; - - /* URI, from source. This is cached, since we return const. */ - char *uri; - - /* The kind of components for this backend */ - icalcomponent_kind kind; - - /* List of Cal objects */ - GMutex *clients_mutex; - GList *clients; - - GMutex *queries_mutex; - EList *queries; - - /* Hash table of live categories, temporary hash of - * added/removed categories, and idle handler for sending - * category_changed. - */ - GHashTable *categories; - GHashTable *changed_categories; - guint category_idle_id; - - /* ECalBackend to pass notifications on to */ - ECalBackend *notification_proxy; -}; - -/* Property IDs */ -enum props { - PROP_0, - PROP_SOURCE, - PROP_URI, - PROP_KIND -}; - -/* Signal IDs */ -enum { - LAST_CLIENT_GONE, - OPENED, - REMOVED, - LAST_SIGNAL -}; -static guint e_cal_backend_signals[LAST_SIGNAL]; - -static void e_cal_backend_class_init (ECalBackendClass *class); -static void e_cal_backend_init (ECalBackend *backend); -static void e_cal_backend_finalize (GObject *object); - -static void notify_categories_changed (ECalBackend *backend); - -#define CLASS(backend) (E_CAL_BACKEND_CLASS (G_OBJECT_GET_CLASS (backend))) - -static GObjectClass *parent_class; - - - -/** - * e_cal_backend_get_type: - * @void: - * - * Registers the #ECalBackend class if necessary, and returns the type ID - * associated to it. - * - * Return value: The type ID of the #ECalBackend class. - **/ -GType -e_cal_backend_get_type (void) -{ - static GType e_cal_backend_type = 0; - - if (!e_cal_backend_type) { - static GTypeInfo info = { - sizeof (ECalBackendClass), - (GBaseInitFunc) NULL, - (GBaseFinalizeFunc) NULL, - (GClassInitFunc) e_cal_backend_class_init, - NULL, NULL, - sizeof (ECalBackend), - 0, - (GInstanceInitFunc) e_cal_backend_init, - }; - e_cal_backend_type = g_type_register_static (G_TYPE_OBJECT, "ECalBackend", &info, 0); - } - - return e_cal_backend_type; -} - -static void -e_cal_backend_set_property (GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) -{ - ECalBackend *backend; - ECalBackendPrivate *priv; - - backend = E_CAL_BACKEND (object); - priv = backend->priv; - - switch (property_id) { - case PROP_SOURCE: - { - ESource *new_source; - - new_source = g_value_get_object (value); - if (new_source) - g_object_ref (new_source); - - if (priv->source) - g_object_unref (priv->source); - - priv->source = new_source; - - /* Cache the URI */ - if (new_source) { - g_free (priv->uri); - priv->uri = e_source_get_uri (priv->source); - } - } - break; - case PROP_URI: - if (!priv->source) { - g_free (priv->uri); - priv->uri = g_value_dup_string (value); - } - break; - case PROP_KIND: - priv->kind = g_value_get_ulong (value); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); - break; - } -} - -static void -e_cal_backend_get_property (GObject *object, guint property_id, GValue *value, GParamSpec *pspec) -{ - ECalBackend *backend; - ECalBackendPrivate *priv; - - backend = E_CAL_BACKEND (object); - priv = backend->priv; - - switch (property_id) { - case PROP_SOURCE: - g_value_set_object (value, e_cal_backend_get_source (backend)); - break; - case PROP_URI: - g_value_set_string (value, e_cal_backend_get_uri (backend)); - break; - case PROP_KIND: - g_value_set_ulong (value, e_cal_backend_get_kind (backend)); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); - break; - } -} - -/* Class initialization function for the calendar backend */ -static void -e_cal_backend_class_init (ECalBackendClass *class) -{ - GObjectClass *object_class; - - parent_class = (GObjectClass *) g_type_class_peek_parent (class); - - object_class = (GObjectClass *) class; - - object_class->set_property = e_cal_backend_set_property; - object_class->get_property = e_cal_backend_get_property; - object_class->finalize = e_cal_backend_finalize; - - g_object_class_install_property (object_class, PROP_SOURCE, - g_param_spec_object ("source", NULL, NULL, E_TYPE_SOURCE, - G_PARAM_READABLE | G_PARAM_WRITABLE - | G_PARAM_CONSTRUCT_ONLY)); - - g_object_class_install_property (object_class, PROP_URI, - g_param_spec_string ("uri", NULL, NULL, "", - G_PARAM_READABLE | G_PARAM_WRITABLE - | G_PARAM_CONSTRUCT_ONLY)); - - g_object_class_install_property (object_class, PROP_KIND, - g_param_spec_ulong ("kind", NULL, NULL, - ICAL_NO_COMPONENT, ICAL_XLICMIMEPART_COMPONENT, - ICAL_NO_COMPONENT, - G_PARAM_READABLE | G_PARAM_WRITABLE - | G_PARAM_CONSTRUCT_ONLY)); - e_cal_backend_signals[LAST_CLIENT_GONE] = - g_signal_new ("last_client_gone", - G_TYPE_FROM_CLASS (class), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalBackendClass, last_client_gone), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - e_cal_backend_signals[OPENED] = - g_signal_new ("opened", - G_TYPE_FROM_CLASS (class), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalBackendClass, opened), - NULL, NULL, - g_cclosure_marshal_VOID__ENUM, - G_TYPE_NONE, 1, - G_TYPE_INT); - e_cal_backend_signals[REMOVED] = - g_signal_new ("removed", - G_TYPE_FROM_CLASS (class), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (ECalBackendClass, removed), - NULL, NULL, - g_cclosure_marshal_VOID__ENUM, - G_TYPE_NONE, 1, - G_TYPE_INT); - - class->last_client_gone = NULL; - class->opened = NULL; - class->obj_updated = NULL; - - class->get_cal_address = NULL; - class->get_alarm_email_address = NULL; - class->get_static_capabilities = NULL; - class->open = NULL; - class->is_loaded = NULL; - class->is_read_only = NULL; - class->start_query = NULL; - class->get_mode = NULL; - class->set_mode = NULL; - class->get_object = NULL; - class->get_default_object = NULL; - class->get_object_list = NULL; - class->get_free_busy = NULL; - class->get_changes = NULL; - class->discard_alarm = NULL; - class->create_object = NULL; - class->modify_object = NULL; - class->remove_object = NULL; - class->receive_objects = NULL; - class->send_objects = NULL; - class->get_timezone = NULL; - class->add_timezone = NULL; - class->set_default_timezone = NULL; -} - -/* Object initialization func for the calendar backend */ -void -e_cal_backend_init (ECalBackend *backend) -{ - ECalBackendPrivate *priv; - - priv = g_new0 (ECalBackendPrivate, 1); - backend->priv = priv; - - priv->clients = NULL; - priv->clients_mutex = g_mutex_new (); - - /* FIXME bonobo_object_ref/unref? */ - priv->queries = e_list_new((EListCopyFunc) g_object_ref, (EListFreeFunc) g_object_unref, NULL); - priv->queries_mutex = g_mutex_new (); - - priv->categories = g_hash_table_new (g_str_hash, g_str_equal); - priv->changed_categories = g_hash_table_new (g_str_hash, g_str_equal); -} - -/* Used from g_hash_table_foreach(), frees a ECalBackendCategory structure */ -static void -free_category_cb (gpointer key, gpointer value, gpointer data) -{ - ECalBackendCategory *c = value; - - g_free (c->name); - g_free (c); -} - -static gboolean -prune_changed_categories (gpointer key, gpointer value, gpointer data) -{ - ECalBackendCategory *c = value; - - if (!c->refcount) - free_category_cb (key, value, data); - return TRUE; -} - -void -e_cal_backend_finalize (GObject *object) -{ - ECalBackend *backend = (ECalBackend *)object; - ECalBackendPrivate *priv; - - priv = backend->priv; - - g_assert (priv->clients == NULL); - - g_object_unref (priv->queries); - - g_hash_table_foreach_remove (priv->changed_categories, prune_changed_categories, NULL); - g_hash_table_destroy (priv->changed_categories); - - g_hash_table_foreach (priv->categories, free_category_cb, NULL); - g_hash_table_destroy (priv->categories); - - g_mutex_free (priv->clients_mutex); - g_mutex_free (priv->queries_mutex); - - if (priv->category_idle_id) - g_source_remove (priv->category_idle_id); - - g_free (priv); - - G_OBJECT_CLASS (parent_class)->finalize (object); -} - - - -ESource * -e_cal_backend_get_source (ECalBackend *backend) -{ - ECalBackendPrivate *priv; - - g_return_val_if_fail (backend != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_BACKEND (backend), NULL); - - priv = backend->priv; - - return priv->source; -} - -/** - * e_cal_backend_get_uri: - * @backend: A calendar backend. - * - * Queries the URI of a calendar backend, which must already have an open - * calendar. - * - * Return value: The URI where the calendar is stored. - **/ -const char * -e_cal_backend_get_uri (ECalBackend *backend) -{ - ECalBackendPrivate *priv; - - g_return_val_if_fail (backend != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_BACKEND (backend), NULL); - - priv = backend->priv; - - return priv->uri; -} - -icalcomponent_kind -e_cal_backend_get_kind (ECalBackend *backend) -{ - ECalBackendPrivate *priv; - - g_return_val_if_fail (backend != NULL, ICAL_NO_COMPONENT); - g_return_val_if_fail (E_IS_CAL_BACKEND (backend), ICAL_NO_COMPONENT); - - priv = backend->priv; - - return priv->kind; -} - -static void -cal_destroy_cb (gpointer data, GObject *where_cal_was) -{ - ECalBackend *backend = E_CAL_BACKEND (data); - - e_cal_backend_remove_client (backend, (EDataCal *) where_cal_was); -} - -static void -listener_died_cb (gpointer cnx, gpointer data) -{ - EDataCal *cal = E_DATA_CAL (data); - - e_cal_backend_remove_client (e_data_cal_get_backend (cal), cal); -} - -static void -last_client_gone (ECalBackend *backend) -{ - g_signal_emit (backend, e_cal_backend_signals[LAST_CLIENT_GONE], 0); -} - -void -e_cal_backend_add_client (ECalBackend *backend, EDataCal *cal) -{ - ECalBackendPrivate *priv; - - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = backend->priv; - - bonobo_object_set_immortal (BONOBO_OBJECT (cal), TRUE); - - g_object_weak_ref (G_OBJECT (cal), cal_destroy_cb, backend); - - ORBit_small_listen_for_broken (e_data_cal_get_listener (cal), G_CALLBACK (listener_died_cb), cal); - - g_mutex_lock (priv->clients_mutex); - priv->clients = g_list_append (priv->clients, cal); - g_mutex_unlock (priv->clients_mutex); - - /* Tell the new client about the list of categories. - * (Ends up telling all the other clients too, but *shrug*.) - */ - /* FIXME This doesn't seem right at all */ - notify_categories_changed (backend); -} - -void -e_cal_backend_remove_client (ECalBackend *backend, EDataCal *cal) -{ - ECalBackendPrivate *priv; - - /* XXX this needs a bit more thinking wrt the mutex - we - should be holding it when we check to see if clients is - NULL */ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = backend->priv; - - /* Disconnect */ - g_mutex_lock (priv->clients_mutex); - priv->clients = g_list_remove (priv->clients, cal); - g_mutex_unlock (priv->clients_mutex); - - /* When all clients go away, notify the parent factory about it so that - * it may decide whether to kill the backend or not. - */ - if (!priv->clients) - last_client_gone (backend); -} - -void -e_cal_backend_add_query (ECalBackend *backend, EDataCalView *query) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_mutex_lock (backend->priv->queries_mutex); - - e_list_append (backend->priv->queries, query); - - g_mutex_unlock (backend->priv->queries_mutex); -} - -EList * -e_cal_backend_get_queries (ECalBackend *backend) -{ - g_return_val_if_fail (backend != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_BACKEND (backend), NULL); - - return g_object_ref (backend->priv->queries); -} - - -/** - * e_cal_backend_get_cal_address: - * @backend: A calendar backend. - * - * Queries the cal address associated with a calendar backend, which - * must already have an open calendar. - * - * Return value: The cal address associated with the calendar. - **/ -void -e_cal_backend_get_cal_address (ECalBackend *backend, EDataCal *cal) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->get_cal_address != NULL); - (* CLASS (backend)->get_cal_address) (backend, cal); -} - -void -e_cal_backend_get_alarm_email_address (ECalBackend *backend, EDataCal *cal) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->get_alarm_email_address != NULL); - (* CLASS (backend)->get_alarm_email_address) (backend, cal); -} - -void -e_cal_backend_get_ldap_attribute (ECalBackend *backend, EDataCal *cal) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->get_ldap_attribute != NULL); - (* CLASS (backend)->get_ldap_attribute) (backend, cal); -} - -void -e_cal_backend_get_static_capabilities (ECalBackend *backend, EDataCal *cal) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->get_static_capabilities != NULL); - (* CLASS (backend)->get_static_capabilities) (backend, cal); -} - -/** - * e_cal_backend_open: - * @backend: A calendar backend. - * @uristr: URI that contains the calendar data. - * @only_if_exists: Whether the calendar should be opened only if it already - * exists. If FALSE, a new calendar will be created when the specified @uri - * does not exist. - * @username: User name to use for authentication (if needed). - * @password: Password for @username. - * - * Opens a calendar backend with data from a calendar stored at the specified - * URI. - * - * Return value: An operation status code. - **/ -void -e_cal_backend_open (ECalBackend *backend, EDataCal *cal, gboolean only_if_exists, - const char *username, const char *password) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->open != NULL); - (* CLASS (backend)->open) (backend, cal, only_if_exists, username, password); -} - -void -e_cal_backend_remove (ECalBackend *backend, EDataCal *cal) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->remove != NULL); - (* CLASS (backend)->remove) (backend, cal); -} - -/** - * e_cal_backend_is_loaded: - * @backend: A calendar backend. - * - * Queries whether a calendar backend has been loaded yet. - * - * Return value: TRUE if the backend has been loaded with data, FALSE - * otherwise. - **/ -gboolean -e_cal_backend_is_loaded (ECalBackend *backend) -{ - gboolean result; - - g_return_val_if_fail (backend != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_BACKEND (backend), FALSE); - - g_assert (CLASS (backend)->is_loaded != NULL); - result = (* CLASS (backend)->is_loaded) (backend); - - return result; -} - -/** - * e_cal_backend_is_read_only - * @backend: A calendar backend. - * - * Queries whether a calendar backend is read only or not. - * - * Return value: TRUE if the calendar is read only, FALSE otherwise. - */ -void -e_cal_backend_is_read_only (ECalBackend *backend, EDataCal *cal) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->is_read_only != NULL); - (* CLASS (backend)->is_read_only) (backend, cal); -} - -void -e_cal_backend_start_query (ECalBackend *backend, EDataCalView *query) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->start_query != NULL); - (* CLASS (backend)->start_query) (backend, query); -} - -/** - * e_cal_backend_get_mode: - * @backend: A calendar backend. - * - * Queries whether a calendar backend is connected remotely. - * - * Return value: The current mode the calendar is in - **/ -CalMode -e_cal_backend_get_mode (ECalBackend *backend) -{ - CalMode result; - - g_return_val_if_fail (backend != NULL, FALSE); - g_return_val_if_fail (E_IS_CAL_BACKEND (backend), FALSE); - - g_assert (CLASS (backend)->get_mode != NULL); - result = (* CLASS (backend)->get_mode) (backend); - - return result; -} - - -/** - * e_cal_backend_set_mode: - * @backend: A calendar backend - * @mode: Mode to change to - * - * Sets the mode of the calendar - * - **/ -void -e_cal_backend_set_mode (ECalBackend *backend, CalMode mode) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->set_mode != NULL); - (* CLASS (backend)->set_mode) (backend, mode); -} - -void -e_cal_backend_get_default_object (ECalBackend *backend, EDataCal *cal) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->get_default_object != NULL); - (* CLASS (backend)->get_default_object) (backend, cal); -} - -/** - * e_cal_backend_get_object: - * @backend: A calendar backend. - * @uid: Unique identifier for a calendar object. - * @rid: ID for the object's recurrence to get. - * - * Queries a calendar backend for a calendar object based on its unique - * identifier and its recurrence ID (if a recurrent appointment). - * - * Return value: The string representation of a complete calendar wrapping the - * the sought object, or NULL if no object had the specified UID. - **/ -void -e_cal_backend_get_object (ECalBackend *backend, EDataCal *cal, const char *uid, const char *rid) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (uid != NULL); - - g_assert (CLASS (backend)->get_object != NULL); - (* CLASS (backend)->get_object) (backend, cal, uid, rid); -} - -/** - * e_cal_backend_get_object_list: - * @backend: - * @type: - * - * - * - * Return value: - **/ -void -e_cal_backend_get_object_list (ECalBackend *backend, EDataCal *cal, const char *sexp) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - g_assert (CLASS (backend)->get_object_list != NULL); - return (* CLASS (backend)->get_object_list) (backend, cal, sexp); -} - -/** - * e_cal_backend_get_free_busy: - * @backend: A calendar backend. - * @users: List of users to get free/busy information for. - * @start: Start time for query. - * @end: End time for query. - * - * Gets a free/busy object for the given time interval - * - * Return value: a list of CalObj's - **/ -void -e_cal_backend_get_free_busy (ECalBackend *backend, EDataCal *cal, GList *users, time_t start, time_t end) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (start != -1 && end != -1); - g_return_if_fail (start <= end); - - g_assert (CLASS (backend)->get_free_busy != NULL); - (* CLASS (backend)->get_free_busy) (backend, cal, users, start, end); -} - -/** - * e_cal_backend_get_changes: - * @backend: A calendar backend - * @change_id: A unique uid for the callers change list - * - * Builds a sequence of objects and the type of change that occurred on them since - * the last time the give change_id was seen - * - * Return value: A list of the objects that changed and the type of change - **/ -void -e_cal_backend_get_changes (ECalBackend *backend, EDataCal *cal, const char *change_id) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (change_id != NULL); - - g_assert (CLASS (backend)->get_changes != NULL); - (* CLASS (backend)->get_changes) (backend, cal, change_id); -} - -/** - * e_cal_backend_discard_alarm - * @backend: A calendar backend. - * @uid: UID of the component to discard the alarm from. - * @auid: Alarm ID. - * - * Discards an alarm from the given component. This allows the specific backend - * to do whatever is needed to really discard the alarm. - * - **/ -void -e_cal_backend_discard_alarm (ECalBackend *backend, EDataCal *cal, const char *uid, const char *auid) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (uid != NULL); - g_return_if_fail (auid != NULL); - - g_assert (CLASS (backend)->discard_alarm != NULL); - (* CLASS (backend)->discard_alarm) (backend, cal, uid, auid); -} - -void -e_cal_backend_create_object (ECalBackend *backend, EDataCal *cal, const char *calobj) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (calobj != NULL); - - if (CLASS (backend)->create_object) - (* CLASS (backend)->create_object) (backend, cal, calobj); - else - e_data_cal_notify_object_created (cal, GNOME_Evolution_Calendar_PermissionDenied, NULL, NULL); -} - -void -e_cal_backend_modify_object (ECalBackend *backend, EDataCal *cal, const char *calobj, CalObjModType mod) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (calobj != NULL); - - if (CLASS (backend)->modify_object) - (* CLASS (backend)->modify_object) (backend, cal, calobj, mod); - else - e_data_cal_notify_object_removed (cal, GNOME_Evolution_Calendar_PermissionDenied, NULL, NULL); -} - -/** - * e_cal_backend_remove_object: - * @backend: A calendar backend. - * @uid: Unique identifier of the object to remove. - * @rid: A recurrence ID. - * - * Removes an object in a calendar backend. The backend will notify all of its - * clients about the change. - * - **/ -void -e_cal_backend_remove_object (ECalBackend *backend, EDataCal *cal, const char *uid, const char *rid, CalObjModType mod) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (uid != NULL); - - g_assert (CLASS (backend)->remove_object != NULL); - (* CLASS (backend)->remove_object) (backend, cal, uid, rid, mod); -} - -void -e_cal_backend_receive_objects (ECalBackend *backend, EDataCal *cal, const char *calobj) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (calobj != NULL); - - g_assert (CLASS (backend)->receive_objects != NULL); - (* CLASS (backend)->receive_objects) (backend, cal, calobj); -} - -void -e_cal_backend_send_objects (ECalBackend *backend, EDataCal *cal, const char *calobj) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (calobj != NULL); - - g_assert (CLASS (backend)->send_objects != NULL); - (* CLASS (backend)->send_objects) (backend, cal, calobj); -} - -/** - * e_cal_backend_get_timezone: - * @backend: A calendar backend. - * @tzid: Unique identifier of a VTIMEZONE object. Note that this must not be - * NULL. - * - * Returns the icaltimezone* corresponding to the TZID, or NULL if the TZID - * can't be found. - * - * Returns: The icaltimezone* corresponding to the given TZID, or NULL. - **/ -void -e_cal_backend_get_timezone (ECalBackend *backend, EDataCal *cal, const char *tzid) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (tzid != NULL); - - g_assert (CLASS (backend)->get_timezone != NULL); - (* CLASS (backend)->get_timezone) (backend, cal, tzid); -} - -/** - * e_cal_backend_set_default_timezone: - * @backend: A calendar backend. - * @tzid: The TZID identifying the timezone. - * - * Sets the default timezone for the calendar, which is used to resolve - * DATE and floating DATE-TIME values. - * - * Returns: TRUE if the VTIMEZONE data for the timezone was found, or FALSE if - * not. - **/ -void -e_cal_backend_set_default_timezone (ECalBackend *backend, EDataCal *cal, const char *tzid) -{ - g_return_if_fail (backend != NULL); - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (tzid != NULL); - - g_assert (CLASS (backend)->set_default_timezone != NULL); - (* CLASS (backend)->set_default_timezone) (backend, cal, tzid); -} - -/** - * e_cal_backend_add_timezone - * @backend: A calendar backend. - * @tzobj: The timezone object, in a string. - * - * Add a timezone object to the given backend. - * - * Returns: TRUE if successful, or FALSE if not. - */ -void -e_cal_backend_add_timezone (ECalBackend *backend, EDataCal *cal, const char *tzobj) -{ - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - g_return_if_fail (tzobj != NULL); - g_return_if_fail (CLASS (backend)->add_timezone != NULL); - - (* CLASS (backend)->add_timezone) (backend, cal, tzobj); -} - -icaltimezone * -e_cal_backend_internal_get_default_timezone (ECalBackend *backend) -{ - g_return_val_if_fail (E_IS_CAL_BACKEND (backend), NULL); - g_return_val_if_fail (CLASS (backend)->internal_get_default_timezone != NULL, NULL); - - return (* CLASS (backend)->internal_get_default_timezone) (backend); -} - -icaltimezone * -e_cal_backend_internal_get_timezone (ECalBackend *backend, const char *tzid) -{ - g_return_val_if_fail (E_IS_CAL_BACKEND (backend), NULL); - g_return_val_if_fail (tzid != NULL, NULL); - g_return_val_if_fail (CLASS (backend)->internal_get_timezone != NULL, NULL); - - return (* CLASS (backend)->internal_get_timezone) (backend, tzid); -} - -void -e_cal_backend_set_notification_proxy (ECalBackend *backend, ECalBackend *proxy) -{ - ECalBackendPrivate *priv; - - g_return_if_fail (E_IS_CAL_BACKEND (backend)); - - priv = backend->priv; - - priv->notification_proxy = proxy; -} - -/** - * e_cal_backend_notify_object_created: - * @backend: A calendar backend. - * @calobj: iCalendar representation of new object - * - * Notifies each of the backend's listeners about a new object. - * - * cal_notify_object_created() calls this for you. You only need to - * call e_cal_backend_notify_object_created() yourself to report objects - * created by non-PCS clients. - **/ -void -e_cal_backend_notify_object_created (ECalBackend *backend, const char *calobj) -{ - ECalBackendPrivate *priv; - EList *queries; - EIterator *iter; - EDataCalView *query; - - priv = backend->priv; - - if (priv->notification_proxy) { - e_cal_backend_notify_object_created (priv->notification_proxy, calobj); - return; - } - - queries = e_cal_backend_get_queries (backend); - iter = e_list_get_iterator (queries); - - while (e_iterator_is_valid (iter)) { - query = QUERY (e_iterator_get (iter)); - - bonobo_object_ref (query); - if (e_data_cal_view_object_matches (query, calobj)) - e_data_cal_view_notify_objects_added_1 (query, calobj); - bonobo_object_unref (query); - - e_iterator_next (iter); - } - g_object_unref (iter); - g_object_unref (queries); -} - -/** - * e_cal_backend_notify_object_modified: - * @backend: A calendar backend. - * @old_object: iCalendar representation of the original form of the object - * @object: iCalendar representation of the new form of the object - * - * Notifies each of the backend's listeners about a modified object. - * - * cal_notify_object_modified() calls this for you. You only need to - * call e_cal_backend_notify_object_modified() yourself to report objects - * modified by non-PCS clients. - **/ -void -e_cal_backend_notify_object_modified (ECalBackend *backend, - const char *old_object, const char *object) -{ - ECalBackendPrivate *priv; - EList *queries; - EIterator *iter; - EDataCalView *query; - gboolean old_match, new_match; - - priv = backend->priv; - - if (priv->notification_proxy) { - e_cal_backend_notify_object_modified (priv->notification_proxy, old_object, object); - return; - } - - queries = e_cal_backend_get_queries (backend); - iter = e_list_get_iterator (queries); - - while (e_iterator_is_valid (iter)) { - query = QUERY (e_iterator_get (iter)); - - bonobo_object_ref (query); - - old_match = e_data_cal_view_object_matches (query, old_object); - new_match = e_data_cal_view_object_matches (query, object); - if (old_match && new_match) - e_data_cal_view_notify_objects_modified_1 (query, object); - else if (new_match) - e_data_cal_view_notify_objects_added_1 (query, object); - else if (old_match) { - icalcomponent *comp; - - comp = icalcomponent_new_from_string ((char *)old_object); - e_data_cal_view_notify_objects_removed_1 (query, icalcomponent_get_uid (comp)); - icalcomponent_free (comp); - } - - bonobo_object_unref (query); - - e_iterator_next (iter); - } - g_object_unref (iter); - g_object_unref (queries); -} - -/** - * e_cal_backend_notify_object_removed: - * @backend: A calendar backend. - * @uid: the UID of the removed object - * @old_object: iCalendar representation of the removed object - * - * Notifies each of the backend's listeners about a removed object. - * - * cal_notify_object_removed() calls this for you. You only need to - * call e_cal_backend_notify_object_removed() yourself to report objects - * removed by non-PCS clients. - **/ -void -e_cal_backend_notify_object_removed (ECalBackend *backend, const char *uid, - const char *old_object) -{ - ECalBackendPrivate *priv; - EList *queries; - EIterator *iter; - EDataCalView *query; - - priv = backend->priv; - - if (priv->notification_proxy) { - e_cal_backend_notify_object_removed (priv->notification_proxy, uid, old_object); - return; - } - - queries = e_cal_backend_get_queries (backend); - iter = e_list_get_iterator (queries); - - while (e_iterator_is_valid (iter)) { - query = QUERY (e_iterator_get (iter)); - - bonobo_object_ref (query); - if (e_data_cal_view_object_matches (query, old_object)) - e_data_cal_view_notify_objects_removed_1 (query, uid); - bonobo_object_unref (query); - - e_iterator_next (iter); - } - g_object_unref (iter); - g_object_unref (queries); -} - -/** - * e_cal_backend_notify_mode: - * @backend: A calendar backend. - * @status: Status of the mode set - * @mode: the current mode - * - * Notifies each of the backend's listeners about the results of a - * setMode call. - **/ -void -e_cal_backend_notify_mode (ECalBackend *backend, - GNOME_Evolution_Calendar_CalListener_SetModeStatus status, - GNOME_Evolution_Calendar_CalMode mode) -{ - ECalBackendPrivate *priv = backend->priv; - GList *l; - - if (priv->notification_proxy) { - e_cal_backend_notify_mode (priv->notification_proxy, status, mode); - return; - } - - for (l = priv->clients; l; l = l->next) - e_data_cal_notify_mode (l->data, status, mode); -} - -/** - * e_cal_backend_notify_error: - * @backend: A calendar backend. - * @message: Error message - * - * Notifies each of the backend's listeners about an error - **/ -void -e_cal_backend_notify_error (ECalBackend *backend, const char *message) -{ - ECalBackendPrivate *priv = backend->priv; - GList *l; - - if (priv->notification_proxy) { - e_cal_backend_notify_error (priv->notification_proxy, message); - return; - } - - for (l = priv->clients; l; l = l->next) - e_data_cal_notify_error (l->data, message); -} - -static void -add_category_cb (gpointer name, gpointer category, gpointer data) -{ - GNOME_Evolution_Calendar_StringSeq *seq = data; - - seq->_buffer[seq->_length++] = CORBA_string_dup (name); -} - -static void -notify_categories_changed (ECalBackend *backend) -{ - ECalBackendPrivate *priv = backend->priv; - GNOME_Evolution_Calendar_StringSeq *seq; - GList *l; - - /* Build the sequence of category names */ - seq = GNOME_Evolution_Calendar_StringSeq__alloc (); - seq->_length = 0; - seq->_maximum = g_hash_table_size (priv->categories); - seq->_buffer = CORBA_sequence_CORBA_string_allocbuf (seq->_maximum); - CORBA_sequence_set_release (seq, TRUE); - - g_hash_table_foreach (priv->categories, add_category_cb, seq); - - /* Notify the clients */ - for (l = priv->clients; l; l = l->next) - e_data_cal_notify_categories_changed (l->data, seq); - - CORBA_free (seq); -} - -static gboolean -idle_notify_categories_changed (gpointer data) -{ - ECalBackend *backend = E_CAL_BACKEND (data); - ECalBackendPrivate *priv = backend->priv; - - if (g_hash_table_size (priv->changed_categories)) { - notify_categories_changed (backend); - g_hash_table_foreach_remove (priv->changed_categories, prune_changed_categories, NULL); - } - - priv->category_idle_id = 0; - - return FALSE; -} - -/** - * e_cal_backend_ref_categories: - * @backend: A calendar backend - * @categories: a list of categories - * - * Adds 1 to the refcount of each of the named categories. If any of - * the categories are new, clients will be notified of the updated - * category list at idle time. - **/ -void -e_cal_backend_ref_categories (ECalBackend *backend, GSList *categories) -{ - ECalBackendPrivate *priv; - ECalBackendCategory *c; - const char *name; - - priv = backend->priv; - - while (categories) { - name = categories->data; - c = g_hash_table_lookup (priv->categories, name); - - if (c) - c->refcount++; - else { - /* See if it was recently removed */ - - c = g_hash_table_lookup (priv->changed_categories, name); - if (c && c->refcount == 0) { - /* Move it back to the set of live categories */ - g_hash_table_remove (priv->changed_categories, c->name); - - c->refcount = 1; - g_hash_table_insert (priv->categories, c->name, c); - } else { - /* Create a new category */ - c = g_new (ECalBackendCategory, 1); - c->name = g_strdup (name); - c->refcount = 1; - g_hash_table_insert (priv->categories, c->name, c); - g_hash_table_insert (priv->changed_categories, c->name, c); - } - } - - categories = categories->next; - } - - if (g_hash_table_size (priv->changed_categories) && - !priv->category_idle_id) - priv->category_idle_id = g_idle_add (idle_notify_categories_changed, backend); -} - -/** - * e_cal_backend_unref_categories: - * @backend: A calendar backend - * @categories: a list of categories - * - * Subtracts 1 from the refcount of each of the named categories. If - * any of the refcounts go down to 0, clients will be notified of the - * updated category list at idle time. - **/ -void -e_cal_backend_unref_categories (ECalBackend *backend, GSList *categories) -{ - ECalBackendPrivate *priv; - ECalBackendCategory *c; - const char *name; - - priv = backend->priv; - - while (categories) { - name = categories->data; - c = g_hash_table_lookup (priv->categories, name); - - if (c) { - g_assert (c != NULL); - g_assert (c->refcount > 0); - - c->refcount--; - - if (c->refcount == 0) { - g_hash_table_remove (priv->categories, c->name); - g_hash_table_insert (priv->changed_categories, c->name, c); - } - } - - categories = categories->next; - } - - if (g_hash_table_size (priv->changed_categories) && - !priv->category_idle_id) - priv->category_idle_id = g_idle_add (idle_notify_categories_changed, backend); -} diff --git a/calendar/libedata-cal/e-cal-backend.h b/calendar/libedata-cal/e-cal-backend.h deleted file mode 100644 index 9650a1d42..000000000 --- a/calendar/libedata-cal/e-cal-backend.h +++ /dev/null @@ -1,181 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* Evolution calendar - generic backend class - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Authors: Federico Mena-Quintero <federico@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_CAL_BACKEND_H -#define E_CAL_BACKEND_H - -#include <libedataserver/e-list.h> -#include <libedataserver/e-source.h> -#include <libecal/e-cal-util.h> -#include <libecal/e-cal-component.h> -#include <libedata-cal/Evolution-DataServer-Calendar.h> -#include <libedata-cal/e-data-cal-common.h> -#include <libedata-cal/e-data-cal.h> -#include <libedata-cal/e-data-cal-view.h> - -G_BEGIN_DECLS - - - -#define E_TYPE_CAL_BACKEND (e_cal_backend_get_type ()) -#define E_CAL_BACKEND(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_CAL_BACKEND, ECalBackend)) -#define E_CAL_BACKEND_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_CAL_BACKEND, \ - ECalBackendClass)) -#define E_IS_CAL_BACKEND(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_CAL_BACKEND)) -#define E_IS_CAL_BACKEND_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_CAL_BACKEND)) - -typedef struct _ECalBackendPrivate ECalBackendPrivate; - -struct _ECalBackend { - GObject object; - - ECalBackendPrivate *priv; -}; - -struct _ECalBackendClass { - GObjectClass parent_class; - - /* Notification signals */ - void (* last_client_gone) (ECalBackend *backend); - void (* cal_added) (ECalBackend *backend, EDataCal *cal); - - gboolean (* is_loaded) (ECalBackend *backend); - - /* FIXME What to pass back here */ - void (* opened) (ECalBackend *backend, int status); - void (* removed) (ECalBackend *backend, int status); - void (* obj_updated) (ECalBackend *backend, const char *uid); - - /* Virtual methods */ - void (* is_read_only) (ECalBackend *backend, EDataCal *cal); - void (* get_cal_address) (ECalBackend *backend, EDataCal *cal); - void (* get_alarm_email_address) (ECalBackend *backend, EDataCal *cal); - void (* get_ldap_attribute) (ECalBackend *backend, EDataCal *cal); - void (* get_static_capabilities) (ECalBackend *backend, EDataCal *cal); - - void (* open) (ECalBackend *backend, EDataCal *cal, gboolean only_if_exists, const char *username, const char *password); - void (* remove) (ECalBackend *backend, EDataCal *cal); - - /* Object related virtual methods */ - void (* create_object) (ECalBackend *backend, EDataCal *cal, const char *calobj); - void (* modify_object) (ECalBackend *backend, EDataCal *cal, const char *calobj, CalObjModType mod); - void (* remove_object) (ECalBackend *backend, EDataCal *cal, const char *uid, const char *rid, CalObjModType mod); - - void (* discard_alarm) (ECalBackend *backend, EDataCal *cal, const char *uid, const char *auid); - - void (* receive_objects) (ECalBackend *backend, EDataCal *cal, const char *calobj); - void (* send_objects) (ECalBackend *backend, EDataCal *cal, const char *calobj); - - void (* get_default_object) (ECalBackend *backend, EDataCal *cal); - void (* get_object) (ECalBackend *backend, EDataCal *cal, const char *uid, const char *rid); - void (* get_object_list) (ECalBackend *backend, EDataCal *cal, const char *sexp); - - /* Timezone related virtual methods */ - void (* get_timezone) (ECalBackend *backend, EDataCal *cal, const char *tzid); - void (* add_timezone) (ECalBackend *backend, EDataCal *cal, const char *object); - void (* set_default_timezone) (ECalBackend *backend, EDataCal *cal, const char *tzid); - - void (* start_query) (ECalBackend *backend, EDataCalView *query); - - /* Mode relate virtual methods */ - CalMode (* get_mode) (ECalBackend *backend); - void (* set_mode) (ECalBackend *backend, CalMode mode); - - void (* get_free_busy) (ECalBackend *backend, EDataCal *cal, GList *users, time_t start, time_t end); - void (* get_changes) (ECalBackend *backend, EDataCal *cal, const char *change_id); - - /* Internal methods for use only in the pcs */ - icaltimezone *(* internal_get_default_timezone) (ECalBackend *backend); - icaltimezone *(* internal_get_timezone) (ECalBackend *backend, const char *tzid); -}; - -GType e_cal_backend_get_type (void); - -ESource *e_cal_backend_get_source (ECalBackend *backend); -const char *e_cal_backend_get_uri (ECalBackend *backend); -icalcomponent_kind e_cal_backend_get_kind (ECalBackend *backend); - -void e_cal_backend_add_client (ECalBackend *backend, EDataCal *cal); -void e_cal_backend_remove_client (ECalBackend *backend, EDataCal *cal); - -void e_cal_backend_add_query (ECalBackend *backend, EDataCalView *query); -EList *e_cal_backend_get_queries (ECalBackend *backend); - -void e_cal_backend_is_read_only (ECalBackend *backend, EDataCal *cal); -void e_cal_backend_get_cal_address (ECalBackend *backend, EDataCal *cal); -void e_cal_backend_get_alarm_email_address (ECalBackend *backend, EDataCal *cal); -void e_cal_backend_get_ldap_attribute (ECalBackend *backend, EDataCal *cal); -void e_cal_backend_get_static_capabilities (ECalBackend *backend, EDataCal *cal); - -void e_cal_backend_open (ECalBackend *backend, EDataCal *cal, gboolean only_if_exists, const char *username, const char *password); -void e_cal_backend_remove (ECalBackend *backend, EDataCal *cal); - -void e_cal_backend_create_object (ECalBackend *backend, EDataCal *cal, const char *calobj); -void e_cal_backend_modify_object (ECalBackend *backend, EDataCal *cal, const char *calobj, CalObjModType mod); -void e_cal_backend_remove_object (ECalBackend *backend, EDataCal *cal, const char *uid, const char *rid, CalObjModType mod); - -void e_cal_backend_discard_alarm (ECalBackend *backend, EDataCal *cal, const char *uid, const char *auid); - -void e_cal_backend_receive_objects (ECalBackend *backend, EDataCal *cal, const char *calobj); -void e_cal_backend_send_objects (ECalBackend *backend, EDataCal *cal, const char *calobj); - -void e_cal_backend_get_default_object (ECalBackend *backend, EDataCal *cal); -void e_cal_backend_get_object (ECalBackend *backend, EDataCal *cal, const char *uid, const char *rid); -void e_cal_backend_get_object_list (ECalBackend *backend, EDataCal *cal, const char *sexp); - -gboolean e_cal_backend_is_loaded (ECalBackend *backend); - -void e_cal_backend_start_query (ECalBackend *backend, EDataCalView *query); - -CalMode e_cal_backend_get_mode (ECalBackend *backend); -void e_cal_backend_set_mode (ECalBackend *backend, CalMode mode); - -void e_cal_backend_get_timezone (ECalBackend *backend, EDataCal *cal, const char *tzid); -void e_cal_backend_add_timezone (ECalBackend *backend, EDataCal *cal, const char *object); -void e_cal_backend_set_default_timezone (ECalBackend *backend, EDataCal *cal, const char *tzid); - -void e_cal_backend_get_changes (ECalBackend *backend, EDataCal *cal, const char *change_id); -void e_cal_backend_get_free_busy (ECalBackend *backend, EDataCal *cal, GList *users, time_t start, time_t end); - -icaltimezone* e_cal_backend_internal_get_default_timezone (ECalBackend *backend); -icaltimezone* e_cal_backend_internal_get_timezone (ECalBackend *backend, const char *tzid); - -void e_cal_backend_last_client_gone (ECalBackend *backend); - -void e_cal_backend_set_notification_proxy (ECalBackend *backend, ECalBackend *proxy); -void e_cal_backend_notify_object_created (ECalBackend *backend, const char *calobj); -void e_cal_backend_notify_object_modified (ECalBackend *backend, const char *old_object, const char *object); -void e_cal_backend_notify_object_removed (ECalBackend *backend, const char *uid, const char *old_object); - -void e_cal_backend_notify_mode (ECalBackend *backend, - GNOME_Evolution_Calendar_CalListener_SetModeStatus status, - GNOME_Evolution_Calendar_CalMode mode); -void e_cal_backend_notify_error (ECalBackend *backend, const char *message); -void e_cal_backend_ref_categories (ECalBackend *backend, GSList *categories); -void e_cal_backend_unref_categories (ECalBackend *backend, GSList *categories); - - - -G_END_DECLS - -#endif diff --git a/calendar/libedata-cal/e-data-cal-common.h b/calendar/libedata-cal/e-data-cal-common.h deleted file mode 100644 index 2b373380d..000000000 --- a/calendar/libedata-cal/e-data-cal-common.h +++ /dev/null @@ -1,47 +0,0 @@ -/* Evolution calendar server - common declarations - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef CAL_COMMON_H -#define CAL_COMMON_H - -#include <glib/gmacros.h> - -G_BEGIN_DECLS - - - -typedef struct _ECalBackend ECalBackend; -typedef struct _ECalBackendClass ECalBackendClass; - -typedef struct _EDataCal EDataCal; -typedef struct _EDataCalClass EDataCalClass; - -typedef struct _EDataCalView EDataCalView; -typedef struct _EDataCalViewClass EDataCalViewClass; - -typedef struct _ECalBackendSExp ECalBackendSExp; -typedef struct _ECalBackendSExpClass ECalBackendSExpClass; - - - -G_END_DECLS - -#endif diff --git a/calendar/libedata-cal/e-data-cal-factory.c b/calendar/libedata-cal/e-data-cal-factory.c deleted file mode 100644 index 0b68bf4ca..000000000 --- a/calendar/libedata-cal/e-data-cal-factory.c +++ /dev/null @@ -1,508 +0,0 @@ -/* Evolution calendar factory - * - * Copyright (C) 2000-2003 Ximian, Inc. - * - * Authors: - * Federico Mena-Quintero <federico@ximian.com> - * JP Rosevear <jpr@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#include <bonobo-activation/bonobo-activation.h> -#include <bonobo/bonobo-exception.h> -#include <bonobo/bonobo-main.h> -#include <libedataserver/e-url.h> -#include <libedataserver/e-source.h> -#include "e-cal-backend.h" -#include "e-data-cal.h" -#include "e-data-cal-factory.h" - -#define PARENT_TYPE BONOBO_TYPE_OBJECT -#define DEFAULT_E_DATA_CAL_FACTORY_OAF_ID "OAFIID:GNOME_Evolution_DataServer_CalFactory:" BASE_VERSION - -static BonoboObjectClass *parent_class; - -/* Private part of the CalFactory structure */ -struct _EDataCalFactoryPrivate { - /* Hash table from URI method strings to GType * for backend class types */ - GHashTable *methods; - - /* Hash table from GnomeVFSURI structures to CalBackend objects */ - GHashTable *backends; - - /* OAFIID of the factory */ - char *iid; - - /* Whether we have been registered with OAF yet */ - guint registered : 1; -}; - -/* Signal IDs */ -enum SIGNALS { - LAST_CALENDAR_GONE, - LAST_SIGNAL -}; - -static guint signals[LAST_SIGNAL]; - -/* Opening calendars */ -static icalcomponent_kind -calobjtype_to_icalkind (const GNOME_Evolution_Calendar_CalObjType type) -{ - switch (type){ - case GNOME_Evolution_Calendar_TYPE_EVENT: - return ICAL_VEVENT_COMPONENT; - case GNOME_Evolution_Calendar_TYPE_TODO: - return ICAL_VTODO_COMPONENT; - case GNOME_Evolution_Calendar_TYPE_JOURNAL: - return ICAL_VJOURNAL_COMPONENT; - } - - return ICAL_NO_COMPONENT; -} - -static GType -get_backend_type (GHashTable *methods, const char *method, icalcomponent_kind kind) -{ - GHashTable *kinds; - GType type; - - kinds = g_hash_table_lookup (methods, method); - if (!kinds) - return 0; - - type = GPOINTER_TO_INT (g_hash_table_lookup (kinds, GINT_TO_POINTER (kind))); - - return type; -} - -/* Looks up a calendar backend in a factory's hash table of uri->cal. If - * *non-NULL, orig_uri_return will be set to point to the original key in the - * *hash table. - */ -static ECalBackend * -lookup_backend (EDataCalFactory *factory, const char *uristr) -{ - EDataCalFactoryPrivate *priv; - EUri *uri; - ECalBackend *backend; - char *tmp; - - priv = factory->priv; - - uri = e_uri_new (uristr); - if (!uri) - return NULL; - - tmp = e_uri_to_string (uri, FALSE); - backend = g_hash_table_lookup (priv->backends, tmp); - g_free (tmp); - e_uri_free (uri); - - return backend; -} - -/* Callback used when a backend loses its last connected client */ -static void -backend_last_client_gone_cb (ECalBackend *backend, gpointer data) -{ - EDataCalFactory *factory; - EDataCalFactoryPrivate *priv; - ECalBackend *ret_backend; - const char *uristr; - - fprintf (stderr, "backend_last_client_gone_cb() called!\n"); - - factory = E_DATA_CAL_FACTORY (data); - priv = factory->priv; - - /* Remove the backend from the hash table */ - - uristr = e_cal_backend_get_uri (backend); - g_assert (uristr != NULL); - - ret_backend = lookup_backend (factory, uristr); - g_assert (ret_backend != NULL); - g_assert (ret_backend == backend); - - g_hash_table_remove (priv->backends, uristr); - - g_signal_handlers_disconnect_matched (backend, G_SIGNAL_MATCH_DATA, - 0, 0, NULL, NULL, data); - - /* Notify upstream if there are no more backends */ - - if (g_hash_table_size (priv->backends) == 0) - g_signal_emit (G_OBJECT (factory), signals[LAST_CALENDAR_GONE], 0); -} - - - -static GNOME_Evolution_Calendar_Cal -impl_CalFactory_getCal (PortableServer_Servant servant, - const CORBA_char *source_xml, - const GNOME_Evolution_Calendar_CalObjType type, - const GNOME_Evolution_Calendar_CalListener listener, - CORBA_Environment *ev) -{ - EDataCalFactory *factory; - EDataCalFactoryPrivate *priv; - EDataCal *cal = CORBA_OBJECT_NIL; - ECalBackend *backend; - CORBA_Environment ev2; - GNOME_Evolution_Calendar_CalListener listener_copy; - GType backend_type; - ESource *source; - char *str_uri; - EUri *uri; - char *uri_type_string; - - factory = E_DATA_CAL_FACTORY (bonobo_object_from_servant (servant)); - priv = factory->priv; - - source = e_source_new_from_standalone_xml (source_xml); - if (!source) { - bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_InvalidURI); - - return CORBA_OBJECT_NIL; - } - - /* Get the URI so we can extract the protocol */ - str_uri = e_source_get_uri (source); - if (!str_uri) { - g_object_unref (source); - bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_InvalidURI); - - return CORBA_OBJECT_NIL; - } - - /* Parse the uri */ - uri = e_uri_new (str_uri); - g_free (str_uri); - - if (!uri) { - bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_InvalidURI); - - return CORBA_OBJECT_NIL; - } - uri_type_string = g_strdup_printf ("%s:%d", e_uri_to_string (uri, FALSE), type); - - /* Find the associated backend type (if any) */ - backend_type = get_backend_type (priv->methods, uri->protocol, calobjtype_to_icalkind (type)); - if (!backend_type) { - /* FIXME Distinguish between method and kind failures? */ - bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_UnsupportedMethod); - goto cleanup; - } - - /* Duplicate the listener object */ - CORBA_exception_init (&ev2); - listener_copy = CORBA_Object_duplicate (listener, &ev2); - - if (BONOBO_EX (&ev2)) { - g_warning (G_STRLOC ": could not duplicate the listener"); - bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_NilListener); - CORBA_exception_free (&ev2); - goto cleanup; - } - CORBA_exception_free (&ev2); - - /* Look for an existing backend */ - backend = lookup_backend (factory, uri_type_string); - if (!backend) { - /* There was no existing backend, create a new one */ - backend = g_object_new (backend_type, "source", source, "kind", calobjtype_to_icalkind (type), NULL); - if (!backend) { - g_warning (G_STRLOC ": could not instantiate backend"); - bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_UnsupportedMethod); - goto cleanup; - } - - /* Track the backend */ - g_hash_table_insert (priv->backends, g_strdup (uri_type_string), backend); - - g_signal_connect (G_OBJECT (backend), "last_client_gone", - G_CALLBACK (backend_last_client_gone_cb), - factory); - } - - /* Create the corba calendar */ - cal = e_data_cal_new (backend, uri_type_string, listener); - if (!cal) { - g_warning (G_STRLOC ": could not create the corba calendar"); - bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_UnsupportedMethod); - goto cleanup; - } - - /* Let the backend know about its clients corba clients */ - e_cal_backend_add_client (backend, cal); - - cleanup: - e_uri_free (uri); - g_free (uri_type_string); - g_object_unref (source); - - return CORBA_Object_duplicate (BONOBO_OBJREF (cal), ev); -} - - - -/** - * e_data_cal_factory_new: - * @void: - * - * Creates a new #EDataCalFactory object. - * - * Return value: A newly-created #EDataCalFactory, or NULL if its corresponding CORBA - * object could not be created. - **/ -EDataCalFactory * -e_data_cal_factory_new (void) -{ - EDataCalFactory *factory; - - factory = g_object_new (E_TYPE_DATA_CAL_FACTORY, - "poa", bonobo_poa_get_threaded (ORBIT_THREAD_HINT_PER_REQUEST, NULL), - NULL); - - return factory; -} - -/* Destroy handler for the calendar */ -static void -e_data_cal_factory_finalize (GObject *object) -{ - EDataCalFactory *factory; - EDataCalFactoryPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_DATA_CAL_FACTORY (object)); - - factory = E_DATA_CAL_FACTORY (object); - priv = factory->priv; - - g_hash_table_destroy (priv->methods); - priv->methods = NULL; - - /* Should we assert that there are no more backends? */ - g_hash_table_destroy (priv->backends); - priv->backends = NULL; - - if (priv->registered) { - bonobo_activation_active_server_unregister (priv->iid, BONOBO_OBJREF (factory)); - priv->registered = FALSE; - } - g_free (priv->iid); - - g_free (priv); - factory->priv = NULL; - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - -/* Class initialization function for the calendar factory */ -static void -e_data_cal_factory_class_init (EDataCalFactoryClass *klass) -{ - GObjectClass *object_class = (GObjectClass *) klass; - POA_GNOME_Evolution_Calendar_CalFactory__epv *epv = &klass->epv; - - parent_class = g_type_class_peek_parent (klass); - - signals[LAST_CALENDAR_GONE] = - g_signal_new ("last_calendar_gone", - G_TYPE_FROM_CLASS (klass), - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (EDataCalFactoryClass, last_calendar_gone), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - - /* Class method overrides */ - object_class->finalize = e_data_cal_factory_finalize; - - /* Epv methods */ - epv->getCal = impl_CalFactory_getCal; -} - -/* Object initialization function for the calendar factory */ -static void -e_data_cal_factory_init (EDataCalFactory *factory, EDataCalFactoryClass *klass) -{ - EDataCalFactoryPrivate *priv; - - priv = g_new0 (EDataCalFactoryPrivate, 1); - factory->priv = priv; - - priv->methods = g_hash_table_new_full (g_str_hash, g_str_equal, - (GDestroyNotify) g_free, (GDestroyNotify) g_hash_table_destroy); - priv->backends = g_hash_table_new_full (g_str_hash, g_str_equal, - (GDestroyNotify) g_free, (GDestroyNotify) g_object_unref); - priv->registered = FALSE; -} - -BONOBO_TYPE_FUNC_FULL (EDataCalFactory, - GNOME_Evolution_Calendar_CalFactory, - PARENT_TYPE, - e_data_cal_factory); - -/** - * e_data_cal_factory_register_storage: - * @factory: A calendar factory. - * @iid: OAFIID for the factory to be registered. - * - * Registers a calendar factory with the OAF object activation daemon. This - * function must be called before any clients can activate the factory. - * - * Return value: TRUE on success, FALSE otherwise. - **/ -gboolean -e_data_cal_factory_register_storage (EDataCalFactory *factory, const char *iid) -{ - EDataCalFactoryPrivate *priv; - Bonobo_RegistrationResult result; - char *tmp_iid; - - g_return_val_if_fail (factory != NULL, FALSE); - g_return_val_if_fail (E_IS_DATA_CAL_FACTORY (factory), FALSE); - - priv = factory->priv; - - g_return_val_if_fail (!priv->registered, FALSE); - - /* if iid is NULL, use the default factory OAFIID */ - if (iid) - tmp_iid = g_strdup (iid); - else - tmp_iid = g_strdup (DEFAULT_E_DATA_CAL_FACTORY_OAF_ID); - - result = bonobo_activation_active_server_register (tmp_iid, BONOBO_OBJREF (factory)); - - switch (result) { - case Bonobo_ACTIVATION_REG_SUCCESS: - priv->registered = TRUE; - priv->iid = tmp_iid; - return TRUE; - - case Bonobo_ACTIVATION_REG_NOT_LISTED: - g_warning (G_STRLOC ": cannot register the calendar factory %s (not listed)", tmp_iid); - break; - - case Bonobo_ACTIVATION_REG_ALREADY_ACTIVE: - g_warning (G_STRLOC ": cannot register the calendar factory (already active)"); - break; - - case Bonobo_ACTIVATION_REG_ERROR: - default: - g_warning (G_STRLOC ": cannot register the calendar factory (generic error)"); - break; - } - - g_free (tmp_iid); - - return FALSE; -} - -/** - * e_data_cal_factory_register_method: - * @factory: A calendar factory. - * @method: Method for the URI, i.e. "http", "file", etc. - * @backend_type: Class type of the backend to create for this @method. - * - * Registers the type of a #ECalBackend subclass that will be used to handle URIs - * with a particular method. When the factory is asked to open a particular - * URI, it will look in its list of registered methods and create a backend of - * the appropriate type. - **/ -void -e_data_cal_factory_register_method (EDataCalFactory *factory, const char *method, icalcomponent_kind kind, GType backend_type) -{ - EDataCalFactoryPrivate *priv; - char *method_str; - GHashTable *kinds; - GType type; - - g_return_if_fail (factory != NULL); - g_return_if_fail (E_IS_DATA_CAL_FACTORY (factory)); - g_return_if_fail (method != NULL); - g_return_if_fail (backend_type != 0); - g_return_if_fail (g_type_is_a (backend_type, E_TYPE_CAL_BACKEND)); - - priv = factory->priv; - - method_str = g_ascii_strdown (method, -1); - - kinds = g_hash_table_lookup (priv->methods, method_str); - if (kinds) { - type = GPOINTER_TO_INT (g_hash_table_lookup (kinds, GINT_TO_POINTER (kind))); - if (type) { - g_warning (G_STRLOC ": method `%s' already registered", method_str); - g_free (method_str); - - return; - } - - g_free (method_str); - } else { - kinds = g_hash_table_new_full (g_direct_hash, g_direct_equal, NULL, NULL); - g_hash_table_insert (priv->methods, method_str, kinds); - } - - g_hash_table_insert (kinds, GINT_TO_POINTER (kind), GINT_TO_POINTER (backend_type)); -} - -/** - * e_data_cal_factory_get_n_backends - * @factory: A calendar factory. - * - * Get the number of backends currently active in the given factory. - * - * Returns: the number of backends. - */ -int -e_data_cal_factory_get_n_backends (EDataCalFactory *factory) -{ - EDataCalFactoryPrivate *priv; - - g_return_val_if_fail (E_IS_DATA_CAL_FACTORY (factory), 0); - - priv = factory->priv; - return g_hash_table_size (priv->backends); -} - -/* Frees a uri/backend pair from the backends hash table */ -static void -dump_backend (gpointer key, gpointer value, gpointer data) -{ - char *uri; - ECalBackend *backend; - - uri = key; - backend = value; - - g_message (" %s: %p", uri, backend); -} - -void -e_data_cal_factory_dump_active_backends (EDataCalFactory *factory) -{ - EDataCalFactoryPrivate *priv; - - g_message ("Active PCS backends"); - - priv = factory->priv; - g_hash_table_foreach (priv->backends, dump_backend, NULL); -} diff --git a/calendar/libedata-cal/e-data-cal-factory.h b/calendar/libedata-cal/e-data-cal-factory.h deleted file mode 100644 index ca6fe61ea..000000000 --- a/calendar/libedata-cal/e-data-cal-factory.h +++ /dev/null @@ -1,73 +0,0 @@ -/* Evolution calendar factory - * - * Copyright (C) 2000 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_DATA_CAL_FACTORY_H -#define E_DATA_CAL_FACTORY_H - -#include <bonobo/bonobo-object.h> -#include <libical/ical.h> -#include <libedata-cal/Evolution-DataServer-Calendar.h> - -G_BEGIN_DECLS - - - -#define E_TYPE_DATA_CAL_FACTORY (e_data_cal_factory_get_type ()) -#define E_DATA_CAL_FACTORY(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_DATA_CAL_FACTORY, EDataCalFactory)) -#define E_DATA_CAL_FACTORY_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_DATA_CAL_FACTORY, \ - EDataCalFactoryClass)) -#define E_IS_DATA_CAL_FACTORY(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_DATA_CAL_FACTORY)) -#define E_IS_DATA_CAL_FACTORY_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_DATA_CAL_FACTORY)) - -typedef struct _EDataCalFactory EDataCalFactory; -typedef struct _EDataCalFactoryClass EDataCalFactoryClass; - -typedef struct _EDataCalFactoryPrivate EDataCalFactoryPrivate; - -struct _EDataCalFactory { - BonoboObject object; - - /* Private data */ - EDataCalFactoryPrivate *priv; -}; - -struct _EDataCalFactoryClass { - BonoboObjectClass parent_class; - - POA_GNOME_Evolution_Calendar_CalFactory__epv epv; - - /* Notification signals */ - void (* last_calendar_gone) (EDataCalFactory *factory); -}; - -GType e_data_cal_factory_get_type (void); -EDataCalFactory *e_data_cal_factory_new (void); - -gboolean e_data_cal_factory_register_storage (EDataCalFactory *factory, const char *iid); -void e_data_cal_factory_register_method (EDataCalFactory *factory, - const char *method, - icalcomponent_kind kind, - GType backend_type); -int e_data_cal_factory_get_n_backends (EDataCalFactory *factory); -void e_data_cal_factory_dump_active_backends (EDataCalFactory *factory); - -G_END_DECLS - -#endif diff --git a/calendar/libedata-cal/e-data-cal-view.c b/calendar/libedata-cal/e-data-cal-view.c deleted file mode 100644 index 6a14a035d..000000000 --- a/calendar/libedata-cal/e-data-cal-view.c +++ /dev/null @@ -1,492 +0,0 @@ -/* Evolution calendar - Live search query implementation - * - * Copyright (C) 2001 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <glib.h> -#include <bonobo/bonobo-exception.h> -#include <libedataserver/e-component-listener.h> -#include "e-cal-backend-sexp.h" -#include "e-data-cal-view.h" - - - -/* Private part of the Query structure */ -struct _EDataCalViewPrivate { - /* The backend we are monitoring */ - ECalBackend *backend; - - /* The listener we report to */ - GNOME_Evolution_Calendar_CalViewListener listener; - EComponentListener *component_listener; - - /* Sexp that defines the query */ - ECalBackendSExp *sexp; -}; - - - - -static void e_data_cal_view_class_init (EDataCalViewClass *class); -static void e_data_cal_view_init (EDataCalView *query, EDataCalViewClass *class); -static void e_data_cal_view_finalize (GObject *object); - -static BonoboObjectClass *parent_class; - - - -BONOBO_TYPE_FUNC_FULL (EDataCalView, - GNOME_Evolution_Calendar_CalView, - BONOBO_TYPE_OBJECT, - e_data_cal_view); - -/* Property IDs */ -enum props { - PROP_0, - PROP_BACKEND, - PROP_LISTENER, - PROP_SEXP -}; - - -static void -listener_died_cb (EComponentListener *cl, gpointer data) -{ - EDataCalView *query = QUERY (data); - EDataCalViewPrivate *priv; - - priv = query->priv; - - g_object_unref (priv->component_listener); - priv->component_listener = NULL; - - bonobo_object_release_unref (priv->listener, NULL); - priv->listener = NULL; -} - -static void -impl_EDataCalView_start (PortableServer_Servant servant, CORBA_Environment *ev) -{ - EDataCalView *query; - EDataCalViewPrivate *priv; - - query = QUERY (bonobo_object_from_servant (servant)); - priv = query->priv; - - e_cal_backend_start_query (priv->backend, query); -} - -static void -e_data_cal_view_set_property (GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) -{ - EDataCalView *query; - EDataCalViewPrivate *priv; - CORBA_Environment ev; - - query = QUERY (object); - priv = query->priv; - - switch (property_id) { - case PROP_BACKEND: - priv->backend = E_CAL_BACKEND (g_value_dup_object (value)); - break; - case PROP_LISTENER: - CORBA_exception_init (&ev); - priv->listener = CORBA_Object_duplicate (g_value_get_pointer (value), &ev); - CORBA_exception_free (&ev); - - priv->component_listener = e_component_listener_new (priv->listener); - g_signal_connect (G_OBJECT (priv->component_listener), "component_died", - G_CALLBACK (listener_died_cb), query); - break; - case PROP_SEXP: - priv->sexp = E_CAL_BACKEND_SEXP (g_value_dup_object (value)); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); - break; - } -} - -static void -e_data_cal_view_get_property (GObject *object, guint property_id, GValue *value, GParamSpec *pspec) -{ - EDataCalView *query; - EDataCalViewPrivate *priv; - - query = QUERY (object); - priv = query->priv; - - switch (property_id) { - case PROP_BACKEND: - g_value_set_object (value, priv->backend); - case PROP_LISTENER: - g_value_set_pointer (value, priv->listener); - break; - case PROP_SEXP: - g_value_set_object (value, priv->sexp); - break; - default: - G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); - break; - } -} - -/* Class initialization function for the live search query */ -static void -e_data_cal_view_class_init (EDataCalViewClass *klass) -{ - GObjectClass *object_class; - POA_GNOME_Evolution_Calendar_CalView__epv *epv = &klass->epv; - GParamSpec *param; - - object_class = (GObjectClass *) klass; - - parent_class = g_type_class_peek_parent (klass); - - object_class->set_property = e_data_cal_view_set_property; - object_class->get_property = e_data_cal_view_get_property; - object_class->finalize = e_data_cal_view_finalize; - - epv->start = impl_EDataCalView_start; - - param = g_param_spec_object ("backend", NULL, NULL, E_TYPE_CAL_BACKEND, - G_PARAM_READABLE | G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY); - g_object_class_install_property (object_class, PROP_BACKEND, param); - param = g_param_spec_pointer ("listener", NULL, NULL, - G_PARAM_READABLE | G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY); - g_object_class_install_property (object_class, PROP_LISTENER, param); - param = g_param_spec_object ("sexp", NULL, NULL, E_TYPE_CAL_BACKEND_SEXP, - G_PARAM_READABLE | G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY); - g_object_class_install_property (object_class, PROP_SEXP, param); -} - -/* Object initialization function for the live search query */ -static void -e_data_cal_view_init (EDataCalView *query, EDataCalViewClass *class) -{ - EDataCalViewPrivate *priv; - - priv = g_new0 (EDataCalViewPrivate, 1); - query->priv = priv; - - priv->backend = NULL; - priv->listener = NULL; - priv->component_listener = NULL; - priv->sexp = NULL; -} - -/* Finalize handler for the live search query */ -static void -e_data_cal_view_finalize (GObject *object) -{ - EDataCalView *query; - EDataCalViewPrivate *priv; - - g_return_if_fail (object != NULL); - g_return_if_fail (IS_QUERY (object)); - - query = QUERY (object); - priv = query->priv; - - if (priv->backend) - g_object_unref (priv->backend); - - if (priv->listener != NULL) - bonobo_object_release_unref (priv->listener, NULL); - - if (priv->component_listener != NULL) - g_object_unref (priv->component_listener); - - if (priv->sexp) - g_object_unref (priv->sexp); - - g_free (priv); - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - -/** - * e_data_cal_view_new: - * @backend: Calendar backend that the query object will monitor. - * @ql: Listener for query results. - * @sexp: Sexp that defines the query. - * - * Creates a new query engine object that monitors a calendar backend. - * - * Return value: A newly-created query object, or NULL on failure. - **/ -EDataCalView * -e_data_cal_view_new (ECalBackend *backend, - GNOME_Evolution_Calendar_CalViewListener ql, - ECalBackendSExp *sexp) -{ - EDataCalView *query; - - query = g_object_new (E_DATA_CAL_VIEW_TYPE, "backend", backend, "listener", ql, - "sexp", sexp, NULL); - - return query; -} - -/** - * e_data_cal_view_get_sexp - * @query: A #EDataCalView object. - * - * Get the expression used for the given query. - * - * Returns: the query expression used to search. - */ -const char * -e_data_cal_view_get_text (EDataCalView *query) -{ - g_return_val_if_fail (IS_QUERY (query), NULL); - - return e_cal_backend_sexp_text (query->priv->sexp); -} - -ECalBackendSExp * -e_data_cal_view_get_object_sexp (EDataCalView *query) -{ - g_return_val_if_fail (IS_QUERY (query), NULL); - - return query->priv->sexp; -} - -gboolean -e_data_cal_view_object_matches (EDataCalView *query, const char *object) -{ - EDataCalViewPrivate *priv; - - g_return_val_if_fail (query != NULL, FALSE); - g_return_val_if_fail (IS_QUERY (query), FALSE); - g_return_val_if_fail (object != NULL, FALSE); - - priv = query->priv; - - return e_cal_backend_sexp_match_object (priv->sexp, object, priv->backend); -} - -void -e_data_cal_view_notify_objects_added (EDataCalView *query, const GList *objects) -{ - EDataCalViewPrivate *priv; - GNOME_Evolution_Calendar_stringlist obj_list; - CORBA_Environment ev; - const GList *l; - int num_objs, i; - - g_return_if_fail (query != NULL); - g_return_if_fail (IS_QUERY (query)); - - priv = query->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - - num_objs = g_list_length ((GList*)objects); - obj_list._buffer = GNOME_Evolution_Calendar_stringlist_allocbuf (num_objs); - obj_list._maximum = num_objs; - obj_list._length = num_objs; - - for (l = objects, i = 0; l; l = l->next, i++) - obj_list._buffer[i] = CORBA_string_dup (l->data); - - GNOME_Evolution_Calendar_CalViewListener_notifyObjectsAdded (priv->listener, &obj_list, &ev); - - CORBA_free (obj_list._buffer); - - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": could not notify the listener of object addition"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_view_notify_objects_added_1 (EDataCalView *query, const char *object) -{ - EDataCalViewPrivate *priv; - GList objects; - - g_return_if_fail (query != NULL); - g_return_if_fail (IS_QUERY (query)); - - priv = query->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - objects.next = objects.prev = NULL; - objects.data = (gpointer)object; - - e_data_cal_view_notify_objects_added (query, &objects); -} - -void -e_data_cal_view_notify_objects_modified (EDataCalView *query, const GList *objects) -{ - EDataCalViewPrivate *priv; - GNOME_Evolution_Calendar_CalObjUIDSeq obj_list; - CORBA_Environment ev; - const GList *l; - int num_objs, i; - - g_return_if_fail (query != NULL); - g_return_if_fail (IS_QUERY (query)); - - priv = query->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - - num_objs = g_list_length ((GList*)objects); - obj_list._buffer = GNOME_Evolution_Calendar_stringlist_allocbuf (num_objs); - obj_list._maximum = num_objs; - obj_list._length = num_objs; - - for (l = objects, i = 0; l; l = l->next, i++) - obj_list._buffer[i] = CORBA_string_dup (l->data); - - GNOME_Evolution_Calendar_CalViewListener_notifyObjectsModified (priv->listener, &obj_list, &ev); - - CORBA_free (obj_list._buffer); - - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": could not notify the listener of object modification"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_view_notify_objects_modified_1 (EDataCalView *query, const char *object) -{ - EDataCalViewPrivate *priv; - GList objects; - - g_return_if_fail (query != NULL); - g_return_if_fail (IS_QUERY (query)); - - priv = query->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - objects.next = objects.prev = NULL; - objects.data = (gpointer)object; - - e_data_cal_view_notify_objects_modified (query, &objects); -} - -void -e_data_cal_view_notify_objects_removed (EDataCalView *query, const GList *uids) -{ - EDataCalViewPrivate *priv; - GNOME_Evolution_Calendar_CalObjUIDSeq uid_list; - CORBA_Environment ev; - const GList *l; - int num_uids, i; - - g_return_if_fail (query != NULL); - g_return_if_fail (IS_QUERY (query)); - - priv = query->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - - num_uids = g_list_length ((GList*)uids); - uid_list._buffer = GNOME_Evolution_Calendar_CalObjUIDSeq_allocbuf (num_uids); - uid_list._maximum = num_uids; - uid_list._length = num_uids; - - for (l = uids, i = 0; l; l = l->next, i ++) - uid_list._buffer[i] = CORBA_string_dup (l->data); - - GNOME_Evolution_Calendar_CalViewListener_notifyObjectsRemoved (priv->listener, &uid_list, &ev); - - CORBA_free (uid_list._buffer); - - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": could not notify the listener of object removal"); - - - CORBA_exception_free (&ev); -} - -void -e_data_cal_view_notify_objects_removed_1 (EDataCalView *query, const char *uid) -{ - EDataCalViewPrivate *priv; - GList uids; - - g_return_if_fail (query != NULL); - g_return_if_fail (IS_QUERY (query)); - - priv = query->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - uids.next = uids.prev = NULL; - uids.data = (gpointer)uid; - - e_data_cal_view_notify_objects_removed (query, &uids); -} - -void -e_data_cal_view_notify_progress (EDataCalView *query, const char *message, int percent) -{ - EDataCalViewPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (query != NULL); - g_return_if_fail (IS_QUERY (query)); - - priv = query->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_CalViewListener_notifyQueryProgress (priv->listener, message, percent, &ev); - - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": could not notify the listener of query progress"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_view_notify_done (EDataCalView *query, GNOME_Evolution_Calendar_CallStatus status) -{ - EDataCalViewPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (query != NULL); - g_return_if_fail (IS_QUERY (query)); - - priv = query->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_CalViewListener_notifyQueryDone (priv->listener, status, &ev); - - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": could not notify the listener of query completion"); - - CORBA_exception_free (&ev); -} diff --git a/calendar/libedata-cal/e-data-cal-view.h b/calendar/libedata-cal/e-data-cal-view.h deleted file mode 100644 index e25affa89..000000000 --- a/calendar/libedata-cal/e-data-cal-view.h +++ /dev/null @@ -1,81 +0,0 @@ -/* Evolution calendar - Live search query implementation - * - * Copyright (C) 2001 Ximian, Inc. - * - * Author: Federico Mena-Quintero <federico@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_DATA_CAL_VIEW_H -#define E_DATA_CAL_VIEW_H - -#include <bonobo/bonobo-object.h> -#include <libedata-cal/Evolution-DataServer-Calendar.h> -#include <libedata-cal/e-data-cal-common.h> -#include <libedata-cal/e-cal-backend-sexp.h> - -G_BEGIN_DECLS - - - -#define E_DATA_CAL_VIEW_TYPE (e_data_cal_view_get_type ()) -#define QUERY(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_DATA_CAL_VIEW_TYPE, EDataCalView)) -#define E_DATA_CAL_VIEW_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_DATA_CAL_VIEW_TYPE, EDataCalViewClass)) -#define IS_QUERY(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_DATA_CAL_VIEW_TYPE)) -#define IS_E_DATA_CAL_VIEW_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_DATA_CAL_VIEW_TYPE)) - -typedef struct _EDataCalViewPrivate EDataCalViewPrivate; - -struct _EDataCalView { - BonoboObject xobject; - - /* Private data */ - EDataCalViewPrivate *priv; -}; - -struct _EDataCalViewClass { - BonoboObjectClass parent_class; - - POA_GNOME_Evolution_Calendar_CalView__epv epv; -}; - -GType e_data_cal_view_get_type (void); -EDataCalView *e_data_cal_view_new (ECalBackend *backend, - GNOME_Evolution_Calendar_CalViewListener ql, - ECalBackendSExp *sexp); -const char *e_data_cal_view_get_text (EDataCalView *query); -ECalBackendSExp *e_data_cal_view_get_object_sexp (EDataCalView *query); -gboolean e_data_cal_view_object_matches (EDataCalView *query, const char *object); -void e_data_cal_view_notify_objects_added (EDataCalView *query, - const GList *objects); -void e_data_cal_view_notify_objects_added_1 (EDataCalView *query, - const char *object); -void e_data_cal_view_notify_objects_modified (EDataCalView *query, - const GList *objects); -void e_data_cal_view_notify_objects_modified_1 (EDataCalView *query, - const char *object); -void e_data_cal_view_notify_objects_removed (EDataCalView *query, - const GList *uids); -void e_data_cal_view_notify_objects_removed_1 (EDataCalView *query, - const char *uid); -void e_data_cal_view_notify_progress (EDataCalView *query, - const char *message, - int percent); -void e_data_cal_view_notify_done (EDataCalView *query, - GNOME_Evolution_Calendar_CallStatus status); - -G_END_DECLS - -#endif diff --git a/calendar/libedata-cal/e-data-cal.c b/calendar/libedata-cal/e-data-cal.c deleted file mode 100644 index fe5339c74..000000000 --- a/calendar/libedata-cal/e-data-cal.c +++ /dev/null @@ -1,1265 +0,0 @@ -/* Evolution calendar client interface object - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Authors: Federico Mena-Quintero <federico@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <libical/ical.h> -#include <bonobo/bonobo-main.h> -#include <bonobo/bonobo-exception.h> -#include <libedata-cal/e-cal-backend.h> -#include "e-data-cal.h" - -#define PARENT_TYPE BONOBO_TYPE_OBJECT - -static BonoboObjectClass *parent_class; - -/* Private part of the Cal structure */ -struct _EDataCalPrivate { - /* Our backend */ - ECalBackend *backend; - - /* Listener on the client we notify */ - GNOME_Evolution_Calendar_CalListener listener; -}; - -/* Cal::get_uri method */ -static CORBA_char * -impl_Cal_get_uri (PortableServer_Servant servant, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - const char *str_uri; - CORBA_char *str_uri_copy; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - str_uri = e_cal_backend_get_uri (priv->backend); - str_uri_copy = CORBA_string_dup (str_uri); - - return str_uri_copy; -} - -static void -impl_Cal_open (PortableServer_Servant servant, - CORBA_boolean only_if_exists, - const CORBA_char *username, - const CORBA_char *password, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_open (priv->backend, cal, only_if_exists, username, password); -} - -static void -impl_Cal_remove (PortableServer_Servant servant, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_remove (priv->backend, cal); -} - -/* Cal::isReadOnly method */ -static void -impl_Cal_isReadOnly (PortableServer_Servant servant, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_is_read_only (priv->backend, cal); -} - -/* Cal::getEmailAddress method */ -static void -impl_Cal_getCalAddress (PortableServer_Servant servant, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_get_cal_address (priv->backend, cal); -} - -/* Cal::get_alarm_email_address method */ -static void -impl_Cal_getAlarmEmailAddress (PortableServer_Servant servant, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_get_alarm_email_address (priv->backend, cal); -} - -/* Cal::get_ldap_attribute method */ -static void -impl_Cal_getLdapAttribute (PortableServer_Servant servant, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_get_ldap_attribute (priv->backend, cal); -} - -/* Cal::getSchedulingInformation method */ -static void -impl_Cal_getStaticCapabilities (PortableServer_Servant servant, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_get_static_capabilities (priv->backend, cal); -} - -/* Cal::setMode method */ -static void -impl_Cal_setMode (PortableServer_Servant servant, - GNOME_Evolution_Calendar_CalMode mode, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_set_mode (priv->backend, mode); -} - -static void -impl_Cal_getDefaultObject (PortableServer_Servant servant, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_get_default_object (priv->backend, cal); -} - -/* Cal::getObject method */ -static void -impl_Cal_getObject (PortableServer_Servant servant, - const CORBA_char *uid, - const CORBA_char *rid, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_get_object (priv->backend, cal, uid, rid); -} - -/* Cal::getObjectsInRange method */ -static void -impl_Cal_getObjectList (PortableServer_Servant servant, - const CORBA_char *query, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_get_object_list (priv->backend, cal, query); -} - -/* Cal::getChanges method */ -static void -impl_Cal_getChanges (PortableServer_Servant servant, - const CORBA_char *change_id, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_get_changes (priv->backend, cal, change_id); -} - -/* Cal::getFreeBusy method */ -static void -impl_Cal_getFreeBusy (PortableServer_Servant servant, - const GNOME_Evolution_Calendar_UserList *user_list, - const GNOME_Evolution_Calendar_Time_t start, - const GNOME_Evolution_Calendar_Time_t end, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - GList *users = NULL; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - /* convert the CORBA user list to a GList */ - if (user_list) { - int i; - - for (i = 0; i < user_list->_length; i++) - users = g_list_append (users, user_list->_buffer[i]); - } - - /* call the backend's get_free_busy method */ - e_cal_backend_get_free_busy (priv->backend, cal, users, start, end); -} - -/* Cal::discardAlarm method */ -static void -impl_Cal_discardAlarm (PortableServer_Servant servant, - const CORBA_char *uid, - const CORBA_char *auid, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_discard_alarm (priv->backend, cal, uid, auid); -} - -static void -impl_Cal_createObject (PortableServer_Servant servant, - const CORBA_char *calobj, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_create_object (priv->backend, cal, calobj); -} - -static void -impl_Cal_modifyObject (PortableServer_Servant servant, - const CORBA_char *calobj, - const GNOME_Evolution_Calendar_CalObjModType mod, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_modify_object (priv->backend, cal, calobj, mod); -} - -/* Cal::removeObject method */ -static void -impl_Cal_removeObject (PortableServer_Servant servant, - const CORBA_char *uid, - const CORBA_char *rid, - const GNOME_Evolution_Calendar_CalObjModType mod, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_remove_object (priv->backend, cal, uid, rid, mod); -} - -static void -impl_Cal_receiveObjects (PortableServer_Servant servant, - const CORBA_char *calobj, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_receive_objects (priv->backend, cal, calobj); -} - -static void -impl_Cal_sendObjects (PortableServer_Servant servant, - const CORBA_char *calobj, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_send_objects (priv->backend, cal, calobj); -} - -/* Cal::getQuery implementation */ -static void -impl_Cal_getQuery (PortableServer_Servant servant, - const CORBA_char *sexp, - GNOME_Evolution_Calendar_CalViewListener ql, - CORBA_Environment *ev) -{ - - EDataCal *cal; - EDataCalPrivate *priv; - EDataCalView *query; - ECalBackendSExp *obj_sexp; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - /* we handle this entirely here, since it doesn't require any - backend involvement now that we have pas_book_view_start to - actually kick off the search. */ - - obj_sexp = e_cal_backend_sexp_new (sexp); - if (!obj_sexp) { - e_data_cal_notify_query (cal, GNOME_Evolution_Calendar_InvalidQuery, NULL); - - return; - } - - query = e_data_cal_view_new (priv->backend, ql, obj_sexp); - if (!query) { - g_object_unref (obj_sexp); - e_data_cal_notify_query (cal, GNOME_Evolution_Calendar_OtherError, NULL); - - return; - } - - e_cal_backend_add_query (priv->backend, query); - - e_data_cal_notify_query (cal, GNOME_Evolution_Calendar_Success, query); - - g_object_unref (query); -} - - -/* Cal::getTimezone method */ -static void -impl_Cal_getTimezone (PortableServer_Servant servant, - const CORBA_char *tzid, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_get_timezone (priv->backend, cal, tzid); -} - -/* Cal::addTimezone method */ -static void -impl_Cal_addTimezone (PortableServer_Servant servant, - const CORBA_char *tz, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_add_timezone (priv->backend, cal, tz); -} - -/* Cal::setDefaultTimezone method */ -static void -impl_Cal_setDefaultTimezone (PortableServer_Servant servant, - const CORBA_char *tzid, - CORBA_Environment *ev) -{ - EDataCal *cal; - EDataCalPrivate *priv; - - cal = E_DATA_CAL (bonobo_object_from_servant (servant)); - priv = cal->priv; - - e_cal_backend_set_default_timezone (priv->backend, cal, tzid); -} - -/** - * cal_construct: - * @cal: A calendar client interface. - * @corba_cal: CORBA object for the calendar. - * @backend: Calendar backend that this @cal presents an interface to. - * @listener: Calendar listener for notification. - * - * Constructs a calendar client interface object by binding the corresponding - * CORBA object to it. The calendar interface is bound to the specified - * @backend, and will notify the @listener about changes to the calendar. - * - * Return value: The same object as the @cal argument. - **/ -EDataCal * -e_data_cal_construct (EDataCal *cal, - ECalBackend *backend, - GNOME_Evolution_Calendar_CalListener listener) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_val_if_fail (cal != NULL, NULL); - g_return_val_if_fail (E_IS_DATA_CAL (cal), NULL); - g_return_val_if_fail (backend != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_BACKEND (backend), NULL); - - priv = cal->priv; - - CORBA_exception_init (&ev); - priv->listener = CORBA_Object_duplicate (listener, &ev); - if (BONOBO_EX (&ev)) { - g_message ("cal_construct: could not duplicate the listener"); - priv->listener = CORBA_OBJECT_NIL; - CORBA_exception_free (&ev); - return NULL; - } - - CORBA_exception_free (&ev); - - priv->backend = backend; - - return cal; -} - -/** - * cal_new: - * @backend: A calendar backend. - * @listener: A calendar listener. - * - * Creates a new calendar client interface object and binds it to the - * specified @backend and @listener objects. - * - * Return value: A newly-created #EDataCal calendar client interface - * object, or %NULL if its corresponding CORBA object could not be - * created. - **/ -EDataCal * -e_data_cal_new (ECalBackend *backend, const char *uri, GNOME_Evolution_Calendar_CalListener listener) -{ - EDataCal *cal, *retval; - - g_return_val_if_fail (backend != NULL, NULL); - g_return_val_if_fail (E_IS_CAL_BACKEND (backend), NULL); - - cal = E_DATA_CAL (g_object_new (E_TYPE_DATA_CAL, - "poa", bonobo_poa_get_threaded (ORBIT_THREAD_HINT_PER_REQUEST, NULL), - NULL)); - - retval = e_data_cal_construct (cal, backend, listener); - if (!retval) { - g_message (G_STRLOC ": could not construct the calendar client interface"); - bonobo_object_unref (BONOBO_OBJECT (cal)); - return NULL; - } - - return retval; -} - -ECalBackend * -e_data_cal_get_backend (EDataCal *cal) -{ - g_return_val_if_fail (cal != NULL, NULL); - g_return_val_if_fail (E_IS_DATA_CAL (cal), NULL); - - return cal->priv->backend; -} - -GNOME_Evolution_Calendar_CalListener -e_data_cal_get_listener (EDataCal *cal) -{ - g_return_val_if_fail (cal != NULL, NULL); - g_return_val_if_fail (E_IS_DATA_CAL (cal), NULL); - - return cal->priv->listener; -} - -/* Destroy handler for the calendar */ -static void -cal_finalize (GObject *object) -{ - EDataCal *cal; - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (object != NULL); - g_return_if_fail (E_IS_DATA_CAL (object)); - - cal = E_DATA_CAL (object); - priv = cal->priv; - - priv->backend = NULL; - - CORBA_exception_init (&ev); - bonobo_object_release_unref (priv->listener, &ev); - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not release the listener"); - - priv->listener = NULL; - CORBA_exception_free (&ev); - - g_free (priv); - - if (G_OBJECT_CLASS (parent_class)->finalize) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - - - -/* Class initialization function for the calendar */ -static void -e_data_cal_class_init (EDataCalClass *klass) -{ - GObjectClass *object_class = (GObjectClass *) klass; - POA_GNOME_Evolution_Calendar_Cal__epv *epv = &klass->epv; - - parent_class = g_type_class_peek_parent (klass); - - /* Class method overrides */ - object_class->finalize = cal_finalize; - - /* Epv methods */ - epv->_get_uri = impl_Cal_get_uri; - epv->open = impl_Cal_open; - epv->remove = impl_Cal_remove; - epv->isReadOnly = impl_Cal_isReadOnly; - epv->getCalAddress = impl_Cal_getCalAddress; - epv->getAlarmEmailAddress = impl_Cal_getAlarmEmailAddress; - epv->getLdapAttribute = impl_Cal_getLdapAttribute; - epv->getStaticCapabilities = impl_Cal_getStaticCapabilities; - epv->setMode = impl_Cal_setMode; - epv->getDefaultObject = impl_Cal_getDefaultObject; - epv->getObject = impl_Cal_getObject; - epv->getTimezone = impl_Cal_getTimezone; - epv->addTimezone = impl_Cal_addTimezone; - epv->setDefaultTimezone = impl_Cal_setDefaultTimezone; - epv->getObjectList = impl_Cal_getObjectList; - epv->getChanges = impl_Cal_getChanges; - epv->getFreeBusy = impl_Cal_getFreeBusy; - epv->discardAlarm = impl_Cal_discardAlarm; - epv->createObject = impl_Cal_createObject; - epv->modifyObject = impl_Cal_modifyObject; - epv->removeObject = impl_Cal_removeObject; - epv->receiveObjects = impl_Cal_receiveObjects; - epv->sendObjects = impl_Cal_sendObjects; - epv->getQuery = impl_Cal_getQuery; -} - - -/* Object initialization function for the calendar */ -static void -e_data_cal_init (EDataCal *cal, EDataCalClass *klass) -{ - EDataCalPrivate *priv; - - priv = g_new0 (EDataCalPrivate, 1); - cal->priv = priv; - - priv->listener = CORBA_OBJECT_NIL; -} - -BONOBO_TYPE_FUNC_FULL (EDataCal, GNOME_Evolution_Calendar_Cal, PARENT_TYPE, e_data_cal); - -void -e_data_cal_notify_read_only (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, gboolean read_only) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyReadOnly (priv->listener, status, read_only, &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of read only"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_cal_address (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, const char *address) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyCalAddress (priv->listener, status, address ? address : "", &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of cal address"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_alarm_email_address (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, const char *address) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyAlarmEmailAddress (priv->listener, status, address ? address : "", &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of alarm address"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_ldap_attribute (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, const char *attribute) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyLDAPAttribute (priv->listener, status, attribute ? attribute : "", &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of ldap attribute"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_static_capabilities (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, const char *capabilities) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyStaticCapabilities (priv->listener, status, - capabilities ? capabilities : "", &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of static capabilities"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_open (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyCalOpened (priv->listener, status, &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of open"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_remove (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyCalRemoved (priv->listener, status, &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of remove"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_object_created (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *uid, const char *object) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - if (status == GNOME_Evolution_Calendar_Success) - e_cal_backend_notify_object_created (priv->backend, object); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyObjectCreated (priv->listener, status, uid ? uid : "", &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of object creation"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_object_modified (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *old_object, const char *object) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - if (status == GNOME_Evolution_Calendar_Success) - e_cal_backend_notify_object_modified (priv->backend, old_object, object); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyObjectModified (priv->listener, status, &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of object creation"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_object_removed (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *uid, const char *object) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - if (status == GNOME_Evolution_Calendar_Success) - e_cal_backend_notify_object_removed (priv->backend, uid, object); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyObjectRemoved (priv->listener, status, &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of object removal"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_objects_received (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyObjectsReceived (priv->listener, status, &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of objects received"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_alarm_discarded (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyAlarmDiscarded (priv->listener, status, &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of alarm discarded"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_objects_sent (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, GList *users, const char *calobj) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - GNOME_Evolution_Calendar_UserList *corba_users; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - corba_users = GNOME_Evolution_Calendar_UserList__alloc (); - corba_users->_length = g_list_length (users); - if (users) { - GList *l; - int n; - - corba_users->_buffer = CORBA_sequence_GNOME_Evolution_Calendar_User_allocbuf (corba_users->_length); - for (l = users, n = 0; l != NULL; l = l->next, n++) - corba_users->_buffer[n] = CORBA_string_dup (l->data); - } - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyObjectsSent (priv->listener, status, corba_users, - calobj ? calobj : "", &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of objects sent"); - - CORBA_exception_free (&ev); - CORBA_free (corba_users); -} - -void -e_data_cal_notify_default_object (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, const char *object) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_CalListener_notifyDefaultObjectRequested (priv->listener, status, - object ? object : "", &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of default object"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_object (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, const char *object) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - - GNOME_Evolution_Calendar_CalListener_notifyObjectRequested (priv->listener, status, - object ? object : "", &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of object"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_object_list (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, GList *objects) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - GNOME_Evolution_Calendar_stringlist seq; - GList *l; - int i; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - - seq._maximum = g_list_length (objects); - seq._length = 0; - seq._buffer = GNOME_Evolution_Calendar_stringlist_allocbuf (seq._maximum); - - for (l = objects, i = 0; l; l = l->next, i++) { - seq._buffer[i] = CORBA_string_dup (l->data); - seq._length++; - } - - GNOME_Evolution_Calendar_CalListener_notifyObjectListRequested (priv->listener, status, &seq, &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of object list"); - - CORBA_exception_free (&ev); - - CORBA_free(seq._buffer); -} - -void -e_data_cal_notify_query (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, EDataCalView *query) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyQuery (priv->listener, status, BONOBO_OBJREF (query), &ev); - - if (BONOBO_EX (&ev)) - g_message (G_STRLOC ": could not notify the listener of query"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_timezone_requested (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, const char *object) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyTimezoneRequested (priv->listener, status, object ? object : "", &ev); - - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": could not notify the listener of timezone requested"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_timezone_added (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, const char *tzid) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyTimezoneAdded (priv->listener, status, tzid ? tzid : "", &ev); - - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": could not notify the listener of timezone added"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_default_timezone_set (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyDefaultTimezoneSet (priv->listener, status, &ev); - - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": could not notify the listener of default timezone set"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_changes (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - GList *adds, GList *modifies, GList *deletes) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - GNOME_Evolution_Calendar_CalObjChangeSeq seq; - GList *l; - int n, i; - - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - n = g_list_length (adds) + g_list_length (modifies) + g_list_length (deletes); - seq._maximum = n; - seq._length = n; - seq._buffer = CORBA_sequence_GNOME_Evolution_Calendar_CalObjChange_allocbuf (n); - - i = 0; - for (l = adds; l; i++, l = l->next) { - GNOME_Evolution_Calendar_CalObjChange *change = &seq._buffer[i]; - - change->calobj = CORBA_string_dup (l->data); - change->type = GNOME_Evolution_Calendar_ADDED; - } - - for (l = modifies; l; i++, l = l->next) { - GNOME_Evolution_Calendar_CalObjChange *change = &seq._buffer[i]; - - change->calobj = CORBA_string_dup (l->data); - change->type = GNOME_Evolution_Calendar_MODIFIED; - } - - for (l = deletes; l; i++, l = l->next) { - GNOME_Evolution_Calendar_CalObjChange *change = &seq._buffer[i]; - - change->calobj = CORBA_string_dup (l->data); - change->type = GNOME_Evolution_Calendar_DELETED; - } - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyChanges (priv->listener, status, &seq, &ev); - - CORBA_free (seq._buffer); - - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": could not notify the listener of default timezone set"); - - CORBA_exception_free (&ev); -} - -void -e_data_cal_notify_free_busy (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, GList *freebusy) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - GNOME_Evolution_Calendar_CalObjSeq seq; - GList *l; - int n, i; - - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - n = g_list_length (freebusy); - seq._maximum = n; - seq._length = n; - seq._buffer = CORBA_sequence_GNOME_Evolution_Calendar_CalObj_allocbuf (n); - - for (i = 0, l = freebusy; l; i++, l = l->next) - seq._buffer[i] = CORBA_string_dup (l->data); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyFreeBusy (priv->listener, status, &seq, &ev); - - CORBA_free (seq._buffer); - - if (BONOBO_EX (&ev)) - g_warning (G_STRLOC ": could not notify the listener of freebusy"); - - CORBA_exception_free (&ev); -} - -/** - * e_data_cal_notify_mode: - * @cal: A calendar client interface. - * @status: Status of the mode set. - * @mode: The current mode. - * - * Notifys the listener of the results of a setMode call. - **/ -void -e_data_cal_notify_mode (EDataCal *cal, - GNOME_Evolution_Calendar_CalListener_SetModeStatus status, - GNOME_Evolution_Calendar_CalMode mode) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyCalSetMode (priv->listener, status, mode, &ev); - - if (BONOBO_EX (&ev)) - g_message ("e_data_cal_notify_mode(): could not notify the listener " - "about a mode change"); - - CORBA_exception_free (&ev); -} - -/** - * e_data_cal_notify_error - * @cal: A calendar client interface. - * @message: Error message. - * - * Notify a calendar client of an error occurred in the backend. - */ -void -e_data_cal_notify_error (EDataCal *cal, const char *message) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - g_return_if_fail (message != NULL); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyErrorOccurred (priv->listener, (char *) message, &ev); - - if (BONOBO_EX (&ev)) - g_message ("e_data_cal_notify_remove(): could not notify the listener " - "about a removed object"); - - CORBA_exception_free (&ev); -} - -/** - * e_data_cal_notify_categories_changed: - * @cal: A calendar client interface. - * @categories: List of categories. - * - * Notifies a listener attached to a calendar client interface object about the - * current set of categories in a calendar backend. - **/ -void -e_data_cal_notify_categories_changed (EDataCal *cal, GNOME_Evolution_Calendar_StringSeq *categories) -{ - EDataCalPrivate *priv; - CORBA_Environment ev; - - g_return_if_fail (cal != NULL); - g_return_if_fail (E_IS_DATA_CAL (cal)); - g_return_if_fail (categories != NULL); - - priv = cal->priv; - g_return_if_fail (priv->listener != CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - GNOME_Evolution_Calendar_CalListener_notifyCategoriesChanged (priv->listener, categories, &ev); - - if (BONOBO_EX (&ev)) - g_message ("e_data_cal_notify_categories_changed(): Could not notify the listener " - "about the current set of categories"); - - CORBA_exception_free (&ev); -} diff --git a/calendar/libedata-cal/e-data-cal.h b/calendar/libedata-cal/e-data-cal.h deleted file mode 100644 index e0a55191d..000000000 --- a/calendar/libedata-cal/e-data-cal.h +++ /dev/null @@ -1,125 +0,0 @@ -/* Evolution calendar client interface object - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * Authors: Federico Mena-Quintero <federico@ximian.com> - * Rodrigo Moya <rodrigo@ximian.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifndef E_DATA_CAL_H -#define E_DATA_CAL_H - -#include <bonobo/bonobo-object.h> -#include <libedata-cal/Evolution-DataServer-Calendar.h> -#include <libedata-cal/e-data-cal-common.h> -#include <libedata-cal/e-data-cal-view.h> - -G_BEGIN_DECLS - - - -#define E_TYPE_DATA_CAL (e_data_cal_get_type ()) -#define E_DATA_CAL(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_DATA_CAL, EDataCal)) -#define E_DATA_CAL_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_DATA_CAL, EDataCalClass)) -#define E_IS_DATA_CAL(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_DATA_CAL)) -#define E_IS_DATA_CAL_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), E_TYPE_DATA_CAL)) - -typedef struct _EDataCalPrivate EDataCalPrivate; - -struct _EDataCal { - BonoboObject object; - - /* Private data */ - EDataCalPrivate *priv; -}; - -struct _EDataCalClass { - BonoboObjectClass parent_class; - - POA_GNOME_Evolution_Calendar_Cal__epv epv; -}; - -GType e_data_cal_get_type (void); - -EDataCal *e_data_cal_construct (EDataCal *cal, - ECalBackend *backend, - GNOME_Evolution_Calendar_CalListener listener); - -EDataCal *e_data_cal_new (ECalBackend *backend, const char *uri, GNOME_Evolution_Calendar_CalListener listener); - -ECalBackend *e_data_cal_get_backend (EDataCal *cal); -GNOME_Evolution_Calendar_CalListener e_data_cal_get_listener (EDataCal *cal); - -void e_data_cal_notify_read_only (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - gboolean read_only); -void e_data_cal_notify_cal_address (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *address); -void e_data_cal_notify_alarm_email_address (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *address); -void e_data_cal_notify_ldap_attribute (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *attribute); -void e_data_cal_notify_static_capabilities (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *capabilities); - -void e_data_cal_notify_open (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status); -void e_data_cal_notify_remove (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status); - -void e_data_cal_notify_object_created (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *uid, const char *object); -void e_data_cal_notify_object_modified (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *old_object, const char *object); -void e_data_cal_notify_object_removed (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *uid, const char *object); -void e_data_cal_notify_alarm_discarded (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status); - -void e_data_cal_notify_objects_received (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status); -void e_data_cal_notify_objects_sent (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, GList *users, - const char *calobj); - -void e_data_cal_notify_default_object (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *object); -void e_data_cal_notify_object (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *object); -void e_data_cal_notify_object_list (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - GList *objects); - -void e_data_cal_notify_query (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - EDataCalView *query); - -void e_data_cal_notify_timezone_requested (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *object); -void e_data_cal_notify_timezone_added (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - const char *tzid); -void e_data_cal_notify_default_timezone_set (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status); - -void e_data_cal_notify_changes (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - GList *adds, GList *modifies, GList *deletes); -void e_data_cal_notify_free_busy (EDataCal *cal, GNOME_Evolution_Calendar_CallStatus status, - GList *freebusy); - -void e_data_cal_notify_mode (EDataCal *cal, - GNOME_Evolution_Calendar_CalListener_SetModeStatus status, - GNOME_Evolution_Calendar_CalMode mode); -void e_data_cal_notify_error (EDataCal *cal, const char *message); - -void e_data_cal_notify_categories_changed (EDataCal *cal, GNOME_Evolution_Calendar_StringSeq *categories); - - - -G_END_DECLS - -#endif diff --git a/calendar/libedata-cal/libedata-cal-1.0.pc.in b/calendar/libedata-cal/libedata-cal-1.0.pc.in deleted file mode 100644 index 722b2da8e..000000000 --- a/calendar/libedata-cal/libedata-cal-1.0.pc.in +++ /dev/null @@ -1,16 +0,0 @@ -prefix=@prefix@ -exec_prefix=@exec_prefix@ -libdir=@libdir@ -includedir=@includedir@ - -idldir=@idldir@ -IDL_INCLUDES=-I ${idldir} @IDL_INCLUDES@ - -privincludedir=@privincludedir@ - -Name: libecal -Description: Client library for evolution calendars -Version: @VERSION@ -Requires: libgnome-2.0 libbonobo-2.0 >= @LIBBONOBO_REQUIRED@ gnome-vfs-2.0 libedataserver-1.0 libecal-1.0 -Libs: -L${libdir} -ledata-cal -lecal -Cflags: -I${privincludedir} diff --git a/calendar/tests/.cvsignore b/calendar/tests/.cvsignore deleted file mode 100644 index c038ed786..000000000 --- a/calendar/tests/.cvsignore +++ /dev/null @@ -1,2 +0,0 @@ -Makefile -Makefile.in
\ No newline at end of file diff --git a/calendar/tests/Makefile.am b/calendar/tests/Makefile.am deleted file mode 100644 index 83d04c0b3..000000000 --- a/calendar/tests/Makefile.am +++ /dev/null @@ -1 +0,0 @@ -SUBDIRS = ecal
\ No newline at end of file diff --git a/calendar/tests/ecal/.cvsignore b/calendar/tests/ecal/.cvsignore deleted file mode 100644 index ba0d2e98d..000000000 --- a/calendar/tests/ecal/.cvsignore +++ /dev/null @@ -1,4 +0,0 @@ -Makefile -Makefile.in -test-ecal -test-search
\ No newline at end of file diff --git a/calendar/tests/ecal/Makefile.am b/calendar/tests/ecal/Makefile.am deleted file mode 100644 index 463a0af27..000000000 --- a/calendar/tests/ecal/Makefile.am +++ /dev/null @@ -1,47 +0,0 @@ -INCLUDES = \ - -DEVOLUTION_LOCALEDIR=\""$(localedir)"\" \ - -I$(top_srcdir) \ - -I$(top_builddir) \ - -I$(top_srcdir)/calendar \ - -I$(top_builddir)/calendar \ - -I$(top_srcdir)/calendar/libical/src \ - -I$(top_builddir)/calendar/libical/src \ - -I$(top_srcdir)/calendar/libical/src/libical \ - -I$(top_builddir)/calendar/libical/src/libical \ - $(EVOLUTION_CALENDAR_CFLAGS) - -EXTRA_DIST = \ - $(test_scripts) \ - testdata.ics - -test_scripts = \ - test-runner.sh \ - cleanup.sh - -# The test program -noinst_PROGRAMS = test-ecal test-search - -test_ecal_SOURCES = \ - test-ecal.c - -test_ecal_INCLUDES = \ - $(INCLUDES) \ - -DG_LOG_DOMAIN=\"test-ecal\" - -test_ecal_LDADD = \ - $(top_builddir)/calendar/libecal/libecal.la \ - $(top_builddir)/calendar/libical/src/libical/libical-evolution.la \ - $(EVOLUTION_CALENDAR_LIBS) - - -test_search_SOURCES = \ - test-search.c - -test_search_INCLUDES = \ - $(INCLUDES) \ - -DG_LOG_DOMAIN=\"test-ecal\" - -test_search_LDADD = \ - $(top_builddir)/calendar/libecal/libecal.la \ - $(top_builddir)/calendar/libical/src/libical/libical-evolution.la \ - $(EVOLUTION_CALENDAR_LIBS) diff --git a/calendar/tests/ecal/cleanup.sh b/calendar/tests/ecal/cleanup.sh deleted file mode 100755 index 5d2cd0244..000000000 --- a/calendar/tests/ecal/cleanup.sh +++ /dev/null @@ -1,4 +0,0 @@ -#! /bin/sh -rm -rf $HOME/.evolution/calendar/local/OnThisComputer/Test* -rm -f tmp/*.out - diff --git a/calendar/tests/ecal/test-ecal.c b/calendar/tests/ecal/test-ecal.c deleted file mode 100644 index ae37689e3..000000000 --- a/calendar/tests/ecal/test-ecal.c +++ /dev/null @@ -1,717 +0,0 @@ -/* Evolution calendar client - test program - * - * Copyright (C) 2000 Ximian, Inc. - * Copyright (C) 2000 Ximian, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <stdlib.h> -#include <string.h> -#include <glib.h> -#include <bonobo-activation/bonobo-activation.h> -#include <bonobo/bonobo-i18n.h> -#include <bonobo/bonobo-main.h> -#include <libecal/e-cal.h> -#include <libecal/e-cal-component.h> -#include <libecal/e-cal-time-util.h> -#include <libical/ical.h> - -// start_testing_scaffold -#define mu_assert(message, test) do { if (!(test)) return message; else { tests_passed++; return NULL;}} while (0) -#define mu_run_test(test) do { char *message = test; tests_run++; \ - if (message) { cl_printf (client, "***Error***\n%s\n", message); break;} } while (0) - -int tests_run = 0; -int tests_passed = 0; -// end_testing_scaffold - -static ECal *client1; -static ECal *client2; - -/* Prints a message with a client identifier */ -static void -cl_printf (ECal *client, const char *format, ...) -{ - va_list args; - - va_start (args, format); - if ( client != client1) - return; - printf ("Client %s: ", "Test"); - vprintf (format, args); - va_end (args); -} - -static void -objects_added_cb (GObject *object, GList *objects, gpointer data) -{ - GList *l; - - for (l = objects; l; l = l->next) - cl_printf (data, "Object added %s\n", icalcomponent_get_uid (l->data)); -} - -static void -objects_modified_cb (GObject *object, GList *objects, gpointer data) -{ - GList *l; - - for (l = objects; l; l = l->next) - cl_printf (data, "Object modified %s\n", icalcomponent_get_uid (l->data)); -} - -static void -objects_removed_cb (GObject *object, GList *objects, gpointer data) -{ - GList *l; - - for (l = objects; l; l = l->next) - cl_printf (data, "Object removed %s\n", icalcomponent_get_uid (l->data)); -} - -static void -view_done_cb (GObject *object, ECalendarStatus status, gpointer data) -{ - cl_printf (data, "View done\n"); -} - -static gboolean -list_uids (ECal *client) -{ - GList *objects = NULL; - GList *l; - - if (!e_cal_get_object_list (client, "(contains? \"any\" \"test\")", &objects, NULL)) - return FALSE; - - cl_printf (client, "UIDS: "); - - cl_printf (client, "\nGot %d objects\n", g_list_length (objects)); - if (!objects) - printf ("none\n"); - else { - for (l = objects; l; l = l->next) { - const char *uid; - - uid = icalcomponent_get_uid (l->data); - printf ("`%s' ", uid); - } - - printf ("\n"); - - for (l = objects; l; l = l->next) { - printf ("------------------------------\n"); - printf ("%s", icalcomponent_as_ical_string (l->data)); - printf ("------------------------------\n"); - } - } - - e_cal_free_object_list (objects); - - return FALSE; -} - -/* Callback used when a client is destroyed */ -static void -client_destroy_cb (gpointer data, GObject *object) -{ - if (E_CAL (object) == client1) - client1 = NULL; - else if (E_CAL (object) == client2) - client2 = NULL; - else - g_assert_not_reached (); - - if (!client1 && !client2) - bonobo_main_quit (); -} - -static char * -test_object_creation (ECal *client, char **uid) -{ - ECalComponent *comp, *comp_retrieved; - icalcomponent *icalcomp, *icalcomp_retrieved; - struct icaltimetype tt; - ECalComponentText text; - ECalComponentDateTime dt; - ECalComponentTransparency transp; - gboolean compare; - GError *error = NULL; - - comp = e_cal_component_new (); - /* set fields */ - e_cal_component_set_new_vtype (comp, E_CAL_COMPONENT_EVENT); - text.value = "Creation of new test event"; - text.altrep = NULL; - e_cal_component_set_summary (comp, &text); - tt = icaltime_from_string ("20040109T090000Z"); - dt.value = &tt; - dt.tzid ="UTC"; - e_cal_component_set_dtstart (comp, &dt); - tt = icaltime_from_string ("20040109T103000"); - dt.value = &tt; - dt.tzid ="UTC"; - e_cal_component_set_dtend (comp, &dt); - e_cal_component_set_transparency (comp, E_CAL_COMPONENT_TRANSP_OPAQUE); - - - e_cal_component_commit_sequence (comp); - icalcomp = e_cal_component_get_icalcomponent (comp); - if (!e_cal_create_object (client, icalcomp, uid, &error)) { - cl_printf (client, "Object creation: %s\n", error->message); - g_free (comp); - g_free (icalcomp); - return "Test Object Creation failed"; - } - e_cal_component_commit_sequence (comp); - if (!e_cal_get_object (client, *uid, NULL, &icalcomp_retrieved, &error)) { - cl_printf (client, "Object retrieval: %s\n", error->message); - g_free (uid); - g_free (comp); - g_free (icalcomp); - return "Test Object Creation failed"; - - } - - comp_retrieved = e_cal_component_new (); - if (!e_cal_component_set_icalcomponent (comp_retrieved, icalcomp_retrieved)) { - cl_printf (client, "Could not set icalcomponent\n"); - g_free (uid); - g_free (comp); - g_free (icalcomp); - g_free (icalcomp_retrieved); - return "Test Object Creation failed"; - - } - /* Dumping icalcomp into a string is not useful as the retrieved object - * has some generated information like timestamps. We compare - * member values we set during creation*/ - compare = e_cal_component_event_dates_match (comp, comp_retrieved); - - if (compare) { - e_cal_component_get_transparency (comp_retrieved, &transp); - compare = (transp == E_CAL_COMPONENT_TRANSP_OPAQUE); - } - - g_free (comp_retrieved); - g_free (comp); - g_free (icalcomp); - g_free (icalcomp_retrieved); - - mu_assert ("Test Object creation : Created object does not match retrieved data\n", compare); - return NULL; -} - -static char * -test_object_modification (ECal *client, char *uid) -{ - const char *summary = "This summary was modified"; - icalcomponent *icalcomp, *icalcomp_modified; - gboolean compare; - GError *error = NULL; - - if (!e_cal_get_object (client, uid, NULL, &icalcomp, &error)) { - cl_printf (client, "Test Modify object : Could not get the object: %s\n", error->message); - g_free (uid); - return error->message; - } - - // modify one property of the icalcomp and save it. Now retrieve it and - // check the field. - icalcomponent_set_summary (icalcomp, summary); - if (!e_cal_modify_object (client, icalcomp, CALOBJ_MOD_THIS, &error)) { - cl_printf (client, "Test Modify object : Could not modify the object: %s\n", error->message); - g_free (uid); - g_free (icalcomp); - return error->message; - } - - if (!e_cal_get_object (client, uid, NULL, &icalcomp_modified, &error)) { - cl_printf (client, "Test Modify object : Could not get the modified object: %s\n", error->message); - g_free (uid); - g_free (icalcomp); - return "Test Object Creation failed"; - } - - compare = !strcmp ( icalcomponent_get_summary (icalcomp_modified), summary); - - g_free (uid); - g_free (icalcomp); - g_free (icalcomp_modified); - - mu_assert ("Test Modify object : Modification failed\n", compare); - return NULL; -} - -static char * -test_object_removal (ECal *client) -{ - - char *uid; - ECalComponent *comp; - icalcomponent *icalcomp; - gboolean compare = 1; - GError *error = NULL; - - comp = e_cal_component_new (); - e_cal_component_commit_sequence (comp); - icalcomp = e_cal_component_get_icalcomponent (comp); - if (!e_cal_create_object (client, icalcomp, &uid, &error)) { - cl_printf (client, "Test object removal - Object creation: %s\n", error->message); - g_object_unref (comp); - g_object_unref(icalcomp); - return "Test Object Removal failed\n"; - } - - if (!e_cal_remove_object (client, uid, &error)) { - cl_printf (client, "Test object removal - Could not remove the object\n"); - g_free (uid); - g_object_unref (comp); - g_object_unref (icalcomp); - return "Test Object Removal failed\n"; - - } - - compare = e_cal_get_object (client, uid, NULL, &icalcomp, &error); - - g_free (uid); - g_object_unref (comp); - g_object_unref (icalcomp); - - mu_assert ("Test object removal - Failed\n", compare); - return NULL; -} - -static char * -test_get_alarms_in_range (ECal *client) -{ - GSList *alarms; - icaltimezone *utc; - time_t start = time (NULL), end; - gboolean compare; - - utc = icaltimezone_get_utc_timezone (); - start = time_from_isodate ("20040212T000000Z"); - end = time_add_day_with_zone (start, 2, utc); - - alarms = e_cal_get_alarms_in_range (client, start, end); - compare = (g_slist_length (alarms) == 3); - - e_cal_free_alarms (alarms); - mu_assert ("Test getting alarms in range\n", compare); - - return NULL; -} - -static char * -test_set_uri (ECal *client, const gchar *uri) -{ - /* The uri is set as part of create_client call. This method merely - * verifies it was done correctly. - */ - char *cal_uri; - gboolean compare = 0; - cal_uri = g_strconcat ("file://", uri, NULL); - compare = !strcmp (e_cal_get_uri (client), cal_uri); - - g_free (cal_uri); - mu_assert ("Test set_uri : uri was not set correctly\n", compare); - - return NULL; -} - -static char * -test_cal_loaded (ECal *client) -{ - /* Test one loaded calendar and another that is not loaded. */ - mu_assert ("Test get_cal_load_state : Failed \n", - (E_CAL_LOAD_LOADED == e_cal_get_load_state (client)) && - (E_CAL_LOAD_NOT_LOADED == e_cal_get_load_state (NULL))); - - return NULL; -} - -static char * -test_get_source (ECal *client, const gchar *expected) -{ - ESource *source; - char *uri; - char *cal_uri; - gboolean compare = 0; - - source = e_cal_get_source (client); - uri = e_source_get_uri (source); - cal_uri = g_strconcat ("file://", expected, NULL); - compare = !strcmp (expected, uri); - - g_free (cal_uri); - mu_assert ("Test get_source : Failed\n", compare); - - return NULL; -} - -static char * -test_query (ECal *client, const char *query, int expected) -{ - /* This uses pre-loaded data. Hence its results are valid only - * when called before any write operation is performed. - */ - int i = 0; - GList *objects = NULL; - - if (!e_cal_get_object_list (client, query, &objects, NULL)) - return "Could not get the list of objects"; - i = g_list_length (objects); - e_cal_free_object_list (objects); - - mu_assert ("Test get_object_list : Expected number of objects not found", i == expected); - - return NULL; -} - -static char * -test_e_cal_new (ECal **cal, const char *uri) -{ - GError *error = NULL; - char *cal_uri, *cal_file; - gboolean created = 0; - - cal_uri = g_strconcat ("file://", uri, NULL); - *cal = e_cal_new_from_uri (cal_uri, E_CAL_SOURCE_TYPE_EVENT); - if (!*cal) { - g_message (G_STRLOC ": could not create the client"); - g_free (cal_uri); - return "Test Creation of new calendar : Failed"; - } - g_object_weak_ref (G_OBJECT (*cal), client_destroy_cb, NULL); - - cl_printf (*cal, "Calendar loading `%s'...\n", uri); - - if (!e_cal_open (*cal, FALSE, &error)) { - cl_printf (*cal, "Load/create %s\n", error->message); - g_free (cal_uri); - return "Test creation of new calendar : Failed"; - } - - cal_file = g_strconcat (uri, "/calendar.ics", NULL); - - created = g_file_test (cal_file, G_FILE_TEST_EXISTS); - g_free (cal_uri); - g_free (cal_file); - - mu_assert ("Test creation of new calendar : Failed", created); - - return NULL; -} - -static char * -test_e_cal_remove (ECal *ecal, const char *uri) -{ - char *cal_uri; - GError *error = NULL; - gboolean removed = 0; - - cal_uri = g_strconcat (uri, "/calendar.ics", NULL); - if (!e_cal_remove (ecal, &error)) { - cl_printf (ecal, "Test Calendar removal : Could not remove the Calendar : %s\n", error->message); - } - - removed = !g_file_test (uri, G_FILE_TEST_EXISTS); - g_free (cal_uri); - - mu_assert ("Test Remove calendar : Failed ", removed); - - return NULL; -} - -static char * -test_new_system_calendar() -{ - ECal *cal; - char *uri; - gboolean created; - - cal = e_cal_new_system_calendar (); - uri = g_build_filename (g_get_home_dir (), ".evolution", "calendar", "local", "system", "calendar.ics", NULL); - created = g_file_test (uri, G_FILE_TEST_EXISTS); - g_free (uri); - - mu_assert ("Test creation of default system calendar : Failed", created); - - return NULL; -} - -static char * -test_new_system_tasks() -{ - ECal *cal; - char *uri; - gboolean created; - - cal = e_cal_new_system_tasks (); - uri = g_build_filename (g_get_home_dir (), ".evolution", "tasks", "local", "system", "tasks.ics", NULL); - created = g_file_test (uri, G_FILE_TEST_EXISTS); - g_free (uri); - - mu_assert ("Test creation of default system tasks : Failed", created); - - return NULL; -} - -static char * -test_get_free_busy (ECal *client) -{ - // TODO uses NULL for users and currently specific to file backend. - GList *l, *freebusy = NULL; - GError *error = NULL; - icaltimezone *utc; - time_t start = time (NULL), end; - - utc = icaltimezone_get_utc_timezone (); - start = time_from_isodate ("20040212T000000Z"); - end = time_add_day_with_zone (start, 2, utc); - - if (!e_cal_get_free_busy (client, NULL, start, end, &freebusy, &error)) { - cl_printf (client, "Test free/busy : Could not retrieve free busy information : %s\n", error->message); - return error->message; - } - if (freebusy) { - cl_printf (client, "Printing free busy information\n"); - for (l = freebusy; l; l = l->next) { - char *comp_string; - ECalComponent *comp = E_CAL_COMPONENT (l->data); - - comp_string = e_cal_component_get_as_string (comp); - cl_printf (client, "%s\n\n", comp_string); - g_object_unref (comp); - g_free (comp_string); - } - } - else { - cl_printf (client, "free_busy was returned but NULL"); - } - return NULL; -} - - -static char * -test_get_default_object (ECal *client) -{ - icalcomponent *icalcomp; - GError *error = NULL; - char *ical_string; - if (e_cal_get_default_object (client, &icalcomp, &error)) { - ical_string = icalcomponent_as_ical_string (icalcomp); - cl_printf (client, "Obtained default object: %s\n", ical_string); - g_free (ical_string); - tests_passed++; - return NULL; - - } else - cl_printf (client, "Test Get default object : Could not get the default object: %s\n", error->message); - return error->message; -} - - -/* XXX The string pasted below is *really* ugly. Alternatively, it could be - * read from a file at run-time. Not sure if it is an elegant solution when - * multiple clients try to load the same file during stress testing. - * how can this be done better ? - */ -#define EXPECTED \ -"BEGIN:VEVENT\ -UID:20040213T055519Z-15802-500-1-3@testcal\ -DTSTAMP:20040213T055519Z\ -DTSTART;TZID=/softwarestudio.org/Olson_20011030_5/Asia/Calcutta:\ - 20040213T130000\ -DTEND;TZID=/softwarestudio.org/Olson_20011030_5/Asia/Calcutta:\ - 20040213T133000\ -TRANSP:OPAQUE\ -SEQUENCE:3\ -SUMMARY:Test - Travel plans to Kansas\ -LOCATION:Yellow Brick road\ -CLASS:PUBLIC\ -ORGANIZER;CN=dorothy:MAILTO:dorothy@oz\ -DESCRIPTION: Discuss way to home\ -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=ACCEPTED;\ - RSVP=TRUE;CN=dorothy;LANGUAGE=en:MAILTO:dorothy@oz\ -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION;\ - RSVP=TRUE;CN=tinman;LANGUAGE=en:MAILTO:tinman@oz\ -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION;\ - RSVP=TRUE;CN=toto;LANGUAGE=en:MAILTO:toto@oz\ -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=OPT-PARTICIPANT;PARTSTAT=NEEDS-ACTION;\ - RSVP=TRUE;CN=scarecrow;LANGUAGE=en:MAILTO:scarecrow@oz\ -LAST-MODIFIED:20040213T055647Z\ -END:VEVENT" - -static char * -test_get_object (ECal *client) -{ - const char *uid = "20040213T055519Z-15802-500-1-3@testcal"; - char *actual; - icalcomponent *icalcomp; - gboolean compare; - GError *error; - - if (!e_cal_get_object (client, uid, NULL, &icalcomp, &error)) { - cl_printf (client, "Test Get object : Could not get the object: %s\n", error->message); - return error->message; - } - - actual = icalcomponent_as_ical_string (icalcomp); - compare = !strcmp (actual, EXPECTED); - - g_free (actual); - - mu_assert ("Test : get_object does not match the expected output", compare); - return NULL; -} - -static char * -test_timezones (ECal *client) -{ - icaltimezone *zone; - GError *error = NULL; - if (!e_cal_get_timezone (client, "UTC", &zone, &error)) - { - cl_printf (client, "Could not get the timezone\n"); - } - - printf ("\n\nTime Zones : \n%s *** %s", icaltimezone_get_display_name (zone), icaltimezone_get_tzid (zone)); - printf ("\n\nTime Zones : \n%s", icaltimezone_get_location (zone)); - - - return NULL; -} - -static char * -all_tests(ECal *client, const gchar *uri) -{ - ECal *ecal; - char *tmp, *uid; - - mu_run_test (test_new_system_calendar ()); - mu_run_test (test_new_system_tasks ()); - mu_run_test (test_set_uri (client, uri)); - mu_run_test (test_get_source (client, uri)); - mu_run_test (test_cal_loaded (client)); - - /* test_query acts on pre-loaded data. Hence it must executed before - * any writes are made */ - mu_run_test (test_query (client, "(contains? \"any\" \"test\")", 2)); - mu_run_test (test_query (client, "(contains? \"summary\" \"Kansas\")", 1)); - mu_run_test (test_query (client, "(contains? \"any\" \"gibberish\")", 0)); - - - mu_run_test (test_get_default_object (client)); - mu_run_test (test_get_object (client)); - mu_run_test (test_get_free_busy (client)); - mu_run_test (test_object_creation (client, &uid)); - mu_run_test (test_object_modification (client, uid)); -// mu_run_test (test_object_removal (client)); - mu_run_test (test_get_alarms_in_range (client)); - -// tmp = g_strconcat (uri, "_tmp", NULL); -// mu_run_test (test_e_cal_new (&ecal, tmp)); -// mu_run_test (test_e_cal_remove (ecal, tmp)); -// g_free (tmp); - - test_timezones (client); - - return NULL; -} - -/* Creates a calendar client and tries to load the specified URI into it */ -static void -create_client (ECal **client, const gchar *uri, ECalSourceType type, gboolean only_if_exists) -{ - char *results; - ECalView *query; - char *cal_uri; - GError *error = NULL; - - cal_uri = g_strconcat ("file://", uri, NULL); - *client = e_cal_new_from_uri (cal_uri, type); - if (!*client) { - g_message (G_STRLOC ": could not create the client"); - exit (1); - } - - g_object_weak_ref (G_OBJECT (*client), client_destroy_cb, NULL); - - cl_printf (*client, "Calendar loading `%s'...\n", uri); - - if (!e_cal_open (*client, only_if_exists, &error)) { - cl_printf (*client, "Load/create %s\n", error->message); - exit (1); - } - g_clear_error (&error); - - if (!e_cal_get_query (*client, "(contains? \"any\" \"Event\")", &query, NULL)) { - cl_printf (*client, G_STRLOC ": Unable to obtain query"); - exit (1); - } - - g_signal_connect (G_OBJECT (query), "objects_added", - G_CALLBACK (objects_added_cb), client); - g_signal_connect (G_OBJECT (query), "objects_modified", - G_CALLBACK (objects_modified_cb), client); - g_signal_connect (G_OBJECT (query), "objects_removed", - G_CALLBACK (objects_removed_cb), client); - g_signal_connect (G_OBJECT (query), "view_done", - G_CALLBACK (view_done_cb), client); - - e_cal_view_start (query); - - results = all_tests (*client, uri); - cl_printf (*client, "\n\n\n*************Tests run: %d****************\n\n", tests_run); - cl_printf (*client, "*************Tests passed: %d*************\n\n\n", tests_passed); - if (results != 0) - cl_printf (*client, "***Failures********%s\n", results); - - - cl_printf (*client, "dump of the test calendar data"); - list_uids (*client); - g_free (cal_uri); - -} - -int -main (int argc, char **argv) -{ - char *uri; - bindtextdomain (GETTEXT_PACKAGE, EVOLUTION_LOCALEDIR); - textdomain (GETTEXT_PACKAGE); - - g_type_init (); - bonobo_activation_init (argc, argv); - - if (!bonobo_init (&argc, argv)) { - g_message ("main(): could not initialize Bonobo"); - exit (1); - } - - /* arg1- file name; arg2- client suffix */ - uri = g_strconcat (argv[1], argv[2], NULL); - create_client (&client1, uri, E_CAL_SOURCE_TYPE_EVENT, FALSE); - - g_free (uri); - bonobo_main (); - return 0; -} diff --git a/calendar/tests/ecal/test-runner.sh b/calendar/tests/ecal/test-runner.sh deleted file mode 100755 index 17709ace3..000000000 --- a/calendar/tests/ecal/test-runner.sh +++ /dev/null @@ -1,22 +0,0 @@ -#! /bin/sh -# Usage : Argument 1 specifies the no. of libecal client instances would be -# executed -i=0 -if [ ! -d tmp ] -then - mkdir tmp -fi -while [ $i -ne $1 ] -do -i=$(($i+1)) -if [ ! -d $HOME/.evolution/calendar/local/OnThisComputer/TestCal$i ] -then - mkdir $HOME/.evolution/calendar/local/OnThisComputer/TestCal$i -fi -cp -f testdata.ics $HOME/.evolution/calendar/local/OnThisComputer/TestCal$i/calendar.ics -./test-ecal $HOME/.evolution/calendar/local/OnThisComputer/TestCal $i | tee -i "tmp/$i.out" & -#./test-ecal $HOME/.evolution/calendar/local/OnThisComputer/TestCal $i > "tmp/$i.out" & -done -dateTest=`date` -echo "End of testing at: $dateTest" -exit 0 diff --git a/calendar/tests/ecal/test-search.c b/calendar/tests/ecal/test-search.c deleted file mode 100644 index c8bf521ee..000000000 --- a/calendar/tests/ecal/test-search.c +++ /dev/null @@ -1,53 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ - -#include <libgnome/gnome-init.h> -#include <bonobo/bonobo-main.h> -#include <stdlib.h> -#include <libecal/e-cal.h> - -int -main (int argc, char **argv) -{ - ECal *ecal; - GList *l, *objects; - - gnome_program_init("test-search", "0.0", LIBGNOME_MODULE, argc, argv, NULL); - - if (bonobo_init (&argc, argv) == FALSE) - g_error ("Could not initialize Bonobo"); - - if (argc < 3) { - printf ("usage: test-search <uid> <query>\n"); - exit (0); - } - - ecal = e_cal_new_from_uri (argv[1], E_CAL_SOURCE_TYPE_EVENT); - - if (!e_cal_open (ecal, TRUE, NULL)) { - printf ("failed to open calendar\n"); - exit(0); - } - - if (!e_cal_get_object_list_as_comp (ecal, argv[2], &objects, NULL)) { - printf ("failed to get objects\n"); - exit(0); - } - - printf ("Received %d objects\n", g_list_length (objects)); - for (l = objects; l; l = l->next) { - ECalComponent *comp = E_CAL_COMPONENT (l->data); - char *str; - - str = e_cal_component_get_as_string (comp); - printf ("%s\n", str); - - g_free (str); - g_object_unref (comp); - } - - g_list_free (objects); - - g_object_unref (ecal); - - return 0; -} diff --git a/calendar/tests/ecal/testdata.ics b/calendar/tests/ecal/testdata.ics deleted file mode 100644 index d5924795b..000000000 --- a/calendar/tests/ecal/testdata.ics +++ /dev/null @@ -1,63 +0,0 @@ -BEGIN:VCALENDAR -CALSCALE:GREGORIAN -PRODID:-//Ximian//NONSGML Evolution Calendar//EN -VERSION:2.0 -BEGIN:VTIMEZONE -TZID:/softwarestudio.org/Olson_20011030_5/Asia/Calcutta -X-LIC-LOCATION:Asia/Calcutta -BEGIN:STANDARD -TZOFFSETFROM:+0530 -TZOFFSETTO:+0530 -TZNAME:IST -DTSTART:19700101T000000 -END:STANDARD -END:VTIMEZONE -BEGIN:VEVENT -UID:20040213T055344Z-15802-500-1-2@testcal -DTSTAMP:20040213T055344Z -DTSTART;TZID=/softwarestudio.org/Olson_20011030_5/Asia/Calcutta: - 20040213T100000 -DTEND;TZID=/softwarestudio.org/Olson_20011030_5/Asia/Calcutta: - 20040213T103000 -TRANSP:OPAQUE -SEQUENCE:3 -SUMMARY: Test - Meet the wizard -LOCATION:Emerald city -CLASS:PUBLIC -ORGANIZER;CN=dorothy:MAILTO:dorothy@oz -DESCRIPTION:Present a wish list -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=ACCEPTED; - RSVP=TRUE;CN=dorothy;LANGUAGE=en:MAILTO:dorothy@oz -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION; - RSVP=TRUE;CN=wizard;LANGUAGE=en:MAILTO:wizard@oz -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION; - RSVP=TRUE;CN=tinman;LANGUAGE=en:MAILTO:tinman@oz -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=OPT-PARTICIPANT;PARTSTAT=NEEDS-ACTION; - RSVP=TRUE;CN=lion;LANGUAGE=en:MAILTO:lion@oz -LAST-MODIFIED:20040213T055500Z -END:VEVENT -BEGIN:VEVENT -UID:20040213T055519Z-15802-500-1-3@testcal -DTSTAMP:20040213T055519Z -DTSTART;TZID=/softwarestudio.org/Olson_20011030_5/Asia/Calcutta: - 20040213T130000 -DTEND;TZID=/softwarestudio.org/Olson_20011030_5/Asia/Calcutta: - 20040213T133000 -TRANSP:OPAQUE -SEQUENCE:3 -SUMMARY:Test - Travel plans to Kansas -LOCATION:Yellow Brick road -CLASS:PUBLIC -ORGANIZER;CN=dorothy:MAILTO:dorothy@oz -DESCRIPTION: Discuss way to home -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=ACCEPTED; - RSVP=TRUE;CN=dorothy;LANGUAGE=en:MAILTO:dorothy@oz -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION; - RSVP=TRUE;CN=tinman;LANGUAGE=en:MAILTO:tinman@oz -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION; - RSVP=TRUE;CN=toto;LANGUAGE=en:MAILTO:toto@oz -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=OPT-PARTICIPANT;PARTSTAT=NEEDS-ACTION; - RSVP=TRUE;CN=scarecrow;LANGUAGE=en:MAILTO:scarecrow@oz -LAST-MODIFIED:20040213T055647Z -END:VEVENT -END:VCALENDAR |