async def _source(self, ctx: commands.Context, command: str, start: typing.Optional[int], end: typing.Optional[int]): """ display the source of a command examples: `>source owner` :: show the full source of `owner` `>source owner 2` :: show line `2` of `owner` `>source owner 3 5` :: show lines 3-5 of `owner` """ command = ctx.bot.get_command(command) if (not command): await ctx.bot.send_help(ctx) return if (not await command.can_run(ctx)): await ctx.bot.send_help(ctx) return if (start): if ((end) and ((start < 1) or (start > end))): raise commands.BadArgument() else: # show all start, end = 1, -1 source = inspect.getsource(command.callback) source = format.get_lines(source, start, end) message = format.dedent(source) message = message.replace("```", "``") for (page) in format.pagify(message, shorten_by=10): if (page): await ctx.send("```py\n{0}```".format(page))
async def _unicode(self, ctx: commands.Context, *, characters: str): """ show unicode information on a character example: `>unicode :zero:` :: \\U00000030\\U000020e3 """ message = "" max_ = max([len(character) for (character) in characters]) for (character) in characters: digit = "{0:x}".format(ord(character)) name = unicodedata.name(character, "unknown name") # fix weird bug with the enclosing keycap if (name in ["COMBINING ENCLOSING KEYCAP", "ZERO WIDTH SPACE"]): i = " " else: i = "" message += "\u200b {0:>{width}} {1} \\U{2:>08} \\N{{{3}}}\n".format( character, i, digit, name, width=max_ ) for (page) in format.pagify(message, shorten_by=8): if (page): await ctx.send("```\n{0}```".format(page))
async def _roll(self, ctx: commands.Context, count: int = 1, sides: int = 6): """ roll count die with sides english is hard examples: `>roll` :: roll `one`, `six` sided die `>roll 2` :: roll `two`, `six` sided dice `>roll 3 10` :: roll `three`, `ten` sided dice """ if ((count < 1) or (sides < 1)): await ctx.bot.send_help(ctx) return rolls = list() for (_) in range(count): roll = random.randint(1, sides) rolls.append(str(roll)) message = ", ".join(rolls) for (page) in format.pagify(message, delims=[" "]): if (page): await ctx.send(page)
async def _github_issue_list(self, ctx: commands.Context): """ list open issues """ # https://developer.github.com/v3/issues/#list-issues-for-a-repository url = "repos/ShineyDev/sbt/issues" async with ctx.typing(): try: issues = await self.request("GET", url) except (GitHubError) as e: await ctx.send("`{0}: {1}`".format(type(e).__name__, str(e))) return message = "" for (issue) in issues: if (issue.get("pull_request")): # not an issue, i will never understand why prs show as # issues ¯\_(ツ)_/¯ continue elif (issue.get("state") == "closed"): continue url = format.wrap_url(issue.get("html_url")) message += "{0}\n".format(url) if (not message): await ctx.send("there are no open issues") return for (page) in format.pagify(message): if (page): await ctx.send(page)
async def _dis(self, ctx: commands.Context, *, command: str): """ display the disassembled source of a command example: `>dis owner` :: show the disassembled source of `owner` """ command = ctx.bot.get_command(command) if (not command): await ctx.bot.send_help(ctx) return if (not await command.can_run(ctx)): await ctx.bot.send_help(ctx) return message = dis.Bytecode(command.callback).dis() if (not message): await ctx.bot.send_help(ctx) return message = message.replace("```", "``") for (page) in format.pagify(message, shorten_by=8): if (page): await ctx.send("```\n{0}```".format(page))
async def list(self, ctx): """displays a list of all users on your server""" msg = "" for member in self.bot.guild.members: msg += f"{member.display_name} - created at {member.created_at} - joined at {member.joined_at}\n" for page in fmt.pagify(msg, delims=["\n#"], page_length=1990): await self.bot.sendc(ctx, fmt.box(page, "md"))
async def list(self, ctx): """ list all current timed messages """ to_send = "" with self.bot.session_scope() as session: msgs = TimedMessage.get_all_from_guild(ctx.guild.id, session) for msg in msgs: to_send += f"{str(msg)}\n\n" for page in pagify(to_send, delims=["\n#"], page_length=1990): await self.bot.sendc(ctx, box(page, "md"))
async def _loaded_extensions(self, ctx: commands.Context): """ show loaded extensions """ message = "" for (extension_name, extension) in ctx.bot.cogs.items(): message += "{0}\n".format(extension_name) for (page) in format.pagify(message, shorten_by=8): if (page): await ctx.send("```\n{0}```".format(page))
async def _loaded_imports(self, ctx: commands.Context): """ show loaded imports """ message = "" for (module_) in sys.modules: message += "{0}\n".format(module_) for (page) in format.pagify(message, shorten_by=8): if (page): await ctx.send("```\n{0}```".format(page))
async def _spellout(self, ctx: commands.Context, *, text: str): """ s p e l l o u t text yeah i think you understand what this one does """ message = "" for (character) in text: message += "{0} ".format(character) for (page) in format.pagify(message, delims=[" "]): if (page): await ctx.send(page)
async def _list_sound_queue(self, ctx): """list current items in queue""" queue = self.bot.audio.list_queue(ctx.guild.id) msg = "" _index = 0 if queue is not None: for t in queue: msg += f"\n# Position {_index} #\n- " msg += f"{t.title}" _index = _index + 1 for page in fmt.pagify(msg, delims=["\n#"], page_length=1990): if page: await self.bot.sendc(ctx, fmt.box(page, "md")) else: await self.bot.sendc(ctx, fmt.box("Queue is empty."))
async def _github_issue_events(self, ctx: commands.Context, id: int): """ show events for an issue """ # https://developer.github.com/v3/issues/events/#list-events-for-an-issue url = "repos/ShineyDev/sbt/issues/{0}/events".format(id) async with ctx.typing(): try: events = await self.request("GET", url) except (GitHubError) as e: await ctx.send("`{0}: {1}`".format(type(e).__name__, str(e))) return # https://developer.github.com/v3/issues/#get-a-single-issue url = "repos/ShineyDev/sbt/issues/{0}".format(id) async with ctx.typing(): try: issue = await self.request("GET", url) except (GitHubError) as e: await ctx.send("`{0}: {1}`".format(type(e).__name__, str(e))) return message = "+ {0} opened this issue\n".format(issue["user"]["login"]) for (event) in events: if (event["event"] == "moved_columns_in_project"): # this will be here until github either remove the # `project_card` key from starfox-preview or remove the # `lock_reason` key from sailor-v-preview since we are # currently using sailor-v-preview to get access to the # `lock_reason` key continue if (event["event"] not in EVENT_MESSAGES.keys()): continue message += EVENT_MESSAGES[event["event"]].format(event) message += "\n" for (page) in format.pagify(message, shorten_by=12): if (page): await ctx.send("```diff\n{0}```".format(page))
async def list(self, ctx): """a list of all available tags""" self.bot.log.info("list") with self.bot.session_scope() as session: tags = Tag.get_all_from_guild(ctx.guild.id, session) msg = "" last_header = "^" for t in tags: if t.Name[0] is not last_header: last_header = t.Name[0] msg += f"\n# {last_header} #\n- " msg += f"[{t.Name}]" typ = TagType(t.Type).name.upper()[0] msg += f"({typ}|{t.entries.count()}) - " for page in fmt.pagify(msg, delims=["\n#"], page_length=1990): await self.bot.sendc(ctx, fmt.box(page, "md"))
async def _walk(self, ctx: commands.Context, module: str): """ walk a module example: `>walk information` """ message = "modules.{0}\n\n".format(module) module = ctx.bot.get_cog(module) if (not module): await ctx.bot.send_help(ctx) return command_ = None callbacks = list() for (command) in module.walk_commands(): if (command.callback.__name__ in callbacks): continue callbacks.append(command.callback.__name__) command_ = command width = len(command.qualified_name.split(" ")) - 1 indent = " " * width name = command.name aliases = "| {0}".format(" | ".join( command.aliases)) if command.aliases else "" enabled = "*" if command.enabled else " " hidden = "*" if command.hidden else " " message += "{0}{1:<{width}} {2:<32} | {3} | {4} |\n".format( indent, name, aliases, enabled, hidden, width=(20 - (width * 2))) for (page) in format.pagify(message, shorten_by=8): if (page): await ctx.send("```\n{0}```".format(page))
async def _whitelist(self, ctx: commands.Context): """ show the current whitelist """ if (not ctx.bot._settings.whitelist): await ctx.bot.send_help(ctx) return message = "" for (id) in ctx.bot._settings.whitelist: user = await ctx.bot.get_user(id) if (user): message += "{0} | {1}\n".format(id, user.name) else: message += "{0}\n".format(id) for (page) in format.pagify(message, shorten_by=8): if (page): await ctx.send("```\n{0}```".format(page))
async def _eval(self, ctx: commands.Context, *, shit: str): """ eval shit there is no better explanation of what this command does """ shit = shit.strip("`") shit = format.dedent(shit) if (shit.startswith("py\n")): shit = shit[3:] globals_ = globals().copy() globals_["self"] = self globals_["ctx"] = ctx for (i, result) in enumerate(self._results): globals_[f"_{i}"] = result if (hasattr(self, "_exception")): globals_["_x"] = self._exception function = "async def _evaluate(self):\n{0}".format( format.indent(shit, amount=4)) try: exec(function, globals_, locals()) result = await locals()["_evaluate"](self) except (Exception) as e: if (ctx.invoked_with == "repl"): return message = await ctx.send("`{0}: {1}`".format( type(e).__name__, str(e))) await ctx.message.add_reaction("\U0000274e") self._exception = e if (not checks.is_debugging_check(ctx)): await asyncio.sleep(5) await message.delete() await ctx.message.delete() return else: await ctx.message.add_reaction("\U00002705") if (result != None): result = str(result) result = (result.replace( ctx.bot._settings.github_api_key, "[REDACTED]").replace( ctx.bot._settings.google_api_key, "[REDACTED]").replace( ctx.bot._settings.google_engine_id, "[REDACTED]").replace(ctx.bot._settings.secret, "[REDACTED]").replace( ctx.bot._settings.token, "[REDACTED]")) for (page) in format.pagify(result, delims=["\n", ",", " "], shorten_by=8): if (page): page = await ctx.send("```\n{0}```".format(page))
async def _embed(self, ctx: commands.Context): """ create and edit an embed, then get either the json or the code given back to you :) """ previous = collections.deque(maxlen=3) current = format.embed() next = collections.deque(maxlen=3) message = await ctx.send(embed=current) keys = [ "title", "description", "color", "colour", "thumbnail", "author", "author_url", "author_icon_url", "field", "image", "footer", "footer_icon_url", ] reactions = [ "\U0001f4dd", "\U0001f4dc", "\U00002b05", "\U000027a1", "\U00002705", "\U0000267b", "\U0001f5d1", ] for (reaction) in reactions: await message.add_reaction(reaction) while (True): def check(reaction: discord.Reaction, member: discord.Member): if (member == ctx.author): if (reaction.message.id == message.id): if (str(reaction.emoji) in reactions): return True return False tasks = { asyncio.create_task( ctx.bot.wait_for("reaction_add", check=check, timeout=120)), asyncio.create_task( ctx.bot.wait_for("reaction_remove", check=check, timeout=120)), } done, pending = await asyncio.wait( tasks, return_when=asyncio.FIRST_COMPLETED) try: reaction, _ = done.pop().result() except (asyncio.TimeoutError) as e: await message.clear_reactions() ctx.command.reset_cooldown(ctx) return for (task) in pending: task.cancel() if (str(reaction.emoji) == reactions[0]): def check(message: discord.Message): if (message.author == ctx.author): if (message.channel == ctx.channel): if ("=" in message.content): if (message.content.split("=", 1)[0] in keys): if (message.content.startswith("field")): if (message.content.count("|") == 1): return True elif (message.content.count("|") == 2): _, _, inline = message.content.split( "|") if (inline.isdigit()): if (int(inline) in [0, 1]): return True else: return True elif (message.content == "field-"): return True try: message_ = await ctx.bot.wait_for("message", check=check, timeout=60) except (asyncio.TimeoutError) as e: await message.remove_reaction(str(reaction.emoji), ctx.author) continue else: if (message_.content == "field-"): if (len(current.fields) != 0): current.remove_field(len(current.fields) - 1) await message.edit(embed=current) else: key, value = message_.content.split("=", 1) if ((len(value) + len(current)) > 6000): await message_.delete() await message.remove_reaction( str(reaction.emoji), ctx.author) continue current_ = current.copy() try: if (key == "title"): if (len(value) <= 256): previous.append(current.copy()) current_.title = value next.clear() elif (key == "description"): previous.append(current.copy()) current_.description = value next.clear() elif ((key == "color") or (key == "colour")): if (len(value) == 3): value = "".join(i * 2 for i in value) if (len(value) == 6): try: color = int(value, 16) except (ValueError) as e: pass else: previous.append(current.copy()) current_.color = color next.clear() elif (key == "thumbnail"): previous.append(current.copy()) current_.set_thumbnail(url=value) next.clear() elif (key == "author"): if (len(value) <= 256): previous.append(current.copy()) current_.set_author( name=value, url=current.author.url, icon_url=current.author.icon_url) next.clear() elif (key == "author_url"): if (current.author.name != discord.Embed.Empty): previous.append(current.copy()) current_.set_author( name=current.author.name, url=value, icon_url=current.author.icon_url) next.clear() elif (key == "author_icon_url"): if (current.author.name != discord.Embed.Empty): previous.append(current.copy()) current_.set_author( name=current.author.name, url=current.author.url, icon_url=value) next.clear() elif (key == "field"): if (len(current.fields) < 25): if (value.count("|") == 1): name, value = value.split("|") if (len(name) <= 256): previous.append(current.copy()) current_.add_field(name=name, value=value) next.clear() else: name, value, inline = value.split("|") if (len(name) <= 256): previous.append(current.copy()) current_.add_field( name=name, value=value, inline=bool(int(inline))) next.clear() elif (key == "image"): previous.append(current.copy()) current_.set_image(url=value) next.clear() elif (key == "footer"): previous.append(current.copy()) current_.set_footer( text=value, icon_url=current.footer.icon_url) next.clear() elif (key == "footer_icon_url"): if (current.footer.text != discord.Embed.Empty): previous.append(current.copy()) current_.set_footer( text=current.footer.text, icon_url=value) next.clear() await message.edit(embed=current_) except (discord.HTTPException) as e: pass else: current = current_.copy() await message_.delete() elif (str(reaction.emoji) == reactions[1]): def check(message: discord.Message): if (message.author == ctx.author): if (message.channel == ctx.channel): try: json.loads(message.content, encoding="utf-8") return True except (json.JSONDecodeError) as e: pass try: message_ = await ctx.bot.wait_for("message", check=check, timeout=60) except (asyncio.TimeoutError) as e: await message.remove_reaction(str(reaction.emoji), ctx.author) continue else: json_ = json.loads(message_.content, encoding="utf-8") dict_ = current.to_dict() dict_.update(json_) previous.append(current.copy()) current = discord.Embed.from_dict(dict_) next.clear() await message.edit(embed=current) await message_.delete() elif (str(reaction.emoji) == reactions[2]): if (previous): next.appendleft(current.copy()) current = previous.pop() await message.edit(embed=current) elif (str(reaction.emoji) == reactions[3]): if (next): previous.append(current.copy()) current = next.popleft() await message.edit(embed=current) elif (str(reaction.emoji) == reactions[4]): await message.clear_reactions() json_ = current.to_dict() if (json_): json_ = json.dumps(json_, indent=2) for (page) in format.pagify(json_, shorten_by=8): await ctx.send("```\n{0}```".format(page)) ctx.command.reset_cooldown(ctx) return elif (str(reaction.emoji) == reactions[5]): previous.append(current.copy()) current = format.embed() next.clear() await message.edit(embed=current) elif (str(reaction.emoji) == reactions[6]): await message.delete() ctx.command.reset_cooldown(ctx) return await message.remove_reaction(str(reaction.emoji), ctx.author)
async def _debug(self, ctx: commands.Context, index: typing.Optional[int], *, shit: str): """ debug shit there is no better explanation of what this command does """ shit = shit.strip("`").strip() globals_ = globals().copy() globals_["self"] = self globals_["ctx"] = ctx for (i, result) in enumerate(self._results): globals_[f"_{i}"] = result if (hasattr(self, "_exception")): globals_["_x"] = self._exception try: result = eval(shit, globals_, locals()) except (Exception) as e: message = await ctx.send("`{0}: {1}`".format( type(e).__name__, str(e))) await ctx.message.add_reaction("\U0000274e") self._exception = e if (not checks.is_debugging_check(ctx)): await asyncio.sleep(5) await message.delete() await ctx.message.delete() return try: if (asyncio.iscoroutine(result)): result = await result except (Exception) as e: message = await ctx.send("`{0}: {1}`".format( type(e).__name__, str(e))) await ctx.message.add_reaction("\U0000274e") self._exception = e if (not checks.is_debugging_check(ctx)): await asyncio.sleep(5) await message.delete() await ctx.message.delete() return else: await ctx.message.add_reaction("\U00002705") if (index in range(len(self._results))): self._results[index] = result else: self._results.appendleft(result) if (result != None): result = str(result) result = (result.replace( ctx.bot._settings.github_api_key, "[REDACTED]").replace( ctx.bot._settings.google_api_key, "[REDACTED]").replace( ctx.bot._settings.google_engine_id, "[REDACTED]").replace(ctx.bot._settings.secret, "[REDACTED]").replace( ctx.bot._settings.token, "[REDACTED]")) for (page) in format.pagify(result, delims=["\n", ",", " "], shorten_by=8): if (page): page = await ctx.send("```\n{0}```".format(page))