1
0
mirror of https://github.com/profanity-im/profanity.git synced 2024-06-23 21:45:30 +00:00

Handle presence received before roster

Presence of contact not found in roster are filtered out.
But sometimes roster is received after a first few presences.

We choose to store presences until we receive roster and then process
this presences.

Fixes #1050
This commit is contained in:
Paul Fariello 2019-04-16 20:44:39 +03:20
parent 3d3eabb63f
commit 973a05d15a
3 changed files with 45 additions and 0 deletions

View File

@ -115,6 +115,7 @@ sv_ev_roster_received(void)
ui_show_roster();
}
roster_process_pending_presence();
char *account_name = session_get_account_name();
#ifdef HAVE_LIBGPGME

View File

@ -67,7 +67,15 @@ typedef struct prof_roster_t {
GHashTable *group_count;
} ProfRoster;
typedef struct pending_presence {
char *barejid;
Resource *resource;
GDateTime *last_activity;
} ProfPendingPresence;
static ProfRoster *roster = NULL;
static gboolean roster_received = FALSE;
static GSList *roster_pending_presence = NULL;
static gboolean _key_equals(void *key1, void *key2);
static gboolean _datetimes_equal(GDateTime *dt1, GDateTime *dt2);
@ -87,6 +95,9 @@ roster_create(void)
roster->name_to_barejid = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, g_free);
roster->groups_ac = autocomplete_new();
roster->group_count = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, NULL);
roster_received = FALSE;
roster_pending_presence = NULL;
}
void
@ -114,6 +125,18 @@ roster_update_presence(const char *const barejid, Resource *resource, GDateTime
assert(barejid != NULL);
assert(resource != NULL);
if (!roster_received) {
ProfPendingPresence *presence = malloc(sizeof(ProfPendingPresence));
presence->barejid = strdup(barejid);
presence->resource = resource;
presence->last_activity = last_activity;
if (last_activity) {
g_date_time_ref(last_activity);
}
roster_pending_presence = g_slist_append(roster_pending_presence, presence);
return FALSE;
}
PContact contact = roster_get_contact(barejid);
if (contact == NULL) {
return FALSE;
@ -664,3 +687,23 @@ roster_compare_presence(PContact a, PContact b)
return roster_compare_name(a, b);
}
}
void
roster_process_pending_presence(void)
{
roster_received = TRUE;
GSList *iter;
for (iter = roster_pending_presence; iter != NULL; iter = iter->next) {
ProfPendingPresence *presence = iter->data;
roster_update_presence(presence->barejid, presence->resource, presence->last_activity);
free(presence->barejid);
/* seems like resource isn't free on the calling side */
if (presence->last_activity) {
g_date_time_unref(presence->last_activity);
}
}
g_slist_free(roster_pending_presence);
roster_pending_presence = NULL;
}

View File

@ -72,5 +72,6 @@ GSList* roster_get_contacts_by_presence(const char *const presence);
char* roster_get_msg_display_name(const char *const barejid, const char *const resource);
gint roster_compare_name(PContact a, PContact b);
gint roster_compare_presence(PContact a, PContact b);
void roster_process_pending_presence(void);
#endif