diff options
Diffstat (limited to 'protocols')
| -rw-r--r-- | protocols/jabber/iq.c | 59 | ||||
| -rw-r--r-- | protocols/jabber/jabber.c | 18 | ||||
| -rw-r--r-- | protocols/jabber/jabber.h | 1 | 
3 files changed, 78 insertions, 0 deletions
| diff --git a/protocols/jabber/iq.c b/protocols/jabber/iq.c index 2fa418fe..8518439e 100644 --- a/protocols/jabber/iq.c +++ b/protocols/jabber/iq.c @@ -1058,3 +1058,62 @@ static xt_status jabber_iq_carbons_response(struct im_connection *ic,  	return XT_HANDLED;  } + +xt_status jabber_iq_disco_muc_response(struct im_connection *ic, struct xt_node *node, struct xt_node *orig); + +int jabber_iq_disco_muc(struct im_connection *ic, const char *muc_server) +{ +	struct xt_node *node; +	int st; + +	node = xt_new_node("query", NULL, NULL); +	xt_add_attr(node, "xmlns", XMLNS_DISCO_ITEMS); +	node = jabber_make_packet("iq", "get", (char *) muc_server, node); + +	jabber_cache_add(ic, node, jabber_iq_disco_muc_response); +	st = jabber_write_packet(ic, node); + +	return st; +} + +xt_status jabber_iq_disco_muc_response(struct im_connection *ic, struct xt_node *node, struct xt_node *orig) +{ +	struct xt_node *query, *c; +	struct jabber_error *err; +	GSList *rooms =  NULL; + +	if ((err = jabber_error_parse(xt_find_node(node->children, "error"), XMLNS_STANZA_ERROR))) { +		imcb_error(ic, "The server replied with an error: %s%s%s", +		           err->code, err->text ? ": " : "", err->text ? err->text : ""); +		jabber_error_free(err); +		return XT_HANDLED; +	} + +	if (!(query = xt_find_node(node->children, "query"))) { +		imcb_error(ic, "Received incomplete MUC list reply"); +		return XT_HANDLED; +	} + +	c = query->children; +	while ((c = xt_find_node(c, "item"))) { +		char *jid = xt_find_attr(c, "jid"); + +		if (!jid || !strchr(jid, '@')) { +			c = c->next; +			continue; +		} + +		bee_chat_info_t *ci = g_new(bee_chat_info_t, 1); +		ci->title = g_strdup(xt_find_attr(c, "jid")); +		ci->topic = g_strdup(xt_find_attr(c, "name")); +		rooms = g_slist_prepend(rooms, ci); + +		c = c->next; +	} + +	imcb_chat_list_free(ic); +	ic->chatlist = g_slist_reverse(rooms); +	imcb_chat_list_finish(ic); + +	return XT_HANDLED; +} diff --git a/protocols/jabber/jabber.c b/protocols/jabber/jabber.c index 36f56fb1..f31abc50 100644 --- a/protocols/jabber/jabber.c +++ b/protocols/jabber/jabber.c @@ -320,6 +320,8 @@ static void jabber_logout(struct im_connection *ic)  {  	struct jabber_data *jd = ic->proto_data; +	imcb_chat_list_free(ic); +  	while (jd->filetransfers) {  		imcb_file_canceled(ic, (( struct jabber_transfer *) jd->filetransfers->data)->ft, "Logging out");  	} @@ -592,6 +594,21 @@ static struct groupchat *jabber_chat_with_(struct im_connection *ic, char *who)  	return jabber_chat_with(ic, who);  } +static void jabber_chat_list_(struct im_connection *ic, const char *server) +{ +	struct jabber_data *jd = ic->proto_data; + +	if (server && *server) { +		jabber_iq_disco_muc(ic, server); +	} else if (jd->muc_host && *jd->muc_host) { +		jabber_iq_disco_muc(ic, jd->muc_host); +	} else { +		/* throw an error here, don't query conference.[server] directly. +		 * for things like jabber.org it gets you 18000 results of garbage */ +		imcb_error(ic, "Please specify a server name such as `conference.%s'", jd->server); +	} +} +  static void jabber_chat_msg_(struct groupchat *c, char *message, int flags)  {  	if (c && message) { @@ -767,6 +784,7 @@ void jabber_initmodule()  	ret->chat_leave = jabber_chat_leave_;  	ret->chat_join = jabber_chat_join_;  	ret->chat_with = jabber_chat_with_; +	ret->chat_list = jabber_chat_list_;  	ret->chat_add_settings = jabber_chat_add_settings;  	ret->chat_free_settings = jabber_chat_free_settings;  	ret->keepalive = jabber_keepalive; diff --git a/protocols/jabber/jabber.h b/protocols/jabber/jabber.h index db43f205..7774c855 100644 --- a/protocols/jabber/jabber.h +++ b/protocols/jabber/jabber.h @@ -262,6 +262,7 @@ xt_status jabber_iq_query_features(struct im_connection *ic, char *bare_jid);  xt_status jabber_iq_query_server(struct im_connection *ic, char *jid, char *xmlns);  void jabber_iq_version_send(struct im_connection *ic, struct jabber_buddy *bud, void *data);  int jabber_iq_disco_server(struct im_connection *ic); +int jabber_iq_disco_muc(struct im_connection *ic, const char *muc_server);  /* si.c */  int jabber_si_handle_request(struct im_connection *ic, struct xt_node *node, struct xt_node *sinode); | 
