Skip to content

Commit 16e7aff

Browse files
Implement bot parameter for AutocompleteContext and implement get_autocomplete_context
1 parent 3d16786 commit 16e7aff

File tree

3 files changed

+56
-16
lines changed

3 files changed

+56
-16
lines changed

discord/bot.py

Lines changed: 35 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@
5454
UserCommand,
5555
ApplicationCommand,
5656
ApplicationContext,
57+
AutocompleteContext,
5758
command,
5859
)
5960
from .cog import CogMixin
@@ -431,7 +432,9 @@ async def process_application_commands(self, interaction: Interaction) -> None:
431432
self.dispatch("unknown_command", interaction)
432433
else:
433434
if interaction.type is InteractionType.auto_complete:
434-
return await command.invoke_autocomplete_callback(interaction)
435+
ctx = await self.get_autocomplete_context(interaction)
436+
ctx.command = command
437+
return await command.invoke_autocomplete_callback(ctx)
435438

436439
ctx = await self.get_application_context(interaction)
437440
ctx.command = command
@@ -567,6 +570,37 @@ class be provided, it must be similar enough to
567570
cls = ApplicationContext
568571
return cls(self, interaction)
569572

573+
async def get_autocomplete_context(
574+
self, interaction: Interaction, cls=None
575+
) -> AutocompleteContext:
576+
r"""|coro|
577+
578+
Returns the autocomplete context from the interaction.
579+
580+
This is a more low-level counter-part for :meth:`.process_application_commands`
581+
to allow users more fine grained control over the processing.
582+
583+
Parameters
584+
-----------
585+
interaction: :class:`discord.Interaction`
586+
The interaction to get the invocation context from.
587+
cls
588+
The factory class that will be used to create the context.
589+
By default, this is :class:`.AutocompleteContext`. Should a custom
590+
class be provided, it must be similar enough to
591+
:class:`.AutocompleteContext`\'s interface.
592+
593+
Returns
594+
--------
595+
:class:`.AutocompleteContext`
596+
The autocomplete context. The type of this can change via the
597+
``cls`` parameter.
598+
"""
599+
if cls is None:
600+
cls = AutocompleteContext
601+
return cls(self, interaction)
602+
603+
570604

571605
class BotBase(ApplicationCommandMixin, CogMixin):
572606
_supports_prefixed_commands = False

discord/commands/commands.py

Lines changed: 11 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -527,17 +527,19 @@ async def _invoke(self, ctx: ApplicationContext) -> None:
527527
else:
528528
await self.callback(ctx, **kwargs)
529529

530-
async def invoke_autocomplete_callback(self, interaction: Interaction):
530+
async def invoke_autocomplete_callback(self, ctx: AutocompleteContext):
531531
values = { i.name: i.default for i in self.options }
532532

533-
for op in interaction.data.get("options", []):
533+
for op in ctx.interaction.data.get("options", []):
534534
if op.get("focused", False):
535535
option = find(lambda o: o.name == op["name"], self.options)
536536
values.update({
537537
i["name"]:i["value"]
538-
for i in interaction.data["options"]
538+
for i in ctx.interaction.data["options"]
539539
})
540-
ctx = AutocompleteContext(interaction, command=self, focused=option, value=op.get("value"), options=values)
540+
ctx.focused = option
541+
ctx.value = op.get("value")
542+
ctx.options = values
541543
if asyncio.iscoroutinefunction(option.autocomplete):
542544
result = await option.autocomplete(ctx)
543545
else:
@@ -547,7 +549,7 @@ async def invoke_autocomplete_callback(self, interaction: Interaction):
547549
o if isinstance(o, OptionChoice) else OptionChoice(o)
548550
for o in result
549551
][:25]
550-
return await interaction.response.send_autocomplete_result(choices=choices)
552+
return await ctx.interaction.response.send_autocomplete_result(choices=choices)
551553

552554

553555
def copy(self):
@@ -786,11 +788,11 @@ async def _invoke(self, ctx: ApplicationContext) -> None:
786788
ctx.interaction.data = option
787789
await command.invoke(ctx)
788790

789-
async def invoke_autocomplete_callback(self, interaction: Interaction) -> None:
790-
option = interaction.data["options"][0]
791+
async def invoke_autocomplete_callback(self, ctx: AutocompleteContext) -> None:
792+
option = ctx.interaction.data["options"][0]
791793
command = find(lambda x: x.name == option["name"], self.subcommands)
792-
interaction.data = option
793-
await command.invoke_autocomplete_callback(interaction)
794+
ctx.interaction.data = option
795+
await command.invoke_autocomplete_callback(ctx)
794796

795797

796798
class ContextMenuCommand(ApplicationCommand):

discord/commands/context.py

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -155,6 +155,8 @@ class AutocompleteContext:
155155
156156
Attributes
157157
-----------
158+
bot: :class:`.Bot`
159+
The bot that the command belongs to.
158160
interaction: :class:`.Interaction`
159161
The interaction object that invoked the autocomplete.
160162
command: :class:`.ApplicationCommand`
@@ -167,14 +169,16 @@ class AutocompleteContext:
167169
A name to value mapping of the options that the user has selected before this option.
168170
"""
169171

170-
__slots__ = ("interaction", "command", "focused", "value", "options")
172+
__slots__ = ("bot", "interaction", "command", "focused", "value", "options")
171173

172-
def __init__(self, interaction: Interaction, *, command: ApplicationCommand, focused: Option, value: str, options: dict) -> None:
174+
def __init__(self, bot: Bot, interaction: Interaction) -> None:
175+
self.bot = bot
173176
self.interaction = interaction
174-
self.command = command
175-
self.focused = focused
176-
self.value = value
177-
self.options = options
177+
178+
# self.command = command
179+
# self.focused = focused
180+
# self.value = value
181+
# self.options = options
178182

179183
@property
180184
def cog(self) -> Optional[Cog]:

0 commit comments

Comments
 (0)