From aa424cd9b26e35f6f68aeeb18c4ed72a7d14b979 Mon Sep 17 00:00:00 2001 From: Matthew Barnes Date: Thu, 24 Jan 2013 20:04:14 -0500 Subject: [PATCH] Replace EGdbusBook with EDBusAddressBook. --- addressbook/libebook/e-book-client.c | 2339 ++++++++++++-------- addressbook/libebook/e-book-client.h | 26 +- addressbook/libedata-book/e-book-backend.c | 41 +- addressbook/libedata-book/e-book-backend.h | 8 +- addressbook/libedata-book/e-data-book.c | 741 ++++--- addressbook/libedata-book/e-data-book.h | 8 +- addressbook/libegdbus/Makefile.am | 2 - addressbook/libegdbus/e-gdbus-book.c | 1462 ------------ addressbook/libegdbus/e-gdbus-book.h | 259 --- .../libedata-book/libedata-book-sections.txt | 8 +- 10 files changed, 1959 insertions(+), 2935 deletions(-) delete mode 100644 addressbook/libegdbus/e-gdbus-book.c delete mode 100644 addressbook/libegdbus/e-gdbus-book.h diff --git a/addressbook/libebook/e-book-client.c b/addressbook/libebook/e-book-client.c index 4767464..c2e4130 100644 --- a/addressbook/libebook/e-book-client.c +++ b/addressbook/libebook/e-book-client.c @@ -27,6 +27,7 @@ #include /* Private D-Bus classes. */ +#include #include #include @@ -36,18 +37,110 @@ #include "e-contact.h" #include "e-name-western.h" -#include "e-gdbus-book.h" - #define E_BOOK_CLIENT_GET_PRIVATE(obj) \ (G_TYPE_INSTANCE_GET_PRIVATE \ ((obj), E_TYPE_BOOK_CLIENT, EBookClientPrivate)) +/* Set this to a sufficiently large value + * to cover most long-running operations. */ +#define DBUS_PROXY_TIMEOUT_MS (3 * 60 * 1000) /* 3 minutes */ + +typedef struct _AsyncContext AsyncContext; +typedef struct _SignalClosure SignalClosure; +typedef struct _RunInThreadClosure RunInThreadClosure; + struct _EBookClientPrivate { - GDBusProxy *dbus_proxy; + EDBusAddressBook *dbus_proxy; + GMainContext *main_context; guint gone_signal_id; + + gulong dbus_proxy_error_handler_id; + gulong dbus_proxy_notify_handler_id; +}; + +struct _AsyncContext { + EContact *contact; + EBookClientView *client_view; + GSList *object_list; + GSList *string_list; + gchar *sexp; + gchar *uid; +}; + +struct _SignalClosure { + EClient *client; + gchar *property_name; + gchar *error_message; +}; + +struct _RunInThreadClosure { + GSimpleAsyncThreadFunc func; + GSimpleAsyncResult *simple; + GCancellable *cancellable; }; -G_DEFINE_TYPE (EBookClient, e_book_client, E_TYPE_CLIENT) +/* Forward Declarations */ +static void e_book_client_initable_init + (GInitableIface *interface); +static void e_book_client_async_initable_init + (GAsyncInitableIface *interface); + +G_DEFINE_TYPE_WITH_CODE ( + EBookClient, + e_book_client, + E_TYPE_CLIENT, + G_IMPLEMENT_INTERFACE ( + G_TYPE_INITABLE, + e_book_client_initable_init) + G_IMPLEMENT_INTERFACE ( + G_TYPE_ASYNC_INITABLE, + e_book_client_async_initable_init)) + +static void +async_context_free (AsyncContext *async_context) +{ + if (async_context->contact != NULL) + g_object_unref (async_context->contact); + + if (async_context->client_view != NULL) + g_object_unref (async_context->client_view); + + g_slist_free_full ( + async_context->object_list, + (GDestroyNotify) g_object_unref); + + g_slist_free_full ( + async_context->string_list, + (GDestroyNotify) g_free); + + g_free (async_context->sexp); + g_free (async_context->uid); + + g_slice_free (AsyncContext, async_context); +} + +static void +signal_closure_free (SignalClosure *signal_closure) +{ + g_object_unref (signal_closure->client); + + g_free (signal_closure->property_name); + g_free (signal_closure->error_message); + + g_slice_free (SignalClosure, signal_closure); +} + +static void +run_in_thread_closure_free (RunInThreadClosure *run_in_thread_closure) +{ + if (run_in_thread_closure->simple != NULL) + g_object_unref (run_in_thread_closure->simple); + + if (run_in_thread_closure->cancellable != NULL) + g_object_unref (run_in_thread_closure->cancellable); + + g_slice_free (RunInThreadClosure, run_in_thread_closure); +} /* * Well-known book backend properties: @@ -285,6 +378,107 @@ gdbus_book_factory_activate (GCancellable *cancellable, return TRUE; } +static gpointer +book_client_dbus_thread (gpointer user_data) +{ + GMainContext *main_context = user_data; + GMainLoop *main_loop; + + g_main_context_push_thread_default (main_context); + + main_loop = g_main_loop_new (main_context, FALSE); + g_main_loop_run (main_loop); + g_main_loop_unref (main_loop); + + g_main_context_pop_thread_default (main_context); + + g_main_context_unref (main_context); + + return NULL; +} + +static gpointer +book_client_dbus_thread_init (gpointer unused) +{ + GMainContext *main_context; + + main_context = g_main_context_new (); + + /* This thread terminates when the process itself terminates, so + * no need to worry about unreferencing the returned GThread. */ + g_thread_new ( + "book-client-dbus-thread", + book_client_dbus_thread, + g_main_context_ref (main_context)); + + return main_context; +} + +static GMainContext * +book_client_ref_dbus_main_context (void) +{ + static GOnce book_client_dbus_thread_once = G_ONCE_INIT; + + g_once ( + &book_client_dbus_thread_once, + book_client_dbus_thread_init, NULL); + + return g_main_context_ref (book_client_dbus_thread_once.retval); +} + +static gboolean +book_client_run_in_dbus_thread_idle_cb (gpointer user_data) +{ + RunInThreadClosure *closure = user_data; + GObject *source_object; + GAsyncResult *result; + + result = G_ASYNC_RESULT (closure->simple); + source_object = g_async_result_get_source_object (result); + + closure->func ( + closure->simple, + source_object, + closure->cancellable); + + if (source_object != NULL) + g_object_unref (source_object); + + g_simple_async_result_complete_in_idle (closure->simple); + + return FALSE; +} + +static void +book_client_run_in_dbus_thread (GSimpleAsyncResult *simple, + GSimpleAsyncThreadFunc func, + gint io_priority, + GCancellable *cancellable) +{ + RunInThreadClosure *closure; + GMainContext *main_context; + GSource *idle_source; + + main_context = book_client_ref_dbus_main_context (); + + closure = g_slice_new0 (RunInThreadClosure); + closure->func = func; + closure->simple = g_object_ref (simple); + + if (G_IS_CANCELLABLE (cancellable)) + closure->cancellable = g_object_ref (cancellable); + + idle_source = g_idle_source_new (); + g_source_set_priority (idle_source, io_priority); + g_source_set_callback ( + idle_source, book_client_run_in_dbus_thread_idle_cb, + closure, (GDestroyNotify) run_in_thread_closure_free); + g_source_attach (idle_source, main_context); + g_source_unref (idle_source); + + g_main_context_unref (main_context); +} + static void gdbus_book_client_disconnect (EBookClient *client); /* @@ -344,7 +538,7 @@ gdbus_book_client_disconnect (EBookClient *client) g_dbus_connection_signal_unsubscribe (connection, client->priv->gone_signal_id); client->priv->gone_signal_id = 0; - e_gdbus_book_call_close_sync ( + e_dbus_address_book_call_close_sync ( client->priv->dbus_proxy, NULL, NULL); g_object_unref (client->priv->dbus_proxy); client->priv->dbus_proxy = NULL; @@ -353,131 +547,167 @@ gdbus_book_client_disconnect (EBookClient *client) UNLOCK_FACTORY (); } -static void -backend_error_cb (EGdbusBook *dbus_proxy, - const gchar *message, - EBookClient *client) +static gboolean +book_client_emit_backend_error_idle_cb (gpointer user_data) { - g_return_if_fail (E_IS_BOOK_CLIENT (client)); - g_return_if_fail (message != NULL); + SignalClosure *signal_closure = user_data; + + g_signal_emit_by_name ( + signal_closure->client, + "backend-error", + signal_closure->error_message); - e_client_emit_backend_error (E_CLIENT (client), message); + return FALSE; } -static void -readonly_cb (EGdbusBook *dbus_proxy, - gboolean readonly, - EBookClient *client) -{ - g_return_if_fail (E_IS_BOOK_CLIENT (client)); +static gboolean +book_client_emit_backend_property_changed_idle_cb (gpointer user_data) +{ + SignalClosure *signal_closure = user_data; + gchar *prop_value = NULL; + + /* XXX Despite appearances, this function does not block. */ + e_client_get_backend_property_sync ( + signal_closure->client, + signal_closure->property_name, + &prop_value, NULL, NULL); + + if (prop_value != NULL) { + g_signal_emit_by_name ( + signal_closure->client, + "backend-property-changed", + signal_closure->property_name, + prop_value); + g_free (prop_value); + } - e_client_set_readonly (E_CLIENT (client), readonly); + return FALSE; } static void -online_cb (EGdbusBook *dbus_proxy, - gboolean is_online, - EBookClient *client) +book_client_dbus_proxy_error_cb (EDBusAddressBook *dbus_proxy, + const gchar *error_message, + EBookClient *book_client) { - g_return_if_fail (E_IS_BOOK_CLIENT (client)); + GSource *idle_source; + SignalClosure *signal_closure; + + signal_closure = g_slice_new0 (SignalClosure); + signal_closure->client = g_object_ref (book_client); + signal_closure->error_message = g_strdup (error_message); - e_client_set_online (E_CLIENT (client), is_online); + idle_source = g_idle_source_new (); + g_source_set_callback ( + idle_source, + book_client_emit_backend_error_idle_cb, + signal_closure, + (GDestroyNotify) signal_closure_free); + g_source_attach (idle_source, book_client->priv->main_context); + g_source_unref (idle_source); } static void -opened_cb (EGdbusBook *dbus_proxy, - const gchar * const *error_strv, - EBookClient *client) +book_client_dbus_proxy_notify_cb (EDBusAddressBook *dbus_proxy, + GParamSpec *pspec, + EBookClient *book_client) { - GError *error = NULL; + const gchar *backend_prop_name = NULL; - g_return_if_fail (E_IS_BOOK_CLIENT (client)); - g_return_if_fail (error_strv != NULL); - g_return_if_fail (e_gdbus_templates_decode_error (error_strv, &error)); - - e_client_emit_opened (E_CLIENT (client), error); + if (g_str_equal (pspec->name, "cache-dir")) { + backend_prop_name = CLIENT_BACKEND_PROPERTY_CACHE_DIR; + } - if (error) - g_error_free (error); -} + if (g_str_equal (pspec->name, "capabilities")) { + gchar **strv; + gchar *csv; -static void -backend_property_changed_cb (EGdbusBook *dbus_proxy, - const gchar * const *name_value_strv, - EBookClient *client) -{ - gchar *prop_name = NULL, *prop_value = NULL; + backend_prop_name = CLIENT_BACKEND_PROPERTY_CAPABILITIES; - g_return_if_fail (E_IS_BOOK_CLIENT (client)); - g_return_if_fail (name_value_strv != NULL); - g_return_if_fail (e_gdbus_templates_decode_two_strings (name_value_strv, &prop_name, &prop_value)); - g_return_if_fail (prop_name != NULL); - g_return_if_fail (*prop_name); - g_return_if_fail (prop_value != NULL); + strv = e_dbus_address_book_dup_capabilities (dbus_proxy); + csv = g_strjoinv (",", strv); + e_client_set_capabilities (E_CLIENT (book_client), csv); + g_free (csv); + g_free (strv); + } - e_client_emit_backend_property_changed (E_CLIENT (client), prop_name, prop_value); + if (g_str_equal (pspec->name, "online")) { + gboolean online; - g_free (prop_name); - g_free (prop_value); -} + backend_prop_name = CLIENT_BACKEND_PROPERTY_ONLINE; -/* - * Converts a GSList of EContact objects into a NULL-terminated array of - * valid UTF-8 vcard strings, suitable for sending over DBus. - */ -static gchar ** -contact_slist_to_utf8_vcard_array (GSList *contacts) -{ - gchar **array; - const GSList *l; - gint i = 0; + online = e_dbus_address_book_get_online (dbus_proxy); + e_client_set_online (E_CLIENT (book_client), online); + } - array = g_new0 (gchar *, g_slist_length (contacts) + 1); - for (l = contacts; l != NULL; l = l->next) { - gchar *vcard = e_vcard_to_string (E_VCARD (l->data), EVC_FORMAT_VCARD_30); - array[i++] = e_util_utf8_make_valid (vcard); - g_free (vcard); + if (g_str_equal (pspec->name, "required-fields")) { + backend_prop_name = BOOK_BACKEND_PROPERTY_REQUIRED_FIELDS; } - return array; -} + if (g_str_equal (pspec->name, "revision")) { + backend_prop_name = CLIENT_BACKEND_PROPERTY_REVISION; + } -static gboolean -book_client_get_backend_property_from_cache_finish (EClient *client, - GAsyncResult *result, - gchar **prop_value, - GError **error) -{ - GSimpleAsyncResult *simple; - GError *local_error = NULL; + if (g_str_equal (pspec->name, "supported-fields")) { + backend_prop_name = BOOK_BACKEND_PROPERTY_SUPPORTED_FIELDS; + } - g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); - g_return_val_if_fail (result != NULL, FALSE); - g_return_val_if_fail (prop_value != NULL, FALSE); - g_return_val_if_fail (g_simple_async_result_is_valid (result, G_OBJECT (client), book_client_get_backend_property_from_cache_finish), FALSE); + if (g_str_equal (pspec->name, "writable")) { + gboolean writable; - simple = G_SIMPLE_ASYNC_RESULT (result); + backend_prop_name = CLIENT_BACKEND_PROPERTY_READONLY; - if (g_simple_async_result_propagate_error (simple, &local_error)) { - e_client_unwrap_dbus_error (client, local_error, error); - return FALSE; + writable = e_dbus_address_book_get_writable (dbus_proxy); + e_client_set_readonly (E_CLIENT (book_client), !writable); } - *prop_value = g_strdup (g_simple_async_result_get_op_res_gpointer (simple)); - - return *prop_value != NULL; + if (backend_prop_name != NULL) { + GSource *idle_source; + SignalClosure *signal_closure; + + signal_closure = g_slice_new0 (SignalClosure); + signal_closure->client = g_object_ref (book_client); + signal_closure->property_name = g_strdup (backend_prop_name); + + idle_source = g_idle_source_new (); + g_source_set_callback ( + idle_source, + book_client_emit_backend_property_changed_idle_cb, + signal_closure, + (GDestroyNotify) signal_closure_free); + g_source_attach (idle_source, book_client->priv->main_context); + g_source_unref (idle_source); + } } static void book_client_dispose (GObject *object) { - EClient *client; + EBookClientPrivate *priv; + + priv = E_BOOK_CLIENT_GET_PRIVATE (object); + + e_client_cancel_all (E_CLIENT (object)); + + if (priv->dbus_proxy_error_handler_id > 0) { + g_signal_handler_disconnect ( + priv->dbus_proxy, + priv->dbus_proxy_error_handler_id); + priv->dbus_proxy_error_handler_id = 0; + } - client = E_CLIENT (object); + if (priv->dbus_proxy_notify_handler_id > 0) { + g_signal_handler_disconnect ( + priv->dbus_proxy, + priv->dbus_proxy_notify_handler_id); + priv->dbus_proxy_notify_handler_id = 0; + } - e_client_cancel_all (client); + gdbus_book_client_disconnect (E_BOOK_CLIENT (object)); - gdbus_book_client_disconnect (E_BOOK_CLIENT (client)); + if (priv->main_context != NULL) { + g_main_context_unref (priv->main_context); + priv->main_context = NULL; + } /* Chain up to parent's dispose() method. */ G_OBJECT_CLASS (e_book_client_parent_class)->dispose (object); @@ -514,94 +744,15 @@ book_client_unwrap_dbus_error (EClient *client, unwrap_dbus_error (dbus_error, out_error); } -static void -book_client_retrieve_capabilities (EClient *client, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - g_return_if_fail (E_IS_BOOK_CLIENT (client)); - - e_client_get_backend_property (client, CLIENT_BACKEND_PROPERTY_CAPABILITIES, cancellable, callback, user_data); -} - -static gboolean -book_client_retrieve_capabilities_finish (EClient *client, - GAsyncResult *result, - gchar **capabilities, - GError **error) -{ - g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); - - return e_client_get_backend_property_finish (client, result, capabilities, error); -} - static gboolean book_client_retrieve_capabilities_sync (EClient *client, gchar **capabilities, GCancellable *cancellable, GError **error) { - g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); - - return e_client_get_backend_property_sync (client, CLIENT_BACKEND_PROPERTY_CAPABILITIES, capabilities, cancellable, error); -} - -static void -book_client_get_backend_property (EClient *client, - const gchar *prop_name, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - gchar *prop_value; - - prop_value = e_client_get_backend_property_from_cache (client, prop_name); - if (prop_value) { - e_client_finish_async_without_dbus ( - client, cancellable, callback, user_data, - book_client_get_backend_property_from_cache_finish, - prop_value, g_free); - } else { - e_client_proxy_call_string_with_res_op_data ( - client, prop_name, - cancellable, callback, user_data, - book_client_get_backend_property, prop_name, - e_gdbus_book_call_get_backend_property, - NULL, NULL, - e_gdbus_book_call_get_backend_property_finish, - NULL, NULL); - } -} - -static gboolean -book_client_get_backend_property_finish (EClient *client, - GAsyncResult *result, - gchar **prop_value, - GError **error) -{ - gchar *str = NULL; - gboolean res; - - g_return_val_if_fail (prop_value != NULL, FALSE); - - if (g_simple_async_result_get_source_tag (G_SIMPLE_ASYNC_RESULT (result)) == book_client_get_backend_property_from_cache_finish) { - res = book_client_get_backend_property_from_cache_finish (client, result, &str, error); - } else { - res = e_client_proxy_call_finish_string ( - client, result, &str, error, - book_client_get_backend_property); - if (res && str) { - const gchar *prop_name = g_object_get_data (G_OBJECT (result), "res-op-data"); - - if (prop_name && *prop_name) - e_client_update_backend_property_cache (client, prop_name, str); - } - } - - *prop_value = str; - - return res; + return e_client_get_backend_property_sync ( + client, CLIENT_BACKEND_PROPERTY_CAPABILITIES, + capabilities, cancellable, error); } static gboolean @@ -612,36 +763,74 @@ book_client_get_backend_property_sync (EClient *client, GError **error) { EBookClient *book_client; - gchar *prop_val; - gboolean res; - - g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); + EDBusAddressBook *dbus_proxy; + gchar **strv; book_client = E_BOOK_CLIENT (client); + dbus_proxy = book_client->priv->dbus_proxy; - if (book_client->priv->dbus_proxy == NULL) { - set_proxy_gone_error (error); - return FALSE; + if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_OPENED)) { + *prop_value = g_strdup ("TRUE"); + return TRUE; } - prop_val = e_client_get_backend_property_from_cache (client, prop_name); - if (prop_val) { - g_return_val_if_fail (prop_value != NULL, FALSE); + if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_OPENING)) { + *prop_value = g_strdup ("FALSE"); + return TRUE; + } - *prop_value = prop_val; + if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_ONLINE)) { + if (e_dbus_address_book_get_online (dbus_proxy)) + *prop_value = g_strdup ("TRUE"); + else + *prop_value = g_strdup ("FALSE"); + return TRUE; + } + if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_READONLY)) { + if (e_dbus_address_book_get_writable (dbus_proxy)) + *prop_value = g_strdup ("FALSE"); + else + *prop_value = g_strdup ("TRUE"); return TRUE; } - res = e_client_proxy_call_sync_string__string ( - client, prop_name, prop_value, cancellable, error, - e_gdbus_book_call_get_backend_property_sync); + if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_CACHE_DIR)) { + *prop_value = e_dbus_address_book_dup_cache_dir (dbus_proxy); + return TRUE; + } - if (res && prop_value) - e_client_update_backend_property_cache ( - client, prop_name, *prop_value); + if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_REVISION)) { + *prop_value = e_dbus_address_book_dup_revision (dbus_proxy); + return TRUE; + } + + if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_CAPABILITIES)) { + strv = e_dbus_address_book_dup_capabilities (dbus_proxy); + *prop_value = g_strjoinv (",", strv); + g_strfreev (strv); + return TRUE; + } + + if (g_str_equal (prop_name, BOOK_BACKEND_PROPERTY_REQUIRED_FIELDS)) { + strv = e_dbus_address_book_dup_required_fields (dbus_proxy); + *prop_value = g_strjoinv (",", strv); + g_strfreev (strv); + return TRUE; + } - return res; + if (g_str_equal (prop_name, BOOK_BACKEND_PROPERTY_SUPPORTED_FIELDS)) { + strv = e_dbus_address_book_dup_supported_fields (dbus_proxy); + *prop_value = g_strjoinv (",", strv); + g_strfreev (strv); + return TRUE; + } + + g_set_error ( + error, E_CLIENT_ERROR, E_CLIENT_ERROR_NOT_SUPPORTED, + _("Unknown book property '%s'"), prop_name); + + return TRUE; } static gboolean @@ -660,31 +849,6 @@ book_client_set_backend_property_sync (EClient *client, return FALSE; } -static void -book_client_open (EClient *client, - gboolean only_if_exists, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_client_proxy_call_boolean ( - client, only_if_exists, - cancellable, callback, user_data, - book_client_open, - e_gdbus_book_call_open, - e_gdbus_book_call_open_finish, - NULL, NULL, NULL, NULL); -} - -static gboolean -book_client_open_finish (EClient *client, - GAsyncResult *result, - GError **error) -{ - return e_client_proxy_call_finish_void ( - client, result, error, book_client_open); -} - static gboolean book_client_open_sync (EClient *client, gboolean only_if_exists, @@ -702,32 +866,8 @@ book_client_open_sync (EClient *client, return FALSE; } - return e_client_proxy_call_sync_boolean__void ( - client, only_if_exists, cancellable, error, - e_gdbus_book_call_open_sync); -} - -static void -book_client_refresh (EClient *client, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_client_proxy_call_void ( - client, cancellable, callback, user_data, - book_client_refresh, - e_gdbus_book_call_refresh, - e_gdbus_book_call_refresh_finish, - NULL, NULL, NULL, NULL); -} - -static gboolean -book_client_refresh_finish (EClient *client, - GAsyncResult *result, - GError **error) -{ - return e_client_proxy_call_finish_void ( - client, result, error, book_client_refresh); + return e_dbus_address_book_call_open_sync ( + book_client->priv->dbus_proxy, cancellable, error); } static gboolean @@ -746,9 +886,168 @@ book_client_refresh_sync (EClient *client, return FALSE; } - return e_client_proxy_call_sync_void__void ( - client, cancellable, error, - e_gdbus_book_call_refresh_sync); + return e_dbus_address_book_call_refresh_sync ( + book_client->priv->dbus_proxy, cancellable, error); +} + +static void +book_client_init_in_dbus_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + EBookClientPrivate *priv; + EClient *client; + ESource *source; + GDBusConnection *connection; + const gchar *uid; + gchar *object_path = NULL; + gulong handler_id; + GError *error = NULL; + + priv = E_BOOK_CLIENT_GET_PRIVATE (source_object); + + client = E_CLIENT (source_object); + source = e_client_get_source (client); + uid = e_source_get_uid (source); + + LOCK_FACTORY (); + gdbus_book_factory_activate (cancellable, &error); + UNLOCK_FACTORY (); + + if (error != NULL) { + unwrap_dbus_error (error, &error); + g_simple_async_result_take_error (simple, error); + return; + } + + e_dbus_address_book_factory_call_open_address_book_sync ( + book_factory, uid, &object_path, cancellable, &error); + + /* Sanity check. */ + g_return_if_fail ( + ((object_path != NULL) && (error == NULL)) || + ((object_path == NULL) && (error != NULL))); + + if (object_path == NULL) { + unwrap_dbus_error (error, &error); + g_simple_async_result_take_error (simple, error); + return; + } + + connection = g_dbus_proxy_get_connection (G_DBUS_PROXY (book_factory)); + + priv->dbus_proxy = e_dbus_address_book_proxy_new_sync ( + connection, + G_DBUS_PROXY_FLAGS_NONE, + ADDRESS_BOOK_DBUS_SERVICE_NAME, + object_path, + cancellable, &error); + + g_free (object_path); + + /* Sanity check. */ + g_return_if_fail ( + ((priv->dbus_proxy != NULL) && (error == NULL)) || + ((priv->dbus_proxy == NULL) && (error != NULL))); + + if (error != NULL) { + unwrap_dbus_error (error, &error); + g_simple_async_result_take_error (simple, error); + return; + } + + g_dbus_proxy_set_default_timeout ( + G_DBUS_PROXY (priv->dbus_proxy), DBUS_PROXY_TIMEOUT_MS); + + priv->gone_signal_id = g_dbus_connection_signal_subscribe ( + connection, + "org.freedesktop.DBus", /* sender */ + "org.freedesktop.DBus", /* interface */ + "NameOwnerChanged", /* member */ + "/org/freedesktop/DBus", /* object_path */ + "org.gnome.evolution.dataserver.AddressBook", /* arg0 */ + G_DBUS_SIGNAL_FLAGS_NONE, + gdbus_book_client_connection_gone_cb, client, NULL); + + g_signal_connect ( + connection, "closed", + G_CALLBACK (gdbus_book_client_closed_cb), client); + + handler_id = g_signal_connect ( + priv->dbus_proxy, "error", + G_CALLBACK (book_client_dbus_proxy_error_cb), client); + priv->dbus_proxy_error_handler_id = handler_id; + + handler_id = g_signal_connect ( + priv->dbus_proxy, "notify", + G_CALLBACK (book_client_dbus_proxy_notify_cb), client); + priv->dbus_proxy_notify_handler_id = handler_id; +} + +static gboolean +book_client_initable_init (GInitable *initable, + GCancellable *cancellable, + GError **error) +{ + EAsyncClosure *closure; + GAsyncResult *result; + gboolean success; + + closure = e_async_closure_new (); + + g_async_initable_init_async ( + G_ASYNC_INITABLE (initable), + G_PRIORITY_DEFAULT, cancellable, + e_async_closure_callback, closure); + + result = e_async_closure_wait (closure); + + success = g_async_initable_init_finish ( + G_ASYNC_INITABLE (initable), result, error); + + e_async_closure_free (closure); + + return success; +} + +static void +book_client_initable_init_async (GAsyncInitable *initable, + gint io_priority, + GCancellable *cancellable, + GAsyncReadyCallback callback, + gpointer user_data) +{ + GSimpleAsyncResult *simple; + + simple = g_simple_async_result_new ( + G_OBJECT (initable), callback, user_data, + book_client_initable_init_async); + + g_simple_async_result_set_check_cancellable (simple, cancellable); + + book_client_run_in_dbus_thread ( + simple, book_client_init_in_dbus_thread, + io_priority, cancellable); + + g_object_unref (simple); +} + +static gboolean +book_client_initable_init_finish (GAsyncInitable *initable, + GAsyncResult *result, + GError **error) +{ + GSimpleAsyncResult *simple; + + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (initable), + book_client_initable_init_async), FALSE); + + simple = G_SIMPLE_ASYNC_RESULT (result); + + /* Assume success unless a GError is set. */ + return !g_simple_async_result_propagate_error (simple, error); } static void @@ -764,21 +1063,26 @@ e_book_client_class_init (EBookClientClass *class) object_class->finalize = book_client_finalize; client_class = E_CLIENT_CLASS (class); - client_class->get_dbus_proxy = book_client_get_dbus_proxy; - client_class->unwrap_dbus_error = book_client_unwrap_dbus_error; - client_class->retrieve_capabilities = book_client_retrieve_capabilities; - client_class->retrieve_capabilities_finish = book_client_retrieve_capabilities_finish; - client_class->retrieve_capabilities_sync = book_client_retrieve_capabilities_sync; - client_class->get_backend_property = book_client_get_backend_property; - client_class->get_backend_property_finish = book_client_get_backend_property_finish; - client_class->get_backend_property_sync = book_client_get_backend_property_sync; - client_class->set_backend_property_sync = book_client_set_backend_property_sync; - client_class->open = book_client_open; - client_class->open_finish = book_client_open_finish; - client_class->open_sync = book_client_open_sync; - client_class->refresh = book_client_refresh; - client_class->refresh_finish = book_client_refresh_finish; - client_class->refresh_sync = book_client_refresh_sync; + client_class->get_dbus_proxy = book_client_get_dbus_proxy; + client_class->unwrap_dbus_error = book_client_unwrap_dbus_error; + client_class->retrieve_capabilities_sync = book_client_retrieve_capabilities_sync; + client_class->get_backend_property_sync = book_client_get_backend_property_sync; + client_class->set_backend_property_sync = book_client_set_backend_property_sync; + client_class->open_sync = book_client_open_sync; + client_class->refresh_sync = book_client_refresh_sync; +} + +static void +e_book_client_initable_init (GInitableIface *interface) +{ + interface->init = book_client_initable_init; +} + +static void +e_book_client_async_initable_init (GAsyncInitableIface *interface) +{ + interface->init_async = book_client_initable_init_async; + interface->init_finish = book_client_initable_init_finish; } static void @@ -789,6 +1093,10 @@ e_book_client_init (EBookClient *client) UNLOCK_FACTORY (); client->priv = E_BOOK_CLIENT_GET_PRIVATE (client); + + /* This is so the D-Bus thread can schedule signal emissions + * on the thread-default context for this thread. */ + client->priv->main_context = g_main_context_ref_thread_default (); } /** @@ -808,105 +1116,11 @@ EBookClient * e_book_client_new (ESource *source, GError **error) { - EBookClient *client; - GError *err = NULL; - GDBusConnection *connection; - const gchar *uid; - gchar *object_path = NULL; - - g_return_val_if_fail (source != NULL, NULL); g_return_val_if_fail (E_IS_SOURCE (source), NULL); - LOCK_FACTORY (); - /* XXX Oops, e_book_client_new() forgot to take a GCancellable. */ - if (!gdbus_book_factory_activate (NULL, &err)) { - UNLOCK_FACTORY (); - if (err) { - unwrap_dbus_error (err, &err); - g_warning ("%s: Failed to run book factory: %s", G_STRFUNC, err->message); - g_propagate_error (error, err); - } else { - g_warning ("%s: Failed to run book factory: Unknown error", G_STRFUNC); - g_set_error_literal (error, E_CLIENT_ERROR, E_CLIENT_ERROR_DBUS_ERROR, _("Failed to run book factory")); - } - - return NULL; - } - - uid = e_source_get_uid (source); - - client = g_object_new (E_TYPE_BOOK_CLIENT, "source", source, NULL); - UNLOCK_FACTORY (); - - e_dbus_address_book_factory_call_open_address_book_sync ( - book_factory, uid, &object_path, NULL, &err); - - /* Sanity check. */ - g_return_val_if_fail ( - ((object_path != NULL) && (err == NULL)) || - ((object_path == NULL) && (err != NULL)), NULL); - - if (err != NULL) { - unwrap_dbus_error (err, &err); - g_propagate_error (error, err); - g_object_unref (client); - return NULL; - } - - connection = g_dbus_proxy_get_connection (G_DBUS_PROXY (book_factory)); - - client->priv->dbus_proxy = G_DBUS_PROXY (e_gdbus_book_proxy_new_sync ( - connection, - G_DBUS_PROXY_FLAGS_NONE, - ADDRESS_BOOK_DBUS_SERVICE_NAME, - object_path, - NULL, &err)); - - g_free (object_path); - - /* Sanity check. */ - g_return_val_if_fail ( - ((client->priv->dbus_proxy != NULL) && (err == NULL)) || - ((client->priv->dbus_proxy == NULL) && (err != NULL)), NULL); - - if (err != NULL) { - unwrap_dbus_error (err, &err); - g_propagate_error (error, err); - g_object_unref (client); - return NULL; - } - - client->priv->gone_signal_id = g_dbus_connection_signal_subscribe ( - connection, - "org.freedesktop.DBus", /* sender */ - "org.freedesktop.DBus", /* interface */ - "NameOwnerChanged", /* member */ - "/org/freedesktop/DBus", /* object_path */ - "org.gnome.evolution.dataserver.AddressBook", /* arg0 */ - G_DBUS_SIGNAL_FLAGS_NONE, - gdbus_book_client_connection_gone_cb, client, NULL); - - g_signal_connect ( - connection, "closed", - G_CALLBACK (gdbus_book_client_closed_cb), client); - - g_signal_connect ( - client->priv->dbus_proxy, "backend_error", - G_CALLBACK (backend_error_cb), client); - g_signal_connect ( - client->priv->dbus_proxy, "readonly", - G_CALLBACK (readonly_cb), client); - g_signal_connect ( - client->priv->dbus_proxy, "online", - G_CALLBACK (online_cb), client); - g_signal_connect ( - client->priv->dbus_proxy, "opened", - G_CALLBACK (opened_cb), client); - g_signal_connect ( - client->priv->dbus_proxy, "backend-property-changed", - G_CALLBACK (backend_property_changed_cb), client); - - return client; + return g_initable_new ( + E_TYPE_BOOK_CLIENT, NULL, error, + "source", source, NULL); } #define SELF_UID_PATH_ID "org.gnome.evolution-data-server.addressbook" @@ -953,12 +1167,12 @@ make_me_card (void) /** * e_book_client_get_self: * @registry: an #ESourceRegistry - * @contact: (out): an #EContact pointer to set - * @client: (out): an #EBookClient pointer to set + * @out_contact: (out): an #EContact pointer to set + * @out_client: (out): an #EBookClient pointer to set * @error: a #GError to set on failure * * Get the #EContact referring to the user of the address book - * and set it in @contact and @client. + * and set it in @out_contact and @out_client. * * Returns: %TRUE if successful, otherwise %FALSE. * @@ -966,67 +1180,74 @@ make_me_card (void) **/ gboolean e_book_client_get_self (ESourceRegistry *registry, - EContact **contact, - EBookClient **client, + EContact **out_contact, + EBookClient **out_client, GError **error) { + EBookClient *book_client; ESource *source; - GError *local_error = NULL; + EContact *contact = NULL; GSettings *settings; gchar *uid; + gboolean success; g_return_val_if_fail (E_IS_SOURCE_REGISTRY (registry), FALSE); - g_return_val_if_fail (contact != NULL, FALSE); - g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); + g_return_val_if_fail (out_contact != NULL, FALSE); + g_return_val_if_fail (out_client != NULL, FALSE); source = e_source_registry_ref_builtin_address_book (registry); - *client = e_book_client_new (source, &local_error); + book_client = e_book_client_new (source, error); g_object_unref (source); - if (!*client) { - g_propagate_error (error, local_error); + if (book_client == NULL) return FALSE; - } - - if (!e_client_open_sync (E_CLIENT (*client), FALSE, NULL, &local_error)) { - g_object_unref (*client); - *client = NULL; - g_propagate_error (error, local_error); + success = e_client_open_sync ( + E_CLIENT (book_client), FALSE, NULL, error); + if (!success) { + g_object_unref (book_client); return FALSE; } + *out_client = book_client; + settings = g_settings_new (SELF_UID_PATH_ID); uid = g_settings_get_string (settings, SELF_UID_KEY); g_object_unref (settings); if (uid) { - gboolean got; - - /* Don't care about errors because we'll create a new card on failure */ - got = e_book_client_get_contact_sync (*client, uid, contact, NULL, NULL); + /* Don't care about errors because + * we'll create a new card on failure. */ + e_book_client_get_contact_sync ( + book_client, uid, &contact, NULL, NULL); g_free (uid); - if (got) + + if (contact != NULL) { + *out_client = book_client; + *out_contact = contact; return TRUE; + } } uid = NULL; - *contact = make_me_card (); - if (!e_book_client_add_contact_sync (*client, *contact, &uid, NULL, &local_error)) { - g_object_unref (*client); - *client = NULL; - g_object_unref (*contact); - *contact = NULL; - g_propagate_error (error, local_error); + contact = make_me_card (); + success = e_book_client_add_contact_sync ( + book_client, contact, &uid, NULL, error); + if (!success) { + g_object_unref (book_client); + g_object_unref (contact); return FALSE; } - if (uid) { - e_contact_set (*contact, E_CONTACT_UID, uid); + if (uid != NULL) { + e_contact_set (contact, E_CONTACT_UID, uid); g_free (uid); } - e_book_client_set_self (*client, *contact, NULL); + e_book_client_set_self (book_client, contact, NULL); + + *out_client = book_client; + *out_contact = contact; return TRUE; } @@ -1092,6 +1313,27 @@ e_book_client_is_self (EContact *contact) return is_self; } +/* Helper for e_book_client_add_contact() */ +static void +book_client_add_contact_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; + + async_context = g_simple_async_result_get_op_res_gpointer (simple); + + e_book_client_add_contact_sync ( + E_BOOK_CLIENT (source_object), + async_context->contact, + &async_context->uid, + cancellable, &error); + + if (error != NULL) + g_simple_async_result_take_error (simple, error); +} + /** * e_book_client_add_contact: * @client: an #EBookClient @@ -1108,45 +1350,45 @@ e_book_client_is_self (EContact *contact) **/ void e_book_client_add_contact (EBookClient *client, - /* const */ EContact *contact, + EContact *contact, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data) { - gchar *vcard, *gdbus_vcard = NULL; - const gchar *strv[2]; + GSimpleAsyncResult *simple; + AsyncContext *async_context; - g_return_if_fail (contact != NULL); + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (E_IS_CONTACT (contact)); - vcard = e_vcard_to_string (E_VCARD (contact), EVC_FORMAT_VCARD_30); - strv[0] = e_util_ensure_gdbus_string (vcard, &gdbus_vcard); - strv[1] = NULL; + async_context = g_slice_new0 (AsyncContext); + async_context->contact = g_object_ref (contact); + + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_add_contact); + + g_simple_async_result_set_check_cancellable (simple, cancellable); - g_return_if_fail (strv[0] != NULL); + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); - e_client_proxy_call_strv ( - E_CLIENT (client), - strv, cancellable, callback, user_data, - e_book_client_add_contact, - e_gdbus_book_call_add_contacts, - NULL, NULL, NULL, - e_gdbus_book_call_add_contacts_finish, - NULL); + g_simple_async_result_run_in_thread ( + simple, book_client_add_contact_thread, + G_PRIORITY_DEFAULT, cancellable); - g_free (vcard); - g_free (gdbus_vcard); + g_object_unref (simple); } /** * e_book_client_add_contact_finish: * @client: an #EBookClient * @result: a #GAsyncResult - * @added_uid: (out): UID of a newly added contact; can be %NULL + * @out_added_uid: (out): UID of a newly added contact; can be %NULL * @error: (out): a #GError to set an error, if any * * Finishes previous call of e_book_client_add_contact() and - * sets @added_uid to a UID of a newly added contact. + * sets @out_added_uid to a UID of a newly added contact. * This string should be freed with g_free(). * * Note: This is not modifying original #EContact. @@ -1158,37 +1400,43 @@ e_book_client_add_contact (EBookClient *client, gboolean e_book_client_add_contact_finish (EBookClient *client, GAsyncResult *result, - gchar **added_uid, + gchar **out_added_uid, GError **error) { - gboolean res; - gchar **out_uids = NULL; + GSimpleAsyncResult *simple; + AsyncContext *async_context; - res = e_client_proxy_call_finish_strv ( - E_CLIENT (client), result, &out_uids, error, - e_book_client_add_contact); + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_add_contact), FALSE); - if (res && out_uids && added_uid) { - *added_uid = g_strdup (out_uids[0]); - } else { - if (added_uid) - *added_uid = NULL; + simple = G_SIMPLE_ASYNC_RESULT (result); + async_context = g_simple_async_result_get_op_res_gpointer (simple); + + if (g_simple_async_result_propagate_error (simple, error)) + return FALSE; + + g_return_val_if_fail (async_context->uid != NULL, FALSE); + + if (out_added_uid != NULL) { + *out_added_uid = async_context->uid; + async_context->uid = NULL; } - g_strfreev (out_uids); - return res; + return TRUE; } /** * e_book_client_add_contact_sync: * @client: an #EBookClient * @contact: an #EContact - * @added_uid: (out): UID of a newly added contact; can be %NULL + * @out_added_uid: (out): UID of a newly added contact; can be %NULL * @cancellable: a #GCancellable; can be %NULL * @error: (out): a #GError to set an error, if any * * Adds @contact to @client and - * sets @added_uid to a UID of a newly added contact. + * sets @out_added_uid to a UID of a newly added contact. * This string should be freed with g_free(). * * Note: This is not modifying original @contact, thus if it's needed, @@ -1200,44 +1448,60 @@ e_book_client_add_contact_finish (EBookClient *client, **/ gboolean e_book_client_add_contact_sync (EBookClient *client, - /* const */ EContact *contact, - gchar **added_uid, + EContact *contact, + gchar **out_added_uid, GCancellable *cancellable, GError **error) { - gboolean res; - gchar *vcard, *gdbus_vcard = NULL, **out_uids = NULL; - const gchar *strv[2]; + GSList link = { contact, NULL }; + GSList *uids = NULL; + gboolean success; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); + g_return_val_if_fail (E_IS_CONTACT (contact), FALSE); if (client->priv->dbus_proxy == NULL) { set_proxy_gone_error (error); return FALSE; } - vcard = e_vcard_to_string (E_VCARD (contact), EVC_FORMAT_VCARD_30); - strv[0] = e_util_ensure_gdbus_string (vcard, &gdbus_vcard); - strv[1] = NULL; + success = e_book_client_add_contacts_sync ( + client, &link, &uids, cancellable, error); - g_return_val_if_fail (strv[0] != NULL, FALSE); + /* Sanity check. */ + g_return_val_if_fail ( + (success && (uids != NULL)) || + (!success && (uids == NULL)), FALSE); - res = e_client_proxy_call_sync_strv__strv ( - E_CLIENT (client), strv, &out_uids, cancellable, error, - e_gdbus_book_call_add_contacts_sync); + if (uids != NULL) { + if (out_added_uid != NULL) + *out_added_uid = g_strdup (uids->data); - if (res && out_uids && added_uid) { - *added_uid = g_strdup (out_uids[0]); - } else { - if (added_uid) - *added_uid = NULL; + g_slist_free_full (uids, (GDestroyNotify) g_free); } - g_strfreev (out_uids); - g_free (vcard); - g_free (gdbus_vcard); + return success; +} + +/* Helper for e_book_client_add_contacts() */ +static void +book_client_add_contacts_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; + + async_context = g_simple_async_result_get_op_res_gpointer (simple); - return res; + e_book_client_add_contacts_sync ( + E_BOOK_CLIENT (source_object), + async_context->object_list, + &async_context->string_list, + cancellable, &error); + + if (error != NULL) + g_simple_async_result_take_error (simple, error); } /** @@ -1256,40 +1520,47 @@ e_book_client_add_contact_sync (EBookClient *client, **/ void e_book_client_add_contacts (EBookClient *client, - /* const */ GSList *contacts, + GSList *contacts, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data) { - gchar **array; + GSimpleAsyncResult *simple; + AsyncContext *async_context; + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (contacts != NULL); - array = contact_slist_to_utf8_vcard_array (contacts); + async_context = g_slice_new0 (AsyncContext); + async_context->object_list = g_slist_copy_deep ( + contacts, (GCopyFunc) g_object_ref, NULL); + + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_add_contacts); + + g_simple_async_result_set_check_cancellable (simple, cancellable); + + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); - e_client_proxy_call_strv ( - E_CLIENT (client), - (const gchar * const *) array, - cancellable, callback, user_data, - e_book_client_add_contacts, - e_gdbus_book_call_add_contacts, - NULL, NULL, NULL, - e_gdbus_book_call_add_contacts_finish, - NULL); + g_simple_async_result_run_in_thread ( + simple, book_client_add_contacts_thread, + G_PRIORITY_DEFAULT, cancellable); - g_strfreev (array); + g_object_unref (simple); } /** * e_book_client_add_contacts_finish: * @client: an #EBookClient * @result: a #GAsyncResult - * @added_uids: (out) (element-type utf8) (allow-none): UIDs of newly added - * contacts; can be %NULL + * @out_added_uids: (out) (element-type utf8) (allow-none): UIDs of + * newly added contacts; can be %NULL * @error: (out): a #GError to set an error, if any * * Finishes previous call of e_book_client_add_contacts() and - * sets @added_uids to the UIDs of newly added contacts if successful. + * sets @out_added_uids to the UIDs of newly added contacts if successful. * This #GSList should be freed with e_client_util_free_string_slist(). * * If any of the contacts cannot be inserted, all of the insertions will be @@ -1304,39 +1575,42 @@ e_book_client_add_contacts (EBookClient *client, gboolean e_book_client_add_contacts_finish (EBookClient *client, GAsyncResult *result, - GSList **added_uids, + GSList **out_added_uids, GError **error) { - gboolean res; - gchar **out_uids = NULL; + GSimpleAsyncResult *simple; + AsyncContext *async_context; - res = e_client_proxy_call_finish_strv ( - E_CLIENT (client), result, &out_uids, error, - e_book_client_add_contacts); + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_add_contacts), FALSE); - if (res && out_uids && added_uids) { - *added_uids = e_client_util_strv_to_slist ((const gchar * const*) out_uids); - } else { - if (added_uids) - *added_uids = NULL; - } + simple = G_SIMPLE_ASYNC_RESULT (result); + async_context = g_simple_async_result_get_op_res_gpointer (simple); + + if (g_simple_async_result_propagate_error (simple, error)) + return FALSE; - g_strfreev (out_uids); + if (out_added_uids != NULL) { + *out_added_uids = async_context->string_list; + async_context->string_list = NULL; + } - return res; + return TRUE; } /** * e_book_client_add_contacts_sync: * @client: an #EBookClient * @contacts: (element-type EContact): a #GSList of #EContact objects to add - * @added_uids: (out) (element-type utf8) (allow-none): UIDs of newly added - * contacts; can be %NULL + * @out_added_uids: (out) (element-type utf8) (allow-none): UIDs of newly + * added contacts; can be %NULL * @cancellable: a #GCancellable; can be %NULL * @error: (out): a #GError to set an error, if any * * Adds @contacts to @client and - * sets @added_uids to the UIDs of newly added contacts if successful. + * sets @out_added_uids to the UIDs of newly added contacts if successful. * This #GSList should be freed with e_client_util_free_string_slist(). * * If any of the contacts cannot be inserted, all of the insertions will be @@ -1351,40 +1625,91 @@ e_book_client_add_contacts_finish (EBookClient *client, **/ gboolean e_book_client_add_contacts_sync (EBookClient *client, - /* const */ GSList *contacts, - GSList **added_uids, + GSList *contacts, + GSList **out_added_uids, GCancellable *cancellable, GError **error) { - gboolean res; - gchar **array, **out_uids = NULL; + GSList *link; + gchar **strv; + gchar **uids = NULL; + gboolean success; + gint ii = 0; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); + g_return_val_if_fail (contacts != NULL, FALSE); if (client->priv->dbus_proxy == NULL) { set_proxy_gone_error (error); return FALSE; } - array = contact_slist_to_utf8_vcard_array (contacts); + /* Build a string array, ensuring each element is valid UTF-8. */ + strv = g_new0 (gchar *, g_slist_length (contacts) + 1); + for (link = contacts; link != NULL; link = g_slist_next (link)) { + EVCard *vcard; + gchar *string; + + vcard = E_VCARD (link->data); + string = e_vcard_to_string (vcard, EVC_FORMAT_VCARD_30); + strv[ii++] = e_util_utf8_make_valid (string); + g_free (string); + } + + success = e_dbus_address_book_call_create_contacts_sync ( + client->priv->dbus_proxy, + (const gchar * const *) strv, + &uids, cancellable, error); - res = e_client_proxy_call_sync_strv__strv ( - E_CLIENT (client), - (const gchar * const *) array, - &out_uids, cancellable, error, - e_gdbus_book_call_add_contacts_sync); + g_strfreev (strv); - if (res && out_uids && added_uids) { - *added_uids = e_client_util_strv_to_slist ((const gchar * const*) out_uids); - } else { - if (added_uids) - *added_uids = NULL; + /* Sanity check. */ + g_return_val_if_fail ( + (success && (uids != NULL)) || + (!success && (uids == NULL)), FALSE); + + if (!success) + return FALSE; + + /* XXX We should have passed the string array directly + * back to the caller instead of building a linked + * list. This is unnecessary work. */ + if (out_added_uids != NULL) { + GSList *tmp = NULL; + gint ii; + + /* Take ownership of the string array elements. */ + for (ii = 0; uids[ii] != NULL; ii++) { + tmp = g_slist_prepend (tmp, uids[ii]); + uids[ii] = NULL; + } + + *out_added_uids = g_slist_reverse (tmp); } - g_strfreev (out_uids); - g_strfreev (array); + g_strfreev (uids); - return res; + return TRUE; +} + +/* Helper for e_book_client_modify_contact() */ +static void +book_client_modify_contact_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; + + async_context = g_simple_async_result_get_op_res_gpointer (simple); + + e_book_client_modify_contact_sync ( + E_BOOK_CLIENT (source_object), + async_context->contact, + cancellable, &error); + + if (error != NULL) + g_simple_async_result_take_error (simple, error); } /** @@ -1403,33 +1728,34 @@ e_book_client_add_contacts_sync (EBookClient *client, **/ void e_book_client_modify_contact (EBookClient *client, - /* const */ EContact *contact, + EContact *contact, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data) { - gchar *vcard, *gdbus_vcard = NULL; - const gchar *strv[2]; + GSimpleAsyncResult *simple; + AsyncContext *async_context; - g_return_if_fail (contact != NULL); + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (E_IS_CONTACT (contact)); - vcard = e_vcard_to_string (E_VCARD (contact), EVC_FORMAT_VCARD_30); - strv[0] = e_util_ensure_gdbus_string (vcard, &gdbus_vcard); - strv[1] = NULL; + async_context = g_slice_new0 (AsyncContext); + async_context->contact = g_object_ref (contact); - g_return_if_fail (strv[0] != NULL); + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_modify_contact); - e_client_proxy_call_strv ( - E_CLIENT (client), - strv, cancellable, callback, user_data, - e_book_client_modify_contact, - e_gdbus_book_call_modify_contacts, - e_gdbus_book_call_modify_contacts_finish, - NULL, NULL, NULL, NULL); + g_simple_async_result_set_check_cancellable (simple, cancellable); - g_free (vcard); - g_free (gdbus_vcard); + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); + + g_simple_async_result_run_in_thread ( + simple, book_client_modify_contact_thread, + G_PRIORITY_DEFAULT, cancellable); + + g_object_unref (simple); } /** @@ -1449,9 +1775,17 @@ e_book_client_modify_contact_finish (EBookClient *client, GAsyncResult *result, GError **error) { - return e_client_proxy_call_finish_void ( - E_CLIENT (client), result, error, - e_book_client_modify_contact); + GSimpleAsyncResult *simple; + + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_modify_contact), FALSE); + + simple = G_SIMPLE_ASYNC_RESULT (result); + + /* Assume success unless a GError is set. */ + return !g_simple_async_result_propagate_error (simple, error); } /** @@ -1469,36 +1803,37 @@ e_book_client_modify_contact_finish (EBookClient *client, **/ gboolean e_book_client_modify_contact_sync (EBookClient *client, - /* const */ EContact *contact, + EContact *contact, GCancellable *cancellable, GError **error) { - gboolean res; - gchar *vcard, *gdbus_vcard = NULL; - const gchar *strv[2]; + GSList link = { contact, NULL }; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); + g_return_val_if_fail (E_IS_CONTACT (contact), FALSE); - if (client->priv->dbus_proxy == NULL) { - set_proxy_gone_error (error); - return FALSE; - } - - vcard = e_vcard_to_string (E_VCARD (contact), EVC_FORMAT_VCARD_30); - strv[0] = e_util_ensure_gdbus_string (vcard, &gdbus_vcard); - strv[1] = NULL; + return e_book_client_modify_contacts_sync ( + client, &link, cancellable, error); +} - g_return_val_if_fail (strv[0] != NULL, FALSE); +/* Helper for e_book_client_modify_contacts() */ +static void +book_client_modify_contacts_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; - res = e_client_proxy_call_sync_strv__void ( - E_CLIENT (client), - strv, cancellable, error, - e_gdbus_book_call_modify_contacts_sync); + async_context = g_simple_async_result_get_op_res_gpointer (simple); - g_free (vcard); - g_free (gdbus_vcard); + e_book_client_modify_contacts_sync ( + E_BOOK_CLIENT (source_object), + async_context->object_list, + cancellable, &error); - return res; + if (error != NULL) + g_simple_async_result_take_error (simple, error); } /** @@ -1517,27 +1852,35 @@ e_book_client_modify_contact_sync (EBookClient *client, **/ void e_book_client_modify_contacts (EBookClient *client, - /* const */ GSList *contacts, + GSList *contacts, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data) { - gchar **array; + GSimpleAsyncResult *simple; + AsyncContext *async_context; + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (contacts != NULL); - array = contact_slist_to_utf8_vcard_array (contacts); + async_context = g_slice_new0 (AsyncContext); + async_context->object_list = g_slist_copy_deep ( + contacts, (GCopyFunc) g_object_ref, NULL); + + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_modify_contacts); + + g_simple_async_result_set_check_cancellable (simple, cancellable); - e_client_proxy_call_strv ( - E_CLIENT (client), - (const gchar * const *) array, - cancellable, callback, user_data, - e_book_client_modify_contacts, - e_gdbus_book_call_modify_contacts, - e_gdbus_book_call_modify_contacts_finish, - NULL, NULL, NULL, NULL); + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); - g_strfreev (array); + g_simple_async_result_run_in_thread ( + simple, book_client_modify_contacts_thread, + G_PRIORITY_DEFAULT, cancellable); + + g_object_unref (simple); } /** @@ -1557,9 +1900,17 @@ e_book_client_modify_contacts_finish (EBookClient *client, GAsyncResult *result, GError **error) { - return e_client_proxy_call_finish_void ( - E_CLIENT (client), result, error, - e_book_client_modify_contacts); + GSimpleAsyncResult *simple; + + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_modify_contacts), FALSE); + + simple = G_SIMPLE_ASYNC_RESULT (result); + + /* Assume success unless a GError is set. */ + return !g_simple_async_result_propagate_error (simple, error); } /** @@ -1577,12 +1928,14 @@ e_book_client_modify_contacts_finish (EBookClient *client, **/ gboolean e_book_client_modify_contacts_sync (EBookClient *client, - /* const */ GSList *contacts, + GSList *contacts, GCancellable *cancellable, GError **error) { - gboolean res; - gchar **array; + GSList *link; + gchar **strv; + gboolean success; + gint ii = 0; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); g_return_val_if_fail (contacts != NULL, FALSE); @@ -1592,17 +1945,46 @@ e_book_client_modify_contacts_sync (EBookClient *client, return FALSE; } - array = contact_slist_to_utf8_vcard_array (contacts); + /* Build a string array, ensuring each element is valid UTF-8. */ + strv = g_new0 (gchar *, g_slist_length (contacts) + 1); + for (link = contacts; link != NULL; link = g_slist_next (link)) { + EVCard *vcard; + gchar *string; + + vcard = E_VCARD (link->data); + string = e_vcard_to_string (vcard, EVC_FORMAT_VCARD_30); + strv[ii++] = e_util_utf8_make_valid (string); + g_free (string); + } + + success = e_dbus_address_book_call_modify_contacts_sync ( + client->priv->dbus_proxy, + (const gchar * const *) strv, + cancellable, error); + + g_strfreev (strv); + + return success; +} + +/* Helper for e_book_client_remove_contact() */ +static void +book_client_remove_contact_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; - res = e_client_proxy_call_sync_strv__void ( - E_CLIENT (client), - (const gchar * const *) array, - cancellable, error, - e_gdbus_book_call_modify_contacts_sync); + async_context = g_simple_async_result_get_op_res_gpointer (simple); - g_strfreev (array); + e_book_client_remove_contact_sync ( + E_BOOK_CLIENT (source_object), + async_context->contact, + cancellable, &error); - return res; + if (error != NULL) + g_simple_async_result_take_error (simple, error); } /** @@ -1626,31 +2008,29 @@ e_book_client_remove_contact (EBookClient *client, GAsyncReadyCallback callback, gpointer user_data) { - const gchar *uid, *safe_uid; - const gchar *strv[2]; - gchar *gdbus_uid = NULL; + GSimpleAsyncResult *simple; + AsyncContext *async_context; - g_return_if_fail (contact != NULL); + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (E_IS_CONTACT (contact)); - uid = e_contact_get_const ( E_CONTACT (contact), E_CONTACT_UID); - g_return_if_fail (uid != NULL); + async_context = g_slice_new0 (AsyncContext); + async_context->contact = g_object_ref (contact); + + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_remove_contact); - safe_uid = e_util_ensure_gdbus_string (uid, &gdbus_uid); - g_return_if_fail (safe_uid != NULL); + g_simple_async_result_set_check_cancellable (simple, cancellable); - strv[0] = safe_uid; - strv[1] = NULL; + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); - e_client_proxy_call_strv ( - E_CLIENT (client), - strv, cancellable, callback, user_data, - e_book_client_remove_contact, - e_gdbus_book_call_remove_contacts, - e_gdbus_book_call_remove_contacts_finish, - NULL, NULL, NULL, NULL); + g_simple_async_result_run_in_thread ( + simple, book_client_remove_contact_thread, + G_PRIORITY_DEFAULT, cancellable); - g_free (gdbus_uid); + g_object_unref (simple); } /** @@ -1670,9 +2050,17 @@ e_book_client_remove_contact_finish (EBookClient *client, GAsyncResult *result, GError **error) { - return e_client_proxy_call_finish_void ( - E_CLIENT (client), result, error, - e_book_client_remove_contact); + GSimpleAsyncResult *simple; + + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_remove_contact), FALSE); + + simple = G_SIMPLE_ASYNC_RESULT (result); + + /* Assume success unless a GError is set. */ + return !g_simple_async_result_propagate_error (simple, error); } /** @@ -1690,40 +2078,40 @@ e_book_client_remove_contact_finish (EBookClient *client, **/ gboolean e_book_client_remove_contact_sync (EBookClient *client, - /* const */ EContact *contact, + EContact *contact, GCancellable *cancellable, GError **error) { - gboolean res; - const gchar *strv[2]; - const gchar *uid, *safe_uid; - gchar *gdbus_uid = NULL; + const gchar *uid; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); g_return_val_if_fail (E_IS_CONTACT (contact), FALSE); - if (client->priv->dbus_proxy == NULL) { - set_proxy_gone_error (error); - return FALSE; - } - - uid = e_contact_get_const (E_CONTACT (contact), E_CONTACT_UID); + uid = e_contact_get_const (contact, E_CONTACT_UID); g_return_val_if_fail (uid != NULL, FALSE); - safe_uid = e_util_ensure_gdbus_string (uid, &gdbus_uid); - g_return_val_if_fail (safe_uid != NULL, FALSE); + return e_book_client_remove_contact_by_uid_sync ( + client, uid, cancellable, error); +} - strv[0] = safe_uid; - strv[1] = NULL; +/* Helper for e_book_client_remove_contact_by_uid() */ +static void +book_client_remove_contact_by_uid_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; - res = e_client_proxy_call_sync_strv__void ( - E_CLIENT (client), - strv, cancellable, error, - e_gdbus_book_call_remove_contacts_sync); + async_context = g_simple_async_result_get_op_res_gpointer (simple); - g_free (gdbus_uid); + e_book_client_remove_contact_by_uid_sync ( + E_BOOK_CLIENT (source_object), + async_context->uid, + cancellable, &error); - return res; + if (error != NULL) + g_simple_async_result_take_error (simple, error); } /** @@ -1747,27 +2135,29 @@ e_book_client_remove_contact_by_uid (EBookClient *client, GAsyncReadyCallback callback, gpointer user_data) { - const gchar *safe_uid; - gchar *gdbus_uid = NULL; - const gchar *strv[2]; + GSimpleAsyncResult *simple; + AsyncContext *async_context; + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (uid != NULL); - safe_uid = e_util_ensure_gdbus_string (uid, &gdbus_uid); - g_return_if_fail (safe_uid != NULL); + async_context = g_slice_new0 (AsyncContext); + async_context->uid = g_strdup (uid); - strv[0] = safe_uid; - strv[1] = NULL; + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_remove_contact_by_uid); + + g_simple_async_result_set_check_cancellable (simple, cancellable); - e_client_proxy_call_strv ( - E_CLIENT (client), - strv, cancellable, callback, user_data, - e_book_client_remove_contact_by_uid, - e_gdbus_book_call_remove_contacts, - e_gdbus_book_call_remove_contacts_finish, - NULL, NULL, NULL, NULL); + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); - g_free (gdbus_uid); + g_simple_async_result_run_in_thread ( + simple, book_client_remove_contact_by_uid_thread, + G_PRIORITY_DEFAULT, cancellable); + + g_object_unref (simple); } /** @@ -1787,9 +2177,17 @@ e_book_client_remove_contact_by_uid_finish (EBookClient *client, GAsyncResult *result, GError **error) { - return e_client_proxy_call_finish_void ( - E_CLIENT (client), result, error, - e_book_client_remove_contact_by_uid); + GSimpleAsyncResult *simple; + + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_remove_contact_by_uid), FALSE); + + simple = G_SIMPLE_ASYNC_RESULT (result); + + /* Assume success unless a GError is set. */ + return !g_simple_async_result_propagate_error (simple, error); } /** @@ -1811,32 +2209,33 @@ e_book_client_remove_contact_by_uid_sync (EBookClient *client, GCancellable *cancellable, GError **error) { - gboolean res; - const gchar *safe_uid; - gchar *gdbus_uid = NULL; - const gchar *strv[2]; + GSList link = { (gpointer) uid, NULL }; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); g_return_val_if_fail (uid != NULL, FALSE); - if (client->priv->dbus_proxy == NULL) { - set_proxy_gone_error (error); - return FALSE; - } - - safe_uid = e_util_ensure_gdbus_string (uid, &gdbus_uid); - g_return_val_if_fail (safe_uid != NULL, FALSE); + return e_book_client_remove_contacts_sync ( + client, &link, cancellable, error); +} - strv[0] = safe_uid; - strv[1] = NULL; +/* Helper for e_book_client_remove_contacts() */ +static void +book_client_remove_contacts_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; - res = e_client_proxy_call_sync_strv__void ( - E_CLIENT (client), strv, cancellable, error, - e_gdbus_book_call_remove_contacts_sync); + async_context = g_simple_async_result_get_op_res_gpointer (simple); - g_free (gdbus_uid); + e_book_client_remove_contacts_sync ( + E_BOOK_CLIENT (source_object), + async_context->string_list, + cancellable, &error); - return res; + if (error != NULL) + g_simple_async_result_take_error (simple, error); } /** @@ -1863,23 +2262,30 @@ e_book_client_remove_contacts (EBookClient *client, GAsyncReadyCallback callback, gpointer user_data) { - gchar **strv; + GSimpleAsyncResult *simple; + AsyncContext *async_context; + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (uids != NULL); - strv = e_client_util_slist_to_strv (uids); - g_return_if_fail (strv != NULL); + async_context = g_slice_new0 (AsyncContext); + async_context->string_list = g_slist_copy_deep ( + (GSList *) uids, (GCopyFunc) g_strdup, NULL); - e_client_proxy_call_strv ( - E_CLIENT (client), - (const gchar * const *) strv, - cancellable, callback, user_data, - e_book_client_remove_contacts, - e_gdbus_book_call_remove_contacts, - e_gdbus_book_call_remove_contacts_finish, - NULL, NULL, NULL, NULL); + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_remove_contacts); - g_strfreev (strv); + g_simple_async_result_set_check_cancellable (simple, cancellable); + + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); + + g_simple_async_result_run_in_thread ( + simple, book_client_remove_contacts_thread, + G_PRIORITY_DEFAULT, cancellable); + + g_object_unref (simple); } /** @@ -1899,9 +2305,17 @@ e_book_client_remove_contacts_finish (EBookClient *client, GAsyncResult *result, GError **error) { - return e_client_proxy_call_finish_void ( - E_CLIENT (client), result, error, - e_book_client_remove_contacts); + GSimpleAsyncResult *simple; + + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_remove_contacts), FALSE); + + simple = G_SIMPLE_ASYNC_RESULT (result); + + /* Assume success unless a GError is set. */ + return !g_simple_async_result_propagate_error (simple, error); } /** @@ -1926,8 +2340,9 @@ e_book_client_remove_contacts_sync (EBookClient *client, GCancellable *cancellable, GError **error) { - gboolean res; gchar **strv; + gboolean success; + gint ii = 0; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); g_return_val_if_fail (uids != NULL, FALSE); @@ -1937,17 +2352,41 @@ e_book_client_remove_contacts_sync (EBookClient *client, return FALSE; } - strv = e_client_util_slist_to_strv (uids); - g_return_val_if_fail (strv != NULL, FALSE); + strv = g_new0 (gchar *, g_slist_length ((GSList *) uids) + 1); + while (uids != NULL) { + strv[ii++] = e_util_utf8_make_valid (uids->data); + uids = g_slist_next (uids); + } - res = e_client_proxy_call_sync_strv__void ( - E_CLIENT (client), (const gchar * const *) strv, - cancellable, error, - e_gdbus_book_call_remove_contacts_sync); + success = e_dbus_address_book_call_remove_contacts_sync ( + client->priv->dbus_proxy, + (const gchar * const *) strv, + cancellable, error); g_strfreev (strv); - return res; + return success; +} + +/* Helper for e_book_client_get_contact() */ +static void +book_client_get_contact_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; + + async_context = g_simple_async_result_get_op_res_gpointer (simple); + + e_book_client_get_contact_sync ( + E_BOOK_CLIENT (source_object), + async_context->uid, + &async_context->contact, + cancellable, &error); + + if (error != NULL) + g_simple_async_result_take_error (simple, error); } /** @@ -1971,35 +2410,40 @@ e_book_client_get_contact (EBookClient *client, GAsyncReadyCallback callback, gpointer user_data) { - const gchar *safe_uid; - gchar *gdbus_uid = NULL; + GSimpleAsyncResult *simple; + AsyncContext *async_context; + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (uid != NULL); - safe_uid = e_util_ensure_gdbus_string (uid, &gdbus_uid); - g_return_if_fail (safe_uid != NULL); + async_context = g_slice_new0 (AsyncContext); + async_context->uid = g_strdup (uid); - e_client_proxy_call_string ( - E_CLIENT (client), - safe_uid, cancellable, callback, user_data, - e_book_client_get_contact, - e_gdbus_book_call_get_contact, - NULL, NULL, - e_gdbus_book_call_get_contact_finish, - NULL, NULL); + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_get_contact); + + g_simple_async_result_set_check_cancellable (simple, cancellable); + + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); + + g_simple_async_result_run_in_thread ( + simple, book_client_get_contact_thread, + G_PRIORITY_DEFAULT, cancellable); - g_free (gdbus_uid); + g_object_unref (simple); } /** * e_book_client_get_contact_finish: * @client: an #EBookClient * @result: a #GAsyncResult - * @contact: (out): an #EContact for previously given uid + * @out_contact: (out): an #EContact for previously given uid * @error: (out): a #GError to set an error, if any * * Finishes previous call of e_book_client_get_contact(). - * If successful, then the @contact is set to newly allocated + * If successful, then the @out_contact is set to newly allocated * #EContact, which should be freed with g_object_unref(). * * Returns: %TRUE if successful, %FALSE otherwise. @@ -2009,39 +2453,41 @@ e_book_client_get_contact (EBookClient *client, gboolean e_book_client_get_contact_finish (EBookClient *client, GAsyncResult *result, - EContact **contact, + EContact **out_contact, GError **error) { - gboolean res; - gchar *vcard = NULL; + GSimpleAsyncResult *simple; + AsyncContext *async_context; - g_return_val_if_fail (contact != NULL, FALSE); + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_get_contact), FALSE); - res = e_client_proxy_call_finish_string ( - E_CLIENT (client), - result, &vcard, error, - e_book_client_get_contact); + simple = G_SIMPLE_ASYNC_RESULT (result); + async_context = g_simple_async_result_get_op_res_gpointer (simple); + + if (g_simple_async_result_propagate_error (simple, error)) + return FALSE; - if (vcard && res) - *contact = e_contact_new_from_vcard (vcard); - else - *contact = NULL; + g_return_val_if_fail (async_context->contact != NULL, FALSE); - g_free (vcard); + if (out_contact != NULL) + *out_contact = g_object_ref (async_context->contact); - return res; + return TRUE; } /** * e_book_client_get_contact_sync: * @client: an #EBookClient * @uid: a unique string ID specifying the contact - * @contact: (out): an #EContact for given @uid + * @out_contact: (out): an #EContact for given @uid * @cancellable: a #GCancellable; can be %NULL * @error: (out): a #GError to set an error, if any * * Receive #EContact from the @client for the gived @uid. - * If successful, then the @contact is set to newly allocated + * If successful, then the @out_contact is set to newly allocated * #EContact, which should be freed with g_object_unref(). * * Returns: %TRUE if successful, %FALSE otherwise. @@ -2051,40 +2497,64 @@ e_book_client_get_contact_finish (EBookClient *client, gboolean e_book_client_get_contact_sync (EBookClient *client, const gchar *uid, - EContact **contact, + EContact **out_contact, GCancellable *cancellable, GError **error) { - gboolean res; - const gchar *safe_uid; - gchar *vcard = NULL, *gdbus_uid = NULL; + gchar *utf8_uid; + gchar *vcard = NULL; + gboolean success; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); g_return_val_if_fail (uid != NULL, FALSE); - g_return_val_if_fail (contact != NULL, FALSE); + g_return_val_if_fail (out_contact != NULL, FALSE); if (client->priv->dbus_proxy == NULL) { set_proxy_gone_error (error); return FALSE; } - safe_uid = e_util_ensure_gdbus_string (uid, &gdbus_uid); - g_return_val_if_fail (safe_uid != NULL, FALSE); + utf8_uid = e_util_utf8_make_valid (uid); + + success = e_dbus_address_book_call_get_contact_sync ( + client->priv->dbus_proxy, + utf8_uid, &vcard, cancellable, error); + + /* Sanity check. */ + g_return_val_if_fail ( + (success && (vcard != NULL)) || + (!success && (vcard == NULL)), FALSE); + + if (vcard != NULL) { + *out_contact = + e_contact_new_from_vcard_with_uid (vcard, utf8_uid); + g_free (vcard); + } + + g_free (utf8_uid); + + return success; +} - res = e_client_proxy_call_sync_string__string ( - E_CLIENT (client), - safe_uid, &vcard, cancellable, error, - e_gdbus_book_call_get_contact_sync); +/* Helper for e_book_client_get_contacts() */ +static void +book_client_get_contacts_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; - if (vcard && res) - *contact = e_contact_new_from_vcard_with_uid (vcard, safe_uid); - else - *contact = NULL; + async_context = g_simple_async_result_get_op_res_gpointer (simple); - g_free (gdbus_uid); - g_free (vcard); + e_book_client_get_contacts_sync ( + E_BOOK_CLIENT (source_object), + async_context->sexp, + &async_context->object_list, + cancellable, &error); - return res; + if (error != NULL) + g_simple_async_result_take_error (simple, error); } /** @@ -2111,33 +2581,42 @@ e_book_client_get_contacts (EBookClient *client, GAsyncReadyCallback callback, gpointer user_data) { - gchar *gdbus_sexp = NULL; + GSimpleAsyncResult *simple; + AsyncContext *async_context; + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (sexp != NULL); - e_client_proxy_call_string ( - E_CLIENT (client), - e_util_ensure_gdbus_string (sexp, &gdbus_sexp), - cancellable, callback, user_data, - e_book_client_get_contacts, - e_gdbus_book_call_get_contact_list, - NULL, NULL, NULL, - e_gdbus_book_call_get_contact_list_finish, - NULL); + async_context = g_slice_new0 (AsyncContext); + async_context->sexp = g_strdup (sexp); + + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_get_contacts); + + g_simple_async_result_set_check_cancellable (simple, cancellable); + + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); - g_free (gdbus_sexp); + g_simple_async_result_run_in_thread ( + simple, book_client_get_contacts_thread, + G_PRIORITY_DEFAULT, cancellable); + + g_object_unref (simple); } /** * e_book_client_get_contacts_finish: * @client: an #EBookClient * @result: a #GAsyncResult - * @contacts: (element-type EContact) (out): a #GSList of matched #EContact-s + * @out_contacts: (element-type EContact) (out): a #GSList of matched + * #EContact-s * @error: (out): a #GError to set an error, if any * * Finishes previous call of e_book_client_get_contacts(). - * If successful, then the @contacts is set to newly allocated list of #EContact-s, - * which should be freed with e_client_util_free_object_slist(). + * If successful, then the @out_contacts is set to newly allocated list of + * #EContact-s, which should be freed with e_client_util_free_object_slist(). * * Returns: %TRUE if successful, %FALSE otherwise. * @@ -2146,47 +2625,42 @@ e_book_client_get_contacts (EBookClient *client, gboolean e_book_client_get_contacts_finish (EBookClient *client, GAsyncResult *result, - GSList **contacts, + GSList **out_contacts, GError **error) { - gboolean res; - gchar **vcards = NULL; - - g_return_val_if_fail (contacts != NULL, FALSE); + GSimpleAsyncResult *simple; + AsyncContext *async_context; - res = e_client_proxy_call_finish_strv ( - E_CLIENT (client), - result, &vcards, error, - e_book_client_get_contacts); + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_get_contacts), FALSE); - if (vcards && res) { - gint ii; - GSList *slist = NULL; + simple = G_SIMPLE_ASYNC_RESULT (result); + async_context = g_simple_async_result_get_op_res_gpointer (simple); - for (ii = 0; vcards[ii]; ii++) { - slist = g_slist_prepend (slist, e_contact_new_from_vcard (vcards[ii])); - } + if (g_simple_async_result_propagate_error (simple, error)) + return FALSE; - *contacts = g_slist_reverse (slist); - } else { - *contacts = NULL; + if (out_contacts != NULL) { + *out_contacts = async_context->object_list; + async_context->object_list = NULL; } - g_strfreev (vcards); - - return res; + return TRUE; } /** * e_book_client_get_contacts_sync: * @client: an #EBookClient * @sexp: an S-expression representing the query - * @contacts: (element-type EContact) (out): a #GSList of matched #EContact-s + * @out_contacts: (element-type EContact) (out): a #GSList of matched + * #EContact-s * @cancellable: a #GCancellable; can be %NULL * @error: (out): a #GError to set an error, if any * * Query @client with @sexp, receiving a list of contacts which matched. - * If successful, then the @contacts is set to newly allocated #GSList of + * If successful, then the @out_contacts is set to newly allocated #GSList of * #EContact-s, which should be freed with e_client_util_free_object_slist(). * * Note: @sexp can be obtained through #EBookQuery, by converting it @@ -2199,46 +2673,73 @@ e_book_client_get_contacts_finish (EBookClient *client, gboolean e_book_client_get_contacts_sync (EBookClient *client, const gchar *sexp, - GSList **contacts, + GSList **out_contacts, GCancellable *cancellable, GError **error) { - gboolean res; - gchar *gdbus_sexp = NULL; + gchar *utf8_sexp; gchar **vcards = NULL; + gboolean success; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); g_return_val_if_fail (sexp != NULL, FALSE); - g_return_val_if_fail (contacts != NULL, FALSE); + g_return_val_if_fail (out_contacts != NULL, FALSE); if (client->priv->dbus_proxy == NULL) { set_proxy_gone_error (error); return FALSE; } - res = e_client_proxy_call_sync_string__strv ( - E_CLIENT (client), - e_util_ensure_gdbus_string (sexp, &gdbus_sexp), - &vcards, cancellable, error, - e_gdbus_book_call_get_contact_list_sync); + utf8_sexp = e_util_utf8_make_valid (sexp); + + success = e_dbus_address_book_call_get_contact_list_sync ( + client->priv->dbus_proxy, + utf8_sexp, &vcards, cancellable, error); + + g_free (utf8_sexp); - if (vcards && res) { + /* Sanity check. */ + g_return_val_if_fail ( + (success && (vcards != NULL)) || + (!success && (vcards == NULL)), FALSE); + + if (vcards != NULL) { + EContact *contact; + GSList *tmp = NULL; gint ii; - GSList *slist = NULL; - for (ii = 0; vcards[ii]; ii++) { - slist = g_slist_prepend (slist, e_contact_new_from_vcard (vcards[ii])); + for (ii = 0; vcards[ii] != NULL; ii++) { + contact = e_contact_new_from_vcard (vcards[ii]); + tmp = g_slist_prepend (tmp, contact); } - *contacts = g_slist_reverse (slist); - } else { - *contacts = NULL; + *out_contacts = g_slist_reverse (tmp); + + g_strfreev (vcards); } - g_free (gdbus_sexp); - g_strfreev (vcards); + return success; +} + +/* Helper for e_book_client_get_contacts_uids() */ +static void +book_client_get_contacts_uids_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; + + async_context = g_simple_async_result_get_op_res_gpointer (simple); + + e_book_client_get_contacts_uids_sync ( + E_BOOK_CLIENT (source_object), + async_context->sexp, + &async_context->string_list, + cancellable, &error); - return res; + if (error != NULL) + g_simple_async_result_take_error (simple, error); } /** @@ -2265,32 +2766,41 @@ e_book_client_get_contacts_uids (EBookClient *client, GAsyncReadyCallback callback, gpointer user_data) { - gchar *gdbus_sexp = NULL; + GSimpleAsyncResult *simple; + AsyncContext *async_context; + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (sexp != NULL); - e_client_proxy_call_string ( - E_CLIENT (client), - e_util_ensure_gdbus_string (sexp, &gdbus_sexp), - cancellable, callback, user_data, - e_book_client_get_contacts_uids, - e_gdbus_book_call_get_contact_list_uids, - NULL, NULL, NULL, - e_gdbus_book_call_get_contact_list_uids_finish, - NULL); + async_context = g_slice_new0 (AsyncContext); + async_context->sexp = g_strdup (sexp); + + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_get_contacts_uids); + + g_simple_async_result_set_check_cancellable (simple, cancellable); + + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); - g_free (gdbus_sexp); + g_simple_async_result_run_in_thread ( + simple, book_client_get_contacts_uids_thread, + G_PRIORITY_DEFAULT, cancellable); + + g_object_unref (simple); } /** * e_book_client_get_contacts_uids_finish: * @client: an #EBookClient * @result: a #GAsyncResult - * @contacts_uids: (element-type utf8) (out): a #GSList of matched contacts UIDs stored as strings + * @out_contact_uids: (element-type utf8) (out): a #GSList of matched + * contact UIDs stored as strings * @error: (out): a #GError to set an error, if any * * Finishes previous call of e_book_client_get_contacts_uids(). - * If successful, then the @contacts_uids is set to newly allocated list + * If successful, then the @out_contact_uids is set to newly allocated list * of UID strings, which should be freed with e_client_util_free_string_slist(). * * Returns: %TRUE if successful, %FALSE otherwise. @@ -2300,47 +2810,42 @@ e_book_client_get_contacts_uids (EBookClient *client, gboolean e_book_client_get_contacts_uids_finish (EBookClient *client, GAsyncResult *result, - GSList **contacts_uids, + GSList **out_contact_uids, GError **error) { - gboolean res; - gchar **uids = NULL; - - g_return_val_if_fail (contacts_uids != NULL, FALSE); + GSimpleAsyncResult *simple; + AsyncContext *async_context; - res = e_client_proxy_call_finish_strv ( - E_CLIENT (client), - result, &uids, error, - e_book_client_get_contacts_uids); + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_get_contacts_uids), FALSE); - if (uids && res) { - gint ii; - GSList *slist = NULL; + simple = G_SIMPLE_ASYNC_RESULT (result); + async_context = g_simple_async_result_get_op_res_gpointer (simple); - for (ii = 0; uids[ii]; ii++) { - slist = g_slist_prepend (slist, g_strdup (uids[ii])); - } + if (g_simple_async_result_propagate_error (simple, error)) + return FALSE; - *contacts_uids = g_slist_reverse (slist); - } else { - *contacts_uids = NULL; + if (out_contact_uids != NULL) { + *out_contact_uids = async_context->string_list; + async_context->string_list = NULL; } - g_strfreev (uids); - - return res; + return TRUE; } /** * e_book_client_get_contacts_uids_sync: * @client: an #EBookClient * @sexp: an S-expression representing the query - * @contacts_uids: (element-type utf8) (out): a #GSList of matched contacts UIDs stored as strings + * @out_contact_uids: (element-type utf8) (out): a #GSList of matched + * contacts UIDs stored as strings * @cancellable: a #GCancellable; can be %NULL * @error: (out): a #GError to set an error, if any * * Query @client with @sexp, receiving a list of contacts UIDs which matched. - * If successful, then the @contacts_uids is set to newly allocated list + * If successful, then the @out_contact_uids is set to newly allocated list * of UID strings, which should be freed with e_client_util_free_string_slist(). * * Note: @sexp can be obtained through #EBookQuery, by converting it @@ -2353,46 +2858,76 @@ e_book_client_get_contacts_uids_finish (EBookClient *client, gboolean e_book_client_get_contacts_uids_sync (EBookClient *client, const gchar *sexp, - GSList **contacts_uids, + GSList **out_contact_uids, GCancellable *cancellable, GError **error) { - gboolean res; - gchar *gdbus_sexp = NULL; + gchar *utf8_sexp; gchar **uids = NULL; + gboolean success; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); g_return_val_if_fail (sexp != NULL, FALSE); - g_return_val_if_fail (contacts_uids != NULL, FALSE); + g_return_val_if_fail (out_contact_uids != NULL, FALSE); if (client->priv->dbus_proxy == NULL) { set_proxy_gone_error (error); return FALSE; } - res = e_client_proxy_call_sync_string__strv ( - E_CLIENT (client), - e_util_ensure_gdbus_string (sexp, &gdbus_sexp), - &uids, cancellable, error, - e_gdbus_book_call_get_contact_list_uids_sync); + utf8_sexp = e_util_utf8_make_valid (sexp); - if (uids && res) { + success = e_dbus_address_book_call_get_contact_list_uids_sync ( + client->priv->dbus_proxy, + utf8_sexp, &uids, cancellable, error); + + g_free (utf8_sexp); + + /* Sanity check. */ + g_return_val_if_fail ( + (success && (uids != NULL)) || + (!success && (uids == NULL)), FALSE); + + /* XXX We should have passed the string array directly + * back to the caller instead of building a linked + * list. This is unnecessary work. */ + if (uids != NULL) { + GSList *tmp = NULL; gint ii; - GSList *slist = NULL; - for (ii = 0; uids[ii]; ii++) { - slist = g_slist_prepend (slist, g_strdup (uids[ii])); + /* Take ownership of the string array elements. */ + for (ii = 0; uids[ii] != NULL; ii++) { + tmp = g_slist_prepend (tmp, uids[ii]); + uids[ii] = NULL; } - *contacts_uids = g_slist_reverse (slist); - } else { - *contacts_uids = NULL; + *out_contact_uids = g_slist_reverse (tmp); + + g_free (uids); } - g_free (gdbus_sexp); - g_strfreev (uids); + return success; +} + +/* Helper for e_book_client_get_view() */ +static void +book_client_get_view_thread (GSimpleAsyncResult *simple, + GObject *source_object, + GCancellable *cancellable) +{ + AsyncContext *async_context; + GError *error = NULL; - return res; + async_context = g_simple_async_result_get_op_res_gpointer (simple); + + e_book_client_get_view_sync ( + E_BOOK_CLIENT (source_object), + async_context->sexp, + &async_context->client_view, + cancellable, &error); + + if (error != NULL) + g_simple_async_result_take_error (simple, error); } /** @@ -2419,73 +2954,41 @@ e_book_client_get_view (EBookClient *client, GAsyncReadyCallback callback, gpointer user_data) { - gchar *gdbus_sexp = NULL; + GSimpleAsyncResult *simple; + AsyncContext *async_context; + g_return_if_fail (E_IS_BOOK_CLIENT (client)); g_return_if_fail (sexp != NULL); - e_client_proxy_call_string ( - E_CLIENT (client), - e_util_ensure_gdbus_string (sexp, &gdbus_sexp), - cancellable, callback, user_data, - e_book_client_get_view, - e_gdbus_book_call_get_view, - NULL, NULL, - e_gdbus_book_call_get_view_finish, NULL, NULL); - - g_free (gdbus_sexp); -} - -static gboolean -complete_get_view (EBookClient *client, - gboolean res, - gchar *view_path, - EBookClientView **view, - GError **error) -{ - g_return_val_if_fail (view != NULL, FALSE); - - if (view_path && res && book_factory) { - GDBusConnection *connection; - GError *local_error = NULL; - - connection = g_dbus_proxy_get_connection ( - G_DBUS_PROXY (book_factory)); + async_context = g_slice_new0 (AsyncContext); + async_context->sexp = g_strdup (sexp); - *view = g_initable_new ( - E_TYPE_BOOK_CLIENT_VIEW, - NULL, &local_error, - "client", client, - "connection", connection, - "object-path", view_path, - NULL); + simple = g_simple_async_result_new ( + G_OBJECT (client), callback, user_data, + e_book_client_get_view); - if (local_error != NULL) { - unwrap_dbus_error (local_error, error); - res = FALSE; - } - } else { - *view = NULL; - res = FALSE; - } + g_simple_async_result_set_check_cancellable (simple, cancellable); - if (!*view && error && !*error) - g_set_error_literal (error, E_CLIENT_ERROR, E_CLIENT_ERROR_DBUS_ERROR, _("Cannot get connection to view")); + g_simple_async_result_set_op_res_gpointer ( + simple, async_context, (GDestroyNotify) async_context_free); - g_free (view_path); + g_simple_async_result_run_in_thread ( + simple, book_client_get_view_thread, + G_PRIORITY_DEFAULT, cancellable); - return res; + g_object_unref (simple); } /** * e_book_client_get_view_finish: * @client: an #EBookClient * @result: a #GAsyncResult - * @view: (out): an #EBookClientView + * @out_view: (out): an #EBookClientView * @error: (out): a #GError to set an error, if any * * Finishes previous call of e_book_client_get_view(). - * If successful, then the @view is set to newly allocated #EBookClientView, - * which should be freed with g_object_unref(). + * If successful, then the @out_view is set to newly allocated + * #EBookClientView, which should be freed with g_object_unref(). * * Returns: %TRUE if successful, %FALSE otherwise. * @@ -2494,33 +2997,42 @@ complete_get_view (EBookClient *client, gboolean e_book_client_get_view_finish (EBookClient *client, GAsyncResult *result, - EBookClientView **view, + EBookClientView **out_view, GError **error) { - gboolean res; - gchar *view_path = NULL; + GSimpleAsyncResult *simple; + AsyncContext *async_context; + + g_return_val_if_fail ( + g_simple_async_result_is_valid ( + result, G_OBJECT (client), + e_book_client_get_view), FALSE); - g_return_val_if_fail (view != NULL, FALSE); + simple = G_SIMPLE_ASYNC_RESULT (result); + async_context = g_simple_async_result_get_op_res_gpointer (simple); - res = e_client_proxy_call_finish_string ( - E_CLIENT (client), - result, &view_path, error, - e_book_client_get_view); + if (g_simple_async_result_propagate_error (simple, error)) + return FALSE; - return complete_get_view (client, res, view_path, view, error); + g_return_val_if_fail (async_context->client_view != NULL, FALSE); + + if (out_view != NULL) + *out_view = g_object_ref (async_context->client_view); + + return TRUE; } /** * e_book_client_get_view_sync: * @client: an #EBookClient * @sexp: an S-expression representing the query - * @view: (out) an #EBookClientView + * @out_view: (out) an #EBookClientView * @cancellable: a #GCancellable; can be %NULL * @error: (out): a #GError to set an error, if any * * Query @client with @sexp, creating an #EBookClientView. - * If successful, then the @view is set to newly allocated #EBookClientView, - * which should be freed with g_object_unref(). + * If successful, then the @out_view is set to newly allocated + * #EBookClientView, which should be freed with g_object_unref(). * * Note: @sexp can be obtained through #EBookQuery, by converting it * to a string with e_book_query_to_string(). @@ -2532,31 +3044,62 @@ e_book_client_get_view_finish (EBookClient *client, gboolean e_book_client_get_view_sync (EBookClient *client, const gchar *sexp, - EBookClientView **view, + EBookClientView **out_view, GCancellable *cancellable, GError **error) { - gboolean res; - gchar *gdbus_sexp = NULL; - gchar *view_path = NULL; + gchar *utf8_sexp; + gchar *object_path = NULL; + gboolean success; g_return_val_if_fail (E_IS_BOOK_CLIENT (client), FALSE); g_return_val_if_fail (sexp != NULL, FALSE); - g_return_val_if_fail (view != NULL, FALSE); + g_return_val_if_fail (out_view != NULL, FALSE); if (client->priv->dbus_proxy == NULL) { set_proxy_gone_error (error); return FALSE; } - res = e_client_proxy_call_sync_string__string ( - E_CLIENT (client), - e_util_ensure_gdbus_string (sexp, &gdbus_sexp), - &view_path, cancellable, error, - e_gdbus_book_call_get_view_sync); + utf8_sexp = e_util_utf8_make_valid (sexp); - g_free (gdbus_sexp); + success = e_dbus_address_book_call_get_view_sync ( + client->priv->dbus_proxy, utf8_sexp, + &object_path, cancellable, error); + + g_free (utf8_sexp); + + /* Sanity check. */ + g_return_val_if_fail ( + (success && (object_path != NULL)) || + (!success && (object_path == NULL)), FALSE); + + if (object_path != NULL) { + GDBusConnection *connection; + EBookClientView *client_view; + + connection = g_dbus_proxy_get_connection ( + G_DBUS_PROXY (client->priv->dbus_proxy)); + + client_view = g_initable_new ( + E_TYPE_BOOK_CLIENT_VIEW, + cancellable, error, + "client", client, + "connection", connection, + "object-path", object_path, + NULL); + + /* XXX Would have been easier to return the + * EBookClientView directly rather than + * through an "out" parameter. */ + if (client_view != NULL) + *out_view = client_view; + else + success = FALSE; + + g_free (object_path); + } - return complete_get_view (client, res, view_path, view, error); + return success; } diff --git a/addressbook/libebook/e-book-client.h b/addressbook/libebook/e-book-client.h index 26da1d6..1e782ab 100644 --- a/addressbook/libebook/e-book-client.h +++ b/addressbook/libebook/e-book-client.h @@ -124,8 +124,8 @@ GType e_book_client_get_type (void) G_GNUC_CONST; EBookClient * e_book_client_new (ESource *source, GError **error); gboolean e_book_client_get_self (ESourceRegistry *registry, - EContact **contact, - EBookClient **client, + EContact **out_contact, + EBookClient **out_client, GError **error); gboolean e_book_client_set_self (EBookClient *client, EContact *contact, @@ -139,11 +139,11 @@ void e_book_client_add_contact (EBookClient *client, gboolean e_book_client_add_contact_finish (EBookClient *client, GAsyncResult *result, - gchar **added_uid, + gchar **out_added_uid, GError **error); gboolean e_book_client_add_contact_sync (EBookClient *client, EContact *contact, - gchar **added_uid, + gchar **out_added_uid, GCancellable *cancellable, GError **error); void e_book_client_add_contacts (EBookClient *client, @@ -154,11 +154,11 @@ void e_book_client_add_contacts (EBookClient *client, gboolean e_book_client_add_contacts_finish (EBookClient *client, GAsyncResult *result, - GSList **added_uids, + GSList **out_added_uids, GError **error); gboolean e_book_client_add_contacts_sync (EBookClient *client, GSList *contacts, - GSList **added_uids, + GSList **out_added_uids, GCancellable *cancellable, GError **error); void e_book_client_modify_contact (EBookClient *client, @@ -240,11 +240,11 @@ void e_book_client_get_contact (EBookClient *client, gboolean e_book_client_get_contact_finish (EBookClient *client, GAsyncResult *result, - EContact **contact, + EContact **out_contact, GError **error); gboolean e_book_client_get_contact_sync (EBookClient *client, const gchar *uid, - EContact **contact, + EContact **out_contact, GCancellable *cancellable, GError **error); void e_book_client_get_contacts (EBookClient *client, @@ -259,7 +259,7 @@ gboolean e_book_client_get_contacts_finish GError **error); gboolean e_book_client_get_contacts_sync (EBookClient *client, const gchar *sexp, - GSList **contacts, + GSList **out_contacts, GCancellable *cancellable, GError **error); void e_book_client_get_contacts_uids (EBookClient *client, @@ -270,12 +270,12 @@ void e_book_client_get_contacts_uids (EBookClient *client, gboolean e_book_client_get_contacts_uids_finish (EBookClient *client, GAsyncResult *result, - GSList **contacts_uids, + GSList **out_contact_uids, GError **error); gboolean e_book_client_get_contacts_uids_sync (EBookClient *client, const gchar *sexp, - GSList **contacts_uids, + GSList **out_contact_uids, GCancellable *cancellable, GError **error); void e_book_client_get_view (EBookClient *client, @@ -285,11 +285,11 @@ void e_book_client_get_view (EBookClient *client, gpointer user_data); gboolean e_book_client_get_view_finish (EBookClient *client, GAsyncResult *result, - EBookClientView **view, + EBookClientView **out_view, GError **error); gboolean e_book_client_get_view_sync (EBookClient *client, const gchar *sexp, - EBookClientView **view, + EBookClientView **out_view, GCancellable *cancellable, GError **error); diff --git a/addressbook/libedata-book/e-book-backend.c b/addressbook/libedata-book/e-book-backend.c index 948dca1..200d8e2 100644 --- a/addressbook/libedata-book/e-book-backend.c +++ b/addressbook/libedata-book/e-book-backend.c @@ -81,6 +81,8 @@ book_backend_get_backend_property (EBookBackend *backend, e_data_book_respond_get_backend_property (book, opid, NULL, "TRUE"); } else if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_OPENING)) { e_data_book_respond_get_backend_property (book, opid, NULL, "FALSE"); + } else if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_REVISION)) { + e_data_book_respond_get_backend_property (book, opid, NULL, "0"); } else if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_ONLINE)) { e_data_book_respond_get_backend_property (book, opid, NULL, e_backend_get_online (E_BACKEND (backend)) ? "TRUE" : "FALSE"); } else if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_READONLY)) { @@ -497,17 +499,8 @@ e_book_backend_open (EBookBackend *backend, g_mutex_lock (&backend->priv->clients_mutex); if (e_book_backend_is_opened (backend)) { - gboolean online; - gboolean writable; - g_mutex_unlock (&backend->priv->clients_mutex); - online = e_backend_get_online (E_BACKEND (backend)); - writable = e_book_backend_get_writable (backend); - - e_data_book_report_online (book, online); - e_data_book_report_readonly (book, !writable); - e_data_book_respond_open (book, opid, NULL); } else { g_mutex_unlock (&backend->priv->clients_mutex); @@ -1246,23 +1239,16 @@ e_book_backend_notify_error (EBookBackend *backend, * Notifies all backend's clients about the current readonly state. * * Since: 3.2 + * + * Deprecated: 3.8: Use e_book_backend_set_writable() instead. **/ void e_book_backend_notify_readonly (EBookBackend *backend, gboolean is_readonly) { - EBookBackendPrivate *priv; - GList *clients; + g_return_if_fail (E_IS_BOOK_BACKEND (backend)); - priv = backend->priv; e_book_backend_set_writable (backend, !is_readonly); - g_mutex_lock (&priv->clients_mutex); - - for (clients = priv->clients; clients != NULL; clients = g_list_next (clients)) - e_data_book_report_readonly (E_DATA_BOOK (clients->data), is_readonly); - - g_mutex_unlock (&priv->clients_mutex); - } /** @@ -1274,25 +1260,16 @@ e_book_backend_notify_readonly (EBookBackend *backend, * Meant to be used by backend implementations. * * Since: 3.2 + * + * Deprecated: 3.8: Use e_backend_set_online() instead. **/ void e_book_backend_notify_online (EBookBackend *backend, gboolean is_online) { - EBookBackendPrivate *priv; - GList *clients; - - /* XXX Disregard the argument. - * EBackend determines this for itself. */ - is_online = e_backend_get_online (E_BACKEND (backend)); - - priv = backend->priv; - g_mutex_lock (&priv->clients_mutex); - - for (clients = priv->clients; clients != NULL; clients = g_list_next (clients)) - e_data_book_report_online (E_DATA_BOOK (clients->data), is_online); + g_return_if_fail (E_IS_BOOK_BACKEND (backend)); - g_mutex_unlock (&priv->clients_mutex); + e_backend_set_online (E_BACKEND (backend), is_online); } /** diff --git a/addressbook/libedata-book/e-book-backend.h b/addressbook/libedata-book/e-book-backend.h index 890e0a6..6358805 100644 --- a/addressbook/libedata-book/e-book-backend.h +++ b/addressbook/libedata-book/e-book-backend.h @@ -285,10 +285,6 @@ void e_book_backend_notify_complete (EBookBackend *backend); void e_book_backend_notify_error (EBookBackend *backend, const gchar *message); -void e_book_backend_notify_readonly (EBookBackend *backend, - gboolean is_readonly); -void e_book_backend_notify_online (EBookBackend *backend, - gboolean is_online); void e_book_backend_notify_property_changed (EBookBackend *backend, const gchar *prop_name, @@ -348,6 +344,10 @@ void e_book_backend_foreach_view (EBookBackend *backend, gpointer user_data); void e_book_backend_notify_opened (EBookBackend *backend, GError *error); +void e_book_backend_notify_readonly (EBookBackend *backend, + gboolean is_readonly); +void e_book_backend_notify_online (EBookBackend *backend, + gboolean is_online); void e_book_backend_respond_opened (EBookBackend *backend, EDataBook *book, guint32 opid, diff --git a/addressbook/libedata-book/e-data-book.c b/addressbook/libedata-book/e-data-book.c index 372647f..6591716 100644 --- a/addressbook/libedata-book/e-data-book.c +++ b/addressbook/libedata-book/e-data-book.c @@ -25,6 +25,9 @@ #include #include +/* Private D-Bus classes. */ +#include + #include #include "e-data-book-factory.h" @@ -33,15 +36,13 @@ #include "e-book-backend.h" #include "e-book-backend-sexp.h" -#include "e-gdbus-book.h" - #define E_DATA_BOOK_GET_PRIVATE(obj) \ (G_TYPE_INSTANCE_GET_PRIVATE \ ((obj), E_TYPE_DATA_BOOK, EDataBookPrivate)) struct _EDataBookPrivate { GDBusConnection *connection; - EGdbusBook *dbus_interface; + EDBusAddressBook *dbus_interface; EBookBackend *backend; gchar *object_path; @@ -89,8 +90,6 @@ typedef struct { guint watcher_id; union { - /* OP_OPEN */ - gboolean only_if_exists; /* OP_GET_CONTACT */ gchar *uid; /* OP_REMOVE_CONTACTS */ @@ -103,7 +102,7 @@ typedef struct { /* OP_GET_CONTACTS_UIDS */ gchar *query; /* OP_GET_BACKEND_PROPERTY */ - gchar *prop_name; + const gchar *prop_name; /* OP_REFRESH */ /* OP_CLOSE */ @@ -166,6 +165,7 @@ op_new (OperationID op, data->book = g_object_ref (book); data->cancellable = g_cancellable_new (); + /* This is optional so we can fake client requests. */ if (invocation != NULL) { GDBusConnection *connection; const gchar *sender; @@ -222,9 +222,6 @@ op_unref (OperationData *data) case OP_GET_CONTACTS_UIDS: g_free (data->d.query); break; - case OP_GET_BACKEND_PROPERTY: - g_free (data->d.prop_name); - break; default: break; } @@ -261,11 +258,36 @@ op_dispatch (EDataBook *book, g_mutex_unlock (&book->priv->open_lock); } +static OperationData * +op_claim (EDataBook *book, + guint32 opid) +{ + OperationData *data; + + g_return_val_if_fail (E_IS_DATA_BOOK (book), NULL); + + e_operation_pool_release_opid (ops_pool, opid); + + g_rec_mutex_lock (&book->priv->pending_ops_lock); + data = g_hash_table_lookup ( + book->priv->pending_ops, + GUINT_TO_POINTER (opid)); + if (data != NULL) { + /* Steal the hash table's reference. */ + g_hash_table_steal ( + book->priv->pending_ops, + GUINT_TO_POINTER (opid)); + } + g_rec_mutex_unlock (&book->priv->pending_ops_lock); + + return data; +} + static void op_complete (EDataBook *book, guint32 opid) { - g_return_if_fail (book != NULL); + g_return_if_fail (E_IS_DATA_BOOK (book)); e_operation_pool_release_opid (ops_pool, opid); @@ -277,11 +299,126 @@ op_complete (EDataBook *book, } static void +data_book_convert_to_client_error (GError *error) +{ + g_return_if_fail (error != NULL); + + if (error->domain != E_DATA_BOOK_ERROR) + return; + + switch (error->code) { + case E_DATA_BOOK_STATUS_REPOSITORY_OFFLINE: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_REPOSITORY_OFFLINE; + break; + + case E_DATA_BOOK_STATUS_PERMISSION_DENIED: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_PERMISSION_DENIED; + break; + + case E_DATA_BOOK_STATUS_CONTACT_NOT_FOUND: + error->domain = E_BOOK_CLIENT_ERROR; + error->code = E_BOOK_CLIENT_ERROR_CONTACT_NOT_FOUND; + break; + + case E_DATA_BOOK_STATUS_CONTACTID_ALREADY_EXISTS: + error->domain = E_BOOK_CLIENT_ERROR; + error->code = E_BOOK_CLIENT_ERROR_CONTACT_ID_ALREADY_EXISTS; + break; + + case E_DATA_BOOK_STATUS_AUTHENTICATION_FAILED: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_AUTHENTICATION_FAILED; + break; + + case E_DATA_BOOK_STATUS_UNSUPPORTED_AUTHENTICATION_METHOD: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_UNSUPPORTED_AUTHENTICATION_METHOD; + break; + + case E_DATA_BOOK_STATUS_TLS_NOT_AVAILABLE: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_TLS_NOT_AVAILABLE; + break; + + case E_DATA_BOOK_STATUS_NO_SUCH_BOOK: + error->domain = E_BOOK_CLIENT_ERROR; + error->code = E_BOOK_CLIENT_ERROR_NO_SUCH_BOOK; + break; + + case E_DATA_BOOK_STATUS_BOOK_REMOVED: + error->domain = E_BOOK_CLIENT_ERROR; + error->code = E_BOOK_CLIENT_ERROR_NO_SUCH_SOURCE; + break; + + case E_DATA_BOOK_STATUS_OFFLINE_UNAVAILABLE: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_OFFLINE_UNAVAILABLE; + break; + + case E_DATA_BOOK_STATUS_SEARCH_SIZE_LIMIT_EXCEEDED: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_SEARCH_SIZE_LIMIT_EXCEEDED; + break; + + case E_DATA_BOOK_STATUS_SEARCH_TIME_LIMIT_EXCEEDED: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_SEARCH_TIME_LIMIT_EXCEEDED; + break; + + case E_DATA_BOOK_STATUS_INVALID_QUERY: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_INVALID_QUERY; + break; + + case E_DATA_BOOK_STATUS_QUERY_REFUSED: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_QUERY_REFUSED; + break; + + case E_DATA_BOOK_STATUS_COULD_NOT_CANCEL: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_COULD_NOT_CANCEL; + break; + + case E_DATA_BOOK_STATUS_NO_SPACE: + error->domain = E_BOOK_CLIENT_ERROR; + error->code = E_BOOK_CLIENT_ERROR_NO_SPACE; + break; + + case E_DATA_BOOK_STATUS_INVALID_ARG: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_INVALID_ARG; + break; + + case E_DATA_BOOK_STATUS_NOT_SUPPORTED: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_NOT_SUPPORTED; + break; + + case E_DATA_BOOK_STATUS_NOT_OPENED: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_NOT_OPENED; + break; + + case E_DATA_BOOK_STATUS_UNSUPPORTED_FIELD: + case E_DATA_BOOK_STATUS_OTHER_ERROR: + case E_DATA_BOOK_STATUS_INVALID_SERVER_VERSION: + error->domain = E_CLIENT_ERROR; + error->code = E_CLIENT_ERROR_OTHER_ERROR; + break; + + default: + g_warn_if_reached (); + } +} + +static void operation_thread (gpointer data, gpointer user_data) { OperationData *op = data; - OperationData *cancel_op; EBookBackend *backend; GHashTableIter iter; gpointer value; @@ -292,7 +429,7 @@ operation_thread (gpointer data, case OP_OPEN: e_book_backend_open ( backend, op->book, op->id, - op->cancellable, op->d.only_if_exists); + op->cancellable, FALSE); break; case OP_ADD_CONTACTS: @@ -352,11 +489,13 @@ operation_thread (gpointer data, card_sexp = e_book_backend_sexp_new (op->d.query); if (!card_sexp) { - error = e_data_book_create_error (E_DATA_BOOK_STATUS_INVALID_QUERY, NULL); - /* Translators: This is prefix to a detailed error message */ - g_prefix_error (&error, "%s", _("Invalid query: ")); - e_gdbus_book_emit_get_view_done (op->book->priv->dbus_interface, op->id, error, NULL); - g_error_free (error); + g_dbus_method_invocation_return_error_literal ( + op->invocation, + E_CLIENT_ERROR, + E_CLIENT_ERROR_INVALID_QUERY, + _("Invalid query")); + + op_complete (op->book, op->id); break; } @@ -377,16 +516,23 @@ operation_thread (gpointer data, if (error != NULL) { /* Translators: This is prefix to a detailed error message */ g_prefix_error (&error, "%s", _("Invalid query: ")); - e_gdbus_book_emit_get_view_done (op->book->priv->dbus_interface, op->id, error, NULL); - g_error_free (error); + data_book_convert_to_client_error (error); + g_dbus_method_invocation_take_error ( + op->invocation, error); + + op_complete (op->book, op->id); g_free (object_path); break; } e_book_backend_add_view (backend, view); - e_gdbus_book_emit_get_view_done (op->book->priv->dbus_interface, op->id, NULL, object_path); + e_dbus_address_book_complete_get_view ( + op->book->priv->dbus_interface, + op->invocation, + object_path); + op_complete (op->book, op->id); g_free (object_path); } break; @@ -399,11 +545,17 @@ operation_thread (gpointer data, g_hash_table_iter_init (&iter, op->book->priv->pending_ops); while (g_hash_table_iter_next (&iter, NULL, &value)) { - cancel_op = (OperationData *) value; + OperationData *cancel_op = value; g_cancellable_cancel (cancel_op->cancellable); } g_rec_mutex_unlock (&op->book->priv->pending_ops_lock); + + e_dbus_address_book_complete_close ( + op->book->priv->dbus_interface, + op->invocation); + + op_complete (op->book, op->id); break; } @@ -547,25 +699,6 @@ e_data_book_create_error_fmt (EDataBookStatus status, return error; } -static void -data_book_return_error (GDBusMethodInvocation *invocation, - const GError *perror, - const gchar *error_prefix) -{ - GError *error; - - if (perror == NULL) - error = g_error_new (E_DATA_BOOK_ERROR, E_DATA_BOOK_STATUS_OTHER_ERROR, "%s", _("Unknown error")); - else - error = g_error_new (E_DATA_BOOK_ERROR, perror->code, "%s", perror->message); - - g_prefix_error (&error, "%s", error_prefix); - - g_dbus_method_invocation_return_gerror (invocation, error); - - g_error_free (error); -} - /** * e_data_book_string_slist_to_comma_string: * @@ -606,17 +739,13 @@ e_data_book_string_slist_to_comma_string (const GSList *strings) } static gboolean -data_book_handle_open_cb (EGdbusBook *interface, +data_book_handle_open_cb (EDBusAddressBook *interface, GDBusMethodInvocation *invocation, - gboolean only_if_exists, EDataBook *book) { OperationData *op; op = op_new (OP_OPEN, book, invocation); - op->d.only_if_exists = only_if_exists; - - e_gdbus_book_complete_open (interface, invocation, op->id); op_dispatch (book, op); @@ -624,7 +753,7 @@ data_book_handle_open_cb (EGdbusBook *interface, } static gboolean -data_book_handle_refresh_cb (EGdbusBook *interface, +data_book_handle_refresh_cb (EDBusAddressBook *interface, GDBusMethodInvocation *invocation, EDataBook *book) { @@ -632,147 +761,93 @@ data_book_handle_refresh_cb (EGdbusBook *interface, op = op_new (OP_REFRESH, book, invocation); - e_gdbus_book_complete_refresh (interface, invocation, op->id); - op_dispatch (book, op); return TRUE; } static gboolean -data_book_handle_get_contact_cb (EGdbusBook *interface, +data_book_handle_get_contact_cb (EDBusAddressBook *interface, GDBusMethodInvocation *invocation, const gchar *in_uid, EDataBook *book) { OperationData *op; - if (in_uid == NULL) { - GError *error; - - error = e_data_book_create_error (E_DATA_BOOK_STATUS_CONTACT_NOT_FOUND, NULL); - /* Translators: This is prefix to a detailed error message */ - data_book_return_error (invocation, error, _("Cannot get contact: ")); - g_error_free (error); - return TRUE; - } - op = op_new (OP_GET_CONTACT, book, invocation); op->d.uid = g_strdup (in_uid); - e_gdbus_book_complete_get_contact (interface, invocation, op->id); - op_dispatch (book, op); return TRUE; } static gboolean -data_book_handle_get_contact_list_cb (EGdbusBook *interface, +data_book_handle_get_contact_list_cb (EDBusAddressBook *interface, GDBusMethodInvocation *invocation, const gchar *in_query, EDataBook *book) { OperationData *op; - if (in_query == NULL || !*in_query) { - GError *error = e_data_book_create_error (E_DATA_BOOK_STATUS_INVALID_QUERY, NULL); - /* Translators: This is prefix to a detailed error message */ - data_book_return_error (invocation, error, _("Empty query: ")); - g_error_free (error); - return TRUE; - } - op = op_new (OP_GET_CONTACTS, book, invocation); op->d.query = g_strdup (in_query); - e_gdbus_book_complete_get_contact_list (interface, invocation, op->id); - op_dispatch (book, op); return TRUE; } static gboolean -data_book_handle_get_contact_list_uids_cb (EGdbusBook *interface, +data_book_handle_get_contact_list_uids_cb (EDBusAddressBook *interface, GDBusMethodInvocation *invocation, const gchar *in_query, EDataBook *book) { OperationData *op; - if (in_query == NULL || !*in_query) { - GError *error = e_data_book_create_error (E_DATA_BOOK_STATUS_INVALID_QUERY, NULL); - /* Translators: This is prefix to a detailed error message */ - data_book_return_error (invocation, error, _("Empty query: ")); - g_error_free (error); - return TRUE; - } - op = op_new (OP_GET_CONTACTS_UIDS, book, invocation); op->d.query = g_strdup (in_query); - e_gdbus_book_complete_get_contact_list_uids (interface, invocation, op->id); - op_dispatch (book, op); return TRUE; } static gboolean -data_book_handle_add_contacts_cb (EGdbusBook *interface, - GDBusMethodInvocation *invocation, - const gchar * const *in_vcards, - EDataBook *book) +data_book_handle_create_contacts_cb (EDBusAddressBook *interface, + GDBusMethodInvocation *invocation, + const gchar * const *in_vcards, + EDataBook *book) { OperationData *op; - if (in_vcards == NULL || !*in_vcards) { - GError *error = e_data_book_create_error (E_DATA_BOOK_STATUS_INVALID_QUERY, NULL); - /* Translators: This is prefix to a detailed error message */ - data_book_return_error (invocation, error, _("Cannot add contact: ")); - g_error_free (error); - return TRUE; - } - op = op_new (OP_ADD_CONTACTS, book, invocation); op->d.vcards = e_util_strv_to_slist (in_vcards); - e_gdbus_book_complete_add_contacts (interface, invocation, op->id); - op_dispatch (book, op); return TRUE; } static gboolean -data_book_handle_modify_contacts_cb (EGdbusBook *interface, +data_book_handle_modify_contacts_cb (EDBusAddressBook *interface, GDBusMethodInvocation *invocation, const gchar * const *in_vcards, EDataBook *book) { OperationData *op; - if (in_vcards == NULL || !*in_vcards) { - GError *error = e_data_book_create_error (E_DATA_BOOK_STATUS_INVALID_QUERY, NULL); - /* Translators: This is prefix to a detailed error message */ - data_book_return_error (invocation, error, _("Cannot modify contacts: ")); - g_error_free (error); - return TRUE; - } - op = op_new (OP_MODIFY_CONTACTS, book, invocation); op->d.vcards = e_util_strv_to_slist (in_vcards); - e_gdbus_book_complete_modify_contacts (interface, invocation, op->id); - op_dispatch (book, op); return TRUE; } static gboolean -data_book_handle_remove_contacts_cb (EGdbusBook *interface, +data_book_handle_remove_contacts_cb (EDBusAddressBook *interface, GDBusMethodInvocation *invocation, const gchar * const *in_uids, EDataBook *book) @@ -786,56 +861,22 @@ data_book_handle_remove_contacts_cb (EGdbusBook *interface, op->d.ids = g_slist_prepend (op->d.ids, g_strdup (*in_uids)); } - e_gdbus_book_complete_remove_contacts (interface, invocation, op->id); - op_dispatch (book, op); return TRUE; } static gboolean -data_book_handle_get_backend_property_cb (EGdbusBook *interface, - GDBusMethodInvocation *invocation, - const gchar *in_prop_name, - EDataBook *book) -{ - OperationData *op; - - op = op_new (OP_GET_BACKEND_PROPERTY, book, invocation); - op->d.prop_name = g_strdup (in_prop_name); - - e_gdbus_book_complete_get_backend_property (interface, invocation, op->id); - - /* This operation is never queued. */ - e_operation_pool_push (ops_pool, op); - - return TRUE; -} - -static gboolean -data_book_handle_get_view_cb (EGdbusBook *interface, +data_book_handle_get_view_cb (EDBusAddressBook *interface, GDBusMethodInvocation *invocation, const gchar *in_query, EDataBook *book) { OperationData *op; - if (!in_query || !*in_query) { - GError *error; - - error = e_data_book_create_error (E_DATA_BOOK_STATUS_INVALID_QUERY, NULL); - /* Translators: This is prefix to a detailed error message */ - data_book_return_error (invocation, error, _("Invalid query: ")); - g_error_free (error); - - return TRUE; - } - op = op_new (OP_GET_VIEW, book, invocation); op->d.query = g_strdup (in_query); - e_gdbus_book_complete_get_view (interface, invocation, op->id); - /* This operation is never queued. */ e_operation_pool_push (ops_pool, op); @@ -843,7 +884,7 @@ data_book_handle_get_view_cb (EGdbusBook *interface, } static gboolean -data_book_handle_close_cb (EGdbusBook *interface, +data_book_handle_close_cb (EDBusAddressBook *interface, GDBusMethodInvocation *invocation, EDataBook *book) { @@ -853,8 +894,6 @@ data_book_handle_close_cb (EGdbusBook *interface, /* unref here makes sure the book is freed in a separate thread */ g_object_unref (book); - e_gdbus_book_complete_close (interface, invocation, NULL); - /* This operation is never queued. */ e_operation_pool_push (ops_pool, op); @@ -866,11 +905,13 @@ e_data_book_respond_open (EDataBook *book, guint opid, GError *error) { + OperationData *data; GError *copy = NULL; g_return_if_fail (E_IS_DATA_BOOK (book)); - op_complete (book, opid); + data = op_claim (book, opid); + g_return_if_fail (data != NULL); /* Translators: This is prefix to a detailed error message */ g_prefix_error (&error, "%s", _("Cannot open book: ")); @@ -882,10 +923,17 @@ e_data_book_respond_open (EDataBook *book, copy = g_error_copy (error); e_book_backend_notify_opened (book->priv->backend, copy); - e_gdbus_book_emit_open_done (book->priv->dbus_interface, opid, error); + if (error == NULL) { + e_dbus_address_book_complete_open ( + book->priv->dbus_interface, + data->invocation); + } else { + data_book_convert_to_client_error (error); + g_dbus_method_invocation_take_error ( + data->invocation, error); + } - if (error != NULL) - g_error_free (error); + op_unref (data); /* Dispatch any pending operations. */ @@ -919,17 +967,27 @@ e_data_book_respond_refresh (EDataBook *book, guint32 opid, GError *error) { + OperationData *data; + g_return_if_fail (E_IS_DATA_BOOK (book)); - op_complete (book, opid); + data = op_claim (book, opid); + g_return_if_fail (data != NULL); /* Translators: This is prefix to a detailed error message */ g_prefix_error (&error, "%s", _("Cannot refresh address book: ")); - e_gdbus_book_emit_refresh_done (book->priv->dbus_interface, opid, error); + if (error == NULL) { + e_dbus_address_book_complete_refresh ( + book->priv->dbus_interface, + data->invocation); + } else { + data_book_convert_to_client_error (error); + g_dbus_method_invocation_take_error ( + data->invocation, error); + } - if (error) - g_error_free (error); + op_unref (data); } /** @@ -945,21 +1003,24 @@ e_data_book_respond_get_backend_property (EDataBook *book, GError *error, const gchar *prop_value) { - gchar *gdbus_prop_value = NULL; + OperationData *data; g_return_if_fail (E_IS_DATA_BOOK (book)); - op_complete (book, opid); - - /* Translators: This is prefix to a detailed error message */ - g_prefix_error (&error, "%s", _("Cannot get backend property: ")); - - e_gdbus_book_emit_get_backend_property_done (book->priv->dbus_interface, opid, error, e_util_ensure_gdbus_string (prop_value, &gdbus_prop_value)); + data = op_claim (book, opid); + g_return_if_fail (data != NULL); - if (error) + if (error == NULL) { + e_data_book_report_backend_property_changed ( + book, data->d.prop_name, prop_value); + } else { + /* This should never happen, since all backend property + * requests now originate from our constructed() method. */ + g_warning ("%s: %s", G_STRFUNC, error->message); g_error_free (error); + } - g_free (gdbus_prop_value); + op_unref (data); } /** @@ -985,21 +1046,34 @@ e_data_book_respond_get_contact (EDataBook *book, GError *error, const gchar *vcard) { - gchar *gdbus_vcard = NULL; + OperationData *data; g_return_if_fail (E_IS_DATA_BOOK (book)); - op_complete (book, opid); + data = op_claim (book, opid); + g_return_if_fail (data != NULL); /* Translators: This is prefix to a detailed error message */ g_prefix_error (&error, "%s", _("Cannot get contact: ")); - e_gdbus_book_emit_get_contact_done (book->priv->dbus_interface, opid, error, e_util_ensure_gdbus_string (vcard, &gdbus_vcard)); + if (error == NULL) { + gchar *utf8_vcard; - if (error) - g_error_free (error); + utf8_vcard = e_util_utf8_make_valid (vcard); - g_free (gdbus_vcard); + e_dbus_address_book_complete_get_contact ( + book->priv->dbus_interface, + data->invocation, + utf8_vcard); + + g_free (utf8_vcard); + } else { + data_book_convert_to_client_error (error); + g_dbus_method_invocation_take_error ( + data->invocation, error); + } + + op_unref (data); } void @@ -1008,27 +1082,42 @@ e_data_book_respond_get_contact_list (EDataBook *book, GError *error, const GSList *cards) { + OperationData *data; + g_return_if_fail (E_IS_DATA_BOOK (book)); - if (error) { - /* Translators: This is prefix to a detailed error message */ - g_prefix_error (&error, "%s", _("Cannot get contact list: ")); - e_gdbus_book_emit_get_contact_list_done (book->priv->dbus_interface, opid, error, NULL); - g_error_free (error); - } else { - gchar **array; - const GSList *l; - gint i = 0; + data = op_claim (book, opid); + g_return_if_fail (data != NULL); + + /* Translators: This is prefix to a detailed error message */ + g_prefix_error (&error, "%s", _("Cannot get contact list: ")); + + if (error == NULL) { + gchar **strv; + guint length; + gint ii = 0; - array = g_new0 (gchar *, g_slist_length ((GSList *) cards) + 1); - for (l = cards; l != NULL; l = l->next) { - array[i++] = e_util_utf8_make_valid (l->data); + length = g_slist_length ((GSList *) cards); + strv = g_new0 (gchar *, length + 1); + + while (cards != NULL) { + strv[ii++] = e_util_utf8_make_valid (cards->data); + cards = g_slist_next ((GSList *) cards); } - e_gdbus_book_emit_get_contact_list_done (book->priv->dbus_interface, opid, NULL, (const gchar * const *) array); + e_dbus_address_book_complete_get_contact_list ( + book->priv->dbus_interface, + data->invocation, + (const gchar * const *) strv); - g_strfreev (array); + g_strfreev (strv); + } else { + data_book_convert_to_client_error (error); + g_dbus_method_invocation_take_error ( + data->invocation, error); } + + op_unref (data); } /** @@ -1044,27 +1133,42 @@ e_data_book_respond_get_contact_list_uids (EDataBook *book, GError *error, const GSList *uids) { + OperationData *data; + g_return_if_fail (E_IS_DATA_BOOK (book)); - if (error) { - /* Translators: This is prefix to a detailed error message */ - g_prefix_error (&error, "%s", _("Cannot get contact list uids: ")); - e_gdbus_book_emit_get_contact_list_uids_done (book->priv->dbus_interface, opid, error, NULL); - g_error_free (error); - } else { - gchar **array; - const GSList *l; - gint i = 0; + data = op_claim (book, opid); + g_return_if_fail (data != NULL); + + /* Translators: This is prefix to a detailed error message */ + g_prefix_error (&error, "%s", _("Cannot get contact list uids: ")); + + if (error == NULL) { + gchar **strv; + guint length; + gint ii = 0; + + length = g_slist_length ((GSList *) uids); + strv = g_new0 (gchar *, length + 1); - array = g_new0 (gchar *, g_slist_length ((GSList *) uids) + 1); - for (l = uids; l != NULL; l = l->next) { - array[i++] = e_util_utf8_make_valid (l->data); + while (uids != NULL) { + strv[ii++] = e_util_utf8_make_valid (uids->data); + uids = g_slist_next ((GSList *) uids); } - e_gdbus_book_emit_get_contact_list_uids_done (book->priv->dbus_interface, opid, NULL, (const gchar * const *) array); + e_dbus_address_book_complete_get_contact_list_uids ( + book->priv->dbus_interface, + data->invocation, + (const gchar * const *) strv); - g_strfreev (array); + g_strfreev (strv); + } else { + data_book_convert_to_client_error (error); + g_dbus_method_invocation_take_error ( + data->invocation, error); } + + op_unref (data); } /** @@ -1080,38 +1184,54 @@ e_data_book_respond_create_contacts (EDataBook *book, GError *error, const GSList *contacts) { - gchar **array = NULL; - const GSList *l; - gint i = 0; + OperationData *data; g_return_if_fail (E_IS_DATA_BOOK (book)); - op_complete (book, opid); - - array = g_new0 (gchar *, g_slist_length ((GSList *) contacts) + 1); - for (l = contacts; l != NULL; l = l->next) { - EContact *contact = E_CONTACT (l->data); - - array[i++] = e_util_utf8_make_valid (e_contact_get_const (contact, E_CONTACT_UID)); - } + data = op_claim (book, opid); + g_return_if_fail (data != NULL); /* Translators: This is prefix to a detailed error message */ g_prefix_error (&error, "%s", _("Cannot add contact: ")); - e_gdbus_book_emit_add_contacts_done (book->priv->dbus_interface, opid, error, (const gchar * const *) array); + if (error == NULL) { + EBookBackend *backend; + gchar **strv; + guint length; + gint ii = 0; - g_strfreev (array); - if (error) { - g_error_free (error); - } else { - for (l = contacts; l != NULL; l = l->next) { - EContact *contact = E_CONTACT (l->data); + backend = e_data_book_get_backend (book); + + length = g_slist_length ((GSList *) contacts); + strv = g_new0 (gchar *, length + 1); + + while (contacts != NULL) { + EContact *contact = E_CONTACT (contacts->data); + const gchar *uid; - e_book_backend_notify_update (e_data_book_get_backend (book), contact); + uid = e_contact_get_const (contact, E_CONTACT_UID); + strv[ii++] = e_util_utf8_make_valid (uid); + + e_book_backend_notify_update (backend, contact); + + contacts = g_slist_next ((GSList *) contacts); } - e_book_backend_notify_complete (e_data_book_get_backend (book)); + e_dbus_address_book_complete_create_contacts ( + book->priv->dbus_interface, + data->invocation, + (const gchar * const *) strv); + + e_book_backend_notify_complete (backend); + + g_strfreev (strv); + } else { + data_book_convert_to_client_error (error); + g_dbus_method_invocation_take_error ( + data->invocation, error); } + + op_unref (data); } /** @@ -1127,25 +1247,39 @@ e_data_book_respond_modify_contacts (EDataBook *book, GError *error, const GSList *contacts) { + OperationData *data; + g_return_if_fail (E_IS_DATA_BOOK (book)); - op_complete (book, opid); + data = op_claim (book, opid); + g_return_if_fail (data != NULL); /* Translators: This is prefix to a detailed error message */ g_prefix_error (&error, "%s", _("Cannot modify contacts: ")); - e_gdbus_book_emit_modify_contacts_done (book->priv->dbus_interface, opid, error); + if (error == NULL) { + EBookBackend *backend; - if (error) { - g_error_free (error); - } else { - const GSList *l; + backend = e_data_book_get_backend (book); + + e_dbus_address_book_complete_modify_contacts ( + book->priv->dbus_interface, + data->invocation); - for (l = contacts; l != NULL; l = l->next) - e_book_backend_notify_update (e_data_book_get_backend (book), l->data); + while (contacts != NULL) { + EContact *contact = E_CONTACT (contacts->data); + e_book_backend_notify_update (backend, contact); + contacts = g_slist_next ((GSList *) contacts); + } - e_book_backend_notify_complete (e_data_book_get_backend (book)); + e_book_backend_notify_complete (backend); + } else { + data_book_convert_to_client_error (error); + g_dbus_method_invocation_take_error ( + data->invocation, error); } + + op_unref (data); } void @@ -1154,26 +1288,38 @@ e_data_book_respond_remove_contacts (EDataBook *book, GError *error, const GSList *ids) { + OperationData *data; + g_return_if_fail (E_IS_DATA_BOOK (book)); - op_complete (book, opid); + data = op_claim (book, opid); + g_return_if_fail (data != NULL); /* Translators: This is prefix to a detailed error message */ g_prefix_error (&error, "%s", _("Cannot remove contacts: ")); - e_gdbus_book_emit_remove_contacts_done (book->priv->dbus_interface, opid, error); + if (error == NULL) { + EBookBackend *backend; - if (error) { - g_error_free (error); - } else { - const GSList *ii; + backend = e_data_book_get_backend (book); + + e_dbus_address_book_complete_remove_contacts ( + book->priv->dbus_interface, + data->invocation); - for (ii = ids; ii; ii = ii->next) - e_book_backend_notify_remove (e_data_book_get_backend (book), ii->data); + while (ids != NULL) { + e_book_backend_notify_remove (backend, ids->data); + ids = g_slist_next ((GSList *) ids); + } - e_book_backend_notify_complete (e_data_book_get_backend (book)); + e_book_backend_notify_complete (backend); + } else { + data_book_convert_to_client_error (error); + g_dbus_method_invocation_take_error ( + data->invocation, error); } + op_unref (data); } /** @@ -1190,7 +1336,7 @@ e_data_book_report_error (EDataBook *book, g_return_if_fail (E_IS_DATA_BOOK (book)); g_return_if_fail (message != NULL); - e_gdbus_book_emit_backend_error (book->priv->dbus_interface, message); + e_dbus_address_book_emit_error (book->priv->dbus_interface, message); } /** @@ -1199,6 +1345,8 @@ e_data_book_report_error (EDataBook *book, * FIXME: Document me. * * Since: 3.2 + * + * Deprecated: 3.8: Use e_book_backend_set_writable() instead. **/ void e_data_book_report_readonly (EDataBook *book, @@ -1206,7 +1354,7 @@ e_data_book_report_readonly (EDataBook *book, { g_return_if_fail (E_IS_DATA_BOOK (book)); - e_gdbus_book_emit_readonly (book->priv->dbus_interface, readonly); + e_book_backend_set_writable (book->priv->backend, !readonly); } /** @@ -1215,6 +1363,8 @@ e_data_book_report_readonly (EDataBook *book, * FIXME: Document me. * * Since: 3.2 + * + * Deprecated: 3.8: Use e_backend_set_online() instead. **/ void e_data_book_report_online (EDataBook *book, @@ -1222,7 +1372,7 @@ e_data_book_report_online (EDataBook *book, { g_return_if_fail (E_IS_DATA_BOOK (book)); - e_gdbus_book_emit_online (book->priv->dbus_interface, is_online); + e_backend_set_online (E_BACKEND (book->priv->backend), is_online); } /** @@ -1256,21 +1406,42 @@ e_data_book_report_backend_property_changed (EDataBook *book, const gchar *prop_name, const gchar *prop_value) { + EDBusAddressBook *dbus_interface; gchar **strv; - /* Notifies client about certain property value change */ - g_return_if_fail (E_IS_DATA_BOOK (book)); g_return_if_fail (prop_name != NULL); - g_return_if_fail (*prop_name != '\0'); - g_return_if_fail (prop_value != NULL); - strv = e_gdbus_templates_encode_two_strings (prop_name, prop_value); - g_return_if_fail (strv != NULL); + if (prop_value == NULL) + prop_value = ""; + + dbus_interface = book->priv->dbus_interface; + + if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_CAPABILITIES)) { + strv = g_strsplit (prop_value, ",", -1); + e_dbus_address_book_set_capabilities ( + dbus_interface, (const gchar * const *) strv); + g_strfreev (strv); + } + + if (g_str_equal (prop_name, CLIENT_BACKEND_PROPERTY_REVISION)) + e_dbus_address_book_set_revision (dbus_interface, prop_value); - e_gdbus_book_emit_backend_property_changed (book->priv->dbus_interface, (const gchar * const *) strv); + if (g_str_equal (prop_name, BOOK_BACKEND_PROPERTY_REQUIRED_FIELDS)) { + strv = g_strsplit (prop_value, ",", -1); + e_dbus_address_book_set_required_fields ( + dbus_interface, (const gchar * const *) strv); + g_strfreev (strv); + } + + if (g_str_equal (prop_name, BOOK_BACKEND_PROPERTY_SUPPORTED_FIELDS)) { + strv = g_strsplit (prop_value, ",", -1); + e_dbus_address_book_set_supported_fields ( + dbus_interface, (const gchar * const *) strv); + g_strfreev (strv); + } - g_strfreev (strv); + /* Disregard anything else. */ } static void @@ -1415,6 +1586,63 @@ data_book_finalize (GObject *object) G_OBJECT_CLASS (e_data_book_parent_class)->finalize (object); } +static void +data_book_constructed (GObject *object) +{ + EDataBook *book = E_DATA_BOOK (object); + OperationData *op; + + /* Chain up to parent's constructed() method. */ + G_OBJECT_CLASS (e_data_book_parent_class)->constructed (object); + + g_object_bind_property ( + book->priv->backend, "cache-dir", + book->priv->dbus_interface, "cache-dir", + G_BINDING_SYNC_CREATE); + + g_object_bind_property ( + book->priv->backend, "online", + book->priv->dbus_interface, "online", + G_BINDING_SYNC_CREATE); + + g_object_bind_property ( + book->priv->backend, "writable", + book->priv->dbus_interface, "writable", + G_BINDING_SYNC_CREATE); + + /* XXX Initialize the rest of the properties by faking client + * requests. At present it's the only way to fish values + * from EBookBackend's antiquated API. */ + + op = op_new (OP_GET_BACKEND_PROPERTY, book, NULL); + op->d.prop_name = CLIENT_BACKEND_PROPERTY_CAPABILITIES; + e_book_backend_get_backend_property ( + book->priv->backend, book, op->id, + op->cancellable, op->d.prop_name); + op_unref (op); + + op = op_new (OP_GET_BACKEND_PROPERTY, book, NULL); + op->d.prop_name = CLIENT_BACKEND_PROPERTY_REVISION; + e_book_backend_get_backend_property ( + book->priv->backend, book, op->id, + op->cancellable, op->d.prop_name); + op_unref (op); + + op = op_new (OP_GET_BACKEND_PROPERTY, book, NULL); + op->d.prop_name = BOOK_BACKEND_PROPERTY_REQUIRED_FIELDS; + e_book_backend_get_backend_property ( + book->priv->backend, book, op->id, + op->cancellable, op->d.prop_name); + op_unref (op); + + op = op_new (OP_GET_BACKEND_PROPERTY, book, NULL); + op->d.prop_name = BOOK_BACKEND_PROPERTY_SUPPORTED_FIELDS; + e_book_backend_get_backend_property ( + book->priv->backend, book, op->id, + op->cancellable, op->d.prop_name); + op_unref (op); +} + static gboolean data_book_initable_init (GInitable *initable, GCancellable *cancellable, @@ -1424,8 +1652,8 @@ data_book_initable_init (GInitable *initable, book = E_DATA_BOOK (initable); - return e_gdbus_book_register_object ( - book->priv->dbus_interface, + return g_dbus_interface_skeleton_export ( + G_DBUS_INTERFACE_SKELETON (book->priv->dbus_interface), book->priv->connection, book->priv->object_path, error); @@ -1443,6 +1671,7 @@ e_data_book_class_init (EDataBookClass *class) object_class->get_property = data_book_get_property; object_class->dispose = data_book_dispose; object_class->finalize = data_book_finalize; + object_class->constructed = data_book_constructed; g_object_class_install_property ( object_class, @@ -1495,11 +1724,13 @@ e_data_book_initable_init (GInitableIface *interface) static void e_data_book_init (EDataBook *ebook) { - EGdbusBook *dbus_interface; + EDBusAddressBook *dbus_interface; ebook->priv = E_DATA_BOOK_GET_PRIVATE (ebook); - ebook->priv->dbus_interface = e_gdbus_book_stub_new (); + dbus_interface = e_dbus_address_book_skeleton_new (); + ebook->priv->dbus_interface = dbus_interface; + ebook->priv->pending_ops = g_hash_table_new_full ( (GHashFunc) g_direct_hash, (GEqualFunc) g_direct_equal, @@ -1509,7 +1740,6 @@ e_data_book_init (EDataBook *ebook) g_mutex_init (&ebook->priv->open_lock); - dbus_interface = ebook->priv->dbus_interface; g_signal_connect ( dbus_interface, "handle-open", G_CALLBACK (data_book_handle_open_cb), ebook); @@ -1526,8 +1756,8 @@ e_data_book_init (EDataBook *ebook) dbus_interface, "handle-get-contact-list-uids", G_CALLBACK (data_book_handle_get_contact_list_uids_cb), ebook); g_signal_connect ( - dbus_interface, "handle-add-contacts", - G_CALLBACK (data_book_handle_add_contacts_cb), ebook); + dbus_interface, "handle-create-contacts", + G_CALLBACK (data_book_handle_create_contacts_cb), ebook); g_signal_connect ( dbus_interface, "handle-modify-contacts", G_CALLBACK (data_book_handle_modify_contacts_cb), ebook); @@ -1535,9 +1765,6 @@ e_data_book_init (EDataBook *ebook) dbus_interface, "handle-remove-contacts", G_CALLBACK (data_book_handle_remove_contacts_cb), ebook); g_signal_connect ( - dbus_interface, "handle-get-backend-property", - G_CALLBACK (data_book_handle_get_backend_property_cb), ebook); - g_signal_connect ( dbus_interface, "handle-get-view", G_CALLBACK (data_book_handle_get_view_cb), ebook); g_signal_connect ( diff --git a/addressbook/libedata-book/e-data-book.h b/addressbook/libedata-book/e-data-book.h index a1b7b7a..7417a9f 100644 --- a/addressbook/libedata-book/e-data-book.h +++ b/addressbook/libedata-book/e-data-book.h @@ -195,10 +195,6 @@ void e_data_book_respond_get_contact_list_uids void e_data_book_report_error (EDataBook *book, const gchar *message); -void e_data_book_report_readonly (EDataBook *book, - gboolean readonly); -void e_data_book_report_online (EDataBook *book, - gboolean is_online); void e_data_book_report_backend_property_changed (EDataBook *book, const gchar *prop_name, @@ -214,6 +210,10 @@ void e_data_book_respond_set_backend_property GError *error); void e_data_book_report_opened (EDataBook *book, const GError *error); +void e_data_book_report_readonly (EDataBook *book, + gboolean readonly); +void e_data_book_report_online (EDataBook *book, + gboolean is_online); #endif /* EDS_DISABLE_DEPRECATED */ G_END_DECLS diff --git a/addressbook/libegdbus/Makefile.am b/addressbook/libegdbus/Makefile.am index 7584a27..6f75cfe 100644 --- a/addressbook/libegdbus/Makefile.am +++ b/addressbook/libegdbus/Makefile.am @@ -11,8 +11,6 @@ libegdbus_book_la_CPPFLAGS = \ $(NULL) libegdbus_book_la_SOURCES = \ - e-gdbus-book.h \ - e-gdbus-book.c \ e-gdbus-book-view.h \ e-gdbus-book-view.c diff --git a/addressbook/libegdbus/e-gdbus-book.c b/addressbook/libegdbus/e-gdbus-book.c deleted file mode 100644 index 2c66074..0000000 --- a/addressbook/libegdbus/e-gdbus-book.c +++ /dev/null @@ -1,1462 +0,0 @@ -/* - * e-gdbus-book.c - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) version 3. - * - * 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with the program; if not, see - * - * - * Copyright (C) 2011 Red Hat, Inc. (www.redhat.com) - * - */ - -#include -#include - -#include "e-gdbus-book.h" - -#define E_GDBUS_BOOK_PROXY_GET_PRIVATE(obj) \ - (G_TYPE_INSTANCE_GET_PRIVATE \ - ((obj), E_TYPE_GDBUS_BOOK_PROXY, EGdbusBookProxyPrivate)) - -#define GDBUS_BOOK_INTERFACE_NAME "org.gnome.evolution.dataserver.AddressBook" - -typedef EGdbusBookIface EGdbusBookInterface; -G_DEFINE_INTERFACE (EGdbusBook, e_gdbus_book, G_TYPE_OBJECT); - -enum -{ - _0_SIGNAL, - __BACKEND_ERROR_SIGNAL, - __READONLY_SIGNAL, - __ONLINE_SIGNAL, - __OPENED_SIGNAL, - __BACKEND_PROPERTY_CHANGED_SIGNAL, - __OPEN_METHOD, - __OPEN_DONE_SIGNAL, - __REMOVE_DONE_SIGNAL, - __REFRESH_METHOD, - __REFRESH_DONE_SIGNAL, - __GET_CONTACT_METHOD, - __GET_CONTACT_DONE_SIGNAL, - __GET_CONTACT_LIST_METHOD, - __GET_CONTACT_LIST_DONE_SIGNAL, - __GET_CONTACT_LIST_UIDS_METHOD, - __GET_CONTACT_LIST_UIDS_DONE_SIGNAL, - __ADD_CONTACTS_METHOD, - __ADD_CONTACTS_DONE_SIGNAL, - __REMOVE_CONTACTS_METHOD, - __REMOVE_CONTACTS_DONE_SIGNAL, - __MODIFY_CONTACTS_METHOD, - __MODIFY_CONTACTS_DONE_SIGNAL, - __GET_BACKEND_PROPERTY_METHOD, - __GET_BACKEND_PROPERTY_DONE_SIGNAL, - __SET_BACKEND_PROPERTY_METHOD, - __SET_BACKEND_PROPERTY_DONE_SIGNAL, - __GET_VIEW_METHOD, - __GET_VIEW_DONE_SIGNAL, - __CANCEL_OPERATION_METHOD, - __CANCEL_ALL_METHOD, - __CLOSE_METHOD, - __LAST_SIGNAL -}; - -static guint signals[__LAST_SIGNAL] = {0}; - -struct _EGdbusBookProxyPrivate -{ - GHashTable *pending_ops; -}; - -/* ------------------------------------------------------------------------- */ - -/* Various lookup tables */ - -static GHashTable *_method_name_to_id = NULL; -static GHashTable *_method_name_to_type = NULL; -static GHashTable *_signal_name_to_id = NULL; -static GHashTable *_signal_name_to_type = NULL; - -static guint -lookup_method_id_from_method_name (const gchar *method_name) -{ - return GPOINTER_TO_UINT (g_hash_table_lookup (_method_name_to_id, method_name)); -} - -static guint -lookup_method_type_from_method_name (const gchar *method_name) -{ - return GPOINTER_TO_UINT (g_hash_table_lookup (_method_name_to_type, method_name)); -} - -static guint -lookup_signal_id_from_signal_name (const gchar *signal_name) -{ - return GPOINTER_TO_UINT (g_hash_table_lookup (_signal_name_to_id, signal_name)); -} - -static guint -lookup_signal_type_from_signal_name (const gchar *signal_name) -{ - return GPOINTER_TO_UINT (g_hash_table_lookup (_signal_name_to_type, signal_name)); -} - -/* ------------------------------------------------------------------------- */ - -E_DECLARE_GDBUS_SIGNAL_EMISSION_HOOK_STRING (GDBUS_BOOK_INTERFACE_NAME, - backend_error) -E_DECLARE_GDBUS_SIGNAL_EMISSION_HOOK_BOOLEAN (GDBUS_BOOK_INTERFACE_NAME, - readonly) -E_DECLARE_GDBUS_SIGNAL_EMISSION_HOOK_BOOLEAN (GDBUS_BOOK_INTERFACE_NAME, - online) -E_DECLARE_GDBUS_SIGNAL_EMISSION_HOOK_STRV (GDBUS_BOOK_INTERFACE_NAME, - opened) -E_DECLARE_GDBUS_SIGNAL_EMISSION_HOOK_STRV (GDBUS_BOOK_INTERFACE_NAME, - backend_property_changed) - -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_VOID (GDBUS_BOOK_INTERFACE_NAME, - open) -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_VOID (GDBUS_BOOK_INTERFACE_NAME, - refresh) -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_STRING (GDBUS_BOOK_INTERFACE_NAME, - get_contact) -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_STRV (GDBUS_BOOK_INTERFACE_NAME, - get_contact_list) -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_STRV (GDBUS_BOOK_INTERFACE_NAME, - get_contact_list_uids) -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_STRV (GDBUS_BOOK_INTERFACE_NAME, - add_contacts) -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_VOID (GDBUS_BOOK_INTERFACE_NAME, - remove_contacts) -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_VOID (GDBUS_BOOK_INTERFACE_NAME, - modify_contacts) -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_STRING (GDBUS_BOOK_INTERFACE_NAME, - get_backend_property) -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_VOID (GDBUS_BOOK_INTERFACE_NAME, - set_backend_property) -E_DECLARE_GDBUS_METHOD_DONE_EMISSION_HOOK_ASYNC_STRING (GDBUS_BOOK_INTERFACE_NAME, - get_view) - -static void -e_gdbus_book_default_init (EGdbusBookIface *iface) -{ - /* Build lookup structures */ - _method_name_to_id = g_hash_table_new (g_str_hash, g_str_equal); - _method_name_to_type = g_hash_table_new (g_str_hash, g_str_equal); - _signal_name_to_id = g_hash_table_new (g_str_hash, g_str_equal); - _signal_name_to_type = g_hash_table_new (g_str_hash, g_str_equal); - - /* GObject signals definitions for D-Bus signals: */ - E_INIT_GDBUS_SIGNAL_STRING ( - EGdbusBookIface, - "backend_error", - backend_error, - __BACKEND_ERROR_SIGNAL) - E_INIT_GDBUS_SIGNAL_BOOLEAN ( - EGdbusBookIface, - "readonly", - readonly, - __READONLY_SIGNAL) - E_INIT_GDBUS_SIGNAL_BOOLEAN ( - EGdbusBookIface, - "online", - online, - __ONLINE_SIGNAL) - E_INIT_GDBUS_SIGNAL_STRV ( - EGdbusBookIface, - "opened", - opened, - __OPENED_SIGNAL) - E_INIT_GDBUS_SIGNAL_STRV ( - EGdbusBookIface, - "backend_property_changed", - backend_property_changed, - __BACKEND_PROPERTY_CHANGED_SIGNAL) - - /* GObject signals definitions for D-Bus methods: */ - E_INIT_GDBUS_METHOD_ASYNC_BOOLEAN__VOID ( - EGdbusBookIface, - "open", - open, - __OPEN_METHOD, - __OPEN_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_ASYNC_VOID__VOID ( - EGdbusBookIface, - "refresh", - refresh, - __REFRESH_METHOD, - __REFRESH_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_ASYNC_STRING__STRING ( - EGdbusBookIface, - "get_contact", - get_contact, - __GET_CONTACT_METHOD, - __GET_CONTACT_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_ASYNC_STRING__STRV ( - EGdbusBookIface, - "get_contact_list", - get_contact_list, - __GET_CONTACT_LIST_METHOD, - __GET_CONTACT_LIST_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_ASYNC_STRING__STRV ( - EGdbusBookIface, - "get_contact_list_uids", - get_contact_list_uids, - __GET_CONTACT_LIST_UIDS_METHOD, - __GET_CONTACT_LIST_UIDS_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_ASYNC_STRV__STRV ( - EGdbusBookIface, - "add_contacts", - add_contacts, - __ADD_CONTACTS_METHOD, - __ADD_CONTACTS_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_ASYNC_STRV__VOID ( - EGdbusBookIface, - "remove_contacts", - remove_contacts, - __REMOVE_CONTACTS_METHOD, - __REMOVE_CONTACTS_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_ASYNC_STRV__VOID ( - EGdbusBookIface, - "modify_contacts", - modify_contacts, - __MODIFY_CONTACTS_METHOD, - __MODIFY_CONTACTS_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_ASYNC_STRING__STRING ( - EGdbusBookIface, - "get_backend_property", - get_backend_property, - __GET_BACKEND_PROPERTY_METHOD, - __GET_BACKEND_PROPERTY_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_ASYNC_STRV__VOID ( - EGdbusBookIface, - "set_backend_property", - set_backend_property, - __SET_BACKEND_PROPERTY_METHOD, - __SET_BACKEND_PROPERTY_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_ASYNC_STRING__STRING ( - EGdbusBookIface, - "get_view", - get_view, - __GET_VIEW_METHOD, - __GET_VIEW_DONE_SIGNAL) - E_INIT_GDBUS_METHOD_UINT ( - EGdbusBookIface, - "cancel_operation", - cancel_operation, - __CANCEL_OPERATION_METHOD) - E_INIT_GDBUS_METHOD_VOID ( - EGdbusBookIface, - "cancel_all", - cancel_all, - __CANCEL_ALL_METHOD) - E_INIT_GDBUS_METHOD_VOID ( - EGdbusBookIface, - "close", - close, - __CLOSE_METHOD) -} - -void -e_gdbus_book_call_open (GDBusProxy *proxy, - gboolean in_only_if_exists, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_boolean ("open", e_gdbus_book_call_open, E_GDBUS_ASYNC_OP_KEEPER (proxy), in_only_if_exists, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_open_finish (GDBusProxy *proxy, - GAsyncResult *result, - GError **error) -{ - return e_gdbus_proxy_finish_call_void (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, error, e_gdbus_book_call_open); -} - -gboolean -e_gdbus_book_call_open_sync (GDBusProxy *proxy, - gboolean in_only_if_exists, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_boolean__void ( - proxy, in_only_if_exists, cancellable, error, - e_gdbus_book_call_open, - e_gdbus_book_call_open_finish); -} - -void -e_gdbus_book_call_refresh (GDBusProxy *proxy, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_void ("refresh", e_gdbus_book_call_refresh, E_GDBUS_ASYNC_OP_KEEPER (proxy), cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_refresh_finish (GDBusProxy *proxy, - GAsyncResult *result, - GError **error) -{ - return e_gdbus_proxy_finish_call_void (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, error, e_gdbus_book_call_refresh); -} - -gboolean -e_gdbus_book_call_refresh_sync (GDBusProxy *proxy, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_void__void ( - proxy, cancellable, error, - e_gdbus_book_call_refresh, - e_gdbus_book_call_refresh_finish); -} - -void -e_gdbus_book_call_get_contact (GDBusProxy *proxy, - const gchar *in_uid, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_string ("get_contact", e_gdbus_book_call_get_contact, E_GDBUS_ASYNC_OP_KEEPER (proxy), in_uid, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_get_contact_finish (GDBusProxy *proxy, - GAsyncResult *result, - gchar **out_vcard, - GError **error) -{ - return e_gdbus_proxy_finish_call_string (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, out_vcard, error, e_gdbus_book_call_get_contact); -} - -gboolean -e_gdbus_book_call_get_contact_sync (GDBusProxy *proxy, - const gchar *in_uid, - gchar **out_vcard, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_string__string ( - proxy, in_uid, out_vcard, cancellable, error, - e_gdbus_book_call_get_contact, - e_gdbus_book_call_get_contact_finish); -} - -void -e_gdbus_book_call_get_contact_list (GDBusProxy *proxy, - const gchar *in_query, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_string ("get_contact_list", e_gdbus_book_call_get_contact_list, E_GDBUS_ASYNC_OP_KEEPER (proxy), in_query, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_get_contact_list_finish (GDBusProxy *proxy, - GAsyncResult *result, - gchar ***out_vcards, - GError **error) -{ - return e_gdbus_proxy_finish_call_strv (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, out_vcards, error, e_gdbus_book_call_get_contact_list); -} - -gboolean -e_gdbus_book_call_get_contact_list_sync (GDBusProxy *proxy, - const gchar *in_query, - gchar ***out_vcards, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_string__strv ( - proxy, in_query, out_vcards, cancellable, error, - e_gdbus_book_call_get_contact_list, - e_gdbus_book_call_get_contact_list_finish); -} - -void -e_gdbus_book_call_get_contact_list_uids (GDBusProxy *proxy, - const gchar *in_query, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_string ("get_contact_list_uids", e_gdbus_book_call_get_contact_list_uids, E_GDBUS_ASYNC_OP_KEEPER (proxy), in_query, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_get_contact_list_uids_finish (GDBusProxy *proxy, - GAsyncResult *result, - gchar ***out_uids, - GError **error) -{ - return e_gdbus_proxy_finish_call_strv (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, out_uids, error, e_gdbus_book_call_get_contact_list_uids); -} - -gboolean -e_gdbus_book_call_get_contact_list_uids_sync (GDBusProxy *proxy, - const gchar *in_query, - gchar ***out_uids, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_string__strv ( - proxy, in_query, out_uids, cancellable, error, - e_gdbus_book_call_get_contact_list_uids, - e_gdbus_book_call_get_contact_list_uids_finish); -} - -void -e_gdbus_book_call_add_contacts (GDBusProxy *proxy, - const gchar * const *in_vcards, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_strv ("add_contacts", e_gdbus_book_call_add_contacts, E_GDBUS_ASYNC_OP_KEEPER (proxy), in_vcards, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_add_contacts_finish (GDBusProxy *proxy, - GAsyncResult *result, - gchar ***out_uids, - GError **error) -{ - return e_gdbus_proxy_finish_call_strv (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, out_uids, error, e_gdbus_book_call_add_contacts); -} - -gboolean -e_gdbus_book_call_add_contacts_sync (GDBusProxy *proxy, - const gchar * const *in_vcards, - gchar ***out_uids, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_strv__strv ( - proxy, in_vcards, out_uids, cancellable, error, - e_gdbus_book_call_add_contacts, - e_gdbus_book_call_add_contacts_finish); -} - -void -e_gdbus_book_call_remove_contacts (GDBusProxy *proxy, - const gchar * const *in_list, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_strv ("remove_contacts", e_gdbus_book_call_remove_contacts, E_GDBUS_ASYNC_OP_KEEPER (proxy), in_list, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_remove_contacts_finish (GDBusProxy *proxy, - GAsyncResult *result, - GError **error) -{ - return e_gdbus_proxy_finish_call_void (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, error, e_gdbus_book_call_remove_contacts); -} - -gboolean -e_gdbus_book_call_remove_contacts_sync (GDBusProxy *proxy, - const gchar * const *in_list, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_strv__void ( - proxy, in_list, cancellable, error, - e_gdbus_book_call_remove_contacts, - e_gdbus_book_call_remove_contacts_finish); -} - -void -e_gdbus_book_call_modify_contacts (GDBusProxy *proxy, - const gchar * const *in_vcards, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_strv ("modify_contacts", e_gdbus_book_call_modify_contacts, E_GDBUS_ASYNC_OP_KEEPER (proxy), in_vcards, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_modify_contacts_finish (GDBusProxy *proxy, - GAsyncResult *result, - GError **error) -{ - return e_gdbus_proxy_finish_call_void (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, error, e_gdbus_book_call_modify_contacts); -} - -gboolean -e_gdbus_book_call_modify_contacts_sync (GDBusProxy *proxy, - const gchar * const *in_vcards, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_strv__void ( - proxy, in_vcards, cancellable, error, - e_gdbus_book_call_modify_contacts, - e_gdbus_book_call_modify_contacts_finish); -} - -void -e_gdbus_book_call_get_backend_property (GDBusProxy *proxy, - const gchar *in_prop_name, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_string ("get_backend_property", e_gdbus_book_call_get_backend_property, E_GDBUS_ASYNC_OP_KEEPER (proxy), in_prop_name, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_get_backend_property_finish (GDBusProxy *proxy, - GAsyncResult *result, - gchar **out_prop_value, - GError **error) -{ - return e_gdbus_proxy_finish_call_string (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, out_prop_value, error, e_gdbus_book_call_get_backend_property); -} - -gboolean -e_gdbus_book_call_get_backend_property_sync (GDBusProxy *proxy, - const gchar *in_prop_name, - gchar **out_prop_value, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_string__string ( - proxy, in_prop_name, out_prop_value, cancellable, error, - e_gdbus_book_call_get_backend_property, - e_gdbus_book_call_get_backend_property_finish); -} - -/* free returned pointer with g_strfreev() */ -gchar ** -e_gdbus_book_encode_set_backend_property (const gchar *in_prop_name, - const gchar *in_prop_value) -{ - return e_gdbus_templates_encode_two_strings (in_prop_name, in_prop_value); -} - -/* free out_prop_name and out_prop_value with g_free() */ -gboolean -e_gdbus_book_decode_set_backend_property (const gchar * const *in_strv, - gchar **out_prop_name, - gchar **out_prop_value) -{ - return e_gdbus_templates_decode_two_strings (in_strv, out_prop_name, out_prop_value); -} - -void -e_gdbus_book_call_set_backend_property (GDBusProxy *proxy, - const gchar * const *in_prop_name_value, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_strv ("set_backend_property", e_gdbus_book_call_set_backend_property, E_GDBUS_ASYNC_OP_KEEPER (proxy), in_prop_name_value, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_set_backend_property_finish (GDBusProxy *proxy, - GAsyncResult *result, - GError **error) -{ - return e_gdbus_proxy_finish_call_void (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, error, e_gdbus_book_call_set_backend_property); -} - -gboolean -e_gdbus_book_call_set_backend_property_sync (GDBusProxy *proxy, - const gchar * const *in_prop_name_value, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_strv__void ( - proxy, in_prop_name_value, cancellable, error, - e_gdbus_book_call_set_backend_property, - e_gdbus_book_call_set_backend_property_finish); -} - -void -e_gdbus_book_call_get_view (GDBusProxy *proxy, - const gchar *in_query, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_call_string ("get_view", e_gdbus_book_call_get_view, E_GDBUS_ASYNC_OP_KEEPER (proxy), in_query, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_get_view_finish (GDBusProxy *proxy, - GAsyncResult *result, - gchar **out_view_path, - GError **error) -{ - return e_gdbus_proxy_finish_call_string (E_GDBUS_ASYNC_OP_KEEPER (proxy), result, out_view_path, error, e_gdbus_book_call_get_view); -} - -gboolean -e_gdbus_book_call_get_view_sync (GDBusProxy *proxy, - const gchar *in_query, - gchar **out_view_path, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_call_sync_string__string ( - proxy, in_query, out_view_path, cancellable, error, - e_gdbus_book_call_get_view, - e_gdbus_book_call_get_view_finish); -} - -void -e_gdbus_book_call_cancel_operation (GDBusProxy *proxy, - guint in_opid, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_method_call_uint ("cancel_operation", proxy, in_opid, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_cancel_operation_finish (GDBusProxy *proxy, - GAsyncResult *result, - GError **error) -{ - return e_gdbus_proxy_method_call_finish_void (proxy, result, error); -} - -gboolean -e_gdbus_book_call_cancel_operation_sync (GDBusProxy *proxy, - guint in_opid, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_method_call_sync_uint__void ("cancel_operation", proxy, in_opid, cancellable, error); -} - -void -e_gdbus_book_call_cancel_all (GDBusProxy *proxy, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_method_call_void ("cancel_all", proxy, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_cancel_all_finish (GDBusProxy *proxy, - GAsyncResult *result, - GError **error) -{ - return e_gdbus_proxy_method_call_finish_void (proxy, result, error); -} - -gboolean -e_gdbus_book_call_cancel_all_sync (GDBusProxy *proxy, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_method_call_sync_void__void ("cancel_all", proxy, cancellable, error); -} - -void -e_gdbus_book_call_close (GDBusProxy *proxy, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - e_gdbus_proxy_method_call_void ("close", proxy, cancellable, callback, user_data); -} - -gboolean -e_gdbus_book_call_close_finish (GDBusProxy *proxy, - GAsyncResult *result, - GError **error) -{ - return e_gdbus_proxy_method_call_finish_void (proxy, result, error); -} - -gboolean -e_gdbus_book_call_close_sync (GDBusProxy *proxy, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_proxy_method_call_sync_void__void ("close", proxy, cancellable, error); -} - -#define DECLARE_EMIT_DONE_SIGNAL_0(_mname, _sig_id) \ -void \ -e_gdbus_book_emit_ ## _mname ## _done (EGdbusBook *object, guint arg_opid, const GError *arg_error) \ -{ \ - g_signal_emit (object, signals[_sig_id], 0, arg_opid, arg_error); \ -} - -#define DECLARE_EMIT_DONE_SIGNAL_1(_mname, _sig_id, _par_type) \ -void \ -e_gdbus_book_emit_ ## _mname ## _done (EGdbusBook *object, guint arg_opid, const GError *arg_error, _par_type out_par) \ -{ \ - g_signal_emit (object, signals[_sig_id], 0, arg_opid, arg_error, out_par); \ -} - -DECLARE_EMIT_DONE_SIGNAL_0 (open, - __OPEN_DONE_SIGNAL) -DECLARE_EMIT_DONE_SIGNAL_0 (refresh, - __REFRESH_DONE_SIGNAL) -DECLARE_EMIT_DONE_SIGNAL_1 (get_contact, - __GET_CONTACT_DONE_SIGNAL, - const gchar *) -DECLARE_EMIT_DONE_SIGNAL_1 (get_contact_list, - __GET_CONTACT_LIST_DONE_SIGNAL, - const gchar * const *) -DECLARE_EMIT_DONE_SIGNAL_1 (get_contact_list_uids, - __GET_CONTACT_LIST_UIDS_DONE_SIGNAL, - const gchar * const *) -DECLARE_EMIT_DONE_SIGNAL_1 (add_contacts, - __ADD_CONTACTS_DONE_SIGNAL, - const gchar * const *) -DECLARE_EMIT_DONE_SIGNAL_0 (remove_contacts, - __REMOVE_CONTACTS_DONE_SIGNAL) -DECLARE_EMIT_DONE_SIGNAL_0 (modify_contacts, - __MODIFY_CONTACTS_DONE_SIGNAL) -DECLARE_EMIT_DONE_SIGNAL_1 (get_backend_property, - __GET_BACKEND_PROPERTY_DONE_SIGNAL, - const gchar *) -DECLARE_EMIT_DONE_SIGNAL_0 (set_backend_property, - __SET_BACKEND_PROPERTY_DONE_SIGNAL) -DECLARE_EMIT_DONE_SIGNAL_1 (get_view, - __GET_VIEW_DONE_SIGNAL, - const gchar *) - -void -e_gdbus_book_emit_backend_error (EGdbusBook *object, - const gchar *arg_message) -{ - g_return_if_fail (object != NULL); - g_return_if_fail (arg_message != NULL); - - g_signal_emit (object, signals[__BACKEND_ERROR_SIGNAL], 0, arg_message); -} - -void -e_gdbus_book_emit_readonly (EGdbusBook *object, - gboolean arg_is_readonly) -{ - g_signal_emit (object, signals[__READONLY_SIGNAL], 0, arg_is_readonly); -} - -void -e_gdbus_book_emit_online (EGdbusBook *object, - gboolean arg_is_online) -{ - g_signal_emit (object, signals[__ONLINE_SIGNAL], 0, arg_is_online); -} - -void -e_gdbus_book_emit_opened (EGdbusBook *object, - const gchar * const *arg_error) -{ - g_signal_emit (object, signals[__OPENED_SIGNAL], 0, arg_error); -} - -void -e_gdbus_book_emit_backend_property_changed (EGdbusBook *object, - const gchar * const *arg_name_value) -{ - g_signal_emit (object, signals[__BACKEND_PROPERTY_CHANGED_SIGNAL], 0, arg_name_value); -} - -E_DECLARE_GDBUS_NOTIFY_SIGNAL_1 (book, - backend_error, - message, - "s") -E_DECLARE_GDBUS_NOTIFY_SIGNAL_1 (book, - readonly, - is_readonly, - "b") -E_DECLARE_GDBUS_NOTIFY_SIGNAL_1 (book, - online, - is_online, - "b") -E_DECLARE_GDBUS_NOTIFY_SIGNAL_1 (book, - opened, - error, - "as") -E_DECLARE_GDBUS_NOTIFY_SIGNAL_1 (book, - backend_property_changed, - name_value, - "as") - -E_DECLARE_GDBUS_ASYNC_METHOD_1 (book, - open, - only_if_exists, - "b") -E_DECLARE_GDBUS_ASYNC_METHOD_0 (book, - refresh) -E_DECLARE_GDBUS_ASYNC_METHOD_1_WITH_RETURN (book, - get_contact, - uid, - "s", - vcard, - "s") -E_DECLARE_GDBUS_ASYNC_METHOD_1_WITH_RETURN (book, - get_contact_list, - query, - "s", - vcards, - "as") -E_DECLARE_GDBUS_ASYNC_METHOD_1_WITH_RETURN (book, - get_contact_list_uids, - query, - "s", - uids, - "as") -E_DECLARE_GDBUS_ASYNC_METHOD_1_WITH_RETURN (book, - add_contacts, - vcards, - "as", - uids, - "as") -E_DECLARE_GDBUS_ASYNC_METHOD_1 (book, - remove_contacts, - list, - "as") -E_DECLARE_GDBUS_ASYNC_METHOD_1 (book, - modify_contacts, - vcard, - "as") -E_DECLARE_GDBUS_ASYNC_METHOD_1_WITH_RETURN (book, - get_backend_property, - prop_name, - "s", - prop_value, - "s") -E_DECLARE_GDBUS_ASYNC_METHOD_1 (book, - set_backend_property, - prop_name_value, - "as") -E_DECLARE_GDBUS_ASYNC_METHOD_1_WITH_RETURN (book, - get_view, - query, - "s", - view, - "s") - -E_DECLARE_GDBUS_SYNC_METHOD_1 (book, - cancel_operation, - opid, - "u") -E_DECLARE_GDBUS_SYNC_METHOD_0 (book, - cancel_all) -E_DECLARE_GDBUS_SYNC_METHOD_0 (book, - close) - -static const GDBusMethodInfo * const e_gdbus_book_method_info_pointers[] = -{ - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, open), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, refresh), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, get_contact), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, get_contact_list), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, get_contact_list_uids), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, add_contacts), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, remove_contacts), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, modify_contacts), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, get_backend_property), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, set_backend_property), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, get_view), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, cancel_operation), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, cancel_all), - &E_DECLARED_GDBUS_METHOD_INFO_NAME (book, close), - NULL -}; - -static const GDBusSignalInfo * const e_gdbus_book_signal_info_pointers[] = -{ - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, backend_error), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, readonly), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, online), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, opened), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, backend_property_changed), - - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, open_done), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, refresh_done), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, get_contact_done), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, get_contact_list_done), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, get_contact_list_uids_done), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, add_contacts_done), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, remove_contacts_done), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, modify_contacts_done), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, get_backend_property_done), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, set_backend_property_done), - &E_DECLARED_GDBUS_SIGNAL_INFO_NAME (book, get_view_done), - NULL -}; - -static const GDBusInterfaceInfo _e_gdbus_book_interface_info = -{ - -1, - (gchar *) GDBUS_BOOK_INTERFACE_NAME, - (GDBusMethodInfo **) &e_gdbus_book_method_info_pointers, - (GDBusSignalInfo **) &e_gdbus_book_signal_info_pointers, - (GDBusPropertyInfo **) NULL -}; - -static void -handle_method_call (GDBusConnection *connection, - const gchar *sender, - const gchar *object_path, - const gchar *interface_name, - const gchar *method_name, - GVariant *parameters, - GDBusMethodInvocation *invocation, - gpointer user_data) -{ - guint method_id, method_type; - - method_id = lookup_method_id_from_method_name (method_name); - method_type = lookup_method_type_from_method_name (method_name); - - g_return_if_fail (method_id != 0); - g_return_if_fail (method_type != 0); - - e_gdbus_stub_handle_method_call (user_data, invocation, parameters, method_name, signals[method_id], method_type); -} - -static GVariant * -get_property (GDBusConnection *connection, - const gchar *sender, - const gchar *object_path, - const gchar *interface_name, - const gchar *property_name, - GError **error, - gpointer user_data) -{ - g_set_error (error, G_DBUS_ERROR, G_DBUS_ERROR_NOT_SUPPORTED, "This implementation does not support property `%s'", property_name); - return NULL; -} - -static gboolean -set_property (GDBusConnection *connection, - const gchar *sender, - const gchar *object_path, - const gchar *interface_name, - const gchar *property_name, - GVariant *value, - GError **error, - gpointer user_data) -{ - g_set_error (error, G_DBUS_ERROR, G_DBUS_ERROR_NOT_SUPPORTED, "This implementation does not support property `%s'", property_name); - return FALSE; -} - -static const GDBusInterfaceVTable e_gdbus_book_interface_vtable = -{ - handle_method_call, - get_property, - set_property -}; - -static gboolean -emit_notifications_in_idle (gpointer user_data) -{ - GObject *object = G_OBJECT (user_data); - GDBusConnection *connection; - const gchar *path; - GHashTable *notification_queue; - GHashTableIter iter; - const gchar *property_name; - GVariant *value; - GVariantBuilder *builder; - GVariantBuilder *invalidated_builder; - GHashTable *pvc; - gboolean has_changes; - - notification_queue = g_object_get_data (object, "gdbus-codegen-notification-queue"); - path = g_object_get_data (object, "gdbus-codegen-path"); - connection = g_object_get_data (object, "gdbus-codegen-connection"); - pvc = g_object_get_data (object, "gdbus-codegen-pvc"); - g_assert (notification_queue != NULL && path != NULL && connection != NULL && pvc != NULL); - - builder = g_variant_builder_new (G_VARIANT_TYPE_ARRAY); - invalidated_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); - g_hash_table_iter_init (&iter, notification_queue); - has_changes = FALSE; - while (g_hash_table_iter_next (&iter, (gpointer) &property_name, (gpointer) &value)) { - GVariant *cached_value; - cached_value = g_hash_table_lookup (pvc, property_name); - if (cached_value == NULL || !g_variant_equal (cached_value, value)) { - g_hash_table_insert (pvc, (gpointer) property_name, (gpointer) g_variant_ref (value)); - g_variant_builder_add (builder, "{sv}", property_name, value); - has_changes = TRUE; - } - } - - if (has_changes) { - g_dbus_connection_emit_signal ( - connection, NULL, path, "org.freedesktop.DBus.Properties", "PropertiesChanged", - g_variant_new ("(sa{sv}as)", GDBUS_BOOK_INTERFACE_NAME, builder, invalidated_builder), - NULL); - } else { - g_variant_builder_unref (builder); - g_variant_builder_unref (invalidated_builder); - } - - g_hash_table_remove_all (notification_queue); - g_object_set_data (object, "gdbus-codegen-notification-idle-id", GUINT_TO_POINTER (0)); - - return FALSE; -} - -/** - * e_gdbus_book_drain_notify: - * @object: A #EGdbusBook that is exported. - * - * If @object has queued notifications, empty the queue forcing - * the PropertiesChanged signal to be emitted. - * See for more background information. - */ -void -e_gdbus_book_drain_notify (EGdbusBook *object) -{ - gint idle_id; - idle_id = GPOINTER_TO_UINT (g_object_get_data (G_OBJECT (object), "gdbus-codegen-notification-idle-id")); - if (idle_id > 0) { - emit_notifications_in_idle (object); - g_source_remove (idle_id); - } -} - -static void -on_object_unregistered (GObject *object) -{ - gint idle_id; - idle_id = GPOINTER_TO_UINT (g_object_get_data (G_OBJECT (object), "gdbus-codegen-notification-idle-id")); - if (idle_id > 0) { - g_source_remove (idle_id); - } - g_object_set_data (G_OBJECT (object), "gdbus-codegen-path", NULL); - g_object_set_data (G_OBJECT (object), "gdbus-codegen-connection", NULL); -} - -/** - * e_gdbus_book_register_object: - * @object: An instance of a #GObject-derived type implementing the #EGdbusBook interface. - * @connection: A #GDBusConnection. - * @object_path: The object to register the object at. - * @error: Return location for error or %NULL. - * - * Registers @object at @object_path on @connection. - * - * See - * for how properties, methods and signals are handled. - * - * Returns: 0 if @error is set, otherwise a registration id (never 0) that can be used with g_dbus_connection_unregister_object(). - */ -guint -e_gdbus_book_register_object (EGdbusBook *object, - GDBusConnection *connection, - const gchar *object_path, - GError **error) -{ - GHashTable *pvc; - - pvc = g_hash_table_new_full (g_str_hash, g_str_equal, NULL, (GDestroyNotify) g_variant_unref); - - g_object_set_data_full (G_OBJECT (object), "gdbus-codegen-path", (gpointer) g_strdup (object_path), g_free); - g_object_set_data (G_OBJECT (object), "gdbus-codegen-connection", (gpointer) connection); - g_object_set_data_full (G_OBJECT (object), "gdbus-codegen-pvc", (gpointer) pvc, (GDestroyNotify) g_hash_table_unref); - - return g_dbus_connection_register_object ( - connection, object_path, (GDBusInterfaceInfo *) &_e_gdbus_book_interface_info, - &e_gdbus_book_interface_vtable, object, (GDestroyNotify) on_object_unregistered, error); -} - -/** - * e_gdbus_book_interface_info: - * - * Gets interface description for the org.gnome.evolution.dataserver.AddressBook D-Bus interface. - * - * Returns: A #GDBusInterfaceInfo. Do not free, the object is statically allocated. - */ -const GDBusInterfaceInfo * -e_gdbus_book_interface_info (void) -{ - return &_e_gdbus_book_interface_info; -} - -/* ---------------------------------------------------------------------- */ - -static void proxy_iface_init (EGdbusBookIface *iface); -static void async_op_keeper_iface_init (EGdbusAsyncOpKeeperInterface *iface); - -G_DEFINE_TYPE_WITH_CODE (EGdbusBookProxy, e_gdbus_book_proxy, G_TYPE_DBUS_PROXY, - G_IMPLEMENT_INTERFACE (E_TYPE_GDBUS_BOOK, proxy_iface_init) - G_IMPLEMENT_INTERFACE (E_TYPE_GDBUS_ASYNC_OP_KEEPER, async_op_keeper_iface_init)); - -static void -e_gdbus_book_proxy_init (EGdbusBookProxy *proxy) -{ - g_dbus_proxy_set_interface_info (G_DBUS_PROXY (proxy), (GDBusInterfaceInfo *) &_e_gdbus_book_interface_info); - - proxy->priv = E_GDBUS_BOOK_PROXY_GET_PRIVATE (proxy); - proxy->priv->pending_ops = e_gdbus_async_op_keeper_create_pending_ops (E_GDBUS_ASYNC_OP_KEEPER (proxy)); - - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_VOID (open); - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_VOID (refresh); - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_STRING (get_contact); - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_STRV (get_contact_list); - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_STRV (get_contact_list_uids); - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_STRV (add_contacts); - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_VOID (remove_contacts); - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_VOID (modify_contacts); - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_STRING (get_backend_property); - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_VOID (set_backend_property); - E_GDBUS_CONNECT_METHOD_DONE_SIGNAL_STRING (get_view); -} - -static void -g_signal (GDBusProxy *proxy, - const gchar *sender_name, - const gchar *signal_name, - GVariant *parameters) -{ - guint signal_id, signal_type; - - signal_id = lookup_signal_id_from_signal_name (signal_name); - signal_type = lookup_signal_type_from_signal_name (signal_name); - - g_return_if_fail (signal_id != 0); - g_return_if_fail (signal_type != 0); - - e_gdbus_proxy_emit_signal (proxy, parameters, signals[signal_id], signal_type); -} - -static void -gdbus_book_proxy_finalize (GObject *object) -{ - EGdbusBookProxy *proxy = E_GDBUS_BOOK_PROXY (object); - - if (g_hash_table_size (proxy->priv->pending_ops)) - g_debug ("%s: Kept %d items in pending_ops", G_STRFUNC, g_hash_table_size (proxy->priv->pending_ops)); - - g_hash_table_destroy (proxy->priv->pending_ops); - - G_OBJECT_CLASS (e_gdbus_book_proxy_parent_class)->finalize (object); -} - -static void -e_gdbus_book_proxy_class_init (EGdbusBookProxyClass *class) -{ - GObjectClass *object_class; - GDBusProxyClass *proxy_class; - - g_type_class_add_private (class, sizeof (EGdbusBookProxyPrivate)); - - object_class = G_OBJECT_CLASS (class); - object_class->finalize = gdbus_book_proxy_finalize; - - proxy_class = G_DBUS_PROXY_CLASS (class); - proxy_class->g_signal = g_signal; -} - -static void -proxy_iface_init (EGdbusBookIface *iface) -{ -} - -static GHashTable * -gdbus_book_get_pending_ops (EGdbusAsyncOpKeeper *object) -{ - EGdbusBookProxy *proxy; - - g_return_val_if_fail (E_IS_GDBUS_BOOK_PROXY (object), NULL); - - proxy = E_GDBUS_BOOK_PROXY (object); - - return proxy->priv->pending_ops; -} - -static gboolean -gdbus_book_call_cancel_operation_sync (EGdbusAsyncOpKeeper *object, - guint in_opid, - GCancellable *cancellable, - GError **error) -{ - return e_gdbus_book_call_cancel_operation_sync (G_DBUS_PROXY (object), in_opid, cancellable, error); -} - -static void -async_op_keeper_iface_init (EGdbusAsyncOpKeeperInterface *iface) -{ - g_return_if_fail (iface != NULL); - - iface->get_pending_ops = gdbus_book_get_pending_ops; - iface->cancel_op_sync = gdbus_book_call_cancel_operation_sync; -} - -/** - * e_gdbus_book_proxy_new: - * @connection: A #GDBusConnection. - * @flags: Flags used when constructing the proxy. - * @name: A bus name (well-known or unique) or %NULL if @connection is not a message bus connection. - * @object_path: An object path. - * @cancellable: A #GCancellable or %NULL. - * @callback: Callback function to invoke when the proxy is ready. - * @user_data: User data to pass to @callback. - * - * Like g_dbus_proxy_new() but returns a #EGdbusBookProxy. - * - * This is a failable asynchronous constructor - when the proxy is ready, callback will be invoked and you can use e_gdbus_book_proxy_new_finish() to get the result. - */ -void -e_gdbus_book_proxy_new (GDBusConnection *connection, - GDBusProxyFlags flags, - const gchar *name, - const gchar *object_path, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - g_async_initable_new_async ( - E_TYPE_GDBUS_BOOK_PROXY, - G_PRIORITY_DEFAULT, - cancellable, - callback, - user_data, - "g-flags", flags, - "g-name", name, - "g-connection", connection, - "g-object-path", object_path, - "g-interface-name", GDBUS_BOOK_INTERFACE_NAME, - NULL); -} - -/** - * e_gdbus_book_proxy_new_finish: - * @result: A #GAsyncResult obtained from the #GAsyncReadyCallback function passed to e_gdbus_book_proxy_new(). - * @error: Return location for error or %NULL. - * - * Finishes creating a #EGdbusBookProxy. - * - * Returns: A #EGdbusBookProxy or %NULL if @error is set. Free with g_object_unref(). - */ -EGdbusBook * -e_gdbus_book_proxy_new_finish (GAsyncResult *result, - GError **error) -{ - GObject *object; - GObject *source_object; - source_object = g_async_result_get_source_object (result); - g_assert (source_object != NULL); - object = g_async_initable_new_finish (G_ASYNC_INITABLE (source_object), result, error); - g_object_unref (source_object); - - if (object != NULL) - return E_GDBUS_BOOK (object); - else - return NULL; -} - -/** - * e_gdbus_book_proxy_new_sync: - * @connection: A #GDBusConnection. - * @flags: Flags used when constructing the proxy. - * @name: A bus name (well-known or unique) or %NULL if @connection is not a message bus connection. - * @object_path: An object path. - * @cancellable: A #GCancellable or %NULL. - * @error: Return location for error or %NULL. - * - * Like g_dbus_proxy_new_sync() but returns a #EGdbusBookProxy. - * - * This is a synchronous failable constructor. See e_gdbus_book_proxy_new() and e_gdbus_book_proxy_new_finish() for the asynchronous version. - * - * Returns: A #EGdbusBookProxy or %NULL if error is set. Free with g_object_unref(). - */ -EGdbusBook * -e_gdbus_book_proxy_new_sync (GDBusConnection *connection, - GDBusProxyFlags flags, - const gchar *name, - const gchar *object_path, - GCancellable *cancellable, - GError **error) -{ - GInitable *initable; - initable = g_initable_new ( - E_TYPE_GDBUS_BOOK_PROXY, - cancellable, - error, - "g-flags", flags, - "g-name", name, - "g-connection", connection, - "g-object-path", object_path, - "g-interface-name", GDBUS_BOOK_INTERFACE_NAME, - NULL); - if (initable != NULL) - return E_GDBUS_BOOK (initable); - else - return NULL; -} - -/** - * e_gdbus_book_proxy_new_for_bus: - * @bus_type: A #GBusType. - * @flags: Flags used when constructing the proxy. - * @name: A bus name (well-known or unique). - * @object_path: An object path. - * @cancellable: A #GCancellable or %NULL. - * @callback: Callback function to invoke when the proxy is ready. - * @user_data: User data to pass to @callback. - * - * Like g_dbus_proxy_new_for_bus() but returns a #EGdbusBookProxy. - * - * This is a failable asynchronous constructor - when the proxy is ready, callback will be invoked and you can use e_gdbus_book_proxy_new_for_bus_finish() to get the result. - */ -void -e_gdbus_book_proxy_new_for_bus (GBusType bus_type, - GDBusProxyFlags flags, - const gchar *name, - const gchar *object_path, - GCancellable *cancellable, - GAsyncReadyCallback callback, - gpointer user_data) -{ - g_async_initable_new_async ( - E_TYPE_GDBUS_BOOK_PROXY, - G_PRIORITY_DEFAULT, - cancellable, - callback, - user_data, - "g-flags", flags, - "g-name", name, - "g-bus-type", bus_type, - "g-object-path", object_path, - "g-interface-name", GDBUS_BOOK_INTERFACE_NAME, - NULL); -} - -/** - * e_gdbus_book_proxy_new_for_bus_finish: - * @result: A #GAsyncResult obtained from the #GAsyncReadyCallback function passed to e_gdbus_book_proxy_new_for_bus(). - * @error: Return location for error or %NULL. - * - * Finishes creating a #EGdbusBookProxy. - * - * Returns: A #EGdbusBookProxy or %NULL if @error is set. Free with g_object_unref(). - */ -EGdbusBook * -e_gdbus_book_proxy_new_for_bus_finish (GAsyncResult *result, - GError **error) -{ - GObject *object; - GObject *source_object; - source_object = g_async_result_get_source_object (result); - g_assert (source_object != NULL); - object = g_async_initable_new_finish (G_ASYNC_INITABLE (source_object), result, error); - g_object_unref (source_object); - - if (object != NULL) - return E_GDBUS_BOOK (object); - else - return NULL; -} - -/** - * e_gdbus_book_proxy_new_for_bus_sync: - * @bus_type: A #GBusType. - * @flags: Flags used when constructing the proxy. - * @name: A bus name (well-known or unique). - * @object_path: An object path. - * @cancellable: A #GCancellable or %NULL. - * @error: Return location for error or %NULL. - * - * Like g_dbus_proxy_new_for_bus_sync() but returns a #EGdbusBookProxy. - * - * This is a synchronous failable constructor. See e_gdbus_book_proxy_new_for_bus() and e_gdbus_book_proxy_new_for_bus_finish() for the asynchronous version. - * - * Returns: A #EGdbusBookProxy or %NULL if error is set. Free with g_object_unref(). - */ -EGdbusBook * -e_gdbus_book_proxy_new_for_bus_sync (GBusType bus_type, - GDBusProxyFlags flags, - const gchar *name, - const gchar *object_path, - GCancellable *cancellable, - GError **error) -{ - GInitable *initable; - - initable = g_initable_new ( - E_TYPE_GDBUS_BOOK_PROXY, - cancellable, - error, - "g-flags", flags, - "g-name", name, - "g-bus-type", bus_type, - "g-object-path", object_path, - "g-interface-name", GDBUS_BOOK_INTERFACE_NAME, - NULL); - if (initable != NULL) - return E_GDBUS_BOOK (initable); - else - return NULL; -} - -/* ---------------------------------------------------------------------- */ - -static void stub_iface_init (EGdbusBookIface *iface); - -G_DEFINE_TYPE_WITH_CODE (EGdbusBookStub, e_gdbus_book_stub, G_TYPE_OBJECT, - G_IMPLEMENT_INTERFACE (E_TYPE_GDBUS_BOOK, stub_iface_init)); - -static void -e_gdbus_book_stub_init (EGdbusBookStub *stub) -{ -} - -static void -e_gdbus_book_stub_class_init (EGdbusBookStubClass *class) -{ -} - -static void -stub_iface_init (EGdbusBookIface *iface) -{ -} - -/** - * e_gdbus_book_stub_new: - * - * Creates a new stub object that can be exported via e_gdbus_book_register_object(). - * - * Returns: A #EGdbusBookStub instance. Free with g_object_unref(). - */ -EGdbusBook * -e_gdbus_book_stub_new (void) -{ - return E_GDBUS_BOOK (g_object_new (E_TYPE_GDBUS_BOOK_STUB, NULL)); -} - -/* Returns GDBus connection associated with the stub object */ -GDBusConnection * -e_gdbus_book_stub_get_connection (EGdbusBook *stub) -{ - g_return_val_if_fail (stub != NULL, NULL); - g_return_val_if_fail (E_IS_GDBUS_BOOK_STUB (stub), NULL); - - return g_object_get_data (G_OBJECT (stub), "gdbus-codegen-connection"); -} diff --git a/addressbook/libegdbus/e-gdbus-book.h b/addressbook/libegdbus/e-gdbus-book.h deleted file mode 100644 index 2ee76f5..0000000 --- a/addressbook/libegdbus/e-gdbus-book.h +++ /dev/null @@ -1,259 +0,0 @@ -/* - * e-gdbus-book.h - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) version 3. - * - * 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with the program; if not, see - * - * - * Copyright (C) 2011 Red Hat, Inc. (www.redhat.com) - * - */ - -#ifndef E_GDBUS_BOOK_H -#define E_GDBUS_BOOK_H - -#include - -#include - -G_BEGIN_DECLS - -#define E_TYPE_GDBUS_BOOK (e_gdbus_book_get_type ()) -#define E_GDBUS_BOOK(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), E_TYPE_GDBUS_BOOK, EGdbusBook)) -#define E_IS_GDBUS_BOOK(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), E_TYPE_GDBUS_BOOK)) -#define E_GDBUS_BOOK_GET_IFACE(o) (G_TYPE_INSTANCE_GET_INTERFACE((o), E_TYPE_GDBUS_BOOK, EGdbusBookIface)) - -/** - * EGdbusBook: - * - * Opaque type representing a proxy or an exported object. - */ -typedef struct _EGdbusBook EGdbusBook; /* Dummy typedef */ - -typedef struct _EGdbusBookIface EGdbusBookIface; - -GType e_gdbus_book_get_type (void) G_GNUC_CONST; - -/* ---------------------------------------------------------------------- */ - -#define E_TYPE_GDBUS_BOOK_PROXY (e_gdbus_book_proxy_get_type ()) -#define E_GDBUS_BOOK_PROXY(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), E_TYPE_GDBUS_BOOK_PROXY, EGdbusBookProxy)) -#define E_IS_GDBUS_BOOK_PROXY(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), E_TYPE_GDBUS_BOOK_PROXY)) - -typedef struct _EGdbusBookProxy EGdbusBookProxy; -typedef struct _EGdbusBookProxyClass EGdbusBookProxyClass; -typedef struct _EGdbusBookProxyPrivate EGdbusBookProxyPrivate; - -struct _EGdbusBookProxy -{ - GDBusProxy parent_instance; - EGdbusBookProxyPrivate *priv; -}; - -struct _EGdbusBookProxyClass -{ - GDBusProxyClass parent_class; -}; - -GType e_gdbus_book_proxy_get_type (void) G_GNUC_CONST; - -void e_gdbus_book_proxy_new (GDBusConnection *connection, GDBusProxyFlags flags, const gchar *name, const gchar *object_path, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -EGdbusBook *e_gdbus_book_proxy_new_finish (GAsyncResult *result, GError **error); -EGdbusBook *e_gdbus_book_proxy_new_sync (GDBusConnection *connection, GDBusProxyFlags flags, const gchar *name, const gchar *object_path, GCancellable *cancellable, GError **error); - -void e_gdbus_book_proxy_new_for_bus (GBusType bus_type, GDBusProxyFlags flags, const gchar *name, const gchar *object_path, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -EGdbusBook *e_gdbus_book_proxy_new_for_bus_finish (GAsyncResult *result, GError **error); -EGdbusBook *e_gdbus_book_proxy_new_for_bus_sync (GBusType bus_type, GDBusProxyFlags flags, const gchar *name, const gchar *object_path, GCancellable *cancellable, GError **error); - -/* ---------------------------------------------------------------------- */ - -typedef struct _EGdbusBookStub EGdbusBookStub; -typedef struct _EGdbusBookStubClass EGdbusBookStubClass; -typedef struct _EGdbusBookStubPrivate EGdbusBookStubPrivate; - -struct _EGdbusBookStub -{ - GObject parent_instance; - EGdbusBookStubPrivate *priv; -}; - -struct _EGdbusBookStubClass -{ - GObjectClass parent_class; -}; - -#define E_TYPE_GDBUS_BOOK_STUB (e_gdbus_book_stub_get_type ()) -#define E_GDBUS_BOOK_STUB(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), E_TYPE_GDBUS_BOOK_STUB, EGdbusBookStub)) -#define E_IS_GDBUS_BOOK_STUB(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), E_TYPE_GDBUS_BOOK_STUB)) - -GType e_gdbus_book_stub_get_type (void) G_GNUC_CONST; - -EGdbusBook *e_gdbus_book_stub_new (void); -GDBusConnection *e_gdbus_book_stub_get_connection (EGdbusBook *stub); - -guint e_gdbus_book_register_object (EGdbusBook *object, GDBusConnection *connection, const gchar *object_path, GError **error); - -void e_gdbus_book_drain_notify (EGdbusBook *object); - -const GDBusInterfaceInfo *e_gdbus_book_interface_info (void) G_GNUC_CONST; - -struct _EGdbusBookIface -{ - GTypeInterface parent_iface; - - /* Signal handlers for receiving D-Bus signals: */ - void (*backend_error) (EGdbusBook *object, const gchar *arg_message); - void (*readonly) (EGdbusBook *object, gboolean arg_is_readonly); - void (*online) (EGdbusBook *object, gboolean arg_is_online); - void (*opened) (EGdbusBook *object, const gchar * const *arg_error); - void (*backend_property_changed) (EGdbusBook *object, const gchar * const *arg_name_value); - - /* Signal handlers for handling D-Bus method calls: */ - gboolean (*handle_open) (EGdbusBook *object, GDBusMethodInvocation *invocation, gboolean in_only_if_exists); - void (*open_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error); - - gboolean (*handle_refresh) (EGdbusBook *object, GDBusMethodInvocation *invocation); - void (*refresh_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error); - - gboolean (*handle_get_contact) (EGdbusBook *object, GDBusMethodInvocation *invocation, const gchar *in_uid); - void (*get_contact_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error, gchar **out_vcard); - - gboolean (*handle_get_contact_list) (EGdbusBook *object, GDBusMethodInvocation *invocation, const gchar *in_query); - void (*get_contact_list_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error, gchar ***out_vcards); - - gboolean (*handle_get_contact_list_uids)(EGdbusBook *object, GDBusMethodInvocation *invocation, const gchar *in_query); - void (*get_contact_list_uids_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error, gchar ***out_uids); - - gboolean (*handle_add_contacts) (EGdbusBook *object, GDBusMethodInvocation *invocation, const gchar * const *in_vcards); - void (*add_contacts_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error, gchar ***out_uids); - - gboolean (*handle_remove_contacts) (EGdbusBook *object, GDBusMethodInvocation *invocation, const gchar * const *in_list); - void (*remove_contacts_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error); - - gboolean (*handle_modify_contacts) (EGdbusBook *object, GDBusMethodInvocation *invocation, const gchar * const *in_vcards); - void (*modify_contacts_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error); - - gboolean (*handle_get_backend_property) (EGdbusBook *object, GDBusMethodInvocation *invocation, const gchar *in_prop_name); - void (*get_backend_property_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error, gchar **out_prop_value); - - gboolean (*handle_set_backend_property) (EGdbusBook *object, GDBusMethodInvocation *invocation, const gchar *in_prop_name_value); - void (*set_backend_property_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error); - - gboolean (*handle_get_view) (EGdbusBook *object, GDBusMethodInvocation *invocation, const gchar *in_query); - void (*get_view_done) (EGdbusBook *object, guint arg_opid, const GError *arg_error, gchar **out_view); - - gboolean (*handle_cancel_operation) (EGdbusBook *object, GDBusMethodInvocation *invocation, guint in_opid); - gboolean (*handle_cancel_all) (EGdbusBook *object, GDBusMethodInvocation *invocation); - gboolean (*handle_close) (EGdbusBook *object, GDBusMethodInvocation *invocation); - -}; - -/* C Bindings for properties */ - -/* D-Bus Methods */ -void e_gdbus_book_call_open (GDBusProxy *proxy, gboolean in_only_if_exists, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_open_finish (GDBusProxy *proxy, GAsyncResult *result, GError **error); -gboolean e_gdbus_book_call_open_sync (GDBusProxy *proxy, gboolean in_only_if_exists, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_refresh (GDBusProxy *proxy, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_refresh_finish (GDBusProxy *proxy, GAsyncResult *result, GError **error); -gboolean e_gdbus_book_call_refresh_sync (GDBusProxy *proxy, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_get_contact (GDBusProxy *proxy, const gchar *in_uid, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_get_contact_finish (GDBusProxy *proxy, GAsyncResult *result, gchar **out_vcard, GError **error); -gboolean e_gdbus_book_call_get_contact_sync (GDBusProxy *proxy, const gchar *in_uid, gchar **out_vcard, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_get_contact_list (GDBusProxy *proxy, const gchar *in_query, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_get_contact_list_finish (GDBusProxy *proxy, GAsyncResult *result, gchar ***out_vcards, GError **error); -gboolean e_gdbus_book_call_get_contact_list_sync (GDBusProxy *proxy, const gchar *in_query, gchar ***out_vcards, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_get_contact_list_uids (GDBusProxy *proxy, const gchar *in_query, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_get_contact_list_uids_finish (GDBusProxy *proxy, GAsyncResult *result, gchar ***out_uids, GError **error); -gboolean e_gdbus_book_call_get_contact_list_uids_sync (GDBusProxy *proxy, const gchar *in_query, gchar ***out_uids, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_add_contacts (GDBusProxy *proxy, const gchar * const *in_vcards, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_add_contacts_finish (GDBusProxy *proxy, GAsyncResult *result, gchar ***out_uids, GError **error); -gboolean e_gdbus_book_call_add_contacts_sync (GDBusProxy *proxy, const gchar * const *in_vcards, gchar ***out_uids, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_remove_contacts (GDBusProxy *proxy, const gchar * const *in_list, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_remove_contacts_finish (GDBusProxy *proxy, GAsyncResult *result, GError **error); -gboolean e_gdbus_book_call_remove_contacts_sync (GDBusProxy *proxy, const gchar * const *in_list, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_modify_contacts (GDBusProxy *proxy, const gchar * const *in_vcards, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_modify_contacts_finish (GDBusProxy *proxy, GAsyncResult *result, GError **error); -gboolean e_gdbus_book_call_modify_contacts_sync (GDBusProxy *proxy, const gchar * const *in_vcards, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_get_backend_property (GDBusProxy *proxy, const gchar *in_prop_name, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_get_backend_property_finish (GDBusProxy *proxy, GAsyncResult *result, gchar **out_prop_value, GError **error); -gboolean e_gdbus_book_call_get_backend_property_sync (GDBusProxy *proxy, const gchar *prop_name, gchar **out_prop_value, GCancellable *cancellable, GError **error); - -gchar ** e_gdbus_book_encode_set_backend_property (const gchar *in_prop_name, const gchar *in_prop_value); -gboolean e_gdbus_book_decode_set_backend_property (const gchar * const *in_strv, gchar **out_prop_name, gchar **out_prop_value); -void e_gdbus_book_call_set_backend_property (GDBusProxy *proxy, const gchar * const *in_prop_name_value, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_set_backend_property_finish (GDBusProxy *proxy, GAsyncResult *result, GError **error); -gboolean e_gdbus_book_call_set_backend_property_sync (GDBusProxy *proxy, const gchar * const *prop_name_value, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_get_view (GDBusProxy *proxy, const gchar *in_query, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_get_view_finish (GDBusProxy *proxy, GAsyncResult *result, gchar **out_view_path, GError **error); -gboolean e_gdbus_book_call_get_view_sync (GDBusProxy *proxy, const gchar *in_query, gchar **out_view_path, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_cancel_operation (GDBusProxy *proxy, guint in_opid, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_cancel_operation_finish (GDBusProxy *proxy, GAsyncResult *result, GError **error); -gboolean e_gdbus_book_call_cancel_operation_sync (GDBusProxy *proxy, guint in_opid, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_cancel_all (GDBusProxy *proxy, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_cancel_all_finish (GDBusProxy *proxy, GAsyncResult *result, GError **error); -gboolean e_gdbus_book_call_cancel_all_sync (GDBusProxy *proxy, GCancellable *cancellable, GError **error); - -void e_gdbus_book_call_close (GDBusProxy *proxy, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data); -gboolean e_gdbus_book_call_close_finish (GDBusProxy *proxy, GAsyncResult *result, GError **error); -gboolean e_gdbus_book_call_close_sync (GDBusProxy *proxy, GCancellable *cancellable, GError **error); - -/* D-Bus Methods Completion Helpers */ -#define e_gdbus_book_complete_open e_gdbus_complete_async_method -#define e_gdbus_book_complete_refresh e_gdbus_complete_async_method -#define e_gdbus_book_complete_get_contact e_gdbus_complete_async_method -#define e_gdbus_book_complete_get_contact_list e_gdbus_complete_async_method -#define e_gdbus_book_complete_get_contact_list_uids e_gdbus_complete_async_method -#define e_gdbus_book_complete_add_contacts e_gdbus_complete_async_method -#define e_gdbus_book_complete_remove_contacts e_gdbus_complete_async_method -#define e_gdbus_book_complete_modify_contacts e_gdbus_complete_async_method -#define e_gdbus_book_complete_get_backend_property e_gdbus_complete_async_method -#define e_gdbus_book_complete_set_backend_property e_gdbus_complete_async_method -#define e_gdbus_book_complete_get_view e_gdbus_complete_async_method -#define e_gdbus_book_complete_cancel_operation e_gdbus_complete_sync_method_void -#define e_gdbus_book_complete_cancel_all e_gdbus_complete_sync_method_void -#define e_gdbus_book_complete_close e_gdbus_complete_sync_method_void - -void e_gdbus_book_emit_open_done (EGdbusBook *object, guint arg_opid, const GError *arg_error); -void e_gdbus_book_emit_refresh_done (EGdbusBook *object, guint arg_opid, const GError *arg_error); -void e_gdbus_book_emit_get_contact_done (EGdbusBook *object, guint arg_opid, const GError *arg_error, const gchar *out_vcard); -void e_gdbus_book_emit_get_contact_list_done (EGdbusBook *object, guint arg_opid, const GError *arg_error, const gchar * const *out_vcards); -void e_gdbus_book_emit_get_contact_list_uids_done (EGdbusBook *object, guint arg_opid, const GError *arg_error, const gchar * const *out_uids); -void e_gdbus_book_emit_add_contacts_done (EGdbusBook *object, guint arg_opid, const GError *arg_error, const gchar *const *out_uids); -void e_gdbus_book_emit_remove_contacts_done (EGdbusBook *object, guint arg_opid, const GError *arg_error); -void e_gdbus_book_emit_modify_contacts_done (EGdbusBook *object, guint arg_opid, const GError *arg_error); -void e_gdbus_book_emit_get_backend_property_done (EGdbusBook *object, guint arg_opid, const GError *arg_error, const gchar *out_prop_value); -void e_gdbus_book_emit_set_backend_property_done (EGdbusBook *object, guint arg_opid, const GError *arg_error); -void e_gdbus_book_emit_get_view_done (EGdbusBook *object, guint arg_opid, const GError *arg_error, const gchar *out_view); - -/* D-Bus Signal Emission Helpers */ -void e_gdbus_book_emit_backend_error (EGdbusBook *object, const gchar *arg_message); -void e_gdbus_book_emit_readonly (EGdbusBook *object, gboolean arg_is_readonly); -void e_gdbus_book_emit_online (EGdbusBook *object, gboolean arg_is_online); -void e_gdbus_book_emit_opened (EGdbusBook *object, const gchar * const *arg_error); -void e_gdbus_book_emit_backend_property_changed (EGdbusBook *object, const gchar * const *arg_name_value); - -G_END_DECLS - -#endif /* E_GDBUS_BOOK_H */ diff --git a/docs/reference/addressbook/libedata-book/libedata-book-sections.txt b/docs/reference/addressbook/libedata-book/libedata-book-sections.txt index 387d5b7..854a7a9 100644 --- a/docs/reference/addressbook/libedata-book/libedata-book-sections.txt +++ b/docs/reference/addressbook/libedata-book/libedata-book-sections.txt @@ -37,8 +37,6 @@ e_book_backend_notify_update e_book_backend_notify_remove e_book_backend_notify_complete e_book_backend_notify_error -e_book_backend_notify_readonly -e_book_backend_notify_online e_book_backend_notify_property_changed e_book_backend_sync e_book_backend_set_is_removed @@ -50,6 +48,8 @@ e_book_backend_is_opening e_book_backend_set_backend_property e_book_backend_foreach_view e_book_backend_notify_opened +e_book_backend_notify_readonly +e_book_backend_notify_online e_book_backend_respond_opened E_BOOK_BACKEND @@ -281,13 +281,13 @@ e_data_book_respond_get_contact e_data_book_respond_get_contact_list e_data_book_respond_get_contact_list_uids e_data_book_report_error -e_data_book_report_readonly -e_data_book_report_online e_data_book_report_backend_property_changed e_data_book_string_slist_to_comma_string e_data_book_respond_set_backend_property e_data_book_report_opened +e_data_book_report_readonly +e_data_book_report_online E_DATA_BOOK E_IS_DATA_BOOK -- 2.7.4