Example #1
0
    def __init__(self, nick, password, connection, channels=[], commands=[]):
        self.nick = nick
        self.password = password
        self.connection = connection
        self.channels = channels
        self.commands = commands
        self.blacklist = Blacklist(BLACKLIST_FILE)
        self.racer_cache = RacerCache(RACER_CACHE_FILE)

        # load from config files
        if os.path.exists(OPS_FILE):
            with open(OPS_FILE, "rb") as ops_file:
                self.ops = pickle.load(ops_file)
        else:
            self.ops = set()
Example #2
0
class BingoBot:

    def __init__(self, nick, password, connection, channels=[], commands=[]):
        self.nick = nick
        self.password = password
        self.connection = connection
        self.channels = channels
        self.commands = commands
        self.blacklist = Blacklist(BLACKLIST_FILE)
        self.racer_cache = RacerCache(RACER_CACHE_FILE)

        # load from config files
        if os.path.exists(OPS_FILE):
            with open(OPS_FILE, "rb") as ops_file:
                self.ops = pickle.load(ops_file)
        else:
            self.ops = set()

    def send(self, s):
        logger.outgoing("OUTGOING: " + s.strip())
        self.connection.send(s)

    def connect(self):
        self.connection.connect()

    def sendmsg(self, chan, msg):
        for line in msg.strip().split("\n"):
            self.send("PRIVMSG " + chan + " :" + line + "\n")

    def joinchan(self, chan):
        self.send("JOIN " + chan + "\n")

    def leavechan(self, chan):
        self.send("PART " + chan + "\n")

    def listen(self):
        while True:
            try:
                next_line = self.connection.read_line()
                self.process_line(next_line)
            except DeadSocketException as e:
                logger.error(str(e))
                raise e

    def process_line(self, ircmsg):
        if is_ping(ircmsg):
            logger.incoming_ping(ircmsg)
            pingmsg = ircmsg.split("PING :")[1]
            self.send("PONG :" + pingmsg + "\n")
        elif is_message(ircmsg):
            logger.log(ircmsg)
            self.process_message(ircmsg)
        else:
            logger.incoming_info(ircmsg)

        # weird hack thing for joining channels?
        if "End of /MOTD" in ircmsg:
            for channel in self.channels:
                self.joinchan(channel)
        # weird hack thing for nickserv identify
        if "[email protected]" in ircmsg:
            if "You are already identified." not in ircmsg:
                self.sendmsg("NickServ", "IDENTIFY " + self.password)

    def process_message(self, ircmsg):
        msg = Message(ircmsg)
        # ignore anything from #speedrunslive to avoid flooding it accidentally
        if msg.channel == "#speedrunslive":
            pass
        # kill command to force disconnect the bot from the server
        # WARNING: the bot will not reconnect until manually reset
        elif msg.command in {"!kill", ".kill"}:
            logger.debug("Kill request detected from " + msg.sender.lower())
            if self.has_op(msg.sender):
                # actually kills the bot if the sender is privelaged
                self.send("QUIT Kill requested by " + msg.sender + "\n")
                raise KillException
        else:
            for command in self.commands:
                try:
                    command(self, msg)
                except NameException as e:
                    logger.error(traceback.format_exc())
                    message = "There was a problem looking up data for " + str(e) + ". "
                    message += "Do they have an SRL profile?"
                    self.sendmsg(msg.channel, message)
                except Exception as e:
                    logger.error(traceback.format_exc())
                    self.sendmsg(msg.channel, "Something weird happened...")

    def get_racer(self, channel, username, refresh=False):
        if refresh:
            self.racer_cache.refresh(username, self, channel)
        return self.racer_cache.get_or_load(username, self, channel)

    def has_admin(self, name):
        return name.lower() in ADMINS

    def has_op(self, name):
        return name.lower() in self.ops or self.has_admin(name)

    def add_op(self, name):
        self.ops.add(name.lower())
        self.save_ops()

    def remove_op(self, name):
        self.ops.remove(name.lower())
        self.save_ops()

    def save_ops(self):
        with open(OPS_FILE, "wb") as ops_file:
            pickle.dump(self.ops, ops_file)