/soc/2012/tomkiewicz/gg: f0ac6497f256: Gadu-Gadu: roster - fix s...
Tomasz Wasilczyk
tomkiewicz at cpw.pidgin.im
Fri Jul 13 04:13:07 EDT 2012
Changeset: f0ac6497f256575efa5e885a876510a498e061c7
Author: Tomasz Wasilczyk <tomkiewicz at cpw.pidgin.im>
Date: 2012-07-13 10:12 +0200
Branch: soc.2012.gg
URL: http://hg.pidgin.im/soc/2012/tomkiewicz/gg/rev/f0ac6497f256
Description:
Gadu-Gadu: roster - fix synchronization for multiple gg accounts
diffstat:
libpurple/protocols/gg/purplew.c | 2 +-
libpurple/protocols/gg/roster.c | 172 +++++++++++++++++++++-----------------
libpurple/protocols/gg/roster.h | 2 +
3 files changed, 100 insertions(+), 76 deletions(-)
diffs (truncated from 481 to 300 lines):
diff --git a/libpurple/protocols/gg/purplew.c b/libpurple/protocols/gg/purplew.c
--- a/libpurple/protocols/gg/purplew.c
+++ b/libpurple/protocols/gg/purplew.c
@@ -57,7 +57,7 @@
PurpleGroup * ggp_purplew_buddy_get_group_only(PurpleBuddy *buddy)
{
PurpleGroup *group = purple_buddy_get_group(buddy);
- if (!group)
+ if (!group) // TODO: get contact's group
return NULL;
if (0 == strcmp(_("Buddies"), purple_group_get_name(group)))
return NULL;
diff --git a/libpurple/protocols/gg/roster.c b/libpurple/protocols/gg/roster.c
--- a/libpurple/protocols/gg/roster.c
+++ b/libpurple/protocols/gg/roster.c
@@ -8,11 +8,10 @@
#include <debug.h>
#define GGP_ROSTER_SYNC_SETT "gg-synchronized"
-#define GGP_ROSTER_ID_SETT "gg-id"
#define GGP_ROSTER_DEBUG 0
#define GGP_ROSTER_GROUPID_DEFAULT "00000000-0000-0000-0000-000000000000"
-// TODO: check what happens, if feature is disabled
+// TODO: ggp_purplew_buddy_get_group_only
typedef struct
{
@@ -31,6 +30,18 @@
* Value: (xmlnode*) xml node for group
*/
GHashTable *group_nodes;
+
+ /**
+ * Key: (gchar*) group name
+ * Value: (gchar*) group id
+ */
+ GHashTable *group_ids;
+
+ /**
+ * Key: (gchar*) group id
+ * Value: (gchar*) group name
+ */
+ GHashTable *group_names; //TODO: wywalic? tylko zapamietujmy grupe "Pomocnicy" (dla botow)
gboolean needs_update;
} ggp_roster_content;
@@ -46,7 +57,11 @@
union
{
uin_t uin;
- gchar *group_name;
+ struct
+ {
+ gchar *old_name;
+ gchar *new_name;
+ } group_rename;
} data;
} ggp_roster_change;
@@ -98,6 +113,7 @@
rdata->sent_updates = NULL;
rdata->pending_updates = NULL;
rdata->timer = 0;
+ rdata->is_updating = FALSE;
if (ggp_roster_enabled())
rdata->timer = purple_timeout_add_seconds(2, ggp_roster_timer_cb, gc);
@@ -124,6 +140,10 @@
g_hash_table_destroy(content->contact_nodes);
if (content->group_nodes)
g_hash_table_destroy(content->group_nodes);
+ if (content->group_ids)
+ g_hash_table_destroy(content->group_ids);
+ if (content->group_names)
+ g_hash_table_destroy(content->group_names);
g_free(content);
}
@@ -132,7 +152,10 @@
ggp_roster_change *change = _change;
if (change->type == GGP_ROSTER_CHANGE_GROUP_RENAME)
- g_free(change->data.group_name);
+ {
+ g_free(change->data.group_rename.old_name);
+ g_free(change->data.group_rename.new_name);
+ }
g_free(change);
}
@@ -146,7 +169,7 @@
purple_blist_node_set_bool(PURPLE_BLIST_NODE(buddy), GGP_ROSTER_SYNC_SETT, synchronized);
if (!synchronized)
{
- change = g_new(ggp_roster_change, 1);
+ change = g_new0(ggp_roster_change, 1);
change->type = GGP_ROSTER_CHANGE_CONTACT_UPDATE;
change->data.uin = uin;
rdata->pending_updates = g_list_append(rdata->pending_updates, change);
@@ -273,13 +296,11 @@
rdata->version = version;
}
-static gboolean ggp_roster_reply_list_read_group(xmlnode *node, ggp_roster_content *content, GHashTable *groups, GHashTable *remove_groups)
+static gboolean ggp_roster_reply_list_read_group(xmlnode *node, ggp_roster_content *content)
{
char *name, *id;
gboolean removable;
gboolean succ = TRUE;
- PurpleGroup *local_group;
- const char *local_group_name;
succ &= ggp_xml_get_string(node, "Id", &id);
succ &= ggp_xml_get_string(node, "Name", &name);
@@ -299,28 +320,14 @@
return TRUE;
}
- local_group = g_hash_table_lookup(remove_groups, id);
- g_hash_table_remove(remove_groups, id);
- if (local_group)
- local_group_name = purple_group_get_name(local_group);
- if (local_group &&
- 0 != g_strcmp0(name, local_group_name))
- {
- purple_debug_info("gg", "ggp_roster_reply_list_read_group: rename group from %s to %s\n", local_group_name, name);
- purple_blist_rename_group(local_group, name);
- }
- if (!local_group)
- local_group = purple_find_group(name);
- if (local_group)
- purple_blist_node_set_string(PURPLE_BLIST_NODE(local_group), GGP_ROSTER_ID_SETT, id);
-
g_hash_table_insert(content->group_nodes, g_strdup(id), node);
- g_hash_table_insert(groups, id, name);
+ g_hash_table_insert(content->group_ids, g_strdup(name), g_strdup(id));
+ g_hash_table_insert(content->group_names, id, name);
return TRUE;
}
-static gboolean ggp_roster_reply_list_read_buddy(PurpleConnection *gc, xmlnode *node, ggp_roster_content *content, GHashTable *groups, GHashTable *remove_buddies)
+static gboolean ggp_roster_reply_list_read_buddy(PurpleConnection *gc, xmlnode *node, ggp_roster_content *content, GHashTable *remove_buddies)
{
gchar *alias, *group_name;
uin_t uin;
@@ -359,13 +366,14 @@
while (group_elem != NULL)
{
gchar *id;
- gboolean isbot;
+ gboolean isbot, isdefault;
if (!ggp_xml_get_string(group_elem, NULL, &id))
continue;
- group_name = g_hash_table_lookup(groups, id);
+ group_name = g_hash_table_lookup(content->group_names, id);
isbot = (strcmp(id, "0b345af6-0001-0000-0000-000000000004") == 0 ||
g_strcmp0(group_name, "Pomocnicy") == 0);
+ isdefault = (0 == g_strcmp0(group_name, _("Buddies")));
g_free(id);
// we don't want to import bots;
@@ -375,6 +383,8 @@
g_free(alias);
return TRUE;
}
+ if (isdefault)
+ group_name = NULL;
if (group_name != NULL)
break;
@@ -396,7 +406,7 @@
g_hash_table_remove(remove_buddies, GINT_TO_POINTER(uin));
if (!buddy)
{
- purple_debug_info("gg", "ggp_roster_reply_list: adding %u to buddy list\n", uin);
+ purple_debug_info("gg", "ggp_roster_reply_list: adding %u (%s) to buddy list\n", uin, alias);
buddy = purple_buddy_new(account, ggp_uin_to_str(uin), alias);
purple_blist_add_buddy(buddy, NULL, group, NULL);
ggp_roster_set_synchronized(gc, buddy, TRUE);
@@ -408,7 +418,7 @@
// buddy exists, but is not synchronized - local list has priority
if (!ggp_roster_is_synchronized(buddy))
{
- purple_debug_info("gg", "ggp_roster_reply_list: ignoring not synchronized %s\n", purple_buddy_get_name(buddy));
+ purple_debug_misc("gg", "ggp_roster_reply_list: ignoring not synchronized %s\n", purple_buddy_get_name(buddy));
g_free(alias);
return TRUE;
}
@@ -436,14 +446,14 @@
{
ggp_roster_session_data *rdata = ggp_roster_get_rdata(gc);
xmlnode *xml, *curr_elem;
- GHashTable *groups;
PurpleAccount *account;
GSList *buddies;
- GHashTable *remove_buddies, *remove_groups;
- GList *remove_buddies_list, *remove_buddies_it, *map_values, *it;
+ GHashTable *remove_buddies;//, *remove_groups;
+ GList *remove_buddies_list, *remove_buddies_it;//, *map_values, *it;
+ //GList *map_values, *it; TODO
GList *update_buddies = NULL, *update_buddies_it;
ggp_roster_content *content;
- PurpleBlistNode *bnode;
+ //PurpleBlistNode *bnode;
g_return_if_fail(gc != NULL);
g_return_if_fail(data != NULL);
@@ -461,46 +471,30 @@
ggp_roster_content_free(rdata->content);
rdata->content = NULL;
+ rdata->is_updating = TRUE;
content = g_new0(ggp_roster_content, 1);
content->xml = xml;
content->contact_nodes = g_hash_table_new(NULL, NULL);
content->group_nodes = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, NULL);
+ content->group_ids = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, g_free);
+ content->group_names = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, g_free);
#if GGP_ROSTER_DEBUG
ggp_roster_dump(content);
#endif
- remove_groups = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, NULL);
- // dumping local group list
- for (bnode = purple_blist_get_root(); bnode != NULL; bnode = bnode->next)
- {
- PurpleGroup *group;
- const char *id;
- if (!PURPLE_BLIST_NODE_IS_GROUP(bnode))
- continue;
- group = (PurpleGroup*)bnode;
-
- id = purple_blist_node_get_string(bnode, GGP_ROSTER_ID_SETT);
- if (!id)
- continue;
- g_hash_table_insert(remove_groups, g_strdup(id), group);
- }
-
// reading groups
content->groups_node = xmlnode_get_child(xml, "Groups");
if (content->groups_node == NULL)
{
ggp_roster_content_free(content);
- g_hash_table_destroy(remove_groups);
g_return_if_reached();
}
- groups = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, g_free);
curr_elem = xmlnode_get_child(content->groups_node, "Group");
while (curr_elem != NULL)
{
- if (!ggp_roster_reply_list_read_group(curr_elem, content, groups, remove_groups))
+ if (!ggp_roster_reply_list_read_group(curr_elem, content))
{
- g_hash_table_destroy(groups);
ggp_roster_content_free(content);
g_return_if_reached();
}
@@ -534,9 +528,7 @@
content->contacts_node = xmlnode_get_child(xml, "Contacts");
if (content->contacts_node == NULL)
{
- g_hash_table_destroy(groups);
g_hash_table_destroy(remove_buddies);
- g_hash_table_destroy(remove_groups);
g_list_free(update_buddies);
ggp_roster_content_free(content);
g_return_if_reached();
@@ -544,11 +536,9 @@
curr_elem = xmlnode_get_child(content->contacts_node, "Contact");
while (curr_elem != NULL)
{
- if (!ggp_roster_reply_list_read_buddy(gc, curr_elem, content, groups, remove_buddies))
+ if (!ggp_roster_reply_list_read_buddy(gc, curr_elem, content, remove_buddies))
{
- g_hash_table_destroy(groups);
g_hash_table_destroy(remove_buddies);
- g_hash_table_destroy(remove_groups);
g_list_free(update_buddies);
ggp_roster_content_free(content);
g_return_if_reached();
@@ -557,8 +547,6 @@
curr_elem = xmlnode_get_next_twin(curr_elem);
}
- g_hash_table_destroy(groups);
-
// removing buddies, which are not present in roster
remove_buddies_list = g_hash_table_get_values(remove_buddies);
remove_buddies_it = g_list_first(remove_buddies_list);
@@ -575,6 +563,7 @@
g_list_free(remove_buddies_list);
g_hash_table_destroy(remove_buddies);
+ /* TODO: remove groups, which are empty, but had contacts before synchronization
// removing groups, which are:
// - not present in roster
More information about the Commits
mailing list