Use custom dict for additional data

This makes it easier to retrive and store values
This commit is contained in:
Philipp Hörist 2018-11-30 23:05:15 +01:00
parent b4f43acbc8
commit 1c09b50791
14 changed files with 102 additions and 67 deletions

View File

@ -42,6 +42,7 @@ from gajim.common import helpers
from gajim.common import ged from gajim.common import ged
from gajim.common import i18n from gajim.common import i18n
from gajim.common.i18n import _ from gajim.common.i18n import _
from gajim.common.helpers import AdditionalDataDict
from gajim.common.contacts import GC_Contact from gajim.common.contacts import GC_Contact
from gajim.common.const import AvatarSize from gajim.common.const import AvatarSize
from gajim.common.const import KindConstant from gajim.common.const import KindConstant
@ -933,7 +934,7 @@ class ChatControl(ChatControlBase):
contact = self.contact contact = self.contact
if additional_data is None: if additional_data is None:
additional_data = {} additional_data = AdditionalDataDict()
if frm == 'status': if frm == 'status':
if not app.config.get('print_status_in_chats'): if not app.config.get('print_status_in_chats'):

View File

@ -38,6 +38,7 @@ from gajim.common import helpers
from gajim.common import ged from gajim.common import ged
from gajim.common import i18n from gajim.common import i18n
from gajim.common.i18n import _ from gajim.common.i18n import _
from gajim.common.helpers import AdditionalDataDict
from gajim.common.contacts import GC_Contact from gajim.common.contacts import GC_Contact
from gajim.common.connection_handlers_events import MessageOutgoingEvent from gajim.common.connection_handlers_events import MessageOutgoingEvent
from gajim.common.const import StyleAttr from gajim.common.const import StyleAttr
@ -905,7 +906,7 @@ class ChatControlBase(MessageControl, ChatCommandProcessor, CommandTools):
if other_tags_for_text is None: if other_tags_for_text is None:
other_tags_for_text = [] other_tags_for_text = []
if additional_data is None: if additional_data is None:
additional_data = {} additional_data = AdditionalDataDict()
textview.print_conversation_line(text, jid, kind, name, tim, textview.print_conversation_line(text, jid, kind, name, tim,
other_tags_for_name, other_tags_for_time, other_tags_for_text, other_tags_for_name, other_tags_for_time, other_tags_for_text,

View File

@ -28,6 +28,7 @@ from gajim.common import helpers
from gajim.common import app from gajim.common import app
from gajim.common import i18n from gajim.common import i18n
from gajim.common.i18n import _ from gajim.common.i18n import _
from gajim.common.helpers import AdditionalDataDict
from gajim.common.modules import dataforms from gajim.common.modules import dataforms
from gajim.common.modules.misc import parse_idle from gajim.common.modules.misc import parse_idle
from gajim.common.modules.misc import parse_delay from gajim.common.modules.misc import parse_delay
@ -91,14 +92,12 @@ class HelperEvent:
def get_oob_data(self, stanza): def get_oob_data(self, stanza):
oob_node = stanza.getTag('x', namespace=nbxmpp.NS_X_OOB) oob_node = stanza.getTag('x', namespace=nbxmpp.NS_X_OOB)
if oob_node is not None: if oob_node is not None:
if 'gajim' not in self.additional_data:
self.additional_data['gajim'] = {}
oob_url = oob_node.getTagData('url') oob_url = oob_node.getTagData('url')
if oob_url is not None: if oob_url is not None:
self.additional_data['gajim']['oob_url'] = oob_url self.additional_data.set_value('gajim', 'oob_url', oob_url)
oob_desc = oob_node.getTagData('desc') oob_desc = oob_node.getTagData('desc')
if oob_desc is not None: if oob_desc is not None:
self.additional_data['gajim']['oob_desc'] = oob_desc self.additional_data.set_value('gajim', 'oob_desc', oob_desc)
def get_stanza_id(self, stanza, query=False): def get_stanza_id(self, stanza, query=False):
if query: if query:
@ -407,7 +406,7 @@ class GcMessageReceivedEvent(nec.NetworkIncomingEvent):
def generate(self): def generate(self):
self.stanza = self.msg_obj.stanza self.stanza = self.msg_obj.stanza
if not hasattr(self.msg_obj, 'additional_data'): if not hasattr(self.msg_obj, 'additional_data'):
self.additional_data = {} self.additional_data = AdditionalDataDict()
else: else:
self.additional_data = self.msg_obj.additional_data self.additional_data = self.msg_obj.additional_data
self.id_ = self.msg_obj.stanza.getID() self.id_ = self.msg_obj.stanza.getID()
@ -626,18 +625,9 @@ class ConnectionTypeEvent(nec.NetworkIncomingEvent):
class StanzaReceivedEvent(nec.NetworkIncomingEvent): class StanzaReceivedEvent(nec.NetworkIncomingEvent):
name = 'stanza-received' name = 'stanza-received'
def init(self):
self.additional_data = {}
def generate(self):
return True
class StanzaSentEvent(nec.NetworkIncomingEvent): class StanzaSentEvent(nec.NetworkIncomingEvent):
name = 'stanza-sent' name = 'stanza-sent'
def init(self):
self.additional_data = {}
class AgentRemovedEvent(nec.NetworkIncomingEvent): class AgentRemovedEvent(nec.NetworkIncomingEvent):
name = 'agent-removed' name = 'agent-removed'
@ -1158,7 +1148,7 @@ class MessageOutgoingEvent(nec.NetworkOutgoingEvent):
name = 'message-outgoing' name = 'message-outgoing'
def init(self): def init(self):
self.additional_data = {} self.additional_data = AdditionalDataDict()
self.message = None self.message = None
self.keyID = None self.keyID = None
self.type_ = 'chat' self.type_ = 'chat'
@ -1211,7 +1201,7 @@ class GcMessageOutgoingEvent(nec.NetworkOutgoingEvent):
name = 'gc-message-outgoing' name = 'gc-message-outgoing'
def init(self): def init(self):
self.additional_data = {} self.additional_data = AdditionalDataDict()
self.message = '' self.message = ''
self.chatstate = None self.chatstate = None
self.xhtml = None self.xhtml = None

View File

@ -81,7 +81,8 @@ class ChatEvent(Event):
self.displaymarking = displaymarking self.displaymarking = displaymarking
self.sent_forwarded = sent_forwarded self.sent_forwarded = sent_forwarded
if additional_data is None: if additional_data is None:
additional_data = {} from gajim.common.helpers import AdditionalDataDict
additional_data = AdditionalDataDict()
self.additional_data = additional_data self.additional_data = additional_data
class NormalEvent(ChatEvent): class NormalEvent(ChatEvent):

View File

@ -41,6 +41,7 @@ import time
import logging import logging
import json import json
import shutil import shutil
import collections
from datetime import datetime, timedelta from datetime import datetime, timedelta
from distutils.version import LooseVersion as V from distutils.version import LooseVersion as V
from encodings.punycode import punycode_encode from encodings.punycode import punycode_encode
@ -1485,3 +1486,51 @@ def load_json(path, key=None, default=None):
if key is None: if key is None:
return json_dict return json_dict
return json_dict.get(key, default) return json_dict.get(key, default)
class AdditionalDataDict(collections.UserDict):
def __init__(self, initialdata=None):
collections.UserDict.__init__(self, initialdata)
@staticmethod
def _get_path_childs(full_path):
path_childs = [full_path]
if ':' in full_path:
path_childs = full_path.split(':')
return path_childs
def set_value(self, full_path, key, value):
path_childs = self._get_path_childs(full_path)
_dict = self.data
for path in path_childs:
try:
_dict = _dict[path]
except KeyError:
_dict[path] = {}
_dict = _dict[path]
_dict[key] = value
def get_value(self, full_path, key, default=None):
path_childs = self._get_path_childs(full_path)
_dict = self.data
for path in path_childs:
try:
_dict = _dict[path]
except KeyError:
return default
try:
return _dict[key]
except KeyError:
return default
def remove_value(self, full_path, key):
path_childs = self._get_path_childs(full_path)
_dict = self.data
for path in path_childs:
try:
_dict = _dict[path]
except KeyError:
return
try:
del _dict[key]
except KeyError:
return

View File

@ -41,6 +41,7 @@ from gi.repository import GLib
from gajim.common import exceptions from gajim.common import exceptions
from gajim.common import app from gajim.common import app
from gajim.common import configpaths from gajim.common import configpaths
from gajim.common.helpers import AdditionalDataDict
from gajim.common.i18n import _ from gajim.common.i18n import _
from gajim.common.const import ( from gajim.common.const import (
JIDConstant, KindConstant, ShowConstant, TypeConstant, JIDConstant, KindConstant, ShowConstant, TypeConstant,
@ -265,8 +266,9 @@ class Logger:
Row = namedtuple("Row", fields) Row = namedtuple("Row", fields)
named_row = Row(*row) named_row = Row(*row)
if 'additional_data' in fields: if 'additional_data' in fields:
_dict = json.loads(named_row.additional_data or '{}')
named_row = named_row._replace( named_row = named_row._replace(
additional_data=json.loads(named_row.additional_data or '{}')) additional_data=AdditionalDataDict(_dict))
# if an alias `account` for the field `account_id` is used for the # if an alias `account` for the field `account_id` is used for the
# query, the account_id is converted to the account jid # query, the account_id is converted to the account jid
@ -1355,7 +1357,8 @@ class Logger:
if not kwargs['additional_data']: if not kwargs['additional_data']:
del kwargs['additional_data'] del kwargs['additional_data']
else: else:
kwargs['additional_data'] = json.dumps(kwargs["additional_data"]) serialized_dict = json.dumps(kwargs["additional_data"].data)
kwargs['additional_data'] = serialized_dict
sql = ''' sql = '''
INSERT INTO logs (account_id, jid_id, time, kind, {columns}) INSERT INTO logs (account_id, jid_id, time, kind, {columns})

View File

@ -118,10 +118,7 @@ class HTTPUpload:
# to distinguish HTTP File Upload Link from pasted URL # to distinguish HTTP File Upload Link from pasted URL
oob = event.msg_iq.addChild('x', namespace=nbxmpp.NS_X_OOB) oob = event.msg_iq.addChild('x', namespace=nbxmpp.NS_X_OOB)
oob.addChild('url').setData(message) oob.addChild('url').setData(message)
if 'gajim' in event.additional_data: event.additional_data.set_value('gajim', 'oob_url', message)
event.additional_data['gajim']['oob_url'] = message
else:
event.additional_data['gajim'] = {'oob_url': message}
def check_file_before_transfer(self, path, encryption, contact, session, def check_file_before_transfer(self, path, encryption, contact, session,
groupchat=False): groupchat=False):

View File

@ -27,6 +27,7 @@ from gajim.common.const import KindConstant
from gajim.common.const import SyncThreshold from gajim.common.const import SyncThreshold
from gajim.common.caps_cache import muc_caps_cache from gajim.common.caps_cache import muc_caps_cache
from gajim.common.helpers import get_sync_threshold from gajim.common.helpers import get_sync_threshold
from gajim.common.helpers import AdditionalDataDict
from gajim.common.modules.misc import parse_delay from gajim.common.modules.misc import parse_delay
from gajim.common.modules.misc import parse_oob from gajim.common.modules.misc import parse_oob
from gajim.common.modules.misc import parse_correction from gajim.common.modules.misc import parse_correction
@ -179,7 +180,7 @@ class MAM:
event_attrs.update( event_attrs.update(
{'conn': self._con, {'conn': self._con,
'additional_data': {}, 'additional_data': AdditionalDataDict(),
'encrypted': False, 'encrypted': False,
'timestamp': delay_timestamp, 'timestamp': delay_timestamp,
'self_message': self_message, 'self_message': self_message,
@ -192,6 +193,7 @@ class MAM:
'archive_jid': archive_jid, 'archive_jid': archive_jid,
'msgtxt': msgtxt, 'msgtxt': msgtxt,
'message': message, 'message': message,
'stanza': message,
'namespace': namespace, 'namespace': namespace,
}) })
@ -256,7 +258,7 @@ class MAM:
'gajim', 'user_timestamp', user_timestamp) 'gajim', 'user_timestamp', user_timestamp)
event.correct_id = parse_correction(event.message) event.correct_id = parse_correction(event.message)
parse_oob(event.message, event.additional_data) parse_oob(event)
with_ = event.with_.getStripped() with_ = event.with_.getStripped()
if event.muc_pm: if event.muc_pm:

View File

@ -22,7 +22,9 @@ import nbxmpp
from gajim.common import app from gajim.common import app
from gajim.common import helpers from gajim.common import helpers
from gajim.common.i18n import _ from gajim.common.i18n import _
from gajim.common.nec import NetworkIncomingEvent, NetworkEvent from gajim.common.nec import NetworkIncomingEvent
from gajim.common.nec import NetworkEvent
from gajim.common.helpers import AdditionalDataDict
from gajim.common.modules.security_labels import parse_securitylabel from gajim.common.modules.security_labels import parse_securitylabel
from gajim.common.modules.user_nickname import parse_nickname from gajim.common.modules.user_nickname import parse_nickname
from gajim.common.modules.carbons import parse_carbon from gajim.common.modules.carbons import parse_carbon
@ -188,7 +190,7 @@ class Message:
'account': self._account, 'account': self._account,
'id_': id_, 'id_': id_,
'encrypted': False, 'encrypted': False,
'additional_data': {}, 'additional_data': AdditionalDataDict(),
'forwarded': forwarded, 'forwarded': forwarded,
'sent': sent, 'sent': sent,
'fjid': fjid, 'fjid': fjid,
@ -266,7 +268,7 @@ class Message:
'timestamp': timestamp, 'timestamp': timestamp,
'delayed': user_timestamp is not None, 'delayed': user_timestamp is not None,
} }
parse_oob(event.stanza, event.additional_data) parse_oob(event)
for name, value in event_attr.items(): for name, value in event_attr.items():
setattr(event, name, value) setattr(event, name, value)

