revert thorstenp patches for now. They introduce bugs.

This commit is contained in:
Yann Leboulanger 2008-10-20 21:38:06 +00:00
parent f801a50260
commit 06ab4a7b6d
75 changed files with 592 additions and 486 deletions

View File

@ -46,7 +46,8 @@ from message_control import MessageControl
from conversation_textview import ConversationTextview
from message_textview import MessageTextView
from common.contacts import GC_Contact
from common.logger import constants
from common.logger import Constants
constants = Constants()
from common.rst_xhtml_generator import create_xhtml
from common.pep import MOODS, ACTIVITIES
from common.xmpp.protocol import NS_XHTML, NS_FILE, NS_MUC, NS_RECEIPTS
@ -151,7 +152,7 @@ class ChatControlBase(MessageControl):
contact = c
MessageControl.__init__(self, type_id, parent_win, widget_name,
contact, acct, resource = resource)
contact, acct, resource = resource);
widget = self.xml.get_widget('history_button')
id = widget.connect('clicked', self._on_history_menuitem_activate)
@ -294,7 +295,7 @@ class ChatControlBase(MessageControl):
if lang:
self.msg_textview.lang = lang
spell.set_language(lang)
except (gobject.GError, RuntimeError):
except (gobject.GError, RuntimeError), msg:
dialogs.AspellDictError(lang)
self.conv_textview.tv.show()
self._paint_banner()
@ -434,6 +435,7 @@ class ChatControlBase(MessageControl):
def show_emoticons_menu(self):
if not gajim.config.get('emoticons_theme'):
return
msg_tv = self.msg_textview
def set_emoticons_menu_position(w, msg_tv = self.msg_textview):
window = msg_tv.get_window(gtk.TEXT_WINDOW_WIDGET)
# get the window position
@ -447,7 +449,7 @@ class ChatControlBase(MessageControl):
cursor.x, cursor.y)
x = origin[0] + cursor[0]
y = origin[1] + size[1]
menu_height = gajim.interface.emoticons_menu.size_request()[1]
menu_width, menu_height = gajim.interface.emoticons_menu.size_request()
#FIXME: get_line_count is not so good
#get the iter of cursor, then tv.get_line_yrange
# so we know in which y we are typing (not how many lines we have
@ -954,7 +956,7 @@ class ChatControlBase(MessageControl):
conv_buf.set_text(self.sent_history[self.sent_history_pos])
elif direction == 'down':
if self.sent_history_pos >= size - 1:
conv_buf.set_text(self.orig_msg)
conv_buf.set_text(self.orig_msg);
self.orig_msg = None
self.sent_history_pos = size
return
@ -1118,7 +1120,7 @@ class ChatControl(ChatControlBase):
if session:
# Don't use previous session if we want to a specific resource
# and it's not the same
r = gajim.get_room_and_nick_from_fjid(str(session.jid))[1]
j, r = gajim.get_room_and_nick_from_fjid(str(session.jid))
if resource and resource != r:
session = None
@ -1424,6 +1426,7 @@ class ChatControl(ChatControlBase):
banner_name_label = self.xml.get_widget('banner_name_label')
banner_name_tooltip = gtk.Tooltips()
banner_eventbox = self.xml.get_widget('banner_eventbox')
name = contact.get_shown_name()
if self.resource:
@ -1825,6 +1828,7 @@ class ChatControl(ChatControlBase):
if contact is set to print_queue: it is incomming from queue
if contact is not set: it's an incomming message'''
contact = self.contact
jid = contact.jid
if frm == 'status':
if not gajim.config.get('print_status_in_chats'):
@ -2212,7 +2216,7 @@ class ChatControl(ChatControlBase):
def on_cancel():
on_no(self)
dialogs.ConfirmationDialog(
dialog = dialogs.ConfirmationDialog(
# %s is being replaced in the code with JID
_('You just received a new message from "%s"') % self.contact.jid,
_('If you close this tab and you have history disabled, '\
@ -2303,6 +2307,7 @@ class ChatControl(ChatControlBase):
path = treeview.get_selection().get_selected_rows()[1][0]
iter = model.get_iter(path)
type = model[iter][2]
account = model[iter][4].decode('utf-8')
if type != 'contact': # source is not a contact
return
dropped_jid = data.decode('utf-8')
@ -2365,7 +2370,7 @@ class ChatControl(ChatControlBase):
pending_how_many, timeout, self.account)
except exceptions.DatabaseMalformed:
dialogs.ErrorDialog(_('Database Error'),
_('The database file (%s) cannot be read. Try to repair it or remove it (all history will be lost).') % constants.LOG_DB_PATH)
_('The database file (%s) cannot be read. Try to repair it or remove it (all history will be lost).') % common.logger.LOG_DB_PATH)
rows = []
local_old_kind = None
for row in rows: # row[0] time, row[1] has kind, row[2] the message

View File

@ -182,9 +182,6 @@ if gajim.HAVE_GPG:
output = proc.handles['stdout'].read()
proc.handles['stdout'].close()
try: proc.wait()
except IOError: pass
keys = {}
lines = output.split('\n')
for line in lines:
@ -196,6 +193,8 @@ if gajim.HAVE_GPG:
# make it unicode instance
keys[sline[4][8:]] = helpers.decode_string(name)
return keys
try: proc.wait()
except IOError: pass
def get_secret_keys(self):
return self.get_keys(True)

View File

@ -24,6 +24,7 @@
##
from itertools import *
import xmpp
import xmpp.features_nb
import gajim
import helpers
@ -145,7 +146,7 @@ class CapsCache(object):
# prepopulate data which we are sure of; note: we do not log these info
for account in gajim.connections:
gajimcaps = self[('sha-1', gajim.caps_hash[account])]
gajimcaps = self[('sha-1', gajim.caps_hash[accout])]
gajimcaps.identities = [gajim.gajim_identity]
gajimcaps.features = gajim.gajim_common_features + \
gajim.gajim_optional_features[account]

View File

@ -27,7 +27,6 @@ import os
import sys
import stat
import exceptions
from common import gajim
import logger

View File

@ -71,7 +71,7 @@ class AdHocCommand:
' bad-request'))
def cancel(self, request):
response = self.buildResponse(request, status = 'canceled')[0]
response, cmd = self.buildResponse(request, status = 'canceled')
self.connection.connection.send(response)
return False # finish the session

View File

@ -415,6 +415,7 @@ class Connection(ConnectionHandlers):
if data:
hostname = data['hostname']
usessl = data['usessl']
self.try_connecting_for_foo_secs = 45
p = data['proxy']
use_srv = True
@ -960,6 +961,7 @@ class Connection(ConnectionHandlers):
sshow = helpers.get_xmpp_show(show)
if not msg:
msg = ''
keyID = gajim.config.get_per('accounts', self.name, 'keyid')
if show == 'offline':
p = common.xmpp.Presence(typ = 'unavailable', to = jid)
p = self.add_sha(p, False)
@ -983,6 +985,7 @@ class Connection(ConnectionHandlers):
sshow = helpers.get_xmpp_show(show)
if not msg:
msg = ''
keyID = gajim.config.get_per('accounts', self.name, 'keyid')
sign_msg = False
if not auto and not show == 'offline':
sign_msg = True
@ -1396,7 +1399,7 @@ class Connection(ConnectionHandlers):
return
iq = common.xmpp.Iq(typ='get')
iq2 = iq.addChild(name='query', namespace=common.xmpp.NS_PRIVATE)
iq2.addChild(name='gajim', namespace='gajim:prefs')
iq3 = iq2.addChild(name='gajim', namespace='gajim:prefs')
self.connection.send(iq)
def get_bookmarks(self):
@ -1426,11 +1429,11 @@ class Connection(ConnectionHandlers):
# Note: need to handle both None and '' as empty
# thus shouldn't use "is not None"
if bm.get('nick', None):
iq4.setTagData('nick', bm['nick'])
iq5 = iq4.setTagData('nick', bm['nick'])
if bm.get('password', None):
iq4.setTagData('password', bm['password'])
iq5 = iq4.setTagData('password', bm['password'])
if bm.get('print_status', None):
iq4.setTagData('print_status', bm['print_status'])
iq5 = iq4.setTagData('print_status', bm['print_status'])
self.connection.send(iq)
def get_annotations(self):
@ -1701,7 +1704,7 @@ class Connection(ConnectionHandlers):
if gajim.account_is_connected(self.name):
hostname = gajim.config.get_per('accounts', self.name, 'hostname')
iq = common.xmpp.Iq(typ = 'set', to = hostname)
iq.setTag(common.xmpp.NS_REGISTER + ' query').setTag('remove')
q = iq.setTag(common.xmpp.NS_REGISTER + ' query').setTag('remove')
con.send(iq)
on_remove_success(True)
return

View File

