From bd3dd9fa32a4f871b7033f0d322e5b675d51b8b1 Mon Sep 17 00:00:00 2001 From: Anubhav1603 Date: Tue, 29 Sep 2020 13:41:59 +0530 Subject: added source command --- bot/exts/evergreen/source.py | 126 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 126 insertions(+) create mode 100644 bot/exts/evergreen/source.py (limited to 'bot/exts/evergreen/source.py') diff --git a/bot/exts/evergreen/source.py b/bot/exts/evergreen/source.py new file mode 100644 index 00000000..164430e2 --- /dev/null +++ b/bot/exts/evergreen/source.py @@ -0,0 +1,126 @@ +import inspect +from pathlib import Path +from typing import Optional, Tuple, Union + +from discord import Embed +from discord.ext import commands + +from bot.constants import Source + +SourceType = Union[commands.HelpCommand, commands.Command, commands.Cog, str, commands.ExtensionNotLoaded] + + +class SourceConverter(commands.Converter): + """Convert an argument into a help command, tag, command, or cog.""" + + async def convert(self, ctx: commands.Context, argument: str) -> SourceType: + """Convert argument into source object.""" + cog = ctx.bot.get_cog(argument) + if cog: + return cog + + cmd = ctx.bot.get_command(argument) + if cmd: + return cmd + + raise commands.BadArgument( + f"Unable to convert `{argument}` to valid command or Cog." + ) + + +class BotSource(commands.Cog): + """Displays information about the bot's source code.""" + + def __init__(self, bot: commands.Bot): + self.bot = bot + + @commands.command(name="source", aliases=("src",)) + async def source_command(self, ctx: commands.Context, *, source_item: SourceConverter = None) -> None: + """Display information and a GitHub link to the source code of a command, tag, or cog.""" + if not source_item: + embed = Embed(title="Bot's GitHub Repository") + embed.add_field(name="Repository", value=f"[Go to GitHub]({Source.github})") + embed.set_thumbnail(url="https://avatars1.githubusercontent.com/u/9919") + await ctx.send(embed=embed) + return + + embed = await self.build_embed(source_item) + await ctx.send(embed=embed) + + def get_source_link(self, source_item: SourceType) -> Tuple[str, str, Optional[int]]: + """ + Build GitHub link of source item, return this link, file location and first line number. + + Raise BadArgument if `source_item` is a dynamically-created object (e.g. via internal eval). + """ + if isinstance(source_item, commands.Command): + if source_item.cog_name == "Alias": + cmd_name = source_item.callback.__name__.replace("_alias", "") + cmd = self.bot.get_command(cmd_name.replace("_", " ")) + src = cmd.callback.__code__ + filename = src.co_filename + else: + src = source_item.callback.__code__ + filename = src.co_filename + else: + src = type(source_item) + try: + filename = inspect.getsourcefile(src) + except TypeError: + raise commands.BadArgument("Cannot get source for a dynamically-created object.") + + if not isinstance(source_item, str): + try: + lines, first_line_no = inspect.getsourcelines(src) + except OSError: + raise commands.BadArgument("Cannot get source for a dynamically-created object.") + + lines_extension = f"#L{first_line_no}-L{first_line_no+len(lines)-1}" + else: + first_line_no = None + lines_extension = "" + + # Handle tag file location differently than others to avoid errors in some cases + if not first_line_no: + file_location = Path(filename).relative_to("/bot/") + else: + file_location = Path(filename).relative_to(Path.cwd()).as_posix() + + url = f"{Source.github}/blob/master/{file_location}{lines_extension}" + + return url, file_location, first_line_no or None + + async def build_embed(self, source_object: SourceType) -> Optional[Embed]: + """Build embed based on source object.""" + url, location, first_line = self.get_source_link(source_object) + + if isinstance(source_object, commands.HelpCommand): + title = "Help Command" + description = source_object.__doc__.splitlines()[1] + elif isinstance(source_object, commands.Command): + if source_object.cog_name == "Alias": + cmd_name = source_object.callback.__name__.replace("_alias", "") + cmd = self.bot.get_command(cmd_name.replace("_", " ")) + description = cmd.short_doc + else: + description = source_object.short_doc + + title = f"Command: {source_object.qualified_name}" + elif isinstance(source_object, str): + title = f"Tag: {source_object}" + description = "" + else: + title = f"Cog: {source_object.qualified_name}" + description = source_object.description.splitlines()[0] + + embed = Embed(title=title, description=description) + embed.add_field(name="Source Code", value=f"[Go to GitHub]({url})") + line_text = f":{first_line}" if first_line else "" + embed.set_footer(text=f"{location}{line_text}") + + return embed + + +def setup(bot: commands.Bot) -> None: + """Load the BotSource cog.""" + bot.add_cog(BotSource(bot)) -- cgit v1.2.3 From e1e0e158e0b42b2bdb488646e8e86cb4a704c683 Mon Sep 17 00:00:00 2001 From: Anubhav1603 Date: Thu, 1 Oct 2020 10:52:45 +0530 Subject: added source command --- bot/exts/evergreen/source.py | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) (limited to 'bot/exts/evergreen/source.py') diff --git a/bot/exts/evergreen/source.py b/bot/exts/evergreen/source.py index 164430e2..62b5f6bb 100644 --- a/bot/exts/evergreen/source.py +++ b/bot/exts/evergreen/source.py @@ -15,6 +15,9 @@ class SourceConverter(commands.Converter): async def convert(self, ctx: commands.Context, argument: str) -> SourceType: """Convert argument into source object.""" + if argument.lower().startswith("help"): + return ctx.bot.help_command + cog = ctx.bot.get_cog(argument) if cog: return cog @@ -38,9 +41,9 @@ class BotSource(commands.Cog): async def source_command(self, ctx: commands.Context, *, source_item: SourceConverter = None) -> None: """Display information and a GitHub link to the source code of a command, tag, or cog.""" if not source_item: - embed = Embed(title="Bot's GitHub Repository") + embed = Embed(title="Seasonal Bot's GitHub Repository") embed.add_field(name="Repository", value=f"[Go to GitHub]({Source.github})") - embed.set_thumbnail(url="https://avatars1.githubusercontent.com/u/9919") + embed.set_thumbnail(url="https://github.githubassets.com/images/modules/logos_page/GitHub-Mark.png") await ctx.send(embed=embed) return @@ -114,6 +117,7 @@ class BotSource(commands.Cog): description = source_object.description.splitlines()[0] embed = Embed(title=title, description=description) + embed.set_thumbnail(url="https://github.githubassets.com/images/modules/logos_page/GitHub-Mark.png") embed.add_field(name="Source Code", value=f"[Go to GitHub]({url})") line_text = f":{first_line}" if first_line else "" embed.set_footer(text=f"{location}{line_text}") -- cgit v1.2.3 From 696dce383d4fddb9fe1767ce014a1ca264a8758b Mon Sep 17 00:00:00 2001 From: Anubhav1603 Date: Fri, 2 Oct 2020 19:15:08 +0530 Subject: removed aliases and default help command --- bot/exts/evergreen/source.py | 37 ++++++++++--------------------------- 1 file changed, 10 insertions(+), 27 deletions(-) (limited to 'bot/exts/evergreen/source.py') diff --git a/bot/exts/evergreen/source.py b/bot/exts/evergreen/source.py index 62b5f6bb..206cf258 100644 --- a/bot/exts/evergreen/source.py +++ b/bot/exts/evergreen/source.py @@ -7,7 +7,7 @@ from discord.ext import commands from bot.constants import Source -SourceType = Union[commands.HelpCommand, commands.Command, commands.Cog, str, commands.ExtensionNotLoaded] +SourceType = Union[commands.Command, commands.Cog, str, commands.ExtensionNotLoaded] class SourceConverter(commands.Converter): @@ -15,9 +15,6 @@ class SourceConverter(commands.Converter): async def convert(self, ctx: commands.Context, argument: str) -> SourceType: """Convert argument into source object.""" - if argument.lower().startswith("help"): - return ctx.bot.help_command - cog = ctx.bot.get_cog(argument) if cog: return cog @@ -43,7 +40,7 @@ class BotSource(commands.Cog): if not source_item: embed = Embed(title="Seasonal Bot's GitHub Repository") embed.add_field(name="Repository", value=f"[Go to GitHub]({Source.github})") - embed.set_thumbnail(url="https://github.githubassets.com/images/modules/logos_page/GitHub-Mark.png") + embed.set_thumbnail(url=Source.github_avatar_url) await ctx.send(embed=embed) return @@ -57,14 +54,8 @@ class BotSource(commands.Cog): Raise BadArgument if `source_item` is a dynamically-created object (e.g. via internal eval). """ if isinstance(source_item, commands.Command): - if source_item.cog_name == "Alias": - cmd_name = source_item.callback.__name__.replace("_alias", "") - cmd = self.bot.get_command(cmd_name.replace("_", " ")) - src = cmd.callback.__code__ - filename = src.co_filename - else: - src = source_item.callback.__code__ - filename = src.co_filename + src = source_item.callback.__code__ + filename = src.co_filename else: src = type(source_item) try: @@ -97,27 +88,19 @@ class BotSource(commands.Cog): """Build embed based on source object.""" url, location, first_line = self.get_source_link(source_object) - if isinstance(source_object, commands.HelpCommand): - title = "Help Command" - description = source_object.__doc__.splitlines()[1] - elif isinstance(source_object, commands.Command): - if source_object.cog_name == "Alias": - cmd_name = source_object.callback.__name__.replace("_alias", "") - cmd = self.bot.get_command(cmd_name.replace("_", " ")) - description = cmd.short_doc + if isinstance(source_object, commands.Command): + if source_object.cog_name == 'Help': + title = "Help Command" + description = source_object.__doc__.splitlines()[1] else: description = source_object.short_doc - - title = f"Command: {source_object.qualified_name}" - elif isinstance(source_object, str): - title = f"Tag: {source_object}" - description = "" + title = f"Command: {source_object.qualified_name}" else: title = f"Cog: {source_object.qualified_name}" description = source_object.description.splitlines()[0] embed = Embed(title=title, description=description) - embed.set_thumbnail(url="https://github.githubassets.com/images/modules/logos_page/GitHub-Mark.png") + embed.set_thumbnail(url=Source.github_avatar_url) embed.add_field(name="Source Code", value=f"[Go to GitHub]({url})") line_text = f":{first_line}" if first_line else "" embed.set_footer(text=f"{location}{line_text}") -- cgit v1.2.3 From 2a415d883fa79d9c421cec07becf7c1f846788da Mon Sep 17 00:00:00 2001 From: Anubhav1603 Date: Sun, 4 Oct 2020 12:35:37 +0530 Subject: removed tag handling --- bot/exts/evergreen/source.py | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) (limited to 'bot/exts/evergreen/source.py') diff --git a/bot/exts/evergreen/source.py b/bot/exts/evergreen/source.py index 206cf258..0725714f 100644 --- a/bot/exts/evergreen/source.py +++ b/bot/exts/evergreen/source.py @@ -74,11 +74,7 @@ class BotSource(commands.Cog): first_line_no = None lines_extension = "" - # Handle tag file location differently than others to avoid errors in some cases - if not first_line_no: - file_location = Path(filename).relative_to("/bot/") - else: - file_location = Path(filename).relative_to(Path.cwd()).as_posix() + file_location = Path(filename).relative_to(Path.cwd()).as_posix() url = f"{Source.github}/blob/master/{file_location}{lines_extension}" -- cgit v1.2.3