package eu.mhsl.craftattack.chatbridge; import net.luckperms.api.LuckPerms; import net.luckperms.api.model.user.User; import net.luckperms.api.node.Node; import net.luckperms.api.node.NodeType; import net.luckperms.api.node.types.PermissionNode; import java.time.Duration; import java.time.Instant; import java.util.Objects; import java.util.Optional; import java.util.UUID; import java.util.concurrent.CompletableFuture; import java.util.function.Consumer; /** * Mute als zeitlich begrenzte LuckPerms-Permission {@value #NODE}. Liegt damit in der gemeinsamen * MariaDB, gilt auf allen Servern und läuft von selbst ab. */ final class Mutes { static final String NODE = "chatbridge.muted"; private final LuckPerms luckPerms; Mutes(LuckPerms luckPerms) { this.luckPerms = luckPerms; } /** Ende des Mutes eines online Spielers, leer wenn nicht gestummt. */ Optional mutedUntil(UUID player) { User user = this.luckPerms.getUserManager().getUser(player); if (user == null) return Optional.empty(); return user.getNodes(NodeType.PERMISSION).stream() .filter(node -> node.getPermission().equals(NODE) && node.getValue()) .filter(node -> node.hasExpiry() && !node.hasExpired()) .map(Node::getExpiry) .filter(Objects::nonNull) .max(Instant::compareTo); } CompletableFuture mute(UUID player, Duration duration) { return this.modify(player, user -> { user.data().clear(node -> node.getKey().equals(NODE)); user.data().add(PermissionNode.builder(NODE).expiry(duration).build()); }); } CompletableFuture unmute(UUID player) { return this.modify(player, user -> user.data().clear(node -> node.getKey().equals(NODE))); } CompletableFuture lookup(String name) { return this.luckPerms.getUserManager().lookupUniqueId(name); } private CompletableFuture modify(UUID player, Consumer action) { User online = this.luckPerms.getUserManager().getUser(player); if (online == null) return this.luckPerms.getUserManager().modifyUser(player, action); action.accept(online); return this.luckPerms.getUserManager().saveUser(online); } /** „2 Stunden 5 Minuten“, unter einer Minute „weniger als eine Minute“. */ static String format(Duration duration) { long hours = duration.toHours(); long minutes = duration.toMinutesPart(); if (hours == 0 && minutes == 0) return "weniger als eine Minute"; StringBuilder text = new StringBuilder(); if (hours > 0) text.append(hours).append(hours == 1 ? " Stunde" : " Stunden"); if (minutes > 0) { if (!text.isEmpty()) text.append(' '); text.append(minutes).append(minutes == 1 ? " Minute" : " Minuten"); } return text.toString(); } }