@ -764,6 +764,7 @@ class ConnectionDisco:
if node:
q.setAttr('node', node)
q.addChild('identity', attrs = gajim.gajim_identity)
extension = None
if node and node.find('#') != -1:
extension = node[node.index('#') + 1:]
client_version = 'http://gajim.org#' + gajim.caps_hash[self.name]
@ -979,7 +980,7 @@ class ConnectionVcard:
j = gajim.get_jid_from_account(self.name)
self.awaiting_answers[id] = (VCARD_ARRIVED, j, groupchat_jid)
if groupchat_jid:
room_jid = gajim.get_room_and_nick_from_fjid(groupchat_jid)[0]
room_jid, nick = gajim.get_room_and_nick_from_fjid(groupchat_jid)
if not room_jid in self.room_jids:
self.room_jids.append(room_jid)
self.groupchat_jids[id] = groupchat_jid
@ -1388,7 +1389,6 @@ class ConnectionHandlers(ConnectionVcard, ConnectionBytestream, ConnectionDisco,
try:
idle.init()
except Exception:
global HAS_IDLE
HAS_IDLE = False
self.gmail_last_tid = None
@ -1414,7 +1414,7 @@ class ConnectionHandlers(ConnectionVcard, ConnectionBytestream, ConnectionDisco,
method = iq_obj.getTagAttr('confirm', 'method')
url = iq_obj.getTagAttr('confirm', 'url')
msg = iq_obj.getTagData('body') # In case it's a message with a body
self.dispatch('HTTP_AUTH', (method, url, id, iq_obj, msg))
self.dispatch('HTTP_AUTH', (method, url, id, iq_obj, msg));
raise common.xmpp.NodeProcessed
def _ErrorCB(self, con, iq_obj):
@ -1518,7 +1518,7 @@ class ConnectionHandlers(ConnectionVcard, ConnectionBytestream, ConnectionDisco,
iq_obj = iq_obj.buildReply('result')
qp = iq_obj.getTag('query')
if not HAS_IDLE:
qp.attrs['seconds'] = '0'
qp.attrs['seconds'] = '0';
else:
qp.attrs['seconds'] = idle.getIdleSec()

View File

@ -23,6 +23,8 @@
## along with Gajim. If not, see <http://www.gnu.org/licenses/>.
##
import re
docdir = '../'
datadir = '../'

View File

@ -256,11 +256,12 @@ def get_resource_from_jid(jid):
return jids[1] # abc@doremi.org/res/res-continued
else:
return ''
# [15:34:28] <asterix> we should add contact.fake_jid I think
# [15:34:46] <asterix> so if we know real jid, it wil be in contact.jid, or we look in contact.fake_jid
# [15:32:54] <asterix> they can have resource if we know the real jid
# [15:33:07] <asterix> and that resource is in contact.resource
'''\
[15:34:28] <asterix> we should add contact.fake_jid I think
[15:34:46] <asterix> so if we know real jid, it wil be in contact.jid, or we look in contact.fake_jid
[15:32:54] <asterix> they can have resource if we know the real jid
[15:33:07] <asterix> and that resource is in contact.resource
'''
def get_number_of_accounts():
'''returns the number of ALL accounts'''

View File

@ -847,6 +847,7 @@ def sanitize_filename(filename):
.replace('*', '_').replace('<', '_').replace('>', '_')
# 48 is the limit
if len(filename) > 48:
extension = filename.split('.')[-1]
filename = filename[0:48]
return filename
@ -1026,7 +1027,7 @@ def get_notification_icon_tooltip_dict():
def get_notification_icon_tooltip_text():
text = None
# How many events must there be before they're shown summarized, not per-user
# max_ungrouped_events = 10
max_ungrouped_events = 10
# Character which should be used to indent in the tooltip.
indent_with = ' '

View File

@ -178,7 +178,7 @@ class Logger:
and after that all okay'''
if jid.find('/') > -1:
possible_room_jid = jid.split('/', 1)[1]
possible_room_jid, possible_nick = jid.split('/', 1)
return self.jid_is_room_jid(possible_room_jid)
else:
# it's not a full jid, so it's not a pm one
@ -466,6 +466,7 @@ class Logger:
and are already logged but pending to be viewed,
returns a list of tupples containg time, kind, message,
list with empty tupple if nothing found to meet our demands'''
jid_id = self.get_jid_id(jid)
where_sql = self._build_contact_where(account, jid)
now = int(float(time.time()))
@ -503,6 +504,7 @@ class Logger:
'''returns contact_name, time, kind, show, message
for each row in a list of tupples,
returns list with empty tupple if we found nothing to meet our demands'''
jid_id = self.get_jid_id(jid)
where_sql = self._build_contact_where(account, jid)
start_of_day = self.get_unix_time_from_date(year, month, day)
@ -523,6 +525,7 @@ class Logger:
'''returns contact_name, time, kind, show, message
for each row in a list of tupples,
returns list with empty tupple if we found nothing to meet our demands'''
jid_id = self.get_jid_id(jid)
if False: #query.startswith('SELECT '): # it's SQL query (FIXME)
try:
@ -545,6 +548,7 @@ class Logger:
def get_days_with_logs(self, jid, year, month, max_day, account):
'''returns the list of days that have logs (not status messages)'''
jid_id = self.get_jid_id(jid)
days_with_logs = []
where_sql = self._build_contact_where(account, jid)
@ -704,7 +708,7 @@ class Logger:
# the data field contains binary object (gzipped data), this is a hack
# to get that data without trying to convert it to unicode
try:
self.cur.execute('SELECT hash_method, hash, data FROM caps_cache;')
self.cur.execute('SELECT hash_method, hash, data FROM caps_cache;');
except sqlite.OperationalError:
# might happen when there's no caps_cache table yet
# -- there's no data to read anyway then

View File

@ -268,7 +268,7 @@ class IdleCommand(IdleObject):
def pollin(self):
try:
res = self.pipe.read()
except Exception:
except Exception, e:
res = ''
if res == '':
return self.pollend()
@ -316,6 +316,7 @@ if __name__ == '__main__':
resolver = Resolver(idlequeue)
def clicked(widget):
global resolver
host = text_view.get_text()
def on_result(host, result_array):
print 'Result:\n' + repr(result_array)

View File

@ -264,7 +264,7 @@ class OptionsParser:
)
con.commit()
gajim.logger.init_vars()
except sqlite.OperationalError:
except sqlite.OperationalError, e:
pass
con.close()
@ -336,7 +336,7 @@ class OptionsParser:
'''
)
con.commit()
except sqlite.OperationalError:
except sqlite.OperationalError, e:
pass
con.close()
gajim.config.set('version', '0.10.1.3')
@ -457,7 +457,7 @@ class OptionsParser:
'''
)
con.commit()
except sqlite.OperationalError:
except sqlite.OperationalError, e:
pass
con.close()
gajim.config.set('version', '0.11.1.3')
@ -499,7 +499,7 @@ class OptionsParser:
'''
)
con.commit()
except sqlite.OperationalError:
except sqlite.OperationalError, e:
pass
con.close()
gajim.config.set('version', '0.11.1.5')
@ -535,7 +535,7 @@ class OptionsParser:
'''
)
con.commit()
except sqlite.OperationalError:
except sqlite.OperationalError, e:
pass
con.close()
gajim.config.set('version', '0.11.4.1')
@ -572,7 +572,7 @@ class OptionsParser:
'''
)
con.commit()
except sqlite.OperationalError:
except sqlite.OperationalError, e:
pass
con.close()
gajim.config.set('version', '0.11.4.3')
@ -586,7 +586,7 @@ class OptionsParser:
try:
cur.executescript('DROP TABLE caps_cache;')
con.commit()
except sqlite.OperationalError:
except sqlite.OperationalError, e:
pass
try:
cur.executescript(

View File

@ -67,7 +67,7 @@ class GnomePasswordStorage(PasswordStorage):
if conf is None:
return None
try:
auth_token = conf.split('gnomekeyring:')[1]
unused, auth_token = conf.split('gnomekeyring:')
auth_token = int(auth_token)
except ValueError:
password = conf

View File

@ -169,7 +169,7 @@ def user_mood(items, name, jid):
if 'text' in acc.mood:
del acc.mood['text']
user = gajim.get_room_and_nick_from_fjid(jid)[0]
(user, resource) = gajim.get_room_and_nick_from_fjid(jid)
for contact in gajim.contacts.get_contacts(name, user):
if has_child:
if 'mood' in contact.mood:
@ -255,7 +255,7 @@ def user_tune(items, name, jid):
if 'length' in acc.tune:
del acc.tune['length']
user = gajim.get_room_and_nick_from_fjid(jid)[0]
(user, resource) = gajim.get_room_and_nick_from_fjid(jid)
for contact in gajim.contacts.get_contacts(name, user):
if has_child:
if 'artist' in contact.tune:
@ -344,7 +344,7 @@ def user_activity(items, name, jid):
if 'text' in acc.activity:
del acc.activity['text']
user = gajim.get_room_and_nick_from_fjid(jid)[0]
(user, resource) = gajim.get_room_and_nick_from_fjid(jid)
for contact in gajim.contacts.get_contacts(name, user):
if has_child:
if 'activity' in contact.activity:
@ -491,7 +491,7 @@ def user_retract_nickname(account):
gajim.connections[account].send_pb_retract('', xmpp.NS_NICK, '0')
def delete_pep(jid, name):
user = gajim.get_room_and_nick_from_fjid(jid)[0]
(user, resource) = gajim.get_room_and_nick_from_fjid(jid)
if jid == gajim.get_jid_from_account(name):
acc = gajim.connections[name]

View File

@ -107,10 +107,11 @@ class ProxyResolver:
self.state = S_RESOLVED
#FIXME: re-enable proxy testing
self.state = S_FINISHED
#self.receiver_tester = ReceiverTester(self.host, self.port, self.jid,
# self.sid, self.sender_jid, self._on_receiver_success,
# self._on_connect_failure)
#self.receiver_tester.connect()
return
self.receiver_tester = ReceiverTester(self.host, self.port, self.jid,
self.sid, self.sender_jid, self._on_receiver_success,
self._on_connect_failure)
self.receiver_tester.connect()
def _on_receiver_success(self):
self.host_tester = HostTester(self.host, self.port, self.jid,
@ -279,7 +280,7 @@ class HostTester(Socks5, IdleObject):
self._send = self._sock.send
self._recv = self._sock.recv
except Exception, ee:
errnum = ee[0]
(errnum, errstr) = ee
# 56 is for freebsd
if errnum in (errno.EINPROGRESS, errno.EALREADY, errno.EWOULDBLOCK):
# still trying to connect
@ -391,7 +392,7 @@ class ReceiverTester(Socks5, IdleObject):
self._send = self._sock.send
self._recv = self._sock.recv
except Exception, ee:
errnum = ee[0]
(errnum, errstr) = ee
# 56 is for freebsd
if errnum in (errno.EINPROGRESS, errno.EALREADY, errno.EWOULDBLOCK):
# still trying to connect

View File

@ -87,7 +87,6 @@ class SleepyWindows:
class SleepyUnix:
def __init__(self, away_interval = 60, xa_interval = 120):
global SUPPORTED
self.away_interval = away_interval
self.xa_interval = xa_interval
self.state = STATE_AWAKE # assume we are awake

View File

@ -31,7 +31,6 @@ from errno import EWOULDBLOCK
from errno import ENOBUFS
from errno import EINTR
from errno import EISCONN
from errno import EINPROGRESS
from xmpp.idlequeue import IdleObject
MAX_BUFF_LEN = 65536
@ -421,7 +420,7 @@ class Socks5:
received = ''
try:
add = self._recv(64)
except Exception:
except Exception, e:
add=''
received +=add
if len(add) == 0:
@ -431,8 +430,8 @@ class Socks5:
def send_raw(self,raw_data):
''' Writes raw outgoing data. '''
try:
self._send(raw_data)
except Exception:
lenn = self._send(raw_data)
except Exception, e:
self.disconnect()
return len(raw_data)
@ -486,7 +485,8 @@ class Socks5:
return -1
def get_file_contents(self, timeout):
''' read file contents from socket and write them to file '''
''' read file contents from socket and write them to file ''', \
self.file_props['type'], self.file_props['sid']
if self.file_props is None or \
('file-name' in self.file_props) is False:
self.file_props['error'] = -2
@ -512,7 +512,7 @@ class Socks5:
fd = self.get_fd()
try:
buff = self._recv(MAX_BUFF_LEN)
except Exception:
except Exception, e:
buff = ''
current_time = self.idlequeue.current_time()
self.file_props['elapsed-time'] += current_time - \
@ -576,7 +576,7 @@ class Socks5:
mechanisms '''
auth_mechanisms = []
try:
num_auth = struct.unpack('!BB', buff[:2])[1]
ver, num_auth = struct.unpack('!BB', buff[:2])
for i in xrange(num_auth):
mechanism, = struct.unpack('!B', buff[1 + i])
auth_mechanisms.append(mechanism)
@ -605,7 +605,8 @@ class Socks5:
def _parse_request_buff(self, buff):
try: # don't trust on what comes from the outside
req_type, host_type = struct.unpack('!xBxB', buff[:4])
version, req_type, reserved, host_type, = \
struct.unpack('!BBBB', buff[:4])
if host_type == 0x01:
host_arr = struct.unpack('!iiii', buff[4:8])
host, = '.'.join(str(s) for s in host_arr)
@ -767,7 +768,7 @@ class Socks5Sender(Socks5, IdleObject):
return -1 # invalid auth methods received
elif self.state == 3: # get next request
buff = self.receive()
req_type, self.sha_msg = self._parse_request_buff(buff)[:2]
(req_type, self.sha_msg, port) = self._parse_request_buff(buff)
if req_type != 0x01:
return -1 # request is not of type 'connect'
self.state += 1 # go to the next step
@ -902,10 +903,10 @@ class Socks5Receiver(Socks5, IdleObject):
self._sock.setblocking(False)
self._server=ai[4]
break
except socket.error, e:
if not isinstance(e, basestring) and e[0] == EINPROGRESS:
except Exception:
if sys.exc_value[0] == errno.EINPROGRESS:
break
# for all other errors, we try other addresses
#for all errors, we try other addresses
continue
self.fd = self._sock.fileno()
self.state = 0 # about to be connected
@ -975,7 +976,7 @@ class Socks5Receiver(Socks5, IdleObject):
self._send=self._sock.send
self._recv=self._sock.recv
except Exception, ee:
errnum = ee[0]
(errnum, errstr) = ee
self.connect_timeout += 1
if errnum == 111 or self.connect_timeout > 1000:
self.queue._connection_refused(self.streamhost,
@ -1020,8 +1021,8 @@ class Socks5Receiver(Socks5, IdleObject):
sub_buff = buff[:4]
if len(sub_buff) < 4:
return None
version, address_type = struct.unpack('!BxxB', buff[:4])
addrlen = 0
version, command, rsvd, address_type = struct.unpack('!BBBB', buff[:4])
addrlen, address, port = 0, 0, 0
if address_type == 0x03:
addrlen = ord(buff[4])
address = struct.unpack('!%ds' % addrlen, buff[5:addrlen + 5])

View File

@ -28,7 +28,6 @@ from common import gajim
from common import xmpp
from common import exceptions
import itertools
import random
import string
@ -92,8 +91,8 @@ class StanzaSession(object):
return any_removed
def generate_thread_id(self):
return ''.join([f(string.ascii_letters) for f in itertools.repeat(
random.choice, 32)])
return ''.join([random.choice(string.ascii_letters) for x in xrange(0,
32)])
def send(self, msg):
if self.thread_id:
@ -284,7 +283,7 @@ class EncryptedStanzaSession(StanzaSession):
return stanza
def is_xep_200_encrypted(self, msg):
msg.getTag('c', namespace=xmpp.NS_STANZA_CRYPTO)
msg.getTag('c', namespace=common.xmpp.NS_STANZA_CRYPTO)
def hmac(self, key, content):
return HMAC.new(key, content, self.hash_alg).digest()
@ -387,9 +386,10 @@ class EncryptedStanzaSession(StanzaSession):
parsed = xmpp.Node(node='<node>' + plaintext + '</node>')
if self.negotiated['recv_pubkey'] == 'hash':
# fingerprint = parsed.getTagData('fingerprint')
fingerprint = parsed.getTagData('fingerprint')
# XXX find stored pubkey or terminate session
raise NotImplementedError()
raise 'unimplemented'
else:
if self.negotiated['sign_algs'] == (XmlDsig + 'rsa-sha256'):
keyvalue = parsed.getTag(name='RSAKeyValue', namespace=XmlDsig)
@ -771,7 +771,7 @@ class EncryptedStanzaSession(StanzaSession):
else:
srses = secrets.secrets().retained_secrets(self.conn.name,
self.jid.getStripped())
rshashes = [self.hmac(self.n_s, rs[0]) for rs in srses]
rshashes = [self.hmac(self.n_s, rs) for (rs,v) in srses]
if not rshashes:
# we've never spoken before, but we'll pretend we have
@ -838,7 +838,7 @@ class EncryptedStanzaSession(StanzaSession):
rshashes = [base64.b64decode(rshash) for rshash in form.getField(
'rshashes').getValues()]
for secret in (s[0] for s in srses):
for (secret, verified) in srses:
if self.hmac(self.n_o, secret) in rshashes:
srs = secret
break
@ -889,7 +889,7 @@ class EncryptedStanzaSession(StanzaSession):
srshash = base64.b64decode(form['srshash'])
for secret in (s[0] for s in srses):
for (secret, verified) in srses:
if self.hmac(secret, 'Shared Retained Secret') == srshash:
srs = secret
break

View File

@ -61,14 +61,8 @@ class NonSASL(PlugIn):
token=query.getTagData('token')
seq=query.getTagData('sequence')
self.DEBUG("Performing zero-k authentication",'ok')
def hasher(s):
return sha.new(s).hexdigest()
def hash_n_times(s, count):
return count and hasher(hash_n_times(s, count-1)) or s
hash = hash_n_times(hasher(hasher(self.password)+token), int(seq))
hash = sha.new(sha.new(self.password).hexdigest()+token).hexdigest()
for foo in xrange(int(seq)): hash = sha.new(hash).hexdigest()
query.setTagData('hash',hash)
method='0k'
else:
@ -188,8 +182,10 @@ class SASL(PlugIn):
resp['username']=self.username
resp['realm']=self._owner.Server
resp['nonce']=chal['nonce']
resp['cnonce'] = ''.join("%x" % randint(0, 2**28) for randint in
itertools.repeat(random.randint, 7))
cnonce=''
for i in range(7):
cnonce+=hex(int(random.random()*65536*4096))[2:]
resp['cnonce']=cnonce
resp['nc']=('00000001')
resp['qop']='auth'
resp['digest-uri']='xmpp/'+self._owner.Server
@ -309,4 +305,4 @@ class ComponentBind(PlugIn):
self.DEBUG('Binding failed: timeout expired.','error')
return ''
# vim: se ts=3:
# vim: se ts=3:

View File

@ -17,14 +17,11 @@
Provides library with all Non-SASL and SASL authentication mechanisms.
Can be used both for client and transport authentication.
'''
import sys
from protocol import *
from auth import *
from client import PlugIn
import sha
import base64
import random
import itertools
import dispatcher_nb
import sha,base64,random,dispatcher_nb
try:
import kerberos
@ -145,8 +142,8 @@ class SASL(PlugIn):
self._owner.RegisterHandler('failure', self.SASLHandler, xmlns=NS_SASL)
self._owner.RegisterHandler('success', self.SASLHandler, xmlns=NS_SASL)
if "GSSAPI" in mecs and have_kerberos:
self.gss_vc = kerberos.authGSSClientInit(
'xmpp@' + self._owner.Server)[1]
rc, self.gss_vc = kerberos.authGSSClientInit('xmpp@' +
self._owner.Server)
response = kerberos.authGSSClientResponse(self.gss_vc)
node=Node('auth',attrs={'xmlns': NS_SASL, 'mechanism': 'GSSAPI'},
payload=(response or ""))
@ -227,8 +224,10 @@ class SASL(PlugIn):
else:
resp['realm'] = self._owner.Server
resp['nonce']=chal['nonce']
resp['cnonce'] = ''.join("%x" % randint(0, 2**28) for randint in
itertools.repeat(random.randint, 7))
cnonce=''
for i in range(7):
cnonce += hex(int(random.random() * 65536 * 4096))[2:]
resp['cnonce'] = cnonce
resp['nc'] = ('00000001')
resp['qop'] = 'auth'
resp['digest-uri'] = 'xmpp/'+self._owner.Server
@ -279,7 +278,7 @@ class NonBlockingNonSASL(PlugIn):
self.DEBUG('Querying server about possible auth methods', 'start')
self.owner = owner
owner.Dispatcher.SendAndWaitForResponse(
resp = owner.Dispatcher.SendAndWaitForResponse(
Iq('get', NS_AUTH, payload=[Node('username', payload=[self.user])]), func=self._on_username
)
@ -303,14 +302,9 @@ class NonBlockingNonSASL(PlugIn):
token=query.getTagData('token')
seq=query.getTagData('sequence')
self.DEBUG("Performing zero-k authentication",'ok')
def hasher(s):
return sha.new(s).hexdigest()
def hash_n_times(s, count):
return count and hasher(hash_n_times(s, count-1)) or s
hash = hash_n_times(hasher(hasher(self.password) + token), int(seq))
hash = sha.new(sha.new(self.password).hexdigest()+token).hexdigest()
for foo in xrange(int(seq)):
hash = sha.new(hash).hexdigest()
query.setTagData('hash',hash)
self._method='0k'
else:
@ -345,7 +339,7 @@ class NonBlockingNonSASL(PlugIn):
self.DEBUG('waiting on handshake', 'notify')
return
self._owner.onreceive(None)
self._owner._registered_name=self.user
owner._registered_name=self.user
if self.handshake+1:
return self.on_auth('ok')
self.on_auth(None)
@ -382,7 +376,7 @@ class NonBlockingBind(Bind):
self._resource = []
self._owner.onreceive(None)
self._owner.Dispatcher.SendAndWaitForResponse(
resp=self._owner.Dispatcher.SendAndWaitForResponse(
Protocol('iq',typ='set',
payload=[Node('bind', attrs={'xmlns':NS_BIND}, payload=self._resource)]),
func=self._on_bound)
@ -444,14 +438,12 @@ class NBComponentBind(ComponentBind):
def Bind(self, domain = None, on_bind = None):
''' Perform binding. Use provided domain name (if not provided). '''
def wrapper(resp):
self._on_bound(resp, domain)
self._owner.onreceive(wrapper)
self._owner.onreceive(self._on_bound)
self.on_bind = on_bind
def _on_bound(self, resp, domain=None):
if resp:
self.Dispatcher.ProcessNonBlocking(resp)
def _on_bound(self, resp):
if data:
self.Dispatcher.ProcessNonBlocking(data)
if self.bound is None:
return
self._owner.onreceive(None)
@ -459,7 +451,7 @@ class NBComponentBind(ComponentBind):
Protocol('bind', attrs={'name':domain}, xmlns=NS_COMPONENT_1),
func=self._on_bind_reponse)
def _on_bind_reponse(self, resp):
def _on_bind_reponse(self, res):
if resp and resp.getAttr('error'):
self.DEBUG('Binding failed: %s.' % resp.getAttr('error'), 'error')
elif resp:

View File

@ -26,8 +26,6 @@ automatically called when user requests some node of your disco tree.
from dispatcher import *
from client import PlugIn
DBG_BROWSER = "Browser"
class Browser(PlugIn):
""" WARNING! This class is for components only. It will not work in client mode!
@ -82,7 +80,7 @@ class Browser(PlugIn):
def __init__(self):
"""Initialises internal variables. Used internally."""
PlugIn.__init__(self)
self.DBG_LINE = DBG_BROWSER
DBG_LINE='browser'
self._exported_methods=[]
self._handlers={'':{}}
@ -91,7 +89,6 @@ class Browser(PlugIn):
Used internally."""
owner.RegisterHandler('iq',self._DiscoveryHandler,typ='get',ns=NS_DISCO_INFO)
owner.RegisterHandler('iq',self._DiscoveryHandler,typ='get',ns=NS_DISCO_ITEMS)
owner.debug_flags.append(DBG_BROWSER)
def plugout(self):
""" Unregisters browser's iq handlers from your application dispatcher instance.
@ -218,4 +215,4 @@ class Browser(PlugIn):
conn.send(rep)
raise NodeProcessed
# vim: se ts=3:
# vim: se ts=3:

View File

@ -21,6 +21,7 @@ examples of xmpppy structures usage.
These classes can be used for simple applications "AS IS" though.
"""
import socket
import debug
Debug=debug
Debug.DEBUGGING_IS_ON=1

View File

@ -23,6 +23,9 @@ examples of xmpppy structures usage.
These classes can be used for simple applications "AS IS" though.
'''
import socket
import debug
import transports_nb, dispatcher_nb, auth_nb, roster_nb
from client import *

View File

@ -31,12 +31,9 @@ What it supplies:
A means of handling requests, by redirection though the command manager.
"""
import math
from protocol import *
from client import PlugIn
DBG_COMMANDS = 'commands'
class Commands(PlugIn):
"""Commands is an ancestor of PlugIn and can be attached to any session.
@ -49,7 +46,7 @@ class Commands(PlugIn):
def __init__(self, browser):
"""Initialises class and sets up local variables"""
PlugIn.__init__(self)
self.DBG_LINE = DBG_COMMANDS
DBG_LINE='commands'
self._exported_methods=[]
self._handlers={'':{}}
self._browser = browser
@ -61,14 +58,13 @@ class Commands(PlugIn):
owner.RegisterHandler('iq',self._CommandHandler,typ='set',ns=NS_COMMANDS)
owner.RegisterHandler('iq',self._CommandHandler,typ='get',ns=NS_COMMANDS)
self._browser.setDiscoHandler(self._DiscoHandler,node=NS_COMMANDS,jid='')
owner.debug_flags.append(DBG_COMMANDS)
def plugout(self):
"""Removes handlers from the session"""
# unPlug from the session and the disco manager
self._owner.UnregisterHandler('iq',self._CommandHandler,ns=NS_COMMANDS)
self._owner.UnregisterHandler('iq',self_CommandHandler,ns=NS_COMMANDS)
for jid in self._handlers:
self._browser.delDiscoHandler(self._DiscoHandler,node=NS_COMMANDS,jid=jid)
self._browser.delDiscoHandler(self._DiscoHandler,node=NS_COMMANDS)
def _CommandHandler(self,conn,request):
"""The internal method to process the routing of command execution requests"""
@ -197,7 +193,7 @@ class Command_Handler_Prototype(PlugIn):
def __init__(self,jid=''):
"""Set up the class"""
PlugIn.__init__(self)
self.DBG_LINE='command'
DBG_LINE='command'
self.sessioncount = 0
self.sessions = {}
# Disco information for command list pre-formatted as a tuple
@ -285,10 +281,10 @@ class TestCommand(Command_Handler_Prototype):
session = None
if session is None:
session = self.getSessionID()
self.sessions[session]={'jid':request.getFrom(),'actions':{'cancel':self.cmdCancel,'next':self.cmdSecondStage},'data':{'type':None}}
sessions[session]={'jid':request.getFrom(),'actions':{'cancel':self.cmdCancel,'next':self.cmdSecondStage},'data':{'type':None}}
# As this is the first stage we only send a form
reply = request.buildReply('result')
form = DataForm(title='Select type of operation',data=['Use the combobox to select the type of calculation you would like to do, then click Next',DataField(name='calctype',label='Calculation Type',value=self.sessions[session]['data']['type'],options=[['circlediameter','Calculate the Diameter of a circle'],['circlearea','Calculate the area of a circle']],typ='list-single',required=1)])
form = DataForm(title='Select type of operation',data=['Use the combobox to select the type of calculation you would like to do, then click Next',DataField(name='calctype',label='Calculation Type',value=sessions[session]['data']['type'],options=[['circlediameter','Calculate the Diameter of a circle'],['circlearea','Calculate the area of a circle']],typ='list-single',required=1)])
replypayload = [Node('actions',attrs={'execute':'next'},payload=[Node('next')]),form]
reply.addChild(name='command',attrs={'xmlns':NS_COMMAND,'node':request.getTagAttr('command','node'),'sessionid':session,'status':'executing'},payload=replypayload)
self._owner.send(reply)
@ -316,9 +312,9 @@ class TestCommand(Command_Handler_Prototype):
except Exception:
self.cmdSecondStageReply(conn,request)
if sessions[request.getTagAttr('command','sessionid')]['data']['type'] == 'circlearea':
result = num*(math.pi**2)
result = num*(pi**2)
else:
result = num*2*math.pi
result = num*2*pi
reply = result.buildReply(request)
form = DataForm(typ='result',data=[DataField(label='result',name='result',value=result)])
reply.addChild(name='command',attrs={'xmlns':NS_COMMAND,'node':request.getTagAttr('command','node'),'sessionid':request.getTagAttr('command','sessionid'),'status':'completed'},payload=form)
@ -329,8 +325,8 @@ class TestCommand(Command_Handler_Prototype):
reply = request.buildReply('result')
reply.addChild(name='command',attrs={'xmlns':NS_COMMAND,'node':request.getTagAttr('command','node'),'sessionid':request.getTagAttr('command','sessionid'),'status':'cancelled'})
self._owner.send(reply)
del self.sessions[request.getTagAttr('command','sessionid')]
del sessions[request.getTagAttr('command','sessionid')]
# vim: se ts=3:
# vim: se ts=3:

View File

@ -12,7 +12,10 @@
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
## GNU Lesser General Public License for more details.
"""
_version_ = '1.4.0'
"""\
Generic debug class
Other modules can always define extra debug flags for local usage, as long as
@ -31,9 +34,9 @@ by the individual classes.
For samples of usage, see samples subdir in distro source, and selftest
in this code
"""
_version_ = '1.4.0'
import sys
@ -41,6 +44,8 @@ import traceback
import time
import os
import types
if 'TERM' in os.environ:
colors_enabled=True
else:
@ -65,34 +70,36 @@ color_bright_cyan = chr(27) + "[36;1m"
color_white = chr(27) + "[37;1m"
# Define your flags in yor modules like this:
#
# from debug import *
#
# DBG_INIT = 'init' ; debug_flags.append( DBG_INIT )
# DBG_CONNECTION = 'connection' ; debug_flags.append( DBG_CONNECTION )
#
# The reason for having a double statement wis so we can validate params
# and catch all undefined debug flags
#
# This gives us control over all used flags, and makes it easier to allow
# global debugging in your code, just do something like
#
# foo = Debug( debug_flags )
#
# group flags, that is a flag in it self containing multiple flags should be
# defined without the debug_flags.append() sequence, since the parts are already
# in the list, also they must of course be defined after the flags they depend on ;)
# example:
#
# DBG_MULTI = [ DBG_INIT, DBG_CONNECTION ]
#
#
#
# NoDebug
# -------
# To speed code up, typically for product releases or such
# use this class instead if you globaly want to disable debugging
"""
Define your flags in yor modules like this:
from debug import *
DBG_INIT = 'init' ; debug_flags.append( DBG_INIT )
DBG_CONNECTION = 'connection' ; debug_flags.append( DBG_CONNECTION )
The reason for having a double statement wis so we can validate params
and catch all undefined debug flags
This gives us control over all used flags, and makes it easier to allow
global debugging in your code, just do something like
foo = Debug( debug_flags )
group flags, that is a flag in it self containing multiple flags should be
defined without the debug_flags.append() sequence, since the parts are already
in the list, also they must of course be defined after the flags they depend on ;)
example:
DBG_MULTI = [ DBG_INIT, DBG_CONNECTION ]
NoDebug
-------
To speed code up, typically for product releases or such
use this class instead if you globaly want to disable debugging
"""
class NoDebug:

View File

@ -28,14 +28,12 @@ from client import PlugIn
DefaultTimeout=25
ID=0
DBG_DISPATCHER = 'dispatcher'
class Dispatcher(PlugIn):
""" Ancestor of PlugIn class. Handles XMPP stream, i.e. aware of stream headers.
Can be plugged out/in to restart these headers (used for SASL f.e.). """
def __init__(self):
PlugIn.__init__(self)
self.DBG_LINE = DBG_DISPATCHER
DBG_LINE='dispatcher'
self.handlers={}
self._expected={}
self._defaultHandler=None
@ -84,7 +82,6 @@ class Dispatcher(PlugIn):
self._owner.lastErr=None
self._owner.lastErrCode=None
self.StreamInit()
owner.debug_flags.append(DBG_DISPATCHER)
def plugout(self):
""" Prepares instance to be destructed. """
@ -295,6 +292,7 @@ class Dispatcher(PlugIn):
for key in list:
if key: chain = chain + self.handlers[xmlns][name][key]
output=''
if ID in session._expected:
user=0
if isinstance(session._expected[ID], tuple):
@ -325,6 +323,7 @@ class Dispatcher(PlugIn):
lastErrNode, lastErr and lastErrCode are set accordingly. """
if timeout is None: timeout=DefaultTimeout
self._expected[ID]=None
has_timed_out=0
abort_time=time.time() + timeout
self.DEBUG("Waiting for ID:%s with timeout %s..." % (ID,timeout),'wait')
while not self._expected[ID]:

