diff --git a/src/common/connection_handlers.py b/src/common/connection_handlers.py index 1e7d05c6a..09d263def 100644 --- a/src/common/connection_handlers.py +++ b/src/common/connection_handlers.py @@ -103,7 +103,8 @@ class ConnectionDisco: jid is mandatory; name, node, action is optional. """ - self._discover(nbxmpp.NS_DISCO_ITEMS, jid, node, id_prefix) + id_ = self._discover(nbxmpp.NS_DISCO_ITEMS, jid, node, id_prefix) + self.disco_items_ids.append(id_) def discoverInfo(self, jid, node=None, id_prefix=None): """ @@ -111,7 +112,8 @@ class ConnectionDisco: For identity: category, type is mandatory, name is optional. For feature: var is mandatory. """ - self._discover(nbxmpp.NS_DISCO_INFO, jid, node, id_prefix) + id_ = self._discover(nbxmpp.NS_DISCO_INFO, jid, node, id_prefix) + self.disco_info_ids.append(id_) def request_register_agent_info(self, agent): if not self.connection or self.connected < 2: @@ -165,12 +167,14 @@ class ConnectionDisco: if not self.connection or self.connected < 2: return iq = nbxmpp.Iq(typ='get', to=jid, queryNS=ns) + id_ = self.connection.getAnID() if id_prefix: - id_ = self.connection.getAnID() - iq.setID('%s%s' % (id_prefix, id_)) + id_ = id_prefix + id_ + iq.setID(id_) if node: iq.setQuerynode(node) self.connection.send(iq) + return id_ def _ReceivedRegInfo(self, con, resp, agent): nbxmpp.features_nb._ReceivedRegInfo(con, resp, agent) @@ -1437,6 +1441,10 @@ ConnectionJingle, ConnectionIBBytestream): self.version_ids = [] # IDs of urn:xmpp:time requests self.entity_time_ids = [] + # IDs of disco#items requests + self.disco_items_ids = [] + # IDs of disco#info requests + self.disco_info_ids = [] # ID of urn:xmpp:ping requests self.awaiting_xmpp_ping_id = None self.continue_connect_info = None @@ -1588,6 +1596,14 @@ ConnectionJingle, ConnectionIBBytestream): gajim.nec.push_incoming_event(TimeResultReceivedEvent(None, conn=self, stanza=obj.stanza)) return True + if obj.id_ in self.disco_items_ids: + gajim.nec.push_incoming_event(AgentItemsErrorReceivedEvent(None, + conn=self, stanza=obj.stanza)) + return True + if obj.id_ in self.disco_info_ids: + gajim.nec.push_incoming_event(AgentInfoErrorReceivedEvent(None, + conn=self, stanza=obj.stanza)) + return True def _nec_private_storate_bookmarks_received(self, obj): if obj.conn.name != self.name: diff --git a/src/common/connection_handlers_events.py b/src/common/connection_handlers_events.py index 8a100f71b..5812829f7 100644 --- a/src/common/connection_handlers_events.py +++ b/src/common/connection_handlers_events.py @@ -1927,6 +1927,8 @@ class AgentItemsReceivedEvent(nec.NetworkIncomingEvent, HelperEvent): self.get_jid_resource() hostname = gajim.config.get_per('accounts', self.conn.name, 'hostname') self.get_id() + if self.id_ in self.conn.disco_items_ids: + self.conn.disco_items_ids.remove(self.id_) if self.fjid == hostname and self.id_[:6] == 'Gajim_': for item in self.items: self.conn.discoverInfo(item['jid'], id_prefix='Gajim_') @@ -1939,6 +1941,9 @@ class AgentItemsErrorReceivedEvent(nec.NetworkIncomingEvent, HelperEvent): def generate(self): self.get_jid_resource() + self.get_id() + if self.id_ in self.conn.disco_items_ids: + self.conn.disco_items_ids.remove(self.id_) return True class AgentInfoReceivedEvent(nec.NetworkIncomingEvent, HelperEvent): @@ -1947,6 +1952,8 @@ class AgentInfoReceivedEvent(nec.NetworkIncomingEvent, HelperEvent): def generate(self): self.get_id() + if self.id_ in self.conn.disco_info_ids: + self.conn.disco_info_ids.remove(self.id_) if self.id_ is None: log.warning('Invalid IQ received without an ID. Ignoring it: %s' % \ self.stanza) @@ -1991,6 +1998,8 @@ class AgentInfoErrorReceivedEvent(nec.NetworkIncomingEvent, HelperEvent): def generate(self): self.get_jid_resource() self.get_id() + if self.id_ in self.conn.disco_info_ids: + self.conn.disco_info_ids.remove(self.id_) return True class FileRequestReceivedEvent(nec.NetworkIncomingEvent, HelperEvent): diff --git a/src/dialogs.py b/src/dialogs.py index 3b930f07c..41a9c65c3 100644 --- a/src/dialogs.py +++ b/src/dialogs.py @@ -36,6 +36,7 @@ from gi.repository import GObject from gi.repository import GLib import cairo import os +import nbxmpp import gtkgui_helpers import vcard @@ -2431,6 +2432,11 @@ class JoinGroupchatWindow: hbox1 = self.xml.get_object('hbox1') hbox1.pack_start(self.server_comboboxentry, False, False, 0) + entry = self.server_comboboxentry.child + entry.connect('changed', self.on_server_entry_changed) + self.browse_button = self.xml.get_object('browse_rooms_button') + self.browse_button.set_sensitive(False) + self.recently_combobox = self.xml.get_object('recently_combobox') liststore = Gtk.ListStore(str, str) self.recently_combobox.set_model(liststore) @@ -2480,12 +2486,22 @@ class JoinGroupchatWindow: if account and not gajim.connections[account].private_storage_supported: self.xml.get_object('bookmark_checkbutton').set_sensitive(False) + self.requested_jid = None + gajim.ged.register_event_handler('agent-info-received', ged.GUI1, + self._nec_agent_info_received) + gajim.ged.register_event_handler('agent-info-error-received', ged.GUI1, + self._nec_agent_info_error_received) + self.window.show_all() def on_join_groupchat_window_destroy(self, widget): """ Close window """ + gajim.ged.remove_event_handler('agent-info-received', ged.GUI1, + self._nec_agent_info_received) + gajim.ged.register_event_handler('agent-info-error-received', ged.GUI1, + self._nec_agent_info_error_received) if self.account and 'join_gc' in gajim.interface.instances[self.account]: # remove us from open windows del gajim.interface.instances[self.account]['join_gc'] @@ -2535,19 +2551,47 @@ class JoinGroupchatWindow: def on_browse_rooms_button_clicked(self, widget): server = self.server_comboboxentry.get_child().get_text() - if server in gajim.interface.instances[self.account]['disco']: - gajim.interface.instances[self.account]['disco'][server].window.\ + self.requested_jid = server + gajim.connections[self.account].discoverInfo(server) + + def _nec_agent_info_error_received(self, obj): + if obj.conn.name != self.account: + return + if obj.jid != self.requested_jid: + return + self.requested_jid = None + ErrorDialog(_('Wrong server'), _('%s is not a groupchat server') % \ + obj.jid) + + def _nec_agent_info_received(self, obj): + if obj.conn.name != self.account: + return + if obj.jid != self.requested_jid: + return + self.requested_jid = None + if nbxmpp.NS_MUC not in obj.features: + ErrorDialog(_('Wrong server'), _('%s is not a groupchat server') % \ + obj.jid) + return + if obj.jid in gajim.interface.instances[self.account]['disco']: + gajim.interface.instances[self.account]['disco'][obj.jid].window.\ present() else: try: # Object will add itself to the window dict import disco - disco.ServiceDiscoveryWindow(self.account, server, + disco.ServiceDiscoveryWindow(self.account, obj.jid, initial_identities=[{'category': 'conference', 'type': 'text'}]) except GajimGeneralException: pass + def on_server_entry_changed(self, widget): + if not widget.get_text(): + self.browse_button.set_sensitive(False) + else: + self.browse_button.set_sensitive(True) + def on_cancel_button_clicked(self, widget): """ When Cancel button is clicked