Wide variety of changes for release
This commit is contained in:
parent
4bfcc5a2ff
commit
de559df98c
@ -56,5 +56,5 @@ tasks.register('copyJarToServer', Exec) {
|
||||
dependsOn shadowJar
|
||||
mustRunAfter shadowJar
|
||||
|
||||
commandLine 'scp', 'build/libs/spawn-1.0-all.jar', 'root@10.20.6.1:/root/server/plugins'
|
||||
commandLine 'scp', 'build/libs/spawn-1.0-all.jar', 'root@10.20.6.1:/home/minecraft/server/plugins'
|
||||
}
|
||||
|
@ -1,10 +1,12 @@
|
||||
package eu.mhsl.craftattack.spawn;
|
||||
|
||||
import eu.mhsl.craftattack.spawn.aggregates.displayName.DisplayName;
|
||||
import eu.mhsl.craftattack.spawn.api.HttpServer;
|
||||
import eu.mhsl.craftattack.spawn.appliance.Appliance;
|
||||
import eu.mhsl.craftattack.spawn.appliances.adminMarker.AdminMarker;
|
||||
import eu.mhsl.craftattack.spawn.appliances.kick.Kick;
|
||||
import eu.mhsl.craftattack.spawn.appliances.chatMessages.ChatMessages;
|
||||
import eu.mhsl.craftattack.spawn.appliances.outlawed.Outlawed;
|
||||
import eu.mhsl.craftattack.spawn.appliances.panicBan.PanicBan;
|
||||
import eu.mhsl.craftattack.spawn.appliances.projectStart.ProjectStart;
|
||||
import eu.mhsl.craftattack.spawn.appliances.debug.Debug;
|
||||
@ -51,8 +53,11 @@ public final class Main extends JavaPlugin {
|
||||
new Restart(),
|
||||
new Kick(),
|
||||
new PanicBan(),
|
||||
new Outlawed(),
|
||||
new DisplayName(),
|
||||
new Debug()
|
||||
);
|
||||
|
||||
Bukkit.getLogger().info("Loading appliances...");
|
||||
appliances.forEach(appliance -> {
|
||||
Bukkit.getLogger().info("Enabling " + appliance.getClass().getSimpleName());
|
||||
@ -81,7 +86,11 @@ public final class Main extends JavaPlugin {
|
||||
}
|
||||
|
||||
public <T extends Appliance> T getAppliance(Class<T> clazz) {
|
||||
return this.appliances.stream().filter(clazz::isInstance).map(clazz::cast).findFirst().orElseThrow();
|
||||
return this.appliances.stream()
|
||||
.filter(clazz::isInstance)
|
||||
.map(clazz::cast)
|
||||
.findFirst()
|
||||
.orElseThrow(() -> new RuntimeException(String.format("Appliance %s not loaded or instantiated!", clazz)));
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
|
@ -0,0 +1,10 @@
|
||||
package eu.mhsl.craftattack.spawn.aggregate;
|
||||
|
||||
import eu.mhsl.craftattack.spawn.Main;
|
||||
import eu.mhsl.craftattack.spawn.appliance.Appliance;
|
||||
|
||||
public abstract class Aggregate extends Appliance {
|
||||
public <T extends Appliance> T queryAppliance(Class<T> clazz) {
|
||||
return Main.instance().getAppliance(clazz);
|
||||
}
|
||||
}
|
@ -0,0 +1,53 @@
|
||||
package eu.mhsl.craftattack.spawn.aggregates.displayName;
|
||||
|
||||
import eu.mhsl.craftattack.spawn.aggregate.Aggregate;
|
||||
import eu.mhsl.craftattack.spawn.appliances.adminMarker.AdminMarker;
|
||||
import eu.mhsl.craftattack.spawn.appliances.adminMarker.AdminMarkerListener;
|
||||
import eu.mhsl.craftattack.spawn.appliances.outlawed.Outlawed;
|
||||
import net.kyori.adventure.text.Component;
|
||||
import net.kyori.adventure.text.ComponentBuilder;
|
||||
import net.kyori.adventure.text.TextComponent;
|
||||
import net.kyori.adventure.text.format.TextColor;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
public class DisplayName extends Aggregate {
|
||||
public void update(Player player) {
|
||||
TextColor playerColor = queryAppliance(AdminMarker.class).getPlayerColor(player);
|
||||
List<Supplier<Component>> prefixes = List.of(
|
||||
() -> queryAppliance(Outlawed.class).getNamePrefix(player)
|
||||
);
|
||||
|
||||
ComponentBuilder<TextComponent, TextComponent.Builder> playerName = Component.text();
|
||||
prefixes.forEach(supplier -> {
|
||||
Component prefix = supplier.get();
|
||||
if(prefix == null) return;
|
||||
playerName.append(prefix).append(Component.text(" "));
|
||||
});
|
||||
|
||||
playerName.append(Component.text(player.getName(), playerColor));
|
||||
|
||||
setGlobal(player, playerName.build());
|
||||
}
|
||||
|
||||
private void setGlobal(Player player, Component component) {
|
||||
try {
|
||||
player.customName(component);
|
||||
player.displayName(component);
|
||||
player.playerListName(component);
|
||||
} catch (Exception e) {
|
||||
//TODO this throws often exceptions, but still works, don't know why
|
||||
//Main.instance().getLogger().log(Level.SEVERE, e, e::getMessage);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
protected @NotNull List<Listener> eventHandlers() {
|
||||
return List.of(new AdminMarkerListener());
|
||||
}
|
||||
}
|
@ -0,0 +1,13 @@
|
||||
package eu.mhsl.craftattack.spawn.aggregates.displayName;
|
||||
|
||||
import eu.mhsl.craftattack.spawn.appliance.ApplianceListener;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.EventPriority;
|
||||
import org.bukkit.event.player.PlayerJoinEvent;
|
||||
|
||||
public class DisplayNameUpdateListener extends ApplianceListener<DisplayName> {
|
||||
@EventHandler(priority = EventPriority.LOWEST)
|
||||
public void onJoin(PlayerJoinEvent event) {
|
||||
getAppliance().update(event.getPlayer());
|
||||
}
|
||||
}
|
@ -51,7 +51,8 @@ public class HttpServer {
|
||||
|
||||
public <TRequest> void post(String path, Class<TRequest> clazz, RequestProvider<TRequest, Request, Object> onCall) {
|
||||
Spark.post(this.buildRoute(path), (req, resp) -> {
|
||||
TRequest parsed = new Gson().fromJson(req.body(), clazz);
|
||||
Main.instance().getLogger().info(req.body());
|
||||
TRequest parsed = HttpServer.this.gson.fromJson(req.body(), clazz);
|
||||
return this.process(() -> onCall.apply(parsed, req));
|
||||
});
|
||||
}
|
||||
|
@ -1,12 +1,19 @@
|
||||
package eu.mhsl.craftattack.spawn.appliances.adminMarker;
|
||||
|
||||
import eu.mhsl.craftattack.spawn.appliance.Appliance;
|
||||
import net.kyori.adventure.text.format.TextColor;
|
||||
import org.bukkit.Color;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public class AdminMarker extends Appliance {
|
||||
public TextColor getPlayerColor(Player player) {
|
||||
if (player.hasPermission("chatcolor")) return TextColor.color(Color.AQUA.asRGB()); // TODO read permission from config
|
||||
return TextColor.color(Color.WHITE.asRGB());
|
||||
}
|
||||
|
||||
@Override
|
||||
protected @NotNull List<Listener> eventHandlers() {
|
||||
|
@ -7,17 +7,12 @@ import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.player.PlayerJoinEvent;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
|
||||
public class AdminMarkerListener extends ApplianceListener<AdminMarker> {
|
||||
@EventHandler
|
||||
public void onPlayerJoin(PlayerJoinEvent event) {
|
||||
Player p = event.getPlayer();
|
||||
|
||||
p.customName(Optional.ofNullable(p.customName()).orElse(p.displayName()).color(getPlayerColor(p)));
|
||||
p.displayName(p.displayName().color(getPlayerColor(p)));
|
||||
p.playerListName(p.playerListName().color(getPlayerColor(p)));
|
||||
|
||||
}
|
||||
|
||||
private TextColor getPlayerColor(Player player) {
|
||||
|
@ -22,6 +22,7 @@ import org.bukkit.entity.Player;
|
||||
import org.bukkit.entity.Villager;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.bukkit.inventory.meta.ItemMeta;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.io.IOException;
|
||||
@ -30,10 +31,7 @@ import java.net.URISyntaxException;
|
||||
import java.net.http.HttpClient;
|
||||
import java.net.http.HttpRequest;
|
||||
import java.net.http.HttpResponse;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.UUID;
|
||||
import java.util.*;
|
||||
|
||||
public class Event extends Appliance {
|
||||
public DisplayVillager.ConfigBound villager;
|
||||
@ -42,8 +40,8 @@ public class Event extends Appliance {
|
||||
private final HttpClient eventServerClient = HttpClient.newHttpClient();
|
||||
private final List<Reward> pendingRewards = new ArrayList<>();
|
||||
|
||||
record RewardConfiguration(String material, Map<UUID, Integer> rewards) {}
|
||||
record Reward(UUID playerUuid, Material material, int amount) {}
|
||||
record RewardConfiguration(String memorialMaterial, String memorialTitle, String memorialLore, List<UUID> memorials, String material, Map<UUID, Integer> rewards) {}
|
||||
record Reward(UUID playerUuid, ItemStack itemStack) {}
|
||||
|
||||
public Event() {
|
||||
super("event");
|
||||
@ -87,6 +85,7 @@ public class Event extends Appliance {
|
||||
}
|
||||
|
||||
try {
|
||||
Main.instance().getLogger().info("Verbinde mit eventserver: " + p.getName());
|
||||
p.sendMessage(Component.text("Authentifiziere...", NamedTextColor.GREEN));
|
||||
record Request(UUID player, UUID room) {}
|
||||
Request request = new Request(p.getUniqueId(), this.roomId);
|
||||
@ -95,9 +94,13 @@ public class Event extends Appliance {
|
||||
.POST(HttpRequest.BodyPublishers.ofString(new Gson().toJson(request)))
|
||||
.build();
|
||||
|
||||
HttpResponse<Void> rawResponse = eventServerClient.send(queueRoomRequest, HttpResponse.BodyHandlers.discarding());
|
||||
if(rawResponse.statusCode() != 200) {
|
||||
p.sendMessage(Component.text("Fehler beim beitreten: " + rawResponse.statusCode(), NamedTextColor.RED));
|
||||
record Response(String error) {}
|
||||
HttpResponse<String> rawResponse = eventServerClient.send(queueRoomRequest, HttpResponse.BodyHandlers.ofString());
|
||||
Main.instance().getLogger().info("Response: " + rawResponse.body());
|
||||
Response response = new Gson().fromJson(rawResponse.body(), Response.class);
|
||||
|
||||
if(rawResponse.statusCode() != 200 || response.error != null) {
|
||||
p.sendMessage(Component.text("Fehler beim betreten: " + response.error, NamedTextColor.RED));
|
||||
return;
|
||||
}
|
||||
|
||||
@ -116,24 +119,36 @@ public class Event extends Appliance {
|
||||
|
||||
private void rewardPlayers(RewardConfiguration rewardConfiguration) {
|
||||
rewardConfiguration.rewards.forEach((uuid, amount) -> {
|
||||
Reward reward = new Reward(uuid, Material.matchMaterial(rewardConfiguration.material), amount);
|
||||
if(reward.material == null) throw new RuntimeException("Material not found");
|
||||
Reward reward = new Reward(uuid, new ItemStack(Objects.requireNonNull(Material.matchMaterial(rewardConfiguration.material)), amount));
|
||||
|
||||
if(Bukkit.getPlayer(uuid) == null) {
|
||||
pendingRewards.add(reward);
|
||||
return;
|
||||
}
|
||||
|
||||
giveReward(reward);
|
||||
});
|
||||
|
||||
for (UUID uuid : rewardConfiguration.memorials) {
|
||||
ItemStack memorialItem = new ItemStack(Objects.requireNonNull(Material.matchMaterial(rewardConfiguration.memorialMaterial)));
|
||||
ItemMeta meta = memorialItem.getItemMeta();
|
||||
meta.displayName(Component.text(rewardConfiguration.memorialTitle, NamedTextColor.GOLD));
|
||||
meta.lore(List.of(Component.text(rewardConfiguration.memorialLore, NamedTextColor.AQUA)));
|
||||
memorialItem.setItemMeta(meta);
|
||||
Reward memorial = new Reward(uuid, memorialItem);
|
||||
|
||||
if (Bukkit.getPlayer(uuid) == null) {
|
||||
pendingRewards.add(memorial);
|
||||
continue;
|
||||
}
|
||||
giveReward(memorial);
|
||||
}
|
||||
}
|
||||
|
||||
private void giveReward(Reward reward) {
|
||||
Player player = Bukkit.getPlayer(reward.playerUuid);
|
||||
if(player == null) throw new RuntimeException("Cannot reward offline playerUuid!");
|
||||
|
||||
ItemStack rewardStack = new ItemStack(reward.material, reward.amount);
|
||||
Map<Integer, ItemStack> remaining = player.getInventory().addItem(rewardStack);
|
||||
Map<Integer, ItemStack> remaining = player.getInventory().addItem(reward.itemStack);
|
||||
Bukkit.getScheduler().runTask(
|
||||
Main.instance(),
|
||||
() -> remaining.values().forEach(remainingStack -> player.getWorld().dropItem(player.getLocation(), remainingStack))
|
||||
|
@ -0,0 +1,7 @@
|
||||
package eu.mhsl.craftattack.spawn.appliances.outlawed;
|
||||
|
||||
public class OutlawForcedException extends Exception {
|
||||
public OutlawForcedException(String message) {
|
||||
super(message);
|
||||
}
|
||||
}
|
@ -0,0 +1,117 @@
|
||||
package eu.mhsl.craftattack.spawn.appliances.outlawed;
|
||||
|
||||
import eu.mhsl.craftattack.spawn.Main;
|
||||
import eu.mhsl.craftattack.spawn.aggregates.displayName.DisplayName;
|
||||
import eu.mhsl.craftattack.spawn.appliance.Appliance;
|
||||
import eu.mhsl.craftattack.spawn.appliance.ApplianceCommand;
|
||||
import eu.mhsl.craftattack.spawn.appliances.whitelist.Whitelist;
|
||||
import eu.mhsl.craftattack.spawn.config.Configuration;
|
||||
import eu.mhsl.craftattack.spawn.util.text.DisconnectInfo;
|
||||
import net.kyori.adventure.text.Component;
|
||||
import net.kyori.adventure.text.event.HoverEvent;
|
||||
import net.kyori.adventure.text.format.NamedTextColor;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.WeakHashMap;
|
||||
|
||||
public class Outlawed extends Appliance {
|
||||
public enum Status {
|
||||
DISABLED,
|
||||
VOLUNTARILY,
|
||||
FORCED
|
||||
}
|
||||
|
||||
private final Map<Player, Status> playerStatusMap = new WeakHashMap<>();
|
||||
private final String voluntarilyEntry = "voluntarily";
|
||||
public Outlawed() {
|
||||
super("outlawed");
|
||||
Bukkit.getScheduler().runTaskTimerAsynchronously(
|
||||
Main.instance(),
|
||||
() -> {
|
||||
playerStatusMap.forEach((player, status) -> {
|
||||
if(status != Status.FORCED) return;
|
||||
try {
|
||||
Main.instance().getAppliance(Whitelist.class).integrityCheck(player);
|
||||
} catch (DisconnectInfo.Throwable e) {
|
||||
Bukkit.getScheduler().runTask(Main.instance(), () -> e.getDisconnectScreen().applyKick(player));
|
||||
}
|
||||
});
|
||||
},
|
||||
20*60,
|
||||
20*60*5
|
||||
);
|
||||
}
|
||||
|
||||
public void switchLawStatus(Player player) throws OutlawForcedException {
|
||||
if(getLawStatus(player).equals(Status.FORCED)) {
|
||||
throw new OutlawForcedException("Dein Vogelfreistatus wurde als Strafe auferlegt und kann daher nicht verändert werden.");
|
||||
}
|
||||
|
||||
setLawStatus(player, isOutlawed(player) ? Status.DISABLED : Status.VOLUNTARILY);
|
||||
}
|
||||
|
||||
public void updateForcedStatus(Player player, boolean forced) {
|
||||
setLawStatus(player, forced ? Status.FORCED : getLawStatus(player) == Status.FORCED ? Status.DISABLED : getLawStatus(player));
|
||||
}
|
||||
|
||||
public Status getLawStatus(Player player) {
|
||||
Status status = playerStatusMap.computeIfAbsent(player, p -> {
|
||||
if(localConfig().getStringList(voluntarilyEntry).contains(p.getUniqueId().toString())) return Status.VOLUNTARILY;
|
||||
return Status.DISABLED;
|
||||
});
|
||||
return status;
|
||||
}
|
||||
|
||||
public void setLawStatus(Player player, Status status) {
|
||||
playerStatusMap.put(player, status);
|
||||
Main.instance().getAppliance(DisplayName.class).update(player);
|
||||
|
||||
List<String> newList = localConfig().getStringList(voluntarilyEntry);
|
||||
if(status.equals(Status.VOLUNTARILY)) {
|
||||
newList.add(player.getUniqueId().toString());
|
||||
} else {
|
||||
newList.remove(player.getUniqueId().toString());
|
||||
}
|
||||
localConfig().set(voluntarilyEntry, newList.stream().distinct().toList());
|
||||
Configuration.saveChanges();
|
||||
|
||||
}
|
||||
|
||||
public boolean isOutlawed(Player player) {
|
||||
return getLawStatus(player) != Status.DISABLED;
|
||||
}
|
||||
|
||||
public Component getStatusDescription(Status status) {
|
||||
return switch (status) {
|
||||
case DISABLED -> Component.text("Vogelfreistatus inaktiv: ", NamedTextColor.GREEN)
|
||||
.append(Component.text("Es gelten die Standart Regeln!", NamedTextColor.GOLD));
|
||||
|
||||
case VOLUNTARILY, FORCED -> Component.text("Vogelfreistatus aktiv: ", NamedTextColor.RED)
|
||||
.append(Component.text("Du darfst von jedem angegriffen und getötet werden!", NamedTextColor.GOLD));
|
||||
};
|
||||
}
|
||||
|
||||
public Component getNamePrefix(Player player) {
|
||||
if(isOutlawed(player)) {
|
||||
return Component.text("[☠]", NamedTextColor.RED)
|
||||
.hoverEvent(HoverEvent.showText(Component.text("Vogelfreie Spieler dürfen ohne Grund angegriffen werden!")));
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected @NotNull List<ApplianceCommand<?>> commands() {
|
||||
return List.of(new OutlawedCommand());
|
||||
}
|
||||
|
||||
@Override
|
||||
protected @NotNull List<Listener> eventHandlers() {
|
||||
return List.of(new OutlawedReminderListener());
|
||||
}
|
||||
}
|
@ -0,0 +1,27 @@
|
||||
package eu.mhsl.craftattack.spawn.appliances.outlawed;
|
||||
|
||||
import eu.mhsl.craftattack.spawn.appliance.ApplianceCommand;
|
||||
import net.kyori.adventure.text.Component;
|
||||
import net.kyori.adventure.text.format.NamedTextColor;
|
||||
import org.bukkit.command.Command;
|
||||
import org.bukkit.command.CommandSender;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class OutlawedCommand extends ApplianceCommand.PlayerChecked<Outlawed> {
|
||||
public OutlawedCommand() {
|
||||
super("vogelfrei");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void execute(@NotNull CommandSender sender, @NotNull Command command, @NotNull String label, @NotNull String[] args) throws Exception {
|
||||
try {
|
||||
getAppliance().switchLawStatus(getPlayer());
|
||||
sender.sendMessage(
|
||||
getAppliance()
|
||||
.getStatusDescription(getAppliance().getLawStatus(getPlayer()))
|
||||
);
|
||||
} catch (OutlawForcedException e) {
|
||||
sender.sendMessage(Component.text(e.getMessage(), NamedTextColor.RED));
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,14 @@
|
||||
package eu.mhsl.craftattack.spawn.appliances.outlawed;
|
||||
|
||||
import eu.mhsl.craftattack.spawn.appliance.ApplianceListener;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.player.PlayerJoinEvent;
|
||||
|
||||
public class OutlawedReminderListener extends ApplianceListener<Outlawed> {
|
||||
@EventHandler
|
||||
public void onJoin(PlayerJoinEvent e) {
|
||||
if(getAppliance().isOutlawed(e.getPlayer())) {
|
||||
e.getPlayer().sendMessage(getAppliance().getStatusDescription(getAppliance().getLawStatus(e.getPlayer())));
|
||||
}
|
||||
}
|
||||
}
|
@ -7,6 +7,7 @@ import eu.mhsl.craftattack.spawn.appliances.projectStart.command.ProjectStartCom
|
||||
import eu.mhsl.craftattack.spawn.appliances.projectStart.command.ProjectStartResetCommand;
|
||||
import eu.mhsl.craftattack.spawn.appliances.projectStart.listener.PlayerInvincibleListener;
|
||||
import eu.mhsl.craftattack.spawn.config.Configuration;
|
||||
import eu.mhsl.craftattack.spawn.util.entity.PlayerUtils;
|
||||
import eu.mhsl.craftattack.spawn.util.world.BlockCycle;
|
||||
import eu.mhsl.craftattack.spawn.util.text.ComponentUtil;
|
||||
import eu.mhsl.craftattack.spawn.util.text.Countdown;
|
||||
@ -21,13 +22,21 @@ import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
|
||||
import static java.util.Map.entry;
|
||||
import static org.bukkit.Sound.MUSIC_DISC_PIGSTEP;
|
||||
|
||||
public class ProjectStart extends Appliance {
|
||||
private final int startMusicAt = 137;
|
||||
private final Location glassLocation = new Location(Bukkit.getWorld("world"), -224, 67, -368);
|
||||
private final World startWorld = Bukkit.getWorld("world");
|
||||
private final Location glassLocation = new Location(startWorld, -224, 67, -368);
|
||||
private final List<Location> netherFireLocations = List.of(
|
||||
new Location(startWorld, -211, 68, -354),
|
||||
new Location(startWorld, -209, 68, -356),
|
||||
new Location(startWorld, -207, 68, -354),
|
||||
new Location(startWorld, -209, 68, -352)
|
||||
);
|
||||
|
||||
private final Countdown countdown = new Countdown(
|
||||
localConfig().getInt("countdown"),
|
||||
@ -102,6 +111,9 @@ public class ProjectStart extends Appliance {
|
||||
|
||||
IteratorUtil.worlds(World::getWorldBorder, worldBorder -> worldBorder.setSize(worldBorder.getMaxSize()));
|
||||
IteratorUtil.worlds(world -> IteratorUtil.setGameRules(gameRulesAfterStart, false));
|
||||
IteratorUtil.worlds(world -> world.setFullTime(0));
|
||||
|
||||
netherFireLocations.forEach(location -> Objects.requireNonNull(startWorld).getBlockAt(location).setType(Material.FIRE));
|
||||
|
||||
Bukkit.getOnlinePlayers().forEach(player -> {
|
||||
player.setFoodLevel(20);
|
||||
@ -114,6 +126,9 @@ public class ProjectStart extends Appliance {
|
||||
player.playSound(Sound.sound(org.bukkit.Sound.ITEM_GOAT_HORN_SOUND_5, Sound.Source.MASTER, 500f, 1f));
|
||||
|
||||
player.sendMessage(Component.text("Viel Spaß bei CraftAttack!", NamedTextColor.GREEN));
|
||||
|
||||
player.setStatistic(Statistic.TIME_SINCE_REST, 0);
|
||||
PlayerUtils.resetStatistics(player);
|
||||
});
|
||||
|
||||
Bukkit.getServer().advancementIterator().forEachRemaining(
|
||||
@ -140,6 +155,7 @@ public class ProjectStart extends Appliance {
|
||||
|
||||
IteratorUtil.worlds(world -> world, world -> IteratorUtil.setGameRules(gameRulesAfterStart, true));
|
||||
|
||||
|
||||
blockCycle.reset();
|
||||
}
|
||||
|
||||
|
@ -9,7 +9,7 @@ public class PlayerJoinListener extends ApplianceListener<Whitelist> {
|
||||
@EventHandler
|
||||
public void preLoginEvent(PlayerLoginEvent preLoginEvent) {
|
||||
try {
|
||||
getAppliance().login(preLoginEvent);
|
||||
getAppliance().integrityCheck(preLoginEvent.getPlayer());
|
||||
} catch (DisconnectInfo.Throwable e) {
|
||||
preLoginEvent.disallow(
|
||||
PlayerLoginEvent.Result.KICK_WHITELIST,
|
||||
|
@ -2,12 +2,16 @@ package eu.mhsl.craftattack.spawn.appliances.whitelist;
|
||||
|
||||
import com.google.gson.Gson;
|
||||
import eu.mhsl.craftattack.spawn.Main;
|
||||
import eu.mhsl.craftattack.spawn.api.HttpServer;
|
||||
import eu.mhsl.craftattack.spawn.appliance.Appliance;
|
||||
import eu.mhsl.craftattack.spawn.appliances.outlawed.Outlawed;
|
||||
import eu.mhsl.craftattack.spawn.util.server.Floodgate;
|
||||
import eu.mhsl.craftattack.spawn.util.text.DisconnectInfo;
|
||||
import org.apache.http.client.utils.URIBuilder;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.bukkit.event.player.PlayerLoginEvent;
|
||||
import org.eclipse.jetty.websocket.server.WebSocketHandler;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.io.IOException;
|
||||
@ -16,13 +20,15 @@ import java.net.URISyntaxException;
|
||||
import java.net.http.HttpClient;
|
||||
import java.net.http.HttpRequest;
|
||||
import java.net.http.HttpResponse;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
import java.util.UUID;
|
||||
import java.time.Instant;
|
||||
import java.time.ZoneOffset;
|
||||
import java.time.format.DateTimeFormatter;
|
||||
import java.time.temporal.ChronoUnit;
|
||||
import java.util.*;
|
||||
import java.util.logging.Level;
|
||||
|
||||
public class Whitelist extends Appliance {
|
||||
private record UserData(UUID uuid, String username, String firstname, String lastname) {}
|
||||
private record UserData(UUID uuid, String username, String firstname, String lastname, Long banned_until, Long outlawed_until) {}
|
||||
|
||||
private final URI apiEndpoint = URI.create(Objects.requireNonNull(localConfig().getString("api")));
|
||||
|
||||
@ -30,23 +36,42 @@ public class Whitelist extends Appliance {
|
||||
super("whitelist");
|
||||
}
|
||||
|
||||
public void login(PlayerLoginEvent login) throws DisconnectInfo.Throwable {
|
||||
public void integrityCheck(Player player) throws DisconnectInfo.Throwable {
|
||||
try {
|
||||
UserData data = this.fetchUserData(login.getPlayer().getUniqueId());
|
||||
Main.instance().getLogger().info(String.format("Running integrityCheck for %s", player.getName()));
|
||||
UserData user = this.fetchUserData(player.getUniqueId());
|
||||
|
||||
String purePlayerName;
|
||||
if(Floodgate.isBedrock(login.getPlayer())) {
|
||||
purePlayerName = Floodgate.getBedrockPlayer(login.getPlayer()).getUsername();
|
||||
} else {
|
||||
purePlayerName = login.getPlayer().getName();
|
||||
if(timestampRelevant(user.banned_until)) {
|
||||
Instant bannedDate = new Date(user.banned_until * 1000L)
|
||||
.toInstant()
|
||||
.plus(1, ChronoUnit.HOURS);
|
||||
|
||||
DateTimeFormatter dateFormat = DateTimeFormatter.ofPattern("dd.MM.yyyy").withZone(ZoneOffset.UTC);
|
||||
DateTimeFormatter timeFormat = DateTimeFormatter.ofPattern("HH:mm").withZone(ZoneOffset.UTC);
|
||||
|
||||
throw new DisconnectInfo.Throwable(
|
||||
"Du wurdest vom Server gebannt.",
|
||||
String.format("Dein Bann läuft am %s um %s ab!", dateFormat.format(bannedDate), timeFormat.format(bannedDate)),
|
||||
"Wende dich an einen Admin für weitere Informationen.",
|
||||
player.getUniqueId()
|
||||
);
|
||||
}
|
||||
|
||||
if(!data.username.equalsIgnoreCase(purePlayerName))
|
||||
Main.instance().getAppliance(Outlawed.class).updateForcedStatus(player, timestampRelevant(user.outlawed_until));
|
||||
|
||||
String purePlayerName;
|
||||
if(Floodgate.isBedrock(player)) {
|
||||
purePlayerName = Floodgate.getBedrockPlayer(player).getUsername();
|
||||
} else {
|
||||
purePlayerName = player.getName();
|
||||
}
|
||||
|
||||
if(!user.username.trim().equalsIgnoreCase(purePlayerName))
|
||||
throw new DisconnectInfo.Throwable(
|
||||
"Nutzername geändert",
|
||||
String.format("Der Name '%s' stimmt nicht mit '%s' überein.", data.username, login.getPlayer().getName()),
|
||||
String.format("Der Name '%s' stimmt nicht mit '%s' überein.", user.username, player.getName()),
|
||||
"Bitte kontaktiere einen Admin, um Deine Anmeldedaten zu aktualisieren!",
|
||||
login.getPlayer().getUniqueId()
|
||||
player.getUniqueId()
|
||||
);
|
||||
|
||||
} catch (DisconnectInfo.Throwable e) {
|
||||
@ -55,13 +80,18 @@ public class Whitelist extends Appliance {
|
||||
Main.instance().getLogger().log(Level.SEVERE, e, e::getMessage);
|
||||
throw new DisconnectInfo.Throwable(
|
||||
"Interner Serverfehler",
|
||||
"Deine Zugangsdaten konnten nicht abgerufen werden.",
|
||||
"Deine Anmeldedaten konnten nicht abgerufen/ überprüft werden.",
|
||||
"Versuche es später erneut oder kontaktiere einen Admin!",
|
||||
login.getPlayer().getUniqueId()
|
||||
player.getUniqueId()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
private boolean timestampRelevant(Long timestamp) {
|
||||
if(timestamp == null) return false;
|
||||
return timestamp > System.currentTimeMillis() / 1000L;
|
||||
}
|
||||
|
||||
private UserData fetchUserData(UUID uuid) throws DisconnectInfo.Throwable {
|
||||
URIBuilder uriBuilder = new URIBuilder(apiEndpoint);
|
||||
uriBuilder.addParameter("uuid", uuid.toString());
|
||||
@ -76,7 +106,7 @@ public class Whitelist extends Appliance {
|
||||
|
||||
HttpResponse<String> httpResponse = client.send(httpRequest, HttpResponse.BodyHandlers.ofString());
|
||||
|
||||
if(httpResponse.statusCode() == 400)
|
||||
if(httpResponse.statusCode() == 404)
|
||||
throw new DisconnectInfo.Throwable(
|
||||
"Nicht angemeldet",
|
||||
"Du bist derzeit nicht als Teilnehmer des CraftAttack-Projektes registriert!",
|
||||
@ -91,6 +121,23 @@ public class Whitelist extends Appliance {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void httpApi(HttpServer.ApiBuilder apiBuilder) {
|
||||
record User(UUID user) {}
|
||||
apiBuilder.post("update", User.class, (user, request) -> {
|
||||
Main.instance().getLogger().info(String.format("API Triggered Profile update for %s", user.user));
|
||||
Player player = Bukkit.getPlayer(user.user);
|
||||
if(player != null) {
|
||||
try {
|
||||
this.integrityCheck(player);
|
||||
} catch (DisconnectInfo.Throwable e) {
|
||||
e.getDisconnectScreen().applyKick(player);
|
||||
}
|
||||
}
|
||||
return HttpServer.nothing;
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
protected @NotNull List<Listener> eventHandlers() {
|
||||
return List.of(
|
||||
|
@ -3,6 +3,7 @@ package eu.mhsl.craftattack.spawn.appliances.worldmuseum;
|
||||
import eu.mhsl.craftattack.spawn.appliance.Appliance;
|
||||
import eu.mhsl.craftattack.spawn.appliance.ApplianceCommand;
|
||||
import eu.mhsl.craftattack.spawn.util.entity.DisplayVillager;
|
||||
import eu.mhsl.craftattack.spawn.util.server.Floodgate;
|
||||
import eu.mhsl.craftattack.spawn.util.server.PluginMessage;
|
||||
import eu.mhsl.craftattack.spawn.util.listener.DismissInventoryOpenFromHolder;
|
||||
import eu.mhsl.craftattack.spawn.util.listener.PlayerInteractAtEntityEventListener;
|
||||
@ -12,6 +13,8 @@ import org.bukkit.Bukkit;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.*;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.geysermc.cumulus.form.SimpleForm;
|
||||
import org.geysermc.cumulus.form.util.FormBuilder;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.List;
|
||||
@ -39,6 +42,19 @@ public class WorldMuseum extends Appliance {
|
||||
}
|
||||
|
||||
public void handleVillagerInteraction(Player player) {
|
||||
if(Floodgate.isBedrock(player)) {
|
||||
Floodgate.runBedrockOnly(player, floodgatePlayer -> {
|
||||
floodgatePlayer.sendForm(
|
||||
SimpleForm.builder()
|
||||
.title("Nicht unterstützt")
|
||||
.content("Bedrock-Spieler werden derzeit für das Weltenmuseum aus Kompatiblitätsgründen nicht zugelassen! Tut uns Leid.")
|
||||
.button("Ok")
|
||||
.build()
|
||||
);
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
Bukkit.getLogger().info("Sending" + player.getName() + " to WorldMuseum");
|
||||
PluginMessage.connect(player, localConfig().getString("connect-server-name"));
|
||||
}
|
||||
|
@ -0,0 +1,32 @@
|
||||
package eu.mhsl.craftattack.spawn.util.entity;
|
||||
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.Statistic;
|
||||
import org.bukkit.entity.EntityType;
|
||||
import org.bukkit.entity.Player;
|
||||
|
||||
public class PlayerUtils {
|
||||
public static void resetStatistics(Player player) {
|
||||
for(Statistic statistic : Statistic.values()) {
|
||||
for(Material material : Material.values()) {
|
||||
try {
|
||||
player.setStatistic(statistic, material, 0);
|
||||
} catch (IllegalArgumentException e) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
for(EntityType entityType : EntityType.values()) {
|
||||
try {
|
||||
player.setStatistic(statistic, entityType, 0);
|
||||
} catch (IllegalArgumentException e) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
try{
|
||||
player.setStatistic(statistic, 0);
|
||||
} catch (IllegalArgumentException ignored){}
|
||||
}
|
||||
}
|
||||
}
|
@ -1,14 +1,16 @@
|
||||
package eu.mhsl.craftattack.spawn.util.text;
|
||||
|
||||
import eu.mhsl.craftattack.spawn.Main;
|
||||
import net.kyori.adventure.text.Component;
|
||||
import net.kyori.adventure.text.format.NamedTextColor;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.entity.Player;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
public record DisconnectInfo(String error, String description, String help, UUID user) {
|
||||
public void applyKick(Player player) {
|
||||
player.kick(this.getComponent());
|
||||
Bukkit.getScheduler().runTask(Main.instance(), () -> player.kick(this.getComponent()));
|
||||
}
|
||||
public Component getComponent() {
|
||||
return Component.text()
|
||||
|
@ -34,3 +34,4 @@ commands:
|
||||
cancelRestart:
|
||||
kick:
|
||||
panicBan:
|
||||
vogelfrei:
|
Loading…
x
Reference in New Issue
Block a user