View File

@ -37,7 +37,7 @@ class Dispatcher(PlugIn):
Can be plugged out/in to restart these headers (used for SASL f.e.). '''
def __init__(self):
PlugIn.__init__(self)
self.DBG_LINE='dispatcher'
DBG_LINE='dispatcher'
self.handlers={}
self._expected={}
self._defaultHandler=None
@ -334,6 +334,7 @@ class Dispatcher(PlugIn):
for key in list:
if key: chain = chain + self.handlers[xmlns][name][key]
output=''
if ID in session._expected:
user=0
if isinstance(session._expected[ID], tuple):

View File

@ -49,10 +49,10 @@ def _discover(disp,ns,jid,node=None,fb2b=0,fb2a=1):
def discoverItems(disp,jid,node=None):
""" Query remote object about any items that it contains. Return items list. """
# According to JEP-0030:
# query MAY have node attribute
# item: MUST HAVE jid attribute and MAY HAVE name, node, action attributes.
# action attribute of item can be either of remove or update value.
""" According to JEP-0030:
query MAY have node attribute
item: MUST HAVE jid attribute and MAY HAVE name, node, action attributes.
action attribute of item can be either of remove or update value."""
ret=[]
for i in _discover(disp,NS_DISCO_ITEMS,jid,node):
if i.getName()=='agent' and i.getTag('name'): i.setAttr('name',i.getTagData('name'))
@ -61,10 +61,10 @@ def discoverItems(disp,jid,node=None):
def discoverInfo(disp,jid,node=None):
""" Query remote object about info that it publishes. Returns identities and features lists."""
# According to JEP-0030:
# query MAY have node attribute
# identity: MUST HAVE category and name attributes and MAY HAVE type attribute.
# feature: MUST HAVE var attribute"""
""" According to JEP-0030:
query MAY have node attribute
identity: MUST HAVE category and name attributes and MAY HAVE type attribute.
feature: MUST HAVE var attribute"""
identities , features = [] , []
for i in _discover(disp,NS_DISCO_INFO,jid,node):
if i.getName()=='identity': identities.append(i.attrs)

View File

@ -58,10 +58,10 @@ def _discover(disp, ns, jid, node = None, fb2b=0, fb2a=1, cb=None):
# this function is not used in gajim ???
def discoverItems(disp,jid,node=None, cb=None):
""" Query remote object about any items that it contains. Return items list. """
# According to JEP-0030:
# query MAY have node attribute
# item: MUST HAVE jid attribute and MAY HAVE name, node, action attributes.
# action attribute of item can be either of remove or update value.
""" According to JEP-0030:
query MAY have node attribute
item: MUST HAVE jid attribute and MAY HAVE name, node, action attributes.
action attribute of item can be either of remove or update value."""
def _on_response(result_array):
ret=[]
for result in result_array:
@ -75,10 +75,10 @@ def discoverItems(disp,jid,node=None, cb=None):
# this one is
def discoverInfo(disp,jid,node=None, cb=None):
""" Query remote object about info that it publishes. Returns identities and features lists."""
# According to JEP-0030:
# query MAY have node attribute
# identity: MUST HAVE category and name attributes and MAY HAVE type attribute.
# feature: MUST HAVE var attribute
""" According to JEP-0030:
query MAY have node attribute
identity: MUST HAVE category and name attributes and MAY HAVE type attribute.
feature: MUST HAVE var attribute"""
def _on_response(result):
identities , features = [] , []
for i in result:
@ -118,6 +118,7 @@ def getRegInfo(disp, host, info={}, sync=True):
disp.SendAndCallForResponse(iq, _ReceivedRegInfo, {'agent': host })
def _ReceivedRegInfo(con, resp, agent):
iq=Iq('get',NS_REGISTER,to=agent)
if not isResultNode(resp):
error_msg = resp.getErrorMsg()
con.Event(NS_REGISTER,REGISTER_DATA_RECEIVED,(agent,None,False,error_msg))
@ -251,4 +252,4 @@ def delPrivacyList(disp,listname,cb=None):
iq = Iq('set',NS_PRIVACY,payload=[Node('list',{'name':listname})])
_on_default_response(disp, iq, cb)
# vim: se ts=3:
# vim: se ts=3:

View File

@ -58,14 +58,16 @@ class IBB(PlugIn):
def StreamOpenHandler(self,conn,stanza):
""" Handles opening of new incoming stream. Used internally. """
# <iq type='set'
# from='romeo@montague.net/orchard'
# to='juliet@capulet.com/balcony'
# id='inband_1'>
# <open sid='mySID'
# block-size='4096'
# xmlns='http://jabber.org/protocol/ibb'/>
# </iq>
"""
<iq type='set'
from='romeo@montague.net/orchard'
to='juliet@capulet.com/balcony'
id='inband_1'>
<open sid='mySID'
block-size='4096'
xmlns='http://jabber.org/protocol/ibb'/>
</iq>
"""
err=None
sid,blocksize=stanza.getTagAttr('open','sid'),stanza.getTagAttr('open','block-size')
self.DEBUG('StreamOpenHandler called sid->%s blocksize->%s'%(sid,blocksize),'info')
@ -99,8 +101,7 @@ class IBB(PlugIn):
self.DEBUG('SendHandler called','info')
for sid in self._streams.keys():
stream=self._streams[sid]
if stream['direction'][:2]=='|>':
pass
if stream['direction'][:2]=='|>': cont=1
elif stream['direction'][0]=='>':
chunk=stream['fp'].read(stream['block-size'])
if chunk:
@ -109,27 +110,29 @@ class IBB(PlugIn):
if stream['seq']==65536: stream['seq']=0
conn.send(Protocol('message',stream['direction'][1:],payload=[datanode,self._ampnode]))
else:
# notify the other side about stream closing
# notify the local user about sucessfull send
# delete the local stream
""" notify the other side about stream closing
notify the local user about sucessfull send
delete the local stream"""
conn.send(Protocol('iq',stream['direction'][1:],'set',payload=[Node(NS_IBB+' close',{'sid':sid})]))
conn.Event(self.DBG_LINE,'SUCCESSFULL SEND',stream)
del self._streams[sid]
self._owner.UnregisterCycleHandler(self.SendHandler)
# <message from='romeo@montague.net/orchard' to='juliet@capulet.com/balcony' id='msg1'>
# <data xmlns='http://jabber.org/protocol/ibb' sid='mySID' seq='0'>
# qANQR1DBwU4DX7jmYZnncmUQB/9KuKBddzQH+tZ1ZywKK0yHKnq57kWq+RFtQdCJ
# WpdWpR0uQsuJe7+vh3NWn59/gTc5MDlX8dS9p0ovStmNcyLhxVgmqS8ZKhsblVeu
# IpQ0JgavABqibJolc3BKrVtVV1igKiX/N7Pi8RtY1K18toaMDhdEfhBRzO/XB0+P
# AQhYlRjNacGcslkhXqNjK5Va4tuOAPy2n1Q8UUrHbUd0g+xJ9Bm0G0LZXyvCWyKH
# kuNEHFQiLuCY6Iv0myq6iX6tjuHehZlFSh80b5BVV9tNLwNR5Eqz1klxMhoghJOA
# </data>
# <amp xmlns='http://jabber.org/protocol/amp'>
# <rule condition='deliver-at' value='stored' action='error'/>
# <rule condition='match-resource' value='exact' action='error'/>
# </amp>
# </message>
"""
<message from='romeo@montague.net/orchard' to='juliet@capulet.com/balcony' id='msg1'>
<data xmlns='http://jabber.org/protocol/ibb' sid='mySID' seq='0'>
qANQR1DBwU4DX7jmYZnncmUQB/9KuKBddzQH+tZ1ZywKK0yHKnq57kWq+RFtQdCJ
WpdWpR0uQsuJe7+vh3NWn59/gTc5MDlX8dS9p0ovStmNcyLhxVgmqS8ZKhsblVeu
IpQ0JgavABqibJolc3BKrVtVV1igKiX/N7Pi8RtY1K18toaMDhdEfhBRzO/XB0+P
AQhYlRjNacGcslkhXqNjK5Va4tuOAPy2n1Q8UUrHbUd0g+xJ9Bm0G0LZXyvCWyKH
kuNEHFQiLuCY6Iv0myq6iX6tjuHehZlFSh80b5BVV9tNLwNR5Eqz1klxMhoghJOA
</data>
<amp xmlns='http://jabber.org/protocol/amp'>
<rule condition='deliver-at' value='stored' action='error'/>
<rule condition='match-resource' value='exact' action='error'/>
</amp>
</message>
"""
def ReceiveHandler(self,conn,stanza):
""" Receive next portion of incoming datastream and store it write
@ -195,4 +198,4 @@ class IBB(PlugIn):
conn.Event(self.DBG_LINE,'STREAM COMMITTED',stream)
else: conn.send(Error(stanza,ERR_UNEXPECTED_REQUEST))
# vim: se ts=3:
# vim: se ts=3:

View File

@ -19,6 +19,7 @@ class IdleObject:
'''
def __init__(self):
self.fd = -1
pass
def pollend(self):
''' called on stream failure '''
@ -219,4 +220,4 @@ class SelectIdleQueue(IdleQueue):
self.check_time_events()
return True
# vim: se ts=3:
# vim: se ts=3:

