diff --git a/examples/echo_client.py b/examples/echo_client.py index 6f06da5..73699a7 100644 --- a/examples/echo_client.py +++ b/examples/echo_client.py @@ -12,6 +12,7 @@ import os import sys +import asyncio import logging from getpass import getpass from argparse import ArgumentParser @@ -39,7 +40,7 @@ class EchoBot(ClientXMPP): ClientXMPP.__init__(self, jid, password) self.add_event_handler("session_start", self.start) - self.add_event_handler("message", self.message) + self.add_event_handler("message", self.message_handler) def start(self, _event) -> None: """ @@ -57,7 +58,10 @@ class EchoBot(ClientXMPP): self.send_presence() self.get_roster() - def message(self, msg: Message, allow_untrusted: bool = False) -> None: + def message_handler(self, msg: Message) -> None: + asyncio.ensure_future(self.message(msg)) + + async def message(self, msg: Message, allow_untrusted: bool = False) -> None: """ Process incoming message stanzas. Be aware that this also includes MUC messages and error messages. It is usually @@ -69,20 +73,21 @@ class EchoBot(ClientXMPP): for stanza objects and the Message stanza to see how it may be used. """ + if msg['type'] not in ('chat', 'normal'): return None if not self['xep_0384'].is_encrypted(msg): - self.plain_reply(msg, 'This message was not encrypted.\n%(body)s' % msg) + await self.plain_reply(msg, 'This message was not encrypted.\n%(body)s' % msg) return None try: body = self['xep_0384'].decrypt_message(msg, allow_untrusted) - self.encrypted_reply(msg, 'Thanks for sending\n%s' % body.decode("utf8")) + await self.encrypted_reply(msg, 'Thanks for sending\n%s' % body.decode("utf8")) except (MissingOwnKey,): # The message is missing our own key, it was not encrypted for # us, and we can't decrypt it. - self.plain_reply( + await self.plain_reply( msg, 'I can\'t decrypt this message as it is not encrypted for me.', ) @@ -93,7 +98,7 @@ class EchoBot(ClientXMPP): # Here, as we need to initiate a new encrypted session, it is # best if we send an encrypted message directly. XXX: Is it # where we talk about self-healing messages? - self.encrypted_reply( + await self.encrypted_reply( msg, 'I can\'t decrypt this message as it uses an encrypted ' 'session I don\'t know about.', @@ -107,21 +112,21 @@ class EchoBot(ClientXMPP): # or not. Clients _should_ indicate that the message was not # trusted, or in undecided state, if they decide to decrypt it # anyway. - self.plain_reply( + await self.plain_reply( msg, "Your device '%s' is not in my trusted devices." % exn.device, ) # We resend, setting the `allow_untrusted` parameter to True. - self.message(msg, allow_untrusted=True) + await self.message(msg, allow_untrusted=True) except (EncryptionPrepareException,): # Slixmpp tried its best, but there were errors it couldn't # resolve. At this point you should have seen other exceptions # and given a chance to resolve them already. - self.plain_reply(msg, 'I was not able to decrypt the message.') + await self.plain_reply(msg, 'I was not able to decrypt the message.') return None - def plain_reply(self, original_msg, body) -> None: + async def plain_reply(self, original_msg, body) -> None: """ Helper to reply to messages """ @@ -130,13 +135,13 @@ class EchoBot(ClientXMPP): mtype = original_msg['type'] msg = self.make_message(mto=mto, mtype=mtype) msg['body'] = body - msg.send() + return msg.send() - def encrypted_reply(self, original_msg, body) -> None: + async def encrypted_reply(self, original_msg, body) -> None: """Helper to reply with encrypted messages""" # TODO: Send the message encrypted. - self.plain_reply(msg, body) + return await self.plain_reply(msg, body) if __name__ == '__main__':