From b46e0483fb8691cd52c0efed2d2d74cc19b0fa34 Mon Sep 17 00:00:00 2001 From: univ Date: Tue, 13 Feb 2018 15:39:46 +0000 Subject: [PATCH 01/14] added formatter.py --- bot/cogs/formatter.py | 8 ++++++++ 1 file changed, 8 insertions(+) create mode 100644 bot/cogs/formatter.py diff --git a/bot/cogs/formatter.py b/bot/cogs/formatter.py new file mode 100644 index 0000000000..81a4901de4 --- /dev/null +++ b/bot/cogs/formatter.py @@ -0,0 +1,8 @@ +# coding=utf-8 +from discord.ext.commands import HelpFormatter, Paginator + +class Formatter(HelpFormatter): + def __init__(self, *args, **kwargs): + super().__init__(*args, **kwargs) + + \ No newline at end of file From 5aaa68c481d9bbb2e8de2699760eb4a99e02ed5d Mon Sep 17 00:00:00 2001 From: univ Date: Tue, 13 Feb 2018 15:58:47 +0000 Subject: [PATCH 02/14] added main help and modulestring --- bot/cogs/formatter.py | 49 ++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 48 insertions(+), 1 deletion(-) diff --git a/bot/cogs/formatter.py b/bot/cogs/formatter.py index 81a4901de4..d5cf8ba60a 100644 --- a/bot/cogs/formatter.py +++ b/bot/cogs/formatter.py @@ -1,8 +1,55 @@ # coding=utf-8 + +""" +Credit to Rapptz's script used as an example: +https://github.com/Rapptz/discord.py/blob/rewrite/discord/ext/commands/formatter.py +Which falls under The MIT License. +""" + +import itertools + from discord.ext.commands import HelpFormatter, Paginator class Formatter(HelpFormatter): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) - \ No newline at end of file + # basically the same function but changed: + # - to make the helptext appear as a comment + # - to change the indentation to the PEP8 standard: 4 spaces + def _add_subcommands_to_page(self, max_width, commands): + for name, command in commands: + if name in command.aliases: + # skip aliases + continue + + entry = " {0:<{width}} # {1}".format(name, command.short_doc, width=max_width) + shortened = self.shorten(entry) + self._paginator.add_line(shortened) + + async def format(self): + self._paginator = Paginator(prefix="```py") + + max_width = self.max_name_size + + def category_check(tup): + cog = tup[1].cog_name + # zero width character to make it appear last when put in alphabetical order + return cog if cog is not None else "\u200bNoCategory" + + command_list = await self.filter_command_list() + data = sorted(command_list, key=category_check) + + for category, commands in itertools.groupby(data, key=category_check): + commands = sorted(commands) + if len(commands) > 0: + self._paginator.add_line(f"class {category}:") + self._add_subcommands_to_page(max_width, commands) + + self._paginator.add_line() + ending_note = self.get_ending_note() + # make the ending note appear as comments + ending_note = "# "+ending_note.replace("\n", "\n# ") + self._paginator.add_line(ending_note) + + return self._paginator.pages \ No newline at end of file From 72ec2f8b7f5ab581efb00def8d0cc72e8fc9d758 Mon Sep 17 00:00:00 2001 From: univ Date: Tue, 13 Feb 2018 15:59:30 +0000 Subject: [PATCH 03/14] added help for specific commands --- bot/cogs/formatter.py | 29 +++++++++++++++++++++++++++++ 1 file changed, 29 insertions(+) diff --git a/bot/cogs/formatter.py b/bot/cogs/formatter.py index d5cf8ba60a..5999e891b3 100644 --- a/bot/cogs/formatter.py +++ b/bot/cogs/formatter.py @@ -30,6 +30,35 @@ def _add_subcommands_to_page(self, max_width, commands): async def format(self): self._paginator = Paginator(prefix="```py") + if isinstance(self.command, Command): + # help on a specific command to look like an async function + + # example: + # async def (ctx, ): + # """ + # + # """ + # await do_(ctx, ) + + # strip the command of bot. and () + stripped_command = self.command.name.replace(PREFIX, "").replace("()", "") + # getting args using the handy inspect module + argspec = getfullargspec(self.command.callback) + arguments = formatargspec(*argspec) + args_no_type_hints = ", ".join(argspec[0]) + # remove self from the arguments + arguments = arguments.replace("self, ", "") + args_no_type_hints = args_no_type_hints.replace("self, ", "") + # first line of help containing the command name and arguments + definition = f"async def {stripped_command}{arguments}:" + self._paginator.add_line(definition) + # next few lines containing the help text formatted as a docstring + self._paginator.add_line(f" \"\"\"\n {self.command.help}\n \"\"\"") + # last line 'invoking' the command + self._paginator.add_line(f" await do_{stripped_command}({args_no_type_hints})") + + return self._paginator.pages + max_width = self.max_name_size def category_check(tup): From 5e66d20ac64f0a69a6a18132795e00caeeae11db Mon Sep 17 00:00:00 2001 From: univ Date: Tue, 13 Feb 2018 16:02:07 +0000 Subject: [PATCH 04/14] fixed imports and added new constant --- bot/cogs/formatter.py | 6 ++++-- bot/constants.py | 2 ++ 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/bot/cogs/formatter.py b/bot/cogs/formatter.py index 5999e891b3..1cb33680c0 100644 --- a/bot/cogs/formatter.py +++ b/bot/cogs/formatter.py @@ -8,7 +8,9 @@ import itertools -from discord.ext.commands import HelpFormatter, Paginator +from discord.ext.commands import HelpFormatter, Paginator, Command +from inspect import getfullargspec, formatargspec +from constants import HELP_PREFIX class Formatter(HelpFormatter): def __init__(self, *args, **kwargs): @@ -41,7 +43,7 @@ async def format(self): # await do_(ctx, ) # strip the command of bot. and () - stripped_command = self.command.name.replace(PREFIX, "").replace("()", "") + stripped_command = self.command.name.replace(HELP_PREFIX, "").replace("()", "") # getting args using the handy inspect module argspec = getfullargspec(self.command.callback) arguments = formatargspec(*argspec) diff --git a/bot/constants.py b/bot/constants.py index e11a625ac5..d6c94511a8 100644 --- a/bot/constants.py +++ b/bot/constants.py @@ -9,3 +9,5 @@ MODERATOR_ROLE = 267629731250176001 VERIFIED_ROLE = 352427296948486144 OWNER_ROLE = 267627879762755584 + +HELP_PREFIX = "bot." \ No newline at end of file From 51deeeb5a2151cc6f12c8ea52a18c4a3c8a4f954 Mon Sep 17 00:00:00 2001 From: univ Date: Tue, 13 Feb 2018 16:02:58 +0000 Subject: [PATCH 05/14] fixed broken import again --- bot/cogs/formatter.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bot/cogs/formatter.py b/bot/cogs/formatter.py index 1cb33680c0..5d371bdf99 100644 --- a/bot/cogs/formatter.py +++ b/bot/cogs/formatter.py @@ -10,7 +10,7 @@ from discord.ext.commands import HelpFormatter, Paginator, Command from inspect import getfullargspec, formatargspec -from constants import HELP_PREFIX +from bot.constants import HELP_PREFIX class Formatter(HelpFormatter): def __init__(self, *args, **kwargs): From 3b0aeb5da041dea0b01dfcee4556514c64442c22 Mon Sep 17 00:00:00 2001 From: univ Date: Tue, 13 Feb 2018 16:05:00 +0000 Subject: [PATCH 06/14] added example --- bot/cogs/formatter.py | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/bot/cogs/formatter.py b/bot/cogs/formatter.py index 5d371bdf99..56f25fbd63 100644 --- a/bot/cogs/formatter.py +++ b/bot/cogs/formatter.py @@ -61,6 +61,14 @@ async def format(self): return self._paginator.pages + # if not a specific command, help page will be in the format: + # class : + # bot.() # + # class : + # bot.() # + # + # # + max_width = self.max_name_size def category_check(tup): From 71c558776628bd010fb90abe9a8191f92b3865a9 Mon Sep 17 00:00:00 2001 From: univ Date: Tue, 13 Feb 2018 16:06:36 +0000 Subject: [PATCH 07/14] moved formatter.py to correct dir, and changed __main__.py to use the formatter --- bot/__main__.py | 4 +++- bot/{cogs => }/formatter.py | 0 2 files changed, 3 insertions(+), 1 deletion(-) rename bot/{cogs => }/formatter.py (100%) diff --git a/bot/__main__.py b/bot/__main__.py index 6d5c2c063d..306e33ff54 100644 --- a/bot/__main__.py +++ b/bot/__main__.py @@ -5,6 +5,7 @@ from discord.ext.commands import AutoShardedBot, when_mentioned_or from bot.utils import CaseInsensitiveDict +from bot.formatter import Formatter bot = AutoShardedBot( command_prefix=when_mentioned_or( @@ -14,7 +15,8 @@ ">>>", ">>", ">" ), # Order matters (and so do commas) game=Game(name="Help: bot.help()"), - help_attrs={"aliases": ["help()"]} + help_attrs={"aliases": ["help()"]}, + formatter=Formatter() ) bot.cogs = CaseInsensitiveDict() diff --git a/bot/cogs/formatter.py b/bot/formatter.py similarity index 100% rename from bot/cogs/formatter.py rename to bot/formatter.py From 1ed81764325468ee3566acbb6c76655f0c723b4e Mon Sep 17 00:00:00 2001 From: univ Date: Tue, 13 Feb 2018 16:17:52 +0000 Subject: [PATCH 08/14] reordered imports on __main__.py --- bot/__main__.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bot/__main__.py b/bot/__main__.py index 306e33ff54..2c9bf4db3a 100644 --- a/bot/__main__.py +++ b/bot/__main__.py @@ -4,8 +4,8 @@ from discord import Game from discord.ext.commands import AutoShardedBot, when_mentioned_or -from bot.utils import CaseInsensitiveDict from bot.formatter import Formatter +from bot.utils import CaseInsensitiveDict bot = AutoShardedBot( command_prefix=when_mentioned_or( From f6fe8c862e89be441ff8445056f5e9e176e16591 Mon Sep 17 00:00:00 2001 From: Sam W Date: Tue, 13 Feb 2018 16:34:15 +0000 Subject: [PATCH 09/14] fixed pylint errors --- bot/formatter.py | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/bot/formatter.py b/bot/formatter.py index 56f25fbd63..6b93ad4b71 100644 --- a/bot/formatter.py +++ b/bot/formatter.py @@ -8,8 +8,10 @@ import itertools -from discord.ext.commands import HelpFormatter, Paginator, Command -from inspect import getfullargspec, formatargspec +from inspect import formatargspec, getfullargspec + +from discord.ext.commands import Command, HelpFormatter, Paginator + from bot.constants import HELP_PREFIX class Formatter(HelpFormatter): @@ -91,4 +93,5 @@ def category_check(tup): ending_note = "# "+ending_note.replace("\n", "\n# ") self._paginator.add_line(ending_note) - return self._paginator.pages \ No newline at end of file + return self._paginator.pages + \ No newline at end of file From e9cbf2eda417fdf2ea3e75211cbbd1bd3776045b Mon Sep 17 00:00:00 2001 From: Sam W Date: Tue, 13 Feb 2018 16:41:19 +0000 Subject: [PATCH 10/14] fixed more pylint --- bot/constants.py | 2 +- bot/formatter.py | 3 +-- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/bot/constants.py b/bot/constants.py index d6c94511a8..9030a100eb 100644 --- a/bot/constants.py +++ b/bot/constants.py @@ -10,4 +10,4 @@ VERIFIED_ROLE = 352427296948486144 OWNER_ROLE = 267627879762755584 -HELP_PREFIX = "bot." \ No newline at end of file +HELP_PREFIX = "bot." diff --git a/bot/formatter.py b/bot/formatter.py index 6b93ad4b71..8fc5a84824 100644 --- a/bot/formatter.py +++ b/bot/formatter.py @@ -7,13 +7,13 @@ """ import itertools - from inspect import formatargspec, getfullargspec from discord.ext.commands import Command, HelpFormatter, Paginator from bot.constants import HELP_PREFIX + class Formatter(HelpFormatter): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) @@ -94,4 +94,3 @@ def category_check(tup): self._paginator.add_line(ending_note) return self._paginator.pages - \ No newline at end of file From 4b3eef1e5dbadce02acba3a33e80a4f4aed71089 Mon Sep 17 00:00:00 2001 From: Sam W Date: Tue, 13 Feb 2018 17:17:28 +0000 Subject: [PATCH 11/14] changed commented examples to docstrings --- bot/formatter.py | 43 +++++++++++++++++++++++-------------------- 1 file changed, 23 insertions(+), 20 deletions(-) diff --git a/bot/formatter.py b/bot/formatter.py index 8fc5a84824..e01c03b297 100644 --- a/bot/formatter.py +++ b/bot/formatter.py @@ -18,10 +18,12 @@ class Formatter(HelpFormatter): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) - # basically the same function but changed: - # - to make the helptext appear as a comment - # - to change the indentation to the PEP8 standard: 4 spaces def _add_subcommands_to_page(self, max_width, commands): + """ + basically the same function from d.py but changed: + - to make the helptext appear as a comment + - to change the indentation to the PEP8 standard: 4 spaces + """ for name, command in commands: if name in command.aliases: # skip aliases @@ -32,18 +34,27 @@ def _add_subcommands_to_page(self, max_width, commands): self._paginator.add_line(shortened) async def format(self): + """ + rewritten help command to make it more python-y + + example of specific command: + async def (ctx, ): + \""" + + \""" + await do_(ctx, ) + + example of standard help page: + class : + bot.() # + class : + bot.() # + + # + """ self._paginator = Paginator(prefix="```py") if isinstance(self.command, Command): - # help on a specific command to look like an async function - - # example: - # async def (ctx, ): - # """ - # - # """ - # await do_(ctx, ) - # strip the command of bot. and () stripped_command = self.command.name.replace(HELP_PREFIX, "").replace("()", "") # getting args using the handy inspect module @@ -63,14 +74,6 @@ async def format(self): return self._paginator.pages - # if not a specific command, help page will be in the format: - # class : - # bot.() # - # class : - # bot.() # - # - # # - max_width = self.max_name_size def category_check(tup): From d02a4faf555e1cb2e3763d8420379a2f3adff971 Mon Sep 17 00:00:00 2001 From: Sam W Date: Tue, 13 Feb 2018 17:19:22 +0000 Subject: [PATCH 12/14] fixed styling (again) --- bot/formatter.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bot/formatter.py b/bot/formatter.py index e01c03b297..fe97b550a0 100644 --- a/bot/formatter.py +++ b/bot/formatter.py @@ -49,7 +49,7 @@ class : bot.() # class : bot.() # - + # """ self._paginator = Paginator(prefix="```py") From 252fa75f40d8f1a5c0f0d45b98b592d238933b54 Mon Sep 17 00:00:00 2001 From: Sam W Date: Tue, 13 Feb 2018 17:33:41 +0000 Subject: [PATCH 13/14] changed the way command names are shown (due to the change in command names for the command wrappers) --- bot/formatter.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/bot/formatter.py b/bot/formatter.py index fe97b550a0..d3dd883496 100644 --- a/bot/formatter.py +++ b/bot/formatter.py @@ -29,7 +29,7 @@ def _add_subcommands_to_page(self, max_width, commands): # skip aliases continue - entry = " {0:<{width}} # {1}".format(name, command.short_doc, width=max_width) + entry = " {0}{1:<{width}} # {2}".format(HELP_PREFIX, name, command.short_doc, width=max_width) shortened = self.shorten(entry) self._paginator.add_line(shortened) @@ -56,7 +56,7 @@ class : if isinstance(self.command, Command): # strip the command of bot. and () - stripped_command = self.command.name.replace(HELP_PREFIX, "").replace("()", "") + stripped_command = self.command.name.replace("()", "") # getting args using the handy inspect module argspec = getfullargspec(self.command.callback) arguments = formatargspec(*argspec) From 3b54d65f33fa9be3f12c97a2d5f9e1579d6bf439 Mon Sep 17 00:00:00 2001 From: Sam W Date: Tue, 13 Feb 2018 17:39:38 +0000 Subject: [PATCH 14/14] added type hinting, and rearranged some code for readability --- bot/formatter.py | 21 ++++++++++++--------- 1 file changed, 12 insertions(+), 9 deletions(-) diff --git a/bot/formatter.py b/bot/formatter.py index d3dd883496..503ae331d3 100644 --- a/bot/formatter.py +++ b/bot/formatter.py @@ -18,7 +18,7 @@ class Formatter(HelpFormatter): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) - def _add_subcommands_to_page(self, max_width, commands): + def _add_subcommands_to_page(self, max_width: int, commands: list): """ basically the same function from d.py but changed: - to make the helptext appear as a comment @@ -56,21 +56,24 @@ class : if isinstance(self.command, Command): # strip the command of bot. and () - stripped_command = self.command.name.replace("()", "") - # getting args using the handy inspect module + stripped_command = self.command.name.replace(HELP_PREFIX, "").replace("()", "") + + # get the args using the handy inspect module argspec = getfullargspec(self.command.callback) arguments = formatargspec(*argspec) args_no_type_hints = ", ".join(argspec[0]) - # remove self from the arguments + + # remove self from the args arguments = arguments.replace("self, ", "") args_no_type_hints = args_no_type_hints.replace("self, ", "") - # first line of help containing the command name and arguments + + # prepare the different sections of the help output, and add them to the paginator definition = f"async def {stripped_command}{arguments}:" + docstring = f" \"\"\"\n {self.command.help}\n \"\"\"" + invocation = f" await do_{stripped_command}({args_no_type_hints})" self._paginator.add_line(definition) - # next few lines containing the help text formatted as a docstring - self._paginator.add_line(f" \"\"\"\n {self.command.help}\n \"\"\"") - # last line 'invoking' the command - self._paginator.add_line(f" await do_{stripped_command}({args_no_type_hints})") + self._paginator.add_line(docstring) + self._paginator.add_line(invocation) return self._paginator.pages