added assignable role place module including: setting up, configuring, deleting commands and documentation

upgraded JDA version to 4.2.0
refactored multiple interfaces to be more convenient/contain more information (reaction added/removed now gets the actual event)
added generic way to check for conditions. these conditions are provided by modules and are loosely connected via condition context and a condition name
added changeable flag to emotes to indicate that they can be updated via setEmote
refactored emote parsing in command parameters, the command parameters will now contain a fake emote
added feature to embed templates for fields to force a new message regardless of the discord limit
added some more functionality to message and channel service regarding field edit/embed sending
introduced the full emote parameter, to have both the emote (if custom) and a fake aemote at hand
refactored some methods to already throw exceptions within the retrieval methods, instead of optionals which need to be dealt outside
changed getEmotes to getEmotesBag to have duplicates of emotes
fixed setEmote to behave correctly with new parameter types
fixed creation of emotes, which previously created additional instances
fixed templating multiple fields handling
refactored command handling to allow async commands, they are the same interface, but configuration dicates whether or not it is async
added generic exception reporting for async commands
refactored a bunch of service methods to be named optional, and the non optional methods throw exceptions in case nothing is found
added a few more customized exceptions
added clearing freemarker internal template cache to clear cache
added feature to skip, not use, embeds if they look to be empty (no fields, no description, no attachment)
added virtual env to gitignore
fixed initial sync of roles un-marking roles as deleted
added some convenience methods to remove reactions from users directly
fixed post command handling in case it is not a templatable instance
fixed exceptions without cause in generic exception model
This commit is contained in:
Sheldan
2020-07-23 02:22:58 +02:00
parent 5317199bf4
commit fd4d784081
201 changed files with 6547 additions and 527 deletions

View File