View File

@ -19,7 +19,7 @@ Protocol module contains tools that is needed for processing of
xmpp-related data structures.
"""
from simplexml import Node, NodeBuilder
from simplexml import Node,NodeBuilder,ustr
import time
NS_ACTIVITY ='http://jabber.org/protocol/activity' # XEP-0108
NS_ADDRESS ='http://jabber.org/protocol/address' # XEP-0033
@ -458,7 +458,7 @@ class Message(Protocol):
self.setTag('html',namespace=NS_XHTML_IM).addChild(node=dom)
except Exception, e:
print "Error", e
#FIXME: log. we could not set xhtml (parse error, whatever)
pass #FIXME: log. we could not set xhtml (parse error, whatever)
def setSubject(self,val):
""" Sets the subject of the message. """
self.setTagData('subject',val)

View File

@ -13,6 +13,7 @@
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
## GNU General Public License for more details.
__version__="$Id"
"""
When your handler is called it is getting the session instance as the first argument.
@ -22,10 +23,6 @@ one client for each connection. Is is specifically important when you are
writing the server.
"""
__version__="$Id"
import random
import simplexml
from protocol import *
# Transport-level flags
@ -252,6 +249,7 @@ class Session:
features=Node('stream:features')
if NS_TLS in self.waiting_features:
features.T.starttls.setNamespace(NS_TLS)
features.T.starttls.T.required
if NS_SASL in self.waiting_features:
features.T.mechanisms.setNamespace(NS_SASL)
for mec in self._owner.SASL.mechanisms:

View File

@ -27,13 +27,11 @@ Transports are stackable so you - f.e. TLS use HTPPROXYsocket or TCPsocket as mo
Also exception 'error' is defined to allow capture of this module specific exceptions.
"""
import socket
import select
import base64
import dispatcher
import socket,select,base64,dispatcher
from simplexml import ustr
from client import PlugIn
from protocol import *
import sys
import os
import errno
@ -66,15 +64,13 @@ class error:
"""Serialise exception into pre-cached descriptive string."""
return self._comment
DBG_SOCKET = "socket"
class TCPsocket(PlugIn):
""" This class defines direct TCP connection method. """
def __init__(self, server=None, use_srv=True):
""" Cache connection point 'server'. 'server' is the tuple of (host, port)
absolutely the same as standard tcp socket uses. """
PlugIn.__init__(self)
self.DBG_LINE = DBG_SOCKET
self.DBG_LINE='socket'
self._exported_methods=[self.send,self.disconnect]
self._server = server
@ -87,7 +83,6 @@ class TCPsocket(PlugIn):
if not self.connect(self._server): return
self._owner.Connection=self
self._owner.RegisterDisconnectHandler(self.disconnected)
owner.debug_flags.append(DBG_SOCKET)
return 'ok'
def getHost(self):
@ -238,7 +233,7 @@ class TLS(PlugIn):
"""
if 'TLS' in owner.__dict__: return # Already enabled.
PlugIn.PlugIn(self,owner)
self.DBG_LINE='TLS'
DBG_LINE='TLS'
if now: return self._startSSL()
if self._owner.Dispatcher.Stream.features:
try: self.FeaturesHandler(self._owner.Dispatcher,self._owner.Dispatcher.Stream.features)
@ -271,7 +266,7 @@ class TLS(PlugIn):
def _startSSL(self):
""" Immidiatedly switch socket to TLS mode. Used internally."""
# Here we should switch pending_data to hint mode.
""" Here we should switch pending_data to hint mode."""
tcpsock=self._owner.Connection
tcpsock._sslObj = socket.ssl(tcpsock._sock, None, None)
tcpsock._sslIssuer = tcpsock._sslObj.issuer()

View File

@ -14,9 +14,7 @@
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
## GNU General Public License for more details.
import socket
import base64
import dispatcher_nb
import socket,select,base64,dispatcher_nb
import struct
from simplexml import ustr
from client import PlugIn
@ -30,6 +28,7 @@ import errno
import time
import traceback
import thread
import logging
log = logging.getLogger('gajim.c.x.transports_nb')
@ -38,7 +37,6 @@ import common.gajim
USE_PYOPENSSL = False
DBG_NONBLOCKINGTLS= 'NonBlockingTLS'
try:
#raise ImportError("Manually disabled PyOpenSSL")
import OpenSSL.SSL
@ -140,10 +138,10 @@ class SSLWrapper:
can indicate that the socket has been closed, so to be sure, we avoid
this by returning None. """
raise NotImplementedError()
raise NotImplementedException()
def send(self, data, flags=None, now = False):
raise NotImplementedError()
raise NotImplementedException()
class PyOpenSSLWrapper(SSLWrapper):
'''Wrapper class for PyOpenSSL's recv() and send() methods'''
@ -663,8 +661,6 @@ class NonBlockingTcp(PlugIn, IdleObject):
''' Return the 'port' value that is connection is [will be] made to.'''
return self._server[1]
DBG_NONBLOCKINGTLS = "NonBlockingTLS"
class NonBlockingTLS(PlugIn):
''' TLS connection used to encrypts already estabilished tcp connection.'''
@ -683,13 +679,12 @@ class NonBlockingTLS(PlugIn):
if 'NonBlockingTLS' in owner.__dict__:
return # Already enabled.
PlugIn.PlugIn(self, owner)
self.DBG_LINE = DBG_NONBLOCKINGTLS
owner.debug_flags.append(DBG_NONBLOCKINGTLS)
DBG_LINE='NonBlockingTLS'
self.on_tls_start = on_tls_start
if now:
try:
res = self._startSSL()
except Exception:
except Exception, e:
log.error("PlugIn: while trying _startSSL():", exc_info=True)
#traceback.print_exc()
self._owner.socket.pollend()
@ -864,7 +859,7 @@ class NonBlockingTLS(PlugIn):
self.DEBUG('Got starttls proceed response. Switching to TLS/SSL...','ok')
try:
self._startSSL()
except Exception:
except Exception, e:
log.error("StartTLSHandler:", exc_info=True)
#traceback.print_exc()
self._owner.socket.pollend()
@ -1105,9 +1100,9 @@ class NBSOCKS5PROXYsocket(NonBlockingTcp):
return
# Get the bound address/port
elif reply[3] == "\x01":
pass # begin, end = 3, 7
begin, end = 3, 7
elif reply[3] == "\x03":
pass # begin, end = 4, 4 + reply[4]
begin, end = 4, 4 + reply[4]
else:
self.DEBUG('Invalid proxy reply', 'error')
self._owner.disconnected()

