mirror of
https://github.com/sciwhiz12/Janitor.git
synced 2024-11-12 23:51:25 +00:00
Externalize translation strings
This commit is contained in:
parent
b02f38c70f
commit
3c13b559e3
|
@ -8,6 +8,8 @@ import net.dv8tion.jda.api.entities.PrivateChannel;
|
|||
import net.dv8tion.jda.api.entities.User;
|
||||
import sciwhiz12.janitor.commands.CommandRegistry;
|
||||
import sciwhiz12.janitor.config.BotConfig;
|
||||
import sciwhiz12.janitor.msg.Messages;
|
||||
import sciwhiz12.janitor.msg.Translations;
|
||||
import sciwhiz12.janitor.utils.Util;
|
||||
|
||||
import java.util.concurrent.CompletableFuture;
|
||||
|
@ -18,14 +20,18 @@ import static sciwhiz12.janitor.Logging.STATUS;
|
|||
public class JanitorBot {
|
||||
private final JDA discord;
|
||||
private final BotConfig config;
|
||||
private final BotConsole console;
|
||||
private final CommandRegistry cmdRegistry;
|
||||
private final Messages messages;
|
||||
private BotConsole console;
|
||||
private CommandRegistry cmdRegistry;
|
||||
private Translations translations;
|
||||
|
||||
public JanitorBot(JDA discord, BotConfig config) {
|
||||
this.config = config;
|
||||
this.console = new BotConsole(this, System.in);
|
||||
this.cmdRegistry = new CommandRegistry(this, config.getCommandPrefix());
|
||||
this.discord = discord;
|
||||
this.translations = new Translations(this, config.getTranslationsFile());
|
||||
this.messages = new Messages(this);
|
||||
discord.addEventListener(cmdRegistry);
|
||||
discord.getPresence().setPresence(OnlineStatus.ONLINE, Activity.playing(" n' sweeping n' testing!"));
|
||||
discord.getGuilds().forEach(Guild::loadMembers);
|
||||
|
@ -52,10 +58,16 @@ public class JanitorBot {
|
|||
return this.config;
|
||||
}
|
||||
|
||||
public Messages getMessages() { return this.messages; }
|
||||
|
||||
public CommandRegistry getCommandRegistry() {
|
||||
return this.cmdRegistry;
|
||||
}
|
||||
|
||||
public Translations getTranslations() {
|
||||
return this.translations;
|
||||
}
|
||||
|
||||
public void shutdown() {
|
||||
JANITOR.info(STATUS, "Shutting down!");
|
||||
console.stop();
|
||||
|
|
|
@ -8,6 +8,7 @@ import org.slf4j.MarkerFactory;
|
|||
public class Logging {
|
||||
public static final Marker STATUS = MarkerFactory.getMarker("STATUS");
|
||||
public static final Marker COMMANDS = MarkerFactory.getMarker("COMMANDS");
|
||||
public static final Marker TRANSLATIONS = MarkerFactory.getMarker("TRANSLATIONS");
|
||||
|
||||
public static final Logger JANITOR = LoggerFactory.getLogger("janitor");
|
||||
public static final Logger CONSOLE = LoggerFactory.getLogger("janitor.console");
|
||||
|
|
|
@ -74,7 +74,8 @@ public class CommandRegistry implements EventListener {
|
|||
}
|
||||
JANITOR.debug(COMMANDS, "Executing command.");
|
||||
dispatcher.execute(parseResults);
|
||||
} catch (CommandSyntaxException ex) {
|
||||
}
|
||||
catch (CommandSyntaxException ex) {
|
||||
JANITOR.error(COMMANDS, "Error while parsing message and executing command", ex);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -4,6 +4,7 @@ import com.mojang.brigadier.builder.LiteralArgumentBuilder;
|
|||
import com.mojang.brigadier.context.CommandContext;
|
||||
import com.mojang.brigadier.exceptions.CommandSyntaxException;
|
||||
import net.dv8tion.jda.api.Permission;
|
||||
import net.dv8tion.jda.api.entities.Guild;
|
||||
import net.dv8tion.jda.api.entities.Member;
|
||||
import net.dv8tion.jda.api.entities.MessageChannel;
|
||||
import net.dv8tion.jda.api.events.message.MessageReceivedEvent;
|
||||
|
@ -12,11 +13,10 @@ import sciwhiz12.janitor.commands.BaseCommand;
|
|||
import sciwhiz12.janitor.commands.CommandRegistry;
|
||||
import sciwhiz12.janitor.commands.util.CommandHelper;
|
||||
import sciwhiz12.janitor.commands.util.ModerationHelper;
|
||||
import sciwhiz12.janitor.msg.General;
|
||||
import sciwhiz12.janitor.msg.Moderation;
|
||||
|
||||
import java.util.EnumSet;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
|
||||
import static com.mojang.brigadier.arguments.StringArgumentType.getString;
|
||||
import static com.mojang.brigadier.arguments.StringArgumentType.greedyString;
|
||||
|
@ -50,20 +50,37 @@ public class KickCommand extends BaseCommand {
|
|||
private int runWithReason(CommandContext<MessageReceivedEvent> ctx, @Nullable String reason) throws CommandSyntaxException {
|
||||
MessageChannel channel = ctx.getSource().getChannel();
|
||||
if (!ctx.getSource().isFromGuild()) {
|
||||
General.guildOnlyCommand(channel).queue();
|
||||
getBot().getMessages().GENERAL.guildOnlyCommand(channel).queue();
|
||||
return 1;
|
||||
}
|
||||
Member performer = ctx.getSource().getMember();
|
||||
if (performer == null) return 1;
|
||||
List<Member> members = getMembers("member", ctx).fromGuild(performer.getGuild());
|
||||
Member target = members.get(0);
|
||||
if (ModerationHelper.ensurePermissions(channel, performer, target, KICK_PERMISSION)) {
|
||||
target.getUser().openPrivateChannel()
|
||||
.flatMap(dm -> Moderation.kickedDM(dm, performer, target, reason))
|
||||
.flatMap(v -> ModerationHelper.kickUser(target.getGuild(), performer, target, reason))
|
||||
.flatMap(v -> Moderation.kickUser(ctx.getSource().getChannel(), performer, target, reason))
|
||||
.queue();
|
||||
final Guild guild = ctx.getSource().getGuild();
|
||||
final Member performer = Objects.requireNonNull(ctx.getSource().getMember());
|
||||
final List<Member> members = getMembers("member", ctx).fromGuild(performer.getGuild());
|
||||
if (members.size() < 1) {
|
||||
return 1;
|
||||
}
|
||||
final Member target = members.get(0);
|
||||
if (!guild.getSelfMember().hasPermission(KICK_PERMISSION)) {
|
||||
getBot().getMessages().GENERAL.insufficientPermissions(channel, KICK_PERMISSION).queue();
|
||||
return 1;
|
||||
}
|
||||
if (!guild.getSelfMember().canInteract(target)) {
|
||||
getBot().getMessages().GENERAL.cannotInteract(channel, target).queue();
|
||||
return 1;
|
||||
}
|
||||
if (!performer.hasPermission(KICK_PERMISSION)) {
|
||||
getBot().getMessages().MODERATION.performerInsufficientPermissions(channel, performer, KICK_PERMISSION).queue();
|
||||
return 1;
|
||||
}
|
||||
if (!performer.canInteract(target)) {
|
||||
getBot().getMessages().MODERATION.cannotModerate(channel, performer, target).queue();
|
||||
return 1;
|
||||
}
|
||||
target.getUser().openPrivateChannel()
|
||||
.flatMap(dm -> getBot().getMessages().MODERATION.kickedDM(dm, performer, target, reason))
|
||||
.flatMap(v -> ModerationHelper.kickUser(target.getGuild(), performer, target, reason))
|
||||
.flatMap(v -> getBot().getMessages().MODERATION.kickUser(channel, performer, target, reason))
|
||||
.queue();
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -3,37 +3,15 @@ package sciwhiz12.janitor.commands.util;
|
|||
import com.mojang.brigadier.arguments.ArgumentType;
|
||||
import com.mojang.brigadier.builder.LiteralArgumentBuilder;
|
||||
import com.mojang.brigadier.builder.RequiredArgumentBuilder;
|
||||
import net.dv8tion.jda.api.Permission;
|
||||
import net.dv8tion.jda.api.entities.Guild;
|
||||
import net.dv8tion.jda.api.entities.Member;
|
||||
import net.dv8tion.jda.api.entities.MessageChannel;
|
||||
import net.dv8tion.jda.api.events.message.MessageReceivedEvent;
|
||||
import sciwhiz12.janitor.msg.General;
|
||||
|
||||
import java.util.EnumSet;
|
||||
|
||||
public class CommandHelper {
|
||||
public static LiteralArgumentBuilder<MessageReceivedEvent> literal(String command) {
|
||||
return LiteralArgumentBuilder.literal(command);
|
||||
}
|
||||
|
||||
public static <Arg> RequiredArgumentBuilder<MessageReceivedEvent, Arg> argument(String command, ArgumentType<Arg> argument) {
|
||||
public static <Arg> RequiredArgumentBuilder<MessageReceivedEvent, Arg> argument(String command,
|
||||
ArgumentType<Arg> argument) {
|
||||
return RequiredArgumentBuilder.argument(command, argument);
|
||||
}
|
||||
|
||||
public static boolean canInteract(MessageChannel response, Member target) {
|
||||
if (!target.getGuild().getSelfMember().canInteract(target)) {
|
||||
General.cannotInteract(response, target).queue();
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
public static boolean hasPermission(MessageChannel response, Guild guild, EnumSet<Permission> permissions) {
|
||||
if (!guild.getSelfMember().hasPermission(permissions)) {
|
||||
General.insufficientPermissions(response, permissions).queue();
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,36 +1,18 @@
|
|||
package sciwhiz12.janitor.commands.util;
|
||||
|
||||
import net.dv8tion.jda.api.Permission;
|
||||
import net.dv8tion.jda.api.entities.Guild;
|
||||
import net.dv8tion.jda.api.entities.Member;
|
||||
import net.dv8tion.jda.api.entities.MessageChannel;
|
||||
import net.dv8tion.jda.api.requests.restaction.AuditableRestAction;
|
||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||
import sciwhiz12.janitor.msg.General;
|
||||
import sciwhiz12.janitor.msg.Moderation;
|
||||
|
||||
import java.util.EnumSet;
|
||||
import static sciwhiz12.janitor.utils.Util.nameFor;
|
||||
|
||||
public class ModerationHelper {
|
||||
public static AuditableRestAction<Void> kickUser(Guild guild, Member performer, Member target, @Nullable String reason) {
|
||||
StringBuilder auditReason = new StringBuilder();
|
||||
auditReason.append("Kicked by ").append(General.nameFor(performer.getUser()));
|
||||
auditReason.append("Kicked by ").append(nameFor(performer.getUser()));
|
||||
if (reason != null)
|
||||
auditReason.append(" for reason: ").append(reason);
|
||||
return guild.kick(target, auditReason.toString());
|
||||
}
|
||||
|
||||
public static boolean ensurePermissions(MessageChannel channel, Member performer, Member target, EnumSet<Permission> permissions) {
|
||||
if (!CommandHelper.hasPermission(channel, target.getGuild(), permissions)) return false;
|
||||
if (!CommandHelper.canInteract(channel, target)) return false;
|
||||
if (!performer.hasPermission(permissions)) {
|
||||
Moderation.performerInsufficientPermissions(channel, performer, permissions).queue();
|
||||
return false;
|
||||
}
|
||||
if (!performer.canInteract(target)) {
|
||||
Moderation.cannotModerate(channel, performer, target).queue();
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -3,6 +3,7 @@ package sciwhiz12.janitor.config;
|
|||
import com.electronwill.nightconfig.core.file.CommentedFileConfig;
|
||||
import com.electronwill.nightconfig.core.file.FileWatcher;
|
||||
import com.electronwill.nightconfig.toml.TomlFormat;
|
||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Path;
|
||||
|
@ -15,6 +16,7 @@ public class BotConfig {
|
|||
public static final Path DEFAULT_CONFIG_PATH = Path.of("config.toml");
|
||||
public static final String CLIENT_TOKEN = "discord.client_token";
|
||||
public static final String OWNER_ID = "discord.owner_id";
|
||||
public static final String TRANSLATION_FILE_PATH = "messages.translation_file";
|
||||
public static final String COMMAND_PREFIX = "commands.prefix";
|
||||
|
||||
private final BotOptions options;
|
||||
|
@ -33,7 +35,8 @@ public class BotConfig {
|
|||
config.load();
|
||||
// TODO: config spec
|
||||
FileWatcher.defaultInstance().addWatch(configPath, this::onFileChange);
|
||||
} catch (IOException ex) {
|
||||
}
|
||||
catch (IOException ex) {
|
||||
JANITOR.error("Error while building config from file {}", configPath, ex);
|
||||
}
|
||||
}
|
||||
|
@ -42,6 +45,13 @@ public class BotConfig {
|
|||
return config;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public Path getTranslationsFile() {
|
||||
return options.getTranslationsFile().
|
||||
or(() -> Optional.ofNullable(config.<String>get(TRANSLATION_FILE_PATH)).map(Path::of))
|
||||
.orElse(null);
|
||||
}
|
||||
|
||||
public Optional<String> getToken() {
|
||||
return options.getToken().or(() -> config.getOptional(CLIENT_TOKEN));
|
||||
}
|
||||
|
@ -62,7 +72,8 @@ public class BotConfig {
|
|||
try {
|
||||
CONFIG.info("Reloading config due to file change {}", configPath);
|
||||
config.load();
|
||||
} catch (Exception ex) {
|
||||
}
|
||||
catch (Exception ex) {
|
||||
CONFIG.error("Error while reloading config from {}", configPath, ex);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -13,6 +13,7 @@ import static joptsimple.util.PathProperties.*;
|
|||
public class BotOptions {
|
||||
private final OptionSet options;
|
||||
private final ArgumentAcceptingOptionSpec<Path> configPath;
|
||||
private final ArgumentAcceptingOptionSpec<Path> translationsPath;
|
||||
private final ArgumentAcceptingOptionSpec<String> token;
|
||||
private final ArgumentAcceptingOptionSpec<String> prefix;
|
||||
private final ArgumentAcceptingOptionSpec<Long> owner;
|
||||
|
@ -23,6 +24,10 @@ public class BotOptions {
|
|||
.accepts("config", "The path to the config file; defaults to 'config.toml'")
|
||||
.withRequiredArg()
|
||||
.withValuesConvertedBy(new PathConverter(FILE_EXISTING, READABLE, WRITABLE));
|
||||
this.translationsPath = parser
|
||||
.accepts("translations", "The path to the translations file")
|
||||
.withRequiredArg()
|
||||
.withValuesConvertedBy(new PathConverter(FILE_EXISTING, READABLE));
|
||||
this.token = parser
|
||||
.accepts("token", "The Discord token for the bot user")
|
||||
.withRequiredArg();
|
||||
|
@ -40,6 +45,10 @@ public class BotOptions {
|
|||
return configPath.valueOptional(options);
|
||||
}
|
||||
|
||||
public Optional<Path> getTranslationsFile() {
|
||||
return translationsPath.valueOptional(options);
|
||||
}
|
||||
|
||||
public Optional<String> getToken() {
|
||||
return token.valueOptional(options);
|
||||
}
|
||||
|
|
|
@ -1,67 +0,0 @@
|
|||
package sciwhiz12.janitor.msg;
|
||||
|
||||
import net.dv8tion.jda.api.EmbedBuilder;
|
||||
import net.dv8tion.jda.api.Permission;
|
||||
import net.dv8tion.jda.api.entities.*;
|
||||
import net.dv8tion.jda.api.requests.RestAction;
|
||||
|
||||
import java.util.EnumSet;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
public final class General {
|
||||
public static final int FAILURE_COLOR = 0xF73132;
|
||||
|
||||
private General() {
|
||||
}
|
||||
|
||||
public static RestAction<Message> guildOnlyCommand(MessageChannel channel) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle("Guild only command!")
|
||||
.setDescription("The previous command can only be run in a guild channel.")
|
||||
.setColor(FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public static RestAction<Message> insufficientPermissions(MessageChannel channel, EnumSet<Permission> permissions) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle("I have insufficient permissions!")
|
||||
.setDescription("I do not have sufficient permissions to carry out this action!\n" +
|
||||
"Please contact your server admins if you believe this is in error.")
|
||||
.addField(new MessageEmbed.Field(
|
||||
"Required permissions",
|
||||
permissions.stream().map(Permission::getName).collect(Collectors.joining(", ")),
|
||||
false))
|
||||
.setColor(FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public static RestAction<Message> ambiguousMember(MessageChannel channel) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle("Ambiguous member argument!")
|
||||
.setDescription("The name you have specified is too ambiguous (leads to more than 1 member)!\n" +
|
||||
"Please narrow down the specified name until it can uniquely identify a member of this guild.")
|
||||
.setColor(FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public static RestAction<Message> cannotInteract(MessageChannel channel, Member target) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle("Member is higher than me!")
|
||||
.setDescription("Cannot perform action on the given member, as they higher up in the hierarchy than me.")
|
||||
.addField("Target", nameFor(target.getUser()), true)
|
||||
.setColor(General.FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public static String nameFor(User user) {
|
||||
return user.getName().concat("#").concat(user.getDiscriminator());
|
||||
}
|
||||
}
|
142
src/main/java/sciwhiz12/janitor/msg/Messages.java
Normal file
142
src/main/java/sciwhiz12/janitor/msg/Messages.java
Normal file
|
@ -0,0 +1,142 @@
|
|||
package sciwhiz12.janitor.msg;
|
||||
|
||||
import net.dv8tion.jda.api.EmbedBuilder;
|
||||
import net.dv8tion.jda.api.Permission;
|
||||
import net.dv8tion.jda.api.entities.Member;
|
||||
import net.dv8tion.jda.api.entities.Message;
|
||||
import net.dv8tion.jda.api.entities.MessageChannel;
|
||||
import net.dv8tion.jda.api.entities.MessageEmbed;
|
||||
import net.dv8tion.jda.api.requests.RestAction;
|
||||
import net.dv8tion.jda.api.requests.restaction.MessageAction;
|
||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||
import sciwhiz12.janitor.JanitorBot;
|
||||
|
||||
import java.util.EnumSet;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import static sciwhiz12.janitor.utils.Util.nameFor;
|
||||
|
||||
public class Messages {
|
||||
private final JanitorBot bot;
|
||||
public final General GENERAL;
|
||||
public final Moderation MODERATION;
|
||||
|
||||
public Messages(JanitorBot bot) {
|
||||
this.bot = bot;
|
||||
this.GENERAL = new General();
|
||||
this.MODERATION = new Moderation();
|
||||
}
|
||||
|
||||
public String translate(String key, Object... args) {
|
||||
return bot.getTranslations().translate(key, args);
|
||||
}
|
||||
|
||||
public final class General {
|
||||
public static final int FAILURE_COLOR = 0xF73132;
|
||||
|
||||
private General() {}
|
||||
|
||||
public RestAction<Message> guildOnlyCommand(MessageChannel channel) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle(translate("general.guild_only_command.title"))
|
||||
.setDescription(translate("general.guild_only_command.desc"))
|
||||
.setColor(FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public RestAction<Message> insufficientPermissions(MessageChannel channel, EnumSet<Permission> permissions) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle(translate("general.insufficient_permissions.title"))
|
||||
.setDescription(translate("general.insufficient_permissions.desc"))
|
||||
.addField(new MessageEmbed.Field(
|
||||
translate("general.insufficient_permissions.field.permissions"),
|
||||
permissions.stream().map(Permission::getName).collect(Collectors.joining(", ")),
|
||||
false))
|
||||
.setColor(FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public RestAction<Message> ambiguousMember(MessageChannel channel) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle(translate("general.ambiguous_member.title"))
|
||||
.setDescription(translate("general.ambiguous_member.desc"))
|
||||
.setColor(FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public RestAction<Message> cannotInteract(MessageChannel channel, Member target) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle(translate("general.cannot_interact.title"))
|
||||
.setDescription(translate("general.cannot_interact.desc"))
|
||||
.addField(translate("general.cannot_interact.field.target"), nameFor(target.getUser()), true)
|
||||
.setColor(General.FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
public final class Moderation {
|
||||
public static final int MODERATION_COLOR = 0xF1BD25;
|
||||
public static final String GAVEL_ICON_URL = "https://cdn.discordapp.com/attachments/738478941760782526" +
|
||||
"/760463743330549760/gavel.png";
|
||||
|
||||
private Moderation() {}
|
||||
|
||||
public MessageAction performerInsufficientPermissions(MessageChannel channel, Member performer,
|
||||
EnumSet<Permission> permissions) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle(translate("moderation.insufficient_permissions.title"))
|
||||
.setDescription(translate("moderation.insufficient_permissions.desc"))
|
||||
.addField(translate("moderation.insufficient_permissions.field.performer"), nameFor(performer.getUser()),
|
||||
true)
|
||||
.addField(new MessageEmbed.Field(
|
||||
translate("moderation.insufficient_permissions.field.permissions"),
|
||||
permissions.stream().map(Permission::getName).collect(Collectors.joining(", ")),
|
||||
true))
|
||||
.setColor(General.FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public MessageAction cannotModerate(MessageChannel channel, Member performer, Member target) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle(translate("moderation.cannot_interact.title"))
|
||||
.setDescription(translate("moderation.cannot_interact.desc"))
|
||||
.addField(translate("moderation.cannot_interact.field.performer"), nameFor(performer.getUser()), true)
|
||||
.addField(translate("moderation.cannot_interact.field.target"), nameFor(target.getUser()), true)
|
||||
.setColor(General.FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public MessageAction kickUser(MessageChannel channel, Member performer, Member target, @Nullable String reason) {
|
||||
final EmbedBuilder embed = new EmbedBuilder()
|
||||
.setAuthor(translate("moderation.kick.info.author"), null, GAVEL_ICON_URL)
|
||||
.addField(translate("moderation.kick.info.field.performer"), nameFor(performer.getUser()), true)
|
||||
.addField(translate("moderation.kick.info.field.target"), nameFor(target.getUser()), true);
|
||||
if (reason != null)
|
||||
embed.addField(translate("moderation.kick.info.field.reason"), reason, false);
|
||||
return channel.sendMessage(embed.setColor(MODERATION_COLOR).build());
|
||||
}
|
||||
|
||||
public MessageAction kickedDM(MessageChannel channel, Member performer, Member target, @Nullable String reason) {
|
||||
final EmbedBuilder embed = new EmbedBuilder()
|
||||
.setAuthor(performer.getGuild().getName(), null, performer.getGuild().getIconUrl())
|
||||
.setTitle(translate("moderation.kick.dm.title"))
|
||||
.addField(translate("moderation.kick.dm.field.performer"), nameFor(performer.getUser()), true);
|
||||
if (reason != null)
|
||||
embed.addField(translate("moderation.kick.dm.field.reason"), reason, false);
|
||||
return channel.sendMessage(embed.setColor(MODERATION_COLOR).build());
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -1,73 +0,0 @@
|
|||
package sciwhiz12.janitor.msg;
|
||||
|
||||
import net.dv8tion.jda.api.EmbedBuilder;
|
||||
import net.dv8tion.jda.api.Permission;
|
||||
import net.dv8tion.jda.api.entities.Member;
|
||||
import net.dv8tion.jda.api.entities.MessageChannel;
|
||||
import net.dv8tion.jda.api.entities.MessageEmbed;
|
||||
import net.dv8tion.jda.api.requests.restaction.MessageAction;
|
||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||
|
||||
import java.util.EnumSet;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import static sciwhiz12.janitor.msg.General.nameFor;
|
||||
|
||||
public final class Moderation {
|
||||
public static final int MODERATION_COLOR = 0xF1BD25;
|
||||
public static final String GAVEL_ICON_URL = "https://cdn.discordapp.com/attachments/738478941760782526/760463743330549760/gavel.png";
|
||||
|
||||
private Moderation() {
|
||||
}
|
||||
|
||||
public static MessageAction performerInsufficientPermissions(MessageChannel channel, Member performer, EnumSet<Permission> permissions) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle("Insufficient permissions.")
|
||||
.setDescription("The performer of this command has insufficient permissions to use this command.")
|
||||
.addField("Performer", nameFor(performer.getUser()), true)
|
||||
.addField(new MessageEmbed.Field(
|
||||
"Required permissions",
|
||||
permissions.stream().map(Permission::getName).collect(Collectors.joining(", ")),
|
||||
true))
|
||||
.setColor(General.FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public static MessageAction cannotModerate(MessageChannel channel, Member performer, Member target) {
|
||||
return channel.sendMessage(
|
||||
new EmbedBuilder()
|
||||
.setTitle("Cannot moderate Target.")
|
||||
.setDescription("The performer of this command cannot moderate the target user, likely due to being lower in the role hierarchy.")
|
||||
.addField("Performer", nameFor(performer.getUser()), true)
|
||||
.addField("Target", nameFor(target.getUser()), true)
|
||||
.setColor(General.FAILURE_COLOR)
|
||||
.build()
|
||||
);
|
||||
}
|
||||
|
||||
public static MessageAction kickUser(MessageChannel channel, Member performer, Member target, @Nullable String reason) {
|
||||
final EmbedBuilder embed = new EmbedBuilder()
|
||||
.setAuthor("Kicked user from server.", null, GAVEL_ICON_URL)
|
||||
.addField("Moderator", nameFor(performer.getUser()), true)
|
||||
.addField("Target", nameFor(target.getUser()), true);
|
||||
if (reason != null)
|
||||
embed.addField("Reason", reason, false);
|
||||
return channel.sendMessage(
|
||||
embed.setColor(MODERATION_COLOR).build()
|
||||
);
|
||||
}
|
||||
|
||||
public static MessageAction kickedDM(MessageChannel channel, Member performer, Member target, @Nullable String reason) {
|
||||
final EmbedBuilder embed = new EmbedBuilder()
|
||||
.setAuthor(performer.getGuild().getName(), null, performer.getGuild().getIconUrl())
|
||||
.setTitle("You were kicked from this server.")
|
||||
.addField("Moderator", nameFor(performer.getUser()), true);
|
||||
if (reason != null)
|
||||
embed.addField("Reason", reason, false);
|
||||
return channel.sendMessage(
|
||||
embed.setColor(MODERATION_COLOR).build()
|
||||
);
|
||||
}
|
||||
}
|
77
src/main/java/sciwhiz12/janitor/msg/Translations.java
Normal file
77
src/main/java/sciwhiz12/janitor/msg/Translations.java
Normal file
|
@ -0,0 +1,77 @@
|
|||
package sciwhiz12.janitor.msg;
|
||||
|
||||
import com.google.common.io.Resources;
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.GsonBuilder;
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
import sciwhiz12.janitor.JanitorBot;
|
||||
|
||||
import java.io.InputStreamReader;
|
||||
import java.lang.reflect.Type;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import static sciwhiz12.janitor.Logging.JANITOR;
|
||||
import static sciwhiz12.janitor.Logging.TRANSLATIONS;
|
||||
|
||||
public class Translations {
|
||||
private static final Gson GSON = new GsonBuilder().create();
|
||||
private static final String DEFAULT_TRANSLATIONS_RESOURCE = "english.json";
|
||||
private static final Type MAP_TYPE = new TypeToken<Map<String, String>>() {}.getType();
|
||||
|
||||
private final JanitorBot bot;
|
||||
private final Path translationsFile;
|
||||
private final Map<String, String> translations = new HashMap<>();
|
||||
|
||||
public Translations(JanitorBot bot, Path translationsFile) {
|
||||
this.bot = bot;
|
||||
this.translationsFile = translationsFile;
|
||||
loadTranslations();
|
||||
}
|
||||
|
||||
void loadTranslations() {
|
||||
if (translationsFile == null) {
|
||||
JANITOR.info(TRANSLATIONS, "No translation file given, using default english translations");
|
||||
loadDefaultTranslations();
|
||||
return;
|
||||
}
|
||||
try {
|
||||
JANITOR.debug(TRANSLATIONS, "Loading translations from file {}", translationsFile);
|
||||
Map<String, String> trans = GSON.fromJson(Files.newBufferedReader(translationsFile), MAP_TYPE);
|
||||
translations.clear();
|
||||
translations.putAll(trans);
|
||||
JANITOR.info(TRANSLATIONS, "Loaded {} translations from file {}", translations.size(), translationsFile);
|
||||
}
|
||||
catch (Exception e) {
|
||||
JANITOR.error(TRANSLATIONS, "Error while loading translations from file {}", translationsFile, e);
|
||||
loadDefaultTranslations();
|
||||
}
|
||||
}
|
||||
|
||||
void loadDefaultTranslations() {
|
||||
try {
|
||||
JANITOR.debug(TRANSLATIONS, "Loading default english translations");
|
||||
// noinspection UnstableApiUsage
|
||||
Map<String, String> trans = GSON.fromJson(
|
||||
new InputStreamReader(Resources.getResource(DEFAULT_TRANSLATIONS_RESOURCE).openStream()),
|
||||
MAP_TYPE);
|
||||
translations.clear();
|
||||
translations.putAll(trans);
|
||||
JANITOR.info(TRANSLATIONS, "Loaded {} default english translations", translations.size());
|
||||
}
|
||||
catch (Exception e) {
|
||||
JANITOR.error(TRANSLATIONS, "Error while loading default english translations", e);
|
||||
}
|
||||
}
|
||||
|
||||
public Map<String, String> getTranslationMap() {
|
||||
return Collections.unmodifiableMap(translations);
|
||||
}
|
||||
|
||||
public String translate(String key, Object... args) {
|
||||
return String.format(translations.getOrDefault(key, key), args);
|
||||
}
|
||||
}
|
|
@ -47,6 +47,10 @@ public class Util {
|
|||
return String.format("<%s%s>", prefix, entity.getId());
|
||||
}
|
||||
|
||||
public static String nameFor(User user) {
|
||||
return user.getName().concat("#").concat(user.getDiscriminator());
|
||||
}
|
||||
|
||||
public static <Success, Error> BiConsumer<Success, Error> handle(final Consumer<Success> success,
|
||||
final Consumer<Error> exceptionally) {
|
||||
return (suc, ex) -> {
|
||||
|
|
|
@ -5,6 +5,10 @@ client_token = "NONE"
|
|||
# The id of the bot owner; used for sending status messages and allowing bot admin commands
|
||||
owner_id = 0
|
||||
|
||||
[messages]
|
||||
# The file containing the translation keys
|
||||
# translation_file = "english.json"
|
||||
|
||||
[commands]
|
||||
# The prefix for commands
|
||||
prefix = "!"
|
||||
|
|
27
src/main/resources/english.json
Normal file
27
src/main/resources/english.json
Normal file
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"general.guild_only_command.title": "Guild only command!",
|
||||
"general.guild_only_command.desc": "The previous command can only be run in a guild channel.",
|
||||
"general.insufficient_permissions.title": "I have insufficient permissions!",
|
||||
"general.insufficient_permissions.desc": "I do not have sufficient permissions to carry out this action!\nPlease contact your server admins if you believe this is in error.",
|
||||
"general.insufficient_permissions.field.permissions": "Required permissions",
|
||||
"general.ambiguous_member.title": "Ambiguous member argument!",
|
||||
"general.ambiguous_member.desc": "The name you have specified is too ambiguous (leads to more than 1 member)!\nPlease narrow down the specified name until it can uniquely identify a member of this guild.",
|
||||
"general.cannot_interact.title": "Member is higher than me!",
|
||||
"general.cannot_interact.desc": "Cannot perform action on the given member, likely due to me being lower in the role hierarchy.",
|
||||
"general.cannot_interact.field.target": "Target",
|
||||
"moderation.insufficient_permissions.title": "Insufficient permissions.",
|
||||
"moderation.insufficient_permissions.desc": "The performer of this command has insufficient permissions to use this command.",
|
||||
"moderation.insufficient_permissions.field.performer": "Performer",
|
||||
"moderation.insufficient_permissions.field.permissions": "Required permissions",
|
||||
"moderation.cannot_interact.title": "Cannot moderate Target.",
|
||||
"moderation.cannot_interact.desc": "The performer of this command cannot moderate the target user, likely due to being lower in the role hierarchy.",
|
||||
"moderation.cannot_interact.field.performer": "Performer",
|
||||
"moderation.cannot_interact.field.target": "Target",
|
||||
"moderation.kick.info.author": "Kicked user from server.",
|
||||
"moderation.kick.info.field.performer": "Performer",
|
||||
"moderation.kick.info.field.target": "Target",
|
||||
"moderation.kick.info.field.reason": "Reason",
|
||||
"moderation.kick.dm.title": "You were kicked from this server.",
|
||||
"moderation.kick.dm.field.performer": "Moderator",
|
||||
"moderation.kick.dm.field.reason": "Reason"
|
||||
}
|
Loading…
Reference in New Issue
Block a user