View File

@ -108,27 +108,18 @@ def parse_delay(stanza, epoch=True, convert='utc', from_=None, not_from=None):
# XEP-0066: Out of Band Data # XEP-0066: Out of Band Data
def parse_oob(stanza, dict_=None, key='gajim'): def parse_oob(event):
oob_node = stanza.getTag('x', namespace=nbxmpp.NS_X_OOB) oob_node = event.stanza.getTag('x', namespace=nbxmpp.NS_X_OOB)
if oob_node is None: if oob_node is None:
return return
result = {}
url = oob_node.getTagData('url') url = oob_node.getTagData('url')
if url is not None: if url is not None:
result['oob_url'] = url event.additional_data.set_value('gajim', 'oob_url', url)
desc = oob_node.getTagData('desc') desc = oob_node.getTagData('desc')
if desc is not None: if desc is not None:
result['oob_desc'] = desc event.additional_data.set_value('gajim', 'oob_desc', desc)
if dict_ is None:
return result
if key in dict_:
dict_[key] += result
else:
dict_[key] = result
return dict_
# XEP-0308: Last Message Correction # XEP-0308: Last Message Correction

View File

@ -30,6 +30,7 @@ from gajim.common.protocol.bytestream import ConnectionSocks5BytestreamZeroconf
from gajim.common.zeroconf.zeroconf import Constant from gajim.common.zeroconf.zeroconf import Constant
from gajim.common import connection_handlers from gajim.common import connection_handlers
from gajim.common.i18n import _ from gajim.common.i18n import _
from gajim.common.helpers import AdditionalDataDict
from gajim.common.nec import NetworkIncomingEvent, NetworkEvent from gajim.common.nec import NetworkIncomingEvent, NetworkEvent
from gajim.common.modules.user_nickname import parse_nickname from gajim.common.modules.user_nickname import parse_nickname
from gajim.common.modules.misc import parse_eme from gajim.common.modules.misc import parse_eme
@ -118,7 +119,7 @@ connection_handlers.ConnectionJingle):
'account': self.name, 'account': self.name,
'id_': id_, 'id_': id_,
'encrypted': False, 'encrypted': False,
'additional_data': {}, 'additional_data': AdditionalDataDict(),
'forwarded': False, 'forwarded': False,
'sent': False, 'sent': False,
'timestamp': time.time(), 'timestamp': time.time(),
@ -165,7 +166,7 @@ connection_handlers.ConnectionJingle):
'stanza_id': event.unique_id 'stanza_id': event.unique_id
} }
parse_oob(event.stanza, event.additional_data) parse_oob(event)
for name, value in event_attr.items(): for name, value in event_attr.items():
setattr(event, name, value) setattr(event, name, value)

