plugin 0249: fixed invitation handling + some improvments:

- properly retrieve payload by namespace
- now use a trigger instead of observer, so the message workflow is stopped if an invitation is found
- namespace is registered

fix 241
This commit is contained in:
Goffi 2019-07-14 11:23:25 +02:00
commit 692a5b34fc
2 changed files with 42 additions and 42 deletions

View file

@ -482,13 +482,19 @@ class XEP_0045(object):
options = {}
if room_jid in client._muc_client.joined_rooms:
room = client._muc_client.joined_rooms[room_jid]
log.info(_(u'{profile} is already in room {room_jid}').format(profile=client.profile, room_jid = room_jid.userhost()))
log.info(_(u'{profile} is already in room {room_jid}').format(
profile=client.profile, room_jid = room_jid.userhost()))
return defer.fail(AlreadyJoined(room))
log.info(_(u"[{profile}] is joining room {room} with nick {nick}").format(profile=client.profile, room=room_jid.userhost(), nick=nick))
log.info(_(u"[{profile}] is joining room {room} with nick {nick}").format(
profile=client.profile, room=room_jid.userhost(), nick=nick))
password = options.get("password")
return client._muc_client.join(room_jid, nick, password).addCallbacks(self._joinCb, self._joinEb, (client, room_jid, nick), errbackArgs=(client, room_jid, nick, password))
d = client._muc_client.join(room_jid, nick, password)
d.addCallbacks(self._joinCb, self._joinEb,
(client, room_jid, nick),
errbackArgs=(client, room_jid, nick, password))
return d
def _nick(self, room_jid_s, nick, profile_key=C.PROF_KEY_NONE):
client = self.host.getClient(profile_key)

View file

@ -38,8 +38,7 @@ except ImportError:
from wokkel.subprotocols import XMPPHandler
MESSAGE = "/message"
NS_DIRECT_MUC_INVITATION = "jabber:x:conference"
DIRECT_MUC_INVITATION_REQUEST = MESSAGE + '/x[@xmlns="' + NS_DIRECT_MUC_INVITATION + '"]'
NS_X_CONFERENCE = "jabber:x:conference"
AUTOJOIN_KEY = "Misc"
AUTOJOIN_NAME = "Auto-join MUC on invitation"
AUTOJOIN_VALUES = ["ask", "always", "never"]
@ -94,9 +93,11 @@ class XEP_0249(object):
self.host.plugins[C.TEXT_CMDS].registerTextCommands(self)
except KeyError:
log.info(_("Text commands not available"))
host.registerNamespace('x-conference', NS_X_CONFERENCE)
host.trigger.add("MessageReceived", self._MessageReceivedTrigger)
def getHandler(self, client):
return XEP_0249_handler(self)
return XEP_0249_handler()
def _invite(self, guest_jid_s, room_jid_s, options, profile_key):
"""Invite an user to a room
@ -119,7 +120,7 @@ class XEP_0249(object):
"""
message = domish.Element((None, "message"))
message["to"] = guest.full()
x_elt = message.addElement((NS_DIRECT_MUC_INVITATION, "x"))
x_elt = message.addElement((NS_X_CONFERENCE, "x"))
x_elt["jid"] = room.userhost()
for key, value in options.iteritems():
if key not in ("password", "reason", "thread"):
@ -142,23 +143,23 @@ class XEP_0249(object):
d = self.host.plugins["XEP-0045"].join(client, room_jid, client.jid.user, {})
return d
def onInvitation(self, message, profile):
"""
called when an invitation is received
@param message: message element
@profile: %(doc_profile)s
"""
client = self.host.getClient(profile)
def _MessageReceivedTrigger(self, client, message_elt, post_treat):
"""Check if a direct invitation is in the message, and handle it"""
x_elt = next(message_elt.elements(NS_X_CONFERENCE, 'x'), None)
if x_elt is None:
return True
try:
room_jid_s = message.firstChildElement()["jid"]
log.info(
_(u"Invitation received for room %(room)s [%(profile)s]")
% {"room": room_jid_s, "profile": profile}
)
except:
log.error(_("Error while parsing invitation"))
return
from_jid_s = message["from"]
room_jid_s = x_elt[u"jid"]
except KeyError:
log.warning(_(u"invalid invitation received: {xml}").format(
xml=message_elt.toXml()))
return False
log.info(
_(u"Invitation received for room %(room)s [%(profile)s]")
% {"room": room_jid_s, "profile": client.profile}
)
from_jid_s = message_elt["from"]
room_jid = jid.JID(room_jid_s)
try:
self.host.plugins["XEP-0045"].checkRoomJoined(client, room_jid)
@ -171,31 +172,34 @@ class XEP_0249(object):
return
autojoin = self.host.memory.getParamA(
AUTOJOIN_NAME, AUTOJOIN_KEY, profile_key=profile
AUTOJOIN_NAME, AUTOJOIN_KEY, profile_key=client.profile
)
if autojoin == "always":
self._accept(room_jid, profile)
self._accept(room_jid, client.profile)
elif autojoin == "never":
msg = D_(
"An invitation from %(user)s to join the room %(room)s has been declined according to your personal settings."
u"An invitation from %(user)s to join the room %(room)s has been "
u"declined according to your personal settings."
) % {"user": from_jid_s, "room": room_jid_s}
title = D_("MUC invitation")
xml_tools.quickNote(self.host, client, msg, title, C.XMLUI_DATA_LVL_INFO)
else: # leave the default value here
confirm_msg = D_(
"You have been invited by %(user)s to join the room %(room)s. Do you accept?"
u"You have been invited by %(user)s to join the room %(room)s. "
u"Do you accept?"
) % {"user": from_jid_s, "room": room_jid_s}
confirm_title = D_("MUC invitation")
d = xml_tools.deferConfirm(
self.host, confirm_msg, confirm_title, profile=profile
self.host, confirm_msg, confirm_title, profile=client.profile
)
def accept_cb(accepted):
if accepted:
self._accept(room_jid, profile)
self._accept(room_jid, client.profile)
d.addCallback(accept_cb)
return False
def cmd_invite(self, client, mess_data):
"""invite someone in the room
@ -209,7 +213,8 @@ class XEP_0249(object):
contact_jid = jid.JID(contact_jid_s)
except (RuntimeError, jid.InvalidFormat, AttributeError):
feedback = _(
u"You must provide a valid JID to invite, like in '/invite contact@{host}'"
u"You must provide a valid JID to invite, like in '/invite "
u"contact@{host}'"
).format(host=my_host)
self.host.plugins[C.TEXT_CMDS].feedBack(client, feedback, mess_data)
return False
@ -222,19 +227,8 @@ class XEP_0249(object):
class XEP_0249_handler(XMPPHandler):
implements(iwokkel.IDisco)
def __init__(self, plugin_parent):
self.plugin_parent = plugin_parent
self.host = plugin_parent.host
def connectionInitialized(self):
self.xmlstream.addObserver(
DIRECT_MUC_INVITATION_REQUEST,
self.plugin_parent.onInvitation,
profile=self.parent.profile,
)
def getDiscoInfo(self, requestor, target, nodeIdentifier=""):
return [disco.DiscoFeature(NS_DIRECT_MUC_INVITATION)]
return [disco.DiscoFeature(NS_X_CONFERENCE)]
def getDiscoItems(self, requestor, target, nodeIdentifier=""):
return []