use event system for jingle FT

This commit is contained in:
Yann Leboulanger 2011-06-24 18:24:42 +02:00
parent f7b0659c04
commit dc3b203168
5 changed files with 76 additions and 78 deletions

View File

@ -53,7 +53,7 @@ from common.logger import constants
from common.pep import MOODS, ACTIVITIES
from common.xmpp.protocol import NS_XHTML, NS_XHTML_IM, NS_FILE, NS_MUC
from common.xmpp.protocol import NS_RECEIPTS, NS_ESESSION
from common.xmpp.protocol import NS_JINGLE_RTP_AUDIO, NS_JINGLE_RTP_VIDEO, NS_JINGLE_ICE_UDP
from common.xmpp.protocol import NS_JINGLE_RTP_AUDIO, NS_JINGLE_RTP_VIDEO, NS_JINGLE_ICE_UDP, NS_JINGLE_FILE_TRANSFER
from common.connection_handlers_events import MessageOutgoingEvent
from command_system.implementation.middleware import ChatCommandProcessor

View File

@ -34,6 +34,7 @@ from common import exceptions
from common.zeroconf import zeroconf
from common.logger import LOG_DB_PATH
from common.pep import SUPPORTED_PERSONAL_USER_EVENTS
from common.jingle_transport import JingleTransportSocks5
import gtkgui_helpers
@ -1818,6 +1819,10 @@ class FileRequestReceivedEvent(nec.NetworkIncomingEvent, HelperEvent):
name = 'file-request-received'
base_network_events = []
def init(self):
self.jingle_content = None
self.FT_content = None
def generate(self):
self.get_id()
self.fjid = self.conn._ft_get_from(self.stanza)
@ -1825,28 +1830,36 @@ class FileRequestReceivedEvent(nec.NetworkIncomingEvent, HelperEvent):
self.file_props = {'type': 'r'}
self.file_props['sender'] = self.fjid
self.file_props['request-id'] = self.id_
si = self.stanza.getTag('si')
profile = si.getAttr('profile')
if profile != xmpp.NS_FILE:
self.conn.send_file_rejection(self.file_props, code='400', typ='profile')
raise xmpp.NodeProcessed
feature_tag = si.getTag('feature', namespace=xmpp.NS_FEATURE)
if not feature_tag:
return
form_tag = feature_tag.getTag('x', namespace=xmpp.NS_DATA)
if not form_tag:
return
self.dataform = dataforms.ExtendForm(node=form_tag)
for f in self.dataform.iter_fields():
if f.var == 'stream-method' and f.type == 'list-single':
values = [o[1] for o in f.options]
self.file_props['stream-methods'] = ' '.join(values)
if xmpp.NS_BYTESTREAM in values or xmpp.NS_IBB in values:
break
if self.jingle_content:
self.file_props['session-type'] = 'jingle'
self.file_props['stream-methods'] = xmpp.NS_BYTESTREAM
file_tag = self.jingle_content.getTag('description').getTag(
'offer').getTag('file')
else:
self.conn.send_file_rejection(self.file_props, code='400', typ='stream')
raise xmpp.NodeProcessed
file_tag = si.getTag('file')
si = self.stanza.getTag('si')
profile = si.getAttr('profile')
if profile != xmpp.NS_FILE:
self.conn.send_file_rejection(self.file_props, code='400',
typ='profile')
raise xmpp.NodeProcessed
feature_tag = si.getTag('feature', namespace=xmpp.NS_FEATURE)
if not feature_tag:
return
form_tag = feature_tag.getTag('x', namespace=xmpp.NS_DATA)
if not form_tag:
return
self.dataform = dataforms.ExtendForm(node=form_tag)
for f in self.dataform.iter_fields():
if f.var == 'stream-method' and f.type == 'list-single':
values = [o[1] for o in f.options]
self.file_props['stream-methods'] = ' '.join(values)
if xmpp.NS_BYTESTREAM in values or xmpp.NS_IBB in values:
break
else:
self.conn.send_file_rejection(self.file_props, code='400',
typ='stream')
raise xmpp.NodeProcessed
file_tag = si.getTag('file')
for attribute in file_tag.getAttrs():
if attribute in ('name', 'size', 'hash', 'date'):
val = file_tag.getAttr(attribute)
@ -1857,13 +1870,41 @@ class FileRequestReceivedEvent(nec.NetworkIncomingEvent, HelperEvent):
if file_desc_tag is not None:
self.file_props['desc'] = file_desc_tag.getData()
mime_type = si.getAttr('mime-type')
if mime_type is not None:
self.file_props['mime-type'] = mime_type
if not self.jingle_content:
mime_type = si.getAttr('mime-type')
if mime_type is not None:
self.file_props['mime-type'] = mime_type
self.file_props['receiver'] = self.conn._ft_get_our_jid()
self.file_props['sid'] = unicode(si.getAttr('id'))
self.file_props['transfered_size'] = []
if self.jingle_content:
self.FT_content.use_security = bool(self.jingle_content.getTag(
'security'))
self.file_props['session-sid'] = unicode(self.stanza.getTag(
'jingle').getAttr('sid'))
self.FT_content.file_props = self.file_props
if not self.FT_content.transport:
self.FT_content.transport = JingleTransportSocks5()
self.FT_content.transport.set_our_jid(
self.FT_content.session.ourjid)
self.FT_content.transport.set_connection(
self.FT_content.session.connection)
self.file_props['sid'] = self.FT_content.transport.sid
self.FT_content.session.connection.files_props[
self.file_props['sid']] = self.file_props
self.FT_content.transport.set_file_props(self.file_props)
if self.file_props.has_key('streamhosts'):
self.file_props['streamhosts'].extend(
self.FT_content.transport.remote_candidates)
else:
self.file_props['streamhosts'] = \
self.FT_content.transport.remote_candidates
for host in self.file_props['streamhosts']:
host['initiator'] = self.FT_content.session.initiator
host['target'] = self.FT_content.session.responder
else:
self.file_props['sid'] = unicode(si.getAttr('id'))
return True
class FileRequestErrorEvent(nec.NetworkIncomingEvent):

