discord.py
discord.py copied to clipboard
Analogues to `command_*` events for application commands
Summary
Add events such as application_command_error
and application_command_completion
to mimic the command_error
and command_completion
events of text commands.
What is the feature request for?
The core library
The Problem
I personally liked to use the command_completion
event as a way to build some statistics for how often a command gets used (only counting successful uses). The normal event listener from discord.ext.commands
works perfectly for this.
However, a similar event for application commands doesn't exist, nor does the command_error
analogue, which is useful in the error handling process.
The Ideal Solution
Having events dispatched that are equivalent in purpose would be the ideal solution, especially if their listeners were as simple to use as the on_command_completion
and on_command_error
ones, i.e., on_application_command_completion
and on_application_command_error
.
They could possibly be added for other Interaction types, or maybe as one generic event overall (interaction_completion
?).
The Current Solution
None.
Additional Context
I don't know if there is a structural reason for these events to not exist or if there is some usable solution (I didn't find any when searching through issues, discussions, or the Discord server).
@MajorTanya There exists a similar listener on_interaction
@MajorTanya There exists a similar listener
on_interaction
Thanks! You're right, but that fires on all invocations of an interaction, right? I was wondering specifically about one that “guarantees” an error / successful completion, like on_command_completion
.
This feature request is common and is something I was aware about even before I published any of the changes. The problems are mainly design and future proofing. The problems I need to resolve are as follows:
- The command framework cheats a bit by adding extra events that have nothing to do with Discord for the sake of usability. In contrast, every event that
discord.Client
dispatches corresponds to at least one gateway event from Discord or from the protocol. There are no library specific events being dispatched by this mechanism. The library specific events are instead done as "hooks" such assetup_hook
andbefore_identify_hook
. - Creating events related to application commands means that there will be possible conflict whenever Discord decides to add events for application commands, some of these have already existed but were removed. Right now there is one Discord dispatch event for application commands for permissions being updated.
- There already exists
on_interaction
foron_app_command
andCommandTree.on_error
foron_app_command_error
. You're right that there's a glaring omission foron_app_command_completion
. - The interaction with hybrid commands would need to be thought out. For example, if you invoke a hybrid command's application command counterpart right now the
on_command_completion
/on_command_error
/on_command
events are dispatched. Should the equivalenton_app_command
ones be called as well?
Thank you for the in-depth response, I didn't know about all those factors before.
- Creating events related to application commands means that there will be possible conflict whenever Discord decides to add events for application commands, some of these have already existed but were removed. [...]
An “easy” solution would be to prepend the events with a dpy
or something and make the events look like DPY_APP_CMD_COMPLETED
/ handlers like on_dpy_app_command_completed
. It would make them immune from immediately breaking Discord changes, though I'm aware that this approach is too icky and breaks with library consistency 😅.
- The interaction with hybrid commands would need to be thought out. For example, if you invoke a hybrid command's application command counterpart right now the
on_command_completion
/on_command_error
/on_command
events are dispatched. Should the equivalenton_app_command
ones be called as well?
It would probably be necessary to call both to avoid unexpected behaviour, but could another option be to only call the handler of the variant invoked?
So if the Hybrid gets called as a Slash Command, it could trigger on_app_command_completion
but if it gets used as a classic Command, it could trigger on_command_completion
.
This way, a command completion doesn't get handled in duplicate, and the triggered one is always type-appropriate. It would also make the library overall more consistent (from my viewpoint at least), considering that Hybrids currently only call the classic handlers.
I'm not sure how this approach could cause problems (other than the new behaviour that would require getting used to by developers?), but I'm sure there are many possibilities.
If they are used as clean-up hooks or similar, developers would maybe need to duplicate code / create methods for them?
My ideas might be too simplistic though, just trying to figure it out