#!/usr/bin/env python3 from mastodon import Mastodon import emoji import json import os import re import socket import sys def masto_from_json(conf): conf = json.load(conf) return Mastodon( client_id=conf["client_id"], client_secret=conf["client_secret"], access_token=conf["access_token"], api_base_url=conf["base_url"] ) def rawsend(msg): print(msg) ircsock.send(f"{msg}\r\n".encode()) def send(chan, msg): rawsend(f"PRIVMSG #{chan} :{msg}") def eventloop(chan, nick, msg): words = re.split("[ \t\s]+", msg) if len(words) > 0 and nick != botnick: if words[0] == "!toot": status = emoji.emojize(" ".join(words[1:]), use_aliases=True) print(f"{status} posted by {nick}") if chan == "team": res = tildeteam.toot(status) else: res = tildeverse.toot(status) print(res) send(chan, "tooted! {}".format(res["url"])) elif words[0] == "!source": send(chan, "https://tildegit.org/ben/tooter") elif words[0] == "!botlist" or words[0] == "!toothelp": send(chan, "helo i can send toots from irc: @tildeverse@tilde.zone - from @tildeteam from the #team channel)") # do setup path = os.path.dirname(os.path.abspath(__file__)) with open(os.path.join(path, "config.json"), "r") as f: config = json.load(f) if os.path.isfile(os.path.join(path, "account.json")): with open(os.path.join(path, "account.json"), "r") as f: account = json.load(f) botnick = config["botnick"] channels = config["channels"] if len(sys.argv) > 1: for c in sys.argv[1:]: channels.append("#" + c) # read masto creds with open(os.path.join(path, "tildeverse.json"), "r") as f: tildeverse = masto_from_json(f) with open(os.path.join(path, "tildeteam.json"), "r") as f: tildeteam = masto_from_json(f) if __name__ == "__main__": ircsock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) ircsock.connect((config["address"], config["port"])) rawsend(f"NICK {botnick}") rawsend(f"USER {botnick} 0 * :mastodon tooter") while 1: for msg in ircsock.recv(2048).decode().split("\r\n"): print(msg) if "PING" in msg: rawsend(msg.replace("I", "O", 1)) if "INVITE" in msg: chan = msg.split(":")[-1] rawsend(f"JOIN {chan}") if "001" in msg: for c in channels: rawsend(f"JOIN {c}") rawsend(f"MODE {botnick} +B") if account is not None: rawsend("SQUERY NickServ IDENTIFY %s %s" % (account["username"], account["password"])) m = re.match(":(?P[^ ]+)!.*PRIVMSG #(?P\w+) :(?P.*)", msg) if m and m.groupdict(): m = m.groupdict() eventloop(m["chan"], m["nick"], m["msg"])