Refuse multiple sessions and implement alternative-session; make jingle GUI a bit more reliable.
This commit is contained in:
parent
b3b8e2f46b
commit
ab0f7899ad
|
@ -1620,11 +1620,14 @@ class ChatControl(ChatControlBase):
|
|||
'stop': self.JINGLE_STATE_AVAILABLE,
|
||||
'error': self.JINGLE_STATE_ERROR}
|
||||
|
||||
if state in states:
|
||||
jingle_state = states[state]
|
||||
if getattr(self, jingle_type + '_state') == jingle_state:
|
||||
return
|
||||
setattr(self, jingle_type + '_state', jingle_state)
|
||||
jingle_state = states[state]
|
||||
if getattr(self, jingle_type + '_state') == jingle_state:
|
||||
return
|
||||
|
||||
if state == 'stop' and getattr(self, jingle_type + '_sid') not in (None, sid):
|
||||
return
|
||||
|
||||
setattr(self, jingle_type + '_state', jingle_state)
|
||||
|
||||
# Destroy existing session with the user when he signs off
|
||||
# We need to do that before modifying the sid
|
||||
|
|
|
@ -121,6 +121,20 @@ class ConnectionJingle(object):
|
|||
jingle.start_session()
|
||||
return jingle.sid
|
||||
|
||||
|
||||
def iter_jingle_sessions(self, jid, sid=None, media=None):
|
||||
if sid:
|
||||
return (session for session in self.__sessions.values() if session.sid == sid)
|
||||
sessions = (session for session in self.__sessions.values() if session.peerjid == jid)
|
||||
if media:
|
||||
if media not in ('audio', 'video'):
|
||||
return tuple()
|
||||
else:
|
||||
return (session for session in sessions if session.get_content(media))
|
||||
else:
|
||||
return sessions
|
||||
|
||||
|
||||
def get_jingle_session(self, jid, sid=None, media=None):
|
||||
if sid:
|
||||
if sid in self.__sessions:
|
||||
|
|
|
@ -426,6 +426,16 @@ class JingleSession(object):
|
|||
# Jingle with unknown entities, it SHOULD return a <service-unavailable/>
|
||||
# error.
|
||||
|
||||
# Check if there's already a session with this user:
|
||||
for session in self.connection.iter_jingle_sessions(self.peerjid):
|
||||
if not session is self:
|
||||
reason = xmpp.Node('reason')
|
||||
alternative_session = reason.setTag('alternative-session')
|
||||
alternative_session.setTagData('sid', session.sid)
|
||||
self.__ack(stanza, jingle, error, action)
|
||||
self._session_terminate(reason)
|
||||
raise xmpp.NodeProcessed
|
||||
|
||||
# Lets check what kind of jingle session does the peer want
|
||||
contents, contents_rejected, reason_txt = self.__parse_contents(jingle)
|
||||
|
||||
|
@ -520,6 +530,7 @@ class JingleSession(object):
|
|||
self.connection.dispatch('JINGLE_ERROR', (self.peerjid, self.sid, text))
|
||||
|
||||
def __reason_from_stanza(self, stanza):
|
||||
# TODO: Move to GUI?
|
||||
reason = 'success'
|
||||
reasons = ['success', 'busy', 'cancel', 'connectivity-error',
|
||||
'decline', 'expired', 'failed-application', 'failed-transport',
|
||||
|
@ -602,6 +613,7 @@ class JingleSession(object):
|
|||
jingle.addChild(node=reason)
|
||||
self.__broadcast_all(stanza, jingle, None, 'session-terminate-sent')
|
||||
self.connection.connection.send(stanza)
|
||||
# TODO: Move to GUI?
|
||||
reason, text = self.__reason_from_stanza(jingle)
|
||||
if reason not in ('success', 'cancel', 'decline'):
|
||||
self.__dispatch_error(reason, reason, text)
|
||||
|
|
|
@ -4925,17 +4925,10 @@ class VoIPCallReceivedDialog(object):
|
|||
#TODO: Ensure that ctrl.contact.resource == resource
|
||||
jid = gajim.get_jid_without_resource(self.fjid)
|
||||
resource = gajim.get_resource_from_jid(self.fjid)
|
||||
ctrl = gajim.interface.msg_win_mgr.get_control(self.fjid, self.account)
|
||||
if not ctrl:
|
||||
ctrl = gajim.interface.msg_win_mgr.get_control(jid, self.account)
|
||||
if not ctrl:
|
||||
# open chat control
|
||||
contact = gajim.contacts.get_contact(self.account, jid, resource)
|
||||
if not contact:
|
||||
contact = gajim.contacts.get_contact(self.account, jid)
|
||||
if not contact:
|
||||
return
|
||||
ctrl = gajim.interface.new_chat(contact, self.account, resource)
|
||||
ctrl = (gajim.interface.msg_win_mgr.get_control(self.fjid, self.account)
|
||||
or gajim.interface.msg_win_mgr.get_control(jid, self.account)
|
||||
or gajim.interface.new_chat_from_jid(self.account, jid))
|
||||
|
||||
# Chat control opened, update content's status
|
||||
audio = session.get_content('audio')
|
||||
video = session.get_content('video')
|
||||
|
|
|
@ -1775,9 +1775,8 @@ class Interface:
|
|||
|
||||
jid = gajim.get_jid_without_resource(peerjid)
|
||||
resource = gajim.get_resource_from_jid(peerjid)
|
||||
ctrl = self.msg_win_mgr.get_control(peerjid, account)
|
||||
if not ctrl:
|
||||
ctrl = self.msg_win_mgr.get_control(jid, account)
|
||||
ctrl = (self.msg_win_mgr.get_control(peerjid, account)
|
||||
or self.msg_win_mgr.get_control(jid, account))
|
||||
if ctrl:
|
||||
if 'audio' in content_types:
|
||||
ctrl.set_audio_state('connection_received', sid)
|
||||
|
@ -2811,6 +2810,8 @@ class Interface:
|
|||
ctrl.user_nick = gajim.nicks[account]
|
||||
gobject.idle_add(mw.window.grab_focus)
|
||||
|
||||
return ctrl
|
||||
|
||||
def on_open_chat_window(self, widget, contact, account, resource=None,
|
||||
session=None):
|
||||
# Get the window containing the chat
|
||||
|
|
Loading…
Reference in New Issue