From c959e761cdb7627971da691b2b837b798cb36f43 Mon Sep 17 00:00:00 2001 From: Morgan McMillian Date: Sat, 13 Feb 2021 16:09:07 -0800 Subject: [PATCH] added xmpp script --- README.md | 4 ++ requirements.txt | 1 + send2xmpp.py | 133 +++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 138 insertions(+) create mode 100755 send2xmpp.py diff --git a/README.md b/README.md index 54790fb..9672491 100644 --- a/README.md +++ b/README.md @@ -5,3 +5,7 @@ Parse email from STDIN and create a post on one or more social network. Currently supports mastodon and pnut.io. +## send2xmpp.py + +Send message from cmdline or parse email from STDIN to a xmpp recipient. + diff --git a/requirements.txt b/requirements.txt index 9e8aedf..d20b433 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,2 +1,3 @@ pnutpy Mastodon.py +slixmpp diff --git a/send2xmpp.py b/send2xmpp.py new file mode 100755 index 0000000..4a82cfb --- /dev/null +++ b/send2xmpp.py @@ -0,0 +1,133 @@ +#!/usr/bin/env python3 +# -*- coding: utf-8 -*- +import logging +import email +import slixmpp +import sys +import os + +from getpass import getpass +from argparse import ArgumentParser + + +class SendMsgBot(slixmpp.ClientXMPP): + + """ + A basic Slixmpp bot that will log in, send a message, + and then log out. + """ + + def __init__(self, jid, password, recipient, message): + slixmpp.ClientXMPP.__init__(self, jid, password) + + # The message we wish to send, and the JID that + # will receive it. + self.recipient = recipient + self.msg = message + + # The session_start event will be triggered when + # the bot establishes its connection with the server + # and the XML streams are ready for use. We want to + # listen for this event so that we we can initialize + # our roster. + self.add_event_handler("session_start", self.start) + + async def start(self, event): + """ + Process the session_start event. + + Typical actions for the session_start event are + requesting the roster and broadcasting an initial + presence stanza. + + Arguments: + event -- An empty dictionary. The session_start + event does not provide any additional + data. + """ + self.send_presence() + await self.get_roster() + + self.send_message(mto=self.recipient, + mbody=self.msg, + mtype='chat') + + self.disconnect() + +def parse_email(data): + body = "" + for part in data.walk(): + disposition = part.get_content_disposition() + contentType = part.get_content_type() + + logging.debug(disposition) + logging.debug(contentType) + + if contentType in ["multipart/mixed", "multipart/alternative"]: + continue + + if disposition == "inline": + body = part.get_payload(decode=True).decode("utf-8") + + elif disposition == "attachment": + continue + + else: + logging.debug("unknown disposition") + logging.debug(disposition) + if contentType == "text/plain": + body = part.get_payload(decode=True).decode("utf-8") + else: + logging.error("can't get the message, bailing out") + + return body + +if __name__ == '__main__': + logging.basicConfig(level=logging.DEBUG) + # Setup the command line arguments. + parser = ArgumentParser(description=SendMsgBot.__doc__) + + # Output verbosity options. + parser.add_argument("-q", "--quiet", help="set logging to ERROR", + action="store_const", dest="loglevel", + const=logging.ERROR, default=logging.INFO) + parser.add_argument("-d", "--debug", help="set logging to DEBUG", + action="store_const", dest="loglevel", + const=logging.DEBUG, default=logging.INFO) + + # JID and password options. + parser.add_argument("-j", "--jid", dest="jid", + help="JID to use") + parser.add_argument("-p", "--password", dest="password", + help="password to use") + parser.add_argument("-t", "--to", dest="to", + help="JID to send the message to") + parser.add_argument("-m", "--message", dest="message", + help="message to send") + parser.add_argument("-e", "--email", dest="email", action="store_true", + help="email from stdin") + + args = parser.parse_args() + + logging.basicConfig(level=args.loglevel) + + if args.email: + data = parse_email(email.message_from_file(sys.stdin)) + + elif args.message is not None: + data = args.message + + else: + parser.print_help() + sys.exit(1) + + # Setup the EchoBot and register plugins. Note that while plugins may + # have interdependencies, the order in which you register them does + # not matter. + xmpp = SendMsgBot(args.jid, args.password, args.to, data) + xmpp.register_plugin('xep_0030') # Service Discovery + xmpp.register_plugin('xep_0199') # XMPP Ping + + # Connect to the XMPP server and start processing XMPP stanzas. + xmpp.connect() + xmpp.process(forever=False)