View File

@ -39,6 +39,7 @@ from gajim.common import app
from gajim.common import helpers from gajim.common import helpers
from gajim.common import i18n from gajim.common import i18n
from gajim.common.i18n import _ from gajim.common.i18n import _
from gajim.common.helpers import AdditionalDataDict
from gajim.common.fuzzyclock import FuzzyClock from gajim.common.fuzzyclock import FuzzyClock
from gajim.common.const import StyleAttr from gajim.common.const import StyleAttr
@ -666,7 +667,7 @@ class ConversationTextview(GObject.GObject):
if not otext: if not otext:
return return
if additional_data is None: if additional_data is None:
additional_data = {} additional_data = AdditionalDataDict()
buffer_ = self.tv.get_buffer() buffer_ = self.tv.get_buffer()
if other_tags: if other_tags:
insert_tags_func = buffer_.insert_with_tags_by_name insert_tags_func = buffer_.insert_with_tags_by_name
@ -686,13 +687,10 @@ class ConversationTextview(GObject.GObject):
specials_limit = 100 specials_limit = 100
# add oob text to the end # add oob text to the end
try:
gajim_data = additional_data['gajim'] oob_url = additional_data.get_value('gajim', 'oob_url')
oob_url = gajim_data['oob_url'] if oob_url is not None:
except KeyError: oob_desc = additional_data.get_value('gajim', 'oob_desc', 'URL:')
pass
else:
oob_desc = additional_data['gajim'].get('oob_desc', 'URL:')
if oob_url != otext: if oob_url != otext:
otext += '\n{} {}'.format(oob_desc, oob_url) otext += '\n{} {}'.format(oob_desc, oob_url)
@ -739,7 +737,7 @@ class ConversationTextview(GObject.GObject):
(emots, links, formatting) (emots, links, formatting)
""" """
if additional_data is None: if additional_data is None:
additional_data = {} additional_data = AdditionalDataDict()
# PluginSystem: adding GUI extension point for ConversationTextview # PluginSystem: adding GUI extension point for ConversationTextview
self.plugin_modified = False self.plugin_modified = False
@ -941,7 +939,7 @@ class ConversationTextview(GObject.GObject):
Print 'chat' type messages Print 'chat' type messages
""" """
if additional_data is None: if additional_data is None:
additional_data = {} additional_data = AdditionalDataDict()
buffer_ = self.tv.get_buffer() buffer_ = self.tv.get_buffer()
buffer_.begin_user_action() buffer_.begin_user_action()
insert_mark = None insert_mark = None
@ -1172,14 +1170,11 @@ class ConversationTextview(GObject.GObject):
@staticmethod @staticmethod
def _get_encryption_details(additional_data): def _get_encryption_details(additional_data):
encrypted = additional_data.get('encrypted') name = additional_data.get_value('encrypted', 'name')
if encrypted is None:
return
name = encrypted.get('name')
if name is None: if name is None:
return return
fingerprint = encrypted.get('fingerprint')
fingerprint = additional_data.get_value('encrypted', 'fingerprint')
return name, fingerprint return name, fingerprint
def print_time(self, text, kind, tim, simple, direction_mark, other_tags_for_time, iter_): def print_time(self, text, kind, tim, simple, direction_mark, other_tags_for_time, iter_):
@ -1260,7 +1255,7 @@ class ConversationTextview(GObject.GObject):
if text_tags is None: if text_tags is None:
text_tags = [] text_tags = []
if additional_data is None: if additional_data is None:
additional_data = {} additional_data = AdditionalDataDict()
buffer_ = self.tv.get_buffer() buffer_ = self.tv.get_buffer()
if not mark: if not mark:
iter_ = buffer_.get_end_iter() iter_ = buffer_.get_end_iter()