View File

@ -71,7 +71,7 @@ class ZeroconfListener(IdleObject):
# will fail when port is busy, or we don't have rights to bind
try:
self._serv.bind((ai[4][0], self.port))
except Exception:
except Exception, e:
# unable to bind, show error dialog
return None
self._serv.listen(socket.SOMAXCONN)
@ -87,14 +87,14 @@ class ZeroconfListener(IdleObject):
def pollin(self):
''' accept a new incomming connection and notify queue'''
sock = self.accept_conn()
# loop through roster to find who has connected to us
''' loop through roster to find who has connected to us'''
from_jid = None
ipaddr = sock[1][0]
for jid in self.conn_holder.getRoster().keys():
entry = self.conn_holder.getRoster().getItem(jid)
if (entry['address'] == ipaddr):
from_jid = jid
break
break;
P2PClient(sock[0], ipaddr, sock[1][1], self.conn_holder, [], from_jid)
def disconnect(self):
@ -158,7 +158,7 @@ class P2PClient(IdleObject):
self.conn_holder.add_connection(self, self.Server, port, self.to)
# count messages in queue
for val in self.stanzaqueue:
is_message = val[1]
stanza, is_message = val
if is_message:
if self.fd == -1:
if on_not_ok:
@ -482,6 +482,18 @@ class P2PConnection(IdleObject, PlugIn):
self.disconnect()
return True
def onreceive(self, recv_handler):
if not recv_handler:
if hasattr(self._owner, 'Dispatcher'):
self.on_receive = self._owner.Dispatcher.ProcessNonBlocking
else:
self.on_receive = None
return
_tmp = self.on_receive
# make sure this cb is not overriden by recursive calls
if not recv_handler(None) and _tmp == self.on_receive:
self.on_receive = recv_handler
def disconnect(self):
''' Closes the socket. '''
gajim.idlequeue.remove_timeout(self.fd)

View File

@ -23,6 +23,7 @@
## along with Gajim. If not, see <http://www.gnu.org/licenses/>.
##
import os
import time
import socket
@ -76,6 +77,7 @@ class ConnectionBytestream(connection_handlers.ConnectionBytestream):
receiver = file_props['receiver']
if sender is None:
sender = file_props['sender']
proxyhosts = []
sha_str = helpers.get_auth_sha(file_props['sid'], sender,
receiver)
file_props['sha_str'] = sha_str
@ -381,7 +383,6 @@ class ConnectionHandlersZeroconf(ConnectionVcard, ConnectionBytestream, connecti
try:
idle.init()
except Exception:
global HAS_IDLE
HAS_IDLE = False
def _messageCB(self, ip, con, msg):
@ -481,4 +482,4 @@ class ConnectionHandlersZeroconf(ConnectionVcard, ConnectionBytestream, connecti
def remove_transfer(self, file_props, remove_from_list = True):
pass
# vim: se ts=3:
# vim: se ts=3:

View File

@ -56,7 +56,8 @@ class Roster:
if not contact:
return
host, address, port, txt = contact[4:7] + contact[8]
(service_jid, domain, interface, protocol, host, address, port, bare_jid, txt) \
= contact
self._data[jid]={}
self._data[jid]['ask'] = 'no' #?

View File

@ -31,8 +31,8 @@ def test_bonjour():
try:
import pybonjour
except ImportError:
return False
except WindowsError:
return False
except WindowsError:
return False
return True
@ -46,4 +46,4 @@ elif test_bonjour():
from common.zeroconf import zeroconf_bonjour
Zeroconf = zeroconf_bonjour.Zeroconf
# vim: se ts=3:
# vim: se ts=3:

View File

@ -292,7 +292,7 @@ class Zeroconf:
return True
else:
return False
except dbus.DBusException:
except dbus.DBusException, e:
gajim.log.debug("Can't remove service. That should not happen")
def browse_domain(self, interface, protocol, domain):
@ -429,4 +429,4 @@ class Zeroconf:
# END Zeroconf
# vim: se ts=3:
# vim: se ts=3:

View File

@ -18,6 +18,7 @@
##
from common import gajim
import sys
import select
import re
from string import split
@ -115,8 +116,7 @@ class Zeroconf:
}
# Split on '.' but do not split on '\.'
result = re.split('(?<!\\\\)\.', fullname)
name, protocol, domain = result[0] + result[2:4]
name, stype, protocol, domain, dummy = re.split('(?<!\\\\)\.', fullname)
# Replace the escaped values
for src, trg in escaping.items():
@ -252,7 +252,7 @@ class Zeroconf:
self.announced = False
return True
except pybonjour.BonjourError, e:
gajim.log.debug(e)
geajim.log.debug(e)
return False
@ -330,9 +330,9 @@ class Zeroconf:
try:
pybonjour.DNSServiceUpdateRecord(self.service_sdRef, None, 0, self.txt)
except pybonjour.BonjourError:
except pybonjour.BonjourError, e:
return False
return True
# vim: se ts=3:
# vim: se ts=3:

View File

@ -57,7 +57,7 @@ from common import connection
from common import passwords
from common import zeroconf
from common import dataforms
from common import GnuPG
from common import pep
from common.exceptions import GajimGeneralException
@ -308,6 +308,9 @@ class PreferencesWindow:
self.xml.get_widget('sounds_scrolledwindow').set_sensitive(False)
self.xml.get_widget('browse_sounds_hbox').set_sensitive(False)
# sound player
player = gajim.config.get('soundplayer')
# sounds treeview
self.sound_tree = self.xml.get_widget('sounds_treeview')
@ -610,25 +613,27 @@ class PreferencesWindow:
helpers.update_optional_features()
def apply_speller(self):
for ctrl in gajim.interface.msg_win_mgr.controls():
if isinstance(ctrl, chat_control.ChatControlBase):
try:
spell_obj = gtkspell.get_from_text_view(ctrl.msg_textview)
except Exception:
spell_obj = None
for acct in gajim.connections:
for ctrl in gajim.interface.msg_win_mgr.controls():
if isinstance(ctrl, chat_control.ChatControlBase):
try:
spell_obj = gtkspell.get_from_text_view(ctrl.msg_textview)
except Exception:
spell_obj = None
if not spell_obj:
gtkspell.Spell(ctrl.msg_textview)
if not spell_obj:
gtkspell.Spell(ctrl.msg_textview)
def remove_speller(self):
for ctrl in gajim.interface.msg_win_mgr.controls():
if isinstance(ctrl, chat_control.ChatControlBase):
try:
spell_obj = gtkspell.get_from_text_view(ctrl.msg_textview)
except Exception:
spell_obj = None
if spell_obj:
spell_obj.detach()
for acct in gajim.connections:
for ctrl in gajim.interface.msg_win_mgr.controls():
if isinstance(ctrl, chat_control.ChatControlBase):
try:
spell_obj = gtkspell.get_from_text_view(ctrl.msg_textview)
except Exception:
spell_obj = None
if spell_obj:
spell_obj.detach()
def on_speller_checkbutton_toggled(self, widget):
active = widget.get_active()
@ -640,7 +645,7 @@ class PreferencesWindow:
lang = gajim.LANG
tv = gtk.TextView()
try:
gtkspell.Spell(tv, lang)
spell = gtkspell.Spell(tv, lang)
except:
dialogs.ErrorDialog(
_('Dictionary for lang %s not available') % lang,
@ -1027,6 +1032,7 @@ class PreferencesWindow:
return
buf = self.xml.get_widget('msg_textview').get_buffer()
first_iter, end_iter = buf.get_bounds()
name = model.get_value(iter, 0)
model.set_value(iter, 1, buf.get_text(first_iter, end_iter))
def on_msg_treeview_key_press_event(self, widget, event):
@ -1684,7 +1690,7 @@ class AccountsWindow:
gajim.interface.instances[account]['remove_account'] = \
RemoveAccountWindow(account)
if win_opened:
dialogs.ConfirmationDialog(
dialog = dialogs.ConfirmationDialog(
_('You have opened chat in account %s') % account,
_('All chat and groupchat windows will be closed. Do you want to '
'continue?'),
@ -1889,7 +1895,7 @@ class AccountsWindow:
def on_synchronise_contacts_button1_clicked(self, widget):
try:
dialogs.SynchroniseSelectAccountDialog(self.current_account)
dialog = dialogs.SynchroniseSelectAccountDialog(self.current_account)
except GajimGeneralException:
# If we showed ErrorDialog, there will not be dialog instance
return
@ -1903,7 +1909,7 @@ class AccountsWindow:
self.xml.get_widget('password_entry1').set_text(new_password)
try:
dialogs.ChangePasswordDialog(self.current_account, on_changed)
dialog = dialogs.ChangePasswordDialog(self.current_account, on_changed)
except GajimGeneralException:
# if we showed ErrorDialog, there will not be dialog instance
return
@ -2068,10 +2074,14 @@ class AccountsWindow:
gajim.config.set_per('accounts', self.current_account, 'keyid',
keyID[0])
dialogs.ChooseGPGKeyDialog(_('OpenPGP Key Selection'),
instance = dialogs.ChooseGPGKeyDialog(_('OpenPGP Key Selection'),
_('Choose your OpenPGP key'), secret_keys, on_key_selected)
def on_use_gpg_agent_checkbutton_toggled(self, widget):
if self.current_account == gajim.ZEROCONF_ACC_NAME:
wiget_name_ext = '2'
else:
wiget_name_ext = '1'
self.on_checkbutton_toggled(widget, 'use_gpg_agent')
def on_edit_details_button1_clicked(self, widget):
@ -2461,7 +2471,7 @@ class GroupchatConfigWindow:
return
model = self.affiliation_treeview[affiliation].get_model()
model.append((jid,'', '', ''))
dialogs.InputDialog(title, prompt, ok_handler=on_ok)
instance = dialogs.InputDialog(title, prompt, ok_handler=on_ok)
def on_remove_button_clicked(self, widget, affiliation):
selection = self.affiliation_treeview[affiliation].get_selection()
@ -2567,7 +2577,7 @@ class RemoveAccountWindow:
gajim.connections[self.account].unregister_account(
self._on_remove_success)
dialogs.PassphraseDialog(
w = dialogs.PassphraseDialog(
_('Password Required'),
_('Enter your password for account %s') % self.account,
_('Save password'), ok_handler=on_ok)
@ -2578,7 +2588,7 @@ class RemoveAccountWindow:
self._on_remove_success(True)
if gajim.connections[self.account].connected:
dialogs.ConfirmationDialog(
dialog = dialogs.ConfirmationDialog(
_('Account "%s" is connected to the server') % self.account,
_('If you remove it, the connection will be lost.'),
on_response_ok=remove)

View File

@ -597,7 +597,7 @@ class ConversationTextview:
def on_textview_motion_notify_event(self, widget, event):
'''change the cursor to a hand when we are over a mail or an
url'''
pointer_x, pointer_y = self.tv.window.get_pointer()[0:2]
pointer_x, pointer_y, spam = self.tv.window.get_pointer()
x, y = self.tv.window_to_buffer_coords(gtk.TEXT_WINDOW_TEXT,
pointer_x, pointer_y)
tags = self.tv.get_iter_at_location(x, y).get_tags()

View File

@ -567,6 +567,7 @@ class SingleForm(gtk.Table, object):
def on_jid_multi_remove_button_clicked(self, widget, treeview, field):
selection = treeview.get_selection()
model = treeview.get_model()
deleted = []
def remove(model, path, iter_, deleted):

View File

@ -427,6 +427,7 @@ class ChangeActivityDialog:
'''
Return activity and messsage (None if no activity selected)
'''
message = None
if self.checkbutton.get_active():
pep.user_send_activity(self.account, self.activity,
self.subactivity,
@ -650,7 +651,7 @@ class ChangeStatusMessageDialog:
self.preset_messages_dict[msg_name] = msg_text
gajim.config.set_per('statusmsg', msg_name, 'message',
msg_text_1l)
ConfirmationDialog(_('Overwrite Status Message?'),
dlg2 = ConfirmationDialog(_('Overwrite Status Message?'),
_('This name is already used. Do you want to overwrite this '
'status message?'), on_response_ok=on_ok2)
return
@ -1576,7 +1577,7 @@ class DubbleInputDialog:
def on_cancelbutton_clicked(self, widget):
self.dialog.destroy()
if not self.cancel_handler:
if not cancel_handler:
return
if isinstance(self.cancel_handler, tuple):
self.cancel_handler[0](*self.cancel_handler[1:])
@ -1852,7 +1853,7 @@ class SynchroniseSelectAccountDialog:
return
else:
try:
SynchroniseSelectContactsDialog(self.account, remote_account)
dialog = SynchroniseSelectContactsDialog(self.account, remote_account)
except GajimGeneralException:
# if we showed ErrorDialog, there will not be dialog instance
return
@ -2194,7 +2195,7 @@ class SingleMessageWindow:
if lang:
spell1.set_language(lang)
spell2.set_language(lang)
except gobject.GError:
except gobject.GError, msg:
AspellDictError(lang)
self.prepare_widgets_for(self.action)
@ -2968,7 +2969,7 @@ class InvitationReceivedDialog:
except GajimGeneralException:
pass
YesNoDialog(pritext, sectext, on_response_yes=on_yes)
dialog = YesNoDialog(pritext, sectext, on_response_yes=on_yes)
class ProgressDialog:
def __init__(self, title_text, during_text, messages_queue):
@ -3155,6 +3156,7 @@ class AddSpecialNotificationDialog:
self.window.destroy()
def on_listen_sound_combobox_changed(self, widget):
model = widget.get_model()
active = widget.get_active()
if active == 1: # user selected 'choose sound'
def on_ok(widget, path_to_snd_file):
@ -3657,6 +3659,9 @@ class TransformChatToMUC:
'server_and_guests_hseparator', 'server_select_label'):
self.__dict__[widget_to_add] = self.xml.get_widget(widget_to_add)
# set comboboxentry
renderer_servers = gtk.CellRendererText()
server_list = []
self.servers = gtk.ListStore(str)
self.server_list_comboboxentry.set_model(self.servers)
@ -3899,7 +3904,7 @@ class GPGInfoWindow:
'encrypt messages.')
image = 'security-low-big.png'
else:
error = gajim.connections[account].gpg.encrypt('test', [keyID])[1]
msgenc, error = gajim.connections[account].gpg.encrypt('test', [keyID])
if error:
verification_status = _('''Contact's identity NOT verified''')
info = _('GPG key is assigned to this contact, but <b>you do not '

View File

@ -969,6 +969,7 @@ _('This service does not contain any items to browse.'))
def _agent_info(self, jid, node, identities, features, data):
'''Callback for when we receive info about an agent's item.'''
addr = get_agent_address(jid, node)
iter = self._find_item(jid, node)
if not iter:
# Not in the treeview, stop
@ -1098,7 +1099,7 @@ class ToplevelAgentBrowser(AgentBrowser):
if not props or self.tooltip.id != props[0]:
self.tooltip.hide_tooltip()
if props:
row = props[0]
[row, col, x, y] = props
iter = None
try:
iter = self.model.get_iter(row)
@ -1429,7 +1430,7 @@ class ToplevelAgentBrowser(AgentBrowser):
def _find_category(self, cat, type_=None):
'''Looks up a category row and returns the iterator to it, or None.'''
cat = self._friendly_category(cat, type_)[0]
cat, prio = self._friendly_category(cat, type_)
iter = self.model.get_iter_root()
while iter:
if self.model.get_value(iter, 3).decode('utf-8') == cat:
@ -1539,6 +1540,7 @@ class ToplevelAgentBrowser(AgentBrowser):
self._expand_all()
def _update_error(self, iter_, jid, node):
addr = get_agent_address(jid, node)
self.model[iter_][4] = 2
self._progress += 1
self._update_progressbar()
@ -1633,6 +1635,7 @@ class MucBrowser(AgentBrowser):
room = model[iter][1].decode('utf-8')
if 'join_gc' not in gajim.interface.instances[self.account]:
try:
room_jid = '%s@%s' % (service, room)
dialogs.JoinGroupchatWindow(self.account, service)
except GajimGeneralException:
pass

View File

@ -28,6 +28,8 @@ import sys
import gtk
import gtkgui_helpers
import dialogs
from common import gajim
from common import helpers
@ -149,6 +151,7 @@ class FeaturesWindow:
if not rows:
return
path = rows[0]
available = self.model[path][1]
feature = self.model[path][0].decode('utf-8')
text = self.features[feature][1] + '\n'
if os.name == 'nt':
@ -184,6 +187,7 @@ class FeaturesWindow:
def gpg_available(self):
if os.name == 'nt':
return False
from common import gajim
return gajim.HAVE_GPG
def network_manager_available(self):
@ -296,6 +300,7 @@ class FeaturesWindow:
return False
def pycrypto_available(self):
from common import gajim
return gajim.HAVE_PYCRYPTO
def docutils_available(self):
@ -306,6 +311,7 @@ class FeaturesWindow:
return True
def pysexy_available(self):
from common import gajim
return gajim.HAVE_PYSEXY
# vim: se ts=3:

View File

@ -150,7 +150,7 @@ class FileTransfersWindow:
dialog.destroy()
if 'file-name' not in file_props:
return
path = os.path.split(file_props['file-name'])[0]
(path, file) = os.path.split(file_props['file-name'])
if os.path.exists(path) and os.path.isdir(path):
helpers.launch_file_manager(path)
self.tree.get_selection().unselect_all()
@ -276,7 +276,7 @@ _('Connection with peer cannot be established.'))
return
(jid, resource) = contact.split('/', 1)
contact = gajim.contacts.create_contact(jid=jid, resource=resource)
file_name = os.path.split(file_path)[1]
(file_dir, file_name) = os.path.split(file_path)
file_props = self.get_send_file_props(account, contact,
file_path, file_name, file_desc)
if file_props is None:
@ -307,7 +307,7 @@ _('Connection with peer cannot be established.'))
if 'desc' in file_props:
sec_text += '\n\t' + _('Description: %s') % file_props['desc']
prim_text = _('%s wants to send you a file:') % contact.jid
dialog = None
dialog, dialog2 = None, None
def on_response_ok(account, contact, file_props):
@ -600,7 +600,7 @@ _('Connection with peer cannot be established.'))
text_labels += '<b>' + _('Recipient: ') + '</b>'
if file_props['type'] == 'r':
file_name = os.path.split(file_props['file-name'])[1]
(file_path, file_name) = os.path.split(file_props['file-name'])
else:
file_name = file_props['name']
text_props = gobject.markup_escape_text(file_name) + '\n'
@ -621,13 +621,14 @@ _('Connection with peer cannot be established.'))
def on_transfers_list_motion_notify_event(self, widget, event):
pointer = self.tree.get_pointer()
orig = widget.window.get_origin()
props = widget.get_path_at_pos(int(event.x), int(event.y))
self.height_diff = pointer[1] - int(event.y)
if self.tooltip.timeout > 0:
if not props or self.tooltip.id != props[0]:
self.tooltip.hide_tooltip()
if props:
row = props[0]
[row, col, x, y] = props
iter = None
try:
iter = self.model.get_iter(row)
@ -889,7 +890,7 @@ _('Connection with peer cannot be established.'))
self.tooltip.hide_tooltip()
iter = None
try:
iter = self.tree.get_selection().get_selected()[1]
store, iter = self.tree.get_selection().get_selected()
except TypeError:
self.tree.get_selection().unselect_all()
@ -907,7 +908,8 @@ _('Connection with peer cannot be established.'))
self.tooltip.hide_tooltip()
path = None
try:
path = self.tree.get_path_at_pos(int(event.x), int(event.y))[0]
path, column, x, y = self.tree.get_path_at_pos(int(event.x),
int(event.y))
except TypeError:
self.tree.get_selection().unselect_all()
if path is None:
@ -920,7 +922,8 @@ _('Connection with peer cannot be established.'))
self.tooltip.hide_tooltip()
path, iter = None, None
try:
path = self.tree.get_path_at_pos(int(event.x), int(event.y))[0]
path, column, x, y = self.tree.get_path_at_pos(int(event.x),
int(event.y))
except TypeError:
self.tree.get_selection().unselect_all()
if event.button == 3: # Right click
@ -940,7 +943,7 @@ _('Connection with peer cannot be established.'))
file_props = self.files_props[sid[0]][sid[1:]]
if 'file-name' not in file_props:
return
path = os.path.split(file_props['file-name'])[0]
(path, file) = os.path.split(file_props['file-name'])
if os.path.exists(path) and os.path.isdir(path):
helpers.launch_file_manager(path)

View File

@ -28,6 +28,7 @@
# gajim-remote help will show you the D-BUS API of Gajim
import sys
import os
import locale
import signal
signal.signal(signal.SIGINT, signal.SIG_DFL) # ^C exits the application

View File

@ -111,7 +111,7 @@ def parseOpts():
try:
shortargs = 'hqvl:p:c:'
longargs = 'help quiet verbose loglevel= profile= config_path='
opts = getopt.getopt(sys.argv[1:], shortargs, longargs.split())[0]
opts, args = getopt.getopt(sys.argv[1:], shortargs, longargs.split())
except getopt.error, msg:
print msg
print 'for help use --help'
@ -251,6 +251,7 @@ from session import ChatControlSession
import common.sleepy
from common.xmpp import idlequeue
from common.zeroconf import connection_zeroconf
from common import nslookup
from common import proxy65_manager
from common import socks5

View File

@ -121,7 +121,7 @@ class GajimThemesWindow:
model.clear()
for config_theme in gajim.config.get_per('themes'):
theme = config_theme.replace('_', ' ')
model.append([theme])
iter = model.append([theme])
def select_active_theme(self):
model = self.themes_tree.get_model()

View File

@ -45,6 +45,7 @@ from common import helpers
from chat_control import ChatControl
from chat_control import ChatControlBase
from conversation_textview import ConversationTextview
from common.exceptions import GajimGeneralException
#(status_image, type, nick, shown_nick)
@ -174,7 +175,7 @@ class GroupchatControl(ChatControlBase):
def __init__(self, parent_win, contact, acct, is_continued=False):
ChatControlBase.__init__(self, self.TYPE_ID, parent_win,
'muc_child_vbox', contact, acct)
'muc_child_vbox', contact, acct);
self.is_continued=is_continued
self.is_anonymous = True
@ -990,6 +991,7 @@ class GroupchatControl(ChatControlBase):
contact in a room'''
if nick is None:
nick = model[iter_][C_NICK].decode('utf-8')
fjid = gajim.construct_fjid(self.room_jid, nick) # 'fake' jid
ctrl = self._start_private_message(nick)
if ctrl and msg:
@ -1790,7 +1792,7 @@ class GroupchatControl(ChatControlBase):
on_minimize(self)
return
if method == self.parent_win.CLOSE_ESC:
iter = self.list_treeview.get_selection().get_selected()[1]
model, iter = self.list_treeview.get_selection().get_selected()
if iter:
self.list_treeview.get_selection().unselect_all()
on_no(self)
@ -1819,7 +1821,7 @@ class GroupchatControl(ChatControlBase):
sectext = _('If you close this window, you will be disconnected '
'from this group chat.')
dialogs.ConfirmationDialogCheck(pritext, sectext,
dialog = dialogs.ConfirmationDialogCheck(pritext, sectext,
_('Do _not ask me again'), on_response_ok=on_ok,
on_response_cancel=on_cancel)
return
@ -1853,7 +1855,7 @@ class GroupchatControl(ChatControlBase):
# will work yet
gajim.connections[self.account].send_gc_subject(self.room_jid, subject)
dialogs.InputTextDialog(_('Changing Subject'),
instance = dialogs.InputTextDialog(_('Changing Subject'),
_('Please specify the new subject:'), input_str=self.subject,
ok_handler=on_ok)
@ -1885,7 +1887,7 @@ class GroupchatControl(ChatControlBase):
jid)
# Ask for a reason
dialogs.DubbleInputDialog(_('Destroying %s') % self.room_jid,
instance = dialogs.DubbleInputDialog(_('Destroying %s') % self.room_jid,
_('You are going to definitively destroy this room.\n'
'You may specify a reason below:'),
_('You may also enter an alternate venue:'), ok_handler=on_ok)
@ -1908,6 +1910,7 @@ class GroupchatControl(ChatControlBase):
path = treeview.get_selection().get_selected_rows()[1][0]
iter = model.get_iter(path)
type = model[iter][2]
account = model[iter][4].decode('utf-8')
if type != 'contact': # source is not a contact
return
contact_jid = data.decode('utf-8')
@ -2035,7 +2038,7 @@ class GroupchatControl(ChatControlBase):
def on_list_treeview_key_press_event(self, widget, event):
if event.keyval == gtk.keysyms.Escape:
selection = widget.get_selection()
iter = selection.get_selected()[1]
model, iter = selection.get_selected()
if iter:
widget.get_selection().unselect_all()
return True
@ -2059,7 +2062,7 @@ class GroupchatControl(ChatControlBase):
'none', reason)
# ask for reason
dialogs.InputDialog(_('Kicking %s') % nick,
instance = dialogs.InputDialog(_('Kicking %s') % nick,
_('You may specify a reason below:'), ok_handler=on_ok)
def mk_menu(self, event, iter_):
@ -2213,13 +2216,13 @@ class GroupchatControl(ChatControlBase):
def on_list_treeview_button_press_event(self, widget, event):
'''popup user's group's or agent menu'''
try:
pos = widget.get_path_at_pos(int(event.x), int(event.y))
path, x = pos[0] + pos[2]
except TypeError:
widget.get_selection().unselect_all()
return
if event.button == 3: # right click
try:
path, column, x, y = widget.get_path_at_pos(int(event.x),
int(event.y))
except TypeError:
widget.get_selection().unselect_all()
return
widget.get_selection().select_path(path)
model = widget.get_model()
iter = model.get_iter(path)
@ -2228,6 +2231,12 @@ class GroupchatControl(ChatControlBase):
return True
elif event.button == 2: # middle click
try:
path, column, x, y = widget.get_path_at_pos(int(event.x),
int(event.y))
except TypeError:
widget.get_selection().unselect_all()
return
widget.get_selection().select_path(path)
model = widget.get_model()
iter = model.get_iter(path)
@ -2237,6 +2246,13 @@ class GroupchatControl(ChatControlBase):
return True
elif event.button == 1: # left click
try:
path, column, x, y = widget.get_path_at_pos(int(event.x),
int(event.y))
except TypeError:
widget.get_selection().unselect_all()
return
if gajim.single_click and not event.state & gtk.gdk.SHIFT_MASK:
self.on_row_activated(widget, path)
return True
@ -2350,7 +2366,7 @@ class GroupchatControl(ChatControlBase):
# to ban we know the real jid. so jid is not fakejid
nick = gajim.get_nick_from_jid(jid)
# ask for reason
dialogs.InputDialog(_('Banning %s') % nick,
instance = dialogs.InputDialog(_('Banning %s') % nick,
_('You may specify a reason below:'), ok_handler=on_ok)
def grant_membership(self, widget, jid):

View File

@ -21,6 +21,8 @@
'''Window to create new post for discussion groups service.'''
import gtk
from common import gajim, xmpp
import gtkgui_helpers

View File

@ -82,6 +82,7 @@ def _info(type_, value, tb):
# on expand the details the dialog remains centered on screen
dialog.set_position(gtk.WIN_POS_CENTER_ALWAYS)
close_clicked = False
def on_dialog_response(dialog, response):
if response == RESPONSE_REPORT_BUG:
url = 'http://trac.gajim.org/wiki/HowToCreateATicket'
@ -103,6 +104,6 @@ if os.name == 'nt' or not sys.stderr.isatty():
if __name__ == '__main__':
_excepthook_save = sys.excepthook
sys.excepthook = _info
raise Exception()
print x # this always tracebacks
# vim: se ts=3:

View File

@ -97,7 +97,7 @@ def popup_emoticons_under_button(menu, button, parent_win):
x = window_x + button_x
y = window_y + button_y
menu_height = menu.size_request()[1]
menu_width, menu_height = menu.size_request()
## should we pop down or up?
if (y + button.allocation.height + menu_height
@ -494,7 +494,7 @@ def file_is_locked(path_to_file):
win32con.FILE_ATTRIBUTE_NORMAL, # normal file
0 # no attr. template
)
except pywintypes.error:
except pywintypes.error, e:
return True
else: # in case all went ok, close file handle (go to hell WinAPI)
hfile.Close()
@ -808,6 +808,10 @@ default_name = ''):
dialog.destroy()
def on_ok(widget):
def on_ok2(file_path, pixbuf):
pixbuf.save(file_path, 'jpeg')
dialog.destroy()
file_path = dialog.get_filename()
file_path = decode_filechooser_file_paths((file_path,))[0]
if os.path.exists(file_path):

View File

@ -220,7 +220,7 @@ class HistoryManager:
def on_no():
gtk.main_quit()
dialogs.YesNoDialog(
dialog = dialogs.YesNoDialog(
_('Do you want to clean up the database? '
'(STRONGLY NOT RECOMMENDED IF GAJIM IS RUNNING)'),
_('Normally allocated database size will not be freed, '
@ -296,7 +296,7 @@ class HistoryManager:
(user will see the first pm as if it was message in room's public chat)
and after that all okay'''
possible_room_jid = jid.split('/', 1)[0]
possible_room_jid, possible_nick = jid.split('/', 1)
self.cur.execute('SELECT jid_id FROM jids WHERE jid = ? AND type = ?',
(possible_room_jid, constants.JID_ROOM_TYPE))
@ -421,6 +421,9 @@ class HistoryManager:
xml.get_widget('delete_menuitem').connect('activate',
self.on_delete_menuitem_activate, widget)
liststore, list_of_paths = self.jids_listview.get_selection()\
.get_selected_rows()
xml.signal_autoconnect(self)
xml.get_widget('context_menu').popup(None, None, None,
event.button, event.time)

