Filtering command usages¶
A command's execution can be rejected by filters, the filter type depends on the command type and must be registered as a service.
They can be used globally (for all commands of the same type), or applied to individual commands.
Implementation¶
A single class can implement multiple filters.
Text commands¶
Filtering text commands to only run in a specific channel
private const val CHANNEL_ID = 722891685755093076
@BService
class TextGeneralChannelFilter : TextCommandFilter {
// So we can apply this filter on specific commands
override val global: Boolean get() = false
override fun check(event: MessageReceivedEvent, commandVariation: TextCommandVariation, args: String): String? {
if (event.getChannel().idLong != CHANNEL_ID) {
event.message
.reply("This command can only be used in <#$CHANNEL_ID>")
.queue()
return "Text command was used in the wrong channel"
}
// Correct channel, return no error message
return null
}
}
@BService
@NullMarked // Everything is non-null unless @Nullable
public class TextGeneralChannelFilter implements TextCommandFilter {
private static final long CHANNEL_ID = 722891685755093076L;
@Override
public boolean getGlobal() {
// So we can apply this filter on specific commands
return false;
}
@Nullable
@Override
public String check(MessageReceivedEvent event, TextCommandVariation commandVariation, String args) {
if (event.getChannel().getIdLong() != CHANNEL_ID) {
event.getMessage()
.reply("This command can only be used in <#" + CHANNEL_ID + ">")
.queue();
return "Text command was used in the wrong channel";
}
// Correct channel, return no error message
return null;
}
}
Application commands¶
Filtering application commands to only run in a specific channel
We'll keep the same example for the sake of consistency, but with application commands, guild managers should restrict your application in Discord, to avoid showing unusable commands.
private const val CHANNEL_ID = 722891685755093076
@BService
class AppGeneralChannelFilter : ApplicationCommandFilter {
// So we can apply this filter on specific commands
override val global: Boolean get() = false
override fun check(event: GenericCommandInteractionEvent, commandInfo: ApplicationCommandInfo): String? {
if (event.channelIdLong != CHANNEL_ID) {
event.reply("This command can only be used in <#$CHANNEL_ID>").queue()
return "Application command was used in the wrong channel"
}
// Correct channel, return no error message
return null
}
}
@BService
@NullMarked // Everything is non-null unless @Nullable
public class AppGeneralChannelFilter implements ApplicationCommandFilter {
private static final long CHANNEL_ID = 722891685755093076L;
@Override
public boolean getGlobal() {
// So we can apply this filter on specific commands
return false;
}
@Nullable
@Override
public String check(GenericCommandInteractionEvent event, ApplicationCommandInfo commandInfo) {
if (event.getChannelIdLong() != CHANNEL_ID) {
event.reply("This command can only be used in <#" + CHANNEL_ID + ">")
.setEphemeral(true)
.queue();
return "Application command was used in the wrong channel";
}
// Correct channel, return no error message
return null;
}
}
Usage¶
This section only applies to non-global filters.
Annotated commands¶
Annotate your command with @Filter and specify your filter's type.
Declarative commands¶
Use the filter function in your command builder. (app commands, text commands)