View File

@ -55,6 +55,7 @@ from gajim.common import events
from gajim.common import app from gajim.common import app
from gajim.common import helpers from gajim.common import helpers
from gajim.common.helpers import launch_browser_mailer from gajim.common.helpers import launch_browser_mailer
from gajim.common.helpers import AdditionalDataDict
from gajim.common.modules import dataforms from gajim.common.modules import dataforms
from gajim.common import ged from gajim.common import ged
from gajim.common import i18n from gajim.common import i18n
@ -1353,7 +1354,7 @@ class GroupchatControl(ChatControlBase):
def print_old_conversation(self, text, contact='', tim=None, xhtml=None, def print_old_conversation(self, text, contact='', tim=None, xhtml=None,
displaymarking=None, msg_stanza_id=None, encrypted=None, additional_data=None): displaymarking=None, msg_stanza_id=None, encrypted=None, additional_data=None):
if additional_data is None: if additional_data is None:
additional_data = {} additional_data = AdditionalDataDict()
if contact: if contact:
if contact == self.nick: # it's us if contact == self.nick: # it's us
@ -1384,7 +1385,7 @@ class GroupchatControl(ChatControlBase):
If contact is not set: it's a message from the server or help. If contact is not set: it's a message from the server or help.
""" """
if additional_data is None: if additional_data is None:
additional_data = {} additional_data = AdditionalDataDict()
other_tags_for_name = [] other_tags_for_name = []
other_tags_for_text = [] other_tags_for_text = []
if contact: if contact:

View File

@ -27,6 +27,7 @@ from gajim.common import events
from gajim.common import app from gajim.common import app
from gajim.common import contacts from gajim.common import contacts
from gajim.common import ged from gajim.common import ged
from gajim.common.helpers import AdditionalDataDict
from gajim.common.const import KindConstant from gajim.common.const import KindConstant
from gajim.gtk.single_message import SingleMessageWindow from gajim.gtk.single_message import SingleMessageWindow
@ -277,7 +278,7 @@ class ChatControlSession:
fjid = jid fjid = jid
if additional_data is None: if additional_data is None:
additional_data = {} additional_data = AdditionalDataDict()
# Try to catch the contact with correct resource # Try to catch the contact with correct resource
if resource: if resource: