Philipp Hörist pushed to branch master at gajim / gajim
Commits:
-
de1866a6
by Philipp Hörist at 2019-08-17T10:53:44Z
-
01be1d6f
by Philipp Hörist at 2019-08-17T10:54:46Z
-
f54a1677
by Philipp Hörist at 2019-08-17T10:55:27Z
-
cf14c04d
by Philipp Hörist at 2019-08-17T10:55:27Z
17 changed files:
- gajim/common/caps_cache.py
- gajim/common/contacts.py
- gajim/common/helpers.py
- gajim/common/logger.py
- gajim/common/modules/discovery.py
- gajim/common/modules/iq.py
- gajim/common/modules/mam.py
- gajim/common/modules/message.py
- gajim/common/modules/muc.py
- gajim/dialog_messages.py
- gajim/gajim.py
- gajim/groupchat_control.py
- gajim/gtk/groupchat_config.py
- gajim/gtk/groupchat_join.py
- gajim/gtk/start_chat.py
- setup.cfg
- test/no_gui/unit/test_caps_cache.py
Changes:
| ... | ... | @@ -29,8 +29,6 @@ through ClientCaps objects which are hold by contact instances. |
| 29 | 29 |
|
| 30 | 30 |
import logging
|
| 31 | 31 |
|
| 32 |
-import nbxmpp
|
|
| 33 |
-from nbxmpp.const import Affiliation
|
|
| 34 | 32 |
from nbxmpp import (NS_XHTML_IM, NS_ESESSION, NS_CHATSTATES,
|
| 35 | 33 |
NS_JINGLE_ICE_UDP, NS_JINGLE_RTP_AUDIO, NS_JINGLE_RTP_VIDEO,
|
| 36 | 34 |
NS_JINGLE_FILE_TRANSFER_5)
|
| ... | ... | @@ -52,15 +50,13 @@ FAKED = 3 # allow NullClientCaps to behave as it has a cached item |
| 52 | 50 |
################################################################################
|
| 53 | 51 |
|
| 54 | 52 |
capscache = None
|
| 55 |
-muc_caps_cache = None
|
|
| 53 |
+ |
|
| 56 | 54 |
def initialize(logger):
|
| 57 | 55 |
"""
|
| 58 | 56 |
Initialize this module
|
| 59 | 57 |
"""
|
| 60 | 58 |
global capscache
|
| 61 |
- global muc_caps_cache
|
|
| 62 | 59 |
capscache = CapsCache(logger)
|
| 63 |
- muc_caps_cache = MucCapsCache()
|
|
| 64 | 60 |
|
| 65 | 61 |
def client_supports(client_caps, requested_feature):
|
| 66 | 62 |
lookup_item = client_caps.get_cache_lookup_strategy()
|
| ... | ... | @@ -333,87 +329,3 @@ class CapsCache: |
| 333 | 329 |
key = (hash_method, hash_)
|
| 334 | 330 |
if key in self.__cache:
|
| 335 | 331 |
del self.__cache[key]
|
| 336 |
- |
|
| 337 |
- |
|
| 338 |
-class MucCapsCache:
|
|
| 339 |
- |
|
| 340 |
- def __init__(self):
|
|
| 341 |
- self.cache = {}
|
|
| 342 |
- |
|
| 343 |
- def append(self, info):
|
|
| 344 |
- if nbxmpp.NS_MUC not in info.features:
|
|
| 345 |
- # Not a MUC, don't cache info
|
|
| 346 |
- return
|
|
| 347 |
- |
|
| 348 |
- self.cache[info.jid] = info
|
|
| 349 |
- |
|
| 350 |
- def is_cached(self, jid):
|
|
| 351 |
- return jid in self.cache
|
|
| 352 |
- |
|
| 353 |
- def supports(self, jid, feature):
|
|
| 354 |
- if jid in self.cache:
|
|
| 355 |
- if feature in self.cache[jid].features:
|
|
| 356 |
- return True
|
|
| 357 |
- return False
|
|
| 358 |
- |
|
| 359 |
- def has_mam(self, jid):
|
|
| 360 |
- try:
|
|
| 361 |
- if nbxmpp.NS_MAM_2 in self.cache[jid].features:
|
|
| 362 |
- return True
|
|
| 363 |
- if nbxmpp.NS_MAM_1 in self.cache[jid].features:
|
|
| 364 |
- return True
|
|
| 365 |
- return False
|
|
| 366 |
- except (KeyError, AttributeError):
|
|
| 367 |
- return False
|
|
| 368 |
- |
|
| 369 |
- def get_mam_namespace(self, jid):
|
|
| 370 |
- try:
|
|
| 371 |
- if nbxmpp.NS_MAM_2 in self.cache[jid].features:
|
|
| 372 |
- return nbxmpp.NS_MAM_2
|
|
| 373 |
- if nbxmpp.NS_MAM_1 in self.cache[jid].features:
|
|
| 374 |
- return nbxmpp.NS_MAM_1
|
|
| 375 |
- except (KeyError, AttributeError):
|
|
| 376 |
- return
|
|
| 377 |
- |
|
| 378 |
- def is_subject_change_allowed(self, jid, affiliation):
|
|
| 379 |
- allowed = True
|
|
| 380 |
- if affiliation in (Affiliation.OWNER, Affiliation.ADMIN):
|
|
| 381 |
- return allowed
|
|
| 382 |
- |
|
| 383 |
- if jid in self.cache:
|
|
| 384 |
- for form in self.cache[jid].dataforms:
|
|
| 385 |
- try:
|
|
| 386 |
- allowed = form['muc#roominfo_changesubject'].value
|
|
| 387 |
- except KeyError:
|
|
| 388 |
- pass
|
|
| 389 |
- return allowed
|
|
| 390 |
- |
|
| 391 |
- def is_open(self, jid):
|
|
| 392 |
- return 'muc_membersonly' not in self.cache[jid].features
|
|
| 393 |
- |
|
| 394 |
- def is_password_protected(self, jid):
|
|
| 395 |
- return 'muc_unsecured' not in self.cache[jid].features
|
|
| 396 |
- |
|
| 397 |
- def is_anonymous(self, jid):
|
|
| 398 |
- return 'muc_nonanonymous' not in self.cache[jid].features
|
|
| 399 |
- |
|
| 400 |
- def is_persistent(self, jid):
|
|
| 401 |
- return 'muc_temporary' not in self.cache[jid].features
|
|
| 402 |
- |
|
| 403 |
- def get_room_infos(self, jid):
|
|
| 404 |
- room_info = {}
|
|
| 405 |
- if jid in self.cache:
|
|
| 406 |
- for form in self.cache[jid].dataforms:
|
|
| 407 |
- try:
|
|
| 408 |
- room_info['name'] = form['muc#roomconfig_roomname'].value
|
|
| 409 |
- except KeyError:
|
|
| 410 |
- room_info['name'] = None
|
|
| 411 |
- try:
|
|
| 412 |
- room_info['desc'] = form['muc#roominfo_description'].value
|
|
| 413 |
- except KeyError:
|
|
| 414 |
- room_info['desc'] = None
|
|
| 415 |
- try:
|
|
| 416 |
- room_info['lang'] = form['muc#roominfo_lang'].value
|
|
| 417 |
- except KeyError:
|
|
| 418 |
- room_info['lang'] = None
|
|
| 419 |
- return room_info or None
|
| ... | ... | @@ -188,11 +188,10 @@ class Contact(CommonContact): |
| 188 | 188 |
if name:
|
| 189 | 189 |
return name
|
| 190 | 190 |
|
| 191 |
- cache = caps_cache.muc_caps_cache.cache
|
|
| 192 |
- if self.jid in cache:
|
|
| 193 |
- name = cache[self.jid].muc_room_name
|
|
| 194 |
- if name:
|
|
| 195 |
- return name
|
|
| 191 |
+ disco_info = app.logger.get_last_disco_info(self.jid)
|
|
| 192 |
+ if disco_info is not None:
|
|
| 193 |
+ if disco_info.muc_room_name:
|
|
| 194 |
+ return disco_info.muc_room_name
|
|
| 196 | 195 |
return self.jid.split('@')[0]
|
| 197 | 196 |
|
| 198 | 197 |
def get_shown_groups(self):
|
| ... | ... | @@ -65,7 +65,6 @@ from gi.repository import GLib |
| 65 | 65 |
import precis_i18n.codec # pylint: disable=unused-import
|
| 66 | 66 |
|
| 67 | 67 |
from gajim.common import app
|
| 68 |
-from gajim.common import caps_cache
|
|
| 69 | 68 |
from gajim.common import configpaths
|
| 70 | 69 |
from gajim.common.i18n import Q_
|
| 71 | 70 |
from gajim.common.i18n import _
|
| ... | ... | @@ -1087,10 +1086,11 @@ def update_optional_features(account=None): |
| 1087 | 1086 |
# Give plugins the possibility to add their features
|
| 1088 | 1087 |
app.plugin_manager.extension_point('update_caps', account_)
|
| 1089 | 1088 |
|
| 1090 |
- app.caps_hash[account_] = compute_caps_hash(DiscoInfo(
|
|
| 1091 |
- None, None, [app.gajim_identity],
|
|
| 1092 |
- app.gajim_common_features + features,
|
|
| 1093 |
- []), compare=False)
|
|
| 1089 |
+ disco_info = DiscoInfo(None,
|
|
| 1090 |
+ [app.gajim_identity],
|
|
| 1091 |
+ app.gajim_common_features + features,
|
|
| 1092 |
+ [])
|
|
| 1093 |
+ app.caps_hash[account_] = compute_caps_hash(disco_info, compare=False)
|
|
| 1094 | 1094 |
# re-send presence with new hash
|
| 1095 | 1095 |
connected = app.connections[account_].connected
|
| 1096 | 1096 |
if connected > 1 and app.SHOW_LIST[connected] != 'invisible':
|
| ... | ... | @@ -1334,9 +1334,9 @@ def call_counter(func): |
| 1334 | 1334 |
return helper
|
| 1335 | 1335 |
|
| 1336 | 1336 |
def get_sync_threshold(jid, archive_info):
|
| 1337 |
- cache = caps_cache.muc_caps_cache
|
|
| 1337 |
+ disco_info = app.logger.get_last_disco_info(jid)
|
|
| 1338 | 1338 |
if archive_info is None or archive_info.sync_threshold is None:
|
| 1339 |
- if cache.supports(jid, 'muc#roomconfig_membersonly'):
|
|
| 1339 |
+ if disco_info is not None and disco_info.muc_is_members_only:
|
|
| 1340 | 1340 |
threshold = app.config.get('private_room_sync_threshold')
|
| 1341 | 1341 |
else:
|
| 1342 | 1342 |
threshold = app.config.get('public_room_sync_threshold')
|
| ... | ... | @@ -38,8 +38,10 @@ from collections import namedtuple |
| 38 | 38 |
from gi.repository import GLib
|
| 39 | 39 |
|
| 40 | 40 |
from nbxmpp.protocol import Node
|
| 41 |
+from nbxmpp.protocol import Iq
|
|
| 41 | 42 |
from nbxmpp.structs import DiscoInfo
|
| 42 | 43 |
from nbxmpp.modules.dataforms import extend_form
|
| 44 |
+from nbxmpp.modules.discovery import parse_disco_info
|
|
| 43 | 45 |
|
| 44 | 46 |
from gajim.common import exceptions
|
| 45 | 47 |
from gajim.common import app
|
| ... | ... | @@ -105,6 +107,11 @@ CACHE_SQL_STATEMENT = ''' |
| 105 | 107 |
data TEXT,
|
| 106 | 108 |
last_seen INTEGER
|
| 107 | 109 |
);
|
| 110 |
+ CREATE TABLE last_seen_disco_info(
|
|
| 111 |
+ jid TEXT PRIMARY KEY UNIQUE,
|
|
| 112 |
+ disco_info TEXT,
|
|
| 113 |
+ last_seen INTEGER
|
|
| 114 |
+ );
|
|
| 108 | 115 |
CREATE TABLE roster_entry(
|
| 109 | 116 |
account_jid_id INTEGER,
|
| 110 | 117 |
jid_id INTEGER,
|
| ... | ... | @@ -120,7 +127,7 @@ CACHE_SQL_STATEMENT = ''' |
| 120 | 127 |
group_name TEXT,
|
| 121 | 128 |
PRIMARY KEY (account_jid_id, jid_id, group_name)
|
| 122 | 129 |
);
|
| 123 |
- PRAGMA user_version=2;
|
|
| 130 |
+ PRAGMA user_version=3;
|
|
| 124 | 131 |
'''
|
| 125 | 132 |
|
| 126 | 133 |
log = logging.getLogger('gajim.c.logger')
|
| ... | ... | @@ -170,6 +177,17 @@ def caps_decoder(dict_): |
| 170 | 177 |
dataforms=dataforms)
|
| 171 | 178 |
|
| 172 | 179 |
|
| 180 |
+def _convert_disco_info(disco_info):
|
|
| 181 |
+ return parse_disco_info(Iq(node=disco_info))
|
|
| 182 |
+ |
|
| 183 |
+def _adapt_disco_info(disco_info):
|
|
| 184 |
+ return str(disco_info.stanza)
|
|
| 185 |
+ |
|
| 186 |
+sqlite.register_converter('disco_info', _convert_disco_info)
|
|
| 187 |
+ |
|
| 188 |
+sqlite.register_adapter(DiscoInfo, _adapt_disco_info)
|
|
| 189 |
+ |
|
| 190 |
+ |
|
| 173 | 191 |
class Logger:
|
| 174 | 192 |
def __init__(self):
|
| 175 | 193 |
self._jid_ids = {}
|
| ... | ... | @@ -179,6 +197,8 @@ class Logger: |
| 179 | 197 |
self._log_db_path = configpaths.get('LOG_DB')
|
| 180 | 198 |
self._cache_db_path = configpaths.get('CACHE_DB')
|
| 181 | 199 |
|
| 200 |
+ self._disco_info_cache = {}
|
|
| 201 |
+ |
|
| 182 | 202 |
self._create_databases()
|
| 183 | 203 |
self._migrate_databases()
|
| 184 | 204 |
self._connect_databases()
|
| ... | ... | @@ -299,6 +319,16 @@ class Logger: |
| 299 | 319 |
]
|
| 300 | 320 |
self._execute_multiple(con, statements)
|
| 301 | 321 |
|
| 322 |
+ if self._get_user_version(con) < 3:
|
|
| 323 |
+ statements = [
|
|
| 324 |
+ '''CREATE TABLE last_seen_disco_info(
|
|
| 325 |
+ jid TEXT PRIMARY KEY UNIQUE,
|
|
| 326 |
+ disco_info TEXT,
|
|
| 327 |
+ last_seen INTEGER)''',
|
|
| 328 |
+ 'PRAGMA user_version=3'
|
|
| 329 |
+ ]
|
|
| 330 |
+ self._execute_multiple(con, statements)
|
|
| 331 |
+ |
|
| 302 | 332 |
@staticmethod
|
| 303 | 333 |
def _execute_multiple(con, statements):
|
| 304 | 334 |
"""
|
| ... | ... | @@ -341,8 +371,10 @@ class Logger: |
| 341 | 371 |
app.ged.raise_event(event, None, str(error))
|
| 342 | 372 |
|
| 343 | 373 |
def _connect_databases(self):
|
| 344 |
- self._con = self._connect(
|
|
| 345 |
- self._log_db_path, timeout=20.0, isolation_level='IMMEDIATE')
|
|
| 374 |
+ self._con = self._connect(self._log_db_path,
|
|
| 375 |
+ timeout=20.0,
|
|
| 376 |
+ isolation_level='IMMEDIATE',
|
|
| 377 |
+ detect_types=sqlite.PARSE_COLNAMES)
|
|
| 346 | 378 |
|
| 347 | 379 |
self._con.row_factory = self.namedtuple_factory
|
| 348 | 380 |
|
| ... | ... | @@ -1465,3 +1497,55 @@ class Logger: |
| 1465 | 1497 |
self._con.execute(sql, tuple(kwargs.values()) + (jid_id,))
|
| 1466 | 1498 |
log.info('Set message archive info: %s %s', jid, kwargs)
|
| 1467 | 1499 |
self._timeout_commit()
|
| 1500 |
+ |
|
| 1501 |
+ def get_last_disco_info(self, jid):
|
|
| 1502 |
+ """
|
|
| 1503 |
+ Get last disco info from jid
|
|
| 1504 |
+ |
|
| 1505 |
+ :param jid: The jid
|
|
| 1506 |
+ |
|
| 1507 |
+ """
|
|
| 1508 |
+ |
|
| 1509 |
+ if jid in self._disco_info_cache:
|
|
| 1510 |
+ return self._disco_info_cache[jid]
|
|
| 1511 |
+ |
|
| 1512 |
+ sql = '''SELECT disco_info as "disco_info [disco_info]", last_seen FROM
|
|
| 1513 |
+ last_seen_disco_info
|
|
| 1514 |
+ WHERE jid = ?'''
|
|
| 1515 |
+ row = self._con.execute(sql, (str(jid),)).fetchone()
|
|
| 1516 |
+ if row is None:
|
|
| 1517 |
+ return None
|
|
| 1518 |
+ |
|
| 1519 |
+ disco_info = row.disco_info._replace(timestamp=row.last_seen)
|
|
| 1520 |
+ self._disco_info_cache[jid] = disco_info
|
|
| 1521 |
+ return disco_info
|
|
| 1522 |
+ |
|
| 1523 |
+ def set_last_disco_info(self, jid, disco_info):
|
|
| 1524 |
+ """
|
|
| 1525 |
+ Get last disco info from jid
|
|
| 1526 |
+ |
|
| 1527 |
+ :param jid: The jid
|
|
| 1528 |
+ |
|
| 1529 |
+ :param disco_info: A DiscoInfo object
|
|
| 1530 |
+ |
|
| 1531 |
+ """
|
|
| 1532 |
+ |
|
| 1533 |
+ log.info('Save disco info from %s', jid)
|
|
| 1534 |
+ |
|
| 1535 |
+ disco_exists = self.get_last_disco_info(jid) is not None
|
|
| 1536 |
+ if disco_exists:
|
|
| 1537 |
+ sql = '''UPDATE last_seen_disco_info SET
|
|
| 1538 |
+ disco_info = ?, last_seen = ?
|
|
| 1539 |
+ WHERE jid = ?'''
|
|
| 1540 |
+ |
|
| 1541 |
+ self._con.execute(sql, (disco_info, disco_info.timestamp, str(jid)))
|
|
| 1542 |
+ |
|
| 1543 |
+ else:
|
|
| 1544 |
+ sql = '''INSERT INTO last_seen_disco_info
|
|
| 1545 |
+ (jid, disco_info, last_seen)
|
|
| 1546 |
+ VALUES (?, ?, ?)'''
|
|
| 1547 |
+ |
|
| 1548 |
+ self._con.execute(sql, (str(jid), disco_info, disco_info.timestamp))
|
|
| 1549 |
+ |
|
| 1550 |
+ self._disco_info_cache[jid] = disco_info
|
|
| 1551 |
+ self._timeout_commit()
|
| ... | ... | @@ -19,10 +19,9 @@ from nbxmpp.structs import StanzaHandler |
| 19 | 19 |
from nbxmpp.util import is_error_result
|
| 20 | 20 |
|
| 21 | 21 |
from gajim.common import app
|
| 22 |
-from gajim.common.caps_cache import muc_caps_cache
|
|
| 23 | 22 |
from gajim.common.nec import NetworkIncomingEvent
|
| 24 | 23 |
from gajim.common.modules.base import BaseModule
|
| 25 |
-from gajim.common.connection_handlers_events import InformationEvent
|
|
| 24 |
+from gajim.common.nec import NetworkEvent
|
|
| 26 | 25 |
|
| 27 | 26 |
|
| 28 | 27 |
class Discovery(BaseModule):
|
| ... | ... | @@ -197,39 +196,27 @@ class Discovery(BaseModule): |
| 197 | 196 |
self._con.connection.send(iq)
|
| 198 | 197 |
raise nbxmpp.NodeProcessed
|
| 199 | 198 |
|
| 200 |
- def disco_muc(self, jid, callback, update=False):
|
|
| 199 |
+ def disco_muc(self, jid, callback=None):
|
|
| 201 | 200 |
if not app.account_is_connected(self._account):
|
| 202 | 201 |
return
|
| 203 |
- if muc_caps_cache.is_cached(jid) and not update:
|
|
| 204 |
- callback()
|
|
| 205 |
- return
|
|
| 206 | 202 |
|
| 207 |
- self._log.info('Request MUC info %s', jid)
|
|
| 203 |
+ self._log.info('Request MUC info for %s', jid)
|
|
| 208 | 204 |
|
| 209 | 205 |
self.disco_info(jid,
|
| 210 |
- callback=self._muc_info_response,
|
|
| 206 |
+ callback=self._muc_info_received,
|
|
| 211 | 207 |
user_data=callback)
|
| 212 | 208 |
|
| 213 |
- def _muc_info_response(self, result, callback):
|
|
| 214 |
- if is_error_result(result):
|
|
| 215 |
- if result.condition == 'item-not-found':
|
|
| 216 |
- # Groupchat does not exist
|
|
| 217 |
- self._log.info('MUC does not exist: %s', result.jid)
|
|
| 218 |
- callback()
|
|
| 219 |
- else:
|
|
| 220 |
- self._log.info('MUC disco error: %s', result)
|
|
| 221 |
- app.nec.push_incoming_event(
|
|
| 222 |
- InformationEvent(
|
|
| 223 |
- None,
|
|
| 224 |
- dialog_name='unable-join-groupchat',
|
|
| 225 |
- kwargs={
|
|
| 226 |
- 'server': result.jid,
|
|
| 227 |
- 'error': str(result)}))
|
|
| 228 |
- return
|
|
| 229 |
- |
|
| 209 |
+ def _muc_info_received(self, result, callback):
|
|
| 230 | 210 |
self._log.info('MUC info received: %s', result.jid)
|
| 231 |
- muc_caps_cache.append(result)
|
|
| 232 |
- callback()
|
|
| 211 |
+ if not is_error_result(result):
|
|
| 212 |
+ app.logger.set_last_disco_info(result.jid, result)
|
|
| 213 |
+ app.nec.push_incoming_event(NetworkEvent(
|
|
| 214 |
+ 'muc-disco-update',
|
|
| 215 |
+ account=self._account,
|
|
| 216 |
+ room_jid=result.jid))
|
|
| 217 |
+ |
|
| 218 |
+ if callback is not None:
|
|
| 219 |
+ callback(result)
|
|
| 233 | 220 |
|
| 234 | 221 |
|
| 235 | 222 |
def get_instance(*args, **kwargs):
|
| ... | ... | @@ -15,7 +15,6 @@ |
| 15 | 15 |
# Iq handler
|
| 16 | 16 |
|
| 17 | 17 |
import nbxmpp
|
| 18 |
-from nbxmpp.const import Error
|
|
| 19 | 18 |
from nbxmpp.structs import StanzaHandler
|
| 20 | 19 |
|
| 21 | 20 |
from gajim.common import app
|
| ... | ... | @@ -37,13 +36,13 @@ class Iq(BaseModule): |
| 37 | 36 |
|
| 38 | 37 |
def _iq_error_received(self, _con, _stanza, properties):
|
| 39 | 38 |
self._log.info('Error: %s', properties.error)
|
| 40 |
- if properties.error.type in (Error.JID_MALFORMED,
|
|
| 41 |
- Error.FORBIDDEN,
|
|
| 42 |
- Error.NOT_ACCEPTABLE):
|
|
| 39 |
+ if properties.error.condition in ('jid-malformed',
|
|
| 40 |
+ 'forbidden',
|
|
| 41 |
+ 'not-acceptable'):
|
|
| 43 | 42 |
sid = self._get_sid(properties.id)
|
| 44 | 43 |
file_props = FilesProp.getFileProp(self._account, sid)
|
| 45 | 44 |
if file_props:
|
| 46 |
- if properties.error.type == Error.JID_MALFORMED:
|
|
| 45 |
+ if properties.error.condition == 'jid-malformed':
|
|
| 47 | 46 |
file_props.error = -3
|
| 48 | 47 |
else:
|
| 49 | 48 |
file_props.error = -4
|
| ... | ... | @@ -52,11 +51,11 @@ class Iq(BaseModule): |
| 52 | 51 |
conn=self._con,
|
| 53 | 52 |
jid=properties.jid.getBare(),
|
| 54 | 53 |
file_props=file_props,
|
| 55 |
- error_msg=properties.error.message))
|
|
| 54 |
+ error_msg=properties.error.get_text()))
|
|
| 56 | 55 |
self._con.get_module('Bytestream').disconnect_transfer(file_props)
|
| 57 | 56 |
raise nbxmpp.NodeProcessed
|
| 58 | 57 |
|
| 59 |
- if properties.error.type == Error.ITEM_NOT_FOUND:
|
|
| 58 |
+ if properties.error.condition == 'item-not-found':
|
|
| 60 | 59 |
sid = self._get_sid(properties.id)
|
| 61 | 60 |
file_props = FilesProp.getFileProp(self._account, sid)
|
| 62 | 61 |
if file_props:
|
| ... | ... | @@ -26,7 +26,6 @@ from gajim.common.nec import NetworkIncomingEvent |
| 26 | 26 |
from gajim.common.const import ArchiveState
|
| 27 | 27 |
from gajim.common.const import KindConstant
|
| 28 | 28 |
from gajim.common.const import SyncThreshold
|
| 29 |
-from gajim.common.caps_cache import muc_caps_cache
|
|
| 30 | 29 |
from gajim.common.helpers import get_sync_threshold
|
| 31 | 30 |
from gajim.common.helpers import AdditionalDataDict
|
| 32 | 31 |
from gajim.common.modules.misc import parse_oob
|
| ... | ... | @@ -112,7 +111,8 @@ class MAM(BaseModule): |
| 112 | 111 |
|
| 113 | 112 |
if properties.type.is_groupchat:
|
| 114 | 113 |
archive_jid = properties.jid.getBare()
|
| 115 |
- namespace = muc_caps_cache.get_mam_namespace(archive_jid)
|
|
| 114 |
+ disco_info = app.logger.get_last_disco_info(archive_jid)
|
|
| 115 |
+ namespace = disco_info.mam_namespace
|
|
| 116 | 116 |
timestamp = properties.timestamp
|
| 117 | 117 |
if namespace is None:
|
| 118 | 118 |
# MUC History
|
| ... | ... | @@ -536,10 +536,12 @@ class MAM(BaseModule): |
| 536 | 536 |
def _get_archive_query(self, query_id, jid=None, start=None, end=None,
|
| 537 | 537 |
with_=None, after=None, max_=70):
|
| 538 | 538 |
# Muc archive query?
|
| 539 |
- namespace = muc_caps_cache.get_mam_namespace(jid)
|
|
| 540 |
- if namespace is None:
|
|
| 539 |
+ disco_info = app.logger.get_last_disco_info(jid)
|
|
| 540 |
+ if disco_info is None:
|
|
| 541 | 541 |
# Query to our own archive
|
| 542 | 542 |
namespace = self.archiving_namespace
|
| 543 |
+ else:
|
|
| 544 |
+ namespace = disco_info.mam_namespace
|
|
| 543 | 545 |
|
| 544 | 546 |
iq = nbxmpp.Iq('set', to=jid)
|
| 545 | 547 |
query = iq.addChild('query', namespace=namespace)
|
| ... | ... | @@ -25,7 +25,6 @@ from gajim.common.i18n import _ |
| 25 | 25 |
from gajim.common.nec import NetworkIncomingEvent
|
| 26 | 26 |
from gajim.common.nec import NetworkEvent
|
| 27 | 27 |
from gajim.common.helpers import AdditionalDataDict
|
| 28 |
-from gajim.common.caps_cache import muc_caps_cache
|
|
| 29 | 28 |
from gajim.common.const import KindConstant
|
| 30 | 29 |
from gajim.common.modules.base import BaseModule
|
| 31 | 30 |
from gajim.common.modules.util import get_eme_message
|
| ... | ... | @@ -293,8 +292,8 @@ class Message(BaseModule): |
| 293 | 292 |
message_id=event.message_id)
|
| 294 | 293 |
|
| 295 | 294 |
def _check_for_mam_compliance(self, room_jid, stanza_id):
|
| 296 |
- namespace = muc_caps_cache.get_mam_namespace(room_jid)
|
|
| 297 |
- if stanza_id is None and namespace == nbxmpp.NS_MAM_2:
|
|
| 295 |
+ disco_info = app.logger.get_last_disco_info(room_jid)
|
|
| 296 |
+ if stanza_id is None and disco_info.mam_namespace == nbxmpp.NS_MAM_2:
|
|
| 298 | 297 |
self._log.warning('%s announces mam:2 without stanza-id', room_jid)
|
| 299 | 298 |
|
| 300 | 299 |
def _get_unique_id(self, properties):
|
| ... | ... | @@ -306,8 +305,9 @@ class Message(BaseModule): |
| 306 | 305 |
return None, None
|
| 307 | 306 |
|
| 308 | 307 |
if properties.type.is_groupchat:
|
| 309 |
- namespace = muc_caps_cache.get_mam_namespace(
|
|
| 308 |
+ disco_info = app.logger.get_last_disco_info(
|
|
| 310 | 309 |
properties.jid.getBare())
|
| 310 |
+ namespace = disco_info.mam_namespace
|
|
| 311 | 311 |
archive = properties.jid
|
| 312 | 312 |
else:
|
| 313 | 313 |
namespace = self._con.get_module('MAM').archiving_namespace
|
| ... | ... | @@ -20,12 +20,10 @@ import logging |
| 20 | 20 |
from datetime import datetime
|
| 21 | 21 |
from datetime import timedelta
|
| 22 | 22 |
from datetime import timezone
|
| 23 |
-from functools import partial
|
|
| 24 | 23 |
|
| 25 | 24 |
import nbxmpp
|
| 26 | 25 |
from nbxmpp.const import InviteType
|
| 27 | 26 |
from nbxmpp.const import PresenceType
|
| 28 |
-from nbxmpp.const import Error
|
|
| 29 | 27 |
from nbxmpp.structs import StanzaHandler
|
| 30 | 28 |
from nbxmpp.util import is_error_result
|
| 31 | 29 |
|
| ... | ... | @@ -41,7 +39,6 @@ from gajim.common.helpers import get_default_muc_config |
| 41 | 39 |
from gajim.common.helpers import get_sync_threshold
|
| 42 | 40 |
from gajim.common.helpers import to_user_string
|
| 43 | 41 |
from gajim.common import idle
|
| 44 |
-from gajim.common.caps_cache import muc_caps_cache
|
|
| 45 | 42 |
from gajim.common.nec import NetworkEvent
|
| 46 | 43 |
from gajim.common.modules.bits_of_binary import store_bob_data
|
| 47 | 44 |
from gajim.common.modules.base import BaseModule
|
| ... | ... | @@ -145,7 +142,20 @@ class MUC(BaseModule): |
| 145 | 142 |
self._muc_data[muc_data.jid] = muc_data
|
| 146 | 143 |
|
| 147 | 144 |
self._con.get_module('Discovery').disco_muc(
|
| 148 |
- muc_data.jid, partial(self._join, muc_data))
|
|
| 145 |
+ muc_data.jid,
|
|
| 146 |
+ callback=self._on_disco_result)
|
|
| 147 |
+ |
|
| 148 |
+ def _on_disco_result(self, result):
|
|
| 149 |
+ if is_error_result(result):
|
|
| 150 |
+ self._log.info('Disco %s failed: %s', result.jid, result.get_text())
|
|
| 151 |
+ app.nec.push_incoming_event(
|
|
| 152 |
+ NetworkEvent('muc-join-failed',
|
|
| 153 |
+ account=self._account,
|
|
| 154 |
+ room_jid=result.jid.getBare(),
|
|
| 155 |
+ error=result))
|
|
| 156 |
+ return
|
|
| 157 |
+ |
|
| 158 |
+ self._join(self._get_muc_data(result.jid))
|
|
| 149 | 159 |
|
| 150 | 160 |
def _join(self, muc_data):
|
| 151 | 161 |
show = helpers.get_xmpp_show(app.SHOW_LIST[self._con.connected])
|
| ... | ... | @@ -228,8 +238,7 @@ class MUC(BaseModule): |
| 228 | 238 |
account=self._account,
|
| 229 | 239 |
room_jid=result.jid))
|
| 230 | 240 |
|
| 231 |
- self._con.get_module('Discovery').disco_muc(
|
|
| 232 |
- result.jid, partial(self._on_disco_update, result.jid), update=True)
|
|
| 241 |
+ self._con.get_module('Discovery').disco_muc(result.jid)
|
|
| 233 | 242 |
|
| 234 | 243 |
# If this is an automatic room creation
|
| 235 | 244 |
try:
|
| ... | ... | @@ -245,12 +254,6 @@ class MUC(BaseModule): |
| 245 | 254 |
for jid in invites:
|
| 246 | 255 |
self.invite(result.jid, jid)
|
| 247 | 256 |
|
| 248 |
- def _on_disco_update(self, room_jid):
|
|
| 249 |
- app.nec.push_incoming_event(NetworkEvent(
|
|
| 250 |
- 'muc-disco-update',
|
|
| 251 |
- account=self._account,
|
|
| 252 |
- room_jid=room_jid))
|
|
| 253 |
- |
|
| 254 | 257 |
def update_presence(self, auto=False):
|
| 255 | 258 |
mucs = self.get_mucs_with_state([MUCJoinedState.JOINED,
|
| 256 | 259 |
MUCJoinedState.JOINING])
|
| ... | ... | @@ -291,7 +294,8 @@ class MUC(BaseModule): |
| 291 | 294 |
status=self._con.status)
|
| 292 | 295 |
|
| 293 | 296 |
def _add_history_query(self, muc_x, room_jid):
|
| 294 |
- if muc_caps_cache.has_mam(room_jid):
|
|
| 297 |
+ disco_info = app.logger.get_last_disco_info(room_jid)
|
|
| 298 |
+ if disco_info.has_mam:
|
|
| 295 | 299 |
# The room is MAM capable dont get MUC History
|
| 296 | 300 |
muc_x.setTag('history', {'maxchars': '0'})
|
| 297 | 301 |
else:
|
| ... | ... | @@ -322,23 +326,27 @@ class MUC(BaseModule): |
| 322 | 326 |
return
|
| 323 | 327 |
|
| 324 | 328 |
if muc_data.state == MUCJoinedState.JOINING:
|
| 325 |
- if properties.error.type == Error.CONFLICT:
|
|
| 329 |
+ if properties.error.condition == 'conflict':
|
|
| 326 | 330 |
muc_data.nick += '_'
|
| 327 | 331 |
self._log.info('Nickname conflict: %s change to %s',
|
| 328 | 332 |
muc_data.jid, muc_data.nick)
|
| 329 | 333 |
self._join(muc_data)
|
| 330 |
- elif properties.error.type == Error.NOT_AUTHORIZED:
|
|
| 334 |
+ elif properties.error.condition == 'not-authorized':
|
|
| 331 | 335 |
self._raise_muc_event('muc-password-required', properties)
|
| 332 | 336 |
else:
|
| 333 |
- self._raise_muc_event('muc-join-failed', properties)
|
|
| 334 | 337 |
self._set_muc_state(room_jid, MUCJoinedState.NOT_JOINED)
|
| 338 |
+ app.nec.push_incoming_event(
|
|
| 339 |
+ NetworkEvent('muc-join-failed',
|
|
| 340 |
+ account=self._account,
|
|
| 341 |
+ room_jid=room_jid,
|
|
| 342 |
+ error=properties.error))
|
|
| 335 | 343 |
|
| 336 | 344 |
elif muc_data.state == MUCJoinedState.CAPTCHA_REQUEST:
|
| 337 | 345 |
app.nec.push_incoming_event(
|
| 338 | 346 |
NetworkEvent('muc-captcha-error',
|
| 339 | 347 |
account=self._account,
|
| 340 | 348 |
room_jid=room_jid,
|
| 341 |
- error_text=properties.error.message))
|
|
| 349 |
+ error_text=properties.error.get_text()))
|
|
| 342 | 350 |
self._set_muc_state(room_jid, MUCJoinedState.CAPTCHA_FAILED)
|
| 343 | 351 |
self._set_muc_state(room_jid, MUCJoinedState.NOT_JOINED)
|
| 344 | 352 |
|
| ... | ... | @@ -104,11 +104,6 @@ messages = { |
| 104 | 104 |
'%(error_msg)s'),
|
| 105 | 105 |
ErrorDialog),
|
| 106 | 106 |
|
| 107 |
- 'unable-join-groupchat': Message(
|
|
| 108 |
- _('Unable to Join Group Chat'),
|
|
| 109 |
- '%(server)s\n%(error)s',
|
|
| 110 |
- ErrorDialog),
|
|
| 111 |
- |
|
| 112 | 107 |
'gstreamer-error': Message(
|
| 113 | 108 |
_('GStreamer Error'),
|
| 114 | 109 |
_('Error: %(error)s\nDebug: %(debug)s'),
|
| ... | ... | @@ -26,7 +26,7 @@ from distutils.version import LooseVersion as V |
| 26 | 26 |
|
| 27 | 27 |
from gajim.common import i18n
|
| 28 | 28 |
|
| 29 |
-_MIN_NBXMPP_VER = "0.9.91"
|
|
| 29 |
+_MIN_NBXMPP_VER = "0.9.92"
|
|
| 30 | 30 |
_MIN_GTK_VER = "3.22.0"
|
| 31 | 31 |
_MIN_CAIRO_VER = "1.14.0"
|
| 32 | 32 |
|
| ... | ... | @@ -53,7 +53,6 @@ from gajim import message_control |
| 53 | 53 |
from gajim import vcard
|
| 54 | 54 |
|
| 55 | 55 |
from gajim.common.const import AvatarSize
|
| 56 |
-from gajim.common.caps_cache import muc_caps_cache
|
|
| 57 | 56 |
from gajim.common import events
|
| 58 | 57 |
from gajim.common import app
|
| 59 | 58 |
from gajim.common import helpers
|
| ... | ... | @@ -371,6 +370,10 @@ class GroupchatControl(ChatControlBase): |
| 371 | 370 |
def room_name(self):
|
| 372 | 371 |
return self.contact.get_shown_name()
|
| 373 | 372 |
|
| 373 |
+ @property
|
|
| 374 |
+ def disco_info(self):
|
|
| 375 |
+ return app.logger.get_last_disco_info(self.contact.jid)
|
|
| 376 |
+ |
|
| 374 | 377 |
def add_actions(self):
|
| 375 | 378 |
super().add_actions()
|
| 376 | 379 |
actions = [
|
| ... | ... | @@ -421,8 +424,10 @@ class GroupchatControl(ChatControlBase): |
| 421 | 424 |
self.parent_win.window.add_action(act)
|
| 422 | 425 |
|
| 423 | 426 |
# Enable notify on all for private rooms
|
| 424 |
- members_only = muc_caps_cache.supports(self.contact.jid,
|
|
| 425 |
- 'muc#roomconfig_membersonly')
|
|
| 427 |
+ members_only = False
|
|
| 428 |
+ if self.disco_info is not None:
|
|
| 429 |
+ members_only = self.disco_info.muc_is_members_only
|
|
| 430 |
+ |
|
| 426 | 431 |
value = app.config.get_per(
|
| 427 | 432 |
'rooms', self.contact.jid, 'notify_on_all_messages', members_only)
|
| 428 | 433 |
|
| ... | ... | @@ -486,12 +491,9 @@ class GroupchatControl(ChatControlBase): |
| 486 | 491 |
role.is_visitor)
|
| 487 | 492 |
|
| 488 | 493 |
# Change Subject
|
| 489 |
- subject = False
|
|
| 490 |
- if contact is not None:
|
|
| 491 |
- subject = muc_caps_cache.is_subject_change_allowed(
|
|
| 492 |
- self.room_jid, contact.affiliation)
|
|
| 494 |
+ subject_change = self._is_subject_change_allowed()
|
|
| 493 | 495 |
self._get_action('change-subject-').set_enabled(self.is_connected and
|
| 494 |
- subject)
|
|
| 496 |
+ subject_change)
|
|
| 495 | 497 |
|
| 496 | 498 |
# Change Nick
|
| 497 | 499 |
self._get_action('change-nickname-').set_enabled(self.is_connected)
|
| ... | ... | @@ -517,7 +519,9 @@ class GroupchatControl(ChatControlBase): |
| 517 | 519 |
self.sendfile_button.set_tooltip_text(tooltip_text)
|
| 518 | 520 |
|
| 519 | 521 |
# Upload Avatar
|
| 520 |
- vcard_support = muc_caps_cache.supports(self.room_jid, nbxmpp.NS_VCARD)
|
|
| 522 |
+ vcard_support = False
|
|
| 523 |
+ if self.disco_info is not None:
|
|
| 524 |
+ vcard_support = self.disco_info.supports(nbxmpp.NS_VCARD)
|
|
| 521 | 525 |
self._get_action('upload-avatar-').set_enabled(
|
| 522 | 526 |
self.is_connected and
|
| 523 | 527 |
vcard_support and
|
| ... | ... | @@ -537,6 +541,19 @@ class GroupchatControl(ChatControlBase): |
| 537 | 541 |
self._get_action('print-status-').set_state(
|
| 538 | 542 |
GLib.Variant.new_boolean(value))
|
| 539 | 543 |
|
| 544 |
+ def _is_subject_change_allowed(self):
|
|
| 545 |
+ contact = app.contacts.get_gc_contact(
|
|
| 546 |
+ self.account, self.room_jid, self.nick)
|
|
| 547 |
+ if contact is None:
|
|
| 548 |
+ return False
|
|
| 549 |
+ |
|
| 550 |
+ if contact.affiliation in (Affiliation.OWNER, Affiliation.ADMIN):
|
|
| 551 |
+ return True
|
|
| 552 |
+ |
|
| 553 |
+ if self.disco_info is None:
|
|
| 554 |
+ return False
|
|
| 555 |
+ return self.disco_info.muc_subjectmod
|
|
| 556 |
+ |
|
| 540 | 557 |
def _get_action(self, name):
|
| 541 | 558 |
win = self.parent_win.window
|
| 542 | 559 |
return win.lookup_action(name + self.control_id)
|
| ... | ... | @@ -623,14 +640,13 @@ class GroupchatControl(ChatControlBase): |
| 623 | 640 |
self.update_actions()
|
| 624 | 641 |
|
| 625 | 642 |
# After the room has been created, reevaluate threshold
|
| 626 |
- if muc_caps_cache.has_mam(self.contact.jid):
|
|
| 643 |
+ if self.disco_info.has_mam:
|
|
| 627 | 644 |
archive_info = app.logger.get_archive_infos(self.contact.jid)
|
| 628 | 645 |
threshold = helpers.get_sync_threshold(self.contact.jid,
|
| 629 | 646 |
archive_info)
|
| 630 | 647 |
win.change_action_state('choose-sync-%s' % self.control_id,
|
| 631 | 648 |
GLib.Variant('s', str(threshold)))
|
| 632 | 649 |
|
| 633 |
- |
|
| 634 | 650 |
def _connect_window_state_change(self, parent_win):
|
| 635 | 651 |
if self._state_change_handler_id is None:
|
| 636 | 652 |
id_ = parent_win.window.connect('notify::is-maximized',
|
| ... | ... | @@ -643,8 +659,7 @@ class GroupchatControl(ChatControlBase): |
| 643 | 659 |
self.leave()
|
| 644 | 660 |
|
| 645 | 661 |
def _on_information(self, action, param):
|
| 646 |
- disco_info = muc_caps_cache.cache[self.contact.jid]
|
|
| 647 |
- self._muc_info_box.set_from_disco_info(disco_info)
|
|
| 662 |
+ self._muc_info_box.set_from_disco_info(self.disco_info)
|
|
| 648 | 663 |
if self._subject_data is not None:
|
| 649 | 664 |
self._muc_info_box.set_subject(self._subject_data.subject)
|
| 650 | 665 |
self._muc_info_box.set_author(self._subject_data.nickname,
|
| ... | ... | @@ -1386,7 +1401,7 @@ class GroupchatControl(ChatControlBase): |
| 1386 | 1401 |
changes.append(_('A setting not related to privacy has been '
|
| 1387 | 1402 |
'changed'))
|
| 1388 | 1403 |
app.connections[self.account].get_module('Discovery').disco_muc(
|
| 1389 |
- self.room_jid, self.update_actions, update=True)
|
|
| 1404 |
+ self.room_jid)
|
|
| 1390 | 1405 |
|
| 1391 | 1406 |
if StatusCode.CONFIG_ROOM_LOGGING in event.status_codes:
|
| 1392 | 1407 |
# Can be a presence (see chg_contact_status in groupchat_control.py)
|
| ... | ... | @@ -1479,7 +1494,7 @@ class GroupchatControl(ChatControlBase): |
| 1479 | 1494 |
GLib.source_remove(self.autorejoin)
|
| 1480 | 1495 |
self.autorejoin = None
|
| 1481 | 1496 |
|
| 1482 |
- if muc_caps_cache.has_mam(self.room_jid):
|
|
| 1497 |
+ if self.disco_info.has_mam:
|
|
| 1483 | 1498 |
# Request MAM
|
| 1484 | 1499 |
con = app.connections[self.account]
|
| 1485 | 1500 |
con.get_module('MAM').request_archive_on_muc_join(
|
| ... | ... | @@ -1925,17 +1940,14 @@ class GroupchatControl(ChatControlBase): |
| 1925 | 1940 |
|
| 1926 | 1941 |
@event_filter(['account', 'room_jid'])
|
| 1927 | 1942 |
def _on_muc_join_failed(self, event):
|
| 1928 |
- self.xml.error_label.set_text(event.properties.error.message)
|
|
| 1943 |
+ self.xml.error_label.set_text(event.error.get_text())
|
|
| 1929 | 1944 |
self._show_page('error')
|
| 1930 | 1945 |
self.autorejoin = False
|
| 1931 | 1946 |
|
| 1932 | 1947 |
@event_filter(['account', 'room_jid'])
|
| 1933 | 1948 |
def _on_presence_error(self, event):
|
| 1934 |
- error_type = event.properties.error.type
|
|
| 1935 |
- error_message = event.properties.error.message
|
|
| 1936 |
- |
|
| 1937 |
- self.add_info_message(
|
|
| 1938 |
- 'Error %s: %s' % (error_type.value, error_message))
|
|
| 1949 |
+ error_message = event.properties.error.get_text()
|
|
| 1950 |
+ self.add_info_message('Error: %s' % error_message)
|
|
| 1939 | 1951 |
|
| 1940 | 1952 |
def add_contact_to_roster(self, nick):
|
| 1941 | 1953 |
contact = app.contacts.get_gc_contact(self.account,
|
| ... | ... | @@ -22,7 +22,6 @@ from gi.repository import Gtk |
| 22 | 22 |
from gajim.common import app
|
| 23 | 23 |
from gajim.common.i18n import _
|
| 24 | 24 |
from gajim.common.const import MUCUser
|
| 25 |
-from gajim.common.caps_cache import muc_caps_cache
|
|
| 26 | 25 |
|
| 27 | 26 |
from gajim.gtk.dialogs import ErrorDialog
|
| 28 | 27 |
from gajim.gtk.dataform import DataFormWidget
|
| ... | ... | @@ -53,7 +52,8 @@ class GroupchatConfig(Gtk.ApplicationWindow): |
| 53 | 52 |
self._ui.add_button.set_sensitive(True)
|
| 54 | 53 |
self._ui.add_button.set_tooltip_text('')
|
| 55 | 54 |
|
| 56 |
- visible = muc_caps_cache.supports(jid, nbxmpp.NS_REGISTER)
|
|
| 55 |
+ disco_info = app.logger.get_last_disco_info(self.jid)
|
|
| 56 |
+ visible = disco_info.supports(nbxmpp.NS_REGISTER)
|
|
| 57 | 57 |
self._ui.reserved_name_column.set_visible(visible)
|
| 58 | 58 |
self._ui.info_button.set_sensitive(False)
|
| 59 | 59 |
|
| ... | ... | @@ -73,17 +73,14 @@ class GroupchatJoin(Gtk.ApplicationWindow): |
| 73 | 73 |
self.add(self._main_box)
|
| 74 | 74 |
self.show_all()
|
| 75 | 75 |
|
| 76 |
- self._disco_muc(jid)
|
|
| 76 |
+ con = app.connections[self.account]
|
|
| 77 |
+ con.get_module('Discovery').disco_muc(
|
|
| 78 |
+ jid, callback=self._disco_info_received)
|
|
| 77 | 79 |
|
| 78 | 80 |
def _on_page_changed(self, stack, _param):
|
| 79 | 81 |
name = stack.get_visible_child_name()
|
| 80 | 82 |
self._join_button.set_sensitive(name == 'info')
|
| 81 | 83 |
|
| 82 |
- def _disco_muc(self, jid):
|
|
| 83 |
- con = app.connections[self.account]
|
|
| 84 |
- con.get_module('Discovery').disco_info(
|
|
| 85 |
- jid, callback=self._disco_info_received)
|
|
| 86 |
- |
|
| 87 | 84 |
@ensure_not_destroyed
|
| 88 | 85 |
def _disco_info_received(self, result):
|
| 89 | 86 |
if is_error_result(result):
|
| ... | ... | @@ -14,6 +14,7 @@ |
| 14 | 14 |
|
| 15 | 15 |
import locale
|
| 16 | 16 |
from enum import IntEnum
|
| 17 |
+from functools import partial
|
|
| 17 | 18 |
|
| 18 | 19 |
from gi.repository import Gdk
|
| 19 | 20 |
from gi.repository import Gtk
|
| ... | ... | @@ -275,11 +276,11 @@ class StartChatDialog(Gtk.ApplicationWindow): |
| 275 | 276 |
def _disco_muc(self, account, jid):
|
| 276 | 277 |
self._ui.stack.set_visible_child_name('progress')
|
| 277 | 278 |
con = app.connections[account]
|
| 278 |
- con.get_module('Discovery').disco_info(
|
|
| 279 |
- jid, callback=self._disco_info_received, user_data=account)
|
|
| 279 |
+ con.get_module('Discovery').disco_muc(
|
|
| 280 |
+ jid, callback=partial(self._disco_info_received, account))
|
|
| 280 | 281 |
|
| 281 | 282 |
@ensure_not_destroyed
|
| 282 |
- def _disco_info_received(self, result, account):
|
|
| 283 |
+ def _disco_info_received(self, account, result):
|
|
| 283 | 284 |
if is_error_result(result):
|
| 284 | 285 |
self._set_error(result)
|
| 285 | 286 |
|
| ... | ... | @@ -22,7 +22,7 @@ test_suite = test |
| 22 | 22 |
install_requires =
|
| 23 | 23 |
cssutils>=1.0.2
|
| 24 | 24 |
keyring
|
| 25 |
- nbxmpp>=0.9.91
|
|
| 25 |
+ nbxmpp>=0.9.92
|
|
| 26 | 26 |
precis-i18n>=1.0.0
|
| 27 | 27 |
pyOpenSSL>=16.2
|
| 28 | 28 |
pycairo>=1.14.0
|
| ... | ... | @@ -61,7 +61,7 @@ class TestCapsCache(CommonCapsTest): |
| 61 | 61 |
def test_set_and_store(self):
|
| 62 | 62 |
''' Test client_caps update gets logged into db '''
|
| 63 | 63 |
|
| 64 |
- disco_info = DiscoInfo(None, None, self.identities, self.features, [])
|
|
| 64 |
+ disco_info = DiscoInfo(None, self.identities, self.features, [])
|
|
| 65 | 65 |
|
| 66 | 66 |
item = self.cc[self.client_caps]
|
| 67 | 67 |
item.set_and_store(disco_info)
|