View File

@ -321,7 +321,7 @@ class HistoryWindow:
# first day of month is 1 not 0
widget.clear_marks()
month = gtkgui_helpers.make_gtk_month_python_month(month)
days_in_this_month = calendar.monthrange(year, month)[1]
weekday, days_in_this_month = calendar.monthrange(year, month)
log_days = gajim.logger.get_days_with_logs(self.jid, year,
month, days_in_this_month, self.account)
for day in log_days:
@ -509,7 +509,7 @@ class HistoryWindow:
'''a row was double clicked, get date from row, and select it in calendar
which results to showing conversation logs for that date'''
# get currently selected date
cur_year, cur_month = self.calendar.get_date()[0:2]
cur_year, cur_month, cur_day = self.calendar.get_date()
cur_month = gtkgui_helpers.make_gtk_month_python_month(cur_month)
model = widget.get_model()
# make it a tupple (Y, M, D, 0, 0, 0...)

View File

@ -91,76 +91,77 @@ element_styles['tt'] = element_styles['kbd']
element_styles['i'] = element_styles['em']
element_styles['b'] = element_styles['strong']
# ==========
# JEP-0071
# ==========
'''
==========
JEP-0071
==========
This Integration Set includes a subset of the modules defined for
XHTML 1.0 but does not redefine any existing modules, nor
does it define any new modules. Specifically, it includes the
following modules only:
- Structure
- Text
* Block
phrasal
addr, blockquote, pre
Struc
div,p
Heading
h1, h2, h3, h4, h5, h6
* Inline
phrasal
abbr, acronym, cite, code, dfn, em, kbd, q, samp, strong, var
structural
br, span
- Hypertext (a)
- List (ul, ol, dl)
- Image (img)
- Style Attribute
Therefore XHTML-IM uses the following content models:
Block.mix
Block-like elements, e.g., paragraphs
Flow.mix
Any block or inline elements
Inline.mix
Character-level elements
InlineNoAnchor.class
Anchor element
InlinePre.mix
Pre element
XHTML-IM also uses the following Attribute Groups:
Core.extra.attrib
TBD
I18n.extra.attrib
TBD
Common.extra
style
...
#block level:
#Heading h
# ( pres = h1 | h2 | h3 | h4 | h5 | h6 )
#Block ( phrasal = address | blockquote | pre )
#NOT ( presentational = hr )
# ( structural = div | p )
#other: section
#Inline ( phrasal = abbr | acronym | cite | code | dfn | em | kbd | q | samp | strong | var )
#NOT ( presentational = b | big | i | small | sub | sup | tt )
# ( structural = br | span )
#Param/Legacy param, font, basefont, center, s, strike, u, dir, menu, isindex
#
# This Integration Set includes a subset of the modules defined for
# XHTML 1.0 but does not redefine any existing modules, nor
# does it define any new modules. Specifically, it includes the
# following modules only:
#
# - Structure
# - Text
#
# * Block
#
# phrasal
# addr, blockquote, pre
# Struc
# div,p
# Heading
# h1, h2, h3, h4, h5, h6
#
# * Inline
#
# phrasal
# abbr, acronym, cite, code, dfn, em, kbd, q, samp, strong, var
# structural
# br, span
#
# - Hypertext (a)
# - List (ul, ol, dl)
# - Image (img)
# - Style Attribute
#
# Therefore XHTML-IM uses the following content models:
#
# Block.mix
# Block-like elements, e.g., paragraphs
# Flow.mix
# Any block or inline elements
# Inline.mix
# Character-level elements
# InlineNoAnchor.class
# Anchor element
# InlinePre.mix
# Pre element
#
# XHTML-IM also uses the following Attribute Groups:
#
# Core.extra.attrib
# TBD
# I18n.extra.attrib
# TBD
# Common.extra
# style
#
#
# ...
# block level:
# Heading h
# ( pres = h1 | h2 | h3 | h4 | h5 | h6 )
# Block ( phrasal = address | blockquote | pre )
# NOT ( presentational = hr )
# ( structural = div | p )
# other: section
# Inline ( phrasal = abbr | acronym | cite | code | dfn | em |
# kbd | q | samp | strong | var )
# NOT ( presentational = b | big | i | small | sub | sup | tt )
# ( structural = br | span )
# Param/Legacy param, font, basefont, center, s, strike, u, dir, menu,
# isindex
'''
BLOCK_HEAD = set(( 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', ))
BLOCK_PHRASAL = set(( 'address', 'blockquote', 'pre', ))
@ -1034,7 +1035,7 @@ if __name__ == '__main__':
def on_textview_motion_notify_event(widget, event):
'''change the cursor to a hand when we are over a mail or an url'''
global change_cursor
pointer_x, pointer_y = htmlview.window.get_pointer()[0:2]
pointer_x, pointer_y, spam = htmlview.window.get_pointer()
x, y = htmlview.window_to_buffer_coords(gtk.TEXT_WINDOW_TEXT, pointer_x,
pointer_y)
tags = htmlview.get_iter_at_location(x, y).get_tags()
@ -1043,6 +1044,7 @@ if __name__ == '__main__':
gtk.gdk.Cursor(gtk.gdk.XTERM))
change_cursor = None
tag_table = htmlview.get_buffer().get_tag_table()
over_line = False
for tag in tags:
try:
if tag.is_anchor:

View File

@ -48,6 +48,7 @@ import sys
import os
import pango
from StringIO import StringIO
import thread
try:
import IPython
@ -213,7 +214,7 @@ class IterableIPShell:
possibilities = self.IP.complete(split_line[-1])
try:
all(())
__builtins__.all
except AttributeError:
def all(iterable):
for element in iterable:
@ -245,6 +246,7 @@ class IterableIPShell:
@param header: Header to be printed before output
@type header: string
'''
stat = 0
if verbose or debug: print header+cmd
# flush stdout so we don't mangle python's buffering
if not debug:

View File

@ -142,6 +142,7 @@ class MessageControl:
self.session = session
new_key = None
if session:
session.control = self
new_key = session.thread_id

View File

@ -213,6 +213,7 @@ class MessageWindow(object):
self.on_delete_ok -= 1
# Make sure all controls are okay with being deleted
ctrl_to_minimize = []
self.on_delete_ok = self.get_nb_controls()
for ctrl in self.controls():
ctrl.allow_shutdown(self.CLOSE_CLOSE_BUTTON, on_yes, on_no,
@ -670,7 +671,11 @@ class MessageWindow(object):
yield ctrl
def get_nb_controls(self):
return sum(len(jid_dict) for jid_dict in self._controls.values())
nb_ctrl = 0
for jid_dict in self._controls.values():
for ctrl in jid_dict.values():
nb_ctrl += 1
return nb_ctrl
def move_to_next_unread_tab(self, forward):
ind = self.notebook.get_current_page()
@ -771,7 +776,7 @@ class MessageWindow(object):
selection, type_, time):
'''Reorder the tabs according to the drop position'''
source_page_num = int(selection.data)
dest_page_num = self.get_tab_at_xy(x, y)[0]
dest_page_num, to_right = self.get_tab_at_xy(x, y)
source_child = self.notebook.get_nth_page(source_page_num)
if dest_page_num != source_page_num:
self.notebook.reorder_child(source_child, dest_page_num)

View File

@ -23,6 +23,7 @@
## along with Gajim. If not, see <http://www.gnu.org/licenses/>.
##
import os
import gobject
if __name__ == '__main__':
# install _() func before importing dbus_support

View File

@ -22,6 +22,8 @@
import gtkgui_helpers
import dataforms_widget
import dialogs
from common import dataforms
from common import gajim
from common import xmpp

View File

@ -443,9 +443,7 @@ class DesktopNotification:
self.event_type = event_type
self.title = title
self.text = text
# 0.3.1 is the only version of notification daemon that has no way
# to determine which version it is. If no method exists, it means
# they're using that one.
'''0.3.1 is the only version of notification daemon that has no way to determine which version it is. If no method exists, it means they're using that one.'''
self.default_version = [0, 3, 1]
self.account = account
self.jid = jid
@ -521,8 +519,8 @@ class DesktopNotification:
if gajim.interface.systray_enabled and \
gajim.config.get('attach_notifications_to_systray'):
x, y = gajim.interface.systray.img_tray.window.get_position()
width, height = \
gajim.interface.systray.img_tray.window.get_geometry()[2:4]
x_, y_, width, height, depth = \
gajim.interface.systray.img_tray.window.get_geometry()
pos_x = x + (width / 2)
pos_y = y + (height / 2)
hints = {'x': pos_x, 'y': pos_y}

View File

@ -14,6 +14,7 @@ try:
import _growl
except Exception:
_growl = False
import types
import struct
import md5
import socket
@ -242,4 +243,4 @@ class GrowlNotifier(object):
def notifyCB(self, userdata):
print "Got notify in pyland", userdata
# vim: se ts=3:
# vim: se ts=3:

View File

@ -1,6 +1,6 @@
import sys, os
from growl.Growl import GrowlNotifier
from common import gajim
from common import gajim, helpers
if sys.platform != "darwin":
@ -22,7 +22,7 @@ growler = None
def init():
global growler
global growler, notifications
icon = open(os.path.join(gajim.DATA_DIR, "pixmaps", "gajim.icns"), "r")
growler = GrowlNotifier(applicationName = "Gajim",
notifications = notifications,
@ -33,6 +33,7 @@ def init():
def notify(event_type, jid, account, msg_type, path_to_image, title, text):
global notifications
if not event_type in notifications:
event_type = GENERIC_NOTIF
if not text:
@ -61,4 +62,4 @@ def filterString(string):
return string
# vim: se ts=3:
# vim: se ts=3:

View File

@ -1,4 +1,3 @@
import sys
from distutils.core import setup, Extension
import commands
@ -27,4 +26,4 @@ setup(name='syncmenu', version='0.2',
extra_compile_args=['-Wall'] + cflags)
])
# vim: se ts=3:
# vim: se ts=3:

View File

@ -6,6 +6,7 @@ copy_item = None
def menu_item_activate_cb(item, user_data):
global open_item, copy_item
print "Item activated: %s" % user_data
#g_object_get (G_OBJECT (copy_item),
@ -76,4 +77,4 @@ syncmenu.takeover_menu(menubar)
gtk.main()
# vim: se ts=3:
# vim: se ts=3:

View File

@ -33,6 +33,8 @@ import dialogs
import vcard
from common import gajim
from common.i18n import Q_
class ProfileWindow:
'''Class for our information window'''

View File

@ -327,7 +327,8 @@ class SignalObject(dbus.service.Object):
'''Shows the tabbed window for new message to 'jid', using account
(optional) 'account' '''
if not jid:
raise dbus_support.MissingArgument()
raise MissingArgument
return DBUS_BOOLEAN(False)
jid = self._get_real_jid(jid, account)
try:
jid = helpers.parse_jid(jid)
@ -407,7 +408,8 @@ class SignalObject(dbus.service.Object):
if not isinstance(jid, unicode):
jid = unicode(jid)
if not jid:
raise dbus_support.MissingArgument()
raise MissingArgument
return DBUS_DICT_SV()
jid = self._get_real_jid(jid)
cached_vcard = gajim.connections.values()[0].get_cached_vcard(jid)

View File

