| @@ -57,6 +57,16 @@ class BaseCommand(object): | |||
| self.config = bot.config | |||
| self.logger = bot.commands.logger.getChild(self.name) | |||
| # Convenience functions: | |||
| self.say = lambda target, msg: self.bot.frontend.say(target, msg) | |||
| self.reply = lambda data, msg: self.bot.frontend.reply(data, msg) | |||
| self.action = lambda target, msg: self.bot.frontend.action(target, msg) | |||
| self.notice = lambda target, msg: self.bot.frontend.notice(target, msg) | |||
| self.join = lambda chan: self.bot.frontend.join(chan) | |||
| self.part = lambda chan: self.bot.frontend.part(chan) | |||
| self.mode = lambda t, level, msg: self.bot.frontend.mode(t, level, msg) | |||
| self.pong = lambda target: self.bot.frontend.pong(target) | |||
| def _wrap_check(self, data): | |||
| """Check whether this command should be called, catching errors.""" | |||
| try: | |||
| @@ -66,8 +76,7 @@ class BaseCommand(object): | |||
| self.logger.exception(e.format(self.name, data)) | |||
| def _wrap_process(self, data): | |||
| """Make a connection alias, process() the message, and catch errors.""" | |||
| self.connection = self.bot.frontend | |||
| """process() the message, catching and reporting any errors.""" | |||
| try: | |||
| self.process(data) | |||
| except Exception: | |||
| @@ -43,7 +43,7 @@ class Command(BaseCommand): | |||
| if not data.args: | |||
| msg = "what submission do you want me to give information about?" | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| return | |||
| title = " ".join(data.args) | |||
| @@ -67,8 +67,7 @@ class Command(BaseCommand): | |||
| if page: | |||
| return self.report(page) | |||
| msg = "submission \x0302{0}\x0301 not found.".format(title) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, "submission \x0302{0}\x0301 not found.".format(title)) | |||
| def get_page(self, title): | |||
| page = self.site.get_page(title, follow_redirects=False) | |||
| @@ -89,9 +88,9 @@ class Command(BaseCommand): | |||
| if status == "accepted": | |||
| msg3 = "Reviewed by \x0302{0}\x0301 ({1})" | |||
| self.connection.reply(self.data, msg1.format(short, url)) | |||
| self.connection.say(self.data.chan, msg2.format(status)) | |||
| self.connection.say(self.data.chan, msg3.format(user_name, user_url)) | |||
| self.reply(self.data, msg1.format(short, url)) | |||
| self.say(self.data.chan, msg2.format(status)) | |||
| self.say(self.data.chan, msg3.format(user_name, user_url)) | |||
| def get_status(self, page): | |||
| if page.is_redirect(): | |||
| @@ -49,7 +49,7 @@ class Command(BaseCommand): | |||
| if data.line[1] == "JOIN": | |||
| status = " ".join(("\x02Current status:\x0F", self.get_status())) | |||
| self.connection.notice(data.nick, status) | |||
| self.notice(data.nick, status) | |||
| return | |||
| if data.args: | |||
| @@ -57,17 +57,17 @@ class Command(BaseCommand): | |||
| if action.startswith("sub") or action == "s": | |||
| subs = self.count_submissions() | |||
| msg = "there are \x0305{0}\x0301 pending AfC submissions (\x0302WP:AFC\x0301)." | |||
| self.connection.reply(data, msg.format(subs)) | |||
| self.reply(data, msg.format(subs)) | |||
| elif action.startswith("redir") or action == "r": | |||
| redirs = self.count_redirects() | |||
| msg = "there are \x0305{0}\x0301 open redirect requests (\x0302WP:AFC/R\x0301)." | |||
| self.connection.reply(data, msg.format(redirs)) | |||
| self.reply(data, msg.format(redirs)) | |||
| elif action.startswith("file") or action == "f": | |||
| files = self.count_redirects() | |||
| msg = "there are \x0305{0}\x0301 open file upload requests (\x0302WP:FFU\x0301)." | |||
| self.connection.reply(data, msg.format(files)) | |||
| self.reply(data, msg.format(files)) | |||
| elif action.startswith("agg") or action == "a": | |||
| try: | |||
| @@ -78,21 +78,21 @@ class Command(BaseCommand): | |||
| agg_num = self.get_aggregate_number(agg_data) | |||
| except ValueError: | |||
| msg = "\x0303{0}\x0301 isn't a number!" | |||
| self.connection.reply(data, msg.format(data.args[1])) | |||
| self.reply(data, msg.format(data.args[1])) | |||
| return | |||
| aggregate = self.get_aggregate(agg_num) | |||
| msg = "aggregate is \x0305{0}\x0301 (AfC {1})." | |||
| self.connection.reply(data, msg.format(agg_num, aggregate)) | |||
| self.reply(data, msg.format(agg_num, aggregate)) | |||
| elif action.startswith("nocolor") or action == "n": | |||
| self.connection.reply(data, self.get_status(color=False)) | |||
| self.reply(data, self.get_status(color=False)) | |||
| else: | |||
| msg = "unknown argument: \x0303{0}\x0301. Valid args are 'subs', 'redirs', 'files', 'agg', 'nocolor'." | |||
| self.connection.reply(data, msg.format(data.args[0])) | |||
| self.reply(data, msg.format(data.args[0])) | |||
| else: | |||
| self.connection.reply(data, self.get_status()) | |||
| self.reply(data, self.get_status()) | |||
| def get_status(self, color=True): | |||
| subs = self.count_submissions() | |||
| @@ -32,7 +32,7 @@ class Command(BaseCommand): | |||
| def process(self, data): | |||
| if not data.args: | |||
| self.connection.reply(data, "what do you want me to calculate?") | |||
| self.reply(data, "what do you want me to calculate?") | |||
| return | |||
| query = ' '.join(data.args) | |||
| @@ -47,7 +47,7 @@ class Command(BaseCommand): | |||
| match = r_result.search(result) | |||
| if not match: | |||
| self.connection.reply(data, "Calculation error.") | |||
| self.reply(data, "Calculation error.") | |||
| return | |||
| result = match.group(1) | |||
| @@ -62,7 +62,7 @@ class Command(BaseCommand): | |||
| result += " " + query.split(" in ", 1)[1] | |||
| res = "%s = %s" % (query, result) | |||
| self.connection.reply(data, res) | |||
| self.reply(data, res) | |||
| def cleanup(self, query): | |||
| fixes = [ | |||
| @@ -23,32 +23,45 @@ | |||
| from earwigbot.commands import BaseCommand | |||
| class Command(BaseCommand): | |||
| """Voice, devoice, op, or deop users in the channel.""" | |||
| """Voice, devoice, op, or deop users in the channel, or join or part from | |||
| other channels.""" | |||
| name = "chanops" | |||
| def check(self, data): | |||
| commands = ["chanops", "voice", "devoice", "op", "deop"] | |||
| commands = ["chanops", "voice", "devoice", "op", "deop", "join", "part"] | |||
| if data.is_command and data.command in commands: | |||
| return True | |||
| return False | |||
| def process(self, data): | |||
| if data.command == "chanops": | |||
| msg = "available commands are !voice, !devoice, !op, and !deop." | |||
| self.connection.reply(data, msg) | |||
| msg = "available commands are !voice, !devoice, !op, !deop, !join, and !part." | |||
| self.reply(data, msg) | |||
| return | |||
| if data.host not in self.config.irc["permissions"]["admins"]: | |||
| msg = "you must be a bot admin to use this command." | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, "you must be a bot admin to use this command.") | |||
| return | |||
| # If it is just !op/!devoice/whatever without arguments, assume they | |||
| # want to do this to themselves: | |||
| if not data.args: | |||
| target = data.nick | |||
| else: | |||
| target = data.args[0] | |||
| if data.command in ["voice", "devoice", "op", "deop"]: | |||
| # If it is just !op/!devoice/whatever without arguments, assume they | |||
| # want to do this to themselves: | |||
| if not data.args: | |||
| target = data.nick | |||
| else: | |||
| target = data.args[0] | |||
| msg = " ".join((data.command, data.chan, target)) | |||
| self.connection.say("ChanServ", msg) | |||
| msg = " ".join((data.command, data.chan, target)) | |||
| self.say("ChanServ", msg) | |||
| else: | |||
| if not data.args: | |||
| msg = "you must specify a channel to join or part from." | |||
| self.reply(data, msg) | |||
| return | |||
| channel = data.args[0] | |||
| if not channel.startswith("#"): | |||
| channel = "#" + channel | |||
| if data.command == "join": | |||
| self.join(channel) | |||
| else: | |||
| self.part(channel) | |||
| @@ -39,12 +39,12 @@ class Command(BaseCommand): | |||
| def process(self, data): | |||
| if data.command == "crypt": | |||
| msg = "available commands are !hash, !encrypt, and !decrypt." | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| return | |||
| if not data.args: | |||
| msg = "what do you want me to {0}?".format(data.command) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| return | |||
| if data.command == "hash": | |||
| @@ -52,14 +52,14 @@ class Command(BaseCommand): | |||
| if algo == "list": | |||
| algos = ', '.join(hashlib.algorithms) | |||
| msg = algos.join(("supported algorithms: ", ".")) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| elif algo in hashlib.algorithms: | |||
| string = ' '.join(data.args[1:]) | |||
| result = getattr(hashlib, algo)(string).hexdigest() | |||
| self.connection.reply(data, result) | |||
| self.reply(data, result) | |||
| else: | |||
| msg = "unknown algorithm: '{0}'.".format(algo) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| else: | |||
| key = data.args[0] | |||
| @@ -67,14 +67,14 @@ class Command(BaseCommand): | |||
| if not text: | |||
| msg = "a key was provided, but text to {0} was not." | |||
| self.connection.reply(data, msg.format(data.command)) | |||
| self.reply(data, msg.format(data.command)) | |||
| return | |||
| try: | |||
| if data.command == "encrypt": | |||
| self.connection.reply(data, blowfish.encrypt(key, text)) | |||
| self.reply(data, blowfish.encrypt(key, text)) | |||
| else: | |||
| self.connection.reply(data, blowfish.decrypt(key, text)) | |||
| self.reply(data, blowfish.decrypt(key, text)) | |||
| except blowfish.BlowfishError as error: | |||
| msg = "{0}: {1}.".format(error.__class__.__name__, error) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| @@ -52,17 +52,17 @@ class Command(BaseCommand): | |||
| if command == "PING": | |||
| msg = " ".join(data.line[4:]) | |||
| if msg: | |||
| self.connection.notice(target, "\x01PING {0}\x01".format(msg)) | |||
| self.notice(target, "\x01PING {0}\x01".format(msg)) | |||
| else: | |||
| self.connection.notice(target, "\x01PING\x01") | |||
| self.notice(target, "\x01PING\x01") | |||
| elif command == "TIME": | |||
| ts = time.strftime("%a, %d %b %Y %H:%M:%S %Z", time.localtime()) | |||
| self.connection.notice(target, "\x01TIME {0}\x01".format(ts)) | |||
| self.notice(target, "\x01TIME {0}\x01".format(ts)) | |||
| elif command == "VERSION": | |||
| default = "EarwigBot - $1 - Python/$2 https://github.com/earwig/earwigbot" | |||
| vers = self.config.irc.get("version", default) | |||
| vers = vers.replace("$1", __version__) | |||
| vers = vers.replace("$2", platform.python_version()) | |||
| self.connection.notice(target, "\x01VERSION {0}\x01".format(vers)) | |||
| self.notice(target, "\x01VERSION {0}\x01".format(vers)) | |||
| @@ -49,10 +49,10 @@ class Command(BaseCommand): | |||
| count = user.editcount() | |||
| except wiki.UserNotFoundError: | |||
| msg = "the user \x0302{0}\x0301 does not exist." | |||
| self.connection.reply(data, msg.format(name)) | |||
| self.reply(data, msg.format(name)) | |||
| return | |||
| safe = quote_plus(user.name()) | |||
| url = "http://toolserver.org/~tparis/pcount/index.php?name={0}&lang=en&wiki=wikipedia" | |||
| msg = "\x0302{0}\x0301 has {1} edits ({2})." | |||
| self.connection.reply(data, msg.format(name, count, url.format(safe))) | |||
| self.reply(data, msg.format(name, count, url.format(safe))) | |||
| @@ -35,7 +35,7 @@ class Command(BaseCommand): | |||
| self.data = data | |||
| if data.host not in self.config.irc["permissions"]["owners"]: | |||
| msg = "you must be a bot owner to use this command." | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| return | |||
| if not data.args: | |||
| @@ -65,7 +65,7 @@ class Command(BaseCommand): | |||
| else: # They asked us to do something we don't know | |||
| msg = "unknown argument: \x0303{0}\x0301.".format(data.args[0]) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| def exec_shell(self, command): | |||
| """Execute a shell command and get the output.""" | |||
| @@ -89,13 +89,13 @@ class Command(BaseCommand): | |||
| for key in sorted(help.keys()): | |||
| msg += "\x0303{0}\x0301 ({1}), ".format(key, help[key]) | |||
| msg = msg[:-2] # Trim last comma and space | |||
| self.connection.reply(self.data, "sub-commands are: {0}.".format(msg)) | |||
| self.reply(self.data, "sub-commands are: {0}.".format(msg)) | |||
| def do_branch(self): | |||
| """Get our current branch.""" | |||
| branch = self.exec_shell("git name-rev --name-only HEAD") | |||
| msg = "currently on branch \x0302{0}\x0301.".format(branch) | |||
| self.connection.reply(self.data, msg) | |||
| self.reply(self.data, msg) | |||
| def do_branches(self): | |||
| """Get a list of branches.""" | |||
| @@ -106,14 +106,14 @@ class Command(BaseCommand): | |||
| branches = branches.replace('\n ', ', ') | |||
| branches = branches.strip() | |||
| msg = "branches: \x0302{0}\x0301.".format(branches) | |||
| self.connection.reply(self.data, msg) | |||
| self.reply(self.data, msg) | |||
| def do_checkout(self): | |||
| """Switch branches.""" | |||
| try: | |||
| branch = self.data.args[1] | |||
| except IndexError: # no branch name provided | |||
| self.connection.reply(self.data, "switch to which branch?") | |||
| self.reply(self.data, "switch to which branch?") | |||
| return | |||
| current_branch = self.exec_shell("git name-rev --name-only HEAD") | |||
| @@ -122,51 +122,51 @@ class Command(BaseCommand): | |||
| result = self.exec_shell("git checkout %s" % branch) | |||
| if "Already on" in result: | |||
| msg = "already on \x0302{0}\x0301!".format(branch) | |||
| self.connection.reply(self.data, msg) | |||
| self.reply(self.data, msg) | |||
| else: | |||
| ms = "switched from branch \x0302{1}\x0301 to \x0302{1}\x0301." | |||
| msg = ms.format(current_branch, branch) | |||
| self.connection.reply(self.data, msg) | |||
| self.reply(self.data, msg) | |||
| except subprocess.CalledProcessError: | |||
| # Git couldn't switch branches; assume the branch doesn't exist: | |||
| msg = "branch \x0302{0}\x0301 doesn't exist!".format(branch) | |||
| self.connection.reply(self.data, msg) | |||
| self.reply(self.data, msg) | |||
| def do_delete(self): | |||
| """Delete a branch, while making sure that we are not already on it.""" | |||
| try: | |||
| delete_branch = self.data.args[1] | |||
| except IndexError: # no branch name provided | |||
| self.connection.reply(self.data, "delete which branch?") | |||
| self.reply(self.data, "delete which branch?") | |||
| return | |||
| current_branch = self.exec_shell("git name-rev --name-only HEAD") | |||
| if current_branch == delete_branch: | |||
| msg = "you're currently on this branch; please checkout to a different branch before deleting." | |||
| self.connection.reply(self.data, msg) | |||
| self.reply(self.data, msg) | |||
| return | |||
| try: | |||
| self.exec_shell("git branch -d %s" % delete_branch) | |||
| msg = "branch \x0302{0}\x0301 has been deleted locally." | |||
| self.connection.reply(self.data, msg.format(delete_branch)) | |||
| self.reply(self.data, msg.format(delete_branch)) | |||
| except subprocess.CalledProcessError: | |||
| # Git couldn't switch branches; assume the branch doesn't exist: | |||
| msg = "branch \x0302{0}\x0301 doesn't exist!".format(delete_branch) | |||
| self.connection.reply(self.data, msg) | |||
| self.reply(self.data, msg) | |||
| def do_pull(self): | |||
| """Pull from our remote repository.""" | |||
| branch = self.exec_shell("git name-rev --name-only HEAD") | |||
| msg = "pulling from remote (currently on \x0302{0}\x0301)..." | |||
| self.connection.reply(self.data, msg.format(branch)) | |||
| self.reply(self.data, msg.format(branch)) | |||
| result = self.exec_shell("git pull") | |||
| if "Already up-to-date." in result: | |||
| self.connection.reply(self.data, "done; no new changes.") | |||
| self.reply(self.data, "done; no new changes.") | |||
| else: | |||
| regex = "\s*((.*?)\sfile(.*?)tions?\(-\))" | |||
| changes = re.findall(regex, result)[0][0] | |||
| @@ -176,11 +176,11 @@ class Command(BaseCommand): | |||
| cmnd_url = "git config --get remote.{0}.url".format(remote) | |||
| url = self.exec_shell(cmnd_url) | |||
| msg = "done; {0} [from {1}].".format(changes, url) | |||
| self.connection.reply(self.data, msg) | |||
| self.reply(self.data, msg) | |||
| except subprocess.CalledProcessError: | |||
| # Something in .git/config is not specified correctly, so we | |||
| # cannot get the remote's URL. However, pull was a success: | |||
| self.connection.reply(self.data, "done; %s." % changes) | |||
| self.reply(self.data, "done; %s." % changes) | |||
| def do_status(self): | |||
| """Check whether we have anything to pull.""" | |||
| @@ -188,7 +188,7 @@ class Command(BaseCommand): | |||
| result = self.exec_shell("git fetch --dry-run") | |||
| if not result: # Nothing was fetched, so remote and local are equal | |||
| msg = "last commit was {0}. Local copy is \x02up-to-date\x0F with remote." | |||
| self.connection.reply(self.data, msg.format(last)) | |||
| self.reply(self.data, msg.format(last)) | |||
| else: | |||
| msg = "last local commit was {0}. Remote is \x02ahead\x0F of local copy." | |||
| self.connection.reply(self.data, msg.format(last)) | |||
| self.reply(self.data, msg.format(last)) | |||
| @@ -40,7 +40,7 @@ class Command(BaseCommand): | |||
| msg = "Hi, I'm a bot! I have {0} commands loaded: {1}. You can get help for any command with '!help <command>'." | |||
| cmnds = sorted(self.bot.commands) | |||
| msg = msg.format(len(cmnds), ', '.join(cmnds)) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| def do_command_help(self, data): | |||
| """Give the user help for a specific command.""" | |||
| @@ -60,9 +60,9 @@ class Command(BaseCommand): | |||
| doc = cmnd.__doc__.replace("\n", "") | |||
| doc = re.sub("\s\s+", " ", doc) | |||
| msg = "help for command \x0303{0}\x0301: \"{1}\"" | |||
| self.connection.reply(data, msg.format(command, doc)) | |||
| self.reply(data, msg.format(command, doc)) | |||
| return | |||
| break | |||
| msg = "sorry, no help for \x0303{0}\x0301.".format(command) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| @@ -43,15 +43,15 @@ class Command(BaseCommand): | |||
| if re.search("(\[\[(.*?)\]\])|(\{\{(.*?)\}\})", msg): | |||
| links = self.parse_line(msg) | |||
| links = " , ".join(links) | |||
| self.connection.reply(data, links) | |||
| self.reply(data, links) | |||
| elif data.command == "link": | |||
| if not data.args: | |||
| self.connection.reply(data, "what do you want me to link to?") | |||
| self.reply(data, "what do you want me to link to?") | |||
| return | |||
| pagename = ' '.join(data.args) | |||
| link = self.parse_link(pagename) | |||
| self.connection.reply(data, link) | |||
| self.reply(data, link) | |||
| def parse_line(self, line): | |||
| results = [] | |||
| @@ -45,7 +45,7 @@ class Command(BaseCommand): | |||
| msg = "You use this command to praise certain people. Who they are is a secret." | |||
| else: | |||
| msg = "You're doing it wrong." | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| return | |||
| self.connection.say(data.chan, msg) | |||
| self.say(data.chan, msg) | |||
| @@ -33,8 +33,7 @@ class Command(BaseCommand): | |||
| def process(self, data): | |||
| if data.host not in self.config.irc["permissions"]["owners"]: | |||
| msg = "you must be a bot owner to use this command." | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, "you must be a bot owner to use this command.") | |||
| return | |||
| if data.command == "quit": | |||
| self.do_quit(data) | |||
| @@ -46,7 +45,7 @@ class Command(BaseCommand): | |||
| def do_quit(self, data): | |||
| nick = self.config.irc.frontend["nick"] | |||
| if not data.args or data.args[0].lower() != nick.lower(): | |||
| self.connection.reply(data, "to confirm this action, the first argument must be my nickname.") | |||
| self.reply(data, "to confirm this action, the first argument must be my nickname.") | |||
| return | |||
| if data.args[1:]: | |||
| msg = " ".join(data.args[1:]) | |||
| @@ -66,4 +65,4 @@ class Command(BaseCommand): | |||
| self.logger.info("Reloading IRC commands and bot tasks") | |||
| self.bot.commands.load() | |||
| self.bot.tasks.load() | |||
| self.connection.reply(data, "IRC commands and bot tasks reloaded.") | |||
| self.reply(data, "IRC commands and bot tasks reloaded.") | |||
| @@ -30,7 +30,7 @@ class Command(BaseCommand): | |||
| name = "registration" | |||
| def check(self, data): | |||
| commands = ["registration", "age"] | |||
| commands = ["registration", "reg", "age"] | |||
| if data.is_command and data.command in commands: | |||
| return True | |||
| return False | |||
| @@ -49,7 +49,7 @@ class Command(BaseCommand): | |||
| reg = user.registration() | |||
| except wiki.UserNotFoundError: | |||
| msg = "the user \x0302{0}\x0301 does not exist." | |||
| self.connection.reply(data, msg.format(name)) | |||
| self.reply(data, msg.format(name)) | |||
| return | |||
| date = time.strftime("%b %d, %Y at %H:%M:%S UTC", reg) | |||
| @@ -64,7 +64,7 @@ class Command(BaseCommand): | |||
| gender = "They're" | |||
| msg = "\x0302{0}\x0301 registered on {1}. {2} {3} old." | |||
| self.connection.reply(data, msg.format(name, date, gender, age)) | |||
| self.reply(data, msg.format(name, date, gender, age)) | |||
| def get_diff(self, t1, t2): | |||
| parts = {"years": 31536000, "days": 86400, "hours": 3600, | |||
| @@ -37,19 +37,19 @@ class Command(BaseCommand): | |||
| def process(self, data): | |||
| if not data.args: | |||
| msg = "please specify a time (in seconds) and a message in the following format: !remind <time> <msg>." | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| return | |||
| try: | |||
| wait = int(data.args[0]) | |||
| except ValueError: | |||
| msg = "the time must be given as an integer, in seconds." | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| return | |||
| message = ' '.join(data.args[1:]) | |||
| if not message: | |||
| msg = "what message do you want me to give you when time is up?" | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| return | |||
| end = time.localtime(time.time() + wait) | |||
| @@ -58,7 +58,7 @@ class Command(BaseCommand): | |||
| msg = 'Set reminder for "{0}" in {1} seconds (ends {2}).' | |||
| msg = msg.format(message, wait, end_time_with_timezone) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| t_reminder = threading.Thread(target=self.reminder, | |||
| args=(data, message, wait)) | |||
| @@ -68,4 +68,4 @@ class Command(BaseCommand): | |||
| def reminder(self, data, message, wait): | |||
| time.sleep(wait) | |||
| self.connection.reply(data, message) | |||
| self.reply(data, message) | |||
| @@ -47,4 +47,4 @@ class Command(BaseCommand): | |||
| conn.close() | |||
| msg = "Replag on \x0302{0}\x0301 is \x02{1}\x0F seconds." | |||
| self.connection.reply(data, msg.format(args["db"], replag)) | |||
| self.reply(data, msg.format(args["db"], replag)) | |||
| @@ -47,7 +47,7 @@ class Command(BaseCommand): | |||
| rights = user.groups() | |||
| except wiki.UserNotFoundError: | |||
| msg = "the user \x0302{0}\x0301 does not exist." | |||
| self.connection.reply(data, msg.format(name)) | |||
| self.reply(data, msg.format(name)) | |||
| return | |||
| try: | |||
| @@ -55,4 +55,4 @@ class Command(BaseCommand): | |||
| except ValueError: | |||
| pass | |||
| msg = "the rights for \x0302{0}\x0301 are {1}." | |||
| self.connection.reply(data, msg.format(name, ', '.join(rights))) | |||
| self.reply(data, msg.format(name, ', '.join(rights))) | |||
| @@ -29,8 +29,9 @@ class Command(BaseCommand): | |||
| name = "test" | |||
| def process(self, data): | |||
| user = "\x02{0}\x0F".format(data.nick) | |||
| hey = random.randint(0, 1) | |||
| if hey: | |||
| self.connection.say(data.chan, "Hey \x02%s\x0F!" % data.nick) | |||
| self.say(data.chan, "Hey {0}!".format(user)) | |||
| else: | |||
| self.connection.say(data.chan, "'sup \x02%s\x0F?" % data.nick) | |||
| self.say(data.chan, "'sup {0}?".format(user)) | |||
| @@ -40,7 +40,7 @@ class Command(BaseCommand): | |||
| self.data = data | |||
| if data.host not in self.config.irc["permissions"]["owners"]: | |||
| msg = "you must be a bot owner to use this command." | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| return | |||
| if not data.args: | |||
| @@ -48,7 +48,7 @@ class Command(BaseCommand): | |||
| self.do_list() | |||
| else: | |||
| msg = "no arguments provided. Maybe you wanted '!{0} list', '!{0} start', or '!{0} listall'?" | |||
| self.connection.reply(data, msg.format(data.command)) | |||
| self.reply(data, msg.format(data.command)) | |||
| return | |||
| if data.args[0] == "list": | |||
| @@ -62,7 +62,7 @@ class Command(BaseCommand): | |||
| else: # They asked us to do something we don't know | |||
| msg = "unknown argument: \x0303{0}\x0301.".format(data.args[0]) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| def do_list(self): | |||
| """With !tasks list (or abbreviation !tasklist), list all running | |||
| @@ -98,7 +98,7 @@ class Command(BaseCommand): | |||
| msg = "\x02{0}\x0F threads active: {1}, and \x020\x0F task threads." | |||
| msg = msg.format(len(threads), ', '.join(normal_threads)) | |||
| self.connection.reply(self.data, msg) | |||
| self.reply(self.data, msg) | |||
| def do_listall(self): | |||
| """With !tasks listall or !tasks all, list all loaded tasks, and report | |||
| @@ -120,7 +120,7 @@ class Command(BaseCommand): | |||
| tasks = ", ".join(tasklist) | |||
| msg = "{0} tasks loaded: {1}.".format(len(tasklist), tasks) | |||
| self.connection.reply(self.data, msg) | |||
| self.reply(self.data, msg) | |||
| def do_start(self): | |||
| """With !tasks start, start any loaded task by name with or without | |||
| @@ -130,23 +130,23 @@ class Command(BaseCommand): | |||
| try: | |||
| task_name = data.args[1] | |||
| except IndexError: # No task name given | |||
| self.connection.reply(data, "what task do you want me to start?") | |||
| self.reply(data, "what task do you want me to start?") | |||
| return | |||
| try: | |||
| data.parse_kwargs() | |||
| except KwargParseException, arg: | |||
| msg = "error parsing argument: \x0303{0}\x0301.".format(arg) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| return | |||
| if task_name not in self.bot.tasks: | |||
| # This task does not exist or hasn't been loaded: | |||
| msg = "task could not be found; either it doesn't exist, or it wasn't loaded correctly." | |||
| self.connection.reply(data, msg.format(task_name)) | |||
| self.reply(data, msg.format(task_name)) | |||
| return | |||
| data.kwargs["fromIRC"] = True | |||
| self.bot.tasks.start(task_name, **data.kwargs) | |||
| msg = "task \x0302{0}\x0301 started.".format(task_name) | |||
| self.connection.reply(data, msg) | |||
| self.reply(data, msg) | |||
| @@ -118,9 +118,9 @@ class IRCConnection(object): | |||
| msg = "PART {0}".format(chan) | |||
| self._send(msg) | |||
| def mode(self, chan, level, msg): | |||
| def mode(self, target, level, msg): | |||
| """Send a mode message to the server.""" | |||
| msg = "MODE {0} {1} {2}".format(chan, level, msg) | |||
| msg = "MODE {0} {1} {2}".format(target, level, msg) | |||
| self._send(msg) | |||
| def pong(self, target): | |||