diff --git a/gajim/common/connection.py b/gajim/common/connection.py index 734481356..b2ad7358f 100644 --- a/gajim/common/connection.py +++ b/gajim/common/connection.py @@ -66,6 +66,7 @@ from gajim.common import idle from gajim.common.modules.entity_time import EntityTime from gajim.common.modules.software_version import SoftwareVersion from gajim.common.modules.ping import Ping +from gajim.common.modules.search import Search from gajim.common.connection_handlers import * from gajim.common.contacts import GC_Contact from gajim.gtkgui_helpers import get_action @@ -663,6 +664,7 @@ class Connection(CommonConnection, ConnectionHandlers): self.register_module('EntityTime', EntityTime, self) self.register_module('SoftwareVersion', SoftwareVersion, self) self.register_module('Ping', Ping, self) + self.register_module('Search', Search, self) app.ged.register_event_handler('privacy-list-received', ged.CORE, self._nec_privacy_list_received) @@ -2938,24 +2940,6 @@ class Connection(CommonConnection, ConnectionHandlers): else: self.time_to_reconnect = None - def request_search_fields(self, jid): - iq = nbxmpp.Iq(typ='get', to=jid, queryNS=nbxmpp.NS_SEARCH) - self.connection.send(iq) - - def send_search_form(self, jid, form, is_form): - iq = nbxmpp.Iq(typ='set', to=jid, queryNS=nbxmpp.NS_SEARCH) - item = iq.setQuery() - if is_form: - item.addChild(node=form) - else: - for i in form.keys(): - item.setTagData(i, form[i]) - def _on_response(resp): - app.nec.push_incoming_event(SearchResultReceivedEvent(None, - conn=self, stanza=resp)) - - self.connection.SendAndCallForResponse(iq, _on_response) - def load_roster_from_db(self): app.nec.push_incoming_event(RosterReceivedEvent(None, conn=self)) diff --git a/gajim/common/connection_handlers.py b/gajim/common/connection_handlers.py index ae1ac3222..be6afc580 100644 --- a/gajim/common/connection_handlers.py +++ b/gajim/common/connection_handlers.py @@ -2018,26 +2018,6 @@ ConnectionHTTPUpload): self.send_awaiting_pep() self.continue_connect_info = None - def _SearchCB(self, con, iq_obj): - log.debug('SearchCB') - app.nec.push_incoming_event(SearchFormReceivedEvent(None, - conn=self, stanza=iq_obj)) - - def _search_fields_received(self, con, iq_obj): - jid = jid = helpers.get_jid_from_iq(iq_obj) - tag = iq_obj.getTag('query', namespace = nbxmpp.NS_SEARCH) - if not tag: - self.dispatch('SEARCH_FORM', (jid, None, False)) - return - df = tag.getTag('x', namespace=nbxmpp.NS_DATA) - if df: - self.dispatch('SEARCH_FORM', (jid, df, True)) - return - df = {} - for i in iq_obj.getQueryPayload(): - df[i.getName()] = i.getData() - self.dispatch('SEARCH_FORM', (jid, df, False)) - def _PubkeyGetCB(self, con, iq_obj): log.info('PubkeyGetCB') jid_from = helpers.get_full_jid_from_iq(iq_obj) @@ -2145,7 +2125,6 @@ ConnectionHTTPUpload): nbxmpp.NS_DISCO_INFO) con.RegisterHandler('iq', self._DiscoverItemsGetCB, 'get', nbxmpp.NS_DISCO_ITEMS) - con.RegisterHandler('iq', self._SearchCB, 'result', nbxmpp.NS_SEARCH) con.RegisterHandler('iq', self._PrivacySetCB, 'set', nbxmpp.NS_PRIVACY) con.RegisterHandler('iq', self._ArchiveCB, ns=nbxmpp.NS_MAM_1) con.RegisterHandler('iq', self._ArchiveCB, ns=nbxmpp.NS_MAM_2) diff --git a/gajim/common/connection_handlers_events.py b/gajim/common/connection_handlers_events.py index 56e6c61ce..ff3446467 100644 --- a/gajim/common/connection_handlers_events.py +++ b/gajim/common/connection_handlers_events.py @@ -513,51 +513,6 @@ class PubsubBookmarksReceivedEvent(nec.NetworkIncomingEvent, BookmarksHelper): self.parse_bookmarks() return True -class SearchFormReceivedEvent(nec.NetworkIncomingEvent, HelperEvent): - name = 'search-form-received' - base_network_events = [] - - def generate(self): - self.get_jid_resource() - self.data = None - self.is_dataform = False - tag = self.stanza.getTag('query', namespace=nbxmpp.NS_SEARCH) - if not tag: - return True - self.data = tag.getTag('x', namespace=nbxmpp.NS_DATA) - if self.data: - self.is_dataform = True - return True - self.data = {} - for i in self.stanza.getQueryPayload(): - self.data[i.getName()] = i.getData() - return True - - -class SearchResultReceivedEvent(nec.NetworkIncomingEvent, HelperEvent): - name = 'search-result-received' - base_network_events = [] - - def generate(self): - self.get_jid_resource() - self.data = None - self.is_dataform = False - tag = self.stanza.getTag('query', namespace=nbxmpp.NS_SEARCH) - if not tag: - return True - self.data = tag.getTag('x', namespace=nbxmpp.NS_DATA) - if self.data: - self.is_dataform = True - return True - self.data = [] - for item in tag.getTags('item'): - # We also show attributes. jid is there - f = item.attrs - for i in item.getPayload(): - f[i.getName()] = i.getData() - self.data.append(f) - return True - class IqErrorReceivedEvent(nec.NetworkIncomingEvent, HelperEvent): name = 'iq-error-received' base_network_events = [] diff --git a/gajim/common/modules/search.py b/gajim/common/modules/search.py new file mode 100644 index 000000000..35342c124 --- /dev/null +++ b/gajim/common/modules/search.py @@ -0,0 +1,114 @@ +# This file is part of Gajim. +# +# Gajim is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published +# by the Free Software Foundation; version 3 only. +# +# Gajim is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with Gajim. If not, see . + +# XEP-0055: Jabber Search + +import logging + +import nbxmpp + +from gajim.common import app +from gajim.common.nec import NetworkIncomingEvent + +log = logging.getLogger('gajim.c.m.search') + + +class Search: + def __init__(self, con): + self._con = con + self._account = con.name + + self.handlers = [] + + def request_search_fields(self, jid): + log.info('Request search fields from %s', jid) + iq = nbxmpp.Iq(typ='get', to=jid, queryNS=nbxmpp.NS_SEARCH) + self._con.connection.SendAndCallForResponse(iq, self._fields_received) + + def _fields_received(self, stanza): + data = None + is_dataform = False + + if nbxmpp.isResultNode(stanza): + log.info('Received search fields from %s', stanza.getFrom()) + tag = stanza.getTag('query', namespace=nbxmpp.NS_SEARCH) + if tag is None: + log.info('Invalid stanza: %s', stanza) + return + + data = tag.getTag('x', namespace=nbxmpp.NS_DATA) + if data is not None: + is_dataform = True + else: + data = {} + for i in stanza.getQueryPayload(): + data[i.getName()] = i.getData() + else: + log.info('Error: %s', stanza.getError()) + + app.nec.push_incoming_event( + SearchFormReceivedEvent(None, conn=self._con, + is_dataform=is_dataform, + data=data)) + + def send_search_form(self, jid, form, is_form): + iq = nbxmpp.Iq(typ='set', to=jid, queryNS=nbxmpp.NS_SEARCH) + item = iq.setQuery() + if is_form: + item.addChild(node=form) + else: + for i in form.keys(): + item.setTagData(i, form[i]) + + self._con.connection.SendAndCallForResponse(iq, self._received_result) + + def _received_result(self, stanza): + data = None + is_dataform = False + + if nbxmpp.isResultNode(stanza): + log.info('Received result from %s', stanza.getFrom()) + tag = stanza.getTag('query', namespace=nbxmpp.NS_SEARCH) + if tag is None: + log.info('Invalid stanza: %s', stanza) + return + + data = tag.getTag('x', namespace=nbxmpp.NS_DATA) + if data is not None: + is_dataform = True + else: + data = [] + for item in tag.getTags('item'): + # We also show attributes. jid is there + f = item.attrs + for i in item.getPayload(): + f[i.getName()] = i.getData() + data.append(f) + else: + log.info('Error: %s', stanza.getError()) + + app.nec.push_incoming_event( + SearchResultReceivedEvent(None, conn=self._con, + is_dataform=is_dataform, + data=data)) + + +class SearchFormReceivedEvent(NetworkIncomingEvent): + name = 'search-form-received' + base_network_events = [] + + +class SearchResultReceivedEvent(NetworkIncomingEvent): + name = 'search-result-received' + base_network_events = [] diff --git a/gajim/search_window.py b/gajim/search_window.py index cfdd79b8e..7837e3867 100644 --- a/gajim/search_window.py +++ b/gajim/search_window.py @@ -68,7 +68,8 @@ class SearchWindow: self._nec_search_result_received) def request_form(self): - app.connections[self.account].request_search_fields(self.jid) + con = app.connections[self.account] + con.get_module('Search').request_search_fields(self.jid) def pulse_callback(self): self.progressbar.pulse() @@ -91,16 +92,16 @@ class SearchWindow: self.window.destroy() def on_search_button_clicked(self, button): + con = app.connections[self.account] if self.is_form: self.data_form_widget.data_form.type_ = 'submit' - app.connections[self.account].send_search_form(self.jid, - self.data_form_widget.data_form.get_purged(), True) + con.get_module('Search').send_search_form( + self.jid, self.data_form_widget.data_form.get_purged(), True) else: infos = self.data_form_widget.get_infos() if 'instructions' in infos: del infos['instructions'] - app.connections[self.account].send_search_form(self.jid, infos, - False) + con.get_module('Search').send_search_form(self.jid, infos, False) self.search_vbox.remove(self.data_form_widget)