mirror of
https://github.com/Sheldan/abstracto.git
synced 2026-07-05 20:30:01 +00:00
[AB-xxx] adding support for user installable apps to varying commands
This commit is contained in:
@@ -5,11 +5,13 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandParameterService;
|
import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandParameterService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.customcommand.config.CustomCommandFeatureDefinition;
|
import dev.sheldan.abstracto.customcommand.config.CustomCommandFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.customcommand.config.CustomCommandSlashCommandNames;
|
import dev.sheldan.abstracto.customcommand.config.CustomCommandSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.customcommand.service.management.CustomCommandService;
|
import dev.sheldan.abstracto.customcommand.service.management.CustomCommandService;
|
||||||
@@ -44,8 +46,11 @@ public class CreateCustomCommand extends AbstractConditionableCommand {
|
|||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
String name = slashCommandParameterService.getCommandOption(CUSTOM_COMMAND_NAME_PARAMETER, event, String.class);
|
String name = slashCommandParameterService.getCommandOption(CUSTOM_COMMAND_NAME_PARAMETER, event, String.class);
|
||||||
String content = slashCommandParameterService.getCommandOption(CUSTOM_COMMAND_CONTENT_PARAMETER, event, String.class);
|
String content = slashCommandParameterService.getCommandOption(CUSTOM_COMMAND_CONTENT_PARAMETER, event, String.class);
|
||||||
|
if(ContextUtils.isUserCommand(event)) {
|
||||||
customCommandService.createCustomCommand(name, content, event.getMember());
|
customCommandService.createUserCustomCommand(name, content, event.getUser());
|
||||||
|
} else {
|
||||||
|
customCommandService.createCustomCommand(name, content, event.getMember());
|
||||||
|
}
|
||||||
return interactionService.replyEmbed(CREATE_CUSTOM_COMMAND_RESPONSE_TEMPLATE_KEY, event)
|
return interactionService.replyEmbed(CREATE_CUSTOM_COMMAND_RESPONSE_TEMPLATE_KEY, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
}
|
}
|
||||||
@@ -80,6 +85,8 @@ public class CreateCustomCommand extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(CustomCommandSlashCommandNames.CUSTOM_COMMAND)
|
.rootCommandName(CustomCommandSlashCommandNames.CUSTOM_COMMAND)
|
||||||
.commandName("create")
|
.commandName("create")
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -5,11 +5,13 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandParameterService;
|
import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandParameterService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.customcommand.config.CustomCommandFeatureDefinition;
|
import dev.sheldan.abstracto.customcommand.config.CustomCommandFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.customcommand.config.CustomCommandSlashCommandNames;
|
import dev.sheldan.abstracto.customcommand.config.CustomCommandSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.customcommand.service.management.CustomCommandService;
|
import dev.sheldan.abstracto.customcommand.service.management.CustomCommandService;
|
||||||
@@ -42,8 +44,11 @@ public class DeleteCustomCommand extends AbstractConditionableCommand {
|
|||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
String name = slashCommandParameterService.getCommandOption(CUSTOM_COMMAND_NAME_PARAMETER, event, String.class);
|
String name = slashCommandParameterService.getCommandOption(CUSTOM_COMMAND_NAME_PARAMETER, event, String.class);
|
||||||
|
if(ContextUtils.isUserCommand(event)) {
|
||||||
customCommandService.deleteCustomCommand(name, event.getGuild());
|
customCommandService.deleteUserCustomCommand(name, event.getUser());
|
||||||
|
} else {
|
||||||
|
customCommandService.deleteCustomCommand(name, event.getGuild());
|
||||||
|
}
|
||||||
return interactionService.replyEmbed(DELETE_CUSTOM_COMMAND_RESPONSE_TEMPLATE_KEY, event)
|
return interactionService.replyEmbed(DELETE_CUSTOM_COMMAND_RESPONSE_TEMPLATE_KEY, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
}
|
}
|
||||||
@@ -66,6 +71,8 @@ public class DeleteCustomCommand extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(CustomCommandSlashCommandNames.CUSTOM_COMMAND)
|
.rootCommandName(CustomCommandSlashCommandNames.CUSTOM_COMMAND)
|
||||||
.commandName("delete")
|
.commandName("delete")
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -5,12 +5,14 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandAutoCompleteService;
|
import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandAutoCompleteService;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandParameterService;
|
import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandParameterService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.customcommand.config.CustomCommandFeatureDefinition;
|
import dev.sheldan.abstracto.customcommand.config.CustomCommandFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.customcommand.config.CustomCommandSlashCommandNames;
|
import dev.sheldan.abstracto.customcommand.config.CustomCommandSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.customcommand.model.command.CustomCommandResponseModel;
|
import dev.sheldan.abstracto.customcommand.model.command.CustomCommandResponseModel;
|
||||||
@@ -48,7 +50,12 @@ public class GetCustomCommand extends AbstractConditionableCommand {
|
|||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
String name = slashCommandParameterService.getCommandOption(CUSTOM_COMMAND_NAME_PARAMETER, event, String.class);
|
String name = slashCommandParameterService.getCommandOption(CUSTOM_COMMAND_NAME_PARAMETER, event, String.class);
|
||||||
CustomCommand customCommand = customCommandService.getCustomCommand(name, event.getGuild());
|
CustomCommand customCommand;
|
||||||
|
if(ContextUtils.isUserCommand(event)) {
|
||||||
|
customCommand = customCommandService.getUserCustomCommand(name, event.getUser());
|
||||||
|
} else {
|
||||||
|
customCommand = customCommandService.getCustomCommand(name, event.getGuild());
|
||||||
|
}
|
||||||
CustomCommandResponseModel model = CustomCommandResponseModel
|
CustomCommandResponseModel model = CustomCommandResponseModel
|
||||||
.builder()
|
.builder()
|
||||||
.additionalText(customCommand.getAdditionalMessage())
|
.additionalText(customCommand.getAdditionalMessage())
|
||||||
@@ -61,11 +68,17 @@ public class GetCustomCommand extends AbstractConditionableCommand {
|
|||||||
public List<String> performAutoComplete(CommandAutoCompleteInteractionEvent event) {
|
public List<String> performAutoComplete(CommandAutoCompleteInteractionEvent event) {
|
||||||
if(slashCommandAutoCompleteService.matchesParameter(event.getFocusedOption(), CUSTOM_COMMAND_NAME_PARAMETER)) {
|
if(slashCommandAutoCompleteService.matchesParameter(event.getFocusedOption(), CUSTOM_COMMAND_NAME_PARAMETER)) {
|
||||||
String input = event.getFocusedOption().getValue();
|
String input = event.getFocusedOption().getValue();
|
||||||
return customCommandService.getCustomCommandsStartingWith(input, event.getGuild())
|
if(ContextUtils.isNotUserCommand(event)) {
|
||||||
.stream()
|
return customCommandService.getCustomCommandsStartingWith(input, event.getGuild())
|
||||||
.map(CustomCommand::getName)
|
.stream()
|
||||||
.limit(25)
|
.map(CustomCommand::getName)
|
||||||
.toList();
|
.toList();
|
||||||
|
} else {
|
||||||
|
return customCommandService.getUserCustomCommandsStartingWith(input, event.getUser())
|
||||||
|
.stream()
|
||||||
|
.map(CustomCommand::getName)
|
||||||
|
.toList();
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
return new ArrayList<>();
|
return new ArrayList<>();
|
||||||
}
|
}
|
||||||
@@ -95,7 +108,10 @@ public class GetCustomCommand extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(CustomCommandSlashCommandNames.CUSTOM_COMMAND_PUBLIC)
|
.rootCommandName(CustomCommandSlashCommandNames.CUSTOM_COMMAND_PUBLIC)
|
||||||
|
.userRootCommandName(CustomCommandSlashCommandNames.CUSTOM_COMMAND)
|
||||||
.commandName("get")
|
.commandName("get")
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
|
|||||||
@@ -4,11 +4,13 @@ import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
|||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.service.PaginatorService;
|
import dev.sheldan.abstracto.core.service.PaginatorService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.customcommand.config.CustomCommandFeatureDefinition;
|
import dev.sheldan.abstracto.customcommand.config.CustomCommandFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.customcommand.config.CustomCommandSlashCommandNames;
|
import dev.sheldan.abstracto.customcommand.config.CustomCommandSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.customcommand.model.command.ListCustomCommandsResponseModel;
|
import dev.sheldan.abstracto.customcommand.model.command.ListCustomCommandsResponseModel;
|
||||||
@@ -42,7 +44,12 @@ public class ListCustomCommands extends AbstractConditionableCommand {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
List<CustomCommand> customCommands = customCommandService.getCustomCommands(event.getGuild());
|
List<CustomCommand> customCommands;
|
||||||
|
if(ContextUtils.isUserCommand(event)) {
|
||||||
|
customCommands = customCommandService.getUserCustomCommands(event.getUser());
|
||||||
|
} else {
|
||||||
|
customCommands = customCommandService.getCustomCommands(event.getGuild());
|
||||||
|
}
|
||||||
if(customCommands.isEmpty()) {
|
if(customCommands.isEmpty()) {
|
||||||
return interactionService.replyEmbed(NO_CUSTOM_COMMANDS_TEMPLATE_KEY, event)
|
return interactionService.replyEmbed(NO_CUSTOM_COMMANDS_TEMPLATE_KEY, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
@@ -67,7 +74,10 @@ public class ListCustomCommands extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(CustomCommandSlashCommandNames.CUSTOM_COMMAND_PUBLIC)
|
.rootCommandName(CustomCommandSlashCommandNames.CUSTOM_COMMAND_PUBLIC)
|
||||||
|
.userRootCommandName(CustomCommandSlashCommandNames.CUSTOM_COMMAND)
|
||||||
.commandName("list")
|
.commandName("list")
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package dev.sheldan.abstracto.customcommand.repository;
|
package dev.sheldan.abstracto.customcommand.repository;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AServer;
|
import dev.sheldan.abstracto.core.models.database.AServer;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.customcommand.model.database.CustomCommand;
|
import dev.sheldan.abstracto.customcommand.model.database.CustomCommand;
|
||||||
import org.springframework.data.jpa.repository.JpaRepository;
|
import org.springframework.data.jpa.repository.JpaRepository;
|
||||||
import org.springframework.stereotype.Repository;
|
import org.springframework.stereotype.Repository;
|
||||||
@@ -11,7 +12,12 @@ import java.util.Optional;
|
|||||||
@Repository
|
@Repository
|
||||||
public interface CustomCommandRepository extends JpaRepository<CustomCommand, Long> {
|
public interface CustomCommandRepository extends JpaRepository<CustomCommand, Long> {
|
||||||
Optional<CustomCommand> getByNameIgnoreCaseAndServer(String name, AServer server);
|
Optional<CustomCommand> getByNameIgnoreCaseAndServer(String name, AServer server);
|
||||||
|
Optional<CustomCommand> getByNameIgnoreCaseAndCreatorUser(String name, AUser creator);
|
||||||
|
Optional<CustomCommand> getByNameIgnoreCaseAndCreatorUser_IdAndUserSpecific(String name, Long userId, Boolean userSpecific);
|
||||||
void deleteByNameAndServer(String name, AServer server);
|
void deleteByNameAndServer(String name, AServer server);
|
||||||
|
void deleteByNameAndCreatorUserAndUserSpecific(String name, AUser aUser, Boolean userSpecific);
|
||||||
List<CustomCommand> findByServer(AServer server);
|
List<CustomCommand> findByServer(AServer server);
|
||||||
|
List<CustomCommand> findByCreatorUserAndUserSpecific(AUser user, Boolean userSpecific);
|
||||||
List<CustomCommand> findByNameStartsWithIgnoreCaseAndServer(String prefix, AServer server);
|
List<CustomCommand> findByNameStartsWithIgnoreCaseAndServer(String prefix, AServer server);
|
||||||
|
List<CustomCommand> findByNameStartsWithIgnoreCaseAndCreatorUserAndUserSpecific(String prefix, AUser aUser, Boolean userSpecific);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,9 +1,11 @@
|
|||||||
package dev.sheldan.abstracto.customcommand.service;
|
package dev.sheldan.abstracto.customcommand.service;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AServer;
|
import dev.sheldan.abstracto.core.models.database.AServer;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import dev.sheldan.abstracto.core.service.management.ServerManagementService;
|
import dev.sheldan.abstracto.core.service.management.ServerManagementService;
|
||||||
import dev.sheldan.abstracto.core.service.management.UserInServerManagementService;
|
import dev.sheldan.abstracto.core.service.management.UserInServerManagementService;
|
||||||
|
import dev.sheldan.abstracto.core.service.management.UserManagementService;
|
||||||
import dev.sheldan.abstracto.customcommand.exception.CustomCommandExistsException;
|
import dev.sheldan.abstracto.customcommand.exception.CustomCommandExistsException;
|
||||||
import dev.sheldan.abstracto.customcommand.exception.CustomCommandNotFoundException;
|
import dev.sheldan.abstracto.customcommand.exception.CustomCommandNotFoundException;
|
||||||
import dev.sheldan.abstracto.customcommand.model.database.CustomCommand;
|
import dev.sheldan.abstracto.customcommand.model.database.CustomCommand;
|
||||||
@@ -11,6 +13,7 @@ import dev.sheldan.abstracto.customcommand.service.management.CustomCommandManag
|
|||||||
import dev.sheldan.abstracto.customcommand.service.management.CustomCommandService;
|
import dev.sheldan.abstracto.customcommand.service.management.CustomCommandService;
|
||||||
import net.dv8tion.jda.api.entities.Guild;
|
import net.dv8tion.jda.api.entities.Guild;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
import net.dv8tion.jda.api.entities.Member;
|
||||||
|
import net.dv8tion.jda.api.entities.User;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
@@ -28,6 +31,9 @@ public class CustomCommandServiceBean implements CustomCommandService {
|
|||||||
@Autowired
|
@Autowired
|
||||||
private ServerManagementService serverManagementService;
|
private ServerManagementService serverManagementService;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private UserManagementService userManagementService;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CustomCommand createCustomCommand(String name, String content, Member creator) {
|
public CustomCommand createCustomCommand(String name, String content, Member creator) {
|
||||||
if(customCommandManagementService.getCustomCommandByName(name, creator.getGuild().getIdLong()).isPresent()) {
|
if(customCommandManagementService.getCustomCommandByName(name, creator.getGuild().getIdLong()).isPresent()) {
|
||||||
@@ -37,6 +43,15 @@ public class CustomCommandServiceBean implements CustomCommandService {
|
|||||||
return customCommandManagementService.createCustomCommand(name, content, creatorUser);
|
return customCommandManagementService.createCustomCommand(name, content, creatorUser);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public CustomCommand createUserCustomCommand(String name, String content, User user) {
|
||||||
|
AUser aUser = userManagementService.loadOrCreateUser(user.getIdLong());
|
||||||
|
if(customCommandManagementService.getUserCustomCommandByName(name, aUser).isPresent()) {
|
||||||
|
throw new CustomCommandExistsException();
|
||||||
|
}
|
||||||
|
return customCommandManagementService.createUserCustomCommand(name, content, aUser);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void deleteCustomCommand(String name, Guild guild) {
|
public void deleteCustomCommand(String name, Guild guild) {
|
||||||
if(customCommandManagementService.getCustomCommandByName(name, guild.getIdLong()).isEmpty()) {
|
if(customCommandManagementService.getCustomCommandByName(name, guild.getIdLong()).isEmpty()) {
|
||||||
@@ -46,21 +61,48 @@ public class CustomCommandServiceBean implements CustomCommandService {
|
|||||||
customCommandManagementService.deleteCustomCommand(name, server);
|
customCommandManagementService.deleteCustomCommand(name, server);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void deleteUserCustomCommand(String name, User user) {
|
||||||
|
if(customCommandManagementService.getUserCustomCommandByName(name, user.getIdLong()).isEmpty()) {
|
||||||
|
throw new CustomCommandNotFoundException();
|
||||||
|
}
|
||||||
|
AUser aUser = userManagementService.loadOrCreateUser(user.getIdLong());
|
||||||
|
customCommandManagementService.deleteCustomCommand(name, aUser);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<CustomCommand> getCustomCommands(Guild guild) {
|
public List<CustomCommand> getCustomCommands(Guild guild) {
|
||||||
AServer server = serverManagementService.loadServer(guild);
|
AServer server = serverManagementService.loadServer(guild);
|
||||||
return customCommandManagementService.getCustomCommands(server);
|
return customCommandManagementService.getCustomCommands(server);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<CustomCommand> getUserCustomCommands(User user) {
|
||||||
|
AUser aUser = userManagementService.loadOrCreateUser(user.getIdLong());
|
||||||
|
return customCommandManagementService.getUserCustomCommands(aUser);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CustomCommand getCustomCommand(String name, Guild guild) {
|
public CustomCommand getCustomCommand(String name, Guild guild) {
|
||||||
return customCommandManagementService.getCustomCommandByName(name, guild.getIdLong())
|
return customCommandManagementService.getCustomCommandByName(name, guild.getIdLong())
|
||||||
.orElseThrow(CustomCommandNotFoundException::new);
|
.orElseThrow(CustomCommandNotFoundException::new);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public CustomCommand getUserCustomCommand(String name, User user) {
|
||||||
|
return customCommandManagementService.getUserCustomCommandByName(name, user.getIdLong())
|
||||||
|
.orElseThrow(CustomCommandNotFoundException::new);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<CustomCommand> getCustomCommandsStartingWith(String prefix, Guild guild) {
|
public List<CustomCommand> getCustomCommandsStartingWith(String prefix, Guild guild) {
|
||||||
AServer server = serverManagementService.loadServer(guild);
|
AServer server = serverManagementService.loadServer(guild);
|
||||||
return customCommandManagementService.getCustomCommandsStartingWith(prefix, server);
|
return customCommandManagementService.getCustomCommandsStartingWith(prefix, server);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<CustomCommand> getUserCustomCommandsStartingWith(String prefix, User user) {
|
||||||
|
AUser aUser = userManagementService.loadOrCreateUser(user.getIdLong());
|
||||||
|
return customCommandManagementService.getUserCustomCommandsStartingWith(prefix, aUser);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package dev.sheldan.abstracto.customcommand.service.management;
|
package dev.sheldan.abstracto.customcommand.service.management;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AServer;
|
import dev.sheldan.abstracto.core.models.database.AServer;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import dev.sheldan.abstracto.core.service.management.ServerManagementService;
|
import dev.sheldan.abstracto.core.service.management.ServerManagementService;
|
||||||
import dev.sheldan.abstracto.customcommand.model.database.CustomCommand;
|
import dev.sheldan.abstracto.customcommand.model.database.CustomCommand;
|
||||||
@@ -26,6 +27,16 @@ public class CustomCommandManagementServiceBean implements CustomCommandManageme
|
|||||||
return repository.getByNameIgnoreCaseAndServer(name, server);
|
return repository.getByNameIgnoreCaseAndServer(name, server);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Optional<CustomCommand> getUserCustomCommandByName(String name, AUser user) {
|
||||||
|
return repository.getByNameIgnoreCaseAndCreatorUser(name, user);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Optional<CustomCommand> getUserCustomCommandByName(String name, Long userId) {
|
||||||
|
return repository.getByNameIgnoreCaseAndCreatorUser_IdAndUserSpecific(name, userId, true);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CustomCommand createCustomCommand(String name, String content, AUserInAServer creator) {
|
public CustomCommand createCustomCommand(String name, String content, AUserInAServer creator) {
|
||||||
CustomCommand customCommand = CustomCommand
|
CustomCommand customCommand = CustomCommand
|
||||||
@@ -34,6 +45,20 @@ public class CustomCommandManagementServiceBean implements CustomCommandManageme
|
|||||||
.additionalMessage(content)
|
.additionalMessage(content)
|
||||||
.server(creator.getServerReference())
|
.server(creator.getServerReference())
|
||||||
.creator(creator)
|
.creator(creator)
|
||||||
|
.userSpecific(false)
|
||||||
|
.creatorUser(creator.getUserReference())
|
||||||
|
.build();
|
||||||
|
return repository.save(customCommand);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public CustomCommand createUserCustomCommand(String name, String content, AUser user) {
|
||||||
|
CustomCommand customCommand = CustomCommand
|
||||||
|
.builder()
|
||||||
|
.name(name)
|
||||||
|
.additionalMessage(content)
|
||||||
|
.creatorUser(user)
|
||||||
|
.userSpecific(true)
|
||||||
.build();
|
.build();
|
||||||
return repository.save(customCommand);
|
return repository.save(customCommand);
|
||||||
}
|
}
|
||||||
@@ -43,14 +68,29 @@ public class CustomCommandManagementServiceBean implements CustomCommandManageme
|
|||||||
repository.deleteByNameAndServer(name, server);
|
repository.deleteByNameAndServer(name, server);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void deleteCustomCommand(String name, AUser user) {
|
||||||
|
repository.deleteByNameAndCreatorUserAndUserSpecific(name, user, true);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<CustomCommand> getCustomCommands(AServer server) {
|
public List<CustomCommand> getCustomCommands(AServer server) {
|
||||||
return repository.findByServer(server);
|
return repository.findByServer(server);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<CustomCommand> getUserCustomCommands(AUser aUser) {
|
||||||
|
return repository.findByCreatorUserAndUserSpecific(aUser, true);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<CustomCommand> getCustomCommandsStartingWith(String prefix, AServer server) {
|
public List<CustomCommand> getCustomCommandsStartingWith(String prefix, AServer server) {
|
||||||
return repository.findByNameStartsWithIgnoreCaseAndServer(prefix, server);
|
return repository.findByNameStartsWithIgnoreCaseAndServer(prefix, server);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<CustomCommand> getUserCustomCommandsStartingWith(String prefix, AUser aUser) {
|
||||||
|
return repository.findByNameStartsWithIgnoreCaseAndCreatorUserAndUserSpecific(prefix, aUser, true);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,6 @@
|
|||||||
|
<?xml version="1.1" encoding="UTF-8" standalone="no"?>
|
||||||
|
<databaseChangeLog xmlns="http://www.liquibase.org/xml/ns/dbchangelog"
|
||||||
|
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||||
|
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog https://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-4.26.xsd" >
|
||||||
|
<include file="tables/tables.xml" relativeToChangelogFile="true"/>
|
||||||
|
</databaseChangeLog>
|
||||||
@@ -0,0 +1,26 @@
|
|||||||
|
<?xml version="1.1" encoding="UTF-8" standalone="no"?>
|
||||||
|
<databaseChangeLog xmlns="http://www.liquibase.org/xml/ns/dbchangelog"
|
||||||
|
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||||
|
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog https://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-4.26.xsd" >
|
||||||
|
<changeSet author="Sheldan" id="custom_command-add_user_installable_support">
|
||||||
|
<addColumn tableName="custom_command">
|
||||||
|
<column name="creator_id" type="BIGINT">
|
||||||
|
<constraints nullable="true"/>
|
||||||
|
</column>
|
||||||
|
<column name="user_specific" type="BOOLEAN" value="false">
|
||||||
|
<constraints nullable="false"/>
|
||||||
|
</column>
|
||||||
|
</addColumn>
|
||||||
|
<sql>
|
||||||
|
update custom_command set creator_id = (select ua.user_id from user_in_server ua where ua.user_in_server_id = creator_user_in_server_id order by ua.server_id limit 1)
|
||||||
|
</sql>
|
||||||
|
<addNotNullConstraint columnName="creator_id"
|
||||||
|
tableName="custom_command"
|
||||||
|
validate="true"/>
|
||||||
|
<sql>
|
||||||
|
ALTER TABLE custom_command ALTER COLUMN server_id DROP NOT NULL;
|
||||||
|
ALTER TABLE custom_command ALTER COLUMN creator_user_in_server_id DROP NOT NULL;
|
||||||
|
</sql>
|
||||||
|
</changeSet>
|
||||||
|
|
||||||
|
</databaseChangeLog>
|
||||||
@@ -0,0 +1,6 @@
|
|||||||
|
<?xml version="1.1" encoding="UTF-8" standalone="no"?>
|
||||||
|
<databaseChangeLog xmlns="http://www.liquibase.org/xml/ns/dbchangelog"
|
||||||
|
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||||
|
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog https://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-4.26.xsd" >
|
||||||
|
<include file="custom_command.xml" relativeToChangelogFile="true"/>
|
||||||
|
</databaseChangeLog>
|
||||||
@@ -4,4 +4,5 @@
|
|||||||
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog https://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-4.26.xsd" >
|
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog https://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-4.26.xsd" >
|
||||||
<include file="1.4.0/collection.xml" relativeToChangelogFile="true"/>
|
<include file="1.4.0/collection.xml" relativeToChangelogFile="true"/>
|
||||||
<include file="1.5.8/collection.xml" relativeToChangelogFile="true"/>
|
<include file="1.5.8/collection.xml" relativeToChangelogFile="true"/>
|
||||||
|
<include file="1.5.37/collection.xml" relativeToChangelogFile="true"/>
|
||||||
</databaseChangeLog>
|
</databaseChangeLog>
|
||||||
@@ -13,11 +13,18 @@ public class ListCustomCommandModel {
|
|||||||
private MemberDisplay creator;
|
private MemberDisplay creator;
|
||||||
|
|
||||||
public static ListCustomCommandModel fromCustomCommand(CustomCommand customCommand) {
|
public static ListCustomCommandModel fromCustomCommand(CustomCommand customCommand) {
|
||||||
|
MemberDisplay creatorObj;
|
||||||
|
if(customCommand.getUserSpecific()) {
|
||||||
|
creatorObj = MemberDisplay.fromAUser(customCommand.getCreatorUser());
|
||||||
|
} else {
|
||||||
|
creatorObj = MemberDisplay.fromAUserInAServer(customCommand.getCreator());
|
||||||
|
}
|
||||||
|
|
||||||
return ListCustomCommandModel
|
return ListCustomCommandModel
|
||||||
.builder()
|
.builder()
|
||||||
.name(customCommand.getName())
|
.name(customCommand.getName())
|
||||||
.content(customCommand.getAdditionalMessage())
|
.content(customCommand.getAdditionalMessage())
|
||||||
.creator(MemberDisplay.fromAUserInAServer(customCommand.getCreator()))
|
.creator(creatorObj)
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -29,13 +29,20 @@ public class CustomCommand implements Serializable {
|
|||||||
private String name;
|
private String name;
|
||||||
|
|
||||||
@ManyToOne(fetch = FetchType.LAZY)
|
@ManyToOne(fetch = FetchType.LAZY)
|
||||||
@JoinColumn(name = "server_id", nullable = false)
|
@JoinColumn(name = "server_id")
|
||||||
private AServer server;
|
private AServer server;
|
||||||
|
|
||||||
@ManyToOne(fetch = FetchType.LAZY)
|
@ManyToOne(fetch = FetchType.LAZY)
|
||||||
@JoinColumn(name = "creator_user_in_server_id", nullable = false)
|
@JoinColumn(name = "creator_user_in_server_id")
|
||||||
private AUserInAServer creator;
|
private AUserInAServer creator;
|
||||||
|
|
||||||
|
@ManyToOne(fetch = FetchType.LAZY)
|
||||||
|
@JoinColumn(name = "creator_id", nullable = false)
|
||||||
|
private AUser creatorUser;
|
||||||
|
|
||||||
|
@Column(name = "user_specific")
|
||||||
|
private Boolean userSpecific;
|
||||||
|
|
||||||
@Column(name = "created", nullable = false, insertable = false, updatable = false)
|
@Column(name = "created", nullable = false, insertable = false, updatable = false)
|
||||||
private Instant created;
|
private Instant created;
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package dev.sheldan.abstracto.customcommand.service.management;
|
package dev.sheldan.abstracto.customcommand.service.management;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AServer;
|
import dev.sheldan.abstracto.core.models.database.AServer;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import dev.sheldan.abstracto.customcommand.model.database.CustomCommand;
|
import dev.sheldan.abstracto.customcommand.model.database.CustomCommand;
|
||||||
|
|
||||||
@@ -9,8 +10,14 @@ import java.util.Optional;
|
|||||||
|
|
||||||
public interface CustomCommandManagementService {
|
public interface CustomCommandManagementService {
|
||||||
Optional<CustomCommand> getCustomCommandByName(String name, Long serverId);
|
Optional<CustomCommand> getCustomCommandByName(String name, Long serverId);
|
||||||
|
Optional<CustomCommand> getUserCustomCommandByName(String name, AUser user);
|
||||||
|
Optional<CustomCommand> getUserCustomCommandByName(String name, Long userId);
|
||||||
CustomCommand createCustomCommand(String name, String content, AUserInAServer creator);
|
CustomCommand createCustomCommand(String name, String content, AUserInAServer creator);
|
||||||
|
CustomCommand createUserCustomCommand(String name, String content, AUser user);
|
||||||
void deleteCustomCommand(String name, AServer server);
|
void deleteCustomCommand(String name, AServer server);
|
||||||
|
void deleteCustomCommand(String name, AUser user);
|
||||||
List<CustomCommand> getCustomCommands(AServer server);
|
List<CustomCommand> getCustomCommands(AServer server);
|
||||||
|
List<CustomCommand> getUserCustomCommands(AUser aUser);
|
||||||
List<CustomCommand> getCustomCommandsStartingWith(String prefix, AServer server);
|
List<CustomCommand> getCustomCommandsStartingWith(String prefix, AServer server);
|
||||||
|
List<CustomCommand> getUserCustomCommandsStartingWith(String prefix, AUser aUser);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,13 +3,19 @@ package dev.sheldan.abstracto.customcommand.service.management;
|
|||||||
import dev.sheldan.abstracto.customcommand.model.database.CustomCommand;
|
import dev.sheldan.abstracto.customcommand.model.database.CustomCommand;
|
||||||
import net.dv8tion.jda.api.entities.Guild;
|
import net.dv8tion.jda.api.entities.Guild;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
import net.dv8tion.jda.api.entities.Member;
|
||||||
|
import net.dv8tion.jda.api.entities.User;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
public interface CustomCommandService {
|
public interface CustomCommandService {
|
||||||
CustomCommand createCustomCommand(String name, String content, Member creator);
|
CustomCommand createCustomCommand(String name, String content, Member creator);
|
||||||
|
CustomCommand createUserCustomCommand(String name, String content, User user);
|
||||||
void deleteCustomCommand(String name, Guild guild);
|
void deleteCustomCommand(String name, Guild guild);
|
||||||
|
void deleteUserCustomCommand(String name, User user);
|
||||||
List<CustomCommand> getCustomCommands(Guild guild);
|
List<CustomCommand> getCustomCommands(Guild guild);
|
||||||
|
List<CustomCommand> getUserCustomCommands(User user);
|
||||||
CustomCommand getCustomCommand(String name, Guild guild);
|
CustomCommand getCustomCommand(String name, Guild guild);
|
||||||
|
CustomCommand getUserCustomCommand(String name, User user);
|
||||||
List<CustomCommand> getCustomCommandsStartingWith(String prefix, Guild guild);
|
List<CustomCommand> getCustomCommandsStartingWith(String prefix, Guild guild);
|
||||||
|
List<CustomCommand> getUserCustomCommandsStartingWith(String prefix, User user);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
@@ -96,6 +97,8 @@ public class Choose extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(EntertainmentSlashCommandNames.UTILITY)
|
.rootCommandName(EntertainmentSlashCommandNames.UTILITY)
|
||||||
.commandName(CHOOSE_COMMAND)
|
.commandName(CHOOSE_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
@@ -12,6 +13,7 @@ import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
|||||||
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
||||||
import dev.sheldan.abstracto.core.service.ChannelService;
|
import dev.sheldan.abstracto.core.service.ChannelService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
import dev.sheldan.abstracto.entertainment.config.EntertainmentFeatureDefinition;
|
import dev.sheldan.abstracto.entertainment.config.EntertainmentFeatureDefinition;
|
||||||
@@ -60,7 +62,7 @@ public class EightBall extends AbstractConditionableCommand {
|
|||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
String text = slashCommandParameterService.getCommandOption(TEXT_PARAMETER, event, String.class);
|
String text = slashCommandParameterService.getCommandOption(TEXT_PARAMETER, event, String.class);
|
||||||
MessageToSend messageToSend = getMessageToSend(text, event.getGuild().getIdLong());
|
MessageToSend messageToSend = getMessageToSend(text, ContextUtils.serverIdOrNull(event));
|
||||||
return interactionService.replyMessageToSend(messageToSend, event)
|
return interactionService.replyMessageToSend(messageToSend, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
}
|
}
|
||||||
@@ -93,6 +95,8 @@ public class EightBall extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(EntertainmentSlashCommandNames.UTILITY)
|
.rootCommandName(EntertainmentSlashCommandNames.UTILITY)
|
||||||
.commandName(BALL_COMMAND)
|
.commandName(BALL_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
@@ -13,6 +14,7 @@ import dev.sheldan.abstracto.core.interaction.InteractionService;
|
|||||||
import dev.sheldan.abstracto.core.service.ChannelService;
|
import dev.sheldan.abstracto.core.service.ChannelService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.entertainment.config.EntertainmentFeatureDefinition;
|
import dev.sheldan.abstracto.entertainment.config.EntertainmentFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.entertainment.config.EntertainmentModuleDefinition;
|
import dev.sheldan.abstracto.entertainment.config.EntertainmentModuleDefinition;
|
||||||
@@ -64,7 +66,7 @@ public class LoveCalc extends AbstractConditionableCommand {
|
|||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
String firstPart = slashCommandParameterService.getCommandOption(FIRST_SUBJECT_PARAMETER, event, String.class);
|
String firstPart = slashCommandParameterService.getCommandOption(FIRST_SUBJECT_PARAMETER, event, String.class);
|
||||||
String secondPart = slashCommandParameterService.getCommandOption(SECOND_SUBJECT_PARAMETER, event, String.class);
|
String secondPart = slashCommandParameterService.getCommandOption(SECOND_SUBJECT_PARAMETER, event, String.class);
|
||||||
MessageToSend messageToSend = getMessageToSend(event.getGuild().getIdLong(), firstPart, secondPart);
|
MessageToSend messageToSend = getMessageToSend(ContextUtils.serverIdOrNull(event), firstPart, secondPart);
|
||||||
return interactionService.replyMessageToSend(messageToSend, event.getInteraction())
|
return interactionService.replyMessageToSend(messageToSend, event.getInteraction())
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
}
|
}
|
||||||
@@ -105,6 +107,8 @@ public class LoveCalc extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(EntertainmentSlashCommandNames.UTILITY)
|
.rootCommandName(EntertainmentSlashCommandNames.UTILITY)
|
||||||
.commandName(LOVE_CALC_COMMAND)
|
.commandName(LOVE_CALC_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -1,10 +1,7 @@
|
|||||||
package dev.sheldan.abstracto.entertainment.command;
|
package dev.sheldan.abstracto.entertainment.command;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CombinedParameterEntry;
|
import dev.sheldan.abstracto.core.command.config.*;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.command.handler.parameter.CombinedParameter;
|
import dev.sheldan.abstracto.core.command.handler.parameter.CombinedParameter;
|
||||||
@@ -108,6 +105,8 @@ public class Mock extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(EntertainmentSlashCommandNames.ENTERTAINMENT)
|
.rootCommandName(EntertainmentSlashCommandNames.ENTERTAINMENT)
|
||||||
.commandName(MOCK_COMMAND)
|
.commandName(MOCK_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.config.validator.MinIntegerValueValidator;
|
import dev.sheldan.abstracto.core.command.config.validator.MinIntegerValueValidator;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
@@ -125,6 +126,8 @@ public class Roll extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(EntertainmentSlashCommandNames.UTILITY)
|
.rootCommandName(EntertainmentSlashCommandNames.UTILITY)
|
||||||
.commandName(ROLL_COMMAND)
|
.commandName(ROLL_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
@@ -71,6 +72,8 @@ public class Roulette extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(EntertainmentSlashCommandNames.UTILITY)
|
.rootCommandName(EntertainmentSlashCommandNames.UTILITY)
|
||||||
.commandName(ROULETTE_COMMAND)
|
.commandName(ROULETTE_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
@@ -15,6 +16,7 @@ import dev.sheldan.abstracto.core.service.ChannelService;
|
|||||||
import dev.sheldan.abstracto.core.service.FeatureFlagService;
|
import dev.sheldan.abstracto.core.service.FeatureFlagService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.entertainment.config.EntertainmentFeatureDefinition;
|
import dev.sheldan.abstracto.entertainment.config.EntertainmentFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.entertainment.config.EntertainmentModuleDefinition;
|
import dev.sheldan.abstracto.entertainment.config.EntertainmentModuleDefinition;
|
||||||
@@ -81,33 +83,39 @@ public class Mines extends AbstractConditionableCommand {
|
|||||||
mines = slashCommandParameterService.getCommandOption(MINES_PARAMETER, event, Integer.class);
|
mines = slashCommandParameterService.getCommandOption(MINES_PARAMETER, event, Integer.class);
|
||||||
}
|
}
|
||||||
Integer credit = null;
|
Integer credit = null;
|
||||||
long serverId = event.getGuild().getIdLong();
|
Long serverId;
|
||||||
boolean economyEnabled = featureFlagService.getFeatureFlagValue(EntertainmentFeatureDefinition.ECONOMY, serverId);
|
boolean economyEnabled = false;
|
||||||
if(economyEnabled){
|
if(ContextUtils.isNotUserCommand(event)) {
|
||||||
credit = 50;
|
serverId = event.getGuild().getIdLong();
|
||||||
if(slashCommandParameterService.hasCommandOption(CREDITS_PARAMETER, event)) {
|
economyEnabled = featureFlagService.getFeatureFlagValue(EntertainmentFeatureDefinition.ECONOMY, serverId);
|
||||||
credit = slashCommandParameterService.getCommandOption(CREDITS_PARAMETER, event, Integer.class);
|
if(economyEnabled){
|
||||||
}
|
credit = 50;
|
||||||
|
if(slashCommandParameterService.hasCommandOption(CREDITS_PARAMETER, event)) {
|
||||||
|
credit = slashCommandParameterService.getCommandOption(CREDITS_PARAMETER, event, Integer.class);
|
||||||
|
}
|
||||||
|
|
||||||
Optional<EconomyUser> userOptional = economyUserManagementService.getUser(ServerUser.fromMember(event.getMember()));
|
Optional<EconomyUser> userOptional = economyUserManagementService.getUser(ServerUser.fromMember(event.getMember()));
|
||||||
if(!userOptional.isPresent()) {
|
if(!userOptional.isPresent()) {
|
||||||
throw new NotEnoughCreditsException();
|
throw new NotEnoughCreditsException();
|
||||||
}
|
}
|
||||||
EconomyUser user = userOptional.get();
|
EconomyUser user = userOptional.get();
|
||||||
if(user.getCredits() < credit) {
|
if(user.getCredits() < credit) {
|
||||||
throw new NotEnoughCreditsException();
|
throw new NotEnoughCreditsException();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
serverId = null;
|
||||||
}
|
}
|
||||||
MineBoard board = gameService.createBoard(width, height, mines, serverId);
|
MineBoard board = gameService.createBoard(width, height, mines, serverId);
|
||||||
board.setCreditsEnabled(economyEnabled);
|
board.setCreditsEnabled(economyEnabled);
|
||||||
board.setUserId(event.getMember().getIdLong());
|
board.setUserId(event.getUser().getIdLong());
|
||||||
board.setServerId(serverId);
|
board.setServerId(serverId);
|
||||||
board.setCredits(credit);
|
board.setCredits(credit);
|
||||||
MessageToSend messageToSend = templateService.renderEmbedTemplate(MINE_BOARD_TEMPLATE_KEY, board, serverId);
|
MessageToSend messageToSend = templateService.renderEmbedTemplate(MINE_BOARD_TEMPLATE_KEY, board, serverId);
|
||||||
return interactionService.replyMessageToSend(messageToSend, event)
|
return interactionService.replyMessageToSend(messageToSend, event)
|
||||||
.thenCompose(interactionHook -> interactionHook.retrieveOriginal().submit())
|
.thenCompose(interactionHook -> interactionHook.retrieveOriginal().submit())
|
||||||
.thenApply(message -> {
|
.thenApply(message -> {
|
||||||
gameService.persistMineBoardMessage(board, message);
|
gameService.persistMineBoardMessage(board, message, serverId);
|
||||||
return CommandResult.fromSuccess();
|
return CommandResult.fromSuccess();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -129,7 +137,7 @@ public class Mines extends AbstractConditionableCommand {
|
|||||||
mines = (Integer) parameters.get(2);
|
mines = (Integer) parameters.get(2);
|
||||||
}
|
}
|
||||||
Integer credit = null;
|
Integer credit = null;
|
||||||
long serverId = commandContext.getGuild().getIdLong();
|
Long serverId = commandContext.getGuild().getIdLong();
|
||||||
boolean economyEnabled = featureFlagService.getFeatureFlagValue(EntertainmentFeatureDefinition.ECONOMY, serverId);
|
boolean economyEnabled = featureFlagService.getFeatureFlagValue(EntertainmentFeatureDefinition.ECONOMY, serverId);
|
||||||
if(economyEnabled){
|
if(economyEnabled){
|
||||||
credit = 50;
|
credit = 50;
|
||||||
@@ -154,7 +162,7 @@ public class Mines extends AbstractConditionableCommand {
|
|||||||
MessageToSend messageToSend = templateService.renderEmbedTemplate(MINE_BOARD_TEMPLATE_KEY, board, serverId);
|
MessageToSend messageToSend = templateService.renderEmbedTemplate(MINE_BOARD_TEMPLATE_KEY, board, serverId);
|
||||||
List<CompletableFuture<Message>> futures = channelService.sendMessageToSendToChannel(messageToSend, commandContext.getChannel());
|
List<CompletableFuture<Message>> futures = channelService.sendMessageToSendToChannel(messageToSend, commandContext.getChannel());
|
||||||
return FutureUtils.toSingleFutureGeneric(futures)
|
return FutureUtils.toSingleFutureGeneric(futures)
|
||||||
.thenAccept(unused -> gameService.persistMineBoardMessage(board, futures.get(0).join()))
|
.thenAccept(unused -> gameService.persistMineBoardMessage(board, futures.get(0).join(), serverId))
|
||||||
.thenApply(unused -> CommandResult.fromSuccess());
|
.thenApply(unused -> CommandResult.fromSuccess());
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -207,6 +215,8 @@ public class Mines extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(EntertainmentSlashCommandNames.GAME)
|
.rootCommandName(EntertainmentSlashCommandNames.GAME)
|
||||||
.commandName(MINES_COMMAND_NAME)
|
.commandName(MINES_COMMAND_NAME)
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ import dev.sheldan.abstracto.core.interaction.button.listener.ButtonClickedListe
|
|||||||
import dev.sheldan.abstracto.core.service.FeatureFlagService;
|
import dev.sheldan.abstracto.core.service.FeatureFlagService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.entertainment.command.games.Mines;
|
import dev.sheldan.abstracto.entertainment.command.games.Mines;
|
||||||
import dev.sheldan.abstracto.entertainment.config.EntertainmentFeatureDefinition;
|
import dev.sheldan.abstracto.entertainment.config.EntertainmentFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.entertainment.model.command.games.MineBoard;
|
import dev.sheldan.abstracto.entertainment.model.command.games.MineBoard;
|
||||||
@@ -49,8 +50,10 @@ public class MinesButtonClickedListener implements ButtonClickedListener {
|
|||||||
GameService.MineResult mineResult = gameService.uncoverField(mineBoard, payload.getX(), payload.getY());
|
GameService.MineResult mineResult = gameService.uncoverField(mineBoard, payload.getX(), payload.getY());
|
||||||
mineBoard.setState(mineResult);
|
mineBoard.setState(mineResult);
|
||||||
if(mineBoard.getState() != GameService.MineResult.CONTINUE) {
|
if(mineBoard.getState() != GameService.MineResult.CONTINUE) {
|
||||||
if(featureFlagService.getFeatureFlagValue(EntertainmentFeatureDefinition.ECONOMY, model.getServerId())){
|
if(ContextUtils.isNotUserCommand(model.getEvent())) {
|
||||||
gameService.evaluateCreditChanges(mineBoard);
|
if(featureFlagService.getFeatureFlagValue(EntertainmentFeatureDefinition.ECONOMY, model.getServerId())){
|
||||||
|
gameService.evaluateCreditChanges(mineBoard);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
gameService.uncoverBoard(mineBoard);
|
gameService.uncoverBoard(mineBoard);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -70,10 +70,16 @@ public class GameServiceBean implements GameService {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
@Transactional
|
@Transactional
|
||||||
public void persistMineBoardMessage(MineBoard mineBoard, Message message) {
|
public void persistMineBoardMessage(MineBoard mineBoard, Message message, Long serverId) {
|
||||||
mineBoard.setMessageId(message.getIdLong());
|
mineBoard.setMessageId(message.getIdLong());
|
||||||
mineBoard.setChannelId(message.getChannel().getIdLong());
|
mineBoard.setChannelId(message.getChannel().getIdLong());
|
||||||
AServer server = serverManagementService.loadServer(message.getGuild());
|
|
||||||
|
AServer server;
|
||||||
|
if(serverId != null) {
|
||||||
|
server = serverManagementService.loadServer(serverId);
|
||||||
|
} else {
|
||||||
|
server = null;
|
||||||
|
}
|
||||||
mineBoard.getFields().forEach(mineBoardField -> {
|
mineBoard.getFields().forEach(mineBoardField -> {
|
||||||
MineBoardPayload payload = MineBoardPayload
|
MineBoardPayload payload = MineBoardPayload
|
||||||
.builder()
|
.builder()
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import net.dv8tion.jda.api.entities.Message;
|
|||||||
|
|
||||||
public interface GameService {
|
public interface GameService {
|
||||||
MineBoard createBoard(Integer width, Integer height, Integer mines, Long serverId);
|
MineBoard createBoard(Integer width, Integer height, Integer mines, Long serverId);
|
||||||
void persistMineBoardMessage(MineBoard mineBoard, Message message);
|
void persistMineBoardMessage(MineBoard mineBoard, Message message, Long serverId);
|
||||||
void updateMineBoard(MineBoard mineBoard);
|
void updateMineBoard(MineBoard mineBoard);
|
||||||
void uncoverBoard(MineBoard mineBoard);
|
void uncoverBoard(MineBoard mineBoard);
|
||||||
void evaluateCreditChanges(MineBoard mineBoard);
|
void evaluateCreditChanges(MineBoard mineBoard);
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
@@ -109,6 +110,8 @@ public class AmongusText extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(ImageGenerationSlashCommandNames.IMAGE_GENERATION)
|
.rootCommandName(ImageGenerationSlashCommandNames.IMAGE_GENERATION)
|
||||||
.groupName("memes")
|
.groupName("memes")
|
||||||
.commandName("amongustext")
|
.commandName("amongustext")
|
||||||
|
|||||||
@@ -2,10 +2,7 @@ package dev.sheldan.abstracto.imagegeneration.command;
|
|||||||
|
|
||||||
import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CombinedParameterEntry;
|
import dev.sheldan.abstracto.core.command.config.*;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.command.handler.parameter.CombinedParameter;
|
import dev.sheldan.abstracto.core.command.handler.parameter.CombinedParameter;
|
||||||
@@ -24,6 +21,7 @@ import dev.sheldan.abstracto.imagegeneration.config.ImageGenerationSlashCommandN
|
|||||||
import dev.sheldan.abstracto.imagegeneration.service.ImageGenerationService;
|
import dev.sheldan.abstracto.imagegeneration.service.ImageGenerationService;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
import net.dv8tion.jda.api.entities.Member;
|
||||||
import net.dv8tion.jda.api.entities.Message;
|
import net.dv8tion.jda.api.entities.Message;
|
||||||
|
import net.dv8tion.jda.api.entities.User;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.beans.factory.annotation.Value;
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
@@ -92,13 +90,25 @@ public class Bonk extends AbstractConditionableCommand {
|
|||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
event.deferReply().queue();
|
event.deferReply().queue();
|
||||||
|
String avatarUrl;
|
||||||
Member targetMember;
|
Member targetMember;
|
||||||
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER_KEY, event)) {
|
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER_KEY, event)) {
|
||||||
targetMember = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER_KEY, event, Member.class);
|
targetMember = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER_KEY, event, Member.class);
|
||||||
} else {
|
} else {
|
||||||
targetMember = event.getMember();
|
targetMember = event.getMember();
|
||||||
}
|
}
|
||||||
File bonkGifFile = imageGenerationService.getBonkGif(targetMember.getEffectiveAvatar().getUrl(imageSize));
|
if(targetMember == null) {
|
||||||
|
User targetUser;
|
||||||
|
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER_KEY, event)) {
|
||||||
|
targetUser = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER_KEY, event, User.class);
|
||||||
|
} else {
|
||||||
|
targetUser = event.getUser();
|
||||||
|
}
|
||||||
|
avatarUrl = targetUser.getEffectiveAvatar().getUrl(imageSize);
|
||||||
|
} else {
|
||||||
|
avatarUrl = targetMember.getEffectiveAvatar().getUrl(imageSize);
|
||||||
|
}
|
||||||
|
File bonkGifFile = imageGenerationService.getBonkGif(avatarUrl);
|
||||||
MessageToSend messageToSend = templateService.renderEmbedTemplate(BONK_EMBED_TEMPLATE_KEY, new Object(), event.getGuild().getIdLong());
|
MessageToSend messageToSend = templateService.renderEmbedTemplate(BONK_EMBED_TEMPLATE_KEY, new Object(), event.getGuild().getIdLong());
|
||||||
// template support does not support binary files
|
// template support does not support binary files
|
||||||
AttachedFile file = AttachedFile
|
AttachedFile file = AttachedFile
|
||||||
@@ -116,13 +126,18 @@ public class Bonk extends AbstractConditionableCommand {
|
|||||||
public CommandConfiguration getConfiguration() {
|
public CommandConfiguration getConfiguration() {
|
||||||
List<Parameter> parameters = new ArrayList<>();
|
List<Parameter> parameters = new ArrayList<>();
|
||||||
Map<String, Object> parameterAlternatives = new HashMap<>();
|
Map<String, Object> parameterAlternatives = new HashMap<>();
|
||||||
parameterAlternatives.put(ADDITIONAL_TYPES_KEY, Arrays.asList(CombinedParameterEntry.messageParameter(Message.class), CombinedParameterEntry.parameter(Member.class)));
|
parameterAlternatives.put(ADDITIONAL_TYPES_KEY, List.of(
|
||||||
|
CombinedParameterEntry.messageParameter(Message.class),
|
||||||
|
CombinedParameterEntry.parameter(Member.class),
|
||||||
|
CombinedParameterEntry.parameter(User.class)
|
||||||
|
));
|
||||||
Parameter memberParameter = Parameter
|
Parameter memberParameter = Parameter
|
||||||
.builder()
|
.builder()
|
||||||
.name(MEMBER_PARAMETER_KEY)
|
.name(MEMBER_PARAMETER_KEY)
|
||||||
.type(CombinedParameter.class)
|
.type(CombinedParameter.class)
|
||||||
.additionalInfo(parameterAlternatives)
|
.additionalInfo(parameterAlternatives)
|
||||||
.templated(true)
|
.templated(true)
|
||||||
|
.useStrictParameters(true)
|
||||||
.optional(true)
|
.optional(true)
|
||||||
.build();
|
.build();
|
||||||
parameters.add(memberParameter);
|
parameters.add(memberParameter);
|
||||||
@@ -134,6 +149,8 @@ public class Bonk extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(ImageGenerationSlashCommandNames.IMAGE_GENERATION)
|
.rootCommandName(ImageGenerationSlashCommandNames.IMAGE_GENERATION)
|
||||||
.groupName("memes")
|
.groupName("memes")
|
||||||
.commandName("bonk")
|
.commandName("bonk")
|
||||||
|
|||||||
@@ -2,10 +2,7 @@ package dev.sheldan.abstracto.imagegeneration.command;
|
|||||||
|
|
||||||
import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CombinedParameterEntry;
|
import dev.sheldan.abstracto.core.command.config.*;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.command.handler.parameter.CombinedParameter;
|
import dev.sheldan.abstracto.core.command.handler.parameter.CombinedParameter;
|
||||||
@@ -24,6 +21,7 @@ import dev.sheldan.abstracto.imagegeneration.config.ImageGenerationSlashCommandN
|
|||||||
import dev.sheldan.abstracto.imagegeneration.service.ImageGenerationService;
|
import dev.sheldan.abstracto.imagegeneration.service.ImageGenerationService;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
import net.dv8tion.jda.api.entities.Member;
|
||||||
import net.dv8tion.jda.api.entities.Message;
|
import net.dv8tion.jda.api.entities.Message;
|
||||||
|
import net.dv8tion.jda.api.entities.User;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.beans.factory.annotation.Value;
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
@@ -92,13 +90,25 @@ public class Pat extends AbstractConditionableCommand {
|
|||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
event.deferReply().queue();
|
event.deferReply().queue();
|
||||||
|
String avatarUrl;
|
||||||
Member targetMember;
|
Member targetMember;
|
||||||
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER_KEY, event)) {
|
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER_KEY, event)) {
|
||||||
targetMember = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER_KEY, event, Member.class);
|
targetMember = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER_KEY, event, Member.class);
|
||||||
} else {
|
} else {
|
||||||
targetMember = event.getMember();
|
targetMember = event.getMember();
|
||||||
}
|
}
|
||||||
File patGifFile = imageGenerationService.getPatGif(targetMember.getEffectiveAvatar().getUrl(imageSize));
|
if(targetMember == null) {
|
||||||
|
User targetUser;
|
||||||
|
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER_KEY, event)) {
|
||||||
|
targetUser = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER_KEY, event, User.class);
|
||||||
|
} else {
|
||||||
|
targetUser = event.getUser();
|
||||||
|
}
|
||||||
|
avatarUrl = targetUser.getEffectiveAvatar().getUrl(imageSize);
|
||||||
|
} else {
|
||||||
|
avatarUrl = targetMember.getEffectiveAvatar().getUrl(imageSize);
|
||||||
|
}
|
||||||
|
File patGifFile = imageGenerationService.getPatGif(avatarUrl);
|
||||||
MessageToSend messageToSend = templateService.renderEmbedTemplate(PAT_EMBED_TEMPLATE_KEY, new Object(), event.getGuild().getIdLong());
|
MessageToSend messageToSend = templateService.renderEmbedTemplate(PAT_EMBED_TEMPLATE_KEY, new Object(), event.getGuild().getIdLong());
|
||||||
// template support does not support binary files
|
// template support does not support binary files
|
||||||
AttachedFile file = AttachedFile
|
AttachedFile file = AttachedFile
|
||||||
@@ -116,13 +126,17 @@ public class Pat extends AbstractConditionableCommand {
|
|||||||
public CommandConfiguration getConfiguration() {
|
public CommandConfiguration getConfiguration() {
|
||||||
List<Parameter> parameters = new ArrayList<>();
|
List<Parameter> parameters = new ArrayList<>();
|
||||||
Map<String, Object> parameterAlternatives = new HashMap<>();
|
Map<String, Object> parameterAlternatives = new HashMap<>();
|
||||||
parameterAlternatives.put(ADDITIONAL_TYPES_KEY, Arrays.asList(CombinedParameterEntry.messageParameter(Message.class), CombinedParameterEntry.parameter(Member.class)));
|
parameterAlternatives.put(ADDITIONAL_TYPES_KEY, List.of(
|
||||||
|
CombinedParameterEntry.messageParameter(Message.class),
|
||||||
|
CombinedParameterEntry.parameter(Member.class),
|
||||||
|
CombinedParameterEntry.parameter(User.class)));
|
||||||
Parameter memberParameter = Parameter
|
Parameter memberParameter = Parameter
|
||||||
.builder()
|
.builder()
|
||||||
.name(MEMBER_PARAMETER_KEY)
|
.name(MEMBER_PARAMETER_KEY)
|
||||||
.type(CombinedParameter.class)
|
.type(CombinedParameter.class)
|
||||||
.additionalInfo(parameterAlternatives)
|
.additionalInfo(parameterAlternatives)
|
||||||
.templated(true)
|
.templated(true)
|
||||||
|
.useStrictParameters(true)
|
||||||
.optional(true)
|
.optional(true)
|
||||||
.build();
|
.build();
|
||||||
parameters.add(memberParameter);
|
parameters.add(memberParameter);
|
||||||
@@ -134,6 +148,8 @@ public class Pat extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(ImageGenerationSlashCommandNames.IMAGE_GENERATION)
|
.rootCommandName(ImageGenerationSlashCommandNames.IMAGE_GENERATION)
|
||||||
.groupName("memes")
|
.groupName("memes")
|
||||||
.commandName("pat")
|
.commandName("pat")
|
||||||
|
|||||||
@@ -2,11 +2,10 @@ package dev.sheldan.abstracto.imagegeneration.command;
|
|||||||
|
|
||||||
import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.*;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
|
import dev.sheldan.abstracto.core.command.handler.parameter.CombinedParameter;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
@@ -21,6 +20,8 @@ import dev.sheldan.abstracto.imagegeneration.config.ImageGenerationFeatureDefini
|
|||||||
import dev.sheldan.abstracto.imagegeneration.config.ImageGenerationSlashCommandNames;
|
import dev.sheldan.abstracto.imagegeneration.config.ImageGenerationSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.imagegeneration.service.ImageGenerationService;
|
import dev.sheldan.abstracto.imagegeneration.service.ImageGenerationService;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
import net.dv8tion.jda.api.entities.Member;
|
||||||
|
import net.dv8tion.jda.api.entities.Message;
|
||||||
|
import net.dv8tion.jda.api.entities.User;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.beans.factory.annotation.Value;
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
@@ -28,9 +29,13 @@ import org.springframework.stereotype.Component;
|
|||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
import java.util.concurrent.CompletableFuture;
|
import java.util.concurrent.CompletableFuture;
|
||||||
|
|
||||||
|
import static dev.sheldan.abstracto.core.command.config.Parameter.ADDITIONAL_TYPES_KEY;
|
||||||
|
|
||||||
@Component
|
@Component
|
||||||
public class Triggered extends AbstractConditionableCommand {
|
public class Triggered extends AbstractConditionableCommand {
|
||||||
|
|
||||||
@@ -84,13 +89,25 @@ public class Triggered extends AbstractConditionableCommand {
|
|||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
event.deferReply().queue();
|
event.deferReply().queue();
|
||||||
|
String avatarUrl;
|
||||||
Member targetMember;
|
Member targetMember;
|
||||||
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER_KEY, event)) {
|
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER_KEY, event)) {
|
||||||
targetMember = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER_KEY, event, Member.class);
|
targetMember = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER_KEY, event, Member.class);
|
||||||
} else {
|
} else {
|
||||||
targetMember = event.getMember();
|
targetMember = event.getMember();
|
||||||
}
|
}
|
||||||
File triggeredGifFile = imageGenerationService.getTriggeredGif(targetMember.getEffectiveAvatar().getUrl(imageSize));
|
if(targetMember == null) {
|
||||||
|
User targetUser;
|
||||||
|
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER_KEY, event)) {
|
||||||
|
targetUser = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER_KEY, event, User.class);
|
||||||
|
} else {
|
||||||
|
targetUser = event.getUser();
|
||||||
|
}
|
||||||
|
avatarUrl = targetUser.getEffectiveAvatar().getUrl(imageSize);
|
||||||
|
} else {
|
||||||
|
avatarUrl = targetMember.getEffectiveAvatar().getUrl(imageSize);
|
||||||
|
}
|
||||||
|
File triggeredGifFile = imageGenerationService.getTriggeredGif(avatarUrl);
|
||||||
MessageToSend messageToSend = templateService.renderEmbedTemplate(TRIGGERED_EMBED_TEMPLATE_KEY, new Object(), event.getGuild().getIdLong());
|
MessageToSend messageToSend = templateService.renderEmbedTemplate(TRIGGERED_EMBED_TEMPLATE_KEY, new Object(), event.getGuild().getIdLong());
|
||||||
// template support does not support binary files
|
// template support does not support binary files
|
||||||
AttachedFile file = AttachedFile
|
AttachedFile file = AttachedFile
|
||||||
@@ -107,11 +124,19 @@ public class Triggered extends AbstractConditionableCommand {
|
|||||||
@Override
|
@Override
|
||||||
public CommandConfiguration getConfiguration() {
|
public CommandConfiguration getConfiguration() {
|
||||||
List<Parameter> parameters = new ArrayList<>();
|
List<Parameter> parameters = new ArrayList<>();
|
||||||
|
Map<String, Object> parameterAlternatives = new HashMap<>();
|
||||||
|
parameterAlternatives.put(ADDITIONAL_TYPES_KEY, List.of(
|
||||||
|
CombinedParameterEntry.messageParameter(Message.class),
|
||||||
|
CombinedParameterEntry.parameter(Member.class),
|
||||||
|
CombinedParameterEntry.parameter(User.class)
|
||||||
|
));
|
||||||
Parameter memberParameter = Parameter
|
Parameter memberParameter = Parameter
|
||||||
.builder()
|
.builder()
|
||||||
.name(MEMBER_PARAMETER_KEY)
|
.name(MEMBER_PARAMETER_KEY)
|
||||||
.type(Member.class)
|
.type(CombinedParameter.class)
|
||||||
|
.additionalInfo(parameterAlternatives)
|
||||||
.templated(true)
|
.templated(true)
|
||||||
|
.useStrictParameters(true)
|
||||||
.optional(true)
|
.optional(true)
|
||||||
.build();
|
.build();
|
||||||
parameters.add(memberParameter);
|
parameters.add(memberParameter);
|
||||||
@@ -123,6 +148,8 @@ public class Triggered extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(ImageGenerationSlashCommandNames.IMAGE_GENERATION)
|
.rootCommandName(ImageGenerationSlashCommandNames.IMAGE_GENERATION)
|
||||||
.groupName("memes")
|
.groupName("memes")
|
||||||
.commandName("triggered")
|
.commandName("triggered")
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import dev.sheldan.abstracto.core.command.Command;
|
|||||||
import dev.sheldan.abstracto.core.command.condition.ConditionResult;
|
import dev.sheldan.abstracto.core.command.condition.ConditionResult;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.service.management.ChannelManagementService;
|
import dev.sheldan.abstracto.core.service.management.ChannelManagementService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.modmail.condition.ModMailContextCondition;
|
import dev.sheldan.abstracto.modmail.condition.ModMailContextCondition;
|
||||||
import dev.sheldan.abstracto.modmail.condition.detail.NotInModMailThreadConditionDetail;
|
import dev.sheldan.abstracto.modmail.condition.detail.NotInModMailThreadConditionDetail;
|
||||||
import dev.sheldan.abstracto.modmail.model.database.ModMailThread;
|
import dev.sheldan.abstracto.modmail.model.database.ModMailThread;
|
||||||
@@ -45,6 +46,9 @@ public class RequiresModMailCondition implements ModMailContextCondition {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ConditionResult shouldExecute(SlashCommandInteractionEvent slashCommandInteractionEvent, Command command) {
|
public ConditionResult shouldExecute(SlashCommandInteractionEvent slashCommandInteractionEvent, Command command) {
|
||||||
|
if(ContextUtils.isUserCommand(slashCommandInteractionEvent)) {
|
||||||
|
return ConditionResult.SUCCESS;
|
||||||
|
}
|
||||||
Optional<ModMailThread> threadOptional = modMailThreadManagementService.getByChannelOptional(channelManagementService.loadChannel(slashCommandInteractionEvent.getChannel()));
|
Optional<ModMailThread> threadOptional = modMailThreadManagementService.getByChannelOptional(channelManagementService.loadChannel(slashCommandInteractionEvent.getChannel()));
|
||||||
if(threadOptional.isPresent()) {
|
if(threadOptional.isPresent()) {
|
||||||
return ConditionResult
|
return ConditionResult
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.ComponentPayloadService;
|
import dev.sheldan.abstracto.core.interaction.ComponentPayloadService;
|
||||||
import dev.sheldan.abstracto.core.interaction.ComponentService;
|
import dev.sheldan.abstracto.core.interaction.ComponentService;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
@@ -14,12 +15,17 @@ import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandParame
|
|||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
||||||
import dev.sheldan.abstracto.core.models.ServerChannelMessage;
|
import dev.sheldan.abstracto.core.models.ServerChannelMessage;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AServer;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import dev.sheldan.abstracto.core.models.template.display.MemberNameDisplay;
|
import dev.sheldan.abstracto.core.models.template.display.UserDisplay;
|
||||||
import dev.sheldan.abstracto.core.service.ChannelService;
|
import dev.sheldan.abstracto.core.service.ChannelService;
|
||||||
|
import dev.sheldan.abstracto.core.service.management.ServerManagementService;
|
||||||
import dev.sheldan.abstracto.core.service.management.UserInServerManagementService;
|
import dev.sheldan.abstracto.core.service.management.UserInServerManagementService;
|
||||||
|
import dev.sheldan.abstracto.core.service.management.UserManagementService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.ParseUtils;
|
import dev.sheldan.abstracto.core.utils.ParseUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.SnowflakeUtils;
|
import dev.sheldan.abstracto.core.utils.SnowflakeUtils;
|
||||||
@@ -73,6 +79,12 @@ public class Remind extends AbstractConditionableCommand {
|
|||||||
@Autowired
|
@Autowired
|
||||||
private ComponentPayloadService componentPayloadService;
|
private ComponentPayloadService componentPayloadService;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private UserManagementService userManagementService;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private ServerManagementService serverManagementService;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeAsync(CommandContext commandContext) {
|
public CompletableFuture<CommandResult> executeAsync(CommandContext commandContext) {
|
||||||
List<Object> parameters = commandContext.getParameters().getParameters();
|
List<Object> parameters = commandContext.getParameters().getParameters();
|
||||||
@@ -88,7 +100,7 @@ public class Remind extends AbstractConditionableCommand {
|
|||||||
ReminderModel remindModel = ReminderModel
|
ReminderModel remindModel = ReminderModel
|
||||||
.builder()
|
.builder()
|
||||||
.remindText(text)
|
.remindText(text)
|
||||||
.memberDisplay(MemberNameDisplay.fromMember(commandContext.getAuthor()))
|
.userDisplay(UserDisplay.fromUser(commandContext.getAuthor().getUser()))
|
||||||
.joinButtonId(joinButtonId)
|
.joinButtonId(joinButtonId)
|
||||||
.reminder(ReminderDisplay.fromReminder(createdReminder))
|
.reminder(ReminderDisplay.fromReminder(createdReminder))
|
||||||
.message(ServerChannelMessage.fromMessage(commandContext.getMessage()))
|
.message(ServerChannelMessage.fromMessage(commandContext.getMessage()))
|
||||||
@@ -118,29 +130,41 @@ public class Remind extends AbstractConditionableCommand {
|
|||||||
if(slashCommandParameterService.hasCommandOption(REMIND_TEXT_PARAMETER, event)) {
|
if(slashCommandParameterService.hasCommandOption(REMIND_TEXT_PARAMETER, event)) {
|
||||||
reminderText = slashCommandParameterService.getCommandOption(REMIND_TEXT_PARAMETER, event, String.class, String.class);
|
reminderText = slashCommandParameterService.getCommandOption(REMIND_TEXT_PARAMETER, event, String.class, String.class);
|
||||||
}
|
}
|
||||||
AUserInAServer aUserInAServer = userInServerManagementService.loadOrCreateUser(event.getMember());
|
String joinButtonId;
|
||||||
Long snowFlake = SnowflakeUtils.createSnowFlake();
|
Reminder createdReminder;
|
||||||
String joinButtonId = componentService.generateComponentId();
|
if(ContextUtils.isUserCommand(event)) {
|
||||||
Reminder createdReminder = remindService.createReminderInForUser(aUserInAServer, reminderText, duration, event.getChannel().getIdLong(), snowFlake);
|
joinButtonId = null;
|
||||||
|
AUser aUser = userManagementService.loadOrCreateUser(event.getUser().getIdLong());
|
||||||
|
createdReminder = remindService.createReminderInForUser(aUser, reminderText, duration);
|
||||||
|
} else {
|
||||||
|
joinButtonId = componentService.generateComponentId();
|
||||||
|
Long snowFlake = SnowflakeUtils.createSnowFlake();
|
||||||
|
AUserInAServer aUserInAServer = userInServerManagementService.loadOrCreateUser(event.getMember());
|
||||||
|
createdReminder = remindService.createReminderInForUser(aUserInAServer, reminderText, duration, event.getChannel().getIdLong(), snowFlake);
|
||||||
|
}
|
||||||
ReminderModel remindModel = ReminderModel
|
ReminderModel remindModel = ReminderModel
|
||||||
.builder()
|
.builder()
|
||||||
.remindText(reminderText)
|
.remindText(reminderText)
|
||||||
.joinButtonId(joinButtonId)
|
.joinButtonId(joinButtonId)
|
||||||
.memberDisplay(MemberNameDisplay.fromMember(event.getMember()))
|
.userDisplay(UserDisplay.fromUser(event.getUser()))
|
||||||
.reminder(ReminderDisplay.fromReminder(createdReminder))
|
.reminder(ReminderDisplay.fromReminder(createdReminder))
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
JoinReminderPayload payload = JoinReminderPayload
|
if(ContextUtils.isNotUserCommand(event)) {
|
||||||
.builder()
|
AServer server = serverManagementService.loadServer(serverId);
|
||||||
.remindedUserId(event.getMember().getIdLong())
|
JoinReminderPayload payload = JoinReminderPayload
|
||||||
.reminderId(createdReminder.getId())
|
.builder()
|
||||||
.serverId(serverId)
|
.remindedUserId(event.getUser().getIdLong())
|
||||||
.build();
|
.reminderId(createdReminder.getId())
|
||||||
|
.serverId(serverId)
|
||||||
|
.build();
|
||||||
|
componentPayloadService.createButtonPayload(joinButtonId, payload, REMINDER_JOIN_BUTTON_ORIGIN, server);
|
||||||
|
}
|
||||||
|
|
||||||
componentPayloadService.createButtonPayload(joinButtonId, payload, REMINDER_JOIN_BUTTON_ORIGIN, aUserInAServer.getServerReference());
|
|
||||||
|
|
||||||
log.info("Notifying user {} about reminder being scheduled.", event.getMember().getId());
|
|
||||||
MessageToSend messageToSend = templateService.renderEmbedTemplate(REMINDER_EMBED_KEY, remindModel, serverId);
|
log.info("Notifying user {} about reminder being scheduled.", event.getUser().getId());
|
||||||
|
MessageToSend messageToSend = templateService.renderEmbedTemplate(REMINDER_EMBED_KEY, remindModel, ContextUtils.serverIdOrNull(event));
|
||||||
return interactionService.replyMessageToSend(messageToSend, event)
|
return interactionService.replyMessageToSend(messageToSend, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
}
|
}
|
||||||
@@ -171,6 +195,8 @@ public class Remind extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(RemindSlashCommandNames.REMIND)
|
.rootCommandName(RemindSlashCommandNames.REMIND)
|
||||||
.commandName("create")
|
.commandName("create")
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -4,17 +4,21 @@ import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
|||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
||||||
import dev.sheldan.abstracto.core.models.ServerChannelMessage;
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
|
import dev.sheldan.abstracto.core.models.template.display.UserDisplay;
|
||||||
import dev.sheldan.abstracto.core.service.ChannelService;
|
import dev.sheldan.abstracto.core.service.ChannelService;
|
||||||
import dev.sheldan.abstracto.core.service.management.UserInServerManagementService;
|
import dev.sheldan.abstracto.core.service.management.UserInServerManagementService;
|
||||||
|
import dev.sheldan.abstracto.core.service.management.UserManagementService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.remind.config.RemindFeatureDefinition;
|
import dev.sheldan.abstracto.remind.config.RemindFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.remind.config.RemindSlashCommandNames;
|
import dev.sheldan.abstracto.remind.config.RemindSlashCommandNames;
|
||||||
@@ -26,6 +30,7 @@ import dev.sheldan.abstracto.remind.service.management.ReminderManagementService
|
|||||||
import dev.sheldan.abstracto.remind.service.management.ReminderParticipantManagementService;
|
import dev.sheldan.abstracto.remind.service.management.ReminderParticipantManagementService;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
import net.dv8tion.jda.api.entities.Member;
|
||||||
|
import net.dv8tion.jda.api.entities.User;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
@@ -57,16 +62,19 @@ public class Reminders extends AbstractConditionableCommand {
|
|||||||
@Autowired
|
@Autowired
|
||||||
private ReminderParticipantManagementService reminderParticipantManagementService;
|
private ReminderParticipantManagementService reminderParticipantManagementService;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private UserManagementService userManagementService;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeAsync(CommandContext commandContext) {
|
public CompletableFuture<CommandResult> executeAsync(CommandContext commandContext) {
|
||||||
Long serverId = commandContext.getGuild().getIdLong();
|
Long serverId = commandContext.getGuild().getIdLong();
|
||||||
Member member = commandContext.getAuthor();
|
Member member = commandContext.getAuthor();
|
||||||
MessageToSend messageToSend = getMessageToSend(serverId, member);
|
MessageToSend messageToSend = getServerReminders(serverId, member);
|
||||||
return FutureUtils.toSingleFutureGeneric(channelService.sendMessageToSendToChannel(messageToSend, commandContext.getChannel()))
|
return FutureUtils.toSingleFutureGeneric(channelService.sendMessageToSendToChannel(messageToSend, commandContext.getChannel()))
|
||||||
.thenApply(aVoid -> CommandResult.fromIgnored());
|
.thenApply(aVoid -> CommandResult.fromIgnored());
|
||||||
}
|
}
|
||||||
|
|
||||||
private MessageToSend getMessageToSend(Long serverId, Member member) {
|
private MessageToSend getServerReminders(Long serverId, Member member) {
|
||||||
AUserInAServer aUserInAServer = userInServerManagementService.loadOrCreateUser(member);
|
AUserInAServer aUserInAServer = userInServerManagementService.loadOrCreateUser(member);
|
||||||
List<Reminder> activeReminders = reminderManagementService.getActiveRemindersForUser(aUserInAServer);
|
List<Reminder> activeReminders = reminderManagementService.getActiveRemindersForUser(aUserInAServer);
|
||||||
List<Reminder> joinedReminders = reminderParticipantManagementService.getActiveReminders(aUserInAServer)
|
List<Reminder> joinedReminders = reminderParticipantManagementService.getActiveReminders(aUserInAServer)
|
||||||
@@ -85,17 +93,37 @@ public class Reminders extends AbstractConditionableCommand {
|
|||||||
RemindersModel model = RemindersModel
|
RemindersModel model = RemindersModel
|
||||||
.builder()
|
.builder()
|
||||||
.reminders(reminders)
|
.reminders(reminders)
|
||||||
.member(member)
|
.userDisplay(UserDisplay.fromUser(member.getUser()))
|
||||||
.build();
|
.build();
|
||||||
log.info("Showing {} reminders for user {} in server {}.", activeReminders.size(), aUserInAServer.getUserReference().getId(), serverId);
|
log.info("Showing {} reminders for user {} in server {}.", activeReminders.size(), aUserInAServer.getUserReference().getId(), serverId);
|
||||||
return templateService.renderEmbedTemplate(REMINDERS_RESPONSE_TEMPLATE, model, serverId);
|
return templateService.renderEmbedTemplate(REMINDERS_RESPONSE_TEMPLATE, model, serverId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private MessageToSend getUserReminders(User user) {
|
||||||
|
AUser aUser = userManagementService.loadOrCreateUser(user.getIdLong());
|
||||||
|
List<Reminder> activeReminders = reminderManagementService.getActiveUserRemindersForUser(aUser);
|
||||||
|
List<ReminderDisplay> reminders = activeReminders
|
||||||
|
.stream()
|
||||||
|
.map(ReminderDisplay::fromReminder)
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
RemindersModel model = RemindersModel
|
||||||
|
.builder()
|
||||||
|
.reminders(reminders)
|
||||||
|
.userDisplay(UserDisplay.fromUser(user))
|
||||||
|
.build();
|
||||||
|
return templateService.renderEmbedTemplate(REMINDERS_RESPONSE_TEMPLATE, model);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
Long serverId = event.getGuild().getIdLong();
|
MessageToSend messageToSend;
|
||||||
Member member = event.getMember();
|
if(ContextUtils.isUserCommand(event)) {
|
||||||
MessageToSend messageToSend = getMessageToSend(serverId, member);
|
messageToSend = getUserReminders(event.getUser());
|
||||||
|
} else {
|
||||||
|
Member member = event.getMember();
|
||||||
|
Long serverId = event.getGuild().getIdLong();
|
||||||
|
messageToSend = getServerReminders(serverId, member);
|
||||||
|
}
|
||||||
return interactionService.replyMessageToSend(messageToSend, event)
|
return interactionService.replyMessageToSend(messageToSend, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
}
|
}
|
||||||
@@ -110,6 +138,8 @@ public class Reminders extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(RemindSlashCommandNames.REMIND)
|
.rootCommandName(RemindSlashCommandNames.REMIND)
|
||||||
.commandName("list")
|
.commandName("list")
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -10,6 +10,8 @@ import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandParame
|
|||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
||||||
import dev.sheldan.abstracto.core.service.management.UserInServerManagementService;
|
import dev.sheldan.abstracto.core.service.management.UserInServerManagementService;
|
||||||
|
import dev.sheldan.abstracto.core.service.management.UserManagementService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.remind.config.RemindFeatureDefinition;
|
import dev.sheldan.abstracto.remind.config.RemindFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.remind.config.RemindSlashCommandNames;
|
import dev.sheldan.abstracto.remind.config.RemindSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.remind.service.ReminderService;
|
import dev.sheldan.abstracto.remind.service.ReminderService;
|
||||||
@@ -36,6 +38,9 @@ public class UnRemind extends AbstractConditionableCommand {
|
|||||||
@Autowired
|
@Autowired
|
||||||
private UserInServerManagementService userInServerManagementService;
|
private UserInServerManagementService userInServerManagementService;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private UserManagementService userManagementService;
|
||||||
|
|
||||||
@Autowired
|
@Autowired
|
||||||
private SlashCommandParameterService slashCommandParameterService;
|
private SlashCommandParameterService slashCommandParameterService;
|
||||||
|
|
||||||
@@ -52,7 +57,11 @@ public class UnRemind extends AbstractConditionableCommand {
|
|||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
Long reminderId = slashCommandParameterService.getCommandOption(REMINDER_ID_PARAMETER, event, Long.class, Integer.class).longValue();
|
Long reminderId = slashCommandParameterService.getCommandOption(REMINDER_ID_PARAMETER, event, Long.class, Integer.class).longValue();
|
||||||
reminderService.unRemind(reminderId, userInServerManagementService.loadOrCreateUser(event.getMember()));
|
if(ContextUtils.isUserCommand(event)) {
|
||||||
|
reminderService.unRemind(reminderId, userManagementService.loadOrCreateUser(event.getUser().getIdLong()));
|
||||||
|
} else {
|
||||||
|
reminderService.unRemind(reminderId, userInServerManagementService.loadOrCreateUser(event.getMember()));
|
||||||
|
}
|
||||||
return interactionService.replyEmbed(UN_REMIND_RESPONSE, event)
|
return interactionService.replyEmbed(UN_REMIND_RESPONSE, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
}
|
}
|
||||||
@@ -74,6 +83,8 @@ public class UnRemind extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(RemindSlashCommandNames.REMIND)
|
.rootCommandName(RemindSlashCommandNames.REMIND)
|
||||||
.commandName("cancel")
|
.commandName("cancel")
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
package dev.sheldan.abstracto.remind.repository;
|
package dev.sheldan.abstracto.remind.repository;
|
||||||
|
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
||||||
import org.springframework.data.jpa.repository.JpaRepository;
|
import org.springframework.data.jpa.repository.JpaRepository;
|
||||||
@@ -11,8 +12,10 @@ import java.util.List;
|
|||||||
public interface ReminderRepository extends JpaRepository<Reminder, Long> {
|
public interface ReminderRepository extends JpaRepository<Reminder, Long> {
|
||||||
|
|
||||||
List<Reminder> getByRemindedUserAndRemindedFalse(AUserInAServer aUserInAServer);
|
List<Reminder> getByRemindedUserAndRemindedFalse(AUserInAServer aUserInAServer);
|
||||||
|
List<Reminder> getByRemindedAUserAndRemindedFalseAndUserCommandTrueAndServerIsNull(AUser aUser);
|
||||||
|
|
||||||
Reminder getByIdAndRemindedUserAndRemindedFalse(Long reminderId, AUserInAServer aUserInAServer);
|
Reminder getByIdAndRemindedUserAndRemindedFalse(Long reminderId, AUserInAServer aUserInAServer);
|
||||||
|
Reminder getByIdAndRemindedAUserAndUserCommandTrue(Long reminderId, AUser aUser);
|
||||||
Reminder getByIdAndRemindedUser(Long reminderId, AUserInAServer aUserInAServer);
|
Reminder getByIdAndRemindedUser(Long reminderId, AUserInAServer aUserInAServer);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,12 +3,11 @@ package dev.sheldan.abstracto.remind.service;
|
|||||||
import dev.sheldan.abstracto.core.models.AServerAChannelAUser;
|
import dev.sheldan.abstracto.core.models.AServerAChannelAUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AChannel;
|
import dev.sheldan.abstracto.core.models.database.AChannel;
|
||||||
import dev.sheldan.abstracto.core.models.database.AServer;
|
import dev.sheldan.abstracto.core.models.database.AServer;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import dev.sheldan.abstracto.core.models.template.display.MemberDisplay;
|
import dev.sheldan.abstracto.core.models.template.display.MemberDisplay;
|
||||||
import dev.sheldan.abstracto.core.models.template.display.MemberNameDisplay;
|
import dev.sheldan.abstracto.core.models.template.display.UserDisplay;
|
||||||
import dev.sheldan.abstracto.core.service.ChannelService;
|
import dev.sheldan.abstracto.core.service.*;
|
||||||
import dev.sheldan.abstracto.core.service.GuildService;
|
|
||||||
import dev.sheldan.abstracto.core.service.MemberService;
|
|
||||||
import dev.sheldan.abstracto.core.service.management.ChannelManagementService;
|
import dev.sheldan.abstracto.core.service.management.ChannelManagementService;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
@@ -18,6 +17,7 @@ import dev.sheldan.abstracto.remind.exception.ReminderNotFoundException;
|
|||||||
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
||||||
import dev.sheldan.abstracto.remind.model.database.ReminderParticipant;
|
import dev.sheldan.abstracto.remind.model.database.ReminderParticipant;
|
||||||
import dev.sheldan.abstracto.remind.model.template.commands.ExecutedReminderModel;
|
import dev.sheldan.abstracto.remind.model.template.commands.ExecutedReminderModel;
|
||||||
|
import dev.sheldan.abstracto.remind.model.template.commands.ReminderDisplay;
|
||||||
import dev.sheldan.abstracto.remind.service.management.ReminderManagementService;
|
import dev.sheldan.abstracto.remind.service.management.ReminderManagementService;
|
||||||
import dev.sheldan.abstracto.remind.service.management.ReminderParticipantManagementService;
|
import dev.sheldan.abstracto.remind.service.management.ReminderParticipantManagementService;
|
||||||
import dev.sheldan.abstracto.scheduling.model.JobParameters;
|
import dev.sheldan.abstracto.scheduling.model.JobParameters;
|
||||||
@@ -55,6 +55,9 @@ public class RemindServiceBean implements ReminderService {
|
|||||||
@Autowired
|
@Autowired
|
||||||
private TemplateService templateService;
|
private TemplateService templateService;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private MessageService messageService;
|
||||||
|
|
||||||
@Autowired
|
@Autowired
|
||||||
private SchedulerService schedulerService;
|
private SchedulerService schedulerService;
|
||||||
|
|
||||||
@@ -64,6 +67,9 @@ public class RemindServiceBean implements ReminderService {
|
|||||||
@Autowired
|
@Autowired
|
||||||
private GuildService guildService;
|
private GuildService guildService;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private UserService userService;
|
||||||
|
|
||||||
@Autowired
|
@Autowired
|
||||||
private RemindServiceBean self;
|
private RemindServiceBean self;
|
||||||
|
|
||||||
@@ -86,15 +92,15 @@ public class RemindServiceBean implements ReminderService {
|
|||||||
@Override
|
@Override
|
||||||
public Reminder createReminderInForUser(AUserInAServer user, String remindText, Duration remindIn, Long channelId, Long messageId) {
|
public Reminder createReminderInForUser(AUserInAServer user, String remindText, Duration remindIn, Long channelId, Long messageId) {
|
||||||
AChannel channel = channelManagementService.loadChannel(channelId);
|
AChannel channel = channelManagementService.loadChannel(channelId);
|
||||||
AServerAChannelAUser aServerAChannelAUser = AServerAChannelAUser
|
|
||||||
.builder()
|
|
||||||
.user(user.getUserReference())
|
|
||||||
.aUserInAServer(user)
|
|
||||||
.guild(user.getServerReference())
|
|
||||||
.channel(channel)
|
|
||||||
.build();
|
|
||||||
Instant remindAt = Instant.now().plusMillis(remindIn.toMillis());
|
Instant remindAt = Instant.now().plusMillis(remindIn.toMillis());
|
||||||
Reminder reminder = reminderManagementService.createReminder(aServerAChannelAUser, remindText, remindAt, messageId);
|
AServerAChannelAUser aServerAChannelAUser = AServerAChannelAUser
|
||||||
|
.builder()
|
||||||
|
.channel(channel)
|
||||||
|
.user(user.getUserReference())
|
||||||
|
.guild(user.getServerReference())
|
||||||
|
.aUserInAServer(user)
|
||||||
|
.build();
|
||||||
|
Reminder reminder = reminderManagementService.createReminder(aServerAChannelAUser, remindText, remindAt, messageId, false, false);
|
||||||
log.info("Creating reminder for user {} in guild {} due at {}.",
|
log.info("Creating reminder for user {} in guild {} due at {}.",
|
||||||
user.getUserReference().getId(), user.getServerReference().getId(), remindAt);
|
user.getUserReference().getId(), user.getServerReference().getId(), remindAt);
|
||||||
|
|
||||||
@@ -102,6 +108,19 @@ public class RemindServiceBean implements ReminderService {
|
|||||||
return reminder;
|
return reminder;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Reminder createReminderInForUser(AUser aUser, String remindText, Duration remindIn) {
|
||||||
|
Instant remindAt = Instant.now().plusMillis(remindIn.toMillis());
|
||||||
|
AServerAChannelAUser aServerAChannelAUser = AServerAChannelAUser
|
||||||
|
.builder()
|
||||||
|
.user(aUser)
|
||||||
|
.build();
|
||||||
|
Reminder reminder = reminderManagementService.createReminder(aServerAChannelAUser, remindText, remindAt, null, true, true);
|
||||||
|
log.info("Creating reminder for user {} due at {}.", aUser.getId(), remindAt);
|
||||||
|
scheduleReminder(remindIn, reminder);
|
||||||
|
return reminder;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Reminder createReminderInForUser(AUserInAServer user, String remindText, Duration remindIn, Long channelId) {
|
public Reminder createReminderInForUser(AUserInAServer user, String remindText, Duration remindIn, Long channelId) {
|
||||||
return createReminderInForUser(user, remindText, remindIn, channelId, null);
|
return createReminderInForUser(user, remindText, remindIn, channelId, null);
|
||||||
@@ -136,30 +155,56 @@ public class RemindServiceBean implements ReminderService {
|
|||||||
@Transactional
|
@Transactional
|
||||||
public void executeReminder(Long reminderId) {
|
public void executeReminder(Long reminderId) {
|
||||||
Reminder reminderToRemindFor = reminderManagementService.loadReminder(reminderId);
|
Reminder reminderToRemindFor = reminderManagementService.loadReminder(reminderId);
|
||||||
if(reminderToRemindFor.isReminded()) {
|
if(reminderToRemindFor.getReminded()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
AServer server = reminderToRemindFor.getServer();
|
Long userId = reminderToRemindFor.getRemindedAUser().getId();
|
||||||
AChannel channel = reminderToRemindFor.getChannel();
|
if(reminderToRemindFor.getSendInDm()) {
|
||||||
Long userId = reminderToRemindFor.getRemindedUser().getUserReference().getId();
|
log.info("Executing reminder {} in DMs of user {}.", reminderId, userId);
|
||||||
log.info("Executing reminder {} in channel {} in server {} for user {}.",
|
Long serverId = reminderToRemindFor.getServer() != null ? reminderToRemindFor.getServer().getId() : null;
|
||||||
reminderId, channel.getId(), server.getId(), userId);
|
Long channelId = reminderToRemindFor.getChannel() != null ? reminderToRemindFor.getChannel().getId() : null;
|
||||||
Optional<Guild> guildToAnswerIn = guildService.getGuildByIdOptional(server.getId());
|
Long messageId = reminderToRemindFor.getMessageId();
|
||||||
if(guildToAnswerIn.isPresent()) {
|
Instant reminderDate = reminderToRemindFor.getReminderDate();
|
||||||
Optional<GuildMessageChannel> channelToAnswerIn = channelService.getMessageChannelFromServerOptional(server.getId(), channel.getId());
|
Instant targetDate = reminderToRemindFor.getTargetDate();
|
||||||
// only send the message if the channel still exists, if not, only set the reminder to reminded.
|
ReminderDisplay reminderDisplay = ReminderDisplay.fromReminder(reminderToRemindFor);
|
||||||
if(channelToAnswerIn.isPresent()) {
|
userService.retrieveUserForId(userId).thenCompose(user -> {
|
||||||
memberService.getMemberInServerAsync(server.getId(), userId).thenAccept(member ->
|
ExecutedReminderModel build = ExecutedReminderModel
|
||||||
self.sendReminderText(reminderId, channelToAnswerIn.get(), member)
|
.builder()
|
||||||
).exceptionally(throwable -> {
|
.reminderId(reminderId)
|
||||||
log.warn("Member {} not anymore in server {} - not reminding.", userId, server.getId(), throwable);
|
.serverId(serverId)
|
||||||
return null;
|
.channelId(channelId)
|
||||||
});
|
.messageId(messageId)
|
||||||
} else {
|
.reminderDisplay(reminderDisplay)
|
||||||
log.warn("Channel {} in server {} to remind user did not exist anymore. Ignoring reminder {}", channel.getId(), server.getId(), reminderId);
|
.userDisplay(UserDisplay.fromUser(user))
|
||||||
}
|
.duration(Duration.between(reminderDate, targetDate))
|
||||||
|
.build();
|
||||||
|
return messageService.sendEmbedToUser(user, REMINDER_TEMPLATE_TEXT, build);
|
||||||
|
}).exceptionally(throwable -> {
|
||||||
|
log.error("Failed to remind user {} about reminder {}.", userId, reminderId, throwable);
|
||||||
|
return null;
|
||||||
|
});
|
||||||
} else {
|
} else {
|
||||||
log.warn("Guild {} to remind user in did not exist anymore. Ignoring reminder {}.", server.getId(), reminderId);
|
AServer server = reminderToRemindFor.getServer();
|
||||||
|
AChannel channel = reminderToRemindFor.getChannel();
|
||||||
|
log.info("Executing reminder {} in channel {} in server {} for user {}.",
|
||||||
|
reminderId, channel.getId(), server.getId(), userId);
|
||||||
|
Optional<Guild> guildToAnswerIn = guildService.getGuildByIdOptional(server.getId());
|
||||||
|
if(guildToAnswerIn.isPresent()) {
|
||||||
|
Optional<GuildMessageChannel> channelToAnswerIn = channelService.getMessageChannelFromServerOptional(server.getId(), channel.getId());
|
||||||
|
// only send the message if the channel still exists, if not, only set the reminder to reminded.
|
||||||
|
if(channelToAnswerIn.isPresent()) {
|
||||||
|
memberService.getMemberInServerAsync(server.getId(), userId).thenCompose(member ->
|
||||||
|
self.sendReminderText(reminderId, channelToAnswerIn.get(), member)
|
||||||
|
).exceptionally(throwable -> {
|
||||||
|
log.warn("Member {} not anymore in server {} - not reminding.", userId, server.getId(), throwable);
|
||||||
|
return null;
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
log.warn("Channel {} in server {} to remind user did not exist anymore. Ignoring reminder {}", channel.getId(), server.getId(), reminderId);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
log.warn("Guild {} to remind user in did not exist anymore. Ignoring reminder {}.", server.getId(), reminderId);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
reminderManagementService.setReminded(reminderToRemindFor);
|
reminderManagementService.setReminded(reminderToRemindFor);
|
||||||
}
|
}
|
||||||
@@ -173,11 +218,12 @@ public class RemindServiceBean implements ReminderService {
|
|||||||
.stream()
|
.stream()
|
||||||
.map(reminderParticipant -> MemberDisplay.fromAUserInAServer(reminderParticipant.getParticipant()))
|
.map(reminderParticipant -> MemberDisplay.fromAUserInAServer(reminderParticipant.getParticipant()))
|
||||||
.collect(Collectors.toList());
|
.collect(Collectors.toList());
|
||||||
|
ReminderDisplay reminderDisplay = ReminderDisplay.fromReminder(reminder);
|
||||||
ExecutedReminderModel build = ExecutedReminderModel
|
ExecutedReminderModel build = ExecutedReminderModel
|
||||||
.builder()
|
.builder()
|
||||||
.reminder(reminder)
|
|
||||||
.reminderParticipants(participantsDisplays)
|
.reminderParticipants(participantsDisplays)
|
||||||
.memberNameDisplay(MemberNameDisplay.fromMember(member))
|
.reminderDisplay(reminderDisplay)
|
||||||
|
.userDisplay(UserDisplay.fromUser(member.getUser()))
|
||||||
.duration(Duration.between(reminder.getReminderDate(), reminder.getTargetDate()))
|
.duration(Duration.between(reminder.getReminderDate(), reminder.getTargetDate()))
|
||||||
.build();
|
.build();
|
||||||
MessageToSend messageToSend = templateService.renderEmbedTemplate(REMINDER_TEMPLATE_TEXT, build, channelToAnswerIn.getGuild().getIdLong());
|
MessageToSend messageToSend = templateService.renderEmbedTemplate(REMINDER_TEMPLATE_TEXT, build, channelToAnswerIn.getGuild().getIdLong());
|
||||||
@@ -195,10 +241,21 @@ public class RemindServiceBean implements ReminderService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void unRemind(Long reminderId, AUser aUser) {
|
||||||
|
log.info("Trying to end reminder {} for user {}.", reminderId, aUser.getId());
|
||||||
|
Reminder reminder = reminderManagementService.getReminderByAndByUserNotRemindedForUserCommand(aUser, reminderId).orElseThrow(() -> new ReminderNotFoundException(reminderId));
|
||||||
|
reminder.setReminded(true);
|
||||||
|
if(reminder.getJobTriggerKey() != null) {
|
||||||
|
log.debug("Stopping scheduled trigger {} for reminder {}.", reminder.getJobTriggerKey(), reminderId);
|
||||||
|
schedulerService.stopTrigger(reminder.getJobTriggerKey());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void snoozeReminder(Long reminderId, AUserInAServer user, Duration newDuration) {
|
public void snoozeReminder(Long reminderId, AUserInAServer user, Duration newDuration) {
|
||||||
Reminder reminder = reminderManagementService.getReminderByAndByUser(user, reminderId).orElseThrow(() -> new ReminderNotFoundException(reminderId));
|
Reminder reminder = reminderManagementService.getReminderByAndByUser(user, reminderId).orElseThrow(() -> new ReminderNotFoundException(reminderId));
|
||||||
if(reminder.getTargetDate().isAfter(Instant.now()) && !reminder.isReminded()) {
|
if(reminder.getTargetDate().isAfter(Instant.now()) && !reminder.getReminded()) {
|
||||||
throw new NotPossibleToSnoozeException();
|
throw new NotPossibleToSnoozeException();
|
||||||
}
|
}
|
||||||
log.info("Snoozing reminder {} to be executed in {}.", reminderId, newDuration);
|
log.info("Snoozing reminder {} to be executed in {}.", reminderId, newDuration);
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package dev.sheldan.abstracto.remind.service.management;
|
package dev.sheldan.abstracto.remind.service.management;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.AServerAChannelAUser;
|
import dev.sheldan.abstracto.core.models.AServerAChannelAUser;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import dev.sheldan.abstracto.remind.exception.ReminderNotFoundException;
|
import dev.sheldan.abstracto.remind.exception.ReminderNotFoundException;
|
||||||
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
||||||
@@ -21,20 +22,20 @@ public class ReminderManagementServiceBean implements ReminderManagementService
|
|||||||
private ReminderRepository reminderRepository;
|
private ReminderRepository reminderRepository;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Reminder createReminder(AServerAChannelAUser userToBeReminded, String text, Instant timeToBeRemindedAt, Long messageId) {
|
public Reminder createReminder(AServerAChannelAUser userToBeReminded, String text, Instant timeToBeRemindedAt, Long messageId, Boolean sendInDms, Boolean userCommand) {
|
||||||
Reminder reminder = Reminder.builder()
|
Reminder reminder = Reminder.builder()
|
||||||
.channel(userToBeReminded.getChannel())
|
.channel(userToBeReminded.getChannel())
|
||||||
.server(userToBeReminded.getGuild())
|
.server(userToBeReminded.getGuild())
|
||||||
.remindedUser(userToBeReminded.getAUserInAServer())
|
.remindedUser(userToBeReminded.getAUserInAServer())
|
||||||
|
.remindedAUser(userToBeReminded.getUser())
|
||||||
|
.sendInDm(sendInDms)
|
||||||
.reminded(false)
|
.reminded(false)
|
||||||
.text(text)
|
.text(text)
|
||||||
.reminderDate(Instant.now())
|
.reminderDate(Instant.now())
|
||||||
|
.userCommand(userCommand)
|
||||||
.targetDate(timeToBeRemindedAt)
|
.targetDate(timeToBeRemindedAt)
|
||||||
.messageId(messageId)
|
.messageId(messageId)
|
||||||
.build();
|
.build();
|
||||||
log.info("Creating reminder for user {} in server {} in message {} to be reminded at {}.",
|
|
||||||
userToBeReminded.getAUserInAServer().getUserReference().getId(), userToBeReminded.getGuild().getId(), messageId, timeToBeRemindedAt);
|
|
||||||
|
|
||||||
return reminderRepository.save(reminder);
|
return reminderRepository.save(reminder);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -65,6 +66,16 @@ public class ReminderManagementServiceBean implements ReminderManagementService
|
|||||||
return reminderRepository.getByRemindedUserAndRemindedFalse(aUserInAServer);
|
return reminderRepository.getByRemindedUserAndRemindedFalse(aUserInAServer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<Reminder> getActiveUserRemindersForUser(AUser aUser) {
|
||||||
|
return reminderRepository.getByRemindedAUserAndRemindedFalseAndUserCommandTrueAndServerIsNull(aUser);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Optional<Reminder> getReminderByAndByUserNotRemindedForUserCommand(AUser aUser, Long reminderId) {
|
||||||
|
return Optional.ofNullable(reminderRepository.getByIdAndRemindedAUserAndUserCommandTrue(reminderId, aUser));
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Optional<Reminder> getReminderByAndByUserNotReminded(AUserInAServer aUserInAServer, Long reminderId) {
|
public Optional<Reminder> getReminderByAndByUserNotReminded(AUserInAServer aUserInAServer, Long reminderId) {
|
||||||
return Optional.ofNullable(reminderRepository.getByIdAndRemindedUserAndRemindedFalse(reminderId, aUserInAServer));
|
return Optional.ofNullable(reminderRepository.getByIdAndRemindedUserAndRemindedFalse(reminderId, aUserInAServer));
|
||||||
|
|||||||
@@ -2,9 +2,35 @@
|
|||||||
<databaseChangeLog xmlns="http://www.liquibase.org/xml/ns/dbchangelog"
|
<databaseChangeLog xmlns="http://www.liquibase.org/xml/ns/dbchangelog"
|
||||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||||
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog https://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-4.26.xsd" >
|
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog https://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-4.26.xsd" >
|
||||||
|
<changeSet author="Sheldan" id="reminder-add_user_installable_support">
|
||||||
|
<addColumn tableName="reminder">
|
||||||
|
<column name="user_id" type="BIGINT">
|
||||||
|
<constraints nullable="true"/>
|
||||||
|
</column>
|
||||||
|
<column name="send_dm" type="BOOLEAN" value="false">
|
||||||
|
<constraints nullable="false"/>
|
||||||
|
</column>
|
||||||
|
<column name="user_command" type="BOOLEAN" value="false">
|
||||||
|
<constraints nullable="false"/>
|
||||||
|
</column>
|
||||||
|
</addColumn>
|
||||||
|
<sql>
|
||||||
|
update reminder set user_id = (select ua.user_id from user_in_server ua where ua.user_in_server_id = user_in_server_id order by ua.server_id limit 1)
|
||||||
|
</sql>
|
||||||
|
<addNotNullConstraint columnName="user_id"
|
||||||
|
tableName="reminder"
|
||||||
|
validate="true"/>
|
||||||
|
<sql>
|
||||||
|
ALTER TABLE reminder ALTER COLUMN server_id DROP NOT NULL;
|
||||||
|
ALTER TABLE reminder ALTER COLUMN channel_id DROP NOT NULL;
|
||||||
|
ALTER TABLE reminder ALTER COLUMN user_in_server_id DROP NOT NULL;
|
||||||
|
</sql>
|
||||||
|
</changeSet>
|
||||||
|
|
||||||
<changeSet author="Sheldan" id="reminder-resize_text">
|
<changeSet author="Sheldan" id="reminder-resize_text">
|
||||||
<modifyDataType columnName="text"
|
<modifyDataType columnName="text"
|
||||||
newDataType="VARCHAR(4000)"
|
newDataType="VARCHAR(4000)"
|
||||||
tableName="reminder"/>
|
tableName="reminder"/>
|
||||||
</changeSet>
|
</changeSet>
|
||||||
|
|
||||||
</databaseChangeLog>
|
</databaseChangeLog>
|
||||||
@@ -1,48 +0,0 @@
|
|||||||
package dev.sheldan.abstracto.remind.command;
|
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
|
||||||
import dev.sheldan.abstracto.core.service.management.UserInServerManagementService;
|
|
||||||
import dev.sheldan.abstracto.core.test.command.CommandConfigValidator;
|
|
||||||
import dev.sheldan.abstracto.core.test.command.CommandTestUtilities;
|
|
||||||
import dev.sheldan.abstracto.remind.service.ReminderService;
|
|
||||||
import org.junit.Test;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.mockito.InjectMocks;
|
|
||||||
import org.mockito.Mock;
|
|
||||||
import org.mockito.Mockito;
|
|
||||||
import org.mockito.junit.MockitoJUnitRunner;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
|
|
||||||
import static org.mockito.Mockito.*;
|
|
||||||
|
|
||||||
@RunWith(MockitoJUnitRunner.class)
|
|
||||||
public class UnRemindTest {
|
|
||||||
|
|
||||||
@InjectMocks
|
|
||||||
private UnRemind testUnit;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private ReminderService reminderService;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private UserInServerManagementService userInServerManagementService;
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testExecuteCommand() {
|
|
||||||
Long reminderId = 6L;
|
|
||||||
CommandContext withParameters = CommandTestUtilities.getWithParameters(Arrays.asList(reminderId));
|
|
||||||
AUserInAServer user = Mockito.mock(AUserInAServer.class);
|
|
||||||
when(userInServerManagementService.loadOrCreateUser(withParameters.getAuthor())).thenReturn(user);
|
|
||||||
CommandResult result = testUnit.execute(withParameters);
|
|
||||||
verify(reminderService, times(1)).unRemind(reminderId, user);
|
|
||||||
CommandTestUtilities.checkSuccessfulCompletion(result);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void validateCommand() {
|
|
||||||
CommandConfigValidator.validateCommandConfiguration(testUnit.getConfiguration());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,267 +0,0 @@
|
|||||||
package dev.sheldan.abstracto.remind.service;
|
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.AServerAChannelAUser;
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AChannel;
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AServer;
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AUser;
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
|
||||||
import dev.sheldan.abstracto.core.service.ChannelService;
|
|
||||||
import dev.sheldan.abstracto.core.service.GuildService;
|
|
||||||
import dev.sheldan.abstracto.core.service.MemberService;
|
|
||||||
import dev.sheldan.abstracto.core.service.management.ChannelManagementService;
|
|
||||||
import dev.sheldan.abstracto.remind.exception.ReminderNotFoundException;
|
|
||||||
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
|
||||||
import dev.sheldan.abstracto.remind.service.management.ReminderManagementService;
|
|
||||||
import dev.sheldan.abstracto.remind.service.management.ReminderParticipantManagementService;
|
|
||||||
import dev.sheldan.abstracto.scheduling.model.JobParameters;
|
|
||||||
import dev.sheldan.abstracto.scheduling.service.SchedulerService;
|
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
|
||||||
import net.dv8tion.jda.api.entities.*;
|
|
||||||
import net.dv8tion.jda.api.entities.channel.unions.GuildMessageChannelUnion;
|
|
||||||
import net.dv8tion.jda.api.entities.channel.unions.MessageChannelUnion;
|
|
||||||
import net.dv8tion.jda.api.utils.ImageProxy;
|
|
||||||
import org.junit.Assert;
|
|
||||||
import org.junit.Before;
|
|
||||||
import org.junit.Test;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.mockito.InjectMocks;
|
|
||||||
import org.mockito.Mock;
|
|
||||||
import org.mockito.Mockito;
|
|
||||||
import org.mockito.junit.MockitoJUnitRunner;
|
|
||||||
|
|
||||||
import java.time.Duration;
|
|
||||||
import java.time.Instant;
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.Date;
|
|
||||||
import java.util.Optional;
|
|
||||||
import java.util.concurrent.CompletableFuture;
|
|
||||||
import java.util.concurrent.ScheduledExecutorService;
|
|
||||||
|
|
||||||
import static org.mockito.Mockito.*;
|
|
||||||
|
|
||||||
@RunWith(MockitoJUnitRunner.class)
|
|
||||||
public class RemindServiceBeanTest {
|
|
||||||
|
|
||||||
@InjectMocks
|
|
||||||
private RemindServiceBean testUnit;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private ReminderManagementService reminderManagementService;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private ChannelManagementService channelManagementService;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private TemplateService templateService;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private SchedulerService schedulerService;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private GuildService guildService;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private MemberService memberService;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private RemindServiceBean self;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private ChannelService channelService;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private Message message;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private GuildMessageChannelUnion guildMessageChannelUnion;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private MessageChannelUnion messageChannelUnion;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private ScheduledExecutorService instantReminderScheduler;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private ReminderParticipantManagementService reminderParticipantManagementService;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private AServer server;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private AUserInAServer aUserInAServer;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private AUser user;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private User jdaUser;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private AChannel aChannel;
|
|
||||||
|
|
||||||
private static final Long REMINDER_ID = 5L;
|
|
||||||
private static final Long CHANNEL_ID = 6L;
|
|
||||||
private static final Long SERVER_ID = 8L;
|
|
||||||
private static final Long USER_ID = 9L;
|
|
||||||
|
|
||||||
@Before
|
|
||||||
public void setup() {
|
|
||||||
when(message.getIdLong()).thenReturn(5L);
|
|
||||||
when(message.getChannel()).thenReturn(messageChannelUnion);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void createReminderWithScheduler() {
|
|
||||||
String remindText = "text";
|
|
||||||
String triggerKey = "trigger";
|
|
||||||
Duration duration = Duration.ofSeconds(62);
|
|
||||||
when(message.getChannel()).thenReturn(messageChannelUnion);
|
|
||||||
when(aUserInAServer.getServerReference()).thenReturn(server);
|
|
||||||
when(aUserInAServer.getUserReference()).thenReturn(user);
|
|
||||||
Instant targetDate = Instant.now().plus(duration);
|
|
||||||
Reminder createdReminder = Mockito.mock(Reminder.class);
|
|
||||||
when(createdReminder.getTargetDate()).thenReturn(targetDate);
|
|
||||||
Long messageId = 5L;
|
|
||||||
when(reminderManagementService.createReminder(any(AServerAChannelAUser.class), eq(remindText), any(Instant.class), eq(messageId))).thenReturn(createdReminder);
|
|
||||||
when(schedulerService.executeJobWithParametersOnce(eq("reminderJob"), eq("utility"), any(JobParameters.class), eq(Date.from(targetDate)))).thenReturn(triggerKey);
|
|
||||||
Reminder returnedReminder = testUnit.createReminderInForUser(aUserInAServer, remindText, duration, message);
|
|
||||||
verify(reminderManagementService, times(1)).saveReminder(createdReminder);
|
|
||||||
Assert.assertEquals(createdReminder, returnedReminder);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void createReminderWithoutScheduler() {
|
|
||||||
String remindText = "text";
|
|
||||||
Duration duration = Duration.ofSeconds(50);
|
|
||||||
when(message.getChannel()).thenReturn(messageChannelUnion);
|
|
||||||
when(messageChannelUnion.getIdLong()).thenReturn(CHANNEL_ID);
|
|
||||||
when(channelManagementService.loadChannel(CHANNEL_ID)).thenReturn(aChannel);
|
|
||||||
Reminder createdReminder = Mockito.mock(Reminder.class);
|
|
||||||
when(createdReminder.getText()).thenReturn(remindText);
|
|
||||||
Long messageId = 5L;
|
|
||||||
when(aUserInAServer.getServerReference()).thenReturn(server);
|
|
||||||
when(aUserInAServer.getUserReference()).thenReturn(user);
|
|
||||||
when(reminderManagementService.createReminder(any(AServerAChannelAUser.class), eq(remindText), any(Instant.class), eq(messageId))).thenReturn(createdReminder);
|
|
||||||
Reminder returnedReminder = testUnit.createReminderInForUser(aUserInAServer, remindText, duration, message);
|
|
||||||
verify(reminderManagementService, times(0)).saveReminder(createdReminder);
|
|
||||||
Assert.assertEquals(remindText, returnedReminder.getText());
|
|
||||||
Assert.assertEquals(createdReminder.getId(), returnedReminder.getId());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testExecuteReminder() {
|
|
||||||
Reminder remindedReminder = Mockito.mock(Reminder.class);
|
|
||||||
when(remindedReminder.getRemindedUser()).thenReturn(aUserInAServer);
|
|
||||||
when(remindedReminder.getChannel()).thenReturn(aChannel);
|
|
||||||
when(remindedReminder.getServer()).thenReturn(server);
|
|
||||||
when(aChannel.getId()).thenReturn(CHANNEL_ID);
|
|
||||||
when(server.getId()).thenReturn(SERVER_ID);
|
|
||||||
when(aUserInAServer.getUserReference()).thenReturn(user);
|
|
||||||
when(user.getId()).thenReturn(USER_ID);
|
|
||||||
when(reminderManagementService.loadReminder(REMINDER_ID)).thenReturn(remindedReminder);
|
|
||||||
Guild guildMock = Mockito.mock(Guild.class);
|
|
||||||
when(guildService.getGuildByIdOptional(SERVER_ID)).thenReturn(Optional.of(guildMock));
|
|
||||||
when(channelService.getMessageChannelFromServerOptional(SERVER_ID, CHANNEL_ID)).thenReturn(Optional.of(guildMessageChannelUnion));
|
|
||||||
Member mockedMember = Mockito.mock(Member.class);
|
|
||||||
when(memberService.getMemberInServerAsync(SERVER_ID, USER_ID)).thenReturn(CompletableFuture.completedFuture(mockedMember));
|
|
||||||
testUnit.executeReminder(REMINDER_ID);
|
|
||||||
verify(reminderManagementService, times(1)).setReminded(remindedReminder);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testExecuteReminderFromNotFoundChannel() {
|
|
||||||
Reminder remindedReminder = Mockito.mock(Reminder.class);
|
|
||||||
when(remindedReminder.getChannel()).thenReturn(aChannel);
|
|
||||||
when(remindedReminder.getServer()).thenReturn(server);
|
|
||||||
when(server.getId()).thenReturn(SERVER_ID);
|
|
||||||
when(aChannel.getId()).thenReturn(CHANNEL_ID);
|
|
||||||
when(reminderManagementService.loadReminder(REMINDER_ID)).thenReturn(remindedReminder);
|
|
||||||
Guild guildMock = Mockito.mock(Guild.class);
|
|
||||||
when(guildService.getGuildByIdOptional(SERVER_ID)).thenReturn(Optional.of(guildMock));
|
|
||||||
when(aUserInAServer.getUserReference()).thenReturn(user);
|
|
||||||
when(remindedReminder.getRemindedUser()).thenReturn(aUserInAServer);
|
|
||||||
when(channelService.getMessageChannelFromServerOptional(SERVER_ID, CHANNEL_ID)).thenReturn(Optional.empty());
|
|
||||||
testUnit.executeReminder(REMINDER_ID);
|
|
||||||
verify(reminderManagementService, times(1)).setReminded(remindedReminder);
|
|
||||||
verify(self, times(0)).sendReminderText(anyLong(), any(), any(Member.class));
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testExecuteReminderFromNotFoundGuild() {
|
|
||||||
Long reminderId = 5L;
|
|
||||||
Reminder remindedReminder = Mockito.mock(Reminder.class);
|
|
||||||
when(remindedReminder.getChannel()).thenReturn(aChannel);
|
|
||||||
when(remindedReminder.getServer()).thenReturn(server);
|
|
||||||
when(server.getId()).thenReturn(SERVER_ID);
|
|
||||||
when(remindedReminder.getRemindedUser()).thenReturn(aUserInAServer);
|
|
||||||
when(aUserInAServer.getUserReference()).thenReturn(user);
|
|
||||||
when(reminderManagementService.loadReminder(reminderId)).thenReturn(remindedReminder);
|
|
||||||
when(guildService.getGuildByIdOptional(SERVER_ID)).thenReturn(Optional.empty());
|
|
||||||
testUnit.executeReminder(reminderId);
|
|
||||||
verify(reminderManagementService, times(1)).setReminded(remindedReminder);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testExecuteRemindedReminder() {
|
|
||||||
Reminder remindedReminder = Mockito.mock(Reminder.class);
|
|
||||||
when(remindedReminder.isReminded()).thenReturn(true);
|
|
||||||
when(reminderManagementService.loadReminder(REMINDER_ID)).thenReturn(remindedReminder);
|
|
||||||
testUnit.executeReminder(REMINDER_ID);
|
|
||||||
verify(guildService, times(0)).getGuildByIdOptional(anyLong());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testUnRemindScheduledReminder() {
|
|
||||||
String triggerKey = "trigger";
|
|
||||||
Reminder reminderToUnRemind = Mockito.mock(Reminder.class);
|
|
||||||
when(reminderToUnRemind.getJobTriggerKey()).thenReturn(triggerKey);
|
|
||||||
when(aUserInAServer.getServerReference()).thenReturn(server);
|
|
||||||
when(aUserInAServer.getUserReference()).thenReturn(user);
|
|
||||||
when(reminderManagementService.getReminderByAndByUserNotReminded(aUserInAServer, REMINDER_ID)).thenReturn(Optional.of(reminderToUnRemind));
|
|
||||||
testUnit.unRemind(REMINDER_ID, aUserInAServer);
|
|
||||||
verify(schedulerService, times(1)).stopTrigger(triggerKey);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testUnRemindNonScheduledReminder() {
|
|
||||||
Reminder reminderToUnRemind = Mockito.mock(Reminder.class);
|
|
||||||
when(aUserInAServer.getServerReference()).thenReturn(server);
|
|
||||||
when(aUserInAServer.getUserReference()).thenReturn(user);
|
|
||||||
when(reminderManagementService.getReminderByAndByUserNotReminded(aUserInAServer, REMINDER_ID)).thenReturn(Optional.of(reminderToUnRemind));
|
|
||||||
testUnit.unRemind(REMINDER_ID, aUserInAServer);
|
|
||||||
verify(schedulerService, times(0)).stopTrigger(anyString());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test(expected = ReminderNotFoundException.class)
|
|
||||||
public void testUnRemindNonExistingReminder() {
|
|
||||||
when(aUserInAServer.getServerReference()).thenReturn(server);
|
|
||||||
when(aUserInAServer.getUserReference()).thenReturn(user);
|
|
||||||
when(reminderManagementService.getReminderByAndByUserNotReminded(aUserInAServer, REMINDER_ID)).thenReturn(Optional.empty());
|
|
||||||
testUnit.unRemind(REMINDER_ID, aUserInAServer);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testSendReminderText() {
|
|
||||||
Member remindedMember = Mockito.mock(Member.class);
|
|
||||||
Guild guild = Mockito.mock(Guild.class);
|
|
||||||
when(remindedMember.getGuild()).thenReturn(guild);
|
|
||||||
when(guild.getIdLong()).thenReturn(8L);
|
|
||||||
when(remindedMember.getIdLong()).thenReturn(9L);
|
|
||||||
when(remindedMember.getUser()).thenReturn(jdaUser);
|
|
||||||
when(remindedMember.getEffectiveAvatar()).thenReturn(Mockito.mock(ImageProxy.class));
|
|
||||||
when(jdaUser.getDefaultAvatar()).thenReturn(Mockito.mock(ImageProxy.class));
|
|
||||||
Reminder remindedReminder = Mockito.mock(Reminder.class);
|
|
||||||
when(remindedReminder.getTargetDate()).thenReturn(Instant.now());
|
|
||||||
when(remindedReminder.getReminderDate()).thenReturn(Instant.now());
|
|
||||||
when(reminderManagementService.loadReminder(REMINDER_ID)).thenReturn(remindedReminder);
|
|
||||||
MessageToSend messageToSend = Mockito.mock(MessageToSend.class);
|
|
||||||
when(guildMessageChannelUnion.getGuild()).thenReturn(guild);
|
|
||||||
when(templateService.renderEmbedTemplate(eq(RemindServiceBean.REMINDER_TEMPLATE_TEXT), any(), eq(SERVER_ID))).thenReturn(messageToSend);
|
|
||||||
when(channelService.sendMessageToSendToChannel(messageToSend, guildMessageChannelUnion)).thenReturn(Arrays.asList(CompletableFuture.completedFuture(null)));
|
|
||||||
CompletableFuture<Void> future = testUnit.sendReminderText(REMINDER_ID, guildMessageChannelUnion, remindedMember);
|
|
||||||
future.join();
|
|
||||||
Assert.assertFalse(future.isCompletedExceptionally());
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
@@ -1,132 +0,0 @@
|
|||||||
package dev.sheldan.abstracto.remind.service.management;
|
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.AServerAChannelAUser;
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AChannel;
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AServer;
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AUser;
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
|
||||||
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
|
||||||
import dev.sheldan.abstracto.remind.repository.ReminderRepository;
|
|
||||||
import org.junit.Assert;
|
|
||||||
import org.junit.Test;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.mockito.ArgumentCaptor;
|
|
||||||
import org.mockito.InjectMocks;
|
|
||||||
import org.mockito.Mock;
|
|
||||||
import org.mockito.Mockito;
|
|
||||||
import org.mockito.junit.MockitoJUnitRunner;
|
|
||||||
|
|
||||||
import java.time.Instant;
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
import java.util.Optional;
|
|
||||||
|
|
||||||
import static org.mockito.Mockito.*;
|
|
||||||
|
|
||||||
@RunWith(MockitoJUnitRunner.class)
|
|
||||||
public class ReminderManagementServiceBeanTest {
|
|
||||||
|
|
||||||
@InjectMocks
|
|
||||||
private ReminderManagementServiceBean testUnit;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private ReminderRepository reminderRepository;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private AUserInAServer aUserInAServer;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private AChannel channel;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private AServer server;
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private Reminder reminder;
|
|
||||||
|
|
||||||
private static final Long REMINDER_ID = 8L;
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testCreateReminder() {
|
|
||||||
AServerAChannelAUser serverAChannelAUser = Mockito.mock(AServerAChannelAUser.class);
|
|
||||||
AUser user = Mockito.mock(AUser.class);
|
|
||||||
when(aUserInAServer.getUserReference()).thenReturn(user);
|
|
||||||
when(serverAChannelAUser.getAUserInAServer()).thenReturn(aUserInAServer);
|
|
||||||
when(serverAChannelAUser.getGuild()).thenReturn(server);
|
|
||||||
when(serverAChannelAUser.getChannel()).thenReturn(channel);
|
|
||||||
String reminderText = "text";
|
|
||||||
Instant reminderTargetDate = Instant.ofEpochSecond(1590615937);
|
|
||||||
Long messageId = 5L;
|
|
||||||
ArgumentCaptor<Reminder> reminderArgumentCaptor = ArgumentCaptor.forClass(Reminder.class);
|
|
||||||
Reminder savedReminder = Mockito.mock(Reminder.class);
|
|
||||||
when(reminderRepository.save(reminderArgumentCaptor.capture())).thenReturn(savedReminder);
|
|
||||||
Reminder createdReminder = testUnit.createReminder(serverAChannelAUser, reminderText, reminderTargetDate, messageId);
|
|
||||||
Assert.assertEquals(savedReminder, createdReminder);
|
|
||||||
Reminder capturedReminder = reminderArgumentCaptor.getValue();
|
|
||||||
Assert.assertEquals(messageId, capturedReminder.getMessageId());
|
|
||||||
Assert.assertEquals(aUserInAServer, capturedReminder.getRemindedUser());
|
|
||||||
Assert.assertEquals(server, capturedReminder.getServer());
|
|
||||||
Assert.assertEquals(reminderText, capturedReminder.getText());
|
|
||||||
Assert.assertEquals(reminderTargetDate, capturedReminder.getTargetDate());
|
|
||||||
Assert.assertEquals(channel, capturedReminder.getChannel());
|
|
||||||
Assert.assertFalse(capturedReminder.isReminded());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testSetReminded() {
|
|
||||||
testUnit.setReminded(reminder);
|
|
||||||
verify(reminder, times(1)).setReminded(true);
|
|
||||||
verify(reminderRepository, times(1)).save(reminder);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testSaveReminder() {
|
|
||||||
testUnit.saveReminder(reminder);
|
|
||||||
verify(reminderRepository, times(1)).save(reminder);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testRetrieveActiveReminders() {
|
|
||||||
Reminder reminder2 = Mockito.mock(Reminder.class);
|
|
||||||
List<Reminder> reminders = Arrays.asList(reminder, reminder2);
|
|
||||||
when(reminderRepository.getByRemindedUserAndRemindedFalse(aUserInAServer)).thenReturn(reminders);
|
|
||||||
List<Reminder> activeRemindersForUser = testUnit.getActiveRemindersForUser(aUserInAServer);
|
|
||||||
for (int i = 0; i < reminders.size(); i++) {
|
|
||||||
Reminder reference = reminders.get(i);
|
|
||||||
Reminder returned = activeRemindersForUser.get(i);
|
|
||||||
Assert.assertEquals(reference, returned);
|
|
||||||
}
|
|
||||||
Assert.assertEquals(reminders.size(), activeRemindersForUser.size());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testGetReminderByIdAndNotReminded() {
|
|
||||||
when(reminderRepository.getByIdAndRemindedUserAndRemindedFalse(REMINDER_ID, aUserInAServer)).thenReturn(reminder);
|
|
||||||
Optional<Reminder> returned = testUnit.getReminderByAndByUserNotReminded(aUserInAServer, REMINDER_ID);
|
|
||||||
Assert.assertTrue(returned.isPresent());
|
|
||||||
returned.ifPresent(returnedReminder -> Assert.assertEquals(reminder, returnedReminder));
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testGetReminderByIdAndNotRemindedNothingFound() {
|
|
||||||
when(reminderRepository.getByIdAndRemindedUserAndRemindedFalse(REMINDER_ID, aUserInAServer)).thenReturn(null);
|
|
||||||
Optional<Reminder> returned = testUnit.getReminderByAndByUserNotReminded(aUserInAServer, REMINDER_ID);
|
|
||||||
Assert.assertFalse(returned.isPresent());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testLoadingReminder() {
|
|
||||||
when(reminderRepository.findById(REMINDER_ID)).thenReturn(Optional.of(reminder));
|
|
||||||
Optional<Reminder> returned = testUnit.loadReminderOptional(REMINDER_ID);
|
|
||||||
Assert.assertTrue(returned.isPresent());
|
|
||||||
returned.ifPresent(returnedReminder -> Assert.assertEquals(reminder, returnedReminder));
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testLoadingReminderNotFound() {
|
|
||||||
when(reminderRepository.findById(REMINDER_ID)).thenReturn(Optional.empty());
|
|
||||||
Optional<Reminder> returned = testUnit.loadReminderOptional(REMINDER_ID);
|
|
||||||
Assert.assertFalse(returned.isPresent());
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
@@ -2,6 +2,7 @@ package dev.sheldan.abstracto.remind.model.database;
|
|||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.database.AChannel;
|
import dev.sheldan.abstracto.core.models.database.AChannel;
|
||||||
import dev.sheldan.abstracto.core.models.database.AServer;
|
import dev.sheldan.abstracto.core.models.database.AServer;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import lombok.*;
|
import lombok.*;
|
||||||
|
|
||||||
@@ -25,18 +26,22 @@ public class Reminder implements Serializable {
|
|||||||
private Long id;
|
private Long id;
|
||||||
|
|
||||||
@ManyToOne(fetch = FetchType.LAZY)
|
@ManyToOne(fetch = FetchType.LAZY)
|
||||||
@JoinColumn(name = "user_in_server_id", nullable = false)
|
@JoinColumn(name = "user_in_server_id")
|
||||||
private AUserInAServer remindedUser;
|
private AUserInAServer remindedUser;
|
||||||
|
|
||||||
|
@ManyToOne(fetch = FetchType.LAZY)
|
||||||
|
@JoinColumn(name = "user_id")
|
||||||
|
private AUser remindedAUser;
|
||||||
|
|
||||||
@Column(name = "message_id")
|
@Column(name = "message_id")
|
||||||
private Long messageId;
|
private Long messageId;
|
||||||
|
|
||||||
@ManyToOne(fetch = FetchType.LAZY)
|
@ManyToOne(fetch = FetchType.LAZY)
|
||||||
@JoinColumn(name = "channel_id", nullable = false)
|
@JoinColumn(name = "channel_id")
|
||||||
private AChannel channel;
|
private AChannel channel;
|
||||||
|
|
||||||
@ManyToOne(fetch = FetchType.LAZY)
|
@ManyToOne(fetch = FetchType.LAZY)
|
||||||
@JoinColumn(name = "server_id", nullable = false)
|
@JoinColumn(name = "server_id")
|
||||||
private AServer server;
|
private AServer server;
|
||||||
|
|
||||||
@Column(name = "created", nullable = false, insertable = false, updatable = false)
|
@Column(name = "created", nullable = false, insertable = false, updatable = false)
|
||||||
@@ -51,9 +56,17 @@ public class Reminder implements Serializable {
|
|||||||
@Column(name = "text")
|
@Column(name = "text")
|
||||||
private String text;
|
private String text;
|
||||||
|
|
||||||
|
@Builder.Default
|
||||||
|
@Column(name = "send_dm", nullable = false)
|
||||||
|
private Boolean sendInDm = false;
|
||||||
|
|
||||||
|
@Builder.Default
|
||||||
|
@Column(name = "user_command", nullable = false)
|
||||||
|
private Boolean userCommand = false;
|
||||||
|
|
||||||
@Builder.Default
|
@Builder.Default
|
||||||
@Column(name = "reminded", nullable = false)
|
@Column(name = "reminded", nullable = false)
|
||||||
private boolean reminded = false;
|
private Boolean reminded = false;
|
||||||
|
|
||||||
@Column(name = "job_trigger_key")
|
@Column(name = "job_trigger_key")
|
||||||
private String jobTriggerKey;
|
private String jobTriggerKey;
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ package dev.sheldan.abstracto.remind.model.template.commands;
|
|||||||
import dev.sheldan.abstracto.core.models.context.ServerContext;
|
import dev.sheldan.abstracto.core.models.context.ServerContext;
|
||||||
import dev.sheldan.abstracto.core.models.template.display.MemberDisplay;
|
import dev.sheldan.abstracto.core.models.template.display.MemberDisplay;
|
||||||
import dev.sheldan.abstracto.core.models.template.display.MemberNameDisplay;
|
import dev.sheldan.abstracto.core.models.template.display.MemberNameDisplay;
|
||||||
|
import dev.sheldan.abstracto.core.models.template.display.UserDisplay;
|
||||||
import dev.sheldan.abstracto.core.utils.MessageUtils;
|
import dev.sheldan.abstracto.core.utils.MessageUtils;
|
||||||
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
@@ -16,12 +17,16 @@ import java.util.List;
|
|||||||
@Setter
|
@Setter
|
||||||
@SuperBuilder
|
@SuperBuilder
|
||||||
public class ExecutedReminderModel extends ServerContext {
|
public class ExecutedReminderModel extends ServerContext {
|
||||||
private Reminder reminder;
|
private Long reminderId;
|
||||||
private MemberNameDisplay memberNameDisplay;
|
private Long serverId;
|
||||||
|
private Long channelId;
|
||||||
|
private Long messageId;
|
||||||
|
private UserDisplay userDisplay;
|
||||||
|
private ReminderDisplay reminderDisplay;
|
||||||
private List<MemberDisplay> reminderParticipants;
|
private List<MemberDisplay> reminderParticipants;
|
||||||
private Duration duration;
|
private Duration duration;
|
||||||
|
|
||||||
public String getMessageUrl() {
|
public String getMessageUrl() {
|
||||||
return MessageUtils.buildMessageUrl(this.reminder.getServer().getId() ,this.reminder.getChannel().getId(), this.reminder.getMessageId());
|
return MessageUtils.buildMessageUrl(serverId , channelId, messageId);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -17,6 +17,8 @@ public class ReminderDisplay {
|
|||||||
private String text;
|
private String text;
|
||||||
private Instant targetDate;
|
private Instant targetDate;
|
||||||
private Instant creationDate;
|
private Instant creationDate;
|
||||||
|
private Boolean sentInDm;
|
||||||
|
private Boolean userCommand;
|
||||||
@Builder.Default
|
@Builder.Default
|
||||||
private Boolean joined = false;
|
private Boolean joined = false;
|
||||||
private ServerChannelMessage message;
|
private ServerChannelMessage message;
|
||||||
@@ -25,15 +27,17 @@ public class ReminderDisplay {
|
|||||||
ServerChannelMessage message = ServerChannelMessage
|
ServerChannelMessage message = ServerChannelMessage
|
||||||
.builder()
|
.builder()
|
||||||
.messageId(reminder.getMessageId())
|
.messageId(reminder.getMessageId())
|
||||||
.channelId(reminder.getChannel().getId())
|
.channelId(reminder.getChannel() != null ? reminder.getChannel().getId() : null)
|
||||||
.serverId(reminder.getServer().getId())
|
.serverId(reminder.getServer() != null ? reminder.getServer().getId() : null)
|
||||||
.build();
|
.build();
|
||||||
return ReminderDisplay
|
return ReminderDisplay
|
||||||
.builder()
|
.builder()
|
||||||
.creationDate(reminder.getReminderDate())
|
.creationDate(reminder.getReminderDate())
|
||||||
.targetDate(reminder.getTargetDate())
|
.targetDate(reminder.getTargetDate())
|
||||||
.id(reminder.getId())
|
.id(reminder.getId())
|
||||||
.reminded(reminder.isReminded())
|
.sentInDm(reminder.getSendInDm())
|
||||||
|
.reminded(reminder.getReminded())
|
||||||
|
.userCommand(reminder.getUserCommand())
|
||||||
.message(message)
|
.message(message)
|
||||||
.text(reminder.getText())
|
.text(reminder.getText())
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
package dev.sheldan.abstracto.remind.model.template.commands;
|
package dev.sheldan.abstracto.remind.model.template.commands;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.ServerChannelMessage;
|
import dev.sheldan.abstracto.core.models.ServerChannelMessage;
|
||||||
import dev.sheldan.abstracto.core.models.template.display.MemberNameDisplay;
|
import dev.sheldan.abstracto.core.models.template.display.UserDisplay;
|
||||||
import lombok.Builder;
|
import lombok.Builder;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
@@ -11,7 +11,7 @@ import lombok.Setter;
|
|||||||
@Builder
|
@Builder
|
||||||
public class ReminderModel {
|
public class ReminderModel {
|
||||||
private String remindText;
|
private String remindText;
|
||||||
private MemberNameDisplay memberDisplay;
|
private UserDisplay userDisplay;
|
||||||
private ReminderDisplay reminder;
|
private ReminderDisplay reminder;
|
||||||
private ServerChannelMessage message;
|
private ServerChannelMessage message;
|
||||||
private String joinButtonId;
|
private String joinButtonId;
|
||||||
|
|||||||
@@ -1,9 +1,9 @@
|
|||||||
package dev.sheldan.abstracto.remind.model.template.commands;
|
package dev.sheldan.abstracto.remind.model.template.commands;
|
||||||
|
|
||||||
|
import dev.sheldan.abstracto.core.models.template.display.UserDisplay;
|
||||||
import lombok.Builder;
|
import lombok.Builder;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
@@ -14,5 +14,5 @@ import java.util.List;
|
|||||||
public class RemindersModel {
|
public class RemindersModel {
|
||||||
@Builder.Default
|
@Builder.Default
|
||||||
private List<ReminderDisplay> reminders = new ArrayList<>();
|
private List<ReminderDisplay> reminders = new ArrayList<>();
|
||||||
private Member member;
|
private UserDisplay userDisplay;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
package dev.sheldan.abstracto.remind.service;
|
package dev.sheldan.abstracto.remind.service;
|
||||||
|
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
||||||
import net.dv8tion.jda.api.entities.Message;
|
import net.dv8tion.jda.api.entities.Message;
|
||||||
@@ -9,8 +10,10 @@ import java.time.Duration;
|
|||||||
public interface ReminderService {
|
public interface ReminderService {
|
||||||
Reminder createReminderInForUser(AUserInAServer user, String remindText, Duration remindIn, Message message);
|
Reminder createReminderInForUser(AUserInAServer user, String remindText, Duration remindIn, Message message);
|
||||||
Reminder createReminderInForUser(AUserInAServer user, String remindText, Duration remindIn, Long channelId, Long messageId);
|
Reminder createReminderInForUser(AUserInAServer user, String remindText, Duration remindIn, Long channelId, Long messageId);
|
||||||
|
Reminder createReminderInForUser(AUser aUser, String remindText, Duration remindIn);
|
||||||
Reminder createReminderInForUser(AUserInAServer user, String remindText, Duration remindIn, Long channelId);
|
Reminder createReminderInForUser(AUserInAServer user, String remindText, Duration remindIn, Long channelId);
|
||||||
void executeReminder(Long reminderId);
|
void executeReminder(Long reminderId);
|
||||||
void unRemind(Long reminderId, AUserInAServer userInAServer);
|
void unRemind(Long reminderId, AUserInAServer userInAServer);
|
||||||
|
void unRemind(Long reminderId, AUser aUser);
|
||||||
void snoozeReminder(Long reminderId, AUserInAServer user, Duration newDuration);
|
void snoozeReminder(Long reminderId, AUserInAServer user, Duration newDuration);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package dev.sheldan.abstracto.remind.service.management;
|
package dev.sheldan.abstracto.remind.service.management;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.AServerAChannelAUser;
|
import dev.sheldan.abstracto.core.models.AServerAChannelAUser;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
import dev.sheldan.abstracto.remind.model.database.Reminder;
|
||||||
|
|
||||||
@@ -9,12 +10,14 @@ import java.util.List;
|
|||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
|
|
||||||
public interface ReminderManagementService {
|
public interface ReminderManagementService {
|
||||||
Reminder createReminder(AServerAChannelAUser userToBeReminded, String text, Instant timeToBeRemindedAt, Long messageId);
|
Reminder createReminder(AServerAChannelAUser userToBeReminded, String text, Instant timeToBeRemindedAt, Long messageId, Boolean sendInDms, Boolean userCommand);
|
||||||
Optional<Reminder> loadReminderOptional(Long reminderId);
|
Optional<Reminder> loadReminderOptional(Long reminderId);
|
||||||
Reminder loadReminder(Long reminderId);
|
Reminder loadReminder(Long reminderId);
|
||||||
void setReminded(Reminder reminder);
|
void setReminded(Reminder reminder);
|
||||||
Reminder saveReminder(Reminder reminder);
|
Reminder saveReminder(Reminder reminder);
|
||||||
List<Reminder> getActiveRemindersForUser(AUserInAServer aUserInAServer);
|
List<Reminder> getActiveRemindersForUser(AUserInAServer aUserInAServer);
|
||||||
|
List<Reminder> getActiveUserRemindersForUser(AUser aUser);
|
||||||
Optional<Reminder> getReminderByAndByUserNotReminded(AUserInAServer aUserInAServer, Long reminderId);
|
Optional<Reminder> getReminderByAndByUserNotReminded(AUserInAServer aUserInAServer, Long reminderId);
|
||||||
|
Optional<Reminder> getReminderByAndByUserNotRemindedForUserCommand(AUser aUser, Long reminderId);
|
||||||
Optional<Reminder> getReminderByAndByUser(AUserInAServer aUserInAServer, Long reminderId);
|
Optional<Reminder> getReminderByAndByUser(AUserInAServer aUserInAServer, Long reminderId);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,9 +2,8 @@ package dev.sheldan.abstracto.utility.command;
|
|||||||
|
|
||||||
import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.*;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.handler.parameter.CombinedParameter;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
@@ -19,14 +18,21 @@ import dev.sheldan.abstracto.utility.config.UtilitySlashCommandNames;
|
|||||||
import dev.sheldan.abstracto.utility.model.ShowAvatarModel;
|
import dev.sheldan.abstracto.utility.model.ShowAvatarModel;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
import net.dv8tion.jda.api.entities.Member;
|
||||||
|
import net.dv8tion.jda.api.entities.Message;
|
||||||
|
import net.dv8tion.jda.api.entities.User;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
import java.util.concurrent.CompletableFuture;
|
import java.util.concurrent.CompletableFuture;
|
||||||
|
|
||||||
|
import static dev.sheldan.abstracto.core.command.config.Parameter.ADDITIONAL_TYPES_KEY;
|
||||||
|
|
||||||
@Component
|
@Component
|
||||||
@Slf4j
|
@Slf4j
|
||||||
public class ShowAvatar extends AbstractConditionableCommand {
|
public class ShowAvatar extends AbstractConditionableCommand {
|
||||||
@@ -44,6 +50,9 @@ public class ShowAvatar extends AbstractConditionableCommand {
|
|||||||
@Autowired
|
@Autowired
|
||||||
private InteractionService interactionService;
|
private InteractionService interactionService;
|
||||||
|
|
||||||
|
@Value("${abstracto.feature.avatar.imagesize}")
|
||||||
|
private Integer imageSize;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeAsync(CommandContext commandContext) {
|
public CompletableFuture<CommandResult> executeAsync(CommandContext commandContext) {
|
||||||
List<Object> parameters = commandContext.getParameters().getParameters();
|
List<Object> parameters = commandContext.getParameters().getParameters();
|
||||||
@@ -53,7 +62,7 @@ public class ShowAvatar extends AbstractConditionableCommand {
|
|||||||
}
|
}
|
||||||
ShowAvatarModel model = ShowAvatarModel
|
ShowAvatarModel model = ShowAvatarModel
|
||||||
.builder()
|
.builder()
|
||||||
.memberInfo(memberToShow)
|
.avatarUrl(memberToShow.getEffectiveAvatar().getUrl(imageSize))
|
||||||
.build();
|
.build();
|
||||||
log.info("Showing avatar for member {} towards user {} in channel {} in server {}.",
|
log.info("Showing avatar for member {} towards user {} in channel {} in server {}.",
|
||||||
memberToShow.getId(), commandContext.getAuthor().getId(), commandContext.getChannel().getId(), commandContext.getGuild().getId());
|
memberToShow.getId(), commandContext.getAuthor().getId(), commandContext.getChannel().getId(), commandContext.getGuild().getId());
|
||||||
@@ -63,15 +72,27 @@ public class ShowAvatar extends AbstractConditionableCommand {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
Member memberToShow;
|
String avatarUrl;
|
||||||
|
Member targetMember;
|
||||||
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER, event)) {
|
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER, event)) {
|
||||||
memberToShow = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER, event, Member.class);
|
targetMember = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER, event, Member.class);
|
||||||
} else {
|
} else {
|
||||||
memberToShow = event.getMember();
|
targetMember = event.getMember();
|
||||||
|
}
|
||||||
|
if(targetMember == null) {
|
||||||
|
User targetUser;
|
||||||
|
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER, event)) {
|
||||||
|
targetUser = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER, event, User.class);
|
||||||
|
} else {
|
||||||
|
targetUser = event.getUser();
|
||||||
|
}
|
||||||
|
avatarUrl = targetUser.getEffectiveAvatar().getUrl(imageSize);
|
||||||
|
} else {
|
||||||
|
avatarUrl = targetMember.getEffectiveAvatar().getUrl(imageSize);
|
||||||
}
|
}
|
||||||
ShowAvatarModel model = ShowAvatarModel
|
ShowAvatarModel model = ShowAvatarModel
|
||||||
.builder()
|
.builder()
|
||||||
.memberInfo(memberToShow)
|
.avatarUrl(avatarUrl)
|
||||||
.build();
|
.build();
|
||||||
return interactionService.replyEmbed(SHOW_AVATAR_RESPONSE_TEMPLATE, model, event.getInteraction())
|
return interactionService.replyEmbed(SHOW_AVATAR_RESPONSE_TEMPLATE, model, event.getInteraction())
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
@@ -80,11 +101,18 @@ public class ShowAvatar extends AbstractConditionableCommand {
|
|||||||
@Override
|
@Override
|
||||||
public CommandConfiguration getConfiguration() {
|
public CommandConfiguration getConfiguration() {
|
||||||
List<Parameter> parameters = new ArrayList<>();
|
List<Parameter> parameters = new ArrayList<>();
|
||||||
|
Map<String, Object> parameterAlternatives = new HashMap<>();
|
||||||
|
parameterAlternatives.put(ADDITIONAL_TYPES_KEY, List.of(
|
||||||
|
CombinedParameterEntry.messageParameter(Message.class),
|
||||||
|
CombinedParameterEntry.parameter(Member.class),
|
||||||
|
CombinedParameterEntry.parameter(User.class)));
|
||||||
Parameter memberParameter = Parameter
|
Parameter memberParameter = Parameter
|
||||||
.builder()
|
.builder()
|
||||||
.type(Member.class)
|
|
||||||
.name(MEMBER_PARAMETER)
|
.name(MEMBER_PARAMETER)
|
||||||
|
.type(CombinedParameter.class)
|
||||||
|
.additionalInfo(parameterAlternatives)
|
||||||
.templated(true)
|
.templated(true)
|
||||||
|
.useStrictParameters(true)
|
||||||
.optional(true)
|
.optional(true)
|
||||||
.build();
|
.build();
|
||||||
parameters.add(memberParameter);
|
parameters.add(memberParameter);
|
||||||
@@ -96,6 +124,8 @@ public class ShowAvatar extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.guildOnly())
|
||||||
.rootCommandName(UtilitySlashCommandNames.UTILITY)
|
.rootCommandName(UtilitySlashCommandNames.UTILITY)
|
||||||
.commandName(SHOW_AVATAR_COMMAND)
|
.commandName(SHOW_AVATAR_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -2,9 +2,8 @@ package dev.sheldan.abstracto.utility.command;
|
|||||||
|
|
||||||
import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.*;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.handler.parameter.CombinedParameter;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
@@ -16,6 +15,7 @@ import dev.sheldan.abstracto.core.models.template.display.MemberNameDisplay;
|
|||||||
import dev.sheldan.abstracto.core.models.template.display.RoleDisplay;
|
import dev.sheldan.abstracto.core.models.template.display.RoleDisplay;
|
||||||
import dev.sheldan.abstracto.core.service.ChannelService;
|
import dev.sheldan.abstracto.core.service.ChannelService;
|
||||||
import dev.sheldan.abstracto.core.service.MemberService;
|
import dev.sheldan.abstracto.core.service.MemberService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.utility.config.UtilityFeatureDefinition;
|
import dev.sheldan.abstracto.utility.config.UtilityFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.utility.config.UtilitySlashCommandNames;
|
import dev.sheldan.abstracto.utility.config.UtilitySlashCommandNames;
|
||||||
@@ -23,6 +23,8 @@ import dev.sheldan.abstracto.utility.model.UserInfoModel;
|
|||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.entities.Activity;
|
import net.dv8tion.jda.api.entities.Activity;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
import net.dv8tion.jda.api.entities.Member;
|
||||||
|
import net.dv8tion.jda.api.entities.Message;
|
||||||
|
import net.dv8tion.jda.api.entities.User;
|
||||||
import net.dv8tion.jda.api.entities.channel.middleman.MessageChannel;
|
import net.dv8tion.jda.api.entities.channel.middleman.MessageChannel;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import net.dv8tion.jda.api.interactions.InteractionHook;
|
import net.dv8tion.jda.api.interactions.InteractionHook;
|
||||||
@@ -31,11 +33,11 @@ import org.springframework.beans.factory.annotation.Autowired;
|
|||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
import org.springframework.transaction.annotation.Transactional;
|
import org.springframework.transaction.annotation.Transactional;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.*;
|
||||||
import java.util.List;
|
|
||||||
import java.util.Optional;
|
|
||||||
import java.util.concurrent.CompletableFuture;
|
import java.util.concurrent.CompletableFuture;
|
||||||
|
|
||||||
|
import static dev.sheldan.abstracto.core.command.config.Parameter.ADDITIONAL_TYPES_KEY;
|
||||||
|
|
||||||
@Component
|
@Component
|
||||||
@Slf4j
|
@Slf4j
|
||||||
public class UserInfo extends AbstractConditionableCommand {
|
public class UserInfo extends AbstractConditionableCommand {
|
||||||
@@ -71,12 +73,12 @@ public class UserInfo extends AbstractConditionableCommand {
|
|||||||
if(!memberToShow.hasTimeJoined()) {
|
if(!memberToShow.hasTimeJoined()) {
|
||||||
log.info("Force reloading member {} in guild {} for user info.", memberToShow.getId(), memberToShow.getGuild().getId());
|
log.info("Force reloading member {} in guild {} for user info.", memberToShow.getId(), memberToShow.getGuild().getId());
|
||||||
return memberService.forceReloadMember(memberToShow).thenCompose(member -> {
|
return memberService.forceReloadMember(memberToShow).thenCompose(member -> {
|
||||||
fillUserInfoModel(model, member);
|
fillUserInfoModel(model, member, false);
|
||||||
return self.sendResponse(commandContext.getChannel(), model)
|
return self.sendResponse(commandContext.getChannel(), model)
|
||||||
.thenApply(aVoid -> CommandResult.fromIgnored());
|
.thenApply(aVoid -> CommandResult.fromIgnored());
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
fillUserInfoModel(model, memberToShow);
|
fillUserInfoModel(model, memberToShow, false);
|
||||||
return self.sendResponse(commandContext.getChannel(), model)
|
return self.sendResponse(commandContext.getChannel(), model)
|
||||||
.thenApply(aVoid -> CommandResult.fromIgnored());
|
.thenApply(aVoid -> CommandResult.fromIgnored());
|
||||||
}
|
}
|
||||||
@@ -94,55 +96,92 @@ public class UserInfo extends AbstractConditionableCommand {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
Member memberToShow;
|
boolean userCommand = ContextUtils.isUserCommandInGuild(event);
|
||||||
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER, event)) {
|
boolean knownGuild = ContextUtils.isGuildKnown(event);
|
||||||
memberToShow = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER, event, Member.class);
|
|
||||||
} else {
|
|
||||||
memberToShow = event.getMember();
|
|
||||||
}
|
|
||||||
if(!memberToShow.getGuild().equals(event.getGuild())) {
|
|
||||||
throw new EntityGuildMismatchException();
|
|
||||||
}
|
|
||||||
UserInfoModel model = UserInfoModel
|
UserInfoModel model = UserInfoModel
|
||||||
.builder()
|
.builder()
|
||||||
.build();
|
.build();
|
||||||
if(!memberToShow.hasTimeJoined()) {
|
if(knownGuild) {
|
||||||
log.info("Force reloading member {} in guild {} for user info.", memberToShow.getId(), memberToShow.getGuild().getId());
|
Member memberToShow;
|
||||||
return memberService.forceReloadMember(memberToShow).thenCompose(member -> {
|
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER, event)) {
|
||||||
fillUserInfoModel(model, member);
|
memberToShow = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER, event, Member.class);
|
||||||
|
} else {
|
||||||
|
memberToShow = event.getMember();
|
||||||
|
}
|
||||||
|
if(!memberToShow.getGuild().equals(event.getGuild())) {
|
||||||
|
throw new EntityGuildMismatchException();
|
||||||
|
}
|
||||||
|
if(!memberToShow.hasTimeJoined()) {
|
||||||
|
log.info("Force reloading member {} in guild {} for user info.", memberToShow.getId(), memberToShow.getGuild().getId());
|
||||||
|
return memberService.forceReloadMember(memberToShow).thenCompose(member -> {
|
||||||
|
fillUserInfoModel(model, member, userCommand);
|
||||||
|
return self.sendResponse(event, model)
|
||||||
|
.thenApply(aVoid -> CommandResult.fromIgnored());
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
fillUserInfoModel(model, memberToShow, userCommand);
|
||||||
return self.sendResponse(event, model)
|
return self.sendResponse(event, model)
|
||||||
.thenApply(aVoid -> CommandResult.fromIgnored());
|
.thenApply(aVoid -> CommandResult.fromIgnored());
|
||||||
});
|
}
|
||||||
} else {
|
} else {
|
||||||
fillUserInfoModel(model, memberToShow);
|
User targetUser;
|
||||||
|
if(slashCommandParameterService.hasCommandOption(MEMBER_PARAMETER, event)) {
|
||||||
|
targetUser = slashCommandParameterService.getCommandOption(MEMBER_PARAMETER, event, User.class);
|
||||||
|
} else {
|
||||||
|
targetUser = event.getUser();
|
||||||
|
}
|
||||||
|
fillUserInfoModel(model, targetUser);
|
||||||
return self.sendResponse(event, model)
|
return self.sendResponse(event, model)
|
||||||
.thenApply(aVoid -> CommandResult.fromIgnored());
|
.thenApply(aVoid -> CommandResult.fromIgnored());
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void fillUserInfoModel(UserInfoModel model, Member member) {
|
private void fillUserInfoModel(UserInfoModel model, User targetUser) {
|
||||||
|
model.setCreationDate(targetUser.getTimeCreated().toInstant());
|
||||||
|
model.setId(targetUser.getIdLong());
|
||||||
|
MemberNameDisplay memberDisplay = MemberNameDisplay
|
||||||
|
.builder()
|
||||||
|
.userName(targetUser.getName())
|
||||||
|
.userAvatarUrl(targetUser.getEffectiveAvatarUrl())
|
||||||
|
.discriminator(targetUser.getDiscriminator())
|
||||||
|
.displayName(targetUser.getGlobalName())
|
||||||
|
.build();
|
||||||
|
model.setMemberDisplay(memberDisplay);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void fillUserInfoModel(UserInfoModel model, Member member, boolean userCommand) {
|
||||||
model.setCreationDate(member.getTimeCreated().toInstant());
|
model.setCreationDate(member.getTimeCreated().toInstant());
|
||||||
model.setJoinDate(member.getTimeJoined().toInstant());
|
model.setJoinDate(member.getTimeJoined().toInstant());
|
||||||
model.setId(member.getIdLong());
|
model.setId(member.getIdLong());
|
||||||
model.setMemberDisplay(MemberNameDisplay.fromMember(member));
|
model.setMemberDisplay(MemberNameDisplay.fromMember(member));
|
||||||
model.setOnlineStatus(member.getOnlineStatus().getKey());
|
if(!userCommand) {
|
||||||
member.getRoles().forEach(role -> model.getRoles().add(RoleDisplay.fromRole(role)));
|
model.setOnlineStatus(member.getOnlineStatus().getKey());
|
||||||
member.getActivities().forEach(activity -> model.getActivities().add(activity.getType().name()));
|
member.getRoles().forEach(role -> model.getRoles().add(RoleDisplay.fromRole(role)));
|
||||||
Optional<Activity> customStatusOptional = member.getActivities().stream().filter(activity -> activity.getType().equals(Activity.ActivityType.CUSTOM_STATUS)).findFirst();
|
member.getActivities().forEach(activity -> model.getActivities().add(activity.getType().name()));
|
||||||
customStatusOptional.ifPresent(activity -> {
|
Optional<Activity> customStatusOptional = member.getActivities().stream().filter(activity -> activity.getType().equals(Activity.ActivityType.CUSTOM_STATUS)).findFirst();
|
||||||
model.setCustomStatus(activity.getName());
|
customStatusOptional.ifPresent(activity -> {
|
||||||
model.setCustomEmoji(activity.getEmoji() != null ? activity.getEmoji().getFormatted() : null);
|
model.setCustomStatus(activity.getName());
|
||||||
});
|
model.setCustomEmoji(activity.getEmoji() != null ? activity.getEmoji().getFormatted() : null);
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CommandConfiguration getConfiguration() {
|
public CommandConfiguration getConfiguration() {
|
||||||
List<Parameter> parameters = new ArrayList<>();
|
List<Parameter> parameters = new ArrayList<>();
|
||||||
|
Map<String, Object> parameterAlternatives = new HashMap<>();
|
||||||
|
parameterAlternatives.put(ADDITIONAL_TYPES_KEY, List.of(
|
||||||
|
CombinedParameterEntry.messageParameter(Message.class),
|
||||||
|
CombinedParameterEntry.parameter(Member.class),
|
||||||
|
CombinedParameterEntry.parameter(User.class)));
|
||||||
Parameter memberParameter = Parameter
|
Parameter memberParameter = Parameter
|
||||||
.builder()
|
.builder()
|
||||||
.type(Member.class)
|
|
||||||
.name(MEMBER_PARAMETER)
|
.name(MEMBER_PARAMETER)
|
||||||
|
.type(CombinedParameter.class)
|
||||||
|
.additionalInfo(parameterAlternatives)
|
||||||
.templated(true)
|
.templated(true)
|
||||||
|
.useStrictParameters(true)
|
||||||
.optional(true)
|
.optional(true)
|
||||||
.build();
|
.build();
|
||||||
parameters.add(memberParameter);
|
parameters.add(memberParameter);
|
||||||
@@ -154,6 +193,8 @@ public class UserInfo extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.guildOnly())
|
||||||
.rootCommandName(UtilitySlashCommandNames.UTILITY)
|
.rootCommandName(UtilitySlashCommandNames.UTILITY)
|
||||||
.commandName(USER_INFO_COMMAND)
|
.commandName(USER_INFO_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -1,2 +1,4 @@
|
|||||||
abstracto.featureFlags.utility.featureName=utility
|
abstracto.featureFlags.utility.featureName=utility
|
||||||
abstracto.featureFlags.utility.enabled=false
|
abstracto.featureFlags.utility.enabled=false
|
||||||
|
|
||||||
|
abstracto.feature.avatar.imagesize=4096
|
||||||
@@ -3,11 +3,10 @@ package dev.sheldan.abstracto.utility.model;
|
|||||||
import lombok.Builder;
|
import lombok.Builder;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
|
||||||
|
|
||||||
@Getter
|
@Getter
|
||||||
@Setter
|
@Setter
|
||||||
@Builder
|
@Builder
|
||||||
public class ShowAvatarModel {
|
public class ShowAvatarModel {
|
||||||
private Member memberInfo;
|
private String avatarUrl;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
@@ -15,6 +16,7 @@ import dev.sheldan.abstracto.core.interaction.slash.parameter.SlashCommandParame
|
|||||||
import dev.sheldan.abstracto.core.service.ChannelService;
|
import dev.sheldan.abstracto.core.service.ChannelService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.webservices.config.WebServicesSlashCommandNames;
|
import dev.sheldan.abstracto.webservices.config.WebServicesSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.webservices.config.WebserviceFeatureDefinition;
|
import dev.sheldan.abstracto.webservices.config.WebserviceFeatureDefinition;
|
||||||
@@ -70,7 +72,7 @@ public class DictionaryApiDefinitionCommand extends AbstractConditionableCommand
|
|||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
String query = slashCommandParameterService.getCommandOption(SEARCH_QUERY_PARAMETER, event, String.class);
|
String query = slashCommandParameterService.getCommandOption(SEARCH_QUERY_PARAMETER, event, String.class);
|
||||||
try {
|
try {
|
||||||
MessageToSend messageToSend = getMessageToSend(event.getGuild().getIdLong(), query);
|
MessageToSend messageToSend = getMessageToSend(ContextUtils.serverIdOrNull(event), query);
|
||||||
return interactionService.replyMessageToSend(messageToSend, event)
|
return interactionService.replyMessageToSend(messageToSend, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
@@ -112,6 +114,8 @@ public class DictionaryApiDefinitionCommand extends AbstractConditionableCommand
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(WebServicesSlashCommandNames.DICTIONARY)
|
.rootCommandName(WebServicesSlashCommandNames.DICTIONARY)
|
||||||
.commandName("definition")
|
.commandName("definition")
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
@@ -16,6 +17,7 @@ import dev.sheldan.abstracto.core.service.ChannelService;
|
|||||||
import dev.sheldan.abstracto.core.service.ConfigService;
|
import dev.sheldan.abstracto.core.service.ConfigService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.webservices.config.WebServicesSlashCommandNames;
|
import dev.sheldan.abstracto.webservices.config.WebServicesSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.webservices.config.WebserviceFeatureDefinition;
|
import dev.sheldan.abstracto.webservices.config.WebserviceFeatureDefinition;
|
||||||
@@ -76,7 +78,7 @@ public class OpenWeatherMap extends AbstractConditionableCommand {
|
|||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
String query = slashCommandParameterService.getCommandOption(SEARCH_QUERY_PARAMETER, event, String.class);
|
String query = slashCommandParameterService.getCommandOption(SEARCH_QUERY_PARAMETER, event, String.class);
|
||||||
MessageToSend messageToSend = getMessageToSend(event.getGuild().getIdLong(), query);
|
MessageToSend messageToSend = getMessageToSend(ContextUtils.serverIdOrNull(event), query);
|
||||||
return interactionService.replyMessageToSend(messageToSend, event)
|
return interactionService.replyMessageToSend(messageToSend, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
}
|
}
|
||||||
@@ -158,6 +160,8 @@ public class OpenWeatherMap extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(WebServicesSlashCommandNames.WEATHER)
|
.rootCommandName(WebServicesSlashCommandNames.WEATHER)
|
||||||
.commandName("search")
|
.commandName("search")
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
@@ -16,6 +17,7 @@ import dev.sheldan.abstracto.core.service.ChannelService;
|
|||||||
import dev.sheldan.abstracto.core.service.ProfanityService;
|
import dev.sheldan.abstracto.core.service.ProfanityService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.webservices.config.WebServicesSlashCommandNames;
|
import dev.sheldan.abstracto.webservices.config.WebServicesSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.webservices.config.WebserviceFeatureDefinition;
|
import dev.sheldan.abstracto.webservices.config.WebserviceFeatureDefinition;
|
||||||
@@ -73,7 +75,7 @@ public class UrbanDefine extends AbstractConditionableCommand {
|
|||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
String query = slashCommandParameterService.getCommandOption(SEARCH_QUERY_PARAMETER, event, String.class);
|
String query = slashCommandParameterService.getCommandOption(SEARCH_QUERY_PARAMETER, event, String.class);
|
||||||
try {
|
try {
|
||||||
MessageToSend messageToSend = getMessageToSend(event.getGuild().getIdLong(), query);
|
MessageToSend messageToSend = getMessageToSend(ContextUtils.serverIdOrNull(event), query);
|
||||||
return interactionService.replyMessageToSend(messageToSend, event)
|
return interactionService.replyMessageToSend(messageToSend, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
@@ -111,6 +113,8 @@ public class UrbanDefine extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(WebServicesSlashCommandNames.URBAN)
|
.rootCommandName(WebServicesSlashCommandNames.URBAN)
|
||||||
.commandName("search")
|
.commandName("search")
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
@@ -16,6 +17,7 @@ import dev.sheldan.abstracto.core.service.ChannelService;
|
|||||||
import dev.sheldan.abstracto.core.service.ConfigService;
|
import dev.sheldan.abstracto.core.service.ConfigService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.webservices.config.WebServicesSlashCommandNames;
|
import dev.sheldan.abstracto.webservices.config.WebServicesSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.webservices.config.WebserviceFeatureDefinition;
|
import dev.sheldan.abstracto.webservices.config.WebserviceFeatureDefinition;
|
||||||
@@ -81,7 +83,7 @@ public class WikipediaArticleSummaryCommand extends AbstractConditionableCommand
|
|||||||
language = null;
|
language = null;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
MessageToSend messageToSend = getMessageToSend(event.getGuild().getIdLong(), query, language);
|
MessageToSend messageToSend = getMessageToSend(ContextUtils.serverIdOrNull(event), query, language);
|
||||||
return interactionService.replyMessageToSend(messageToSend, event)
|
return interactionService.replyMessageToSend(messageToSend, event)
|
||||||
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
.thenApply(interactionHook -> CommandResult.fromSuccess());
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
@@ -132,6 +134,8 @@ public class WikipediaArticleSummaryCommand extends AbstractConditionableCommand
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(WebServicesSlashCommandNames.WIKIPEDIA)
|
.rootCommandName(WebServicesSlashCommandNames.WIKIPEDIA)
|
||||||
.groupName("article")
|
.groupName("article")
|
||||||
.commandName("summary")
|
.commandName("summary")
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
@@ -16,6 +17,7 @@ import dev.sheldan.abstracto.core.service.ChannelService;
|
|||||||
import dev.sheldan.abstracto.core.service.FeatureModeService;
|
import dev.sheldan.abstracto.core.service.FeatureModeService;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.webservices.common.service.SuggestQueriesService;
|
import dev.sheldan.abstracto.webservices.common.service.SuggestQueriesService;
|
||||||
import dev.sheldan.abstracto.webservices.config.WebServicesSlashCommandNames;
|
import dev.sheldan.abstracto.webservices.config.WebServicesSlashCommandNames;
|
||||||
@@ -95,9 +97,16 @@ public class YoutubeVideoSearch extends AbstractConditionableCommand {
|
|||||||
.builder()
|
.builder()
|
||||||
.video(foundVideo)
|
.video(foundVideo)
|
||||||
.build();
|
.build();
|
||||||
boolean sendInfo = featureModeService.featureModeActive(WebserviceFeatureDefinition.YOUTUBE, event.getGuild().getIdLong(), YoutubeWebServiceFeatureMode.VIDEO_DETAILS);
|
boolean sendInfo;
|
||||||
MessageToSend linkEmbed = templateService.renderEmbedTemplate(YOUTUBE_SEARCH_COMMAND_RESPONSE_LINK_TEMPLATE_KEY, model, event.getGuild().getIdLong());
|
MessageToSend linkEmbed = templateService.renderEmbedTemplate(YOUTUBE_SEARCH_COMMAND_RESPONSE_LINK_TEMPLATE_KEY, model, ContextUtils.serverIdOrNull(event));
|
||||||
MessageToSend infoEmbed = templateService.renderEmbedTemplate(YOUTUBE_SEARCH_COMMAND_RESPONSE_TEMPLATE_KEY, model, event.getGuild().getIdLong());
|
MessageToSend infoEmbed;
|
||||||
|
if(ContextUtils.isNotUserCommand(event)) {
|
||||||
|
sendInfo = featureModeService.featureModeActive(WebserviceFeatureDefinition.YOUTUBE, event.getGuild().getIdLong(), YoutubeWebServiceFeatureMode.VIDEO_DETAILS);
|
||||||
|
infoEmbed = templateService.renderEmbedTemplate(YOUTUBE_SEARCH_COMMAND_RESPONSE_TEMPLATE_KEY, model, ContextUtils.serverIdOrNull(event));
|
||||||
|
} else {
|
||||||
|
infoEmbed = null;
|
||||||
|
sendInfo = false;
|
||||||
|
}
|
||||||
return interactionService.replyMessageToSend(linkEmbed, event)
|
return interactionService.replyMessageToSend(linkEmbed, event)
|
||||||
.thenCompose(interactionHook -> {
|
.thenCompose(interactionHook -> {
|
||||||
if(sendInfo) {
|
if(sendInfo) {
|
||||||
@@ -139,6 +148,8 @@ public class YoutubeVideoSearch extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(WebServicesSlashCommandNames.YOUTUBE)
|
.rootCommandName(WebServicesSlashCommandNames.YOUTUBE)
|
||||||
.commandName("search")
|
.commandName("search")
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -11,6 +11,7 @@ import dev.sheldan.abstracto.core.interaction.InteractionService;
|
|||||||
import dev.sheldan.abstracto.core.models.GuildChannelMember;
|
import dev.sheldan.abstracto.core.models.GuildChannelMember;
|
||||||
import dev.sheldan.abstracto.core.service.ChannelService;
|
import dev.sheldan.abstracto.core.service.ChannelService;
|
||||||
import dev.sheldan.abstracto.core.service.ReactionService;
|
import dev.sheldan.abstracto.core.service.ReactionService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import net.dv8tion.jda.api.entities.channel.middleman.GuildChannel;
|
import net.dv8tion.jda.api.entities.channel.middleman.GuildChannel;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
@@ -53,7 +54,7 @@ public class ConditionPostExecution implements PostCommandExecution {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void executeSlash(SlashCommandInteractionEvent interaction, CommandResult commandResult, Command command) {
|
public void executeSlash(SlashCommandInteractionEvent interaction, CommandResult commandResult, Command command) {
|
||||||
if(commandResult.getResult().equals(ResultState.CONDITION)
|
if(commandResult.getResult().equals(ResultState.CONDITION) && ContextUtils.isNotUserCommand(interaction)
|
||||||
&& commandResult.getConditionResult() != null &&
|
&& commandResult.getConditionResult() != null &&
|
||||||
!commandResult.getConditionResult().isResult()
|
!commandResult.getConditionResult().isResult()
|
||||||
&& commandResult.getConditionResult().getConditionDetail() != null
|
&& commandResult.getConditionResult().getConditionDetail() != null
|
||||||
|
|||||||
@@ -6,6 +6,7 @@ import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
|||||||
import dev.sheldan.abstracto.core.command.execution.ResultState;
|
import dev.sheldan.abstracto.core.command.execution.ResultState;
|
||||||
import dev.sheldan.abstracto.core.command.service.CommandCoolDownService;
|
import dev.sheldan.abstracto.core.command.service.CommandCoolDownService;
|
||||||
import dev.sheldan.abstracto.core.command.service.PostCommandExecution;
|
import dev.sheldan.abstracto.core.command.service.PostCommandExecution;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
@@ -35,7 +36,9 @@ public class CoolDownPostExecution implements PostCommandExecution {
|
|||||||
public void executeSlash(SlashCommandInteractionEvent interaction, CommandResult commandResult, Command command) {
|
public void executeSlash(SlashCommandInteractionEvent interaction, CommandResult commandResult, Command command) {
|
||||||
ResultState result = commandResult.getResult();
|
ResultState result = commandResult.getResult();
|
||||||
if(result.equals(ResultState.SUCCESSFUL) || result.equals(ResultState.IGNORED)) {
|
if(result.equals(ResultState.SUCCESSFUL) || result.equals(ResultState.IGNORED)) {
|
||||||
commandCoolDownService.updateCoolDowns(command, interaction);
|
if(ContextUtils.isNotUserCommand(interaction)) {
|
||||||
|
commandCoolDownService.updateCoolDowns(command, interaction);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ import dev.sheldan.abstracto.core.command.service.ExceptionService;
|
|||||||
import dev.sheldan.abstracto.core.command.service.PostCommandExecution;
|
import dev.sheldan.abstracto.core.command.service.PostCommandExecution;
|
||||||
import dev.sheldan.abstracto.core.interaction.InteractionExceptionService;
|
import dev.sheldan.abstracto.core.interaction.InteractionExceptionService;
|
||||||
import dev.sheldan.abstracto.core.service.ConfigService;
|
import dev.sheldan.abstracto.core.service.ConfigService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.apache.commons.lang3.BooleanUtils;
|
import org.apache.commons.lang3.BooleanUtils;
|
||||||
@@ -53,7 +54,7 @@ public class ExceptionPostExecution implements PostCommandExecution {
|
|||||||
if(result.equals(ResultState.ERROR)) {
|
if(result.equals(ResultState.ERROR)) {
|
||||||
Throwable throwable = commandResult.getThrowable();
|
Throwable throwable = commandResult.getThrowable();
|
||||||
if(throwable != null) {
|
if(throwable != null) {
|
||||||
if(throwable instanceof CommandNotFoundException){
|
if(throwable instanceof CommandNotFoundException && ContextUtils.isNotUserCommand(interaction)){
|
||||||
String configValue = configService.getStringValueOrConfigDefault(CoreFeatureConfig.NO_COMMAND_REPORTING_CONFIG_KEY, interaction.getGuild().getIdLong());
|
String configValue = configService.getStringValueOrConfigDefault(CoreFeatureConfig.NO_COMMAND_REPORTING_CONFIG_KEY, interaction.getGuild().getIdLong());
|
||||||
if(!BooleanUtils.toBoolean(configValue)) {
|
if(!BooleanUtils.toBoolean(configValue)) {
|
||||||
return;
|
return;
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
package dev.sheldan.abstracto.core.commands.help;
|
package dev.sheldan.abstracto.core.commands.help;
|
||||||
|
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.CoreSlashCommandNames;
|
import dev.sheldan.abstracto.core.interaction.slash.CoreSlashCommandNames;
|
||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
@@ -52,6 +53,8 @@ public class Documentation extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(CoreSlashCommandNames.INFO)
|
.rootCommandName(CoreSlashCommandNames.INFO)
|
||||||
.commandName("documentation")
|
.commandName("documentation")
|
||||||
.build();
|
.build();
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.config.features.CoreFeatureDefinition;
|
import dev.sheldan.abstracto.core.command.config.features.CoreFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
@@ -18,6 +19,7 @@ import dev.sheldan.abstracto.core.models.template.display.ChannelDisplay;
|
|||||||
import dev.sheldan.abstracto.core.service.ChannelService;
|
import dev.sheldan.abstracto.core.service.ChannelService;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
import net.dv8tion.jda.api.entities.channel.middleman.GuildMessageChannel;
|
import net.dv8tion.jda.api.entities.channel.middleman.GuildMessageChannel;
|
||||||
|
import net.dv8tion.jda.api.entities.channel.middleman.MessageChannel;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
@@ -64,15 +66,14 @@ public class Echo extends AbstractConditionableCommand {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
public CompletableFuture<CommandResult> executeSlash(SlashCommandInteractionEvent event) {
|
||||||
|
|
||||||
String message = slashCommandParameterService.getCommandOption(INPUT_PARAMETER, event, String.class);
|
String message = slashCommandParameterService.getCommandOption(INPUT_PARAMETER, event, String.class);
|
||||||
GuildMessageChannel messageChannel;
|
MessageChannel messageChannel;
|
||||||
boolean redirect = false;
|
boolean redirect = false;
|
||||||
if (slashCommandParameterService.hasCommandOption(TARGET_CHANNEL_PARAMETER, event)) {
|
if (slashCommandParameterService.hasCommandOption(TARGET_CHANNEL_PARAMETER, event)) {
|
||||||
messageChannel = slashCommandParameterService.getCommandOption(TARGET_CHANNEL_PARAMETER, event, GuildMessageChannel.class);
|
messageChannel = slashCommandParameterService.getCommandOption(TARGET_CHANNEL_PARAMETER, event, GuildMessageChannel.class);
|
||||||
redirect = true;
|
redirect = true;
|
||||||
} else {
|
} else {
|
||||||
messageChannel = event.getGuildChannel();
|
messageChannel = event.getChannel();
|
||||||
}
|
}
|
||||||
|
|
||||||
EchoModel model = EchoModel
|
EchoModel model = EchoModel
|
||||||
@@ -110,6 +111,7 @@ public class Echo extends AbstractConditionableCommand {
|
|||||||
.name(TARGET_CHANNEL_PARAMETER)
|
.name(TARGET_CHANNEL_PARAMETER)
|
||||||
.type(GuildMessageChannel.class)
|
.type(GuildMessageChannel.class)
|
||||||
.slashCommandOnly(true)
|
.slashCommandOnly(true)
|
||||||
|
.supportsUserCommands(false)
|
||||||
.optional(true)
|
.optional(true)
|
||||||
.templated(true)
|
.templated(true)
|
||||||
.remainder(true)
|
.remainder(true)
|
||||||
@@ -118,6 +120,8 @@ public class Echo extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(ECHO_COMMAND)
|
.rootCommandName(ECHO_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
HelpInfo helpInfo = HelpInfo.builder().templated(true).build();
|
HelpInfo helpInfo = HelpInfo.builder().templated(true).build();
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
|||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.config.features.CoreFeatureDefinition;
|
import dev.sheldan.abstracto.core.command.config.features.CoreFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
@@ -60,6 +61,8 @@ public class Ping extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(PING_COMMAND)
|
.rootCommandName(PING_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
return CommandConfiguration.builder()
|
return CommandConfiguration.builder()
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import dev.sheldan.abstracto.core.command.UtilityModuleDefinition;
|
|||||||
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
import dev.sheldan.abstracto.core.command.condition.AbstractConditionableCommand;
|
||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
import dev.sheldan.abstracto.core.command.config.HelpInfo;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.config.features.CoreFeatureDefinition;
|
import dev.sheldan.abstracto.core.command.config.features.CoreFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
@@ -69,6 +70,8 @@ public class Uptime extends AbstractConditionableCommand {
|
|||||||
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
SlashCommandConfig slashCommandConfig = SlashCommandConfig
|
||||||
.builder()
|
.builder()
|
||||||
.enabled(true)
|
.enabled(true)
|
||||||
|
.userInstallable(true)
|
||||||
|
.userCommandConfig(UserCommandConfig.all())
|
||||||
.rootCommandName(UPTIME_COMMAND)
|
.rootCommandName(UPTIME_COMMAND)
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
|
|||||||
@@ -4,8 +4,6 @@ import dev.sheldan.abstracto.core.command.Command;
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureConfig;
|
import dev.sheldan.abstracto.core.config.FeatureConfig;
|
||||||
import dev.sheldan.abstracto.core.interaction.context.ContextCommandService;
|
import dev.sheldan.abstracto.core.interaction.context.ContextCommandService;
|
||||||
import dev.sheldan.abstracto.core.interaction.context.management.ContextCommandInServerManagementService;
|
|
||||||
import dev.sheldan.abstracto.core.interaction.context.management.ContextCommandManagementService;
|
|
||||||
import dev.sheldan.abstracto.core.interaction.context.message.MessageContextCommandListenerBean;
|
import dev.sheldan.abstracto.core.interaction.context.message.MessageContextCommandListenerBean;
|
||||||
import dev.sheldan.abstracto.core.interaction.context.message.listener.MessageContextCommandListener;
|
import dev.sheldan.abstracto.core.interaction.context.message.listener.MessageContextCommandListener;
|
||||||
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandListenerBean;
|
import dev.sheldan.abstracto.core.interaction.slash.SlashCommandListenerBean;
|
||||||
@@ -20,6 +18,7 @@ import dev.sheldan.abstracto.core.service.management.ServerManagementService;
|
|||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.JDA;
|
import net.dv8tion.jda.api.JDA;
|
||||||
import net.dv8tion.jda.api.entities.Guild;
|
import net.dv8tion.jda.api.entities.Guild;
|
||||||
|
import net.dv8tion.jda.api.interactions.commands.build.CommandData;
|
||||||
import net.dv8tion.jda.api.interactions.commands.build.SlashCommandData;
|
import net.dv8tion.jda.api.interactions.commands.build.SlashCommandData;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.data.util.Pair;
|
import org.springframework.data.util.Pair;
|
||||||
@@ -28,6 +27,7 @@ import org.springframework.transaction.annotation.Transactional;
|
|||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
@Component
|
@Component
|
||||||
@Slf4j
|
@Slf4j
|
||||||
@@ -60,12 +60,6 @@ public class CommandLoaderListener implements AsyncStartupListener {
|
|||||||
@Autowired
|
@Autowired
|
||||||
private ServerManagementService serverManagementService;
|
private ServerManagementService serverManagementService;
|
||||||
|
|
||||||
@Autowired
|
|
||||||
private ContextCommandManagementService contextCommandManagementService;
|
|
||||||
|
|
||||||
@Autowired
|
|
||||||
private ContextCommandInServerManagementService contextCommandInServerManagementService;
|
|
||||||
|
|
||||||
@Autowired
|
@Autowired
|
||||||
private CommandLoaderListener self;
|
private CommandLoaderListener self;
|
||||||
|
|
||||||
@@ -92,7 +86,7 @@ public class CommandLoaderListener implements AsyncStartupListener {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
log.info("Updating slash command {} in guild {}.", command.getConfiguration().getName(), guild.getId());
|
log.info("Updating slash command {} in guild {}.", command.getConfiguration().getName(), guild.getId());
|
||||||
slashCommandService.convertCommandConfigToCommandData(command.getConfiguration(), slashCommandsToUpdate, guild.getIdLong());
|
slashCommandService.convertCommandConfigToCommandData(command.getConfiguration(), slashCommandsToUpdate, guild.getIdLong(), false);
|
||||||
});
|
});
|
||||||
|
|
||||||
log.info("Updating context commands for guild {}.", guild.getIdLong());
|
log.info("Updating context commands for guild {}.", guild.getIdLong());
|
||||||
@@ -126,7 +120,15 @@ public class CommandLoaderListener implements AsyncStartupListener {
|
|||||||
return null;
|
return null;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
List<Pair<List<CommandConfiguration>, SlashCommandData>> userCommandsToUpdate = new ArrayList<>();
|
||||||
|
incomingSlashCommands.forEach(command -> {
|
||||||
|
slashCommandService.convertCommandConfigToCommandData(command.getConfiguration(), userCommandsToUpdate, null, true);
|
||||||
|
});
|
||||||
|
List<CommandData> userCommands = userCommandsToUpdate
|
||||||
|
.stream()
|
||||||
|
.map(Pair::getSecond)
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
jda.updateCommands().addCommands(userCommands).queue();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Transactional
|
@Transactional
|
||||||
|
|||||||
@@ -7,6 +7,8 @@ import dev.sheldan.abstracto.core.interaction.context.message.listener.MessageCo
|
|||||||
import dev.sheldan.abstracto.core.interaction.modal.listener.ModalInteractionListener;
|
import dev.sheldan.abstracto.core.interaction.modal.listener.ModalInteractionListener;
|
||||||
import dev.sheldan.abstracto.core.interaction.modal.listener.ModalInteractionListenerModel;
|
import dev.sheldan.abstracto.core.interaction.modal.listener.ModalInteractionListenerModel;
|
||||||
import dev.sheldan.abstracto.core.models.listener.interaction.MessageContextInteractionModel;
|
import dev.sheldan.abstracto.core.models.listener.interaction.MessageContextInteractionModel;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import net.dv8tion.jda.api.interactions.callbacks.IReplyCallback;
|
import net.dv8tion.jda.api.interactions.callbacks.IReplyCallback;
|
||||||
@@ -57,18 +59,32 @@ public class InteractionExceptionServiceBean implements InteractionExceptionServ
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void reportSlashException(Throwable exception, SlashCommandInteractionEvent event, Command command) {
|
public void reportSlashException(Throwable exception, SlashCommandInteractionEvent event, Command command) {
|
||||||
log.info("Reporting exception of {} command {} in channel {} in guild {} from user {}.",
|
if(ContextUtils.hasGuild(event)) {
|
||||||
exception.getClass().getSimpleName(), command.getConfiguration().getName(),
|
log.info("Reporting exception of {} command {} in channel {} in guild {} from user {}.",
|
||||||
event.getChannel().getIdLong(), event.getGuild().getIdLong(), event.getMember().getIdLong(), exception);
|
exception.getClass().getSimpleName(), command.getConfiguration().getName(),
|
||||||
|
event.getChannel().getIdLong(), event.getGuild().getIdLong(), event.getMember().getIdLong(), exception);
|
||||||
|
} else {
|
||||||
|
log.info("Reporting exception of user command for user {}.", event.getUser().getIdLong());
|
||||||
|
}
|
||||||
reportGenericInteractionException(exception, event.getInteraction());
|
reportGenericInteractionException(exception, event.getInteraction());
|
||||||
}
|
}
|
||||||
|
|
||||||
private void reportGenericInteractionException(Throwable throwable, IReplyCallback replyCallback) {
|
private void reportGenericInteractionException(Throwable throwable, IReplyCallback replyCallback) {
|
||||||
GenericInteractionExceptionModel exceptionModel = buildInteractionExceptionModel(throwable, replyCallback);
|
GenericInteractionExceptionModel exceptionModel = buildInteractionExceptionModel(throwable, replyCallback);
|
||||||
if(replyCallback.isAcknowledged()) {
|
if(replyCallback.isAcknowledged()) {
|
||||||
interactionService.sendMessageToInteraction(GENERIC_INTERACTION_EXCEPTION, exceptionModel, replyCallback.getHook());
|
FutureUtils.toSingleFutureGeneric(interactionService.sendMessageToInteraction(GENERIC_INTERACTION_EXCEPTION, exceptionModel, replyCallback.getHook()))
|
||||||
|
.thenAccept(interactionHook -> log.info("Notified about exception."))
|
||||||
|
.exceptionally(throwable1 -> {
|
||||||
|
log.warn("Failed to notify about exception.", throwable1);
|
||||||
|
return null;
|
||||||
|
});;
|
||||||
} else {
|
} else {
|
||||||
interactionService.replyEmbed(GENERIC_INTERACTION_EXCEPTION, exceptionModel, replyCallback);
|
interactionService.replyEmbed(GENERIC_INTERACTION_EXCEPTION, exceptionModel, replyCallback)
|
||||||
|
.thenAccept(interactionHook -> log.info("Notified about exception."))
|
||||||
|
.exceptionally(throwable1 -> {
|
||||||
|
log.warn("Failed to notify about exception.", throwable1);
|
||||||
|
return null;
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ import dev.sheldan.abstracto.core.service.management.ServerManagementService;
|
|||||||
import dev.sheldan.abstracto.core.templating.model.AttachedFile;
|
import dev.sheldan.abstracto.core.templating.model.AttachedFile;
|
||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.entities.Message;
|
import net.dv8tion.jda.api.entities.Message;
|
||||||
import net.dv8tion.jda.api.entities.MessageEmbed;
|
import net.dv8tion.jda.api.entities.MessageEmbed;
|
||||||
@@ -107,9 +108,11 @@ public class InteractionServiceBean implements InteractionService {
|
|||||||
if(messageToSend.getEphemeral()) {
|
if(messageToSend.getEphemeral()) {
|
||||||
Interaction interaction = interactionHook.getInteraction();
|
Interaction interaction = interactionHook.getInteraction();
|
||||||
interactionHook.setEphemeral(messageToSend.getEphemeral());
|
interactionHook.setEphemeral(messageToSend.getEphemeral());
|
||||||
log.info("Sending ephemeral message to interaction in guild {} in channel {} for user {}.",
|
if(ContextUtils.hasGuild(interaction)) {
|
||||||
interaction.getGuild().getIdLong(), interaction.getChannel().getId(),
|
log.info("Sending ephemeral message to interaction in guild {} in channel {} for user {}.",
|
||||||
interaction.getMember().getIdLong());
|
interaction.getGuild().getIdLong(), interaction.getChannel().getId(),
|
||||||
|
interaction.getUser().getIdLong());
|
||||||
|
}
|
||||||
metricService.incrementCounter(EPHEMERAL_MESSAGES_SEND);
|
metricService.incrementCounter(EPHEMERAL_MESSAGES_SEND);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -134,13 +137,14 @@ public class InteractionServiceBean implements InteractionService {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<CompletableFuture<Message>> sendMessageToInteraction(String templateKey, Object model, InteractionHook interactionHook) {
|
public List<CompletableFuture<Message>> sendMessageToInteraction(String templateKey, Object model, InteractionHook interactionHook) {
|
||||||
MessageToSend messageToSend = templateService.renderEmbedTemplate(templateKey, model, interactionHook.getInteraction().getGuild().getIdLong());
|
Long serverId = ContextUtils.serverIdOrNull(interactionHook);
|
||||||
|
MessageToSend messageToSend = templateService.renderEmbedTemplate(templateKey, model, serverId);
|
||||||
return sendMessageToInteraction(messageToSend, interactionHook);
|
return sendMessageToInteraction(messageToSend, interactionHook);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<InteractionHook> replyEmbed(String templateKey, Object model, IReplyCallback callback) {
|
public CompletableFuture<InteractionHook> replyEmbed(String templateKey, Object model, IReplyCallback callback) {
|
||||||
Long serverId = callback.getGuild().getIdLong();
|
Long serverId = ContextUtils.serverIdOrNull(callback);
|
||||||
MessageToSend messageToSend = templateService.renderEmbedTemplate(templateKey, model, serverId);
|
MessageToSend messageToSend = templateService.renderEmbedTemplate(templateKey, model, serverId);
|
||||||
return replyMessageToSend(messageToSend, callback);
|
return replyMessageToSend(messageToSend, callback);
|
||||||
}
|
}
|
||||||
@@ -160,20 +164,24 @@ public class InteractionServiceBean implements InteractionService {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<CompletableFuture<Message>> sendEmbed(String templateKey, InteractionHook interactionHook) {
|
public List<CompletableFuture<Message>> sendEmbed(String templateKey, InteractionHook interactionHook) {
|
||||||
Long serverId = interactionHook.getInteraction().getGuild().getIdLong();
|
Long serverId = ContextUtils.serverIdOrNull(interactionHook);
|
||||||
MessageToSend messageToSend = templateService.renderEmbedTemplate(templateKey, new Object(), serverId);
|
MessageToSend messageToSend = templateService.renderEmbedTemplate(templateKey, new Object(), serverId);
|
||||||
return sendMessageToInteraction(messageToSend, interactionHook);
|
return sendMessageToInteraction(messageToSend, interactionHook);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<Message> replaceOriginal(MessageToSend messageToSend, InteractionHook interactionHook) {
|
public CompletableFuture<Message> replaceOriginal(MessageToSend messageToSend, InteractionHook interactionHook) {
|
||||||
Long serverId = interactionHook.getInteraction().getGuild().getIdLong();
|
Long serverId = ContextUtils.serverIdOrNull(interactionHook);
|
||||||
|
|
||||||
if(messageToSend.getEphemeral()) {
|
if(messageToSend.getEphemeral()) {
|
||||||
Interaction interaction = interactionHook.getInteraction();
|
Interaction interaction = interactionHook.getInteraction();
|
||||||
log.info("Sending ephemeral message to interaction in guild {} in channel {} for user {}.",
|
if(ContextUtils.hasGuild(interaction)) {
|
||||||
interaction.getGuild().getIdLong(), interaction.getChannel().getId(),
|
log.info("Sending ephemeral message to interaction in guild {} in channel {} for user {}.",
|
||||||
interaction.getMember().getIdLong());
|
interaction.getGuild().getIdLong(), interaction.getChannel().getId(),
|
||||||
|
interaction.getUser().getIdLong());
|
||||||
|
} else {
|
||||||
|
log.info("Sending ephemeral message to interaction for user {}", interactionHook.getInteraction().getUser().getIdLong());
|
||||||
|
}
|
||||||
metricService.incrementCounter(EPHEMERAL_MESSAGES_SEND);
|
metricService.incrementCounter(EPHEMERAL_MESSAGES_SEND);
|
||||||
interactionHook.setEphemeral(true);
|
interactionHook.setEphemeral(true);
|
||||||
}
|
}
|
||||||
@@ -215,7 +223,11 @@ public class InteractionServiceBean implements InteractionService {
|
|||||||
action = interactionHook.editOriginal(".");
|
action = interactionHook.editOriginal(".");
|
||||||
}
|
}
|
||||||
action = action.setComponents(actionRows);
|
action = action.setComponents(actionRows);
|
||||||
AServer server = serverManagementService.loadServer(serverId);
|
AServer server;
|
||||||
|
if(ContextUtils.isGuildKnown(interactionHook.getInteraction())) {
|
||||||
|
server = serverManagementService.loadServer(serverId);
|
||||||
|
} else {
|
||||||
|
server = null; }
|
||||||
actionRows.forEach(components -> components.forEach(component -> {
|
actionRows.forEach(components -> components.forEach(component -> {
|
||||||
if(component instanceof ActionComponent) {
|
if(component instanceof ActionComponent) {
|
||||||
String id = ((ActionComponent)component).getId();
|
String id = ((ActionComponent)component).getId();
|
||||||
@@ -242,7 +254,6 @@ public class InteractionServiceBean implements InteractionService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public CompletableFuture<InteractionHook> replyMessageToSend(MessageToSend messageToSend, IReplyCallback callback) {
|
public CompletableFuture<InteractionHook> replyMessageToSend(MessageToSend messageToSend, IReplyCallback callback) {
|
||||||
Long serverId = callback.getGuild().getIdLong();
|
|
||||||
ReplyCallbackAction action = null;
|
ReplyCallbackAction action = null;
|
||||||
if(messageToSend.getMessages() != null && !messageToSend.getMessages().isEmpty()) {
|
if(messageToSend.getMessages() != null && !messageToSend.getMessages().isEmpty()) {
|
||||||
metricService.incrementCounter(MESSAGE_SEND_METRIC);
|
metricService.incrementCounter(MESSAGE_SEND_METRIC);
|
||||||
@@ -279,7 +290,12 @@ public class InteractionServiceBean implements InteractionService {
|
|||||||
action = callback.reply(".");
|
action = callback.reply(".");
|
||||||
}
|
}
|
||||||
action = action.setComponents(actionRows);
|
action = action.setComponents(actionRows);
|
||||||
AServer server = serverManagementService.loadServer(serverId);
|
AServer server;
|
||||||
|
if(ContextUtils.isGuildKnown(callback)) {
|
||||||
|
server = serverManagementService.loadServer(callback.getGuild().getIdLong());
|
||||||
|
} else {
|
||||||
|
server = null;
|
||||||
|
}
|
||||||
actionRows.forEach(components -> components.forEach(component -> {
|
actionRows.forEach(components -> components.forEach(component -> {
|
||||||
if(component instanceof ActionComponent) {
|
if(component instanceof ActionComponent) {
|
||||||
String id = ((ActionComponent)component).getId();
|
String id = ((ActionComponent)component).getId();
|
||||||
@@ -292,17 +308,23 @@ public class InteractionServiceBean implements InteractionService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if(messageToSend.getEphemeral()) {
|
if(messageToSend.getEphemeral()) {
|
||||||
log.info("Sending ephemeral message to interaction in guild {} in channel {} for user {}.",
|
if(ContextUtils.hasGuild(callback)) {
|
||||||
callback.getGuild().getIdLong(), callback.getChannel().getId(),
|
log.info("Sending ephemeral message to interaction in guild {} in channel {} for user {}.",
|
||||||
callback.getMember().getIdLong());
|
callback.getGuild().getIdLong(), callback.getChannel().getId(),
|
||||||
|
callback.getUser().getIdLong());
|
||||||
|
} else {
|
||||||
|
log.info("Sending ephemeral message to user {}.", callback.getUser().getIdLong());
|
||||||
|
}
|
||||||
metricService.incrementCounter(EPHEMERAL_MESSAGES_SEND);
|
metricService.incrementCounter(EPHEMERAL_MESSAGES_SEND);
|
||||||
if(action != null) {
|
if(action != null) {
|
||||||
action = action.setEphemeral(messageToSend.getEphemeral());
|
action = action.setEphemeral(messageToSend.getEphemeral());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Set<Message.MentionType> allowedMentions = allowedMentionService.getAllowedMentionsFor(callback.getMessageChannel(), messageToSend);
|
if(ContextUtils.isGuildKnown(callback)) {
|
||||||
if(action != null) {
|
Set<Message.MentionType> allowedMentions = allowedMentionService.getAllowedMentionsFor(callback.getMessageChannel(), messageToSend);
|
||||||
action.setAllowedMentions(allowedMentions);
|
if (action != null) {
|
||||||
|
action.setAllowedMentions(allowedMentions);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(action == null) {
|
if(action == null) {
|
||||||
@@ -313,7 +335,7 @@ public class InteractionServiceBean implements InteractionService {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<InteractionHook> replyMessage(String templateKey, Object model, IReplyCallback callback) {
|
public CompletableFuture<InteractionHook> replyMessage(String templateKey, Object model, IReplyCallback callback) {
|
||||||
Long serverId = callback.getGuild().getIdLong();
|
Long serverId = ContextUtils.serverIdOrNull(callback);
|
||||||
MessageToSend messageToSend = templateService.renderTemplateToMessageToSend(templateKey, model, serverId);
|
MessageToSend messageToSend = templateService.renderTemplateToMessageToSend(templateKey, model, serverId);
|
||||||
return replyMessageToSend(messageToSend, callback);
|
return replyMessageToSend(messageToSend, callback);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -11,6 +11,7 @@ import dev.sheldan.abstracto.core.service.FeatureFlagService;
|
|||||||
import dev.sheldan.abstracto.core.service.FeatureModeService;
|
import dev.sheldan.abstracto.core.service.FeatureModeService;
|
||||||
import dev.sheldan.abstracto.core.interaction.ComponentPayloadManagementService;
|
import dev.sheldan.abstracto.core.interaction.ComponentPayloadManagementService;
|
||||||
import dev.sheldan.abstracto.core.utils.BeanUtils;
|
import dev.sheldan.abstracto.core.utils.BeanUtils;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.events.interaction.component.ButtonInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.component.ButtonInteractionEvent;
|
||||||
import net.dv8tion.jda.api.hooks.ListenerAdapter;
|
import net.dv8tion.jda.api.hooks.ListenerAdapter;
|
||||||
@@ -124,6 +125,9 @@ public class SyncButtonClickedListenerBean extends ListenerAdapter {
|
|||||||
if(!model.getEvent().isFromGuild()) {
|
if(!model.getEvent().isFromGuild()) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
if(ContextUtils.isUserCommand(model.getEvent())) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
if (!featureFlagService.isFeatureEnabled(feature, model.getServerId())) {
|
if (!featureFlagService.isFeatureEnabled(feature, model.getServerId())) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -30,6 +30,7 @@ import java.util.Date;
|
|||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.concurrent.ConcurrentHashMap;
|
import java.util.concurrent.ConcurrentHashMap;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.entities.Message;
|
import net.dv8tion.jda.api.entities.Message;
|
||||||
@@ -126,7 +127,11 @@ public class SlashCommandListenerBean extends ListenerAdapter {
|
|||||||
public void onSlashCommandInteraction(SlashCommandInteractionEvent event) {
|
public void onSlashCommandInteraction(SlashCommandInteractionEvent event) {
|
||||||
try {
|
try {
|
||||||
if(commands == null || commands.isEmpty()) return;
|
if(commands == null || commands.isEmpty()) return;
|
||||||
log.debug("Executing slash command in guild {} from user {}.", event.getGuild().getIdLong(), event.getMember().getIdLong());
|
if(ContextUtils.hasGuild(event.getInteraction())) {
|
||||||
|
log.debug("Executing slash command in guild {} from user {}.", event.getGuild().getIdLong(), event.getUser().getIdLong());
|
||||||
|
} else {
|
||||||
|
log.debug("Executing slash command by user {}", event.getUser().getIdLong());
|
||||||
|
}
|
||||||
CompletableFuture.runAsync(() -> self.executeListenerLogic(event), slashCommandExecutor).exceptionally(throwable -> {
|
CompletableFuture.runAsync(() -> self.executeListenerLogic(event), slashCommandExecutor).exceptionally(throwable -> {
|
||||||
log.error("Failed to execute listener logic in async slash command event.", throwable);
|
log.error("Failed to execute listener logic in async slash command event.", throwable);
|
||||||
return null;
|
return null;
|
||||||
@@ -136,6 +141,7 @@ public class SlashCommandListenerBean extends ListenerAdapter {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@Transactional
|
@Transactional
|
||||||
public void executeListenerLogic(SlashCommandInteractionEvent event) {
|
public void executeListenerLogic(SlashCommandInteractionEvent event) {
|
||||||
Optional<Command> potentialCommand = findCommand(event);
|
Optional<Command> potentialCommand = findCommand(event);
|
||||||
@@ -179,7 +185,14 @@ public class SlashCommandListenerBean extends ListenerAdapter {
|
|||||||
List<String> fullRepliesList = command.performAutoComplete(event);
|
List<String> fullRepliesList = command.performAutoComplete(event);
|
||||||
List<String> replies = fullRepliesList.subList(0, Math.min(fullRepliesList.size(), OptionData.MAX_CHOICES));
|
List<String> replies = fullRepliesList.subList(0, Math.min(fullRepliesList.size(), OptionData.MAX_CHOICES));
|
||||||
event.replyChoiceStrings(replies).queue(unused -> {},
|
event.replyChoiceStrings(replies).queue(unused -> {},
|
||||||
throwable -> log.error("Failed to response to complete of command {} in guild {}.", command.getConfiguration().getName(), event.getGuild().getIdLong()));
|
throwable -> {
|
||||||
|
if(ContextUtils.hasGuild(event)) {
|
||||||
|
log.error("Failed to respond to complete of command {} in guild {} by user {}.",
|
||||||
|
command.getConfiguration().getName(), event.getGuild().getIdLong(), event.getUser().getIdLong());
|
||||||
|
} else {
|
||||||
|
log.error("Failed to resp ond to complete of command {} for user {}.", command.getConfiguration().getName(), event.getUser().getIdLong());
|
||||||
|
}
|
||||||
|
});
|
||||||
} catch (Exception exception) {
|
} catch (Exception exception) {
|
||||||
log.error("Error while executing autocomplete of command {}.", command.getConfiguration().getName(), exception);
|
log.error("Error while executing autocomplete of command {}.", command.getConfiguration().getName(), exception);
|
||||||
}
|
}
|
||||||
@@ -268,7 +281,11 @@ public class SlashCommandListenerBean extends ListenerAdapter {
|
|||||||
CompletableFuture<CommandResult> commandOutput;
|
CompletableFuture<CommandResult> commandOutput;
|
||||||
if(conditionResult.isResult()) {
|
if(conditionResult.isResult()) {
|
||||||
commandOutput = command.executeSlash(event).thenApply(commandResult -> {
|
commandOutput = command.executeSlash(event).thenApply(commandResult -> {
|
||||||
log.info("Command {} in server {} was executed.", commandName, event.getGuild().getIdLong());
|
if(ContextUtils.hasGuild(event)) {
|
||||||
|
log.info("Command {} in server {} was executed by user {}.", command.getConfiguration().getName(), event.getGuild().getIdLong(), event.getUser().getIdLong());
|
||||||
|
} else {
|
||||||
|
log.info("Command {} was executed by user {}.", command.getConfiguration().getName(), event.getUser().getId());
|
||||||
|
}
|
||||||
return commandResult;
|
return commandResult;
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ package dev.sheldan.abstracto.core.interaction.slash;
|
|||||||
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
import dev.sheldan.abstracto.core.command.config.CommandConfiguration;
|
||||||
import dev.sheldan.abstracto.core.command.config.Parameter;
|
import dev.sheldan.abstracto.core.command.config.Parameter;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
import dev.sheldan.abstracto.core.command.execution.CommandResult;
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
import dev.sheldan.abstracto.core.command.model.database.ACommand;
|
import dev.sheldan.abstracto.core.command.model.database.ACommand;
|
||||||
import dev.sheldan.abstracto.core.command.model.database.ACommandInAServer;
|
import dev.sheldan.abstracto.core.command.model.database.ACommandInAServer;
|
||||||
import dev.sheldan.abstracto.core.command.service.management.CommandInServerManagementService;
|
import dev.sheldan.abstracto.core.command.service.management.CommandInServerManagementService;
|
||||||
@@ -15,19 +16,19 @@ import dev.sheldan.abstracto.core.service.FeatureFlagService;
|
|||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
import dev.sheldan.abstracto.core.utils.CompletableFutureList;
|
import dev.sheldan.abstracto.core.utils.CompletableFutureList;
|
||||||
import net.dv8tion.jda.api.entities.Guild;
|
import net.dv8tion.jda.api.entities.Guild;
|
||||||
|
import net.dv8tion.jda.api.interactions.IntegrationType;
|
||||||
|
import net.dv8tion.jda.api.interactions.InteractionContextType;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import net.dv8tion.jda.api.interactions.commands.Command;
|
import net.dv8tion.jda.api.interactions.commands.Command;
|
||||||
import net.dv8tion.jda.api.interactions.commands.OptionType;
|
import net.dv8tion.jda.api.interactions.commands.OptionType;
|
||||||
import net.dv8tion.jda.api.interactions.commands.build.*;
|
import net.dv8tion.jda.api.interactions.commands.build.*;
|
||||||
|
import org.apache.commons.lang3.StringUtils;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.data.util.Pair;
|
import org.springframework.data.util.Pair;
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
import org.springframework.transaction.annotation.Transactional;
|
import org.springframework.transaction.annotation.Transactional;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.*;
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
import java.util.Optional;
|
|
||||||
import java.util.concurrent.CompletableFuture;
|
import java.util.concurrent.CompletableFuture;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
@@ -58,8 +59,19 @@ public class SlashCommandServiceBean implements SlashCommandService {
|
|||||||
@Autowired
|
@Autowired
|
||||||
private InteractionService interactionService;
|
private InteractionService interactionService;
|
||||||
|
|
||||||
|
private final static Map<UserCommandConfig.CommandContext, InteractionContextType> CONTEXT_CONFIG = new HashMap<>();
|
||||||
|
|
||||||
|
static {
|
||||||
|
CONTEXT_CONFIG.put(UserCommandConfig.CommandContext.DM, InteractionContextType.PRIVATE_CHANNEL);
|
||||||
|
CONTEXT_CONFIG.put(UserCommandConfig.CommandContext.BOT_DM, InteractionContextType.BOT_DM);
|
||||||
|
CONTEXT_CONFIG.put(UserCommandConfig.CommandContext.GUILD, InteractionContextType.GUILD);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void convertCommandConfigToCommandData(CommandConfiguration commandConfiguration, List<Pair<List<CommandConfiguration>, SlashCommandData>> existingCommands, Long serverId) {
|
public void convertCommandConfigToCommandData(CommandConfiguration commandConfiguration, List<Pair<List<CommandConfiguration>, SlashCommandData>> existingCommands, Long serverId, boolean userCommandsOnly) {
|
||||||
|
if(userCommandsOnly && !commandConfiguration.isUserInstallable()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
boolean isTemplated = commandConfiguration.isTemplated();
|
boolean isTemplated = commandConfiguration.isTemplated();
|
||||||
SlashCommandConfig slashConfig = commandConfiguration.getSlashCommandConfig();
|
SlashCommandConfig slashConfig = commandConfiguration.getSlashCommandConfig();
|
||||||
String description;
|
String description;
|
||||||
@@ -69,15 +81,25 @@ public class SlashCommandServiceBean implements SlashCommandService {
|
|||||||
} else {
|
} else {
|
||||||
description = templateService.renderSimpleTemplate(internalCommandName + "_description", serverId);
|
description = templateService.renderSimpleTemplate(internalCommandName + "_description", serverId);
|
||||||
}
|
}
|
||||||
String rootName = slashConfig.getSlashCompatibleRootName();
|
String rootName = userCommandsOnly ? StringUtils.defaultString(slashConfig.getUserSlashCompatibleRootName(), slashConfig.getSlashCompatibleRootName()) : slashConfig.getSlashCompatibleRootName();
|
||||||
String groupName = slashConfig.getSlashCompatibleGroupName();
|
String groupName = userCommandsOnly ? StringUtils.defaultString(slashConfig.getUserSlashCompatibleGroupName(), slashConfig.getSlashCompatibleGroupName()) : slashConfig.getSlashCompatibleGroupName();
|
||||||
String commandName = slashConfig.getSlashCompatibleCommandName();
|
String commandName = userCommandsOnly ? StringUtils.defaultString(slashConfig.getUserSlashCompatibleCommandName(), slashConfig.getSlashCompatibleCommandName()) : slashConfig.getSlashCompatibleCommandName();
|
||||||
Optional<SlashCommandData> existingRootCommand = existingCommands
|
Optional<SlashCommandData> existingRootCommand = existingCommands
|
||||||
.stream()
|
.stream()
|
||||||
.filter(commandData -> commandData.getSecond().getName().equals(rootName))
|
.filter(commandData -> commandData.getSecond().getName().equals(rootName))
|
||||||
.map(Pair::getSecond)
|
.map(Pair::getSecond)
|
||||||
.findAny();
|
.findAny();
|
||||||
SlashCommandData rootCommand = existingRootCommand.orElseGet(() -> Commands.slash(rootName, description));
|
SlashCommandData rootCommand = existingRootCommand.orElseGet(() -> Commands.slash(rootName, description));
|
||||||
|
if(commandConfiguration.isUserInstallable() && userCommandsOnly) {
|
||||||
|
rootCommand.setIntegrationTypes(IntegrationType.USER_INSTALL);
|
||||||
|
if(commandConfiguration.getSlashCommandConfig().getUserCommandConfig() != null) {
|
||||||
|
Set<UserCommandConfig.CommandContext> allowedContexts = commandConfiguration.getSlashCommandConfig().getUserCommandConfig().getContexts();
|
||||||
|
Set<InteractionContextType> interactionContextTypes = mapCommandContexts(allowedContexts);
|
||||||
|
rootCommand.setContexts(interactionContextTypes);
|
||||||
|
} else {
|
||||||
|
rootCommand.setContexts(InteractionContextType.GUILD);
|
||||||
|
}
|
||||||
|
}
|
||||||
if(commandName != null) {
|
if(commandName != null) {
|
||||||
SubcommandData slashCommand = new SubcommandData(commandName, description);
|
SubcommandData slashCommand = new SubcommandData(commandName, description);
|
||||||
if(groupName == null) {
|
if(groupName == null) {
|
||||||
@@ -94,13 +116,13 @@ public class SlashCommandServiceBean implements SlashCommandService {
|
|||||||
rootCommand.addSubcommandGroups(groupData);
|
rootCommand.addSubcommandGroups(groupData);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
List<OptionData> requiredParameters = getParameters(commandConfiguration, isTemplated, internalCommandName, serverId);
|
List<OptionData> requiredParameters = getParameters(commandConfiguration, isTemplated, internalCommandName, serverId, userCommandsOnly);
|
||||||
slashCommand.addOptions(requiredParameters);
|
slashCommand.addOptions(requiredParameters);
|
||||||
} else {
|
} else {
|
||||||
List<OptionData> requiredParameters = getParameters(commandConfiguration, isTemplated, internalCommandName, serverId);
|
List<OptionData> requiredParameters = getParameters(commandConfiguration, isTemplated, internalCommandName, serverId, userCommandsOnly);
|
||||||
rootCommand.addOptions(requiredParameters);
|
rootCommand.addOptions(requiredParameters);
|
||||||
}
|
}
|
||||||
if(!existingRootCommand.isPresent()) {
|
if(existingRootCommand.isEmpty()) {
|
||||||
Optional<Pair<List<CommandConfiguration>, SlashCommandData>> existingCommand = existingCommands
|
Optional<Pair<List<CommandConfiguration>, SlashCommandData>> existingCommand = existingCommands
|
||||||
.stream()
|
.stream()
|
||||||
.filter(listSlashCommandDataPair -> listSlashCommandDataPair.getSecond().equals(rootCommand))
|
.filter(listSlashCommandDataPair -> listSlashCommandDataPair.getSecond().equals(rootCommand))
|
||||||
@@ -113,6 +135,18 @@ public class SlashCommandServiceBean implements SlashCommandService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private Set<InteractionContextType> mapCommandContexts(Set<UserCommandConfig.CommandContext> contexts) {
|
||||||
|
Set<InteractionContextType> mapped = new HashSet<>();
|
||||||
|
contexts.forEach(commandContext -> {
|
||||||
|
if(commandContext == UserCommandConfig.CommandContext.ALL) {
|
||||||
|
mapped.addAll(InteractionContextType.ALL);
|
||||||
|
} else {
|
||||||
|
mapped.add(CONTEXT_CONFIG.get(commandContext));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return mapped;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<CommandResult> completeConfirmableCommand(SlashCommandInteractionEvent event, String template) {
|
public CompletableFuture<CommandResult> completeConfirmableCommand(SlashCommandInteractionEvent event, String template) {
|
||||||
return completeConfirmableCommand(event, template, new Object());
|
return completeConfirmableCommand(event, template, new Object());
|
||||||
@@ -131,16 +165,19 @@ public class SlashCommandServiceBean implements SlashCommandService {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void convertCommandConfigToCommandData(CommandConfiguration commandConfiguration, List<Pair<List<CommandConfiguration>, SlashCommandData>> existingCommands) {
|
public void convertCommandConfigToCommandData(CommandConfiguration commandConfiguration, List<Pair<List<CommandConfiguration>, SlashCommandData>> existingCommands) {
|
||||||
convertCommandConfigToCommandData(commandConfiguration, existingCommands, null);
|
convertCommandConfigToCommandData(commandConfiguration, existingCommands, null, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
private List<OptionData> getParameters(CommandConfiguration commandConfiguration, boolean isTemplated, String internalCommandName, Long serverId) {
|
private List<OptionData> getParameters(CommandConfiguration commandConfiguration, boolean isTemplated, String internalCommandName, Long serverId, boolean userCommandsOnly) {
|
||||||
List<OptionData> requiredParameters = new ArrayList<>();
|
List<OptionData> requiredParameters = new ArrayList<>();
|
||||||
List<OptionData> optionalParameters = new ArrayList<>();
|
List<OptionData> optionalParameters = new ArrayList<>();
|
||||||
commandConfiguration.getParameters().forEach(parameter -> {
|
commandConfiguration.getParameters().forEach(parameter -> {
|
||||||
if(!shouldParameterBeCreated(parameter, serverId)) {
|
if(!shouldParameterBeCreated(parameter, serverId)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
if(userCommandsOnly && !parameter.getSupportsUserCommands()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
List<OptionType> types = slashCommandParameterService.getTypesFromParameter(parameter);
|
List<OptionType> types = slashCommandParameterService.getTypesFromParameter(parameter);
|
||||||
if(types.size() > 1) {
|
if(types.size() > 1) {
|
||||||
if(parameter.isListParam()) {
|
if(parameter.isListParam()) {
|
||||||
@@ -193,6 +230,9 @@ public class SlashCommandServiceBean implements SlashCommandService {
|
|||||||
if(parameter.getDependentFeatures().isEmpty()) {
|
if(parameter.getDependentFeatures().isEmpty()) {
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
|
if(serverId == null) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
List<FeatureDefinition> featureDefinitions = parameter
|
List<FeatureDefinition> featureDefinitions = parameter
|
||||||
.getDependentFeatures()
|
.getDependentFeatures()
|
||||||
.stream()
|
.stream()
|
||||||
|
|||||||
@@ -55,7 +55,7 @@ public class SlashCommandFeatureActivationListener implements FeatureActivationL
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
log.info("Updating slash command {} in guild {}.", command.getConfiguration().getName(), guild.getId());
|
log.info("Updating slash command {} in guild {}.", command.getConfiguration().getName(), guild.getId());
|
||||||
slashCommandService.convertCommandConfigToCommandData(command.getConfiguration(), commandsToUpDate, model.getServerId());
|
slashCommandService.convertCommandConfigToCommandData(command.getConfiguration(), commandsToUpDate, model.getServerId(), false);
|
||||||
});
|
});
|
||||||
slashCommandService.addGuildSlashCommands(guild, commandsToUpDate)
|
slashCommandService.addGuildSlashCommands(guild, commandsToUpDate)
|
||||||
.thenAccept(commands1 -> log.info("Updating {} slash commands in guild {}.", commandsToUpDate.size(), guild.getIdLong()));
|
.thenAccept(commands1 -> log.info("Updating {} slash commands in guild {}.", commandsToUpDate.size(), guild.getIdLong()));
|
||||||
|
|||||||
@@ -31,6 +31,7 @@ public class SlashCommandParameterServiceBean implements SlashCommandParameterSe
|
|||||||
name = name.toLowerCase(Locale.ROOT);
|
name = name.toLowerCase(Locale.ROOT);
|
||||||
List<OptionType> potentialOptionTypes = getTypesFromParameter(parameterType);
|
List<OptionType> potentialOptionTypes = getTypesFromParameter(parameterType);
|
||||||
OptionType actualOptionType = potentialOptionTypes.size() == 1 ? potentialOptionTypes.get(0) : null;
|
OptionType actualOptionType = potentialOptionTypes.size() == 1 ? potentialOptionTypes.get(0) : null;
|
||||||
|
boolean useFullName = true;
|
||||||
if (potentialOptionTypes.size() > 1) {
|
if (potentialOptionTypes.size() > 1) {
|
||||||
for (OptionType optionType: potentialOptionTypes) {
|
for (OptionType optionType: potentialOptionTypes) {
|
||||||
if(event.getOption(getFullQualifiedParameterName(name, optionType)) != null) {
|
if(event.getOption(getFullQualifiedParameterName(name, optionType)) != null) {
|
||||||
@@ -38,11 +39,17 @@ public class SlashCommandParameterServiceBean implements SlashCommandParameterSe
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if(actualOptionType == null) { // if we still didnt find it, lets try without the fully qualified name
|
||||||
|
if(event.getOption(name) != null) {
|
||||||
|
actualOptionType = event.getOption(name).getType();
|
||||||
|
useFullName = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if(actualOptionType == null) {
|
if(actualOptionType == null) {
|
||||||
throw new IllegalArgumentException(String.format("Could not determine option type for parameter %s", name));
|
throw new IllegalArgumentException(String.format("Could not determine option type for parameter %s", name));
|
||||||
}
|
}
|
||||||
if(potentialOptionTypes.size() > 1) {
|
if(potentialOptionTypes.size() > 1 && useFullName) {
|
||||||
name = getFullQualifiedParameterName(name, actualOptionType);
|
name = getFullQualifiedParameterName(name, actualOptionType);
|
||||||
}
|
}
|
||||||
if(actualOptionType == OptionType.BOOLEAN) {
|
if(actualOptionType == OptionType.BOOLEAN) {
|
||||||
@@ -77,6 +84,7 @@ public class SlashCommandParameterServiceBean implements SlashCommandParameterSe
|
|||||||
name = name.toLowerCase(Locale.ROOT);
|
name = name.toLowerCase(Locale.ROOT);
|
||||||
List<OptionType> potentialOptionTypes = getTypesFromParameter(parameterType);
|
List<OptionType> potentialOptionTypes = getTypesFromParameter(parameterType);
|
||||||
OptionType actualOptionType = potentialOptionTypes.size() == 1 ? potentialOptionTypes.get(0) : null;
|
OptionType actualOptionType = potentialOptionTypes.size() == 1 ? potentialOptionTypes.get(0) : null;
|
||||||
|
boolean useFullName = true;
|
||||||
if (potentialOptionTypes.size() > 1) {
|
if (potentialOptionTypes.size() > 1) {
|
||||||
for (OptionType optionType: potentialOptionTypes) {
|
for (OptionType optionType: potentialOptionTypes) {
|
||||||
if(event.getOption(getFullQualifiedParameterName(name, optionType)) != null) {
|
if(event.getOption(getFullQualifiedParameterName(name, optionType)) != null) {
|
||||||
@@ -84,11 +92,17 @@ public class SlashCommandParameterServiceBean implements SlashCommandParameterSe
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if(actualOptionType == null) { // if we still didnt find it, lets try without the fully qualified name
|
||||||
|
if(event.getOption(name) != null) {
|
||||||
|
actualOptionType = event.getOption(name).getType();
|
||||||
|
useFullName = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if(actualOptionType == null) {
|
if(actualOptionType == null) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if(potentialOptionTypes.size() > 1) {
|
if(potentialOptionTypes.size() > 1 && useFullName) {
|
||||||
name = getFullQualifiedParameterName(name, actualOptionType);
|
name = getFullQualifiedParameterName(name, actualOptionType);
|
||||||
}
|
}
|
||||||
if(actualOptionType == OptionType.BOOLEAN) {
|
if(actualOptionType == OptionType.BOOLEAN) {
|
||||||
@@ -159,17 +173,38 @@ public class SlashCommandParameterServiceBean implements SlashCommandParameterSe
|
|||||||
.stream()
|
.stream()
|
||||||
.filter(slashCommandParameterProvider -> slashCommandParameterProvider.getOptionMapping().getType().equals(parameter.getType()))
|
.filter(slashCommandParameterProvider -> slashCommandParameterProvider.getOptionMapping().getType().equals(parameter.getType()))
|
||||||
.findAny()
|
.findAny()
|
||||||
.map(slashCommandParameterProvider -> slashCommandParameterProvider.getOptionMapping(parameter).getOptionTypes())
|
.map(slashCommandParameterProvider -> {
|
||||||
|
List<OptionType> optionTypes;
|
||||||
|
if(parameter.getUseStrictParameters()) {
|
||||||
|
optionTypes = slashCommandParameterProvider.getOptionMapping(parameter).getStrictTypes();
|
||||||
|
} else {
|
||||||
|
optionTypes = slashCommandParameterProvider.getOptionMapping(parameter).getOptionTypes();
|
||||||
|
}
|
||||||
|
return optionTypes;
|
||||||
|
})
|
||||||
.orElseThrow(() -> new IllegalArgumentException(String.format("Unknown type for slash command parameter desired %s", parameter.getType().getName())));
|
.orElseThrow(() -> new IllegalArgumentException(String.format("Unknown type for slash command parameter desired %s", parameter.getType().getName())));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<OptionType> getTypesFromParameter(Class clazz) {
|
public List<OptionType> getTypesFromParameter(Class clazz) {
|
||||||
|
return getTypesFromParameter(clazz, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<OptionType> getTypesFromParameter(Class clazz, boolean strict) {
|
||||||
return parameterProviders
|
return parameterProviders
|
||||||
.stream()
|
.stream()
|
||||||
.filter(slashCommandParameterProvider -> slashCommandParameterProvider.getOptionMapping().getType().equals(clazz))
|
.filter(slashCommandParameterProvider -> slashCommandParameterProvider.getOptionMapping().getType().equals(clazz))
|
||||||
.findAny()
|
.findAny()
|
||||||
.map(slashCommandParameterProvider -> slashCommandParameterProvider.getOptionMapping().getOptionTypes())
|
.map(slashCommandParameterProvider -> {
|
||||||
|
List<OptionType> optionTypes;
|
||||||
|
if(strict) {
|
||||||
|
optionTypes = slashCommandParameterProvider.getOptionMapping().getStrictTypes();
|
||||||
|
} else {
|
||||||
|
optionTypes = slashCommandParameterProvider.getOptionMapping().getOptionTypes();
|
||||||
|
}
|
||||||
|
return optionTypes;
|
||||||
|
})
|
||||||
.orElseThrow(() -> new IllegalArgumentException(String.format("Unknown type for slash command parameter desired %s", clazz.getName())));
|
.orElseThrow(() -> new IllegalArgumentException(String.format("Unknown type for slash command parameter desired %s", clazz.getName())));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -55,12 +55,14 @@ public class CombinedSlashCommandParameterProvider implements SlashCommandParame
|
|||||||
}
|
}
|
||||||
Set<OptionType> optionTypes = new HashSet<>();
|
Set<OptionType> optionTypes = new HashSet<>();
|
||||||
possibleTypes.forEach(additionalType -> {
|
possibleTypes.forEach(additionalType -> {
|
||||||
optionTypes.addAll(slashCommandParameterService.getTypesFromParameter(additionalType));
|
optionTypes.addAll(slashCommandParameterService.getTypesFromParameter(additionalType, parameter.getUseStrictParameters()));
|
||||||
});
|
});
|
||||||
return SlashCommandOptionTypeMapping
|
return SlashCommandOptionTypeMapping
|
||||||
.builder()
|
.builder()
|
||||||
.type(CombinedParameter.class)
|
.type(CombinedParameter.class)
|
||||||
.optionTypes(new ArrayList<>(optionTypes))
|
.optionTypes(new ArrayList<>(optionTypes))
|
||||||
|
// this is needed, because the combined parameter is defined as strict, hence we are using the strictTypes value from the returned object
|
||||||
|
.strictTypes(parameter.getUseStrictParameters() ? new ArrayList<>(optionTypes) : new ArrayList<>())
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ import net.dv8tion.jda.api.interactions.commands.OptionType;
|
|||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
@Component
|
@Component
|
||||||
public class UserSlashCommandParameterProvider implements SlashCommandParameterProvider {
|
public class UserSlashCommandParameterProvider implements SlashCommandParameterProvider {
|
||||||
@@ -16,6 +17,7 @@ public class UserSlashCommandParameterProvider implements SlashCommandParameterP
|
|||||||
.builder()
|
.builder()
|
||||||
.type(User.class)
|
.type(User.class)
|
||||||
.optionTypes(Arrays.asList(OptionType.USER, OptionType.STRING))
|
.optionTypes(Arrays.asList(OptionType.USER, OptionType.STRING))
|
||||||
|
.strictTypes(List.of(OptionType.USER))
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -56,7 +56,12 @@ public class ComponentPayloadManagementServiceBean implements ComponentPayloadMa
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ComponentPayload createButtonPayload(ButtonConfigModel buttonConfigModel, Long serverId) {
|
public ComponentPayload createButtonPayload(ButtonConfigModel buttonConfigModel, Long serverId) {
|
||||||
AServer server = serverManagementService.loadOrCreate(serverId);
|
AServer server;
|
||||||
|
if(serverId != null) {
|
||||||
|
server = serverManagementService.loadOrCreate(serverId);
|
||||||
|
} else {
|
||||||
|
server = null;
|
||||||
|
}
|
||||||
return createButtonPayload(buttonConfigModel, server);
|
return createButtonPayload(buttonConfigModel, server);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ package dev.sheldan.abstracto.core.service.paginator;
|
|||||||
import dev.sheldan.abstracto.core.command.config.features.CoreFeatureDefinition;
|
import dev.sheldan.abstracto.core.command.config.features.CoreFeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.config.ListenerPriority;
|
import dev.sheldan.abstracto.core.config.ListenerPriority;
|
||||||
|
import dev.sheldan.abstracto.core.interaction.InteractionService;
|
||||||
import dev.sheldan.abstracto.core.interaction.button.listener.ButtonClickedListenerResult;
|
import dev.sheldan.abstracto.core.interaction.button.listener.ButtonClickedListenerResult;
|
||||||
import dev.sheldan.abstracto.core.interaction.button.listener.ButtonClickedListener;
|
import dev.sheldan.abstracto.core.interaction.button.listener.ButtonClickedListener;
|
||||||
import dev.sheldan.abstracto.core.interaction.button.listener.ButtonClickedListenerModel;
|
import dev.sheldan.abstracto.core.interaction.button.listener.ButtonClickedListenerModel;
|
||||||
@@ -31,6 +32,9 @@ public class PaginatorButtonListener implements ButtonClickedListener {
|
|||||||
@Autowired
|
@Autowired
|
||||||
private TemplateServiceBean templateServiceBean;
|
private TemplateServiceBean templateServiceBean;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private InteractionService interactionService;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ButtonClickedListenerResult execute(ButtonClickedListenerModel model) {
|
public ButtonClickedListenerResult execute(ButtonClickedListenerModel model) {
|
||||||
PaginatorButtonPayload payload = (PaginatorButtonPayload) model.getDeserializedPayload();
|
PaginatorButtonPayload payload = (PaginatorButtonPayload) model.getDeserializedPayload();
|
||||||
@@ -64,8 +68,12 @@ public class PaginatorButtonListener implements ButtonClickedListener {
|
|||||||
log.debug("Moving to page {} in paginator {}.", targetPage, payload.getPaginatorId());
|
log.debug("Moving to page {} in paginator {}.", targetPage, payload.getPaginatorId());
|
||||||
MessageConfiguration messageConfiguration = payload.getEmbedConfigs().get(targetPage);
|
MessageConfiguration messageConfiguration = payload.getEmbedConfigs().get(targetPage);
|
||||||
MessageToSend messageToSend = templateServiceBean.convertEmbedConfigurationToMessageToSend(messageConfiguration);
|
MessageToSend messageToSend = templateServiceBean.convertEmbedConfigurationToMessageToSend(messageConfiguration);
|
||||||
messageService.editMessageInChannel(model.getEvent().getMessageChannel(), messageToSend, originalMessage.getIdLong())
|
interactionService.replaceOriginal(messageToSend, model.getEvent().getHook())
|
||||||
.thenAccept(unused -> log.info("Updated paginator {} to switch to page {}.", payload.getPaginatorId(), targetPage));
|
.thenAccept(unused -> log.info("Updated paginator {} to switch to page {}.", payload.getPaginatorId(), targetPage))
|
||||||
|
.exceptionally(throwable -> {
|
||||||
|
log.warn("Failed to update the paginator message.", throwable);
|
||||||
|
return null;
|
||||||
|
});
|
||||||
String accessorId = UUID.randomUUID().toString();
|
String accessorId = UUID.randomUUID().toString();
|
||||||
paginatorServiceBean.updateCurrentPage(payload.getPaginatorId(), targetPage, accessorId);
|
paginatorServiceBean.updateCurrentPage(payload.getPaginatorId(), targetPage, accessorId);
|
||||||
paginatorServiceBean.schedulePaginationDeletion(payload.getPaginatorId(), accessorId);
|
paginatorServiceBean.schedulePaginationDeletion(payload.getPaginatorId(), accessorId);
|
||||||
@@ -79,7 +87,7 @@ public class PaginatorButtonListener implements ButtonClickedListener {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Boolean handlesEvent(ButtonClickedListenerModel model) {
|
public Boolean handlesEvent(ButtonClickedListenerModel model) {
|
||||||
return PaginatorServiceBean.PAGINATOR_BUTTON.equals(model.getOrigin()) && model.getEvent().isFromGuild();
|
return PaginatorServiceBean.PAGINATOR_BUTTON.equals(model.getOrigin());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|||||||
@@ -14,6 +14,7 @@ import dev.sheldan.abstracto.core.templating.model.EmbedFooter;
|
|||||||
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
import dev.sheldan.abstracto.core.templating.model.MessageToSend;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
import dev.sheldan.abstracto.core.templating.service.TemplateService;
|
||||||
import dev.sheldan.abstracto.core.templating.service.TemplateServiceBean;
|
import dev.sheldan.abstracto.core.templating.service.TemplateServiceBean;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import dev.sheldan.abstracto.core.utils.CompletableFutureList;
|
import dev.sheldan.abstracto.core.utils.CompletableFutureList;
|
||||||
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
import dev.sheldan.abstracto.core.utils.FutureUtils;
|
||||||
import dev.sheldan.abstracto.scheduling.model.JobParameters;
|
import dev.sheldan.abstracto.scheduling.model.JobParameters;
|
||||||
@@ -77,12 +78,12 @@ public class PaginatorServiceBean implements PaginatorService {
|
|||||||
private static final ReentrantLock lock = new ReentrantLock();
|
private static final ReentrantLock lock = new ReentrantLock();
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<Void> createPaginatorFromTemplate(String templateKey, Object model, GuildMessageChannel textChannel, Long userId) {
|
public CompletableFuture<Void> createPaginatorFromTemplate(String templateKey, Object model, GuildMessageChannel messageChannel, Long userId) {
|
||||||
Long serverId = textChannel.getGuild().getIdLong();
|
Long serverId = messageChannel.getGuild().getIdLong();
|
||||||
PaginatorSetup setup = getPaginatorSetup(templateKey, model, userId, serverId);
|
PaginatorSetup setup = getPaginatorSetup(templateKey, model, userId, serverId);
|
||||||
log.info("Setting up paginator in channel {} in server {} with {} pages.", textChannel.getIdLong(),
|
log.info("Setting up paginator in channel {} in server {} with {} pages.", messageChannel.getIdLong(),
|
||||||
textChannel.getGuild().getIdLong(), setup.getConfiguration().getEmbedConfigs().size());
|
messageChannel.getGuild().getIdLong(), setup.getConfiguration().getEmbedConfigs().size());
|
||||||
List<CompletableFuture<Message>> paginatorFutures = channelService.sendMessageToSendToChannel(setup.getMessageToSend(), textChannel);
|
List<CompletableFuture<Message>> paginatorFutures = channelService.sendMessageToSendToChannel(setup.getMessageToSend(), messageChannel);
|
||||||
return FutureUtils.toSingleFutureGeneric(paginatorFutures)
|
return FutureUtils.toSingleFutureGeneric(paginatorFutures)
|
||||||
.thenAccept(unused -> self.setupButtonPayloads(paginatorFutures.get(0).join(), setup, serverId));
|
.thenAccept(unused -> self.setupButtonPayloads(paginatorFutures.get(0).join(), setup, serverId));
|
||||||
}
|
}
|
||||||
@@ -106,7 +107,7 @@ public class PaginatorServiceBean implements PaginatorService {
|
|||||||
PaginatorConfiguration configuration = gson.fromJson(embedConfig, PaginatorConfiguration.class);
|
PaginatorConfiguration configuration = gson.fromJson(embedConfig, PaginatorConfiguration.class);
|
||||||
setupFooters(configuration, serverId);
|
setupFooters(configuration, serverId);
|
||||||
|
|
||||||
configuration.setPaginatorId(componentService.generateComponentId());
|
configuration.setPaginatorId(componentService.generateComponentId(serverId));
|
||||||
configuration.setSinglePage(configuration.getEmbedConfigs().size() < 2);
|
configuration.setSinglePage(configuration.getEmbedConfigs().size() < 2);
|
||||||
PaginatorButtonPayload buttonPayload = getButtonPayload(configuration, exitButtonId, startButtonId, previousButtonId, nextButtonId, lastButtonId);
|
PaginatorButtonPayload buttonPayload = getButtonPayload(configuration, exitButtonId, startButtonId, previousButtonId, nextButtonId, lastButtonId);
|
||||||
if(configuration.getRestrictUser() != null && configuration.getRestrictUser()) {
|
if(configuration.getRestrictUser() != null && configuration.getRestrictUser()) {
|
||||||
@@ -133,8 +134,8 @@ public class PaginatorServiceBean implements PaginatorService {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<Void> createPaginatorFromTemplate(String templateKey, Object model, IReplyCallback callback) {
|
public CompletableFuture<Void> createPaginatorFromTemplate(String templateKey, Object model, IReplyCallback callback) {
|
||||||
Long serverId = callback.getGuild().getIdLong();
|
Long serverId = ContextUtils.serverIdOrNull(callback);
|
||||||
PaginatorSetup setup = getPaginatorSetup(templateKey, model, callback.getMember().getIdLong(), serverId);
|
PaginatorSetup setup = getPaginatorSetup(templateKey, model, callback.getUser().getIdLong(), serverId);
|
||||||
return interactionService.replyMessageToSend(setup.getMessageToSend(), callback)
|
return interactionService.replyMessageToSend(setup.getMessageToSend(), callback)
|
||||||
.thenCompose(interactionHook -> interactionHook.retrieveOriginal().submit())
|
.thenCompose(interactionHook -> interactionHook.retrieveOriginal().submit())
|
||||||
.thenAccept(message -> self.setupButtonPayloads(message, setup, serverId));
|
.thenAccept(message -> self.setupButtonPayloads(message, setup, serverId));
|
||||||
@@ -287,9 +288,12 @@ public class PaginatorServiceBean implements PaginatorService {
|
|||||||
|
|
||||||
@Transactional
|
@Transactional
|
||||||
public void cleanupPaginator(PaginatorInfo paginatorInfo) {
|
public void cleanupPaginator(PaginatorInfo paginatorInfo) {
|
||||||
|
// TODO not sure how this is supposed to work, maybe .... not sure
|
||||||
log.info("Cleaning up paginator {} in server {} channel {} message {}.", paginatorInfo.getPaginatorId(),
|
log.info("Cleaning up paginator {} in server {} channel {} message {}.", paginatorInfo.getPaginatorId(),
|
||||||
paginatorInfo.getServerId(), paginatorInfo.getChannelId(), paginatorInfo.getMessageId());
|
paginatorInfo.getServerId(), paginatorInfo.getChannelId(), paginatorInfo.getMessageId());
|
||||||
messageService.deleteMessageInChannelInServer(paginatorInfo.getServerId(), paginatorInfo.getChannelId(), paginatorInfo.getMessageId());
|
if(paginatorInfo.getServerId() != null) { // user commands store them with null, and we cannot cleanup those
|
||||||
|
messageService.deleteMessageInChannelInServer(paginatorInfo.getServerId(), paginatorInfo.getChannelId(), paginatorInfo.getMessageId());
|
||||||
|
}
|
||||||
componentPayloadManagementService.deletePayloads(paginatorInfo.getPayloadIds());
|
componentPayloadManagementService.deletePayloads(paginatorInfo.getPayloadIds());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import dev.sheldan.abstracto.core.command.Command;
|
|||||||
import dev.sheldan.abstracto.core.command.condition.detail.AdminModeDetail;
|
import dev.sheldan.abstracto.core.command.condition.detail.AdminModeDetail;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.service.ServerService;
|
import dev.sheldan.abstracto.core.service.ServerService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.Permission;
|
import net.dv8tion.jda.api.Permission;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
@@ -42,6 +43,9 @@ public class AdminModeCondition implements CommandCondition {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ConditionResult shouldExecute(SlashCommandInteractionEvent slashCommandInteractionEvent, Command command) {
|
public ConditionResult shouldExecute(SlashCommandInteractionEvent slashCommandInteractionEvent, Command command) {
|
||||||
|
if(ContextUtils.isUserCommand(slashCommandInteractionEvent)) {
|
||||||
|
return ConditionResult.SUCCESS;
|
||||||
|
}
|
||||||
boolean adminModeActive = service.adminModeActive(slashCommandInteractionEvent.getGuild());
|
boolean adminModeActive = service.adminModeActive(slashCommandInteractionEvent.getGuild());
|
||||||
if(adminModeActive){
|
if(adminModeActive){
|
||||||
if(slashCommandInteractionEvent.getMember().hasPermission(Permission.ADMINISTRATOR)) {
|
if(slashCommandInteractionEvent.getMember().hasPermission(Permission.ADMINISTRATOR)) {
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import dev.sheldan.abstracto.core.command.condition.detail.CommandCoolDownDetail
|
|||||||
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
||||||
import dev.sheldan.abstracto.core.command.execution.CoolDownCheckResult;
|
import dev.sheldan.abstracto.core.command.execution.CoolDownCheckResult;
|
||||||
import dev.sheldan.abstracto.core.command.service.CommandCoolDownService;
|
import dev.sheldan.abstracto.core.command.service.CommandCoolDownService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
@@ -39,6 +40,9 @@ public class CommandCoolDownCondition implements CommandCondition {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ConditionResult shouldExecute(SlashCommandInteractionEvent slashCommandInteractionEvent, Command command) {
|
public ConditionResult shouldExecute(SlashCommandInteractionEvent slashCommandInteractionEvent, Command command) {
|
||||||
|
if(ContextUtils.isUserCommand(slashCommandInteractionEvent)) {
|
||||||
|
return ConditionResult.SUCCESS;
|
||||||
|
}
|
||||||
commandCoolDownService.takeLock();
|
commandCoolDownService.takeLock();
|
||||||
try {
|
try {
|
||||||
CoolDownCheckResult result = commandCoolDownService.allowedToExecuteCommand(command, slashCommandInteractionEvent);
|
CoolDownCheckResult result = commandCoolDownService.allowedToExecuteCommand(command, slashCommandInteractionEvent);
|
||||||
|
|||||||
@@ -6,6 +6,7 @@ import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
|||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.service.FeatureConfigService;
|
import dev.sheldan.abstracto.core.service.FeatureConfigService;
|
||||||
import dev.sheldan.abstracto.core.service.FeatureFlagService;
|
import dev.sheldan.abstracto.core.service.FeatureFlagService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
@@ -29,6 +30,9 @@ public class FeatureEnabledCondition implements CommandCondition {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ConditionResult shouldExecute(SlashCommandInteractionEvent slashCommandInteractionEvent, Command command) {
|
public ConditionResult shouldExecute(SlashCommandInteractionEvent slashCommandInteractionEvent, Command command) {
|
||||||
|
if(ContextUtils.isUserCommand(slashCommandInteractionEvent)) {
|
||||||
|
return ConditionResult.SUCCESS;
|
||||||
|
}
|
||||||
Long serverId = slashCommandInteractionEvent.getGuild().getIdLong();
|
Long serverId = slashCommandInteractionEvent.getGuild().getIdLong();
|
||||||
return evaluateFeatureCondition(command, serverId);
|
return evaluateFeatureCondition(command, serverId);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,6 +6,7 @@ import dev.sheldan.abstracto.core.command.execution.CommandContext;
|
|||||||
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
import dev.sheldan.abstracto.core.config.FeatureDefinition;
|
||||||
import dev.sheldan.abstracto.core.config.FeatureMode;
|
import dev.sheldan.abstracto.core.config.FeatureMode;
|
||||||
import dev.sheldan.abstracto.core.service.FeatureModeService;
|
import dev.sheldan.abstracto.core.service.FeatureModeService;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
import net.dv8tion.jda.api.events.interaction.command.SlashCommandInteractionEvent;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
@@ -50,6 +51,9 @@ public class FeatureModeCondition implements CommandCondition {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ConditionResult shouldExecute(SlashCommandInteractionEvent slashCommandInteractionEvent, Command command) {
|
public ConditionResult shouldExecute(SlashCommandInteractionEvent slashCommandInteractionEvent, Command command) {
|
||||||
|
if(ContextUtils.isUserCommand(slashCommandInteractionEvent)) {
|
||||||
|
return ConditionResult.SUCCESS;
|
||||||
|
}
|
||||||
Long serverId = slashCommandInteractionEvent.getGuild().getIdLong();
|
Long serverId = slashCommandInteractionEvent.getGuild().getIdLong();
|
||||||
return checkFeatureModeCondition(command, serverId);
|
return checkFeatureModeCondition(command, serverId);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ import dev.sheldan.abstracto.core.models.database.RoleImmunity;
|
|||||||
import dev.sheldan.abstracto.core.service.RoleImmunityService;
|
import dev.sheldan.abstracto.core.service.RoleImmunityService;
|
||||||
import dev.sheldan.abstracto.core.service.RoleService;
|
import dev.sheldan.abstracto.core.service.RoleService;
|
||||||
import dev.sheldan.abstracto.core.utils.CompletableFutureList;
|
import dev.sheldan.abstracto.core.utils.CompletableFutureList;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.entities.Member;
|
import net.dv8tion.jda.api.entities.Member;
|
||||||
import net.dv8tion.jda.api.entities.User;
|
import net.dv8tion.jda.api.entities.User;
|
||||||
@@ -113,6 +114,9 @@ public class ImmuneUserCondition implements CommandCondition {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CompletableFuture<ConditionResult> shouldExecuteAsync(SlashCommandInteractionEvent event, Command command) {
|
public CompletableFuture<ConditionResult> shouldExecuteAsync(SlashCommandInteractionEvent event, Command command) {
|
||||||
|
if(ContextUtils.isUserCommand(event)) {
|
||||||
|
return CompletableFuture.completedFuture(ConditionResult.SUCCESS);
|
||||||
|
}
|
||||||
CommandConfiguration commandConfig = command.getConfiguration();
|
CommandConfiguration commandConfig = command.getConfiguration();
|
||||||
if(commandConfig.getEffects().isEmpty()) {
|
if(commandConfig.getEffects().isEmpty()) {
|
||||||
return ConditionResult.fromAsyncSuccess();
|
return ConditionResult.fromAsyncSuccess();
|
||||||
|
|||||||
@@ -8,7 +8,9 @@ import lombok.Getter;
|
|||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
@Getter @Builder @EqualsAndHashCode
|
@Getter
|
||||||
|
@Builder
|
||||||
|
@EqualsAndHashCode
|
||||||
public class CommandConfiguration {
|
public class CommandConfiguration {
|
||||||
|
|
||||||
private String name;
|
private String name;
|
||||||
@@ -56,4 +58,8 @@ public class CommandConfiguration {
|
|||||||
.enabled(false)
|
.enabled(false)
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
|
public boolean isUserInstallable() {
|
||||||
|
return slashCommandConfig != null && slashCommandConfig.isUserInstallable();
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -39,6 +39,10 @@ public class Parameter implements Serializable {
|
|||||||
private List<String> dependentFeatures = new ArrayList<>();
|
private List<String> dependentFeatures = new ArrayList<>();
|
||||||
@Builder.Default
|
@Builder.Default
|
||||||
private List<String> choices = new ArrayList<>();
|
private List<String> choices = new ArrayList<>();
|
||||||
|
@Builder.Default
|
||||||
|
private Boolean useStrictParameters = false;
|
||||||
|
@Builder.Default
|
||||||
|
private Boolean supportsUserCommands = true;
|
||||||
|
|
||||||
public String getSlashCompatibleName() {
|
public String getSlashCompatibleName() {
|
||||||
return name.toLowerCase(Locale.ROOT);
|
return name.toLowerCase(Locale.ROOT);
|
||||||
|
|||||||
@@ -0,0 +1,35 @@
|
|||||||
|
package dev.sheldan.abstracto.core.command.config;
|
||||||
|
|
||||||
|
import lombok.Builder;
|
||||||
|
import lombok.Getter;
|
||||||
|
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
|
@Getter
|
||||||
|
@Builder
|
||||||
|
public class UserCommandConfig {
|
||||||
|
@Builder.Default
|
||||||
|
private Set<CommandContext> contexts = new HashSet<>(List.of(CommandContext.GUILD));
|
||||||
|
|
||||||
|
public static UserCommandConfig guildOnly() {
|
||||||
|
return UserCommandConfig
|
||||||
|
.builder()
|
||||||
|
.contexts(Set.of(CommandContext.GUILD))
|
||||||
|
.build();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static UserCommandConfig all() {
|
||||||
|
return UserCommandConfig
|
||||||
|
.builder()
|
||||||
|
.contexts(Set.of(CommandContext.ALL))
|
||||||
|
.build();
|
||||||
|
}
|
||||||
|
|
||||||
|
public enum CommandContext {
|
||||||
|
BOT_DM, DM, GUILD, ALL
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
@@ -2,6 +2,7 @@ package dev.sheldan.abstracto.core.interaction.button.listener;
|
|||||||
|
|
||||||
import dev.sheldan.abstracto.core.listener.FeatureAwareListenerModel;
|
import dev.sheldan.abstracto.core.listener.FeatureAwareListenerModel;
|
||||||
import dev.sheldan.abstracto.core.interaction.button.ButtonPayload;
|
import dev.sheldan.abstracto.core.interaction.button.ButtonPayload;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.Builder;
|
import lombok.Builder;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
@@ -19,6 +20,6 @@ public class ButtonClickedListenerModel implements FeatureAwareListenerModel {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Long getServerId() {
|
public Long getServerId() {
|
||||||
return event.isFromGuild() ? event.getGuild().getIdLong() : null;
|
return ContextUtils.hasGuild(event) ? event.getGuild().getIdLong() : null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ package dev.sheldan.abstracto.core.interaction.menu.listener;
|
|||||||
|
|
||||||
import dev.sheldan.abstracto.core.interaction.menu.SelectMenuPayload;
|
import dev.sheldan.abstracto.core.interaction.menu.SelectMenuPayload;
|
||||||
import dev.sheldan.abstracto.core.listener.FeatureAwareListenerModel;
|
import dev.sheldan.abstracto.core.listener.FeatureAwareListenerModel;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.Builder;
|
import lombok.Builder;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
@@ -19,6 +20,6 @@ public class StringSelectMenuListenerModel implements FeatureAwareListenerModel
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Long getServerId() {
|
public Long getServerId() {
|
||||||
return event.isFromGuild() ? event.getGuild().getIdLong() : null;
|
return ContextUtils.hasGuild(event) ? event.getGuild().getIdLong() : null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ package dev.sheldan.abstracto.core.interaction.modal.listener;
|
|||||||
|
|
||||||
import dev.sheldan.abstracto.core.interaction.modal.ModalPayload;
|
import dev.sheldan.abstracto.core.interaction.modal.ModalPayload;
|
||||||
import dev.sheldan.abstracto.core.listener.FeatureAwareListenerModel;
|
import dev.sheldan.abstracto.core.listener.FeatureAwareListenerModel;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.Builder;
|
import lombok.Builder;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
@@ -18,6 +19,6 @@ public class ModalInteractionListenerModel implements FeatureAwareListenerModel
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Long getServerId() {
|
public Long getServerId() {
|
||||||
return event.isFromGuild() ? event.getGuild().getIdLong() : null;
|
return ContextUtils.hasGuild(event) ? event.getGuild().getIdLong() : null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,9 +1,12 @@
|
|||||||
package dev.sheldan.abstracto.core.interaction.slash;
|
package dev.sheldan.abstracto.core.interaction.slash;
|
||||||
|
|
||||||
|
import dev.sheldan.abstracto.core.command.config.UserCommandConfig;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.Builder;
|
import lombok.Builder;
|
||||||
import lombok.EqualsAndHashCode;
|
import lombok.EqualsAndHashCode;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import net.dv8tion.jda.api.interactions.commands.CommandInteractionPayload;
|
import net.dv8tion.jda.api.interactions.commands.CommandInteractionPayload;
|
||||||
|
import org.apache.commons.lang3.StringUtils;
|
||||||
|
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
|
|
||||||
@@ -13,20 +16,29 @@ import java.util.Locale;
|
|||||||
public class SlashCommandConfig {
|
public class SlashCommandConfig {
|
||||||
private boolean enabled;
|
private boolean enabled;
|
||||||
private String rootCommandName;
|
private String rootCommandName;
|
||||||
|
private String userRootCommandName;
|
||||||
private String groupName;
|
private String groupName;
|
||||||
|
private String userGroupName;
|
||||||
private String commandName;
|
private String commandName;
|
||||||
|
private String userCommandName;
|
||||||
|
|
||||||
|
@Builder.Default
|
||||||
|
private boolean userInstallable = false;
|
||||||
|
private UserCommandConfig userCommandConfig;
|
||||||
|
|
||||||
public boolean matchesInteraction(CommandInteractionPayload payload) {
|
public boolean matchesInteraction(CommandInteractionPayload payload) {
|
||||||
if(getSlashCompatibleRootName() != null && payload.getName() != null && !getSlashCompatibleRootName().equals(payload.getName())) {
|
String rootNameToUse = ContextUtils.isUserCommand(payload) ? StringUtils.defaultString(getUserSlashCompatibleRootName(), getSlashCompatibleRootName()) : getSlashCompatibleRootName();
|
||||||
|
String groupNameToUse = ContextUtils.isUserCommand(payload) ? StringUtils.defaultString(getUserSlashCompatibleGroupName(), getSlashCompatibleGroupName()) : getSlashCompatibleGroupName();
|
||||||
|
String commandNameToUse = ContextUtils.isUserCommand(payload) ? StringUtils.defaultString(getUserSlashCompatibleCommandName(), getSlashCompatibleCommandName()) : getSlashCompatibleCommandName();
|
||||||
|
if(!StringUtils.equals(rootNameToUse, payload.getName())) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if(getSlashCompatibleGroupName() != null && payload.getSubcommandGroup() != null && !getSlashCompatibleGroupName().equals(payload.getSubcommandGroup())) {
|
if(!StringUtils.equals(groupNameToUse, payload.getSubcommandGroup())) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if(getSlashCompatibleCommandName() != null && payload.getSubcommandName() != null && !getSlashCompatibleCommandName().equals(payload.getSubcommandName())) {
|
if(!StringUtils.equals(commandNameToUse, payload.getSubcommandName())) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -41,4 +53,16 @@ public class SlashCommandConfig {
|
|||||||
public String getSlashCompatibleCommandName() {
|
public String getSlashCompatibleCommandName() {
|
||||||
return commandName != null ? commandName.toLowerCase(Locale.ROOT) : null;
|
return commandName != null ? commandName.toLowerCase(Locale.ROOT) : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public String getUserSlashCompatibleRootName() {
|
||||||
|
return userRootCommandName != null ? userRootCommandName.toLowerCase(Locale.ROOT) : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getUserSlashCompatibleGroupName() {
|
||||||
|
return userGroupName != null ? userGroupName.toLowerCase(Locale.ROOT) : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getUserSlashCompatibleCommandName() {
|
||||||
|
return userCommandName != null ? userCommandName.toLowerCase(Locale.ROOT) : null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ import java.util.List;
|
|||||||
import java.util.concurrent.CompletableFuture;
|
import java.util.concurrent.CompletableFuture;
|
||||||
|
|
||||||
public interface SlashCommandService {
|
public interface SlashCommandService {
|
||||||
void convertCommandConfigToCommandData(CommandConfiguration commandConfiguration, List<Pair<List<CommandConfiguration>, SlashCommandData>> existingCommands, Long serverId);
|
void convertCommandConfigToCommandData(CommandConfiguration commandConfiguration, List<Pair<List<CommandConfiguration>, SlashCommandData>> existingCommands, Long serverId, boolean userCommandsOnly);
|
||||||
void convertCommandConfigToCommandData(CommandConfiguration commandConfiguration, List<Pair<List<CommandConfiguration>, SlashCommandData>> existingCommands);
|
void convertCommandConfigToCommandData(CommandConfiguration commandConfiguration, List<Pair<List<CommandConfiguration>, SlashCommandData>> existingCommands);
|
||||||
CompletableFuture<List<Command>> updateGuildSlashCommand(Guild guild, List<Pair<List<CommandConfiguration>, SlashCommandData>> commandData);
|
CompletableFuture<List<Command>> updateGuildSlashCommand(Guild guild, List<Pair<List<CommandConfiguration>, SlashCommandData>> commandData);
|
||||||
CompletableFuture<Void> deleteGuildSlashCommands(Guild guild, List<Long> slashCommandId, List<Long> commandInServerIdsToUnset);
|
CompletableFuture<Void> deleteGuildSlashCommands(Guild guild, List<Long> slashCommandId, List<Long> commandInServerIdsToUnset);
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import lombok.Builder;
|
|||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import net.dv8tion.jda.api.interactions.commands.OptionType;
|
import net.dv8tion.jda.api.interactions.commands.OptionType;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
@Getter
|
@Getter
|
||||||
@@ -11,4 +12,6 @@ import java.util.List;
|
|||||||
public class SlashCommandOptionTypeMapping {
|
public class SlashCommandOptionTypeMapping {
|
||||||
private Class type;
|
private Class type;
|
||||||
private List<OptionType> optionTypes;
|
private List<OptionType> optionTypes;
|
||||||
|
@Builder.Default
|
||||||
|
private List<OptionType> strictTypes = new ArrayList<>();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -21,5 +21,6 @@ public interface SlashCommandParameterService {
|
|||||||
Emoji loadEmoteFromString(String input, Guild guild);
|
Emoji loadEmoteFromString(String input, Guild guild);
|
||||||
List<OptionType> getTypesFromParameter(Parameter parameter);
|
List<OptionType> getTypesFromParameter(Parameter parameter);
|
||||||
List<OptionType> getTypesFromParameter(Class clazz);
|
List<OptionType> getTypesFromParameter(Class clazz);
|
||||||
|
List<OptionType> getTypesFromParameter(Class clazz, boolean strict);
|
||||||
String getFullQualifiedParameterName(String name, OptionType type);
|
String getFullQualifiedParameterName(String name, OptionType type);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package dev.sheldan.abstracto.core.models.listener.interaction;
|
package dev.sheldan.abstracto.core.models.listener.interaction;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.listener.FeatureAwareListenerModel;
|
import dev.sheldan.abstracto.core.listener.FeatureAwareListenerModel;
|
||||||
|
import dev.sheldan.abstracto.core.utils.ContextUtils;
|
||||||
import lombok.Builder;
|
import lombok.Builder;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
@@ -14,6 +15,6 @@ public class MessageContextInteractionModel implements FeatureAwareListenerModel
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Long getServerId() {
|
public Long getServerId() {
|
||||||
return event.isFromGuild() ? event.getGuild().getIdLong() : null;
|
return ContextUtils.hasGuild(event) ? event.getGuild().getIdLong() : null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import lombok.Getter;
|
|||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
import net.dv8tion.jda.api.entities.channel.concrete.TextChannel;
|
import net.dv8tion.jda.api.entities.channel.concrete.TextChannel;
|
||||||
import net.dv8tion.jda.api.entities.channel.middleman.GuildMessageChannel;
|
import net.dv8tion.jda.api.entities.channel.middleman.GuildMessageChannel;
|
||||||
|
import net.dv8tion.jda.api.entities.channel.middleman.MessageChannel;
|
||||||
|
|
||||||
@Getter
|
@Getter
|
||||||
@Setter
|
@Setter
|
||||||
@@ -13,18 +14,7 @@ public class ChannelDisplay {
|
|||||||
private String name;
|
private String name;
|
||||||
private String channelMention;
|
private String channelMention;
|
||||||
|
|
||||||
public static ChannelDisplay fromChannel(TextChannel channel) {
|
public static ChannelDisplay fromChannel(MessageChannel channel) {
|
||||||
if(channel == null) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
return ChannelDisplay
|
|
||||||
.builder()
|
|
||||||
.name(channel.getName())
|
|
||||||
.channelMention(channel.getAsMention())
|
|
||||||
.build();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static ChannelDisplay fromChannel(GuildMessageChannel channel) {
|
|
||||||
if(channel == null) {
|
if(channel == null) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package dev.sheldan.abstracto.core.models.template.display;
|
package dev.sheldan.abstracto.core.models.template.display;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.models.ServerUser;
|
import dev.sheldan.abstracto.core.models.ServerUser;
|
||||||
|
import dev.sheldan.abstracto.core.models.database.AUser;
|
||||||
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
|
||||||
import dev.sheldan.abstracto.core.utils.MemberUtils;
|
import dev.sheldan.abstracto.core.utils.MemberUtils;
|
||||||
import lombok.Builder;
|
import lombok.Builder;
|
||||||
@@ -38,6 +39,14 @@ public class MemberDisplay {
|
|||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static MemberDisplay fromAUser(AUser aUser) {
|
||||||
|
return MemberDisplay
|
||||||
|
.builder()
|
||||||
|
.memberMention(MemberUtils.getUserAsMention(aUser.getId()))
|
||||||
|
.userId(aUser.getId())
|
||||||
|
.build();
|
||||||
|
}
|
||||||
|
|
||||||
public static MemberDisplay fromIds(Long serverId, Long userId) {
|
public static MemberDisplay fromIds(Long serverId, Long userId) {
|
||||||
return MemberDisplay
|
return MemberDisplay
|
||||||
.builder()
|
.builder()
|
||||||
|
|||||||
@@ -11,6 +11,7 @@ import net.dv8tion.jda.api.entities.User;
|
|||||||
@Builder
|
@Builder
|
||||||
public class MemberNameDisplay {
|
public class MemberNameDisplay {
|
||||||
private String userName;
|
private String userName;
|
||||||
|
private String displayName;
|
||||||
private String nickname;
|
private String nickname;
|
||||||
private String discriminator;
|
private String discriminator;
|
||||||
private String userAvatarUrl;
|
private String userAvatarUrl;
|
||||||
@@ -25,6 +26,7 @@ public class MemberNameDisplay {
|
|||||||
.memberAvatarUrl(member.getEffectiveAvatar().getUrl(4096))
|
.memberAvatarUrl(member.getEffectiveAvatar().getUrl(4096))
|
||||||
.nickname(member.getNickname())
|
.nickname(member.getNickname())
|
||||||
.userName(user.getName())
|
.userName(user.getName())
|
||||||
|
.displayName(user.getGlobalName())
|
||||||
.memberMention(member.getAsMention())
|
.memberMention(member.getAsMention())
|
||||||
.userAvatarUrl(userAvatar)
|
.userAvatarUrl(userAvatar)
|
||||||
.discriminator(user.getDiscriminator())
|
.discriminator(user.getDiscriminator())
|
||||||
|
|||||||
@@ -1,47 +1,42 @@
|
|||||||
package dev.sheldan.abstracto.core.utils;
|
package dev.sheldan.abstracto.core.utils;
|
||||||
|
|
||||||
import dev.sheldan.abstracto.core.exception.AbstractoRunTimeException;
|
|
||||||
import dev.sheldan.abstracto.core.models.GuildChannelMember;
|
|
||||||
import dev.sheldan.abstracto.core.models.cache.CachedMessage;
|
|
||||||
import dev.sheldan.abstracto.core.models.context.UserInitiatedServerContext;
|
|
||||||
import dev.sheldan.abstracto.core.service.MemberService;
|
|
||||||
import dev.sheldan.abstracto.core.service.management.ChannelManagementService;
|
|
||||||
import dev.sheldan.abstracto.core.service.management.UserInServerManagementService;
|
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.dv8tion.jda.api.entities.channel.middleman.GuildMessageChannel;
|
import net.dv8tion.jda.api.interactions.Interaction;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import net.dv8tion.jda.api.interactions.InteractionHook;
|
||||||
import org.springframework.stereotype.Component;
|
|
||||||
|
|
||||||
import java.lang.reflect.InvocationTargetException;
|
|
||||||
import java.lang.reflect.Method;
|
|
||||||
|
|
||||||
@Component
|
|
||||||
@Slf4j
|
@Slf4j
|
||||||
public class ContextUtils {
|
public class ContextUtils {
|
||||||
|
|
||||||
@Autowired
|
public static boolean isGuildKnown(Interaction interaction) {
|
||||||
private ChannelManagementService channelManagementService;
|
return interaction.hasFullGuild();
|
||||||
|
}
|
||||||
|
|
||||||
@Autowired
|
public static boolean isGuildNotKnown(Interaction interaction) {
|
||||||
private UserInServerManagementService userInServerManagementService;
|
return !isGuildKnown(interaction);
|
||||||
|
}
|
||||||
|
|
||||||
@Autowired
|
public static boolean hasGuild(Interaction interaction) {
|
||||||
private MemberService memberService;
|
return interaction.getGuild() != null;
|
||||||
|
}
|
||||||
|
|
||||||
public <T extends UserInitiatedServerContext> UserInitiatedServerContext fromMessage(CachedMessage message, Class<T> clazz) {
|
|
||||||
Method m = null;
|
public static boolean isUserCommandInGuild(Interaction interaction) {
|
||||||
GuildChannelMember guildChannelMember = memberService.getServerChannelUser(message.getServerId(), message.getChannelId(), message.getAuthor().getAuthorId());
|
return isUserCommand(interaction) && interaction.getGuild() != null && interaction.getGuild().isDetached();
|
||||||
try {
|
}
|
||||||
m = clazz.getMethod("builder");
|
|
||||||
UserInitiatedServerContext.UserInitiatedServerContextBuilder<?, ?> builder = (UserInitiatedServerContext.UserInitiatedServerContextBuilder) m.invoke(null, null);
|
public static boolean isUserCommand(Interaction interaction) {
|
||||||
return builder
|
return interaction.getIntegrationOwners().getUserIntegration() != null && interaction.getIntegrationOwners().getGuildIntegration() == null;
|
||||||
.member(guildChannelMember.getMember())
|
}
|
||||||
.guild(guildChannelMember.getGuild())
|
|
||||||
.messageChannel((GuildMessageChannel) guildChannelMember.getTextChannel())
|
public static boolean isNotUserCommand(Interaction interaction) {
|
||||||
.build();
|
return !isUserCommand(interaction);
|
||||||
} catch (NoSuchMethodException | IllegalAccessException | InvocationTargetException e) {
|
}
|
||||||
log.error("Failed to execute builder method", e);
|
|
||||||
}
|
public static Long serverIdOrNull(Interaction interaction) {
|
||||||
throw new AbstractoRunTimeException("Failed to create UserInitiatedServerContext from message");
|
return ContextUtils.isGuildKnown(interaction) ? interaction.getGuild().getIdLong() : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Long serverIdOrNull(InteractionHook hook) {
|
||||||
|
return ContextUtils.isGuildKnown(hook.getInteraction()) ? hook.getInteraction().getGuild().getIdLong() : null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,6 +7,9 @@ public class MessageUtils {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static String buildMessageUrl(Long serverId, Long channelId, Long messageId) {
|
public static String buildMessageUrl(Long serverId, Long channelId, Long messageId) {
|
||||||
|
if(serverId == null || channelId == null || messageId == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
return String.format("https://discord.com/channels/%s/%s/%s", serverId, channelId, messageId);
|
return String.format("https://discord.com/channels/%s/%s/%s", serverId, channelId, messageId);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -55,7 +55,7 @@
|
|||||||
|
|
||||||
<properties>
|
<properties>
|
||||||
<maven.build.timestamp.format>yyyy/MM/dd HH:mm</maven.build.timestamp.format>
|
<maven.build.timestamp.format>yyyy/MM/dd HH:mm</maven.build.timestamp.format>
|
||||||
<jda.version>5.0.0-beta.21</jda.version>
|
<jda.version>5.3.0</jda.version>
|
||||||
<asciidoctor.maven.plugin.version>2.2.6</asciidoctor.maven.plugin.version>
|
<asciidoctor.maven.plugin.version>2.2.6</asciidoctor.maven.plugin.version>
|
||||||
<asciidoctorj.pdf.version>1.5.3</asciidoctorj.pdf.version>
|
<asciidoctorj.pdf.version>1.5.3</asciidoctorj.pdf.version>
|
||||||
<asciidoctorj.version>2.3.0</asciidoctorj.version>
|
<asciidoctorj.version>2.3.0</asciidoctorj.version>
|
||||||
|
|||||||
Reference in New Issue
Block a user