summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorZeeshan Ali (Khattak) <zeeshanak@gnome.org>2013-09-06 04:16:12 +0300
committerZeeshan Ali (Khattak) <zeeshanak@gnome.org>2013-09-06 04:19:34 +0300
commit4d513c5cf5011342dce85a1c4d983c53ffbb58d2 (patch)
tree25e0520208a8887612595c76d321249ed7c9bc17
parentc5c79fce6658ea06215c28952cac861a7c6aa971 (diff)
ipclient: Make search actually cancellable
The search call was taking a cancellable but it wasn't handling cancellation on it. This patch adds that handling.
-rw-r--r--src/gclue-ipclient.c74
1 files changed, 60 insertions, 14 deletions
diff --git a/src/gclue-ipclient.c b/src/gclue-ipclient.c
index 285205c..a195d8c 100644
--- a/src/gclue-ipclient.c
+++ b/src/gclue-ipclient.c
@@ -244,21 +244,60 @@ get_search_query (GClueIpclient *ipclient)
return ret;
}
+typedef struct
+{
+ GSimpleAsyncResult *simple;
+ SoupMessage *message;
+ GCancellable *cancellable;
+
+ gulong cancelled_id;
+} QueryCallbackData;
+
+static void
+query_callback_data_free (QueryCallbackData *data)
+{
+ g_object_unref (data->simple);
+ g_slice_free (QueryCallbackData, data);
+}
+
+static void
+search_cancelled_callback (GCancellable *cancellable,
+ QueryCallbackData *data)
+{
+ GClueIpclient *ipclient = GCLUE_IPCLIENT
+ (g_async_result_get_source_object
+ (G_ASYNC_RESULT (data->simple)));
+ soup_session_cancel_message (ipclient->priv->soup_session,
+ data->message,
+ SOUP_STATUS_CANCELLED);
+}
+
static void
query_callback (SoupSession *session,
SoupMessage *query,
gpointer user_data)
{
- GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (user_data);
+ QueryCallbackData *data = (QueryCallbackData *) user_data;
+ GSimpleAsyncResult *simple = data->simple;
GError *error = NULL;
char *contents;
+ if (data->cancellable != NULL)
+ g_signal_handler_disconnect (data->cancellable,
+ data->cancelled_id);
+
if (query->status_code != SOUP_STATUS_OK) {
- g_set_error_literal (&error, G_IO_ERROR, G_IO_ERROR_FAILED,
+ GIOErrorEnum code;
+
+ if (query->status_code == SOUP_STATUS_CANCELLED)
+ code = G_IO_ERROR_CANCELLED;
+ else
+ code = G_IO_ERROR_FAILED;
+ g_set_error_literal (&error, G_IO_ERROR, code,
query->reason_phrase ? query->reason_phrase : "Query failed");
g_simple_async_result_take_error (simple, error);
g_simple_async_result_complete_in_idle (simple);
- g_object_unref (simple);
+ query_callback_data_free (data);
return;
}
@@ -266,7 +305,7 @@ query_callback (SoupSession *session,
g_simple_async_result_set_op_res_gpointer (simple, contents, NULL);
g_simple_async_result_complete_in_idle (simple);
- g_object_unref (simple);
+ query_callback_data_free (data);
}
/**
@@ -289,22 +328,29 @@ gclue_ipclient_search_async (GClueIpclient *ipclient,
GAsyncReadyCallback callback,
gpointer user_data)
{
- GSimpleAsyncResult *simple;
- SoupMessage *query;
+ QueryCallbackData *data;
g_return_if_fail (GCLUE_IS_IPCLIENT (ipclient));
g_return_if_fail (ipclient->priv->server != NULL);
- simple = g_simple_async_result_new (G_OBJECT (ipclient),
- callback,
- user_data,
- gclue_ipclient_search_async);
-
- query = get_search_query (ipclient);
+ data = g_slice_new0 (QueryCallbackData);
+ data->simple = g_simple_async_result_new (G_OBJECT (ipclient),
+ callback,
+ user_data,
+ gclue_ipclient_search_async);
+ data->cancellable = cancellable;
+ data->message = get_search_query (ipclient);
+
+ if (cancellable != NULL)
+ data->cancelled_id = g_signal_connect
+ (cancellable,
+ "cancelled",
+ G_CALLBACK (search_cancelled_callback),
+ data);
soup_session_queue_message (ipclient->priv->soup_session,
- query,
+ data->message,
query_callback,
- simple);
+ data);
}
static gboolean