@ -50,6 +50,7 @@ import cell_renderer_image
import tooltips
import message_control
import adhoc_commands
import notify
import features_window
from common import gajim
@ -61,10 +62,13 @@ from common import pep
from message_window import MessageWindowMgr
from session import ChatControlSession
from common import dbus_support
if dbus_support.supported:
from music_track_listener import MusicTrackListener
import dbus
from lastfm_track_listener import LastFMTrackListener
from common.xmpp.protocol import NS_COMMANDS, NS_FILE, NS_MUC
from common.pep import MOODS, ACTIVITIES
@ -517,6 +521,7 @@ class RosterWindow:
# Family might has changed (actual big brother not on top).
# Remove childs first then big brother
family_in_roster = False
big_brother_jid = None
for data in nearby_family:
_account = data['account']
_jid = data['jid']
@ -834,6 +839,7 @@ class RosterWindow:
def remove_transport(self, jid, account):
'''Remove transport from roster and redraw account and group.'''
contact = gajim.contacts.get_contact_with_highest_priority(account, jid)
self.remove_contact(jid, account, force=True, backend=True)
return True
@ -1148,8 +1154,8 @@ class RosterWindow:
is_big_brother = False
have_visible_children = False
if family:
bb_jid, bb_account = \
self._get_nearby_family_and_big_brother(family, account)[1:]
nearby_family, bb_jid, bb_account = \
self._get_nearby_family_and_big_brother(family, account)
is_big_brother = (jid, account) == (bb_jid, bb_account)
iters = self._get_contact_iter(jid, account)
have_visible_children = iters \
@ -1710,7 +1716,7 @@ class RosterWindow:
obj = bus.get_object('com.google.code.Awn', '/com/google/code/Awn')
awn = dbus.Interface(obj, 'com.google.code.Awn')
awn.SetTaskIconByName('Gajim', os.path.abspath(path))
except Exception:
except Exception, e:
pass
def music_track_changed(self, unused_listener, music_track_info,
@ -1722,10 +1728,14 @@ class RosterWindow:
artist = ''
title = ''
source = ''
track = ''
length = ''
elif hasattr(music_track_info, 'paused') and music_track_info.paused == 0:
artist = ''
title = ''
source = ''
track = ''
length = ''
else:
artist = music_track_info.artist
title = music_track_info.title
@ -1893,6 +1903,7 @@ class RosterWindow:
self.set_connecting_state(account)
if not gajim.connections[account].password:
passphrase = ''
text = _('Enter your password for account %s') % account
if passwords.USER_HAS_GNOMEKEYRING and \
not passwords.USER_USES_GNOMEKEYRING:
@ -1906,7 +1917,7 @@ class RosterWindow:
passwords.save_password(account, passphrase)
keyid = gajim.config.get_per('accounts', account, 'keyid')
if keyid and not gajim.connections[account].gpg:
dialogs.WarningDialog(_('GPG is not usable'),
dialog = dialogs.WarningDialog(_('GPG is not usable'),
_('You will be connected to %s without OpenPGP.') % \
account)
self.send_status_continue(account, status, txt, auto, to)
@ -1919,14 +1930,14 @@ class RosterWindow:
gajim.interface.systray.change_status('offline')
self.update_status_combobox()
dialogs.PassphraseDialog(_('Password Required'), text,
w = dialogs.PassphraseDialog(_('Password Required'), text,
_('Save password'), ok_handler=on_ok,
cancel_handler=on_cancel)
return
keyid = gajim.config.get_per('accounts', account, 'keyid')
if keyid and not gajim.connections[account].gpg:
dialogs.WarningDialog(_('GPG is not usable'),
dialog = dialogs.WarningDialog(_('GPG is not usable'),
_('You will be connected to %s without OpenPGP.') % account)
self.send_status_continue(account, status, txt, auto, to)
@ -2256,7 +2267,7 @@ class RosterWindow:
break
if unread or recent:
dialogs.ConfirmationDialog(_('You have unread messages'),
dialog = dialogs.ConfirmationDialog(_('You have unread messages'),
_('Messages will only be available for reading them later if you'
' have history enabled and contact is in your roster.'),
on_response_ok=(on_continue2, message))
@ -2364,7 +2375,7 @@ class RosterWindow:
if not props or self.tooltip.id != props[0]:
self.tooltip.hide_tooltip()
if props:
row = props[0]
[row, col, x, y] = props
titer = None
try:
titer = model.get_iter(row)
@ -2518,6 +2529,7 @@ class RosterWindow:
if msg is None:
# user pressed Cancel to change status message dialog
return
model = self.modelfilter
accounts = []
if group is None:
for (contact, account) in list_:
@ -2560,6 +2572,7 @@ class RosterWindow:
def on_unblock(self, widget, list_, group=None):
''' When clicked on the 'unblock' button in context menu. '''
model = self.modelfilter
accounts = []
if group is None:
for (contact, account) in list_:
@ -2631,6 +2644,7 @@ class RosterWindow:
if 'rename' in gajim.interface.instances:
gajim.interface.instances['rename'].dialog.present()
return
model = self.modelfilter
# account is offline, don't allow to rename
if gajim.connections[account].connected < 2:
@ -2743,7 +2757,7 @@ class RosterWindow:
u.keyID = helpers.prepare_and_validate_gpg_keyID(account,
contact.jid, keyID)
dialogs.ChooseGPGKeyDialog(_('Assign OpenPGP Key'),
instance = dialogs.ChooseGPGKeyDialog(_('Assign OpenPGP Key'),
_('Select a key to apply to the contact'), public_keys,
on_key_selected, selected=keyID)
@ -2860,7 +2874,7 @@ class RosterWindow:
resource = None):
''' resource parameter MUST NOT be used if more than one contact in
list '''
for contact in (e[0] for e in list_):
for (contact, acct) in list_:
contact_jid = contact.jid
if resource: # we MUST have one contact only in list_
contact_jid += '/' + resource
@ -2905,10 +2919,10 @@ class RosterWindow:
helpers.launch_browser_mailer('url', url)
def on_change_activity_activate(self, widget, account):
dialogs.ChangeActivityDialog(account)
dlg = dialogs.ChangeActivityDialog(account)
def on_change_mood_activate(self, widget, account):
dialogs.ChangeMoodDialog(account)
dlg = dialogs.ChangeMoodDialog(account)
def on_change_status_message_activate(self, widget, account):
show = gajim.SHOW_LIST[gajim.connections[account].connected]
@ -2967,7 +2981,8 @@ class RosterWindow:
def on_roster_treeview_button_release_event(self, widget, event):
try:
path = self.tree.get_path_at_pos(int(event.x), int(event.y))[0]
path, column, x, y = self.tree.get_path_at_pos(int(event.x),
int(event.y))
except TypeError:
return False
@ -2983,8 +2998,8 @@ class RosterWindow:
# hide tooltip, no matter the button is pressed
self.tooltip.hide_tooltip()
try:
pos = self.tree.get_path_at_pos(int(event.x), int(event.y))
path, x = pos[0] + pos[2]
path, column, x, y = self.tree.get_path_at_pos(int(event.x),
int(event.y))
except TypeError:
self.tree.get_selection().unselect_all()
return False
@ -3095,6 +3110,7 @@ class RosterWindow:
if len(list_) == 1:
contact = list_[0][0]
account = list_[0][1]
pritext = _('Contact "%s" will be removed from your roster') % \
contact.get_shown_name()
if contact.sub == 'to':
@ -3233,7 +3249,7 @@ class RosterWindow:
def on_cancel():
self.update_status_combobox()
dialogs.ConfirmationDialog(
dialog = dialogs.ConfirmationDialog(
_('You are participating in one or more group chats'),
_('Changing your status to invisible will result in '
'disconnection from those group chats. Are you sure you want to '
@ -3387,7 +3403,7 @@ class RosterWindow:
gajim.interface.msg_win_mgr.one_window_opened():
# let message window close the tab
return
list_of_paths = self.tree.get_selection().get_selected_rows()[1]
model, list_of_paths = self.tree.get_selection().get_selected_rows()
if not len(list_of_paths) and gajim.interface.systray_enabled and \
not gajim.config.get('quit_on_roster_x_button'):
self.tooltip.hide_tooltip()
@ -3506,8 +3522,8 @@ class RosterWindow:
jid = model[titer][C_JID].decode('utf-8')
account = model[titer][C_ACCOUNT].decode('utf-8')
family = gajim.contacts.get_metacontacts_family(account, jid)
nearby_family = \
self._get_nearby_family_and_big_brother(family, account)[0]
nearby_family, bb_jid, bb_account = \
self._get_nearby_family_and_big_brother(family, account)
# Redraw all brothers to show pending events
for data in nearby_family:
self.draw_contact(data['jid'], data['account'])
@ -3546,8 +3562,8 @@ class RosterWindow:
jid = model[titer][C_JID].decode('utf-8')
account = model[titer][C_ACCOUNT].decode('utf-8')
family = gajim.contacts.get_metacontacts_family(account, jid)
nearby_family = \
self._get_nearby_family_and_big_brother(family, account)[0]
nearby_family, bb_jid, bb_account = \
self._get_nearby_family_and_big_brother(family, account)
# Redraw all brothers to show pending events
for data in nearby_family:
self.draw_contact(data['jid'], data['account'])
@ -3812,7 +3828,7 @@ class RosterWindow:
def drag_drop(self, treeview, context, x, y, timestamp):
target_list = treeview.drag_dest_get_target_list()
target = treeview.drag_dest_find_target(context, target_list)
treeview.drag_get_data(context, target)
selection = treeview.drag_get_data(context, target)
context.finish(False, True)
return True
@ -5388,11 +5404,10 @@ class RosterWindow:
else:
execute_command_menuitem.set_sensitive(False)
# This does nothing:
# our_jid_other_resource = None
# if our_jid:
# # It's another resource of us, be sure to send invite to her
# our_jid_other_resource = contact.resource
our_jid_other_resource = None
if our_jid:
# It's another resource of us, be sure to send invite to her
our_jid_other_resource = contact.resource
# Else this var is useless but harmless in next connect calls
if gajim.capscache.is_supported(contact, NS_FILE):
@ -5753,6 +5768,7 @@ class RosterWindow:
def make_groupchat_menu(self, event, titer):
model = self.modelfilter
path = model.get_path(titer)
jid = model[titer][C_JID].decode('utf-8')
account = model[titer][C_ACCOUNT].decode('utf-8')
contact = gajim.contacts.get_contact_with_highest_priority(account, jid)
@ -6034,52 +6050,52 @@ class RosterWindow:
return True
def setup_for_osx(self):
# This is broken
return
'''Massage the GTK menu so it will match up to the OS/X nib style menu
when passed to sync-menu and merged'''
pass
# This is broken
# main_menu = self.xml.get_widget('menubar')
# app_item = gtk.MenuItem('Gajim')
# main_menu.insert(app_item, 0)
# win_item = gtk.MenuItem('Window')
# main_menu.insert(win_item, 4)
# actions_menu = self.xml.get_widget('actions_menu_menu')
# quit_item = self.xml.get_widget('quit_menuitem')
# actions_menu.remove(quit_item)
# actions_menu.remove(self.xml.get_widget('separator1'))
# edit_menu = self.xml.get_widget('edit_menu_menu')
# #edit_menu.remove(self.xml.get_widget('preferences_menuitem'))
# edit_menu.remove(self.xml.get_widget('separator2'))
# help_menu = self.xml.get_widget('help_menu_menu')
# about_item = self.xml.get_widget('about_menuitem')
# help_menu.remove(about_item)
# # Build up App menu
# app_menu = gtk.Menu()
# app_item.set_submenu(app_menu)
# app_menu.append(about_item)
# app_menu.append(gtk.MenuItem('__SKIP__'))
# prefs_item = gtk.MenuItem('Preferences...')
# prefs_item.connect('activate', self.on_preferences_menuitem_activate)
# accels = gtk.AccelGroup()
# self.xml.get_widget('roster_window').add_accel_group(accels)
# prefs_item.add_accelerator('activate', accels, ord(','),
# gtk.gdk.CONTROL_MASK, gtk.ACCEL_VISIBLE)
# app_menu.append(prefs_item)
# app_menu.append(gtk.MenuItem('__SKIP__'))
# app_menu.append(gtk.MenuItem('__SKIP__'))
# app_menu.append(gtk.MenuItem('__SKIP__'))
# app_menu.append(gtk.MenuItem('__SKIP__'))
# app_menu.append(gtk.MenuItem('__SKIP__'))
# app_menu.append(gtk.MenuItem('__SKIP__'))
# app_menu.append(gtk.MenuItem('__SKIP__'))
# app_menu.append(quit_item)
# app_menu.show_all()
# # Do the merge baby!
# syncmenu.takeover_menu(main_menu)
# self.make_menu(force=True)
# # Hide the GTK menubar itself and let the OS/X menubar do its thing
# #self.xml.get_widget('menubar').hide()
# return
main_menu = self.xml.get_widget('menubar')
app_item = gtk.MenuItem('Gajim')
main_menu.insert(app_item, 0)
win_item = gtk.MenuItem('Window')
main_menu.insert(win_item, 4)
actions_menu = self.xml.get_widget('actions_menu_menu')
quit_item = self.xml.get_widget('quit_menuitem')
actions_menu.remove(quit_item)
actions_menu.remove(self.xml.get_widget('separator1'))
edit_menu = self.xml.get_widget('edit_menu_menu')
#edit_menu.remove(self.xml.get_widget('preferences_menuitem'))
edit_menu.remove(self.xml.get_widget('separator2'))
help_menu = self.xml.get_widget('help_menu_menu')
about_item = self.xml.get_widget('about_menuitem')
help_menu.remove(about_item)
# Build up App menu
app_menu = gtk.Menu()
app_item.set_submenu(app_menu)
app_menu.append(about_item)
app_menu.append(gtk.MenuItem('__SKIP__'))
prefs_item = gtk.MenuItem('Preferences...')
prefs_item.connect('activate', self.on_preferences_menuitem_activate)
accels = gtk.AccelGroup()
self.xml.get_widget('roster_window').add_accel_group(accels)
prefs_item.add_accelerator('activate', accels, ord(','),
gtk.gdk.CONTROL_MASK, gtk.ACCEL_VISIBLE)
app_menu.append(prefs_item)
app_menu.append(gtk.MenuItem('__SKIP__'))
app_menu.append(gtk.MenuItem('__SKIP__'))
app_menu.append(gtk.MenuItem('__SKIP__'))
app_menu.append(gtk.MenuItem('__SKIP__'))
app_menu.append(gtk.MenuItem('__SKIP__'))
app_menu.append(gtk.MenuItem('__SKIP__'))
app_menu.append(gtk.MenuItem('__SKIP__'))
app_menu.append(quit_item)
app_menu.show_all()
# Do the merge baby!
syncmenu.takeover_menu(main_menu)
self.make_menu(force=True)
# Hide the GTK menubar itself and let the OS/X menubar do its thing
#self.xml.get_widget('menubar').hide()
return
################################################################################
###
@ -6328,7 +6344,8 @@ class RosterWindow:
if not gajim.ZEROCONF_ACC_NAME in gajim.config.get_per('accounts'):
# Create zeroconf in config file
from common.zeroconf import connection_zeroconf
connection_zeroconf.ConnectionZeroconf(gajim.ZEROCONF_ACC_NAME)
zeroconf = connection_zeroconf.ConnectionZeroconf(
gajim.ZEROCONF_ACC_NAME)
if sys.platform == 'darwin':
self.setup_for_osx()

View File

@ -21,7 +21,6 @@
from common.configpaths import gajimpaths
import Crypto
from common import crypto
from common import exceptions

View File

@ -655,7 +655,7 @@ class FileTransfersTooltip(BaseTooltip):
properties = []
name = file_props['name']
if file_props['type'] == 'r':
file_name = os.path.split(file_props['file-name'])[1]
(file_path, file_name) = os.path.split(file_props['file-name'])
else:
file_name = file_props['name']
properties.append((_('Name: '),

View File

@ -39,6 +39,7 @@ import locale
import os
import gtkgui_helpers
import message_control
from common import helpers
from common import gajim