TpConnectionPresenceType global_presence;
gchar *global_status;
gchar *global_status_message;
+
+ /* desired global presence, could be different
+ * from the actual global one.
+ */
+ TpConnectionPresenceType desired_presence;
+ gchar *desired_status;
+ gchar *desired_status_message;
+
+ GHashTable *create_results;
} EmpathyAccountManagerPriv;
enum {
GParamSpec *spec,
gpointer manager)
{
+ EmpathyAccountManagerPriv *priv = GET_PRIV (manager);
+
if (empathy_account_is_enabled (account))
- g_signal_emit (manager, signals[ACCOUNT_ENABLED], 0, account);
+ {
+ g_signal_emit (manager, signals[ACCOUNT_ENABLED], 0, account);
+
+ /* set the desired global presence on the account */
+ empathy_account_request_presence (account, priv->desired_presence,
+ priv->desired_status, priv->desired_status_message);
+ }
else
g_signal_emit (manager, signals[ACCOUNT_DISABLED], 0, account);
}
}
static void
-emp_account_ready_cb (GObject *obj, GParamSpec *spec, gpointer user_data)
+account_manager_account_ready_cb (GObject *obj,
+ GParamSpec *spec,
+ gpointer user_data)
{
EmpathyAccountManager *manager = EMPATHY_ACCOUNT_MANAGER (user_data);
+ EmpathyAccountManagerPriv *priv = GET_PRIV (manager);
EmpathyAccount *account = EMPATHY_ACCOUNT (obj);
+ GSimpleAsyncResult *result;
gboolean ready;
g_object_get (account, "ready", &ready, NULL);
if (!ready)
return;
+ /* see if there's any pending callbacks for this account */
+ result = g_hash_table_lookup (priv->create_results, account);
+ if (result != NULL)
+ {
+ g_simple_async_result_set_op_res_gpointer (
+ G_SIMPLE_ASYNC_RESULT (result), account, NULL);
+
+ g_simple_async_result_complete (result);
+
+ g_hash_table_remove (priv->create_results, account);
+ g_object_unref (result);
+ }
+
g_signal_emit (manager, signals[ACCOUNT_CREATED], 0, account);
g_signal_connect (account, "notify::connection",
g_hash_table_insert (priv->accounts, g_strdup (path), account);
g_signal_connect (account, "notify::ready",
- G_CALLBACK (emp_account_ready_cb), manager);
+ G_CALLBACK (account_manager_account_ready_cb), manager);
return account;
}
priv->accounts = g_hash_table_new_full (g_str_hash, g_str_equal,
g_free, (GDestroyNotify) g_object_unref);
+ priv->create_results = g_hash_table_new (g_direct_hash, g_direct_equal);
+
priv->dbus = tp_dbus_daemon_dup (NULL);
tp_dbus_daemon_watch_name_owner (priv->dbus,
EmpathyAccountManager *manager = EMPATHY_ACCOUNT_MANAGER (obj);
EmpathyAccountManagerPriv *priv = GET_PRIV (manager);
+ g_hash_table_destroy (priv->create_results);
g_hash_table_destroy (priv->accounts);
+ g_free (priv->global_status);
+ g_free (priv->global_status_message);
+
+ g_free (priv->desired_status);
+ g_free (priv->desired_status_message);
+
G_OBJECT_CLASS (empathy_account_manager_parent_class)->finalize (obj);
}
priv->dispose_run = TRUE;
+ if (priv->create_results != NULL &&
+ g_hash_table_size (priv->create_results) > 0)
+ {
+ /* the manager is being destroyed while there are account creation
+ * processes pending; this should not happen, but emit the callbacks
+ * with an error anyway.
+ */
+ GHashTableIter iter;
+ GSimpleAsyncResult *result;
+
+ g_hash_table_iter_init (&iter, priv->create_results);
+ while (g_hash_table_iter_next (&iter, NULL, (gpointer *) &result))
+ {
+ g_simple_async_result_set_error (result, G_IO_ERROR,
+ G_IO_ERROR_CANCELLED, "The account manager was disposed while "
+ "creating the account");
+ g_simple_async_result_complete (result);
+ g_object_unref (result);
+ }
+ }
+
tp_dbus_daemon_cancel_name_owner_watch (priv->dbus,
TP_ACCOUNT_MANAGER_BUS_NAME, account_manager_name_owner_cb, manager);
- if (priv->dbus == NULL)
- g_object_unref (priv->dbus);
- priv->dbus = NULL;
+ if (priv->dbus != NULL)
+ {
+ g_object_unref (priv->dbus);
+ priv->dbus = NULL;
+ }
G_OBJECT_CLASS (empathy_account_manager_parent_class)->dispose (obj);
}
const gchar *status,
const gchar *message)
{
- /* FIXME should remember requested presence and set it on new accounts
- as well */
EmpathyAccountManagerPriv *priv = GET_PRIV (manager);
GHashTableIter iter;
gpointer value;
if (ready)
empathy_account_request_presence (account, type, status, message);
}
+
+ /* save the requested global presence, to use it in case we create
+ * new accounts.
+ */
+ priv->desired_presence = type;
+
+ if (tp_strdiff (priv->desired_status, status))
+ {
+ g_free (priv->desired_status);
+ priv->desired_status = g_strdup (status);
+ }
+
+ if (tp_strdiff (priv->desired_status_message, message))
+ {
+ g_free (priv->desired_status_message);
+ priv->desired_status_message = g_strdup (message);
+ }
}
TpConnectionPresenceType
return priv->global_presence;
}
-static void
-empathy_account_manager_created_ready_cb (EmpathyAccount *account,
- GParamSpec *spec, gpointer user_data)
-{
- GSimpleAsyncResult *result = G_SIMPLE_ASYNC_RESULT (user_data);
-
- if (!empathy_account_is_ready (account))
- return;
-
- g_simple_async_result_set_op_res_gpointer (
- G_SIMPLE_ASYNC_RESULT (result), account, NULL);
-
- g_simple_async_result_complete (result);
- g_object_unref (G_OBJECT (result));
-}
-
static void
empathy_account_manager_created_cb (TpAccountManager *proxy,
const gchar *account_path,
GObject *weak_object)
{
EmpathyAccountManager *manager = EMPATHY_ACCOUNT_MANAGER (weak_object);
- GSimpleAsyncResult *result = G_SIMPLE_ASYNC_RESULT (user_data);
+ EmpathyAccountManagerPriv *priv = GET_PRIV (manager);
+ GSimpleAsyncResult *my_res = user_data;
EmpathyAccount *account;
if (error != NULL)
{
- g_simple_async_result_set_from_error (result, (GError *) error);
- g_simple_async_result_complete (result);
- g_object_unref (G_OBJECT (result));
+ g_simple_async_result_set_from_error (my_res,
+ (GError *) error);
+ g_simple_async_result_complete (my_res);
+ g_object_unref (my_res);
+
return;
}
account = account_manager_add_account (manager, account_path);
- if (empathy_account_is_ready (account))
- empathy_account_manager_created_ready_cb (account, NULL, result);
- else
- g_signal_connect (account, "notify::ready",
- G_CALLBACK (empathy_account_manager_created_ready_cb), result);
+
+ g_hash_table_insert (priv->create_results, account, my_res);
}
void
gpointer user_data)
{
EmpathyAccountManagerPriv *priv = GET_PRIV (manager);
- GSimpleAsyncResult *result = g_simple_async_result_new (G_OBJECT (manager),
- callback, user_data, empathy_account_manager_create_account_finish);
+ GSimpleAsyncResult *res;
+
+ res = g_simple_async_result_new
+ (G_OBJECT (manager), callback, user_data,
+ empathy_account_manager_create_account_finish);
tp_cli_account_manager_call_create_account (priv->tp_manager,
-1,
parameters,
properties,
empathy_account_manager_created_cb,
- result,
+ res,
NULL,
G_OBJECT (manager));
}
empathy_account_manager_create_account_finish (
EmpathyAccountManager *manager, GAsyncResult *result, GError **error)
{
+ EmpathyAccount *retval;
+
if (g_simple_async_result_propagate_error (G_SIMPLE_ASYNC_RESULT (result),
error))
return NULL;
g_return_val_if_fail (g_simple_async_result_is_valid (result,
G_OBJECT (manager), empathy_account_manager_create_account_finish), NULL);
- return EMPATHY_ACCOUNT (g_simple_async_result_get_op_res_gpointer (
+ retval = EMPATHY_ACCOUNT (g_simple_async_result_get_op_res_gpointer (
G_SIMPLE_ASYNC_RESULT (result)));
+
+ return retval;
}