@@ -49,7 +49,7 @@ public class ModMailMessageServiceBean implements ModMailMessageService {
// the opening of a private channel is a rest operation it itself, so we need
// to create the promises here already, else the list is empty for example
modMailMessages.forEach(modMailMessage -> messageFutures.add(new CompletableFuture<>()));
Optional<TextChannel> textChannelFromServer = botService.getTextChannelFromServer(thread.getServer().getId(), thread.getChannel().getId());
Optional<TextChannel> textChannelFromServer = botService.getTextChannelFromServerOptional(thread.getServer().getId(), thread.getChannel().getId());
if(textChannelFromServer.isPresent()) {
TextChannel modMailThread = textChannelFromServer.get();
botService.getInstance().openPrivateChannelById(thread.getUser().getUserReference().getId()).queue(privateChannel -> {

View File

@@ -313,7 +313,7 @@ public class ModMailThreadServiceBean implements ModMailThreadService {
@Override
public void relayMessageToModMailThread(ModMailThread modMailThread, Message message) {
Optional<TextChannel> textChannelFromServer = botService.getTextChannelFromServer(modMailThread.getServer().getId(), modMailThread.getChannel().getId());
Optional<TextChannel> textChannelFromServer = botService.getTextChannelFromServerOptional(modMailThread.getServer().getId(), modMailThread.getChannel().getId());
if(textChannelFromServer.isPresent()) {
TextChannel textChannel = textChannelFromServer.get();
self.sendUserReply(textChannel, modMailThread, message);

View File

@@ -1,6 +1,5 @@
package dev.sheldan.abstracto.modmail.service.management;
import dev.sheldan.abstracto.core.exception.ChannelNotFoundException;
import dev.sheldan.abstracto.core.models.database.AChannel;
import dev.sheldan.abstracto.core.models.database.AUser;
import dev.sheldan.abstracto.core.models.database.AUserInAServer;
@@ -26,8 +25,7 @@ public class ModMailThreadManagementServiceBean implements ModMailThreadManageme
@Override
public ModMailThread getByChannelId(Long channelId) {
Optional<AChannel> channelOpt = channelManagementService.loadChannel(channelId);
AChannel channel = channelOpt.orElseThrow(() -> new ChannelNotFoundException(channelId, 0L));
AChannel channel = channelManagementService.loadChannel(channelId);
return getByChannel(channel);
}

View File

@@ -1,6 +1,5 @@
package dev.sheldan.abstracto.modmail.setup;
import dev.sheldan.abstracto.core.exception.ChannelNotFoundException;
import dev.sheldan.abstracto.core.interactive.*;
import dev.sheldan.abstracto.core.models.AServerChannelUserId;
import dev.sheldan.abstracto.core.models.FeatureValidationResult;
@@ -25,7 +24,6 @@ import org.springframework.stereotype.Component;
import java.util.Arrays;
import java.util.List;
import java.util.Optional;
import java.util.concurrent.CompletableFuture;
import java.util.function.Consumer;
@@ -86,59 +84,54 @@ public class ModMailCategorySetupBean implements ModMailCategorySetup {
model.setCategory(category);
}
String messageText = templateService.renderTemplate(messageTemplateKey, model);
Optional<AChannel> channel = channelManagementService.loadChannel(user.getChannelId());
AChannel channel = channelManagementService.loadChannel(user.getChannelId());
CompletableFuture<SetupStepResult> future = new CompletableFuture<>();
AUserInAServer aUserInAServer = userInServerManagementService.loadUser(user.getGuildId(), user.getUserId());
// very odd case, if the channel the command was executed in, was not found in the database.
if(channel.isPresent()) {
Runnable finalAction = getTimeoutRunnable(user.getGuildId(), user.getChannelId());
Consumer<MessageReceivedEvent> configAction = (MessageReceivedEvent event) -> {
try {
Runnable finalAction = getTimeoutRunnable(user.getGuildId(), user.getChannelId());
Consumer<MessageReceivedEvent> configAction = (MessageReceivedEvent event) -> {
try {
SetupStepResult result;
Message message = event.getMessage();
// this checks whether or not the user wanted to cancel the setup
if(checkForExit(message)) {
result = SetupStepResult.fromCancelled();
SetupStepResult result;
Message message = event.getMessage();
// this checks whether or not the user wanted to cancel the setup
if(checkForExit(message)) {
result = SetupStepResult.fromCancelled();
} else {
String messageContent = event.getMessage().getContentRaw();
// directly parse the long from the message, for *now*, only the category ID is supported
Long categoryId = Long.parseLong(messageContent);
Guild guild = botService.getGuildByIdNullable(user.getGuildId());
FeatureValidationResult featureValidationResult = FeatureValidationResult.builder().validationResult(true).build();
// directly validate whether or not the given category ID is a valid value
modMailFeatureValidator.validateModMailCategory(featureValidationResult, guild, categoryId);
if(Boolean.TRUE.equals(featureValidationResult.getValidationResult())) {
ModMailCategoryDelayedActionConfig build = ModMailCategoryDelayedActionConfig
.builder()
.serverId(user.getGuildId())
.category(guild.getCategoryById(categoryId))
.categoryId(categoryId)
.build();
List<DelayedActionConfig> delayedSteps = Arrays.asList(build);
result = SetupStepResult
.builder()
.result(SetupStepResultType.SUCCESS)
.delayedActionConfigList(delayedSteps)
.build();
} else {
String messageContent = event.getMessage().getContentRaw();
// directly parse the long from the message, for *now*, only the category ID is supported
Long categoryId = Long.parseLong(messageContent);
Guild guild = botService.getGuildByIdNullable(user.getGuildId());
FeatureValidationResult featureValidationResult = FeatureValidationResult.builder().validationResult(true).build();
// directly validate whether or not the given category ID is a valid value
modMailFeatureValidator.validateModMailCategory(featureValidationResult, guild, categoryId);
if(Boolean.TRUE.equals(featureValidationResult.getValidationResult())) {
ModMailCategoryDelayedActionConfig build = ModMailCategoryDelayedActionConfig
.builder()
.serverId(user.getGuildId())
.category(guild.getCategoryById(categoryId))
.categoryId(categoryId)
.build();
List<DelayedActionConfig> delayedSteps = Arrays.asList(build);
result = SetupStepResult
.builder()
.result(SetupStepResultType.SUCCESS)
.delayedActionConfigList(delayedSteps)
.build();
} else {
// exceptions this exception is used to effectively fail the setup step
throw new InvalidCategoryException();
}
// exceptions this exception is used to effectively fail the setup step
throw new InvalidCategoryException();
}
future.complete(result);
} catch (Exception e) {
log.error("Failed to handle mod mail category step.", e);
future.completeExceptionally(new SetupStepException(e));
}
};
interactiveService.createMessageWithResponse(messageText, aUserInAServer, channel.get(), parameter.getPreviousMessageId(), configAction, finalAction);
} else {
future.completeExceptionally(new ChannelNotFoundException(user.getGuildId(), user.getChannelId()));
}
future.complete(result);
} catch (Exception e) {
log.error("Failed to handle mod mail category step.", e);
future.completeExceptionally(new SetupStepException(e));
}
};
interactiveService.createMessageWithResponse(messageText, aUserInAServer, channel, parameter.getPreviousMessageId(), configAction, finalAction);
return future;
}