View File

@ -25,6 +25,7 @@ from jingle_content import contents, JingleContent
from jingle_transport import JingleTransportICEUDP, JingleTransportSocks5
from common import helpers
from common.socks5 import Socks5Receiver
from common.connection_handlers_events import FileRequestReceivedEvent
import logging
log = logging.getLogger('gajim.c.jingle_ft')
@ -87,55 +88,9 @@ class JingleFileTransfer(JingleContent):
self.media = 'file'
def __on_session_initiate(self, stanza, content, error, action):
jid = unicode(stanza.getFrom())
log.info("jid:%s" % jid)
file_props = {'type': 'r'}
file_props['sender'] = jid
file_props['request-id'] = unicode(stanza.getAttr('id'))
file_props['session-type'] = 'jingle'
self.use_security = bool(content.getTag('security'))
# TODO: extract fingerprint element, encryption method element for later
# use
file_tag = content.getTag('description').getTag('offer').getTag('file')
for attribute in file_tag.getAttrs():
if attribute in ('name', 'size', 'hash', 'date'):
val = file_tag.getAttr(attribute)
if val is None:
continue
file_props[attribute] = val
file_desc_tag = file_tag.getTag('desc')
if file_desc_tag is not None:
file_props['desc'] = file_desc_tag.getData()
file_props['receiver'] = self.session.ourjid
log.info("ourjid: %s" % self.session.ourjid)
file_props['session-sid'] = unicode(stanza.getTag('jingle').getAttr('sid'))
file_props['transfered_size'] = []
self.file_props = file_props
if self.transport is None:
self.transport = JingleTransportSocks5()
self.transport.set_our_jid(self.session.ourjid)
self.transport.set_connection(self.session.connection)
self.file_props['sid'] = self.transport.sid
self.session.connection.files_props[file_props['sid']] = file_props
self.transport.set_file_props(self.file_props)
if self.file_props.has_key('streamhosts'):
self.file_props['streamhosts'].extend(
self.transport.remote_candidates)
else:
self.file_props['streamhosts'] = self.transport.remote_candidates
for host in self.file_props['streamhosts']:
host['initiator'] = self.session.initiator
host['target'] = self.session.responder
log.info("FT request: %s" % file_props)
self.session.connection.dispatch('FILE_REQUEST', (jid, file_props))
gajim.nec.push_incoming_event(FileRequestReceivedEvent(None,
conn=self.session.connection, stanza=stanza, jingle_content=content,
FT_content=self))
def __on_session_accept(self, stanza, content, error, action):
log.info("__on_session_accept")

View File

@ -104,7 +104,8 @@ def get_context(fingerprint, verify_cb=None):
store = ctx.get_cert_store()
for f in os.listdir(os.path.expanduser(gajim.MY_PEER_CERTS_PATH)):
load_cert_file(os.path.join(os.path.expanduser(gajim.MY_PEER_CERTS_PATH), f), store)
print 'certificate file' + f + ' loaded', 'fingerprint', fingerprint
log.debug('certificate file ' + f + ' loaded fingerprint ' + \
fingerprint)
return ctx
def send_cert(con, jid_from, sid):

View File

@ -753,10 +753,11 @@ class Socks5Sender(Socks5, IdleObject):
self.queue = parent
Socks5.__init__(self, idlequeue, host, port, None, None, None)
self._sock = _sock
if not self.fingerprint is None:
if self.fingerprint is not None:
self._sock = OpenSSL.SSL.Connection(
jingle_xtls.get_context('server'), self._sock)
self._sock.setblocking(False)
else:
self._sock.setblocking(False)
self.fd = _sock.fileno()
self._recv = _sock.recv
self._send = _sock.send