diff --git a/.gitignore b/.gitignore index b610217..3bb7cb9 100644 --- a/.gitignore +++ b/.gitignore @@ -172,6 +172,8 @@ Desktop.ini ## Misc. ############# +.cursorrules + # Compiled class file *.class diff --git a/src/main/java/net/coreprotect/command/CommandHandler.java b/src/main/java/net/coreprotect/command/CommandHandler.java index d61837e..d07e60a 100755 --- a/src/main/java/net/coreprotect/command/CommandHandler.java +++ b/src/main/java/net/coreprotect/command/CommandHandler.java @@ -1,40 +1,19 @@ package net.coreprotect.command; -import java.math.BigDecimal; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.HashMap; -import java.util.List; import java.util.Locale; -import java.util.Map; -import java.util.Map.Entry; -import java.util.Set; import java.util.concurrent.ConcurrentHashMap; -import org.bukkit.Bukkit; -import org.bukkit.Location; -import org.bukkit.Material; -import org.bukkit.command.BlockCommandSender; import org.bukkit.command.Command; import org.bukkit.command.CommandExecutor; import org.bukkit.command.CommandSender; -import org.bukkit.entity.EntityType; -import org.bukkit.entity.Player; -import net.coreprotect.bukkit.BukkitAdapter; -import net.coreprotect.config.Config; import net.coreprotect.config.ConfigHandler; import net.coreprotect.extensions.Extensions; import net.coreprotect.language.Phrase; -import net.coreprotect.language.Selector; -import net.coreprotect.model.BlockGroup; import net.coreprotect.thread.NetworkHandler; import net.coreprotect.utility.Chat; import net.coreprotect.utility.Color; -import net.coreprotect.utility.EntityUtils; -import net.coreprotect.utility.MaterialUtils; import net.coreprotect.utility.VersionUtils; -import net.coreprotect.utility.WorldUtils; public class CommandHandler implements CommandExecutor { private static CommandHandler instance; @@ -47,1143 +26,6 @@ public class CommandHandler implements CommandExecutor { return instance; } - protected static String[] parsePage(String[] argumentArray) { - if (argumentArray.length == 2) { - argumentArray[1] = argumentArray[1].replaceFirst("page:", ""); - } - - return argumentArray; - } - - protected static List parseAction(String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - List result = new ArrayList<>(); - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("a:") || argument.equals("action:")) { - next = 1; - } - else if (next == 1 || argument.startsWith("a:") || argument.startsWith("action:")) { - result.clear(); - argument = argument.replaceAll("action:", ""); - argument = argument.replaceAll("a:", ""); - if (argument.startsWith("#")) { - argument = argument.replaceFirst("#", ""); - } - if (argument.equals("broke") || argument.equals("break") || argument.equals("remove") || argument.equals("destroy") || argument.equals("block-break") || argument.equals("block-remove") || argument.equals("-block") || argument.equals("-blocks") || argument.equals("block-")) { - result.add(0); - } - else if (argument.equals("placed") || argument.equals("place") || argument.equals("block-place") || argument.equals("+block") || argument.equals("+blocks") || argument.equals("block+")) { - result.add(1); - } - else if (argument.equals("block") || argument.equals("blocks") || argument.equals("block-change") || argument.equals("change") || argument.equals("changes")) { - result.add(0); - result.add(1); - } - else if (argument.equals("click") || argument.equals("clicks") || argument.equals("interact") || argument.equals("interaction") || argument.equals("player-interact") || argument.equals("player-interaction") || argument.equals("player-click")) { - result.add(2); - } - else if (argument.equals("death") || argument.equals("deaths") || argument.equals("entity-death") || argument.equals("entity-deaths") || argument.equals("kill") || argument.equals("kills") || argument.equals("entity-kill") || argument.equals("entity-kills")) { - result.add(3); - } - else if (argument.equals("container") || argument.equals("container-change") || argument.equals("containers") || argument.equals("chest") || argument.equals("transaction") || argument.equals("transactions")) { - result.add(4); - } - else if (argument.equals("-container") || argument.equals("container-") || argument.equals("remove-container")) { - result.add(4); - result.add(0); - } - else if (argument.equals("+container") || argument.equals("container+") || argument.equals("container-add") || argument.equals("add-container")) { - result.add(4); - result.add(1); - } - else if (argument.equals("chat") || argument.equals("chats")) { - result.add(6); - } - else if (argument.equals("command") || argument.equals("commands")) { - result.add(7); - } - else if (argument.equals("logins") || argument.equals("login") || argument.equals("+session") || argument.equals("+sessions") || argument.equals("session+") || argument.equals("+connection") || argument.equals("connection+")) { - result.add(8); - result.add(1); - } - else if (argument.equals("logout") || argument.equals("logouts") || argument.equals("-session") || argument.equals("-sessions") || argument.equals("session-") || argument.equals("-connection") || argument.equals("connection-")) { - result.add(8); - result.add(0); - } - else if (argument.equals("session") || argument.equals("sessions") || argument.equals("connection") || argument.equals("connections")) { - result.add(8); - } - else if (argument.equals("username") || argument.equals("usernames") || argument.equals("user") || argument.equals("users") || argument.equals("name") || argument.equals("names") || argument.equals("uuid") || argument.equals("uuids") || argument.equals("username-change") || argument.equals("username-changes") || argument.equals("name-change") || argument.equals("name-changes")) { - result.add(9); - } - else if (argument.equals("sign") || argument.equals("signs")) { - result.add(10); - } - else if (argument.equals("inv") || argument.equals("inventory") || argument.equals("inventories")) { - result.add(4); // container - result.add(11); // item - } - else if (argument.equals("-inv") || argument.equals("inv-") || argument.equals("-inventory") || argument.equals("inventory-") || argument.equals("-inventories")) { - result.add(4); - result.add(11); - result.add(1); - } - else if (argument.equals("+inv") || argument.equals("inv+") || argument.equals("+inventory") || argument.equals("inventory+") || argument.equals("+inventories")) { - result.add(4); - result.add(11); - result.add(0); - } - else if (argument.equals("item") || argument.equals("items")) { - result.add(11); - } - else if (argument.equals("-item") || argument.equals("item-") || argument.equals("-items") || argument.equals("items-") || argument.equals("drop") || argument.equals("drops") || argument.equals("deposit") || argument.equals("deposits") || argument.equals("deposited")) { - result.add(11); - result.add(0); - } - else if (argument.equals("+item") || argument.equals("item+") || argument.equals("+items") || argument.equals("items+") || argument.equals("pickup") || argument.equals("pickups") || argument.equals("withdraw") || argument.equals("withdraws") || argument.equals("withdrew")) { - result.add(11); - result.add(1); - } - else { - result.add(-1); - } - next = 0; - } - else { - next = 0; - } - } - count++; - } - return result; - } - - protected static Location parseCoordinates(Location location, String[] inputArguments, int worldId) { - String[] argumentArray = inputArguments.clone(); - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("position:") || argument.equals("location:") || argument.equals("c:") || argument.equals("coord:") || argument.equals("coords:") || argument.equals("cord:") || argument.equals("cords:") || argument.equals("coordinate:") || argument.equals("coordinates:") || argument.equals("cordinate:") || argument.equals("cordinates:")) { - next = 2; - } - else if (next == 2 || argument.startsWith("c:") || argument.startsWith("coord:") || argument.startsWith("coords:") || argument.startsWith("cord:") || argument.startsWith("cords:") || argument.startsWith("coordinate:") || argument.startsWith("coordinates:") || argument.startsWith("cordinate:") || argument.startsWith("cordinates:")) { - argument = argument.replaceAll("coordinates:", ""); - argument = argument.replaceAll("coordinate:", ""); - argument = argument.replaceAll("cordinates:", ""); - argument = argument.replaceAll("cordinate:", ""); - argument = argument.replaceAll("coords:", ""); - argument = argument.replaceAll("coord:", ""); - argument = argument.replaceAll("cords:", ""); - argument = argument.replaceAll("cord:", ""); - argument = argument.replaceAll("c:", ""); - if (argument.contains(",")) { - String[] i2 = argument.split(","); - double x = 0.00; - double y = 0.00; - double z = 0.00; - int cCount = 0; - for (String coord : i2) { - coord = coord.replaceAll("[^0-9.\\-]", ""); - if (coord.length() > 0 && !coord.equals(".") && !coord.equals("-") && coord.indexOf('.') == coord.lastIndexOf('.')) { - double parsedCoord = Double.parseDouble(coord); - if (cCount == 0) { - x = parsedCoord; - } - else if (cCount == 1) { - z = parsedCoord; - } - else if (cCount == 2) { - y = z; - z = parsedCoord; - } - cCount++; - } - } - if (cCount > 1) { - if (location == null && worldId > 0) { - location = new Location(Bukkit.getWorld(WorldUtils.getWorldName(worldId)), 0, 0, 0); - } - if (location != null) { - int worldMaxHeight = location.getWorld().getMaxHeight() - 1; - int worldMinHeight = BukkitAdapter.ADAPTER.getMinHeight(location.getWorld()); - - if (y < worldMinHeight) { - y = Double.valueOf(worldMinHeight); - } - if (y > worldMaxHeight) { - y = Double.valueOf(worldMaxHeight); - } - - location.setX(x); - location.setY(y); - location.setZ(z); - } - } - } - next = 0; - } - else { - next = 0; - } - } - count++; - } - return location; - } - - protected static boolean parseCount(String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - boolean result = false; - int count = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - if (argument.equals("#count") || argument.equals("#sum")) { - result = true; - } - } - count++; - } - return result; - } - - protected static Map parseExcluded(CommandSender player, String[] inputArguments, List argAction) { - String[] argumentArray = inputArguments.clone(); - Map excluded = new HashMap<>(); - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("e:") || argument.equals("exclude:")) { - next = 5; - } - else if (next == 5 || argument.startsWith("e:") || argument.startsWith("exclude:")) { - argument = argument.replaceAll("exclude:", ""); - argument = argument.replaceAll("e:", ""); - if (argument.contains(",")) { - String[] i2 = argument.split(","); - for (String i3 : i2) { - if (!checkTags(i3, excluded)) { - Material i3_material = MaterialUtils.getType(i3); - if (i3_material != null && (i3_material.isBlock() || argAction.contains(4))) { - excluded.put(i3_material, false); - } - else { - EntityType i3_entity = EntityUtils.getEntityType(i3); - if (i3_entity != null) { - excluded.put(i3_entity, false); - } - else if (i3_material != null) { - excluded.put(i3_material, false); - } - } - } - } - if (argument.endsWith(",")) { - next = 5; - } - else { - next = 0; - } - } - else { - if (!checkTags(argument, excluded)) { - Material iMaterial = MaterialUtils.getType(argument); - if (iMaterial != null && (iMaterial.isBlock() || argAction.contains(4))) { - excluded.put(iMaterial, false); - } - else { - EntityType iEntity = EntityUtils.getEntityType(argument); - if (iEntity != null) { - excluded.put(iEntity, false); - } - else if (iMaterial != null) { - excluded.put(iMaterial, false); - } - } - } - next = 0; - } - } - else { - next = 0; - } - } - count++; - } - return excluded; - } - - protected static List parseExcludedUsers(CommandSender player, String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - List excluded = new ArrayList<>(); - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("e:") || argument.equals("exclude:")) { - next = 5; - } - else if (next == 5 || argument.startsWith("e:") || argument.startsWith("exclude:")) { - argument = argument.replaceAll("exclude:", ""); - argument = argument.replaceAll("e:", ""); - if (argument.contains(",")) { - String[] i2 = argument.split(","); - for (String i3 : i2) { - boolean isBlock = false; - if (checkTags(i3)) { - isBlock = true; - } - else { - Material i3_material = MaterialUtils.getType(i3); - if (i3_material != null) { - isBlock = true; - } - else { - EntityType i3Entity = EntityUtils.getEntityType(i3); - if (i3Entity != null) { - isBlock = true; - } - } - } - if (!isBlock) { - excluded.add(i3); - } - } - if (argument.endsWith(",")) { - next = 5; - } - else { - next = 0; - } - } - else { - boolean isBlock = false; - if (checkTags(argument)) { - isBlock = true; - } - else { - Material iMaterial = MaterialUtils.getType(argument); - if (iMaterial != null) { - isBlock = true; - } - else { - EntityType entityType = EntityUtils.getEntityType(argument); - if (entityType != null) { - isBlock = true; - } - } - } - if (!isBlock) { - excluded.add(argument); - } - next = 0; - } - } - else { - next = 0; - } - } - count++; - } - return excluded; - } - - protected static boolean parseForceGlobal(String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - boolean result = false; - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("r:") || argument.equals("radius:")) { - next = 2; - } - else if (next == 2 || argument.startsWith("r:") || argument.startsWith("radius:")) { - argument = argument.replaceAll("radius:", ""); - argument = argument.replaceAll("r:", ""); - if (argument.equals("#global") || argument.equals("global") || argument.equals("off") || argument.equals("-1") || argument.equals("none") || argument.equals("false")) { - result = true; - } - else if (argument.startsWith("#")) { - int worldId = WorldUtils.matchWorld(argument); - if (worldId > 0) { - result = true; - } - } - next = 0; - } - else { - next = 0; - } - } - count++; - } - return result; - } - - protected static Location parseLocation(CommandSender user, String[] argumentArray) { - Location location = null; - if (user instanceof Player) { - location = ((Player) user).getLocation(); - } - else if (user instanceof BlockCommandSender) { - location = ((BlockCommandSender) user).getBlock().getLocation(); - } - - return parseCoordinates(location, argumentArray, parseWorld(argumentArray, true, true)); - } - - protected static int parseNoisy(String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - int noisy = 0; - int count = 0; - if (Config.getGlobal().VERBOSE) { - noisy = 1; - } - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("n") || argument.equals("noisy") || argument.equals("v") || argument.equals("verbose") || argument.equals("#v") || argument.equals("#verbose")) { - noisy = 1; - } - else if (argument.equals("#silent")) { - noisy = 0; - } - } - count++; - } - return noisy; - } - - protected static int parsePreview(String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - int result = 0; - int count = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - if (argument.equals("#preview")) { - result = 1; - } - else if (argument.equals("#preview_cancel")) { - result = 2; - } - } - count++; - } - return result; - } - - protected static Integer[] parseRadius(String[] inputArguments, CommandSender user, Location location) { - String[] argumentArray = inputArguments.clone(); - Integer[] radius = null; - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("r:") || argument.equals("radius:")) { - next = 2; - } - else if (next == 2 || argument.startsWith("r:") || argument.startsWith("radius:")) { - argument = argument.replaceAll("radius:", ""); - argument = argument.replaceAll("r:", ""); - if (argument.equals("#worldedit") || argument.equals("#we")) { - if (user.getServer().getPluginManager().getPlugin("WorldEdit") != null) { - Integer[] worldEditResult = WorldEditHandler.runWorldEditCommand(user); - if (worldEditResult != null) { - radius = worldEditResult; - } - } - } - else if ((argument.startsWith("#") && argument.length() > 1) || argument.equals("global") || argument.equals("off") || argument.equals("-1") || argument.equals("none") || argument.equals("false")) { - // radius = -2; - } - else { - int rcount = 0; - int r_x = 0; - int r_y = -1; - int r_z = 0; - String[] r_dat = new String[] { argument }; - boolean validRadius = false; - if (argument.contains("x")) { - r_dat = argument.split("x"); - } - for (String value : r_dat) { - String i4 = value.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.length() == value.length() && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - double a1 = Double.parseDouble(i4); - if (rcount == 0) { // x - r_x = (int) a1; - r_z = (int) a1; - } - else if (rcount == 1) { // y - r_y = (int) a1; - } - else if (rcount == 2) { // z - r_z = (int) a1; - } - validRadius = true; - } - rcount++; - } - if (location != null) { - Integer xmin = location.getBlockX() - r_x; - Integer xmax = location.getBlockX() + r_x; - Integer ymin = null; - Integer ymax = null; - Integer zmin = location.getBlockZ() - r_z; - Integer zmax = location.getBlockZ() + r_z; - if (r_y > -1) { - ymin = location.getBlockY() - r_y; - ymax = location.getBlockY() + r_y; - } - int max = r_x; - if (r_y > max) { - max = r_y; - } - if (r_z > max) { - max = r_z; - } - if (validRadius) { - radius = new Integer[] { max, xmin, xmax, ymin, ymax, zmin, zmax, 0 }; - } - else { - radius = new Integer[] { -1 }; - } - } - } - next = 0; - } - else { - next = 0; - } - } - count++; - } - return radius; - } - - protected static List parseRestricted(CommandSender player, String[] inputArguments, List argAction) { - String[] argumentArray = inputArguments.clone(); - List restricted = new ArrayList<>(); - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("i:") || argument.equals("include:") || argument.equals("item:") || argument.equals("items:") || argument.equals("b:") || argument.equals("block:") || argument.equals("blocks:")) { - next = 4; - } - else if (next == 4 || argument.startsWith("i:") || argument.startsWith("include:") || argument.startsWith("item:") || argument.startsWith("items:") || argument.startsWith("b:") || argument.startsWith("block:") || argument.startsWith("blocks:")) { - argument = argument.replaceAll("include:", ""); - argument = argument.replaceAll("i:", ""); - argument = argument.replaceAll("items:", ""); - argument = argument.replaceAll("item:", ""); - argument = argument.replaceAll("blocks:", ""); - argument = argument.replaceAll("block:", ""); - argument = argument.replaceAll("b:", ""); - if (argument.contains(",")) { - String[] i2 = argument.split(","); - for (String i3 : i2) { - if (!checkTags(argument, restricted)) { - Material i3_material = MaterialUtils.getType(i3); - if (i3_material != null && (i3_material.isBlock() || argAction.contains(4))) { - restricted.add(i3_material); - } - else { - EntityType i3_entity = EntityUtils.getEntityType(i3); - if (i3_entity != null) { - restricted.add(i3_entity); - } - else if (i3_material != null) { - restricted.add(i3_material); - } - else { - Chat.sendMessage(player, Color.DARK_AQUA + "CoreProtect " + Color.WHITE + "- " + Phrase.build(Phrase.INVALID_INCLUDE, i3)); - // Functions.sendMessage(player, Color.DARK_AQUA + "CoreProtect " + Color.WHITE + "- " + Phrase.build(Phrase.MISSING_PARAMETERS, "/co help include")); - return null; - } - } - } - } - if (argument.endsWith(",")) { - next = 4; - } - else { - next = 0; - } - } - else { - if (!checkTags(argument, restricted)) { - Material material = MaterialUtils.getType(argument); - if (material != null && (material.isBlock() || argAction.contains(4))) { - restricted.add(material); - } - else { - EntityType entityType = EntityUtils.getEntityType(argument); - if (entityType != null) { - restricted.add(entityType); - } - else if (material != null) { - restricted.add(material); - } - else { - Chat.sendMessage(player, Color.DARK_AQUA + "CoreProtect " + Color.WHITE + "- " + Phrase.build(Phrase.INVALID_INCLUDE, argument)); - // Functions.sendMessage(player, Color.DARK_AQUA + "CoreProtect " + Color.WHITE + "- " + Phrase.build(Phrase.MISSING_PARAMETERS, "/co help include")); - return null; - } - } - } - next = 0; - } - } - else { - next = 0; - } - } - count++; - } - return restricted; - } - - protected static long[] parseTime(String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - long timeStart = 0; - long timeEnd = 0; - int count = 0; - int next = 0; - boolean range = false; - double w = 0; - double d = 0; - double h = 0; - double m = 0; - double s = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("t:") || argument.equals("time:")) { - next = 1; - } - else if (next == 1 || argument.startsWith("t:") || argument.startsWith("time:")) { - // time arguments - argument = argument.replaceAll("time:", ""); - argument = argument.replaceAll("t:", ""); - argument = argument.replaceAll("y", "y:"); - argument = argument.replaceAll("m", "m:"); - argument = argument.replaceAll("w", "w:"); - argument = argument.replaceAll("d", "d:"); - argument = argument.replaceAll("h", "h:"); - argument = argument.replaceAll("s", "s:"); - range = argument.contains("-"); - - int argCount = 0; - String[] i2 = argument.split(":"); - for (String i3 : i2) { - if (range && argCount > 0 && timeStart == 0 && i3.startsWith("-")) { - timeStart = (long) (((w * 7 * 24 * 60 * 60) + (d * 24 * 60 * 60) + (h * 60 * 60) + (m * 60) + s)); - w = 0; - d = 0; - h = 0; - m = 0; - s = 0; - } - - if (i3.endsWith("w") && w == 0) { - String i4 = i3.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - w = Double.parseDouble(i4); - } - } - else if (i3.endsWith("d") && d == 0) { - String i4 = i3.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - d = Double.parseDouble(i4); - } - } - else if (i3.endsWith("h") && h == 0) { - String i4 = i3.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - h = Double.parseDouble(i4); - } - } - else if (i3.endsWith("m") && m == 0) { - String i4 = i3.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - m = Double.parseDouble(i4); - } - } - else if (i3.endsWith("s") && s == 0) { - String i4 = i3.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - s = Double.parseDouble(i4); - } - } - - argCount++; - } - if (timeStart > 0) { - timeEnd = (long) (((w * 7 * 24 * 60 * 60) + (d * 24 * 60 * 60) + (h * 60 * 60) + (m * 60) + s)); - } - else { - timeStart = (long) (((w * 7 * 24 * 60 * 60) + (d * 24 * 60 * 60) + (h * 60 * 60) + (m * 60) + s)); - } - next = 0; - } - else { - next = 0; - } - } - count++; - } - - if (timeEnd >= timeStart) { - return new long[] { timeEnd, timeStart }; - } - else { - return new long[] { timeStart, timeEnd }; - } - } - - private static String timeString(BigDecimal input) { - return input.stripTrailingZeros().toPlainString(); - } - - protected static String parseTimeString(String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - String time = ""; - int count = 0; - int next = 0; - boolean range = false; - BigDecimal w = new BigDecimal(0); - BigDecimal d = new BigDecimal(0); - BigDecimal h = new BigDecimal(0); - BigDecimal m = new BigDecimal(0); - BigDecimal s = new BigDecimal(0); - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("t:") || argument.equals("time:")) { - next = 1; - } - else if (next == 1 || argument.startsWith("t:") || argument.startsWith("time:")) { - // time arguments - argument = argument.replaceAll("time:", ""); - argument = argument.replaceAll("t:", ""); - argument = argument.replaceAll("y", "y:"); - argument = argument.replaceAll("m", "m:"); - argument = argument.replaceAll("w", "w:"); - argument = argument.replaceAll("d", "d:"); - argument = argument.replaceAll("h", "h:"); - argument = argument.replaceAll("s", "s:"); - range = argument.contains("-"); - - int argCount = 0; - String[] i2 = argument.split(":"); - for (String i3 : i2) { - if (range && argCount > 0 && !time.contains("-") && i3.startsWith("-")) { - w = new BigDecimal(0); - d = new BigDecimal(0); - h = new BigDecimal(0); - m = new BigDecimal(0); - s = new BigDecimal(0); - time = time + " -"; - } - - if (i3.endsWith("w") && w.intValue() == 0) { - String i4 = i3.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - w = new BigDecimal(i4); - if (range) { - time = time + " " + timeString(w) + "w"; - } - else { - time = time + " " + Phrase.build(Phrase.TIME_WEEKS, timeString(w), (w.doubleValue() == 1 ? Selector.FIRST : Selector.SECOND)); - } - } - } - else if (i3.endsWith("d") && d.intValue() == 0) { - String i4 = i3.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - d = new BigDecimal(i4); - if (range) { - time = time + " " + timeString(d) + "d"; - } - else { - time = time + " " + Phrase.build(Phrase.TIME_DAYS, timeString(d), (d.doubleValue() == 1 ? Selector.FIRST : Selector.SECOND)); - } - } - } - else if (i3.endsWith("h") && h.intValue() == 0) { - String i4 = i3.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - h = new BigDecimal(i4); - if (range) { - time = time + " " + timeString(h) + "h"; - } - else { - time = time + " " + Phrase.build(Phrase.TIME_HOURS, timeString(h), (h.doubleValue() == 1 ? Selector.FIRST : Selector.SECOND)); - } - } - } - else if (i3.endsWith("m") && m.intValue() == 0) { - String i4 = i3.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - m = new BigDecimal(i4); - if (range) { - time = time + " " + timeString(m) + "m"; - } - else { - time = time + " " + Phrase.build(Phrase.TIME_MINUTES, timeString(m), (m.doubleValue() == 1 ? Selector.FIRST : Selector.SECOND)); - } - } - } - else if (i3.endsWith("s") && s.intValue() == 0) { - String i4 = i3.replaceAll("[^0-9.]", ""); - if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { - s = new BigDecimal(i4); - if (range) { - time = time + " " + timeString(s) + "s"; - } - else { - time = time + " " + Phrase.build(Phrase.TIME_SECONDS, timeString(s), (s.doubleValue() == 1 ? Selector.FIRST : Selector.SECOND)); - } - } - } - - argCount++; - } - next = 0; - } - else { - next = 0; - } - } - count++; - } - - if (time.startsWith(" ")) { - time = time.substring(1); - } - - return time; - } - - protected static int parseRows(String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - int rows = 0; - int count = 0; - int next = 0; - - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("rows:")) { - next = 1; - } - else if (next == 1 || argument.startsWith("rows:")) { - argument = argument.replaceAll("rows:", "").trim(); - if (!argument.startsWith("-")) { - String i2 = argument.replaceAll("[^0-9]", ""); - if (i2.length() > 0 && i2.length() < 10) { - rows = Integer.parseInt(i2); - } - } - - next = 0; - } - else { - next = 0; - } - } - count++; - } - - return rows; - } - - private static void parseUser(List users, String string) { - string = string.trim(); - if (string.contains(",")) { - String[] data = string.split(","); - for (String user : data) { - validUserCheck(users, user); - } - } - else { - validUserCheck(users, string); - } - } - - protected static List parseUsers(String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - List users = new ArrayList<>(); - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (next == 2) { - if (argument.endsWith(",")) { - next = 2; - } - else { - next = 0; - } - } - else if (argument.equals("p:") || argument.equals("user:") || argument.equals("users:") || argument.equals("u:")) { - next = 1; - } - else if (next == 1 || argument.startsWith("p:") || argument.startsWith("user:") || argument.startsWith("users:") || argument.startsWith("u:")) { - argument = argument.replaceAll("user:", ""); - argument = argument.replaceAll("users:", ""); - argument = argument.replaceAll("p:", ""); - argument = argument.replaceAll("u:", ""); - if (argument.contains(",")) { - String[] i2 = argument.split(","); - for (String i3 : i2) { - parseUser(users, i3); - } - if (argument.endsWith(",")) { - next = 1; - } - else { - next = 0; - } - } - else { - parseUser(users, argument); - next = 0; - } - } - else if (argument.endsWith(",") || argument.endsWith(":")) { - next = 2; - } - else if (argument.contains(":")) { - next = 0; - } - else { - parseUser(users, argument); - next = 0; - } - } - count++; - } - return users; - } - - protected static int parseWorld(String[] inputArguments, boolean processWorldEdit, boolean requireLoaded) { - String[] argumentArray = inputArguments.clone(); - int world_id = 0; - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim(); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - String inputProcessed = argument.toLowerCase(Locale.ROOT); - if (inputProcessed.equals("r:") || inputProcessed.equals("radius:")) { - next = 2; - } - else if (next == 2 || inputProcessed.startsWith("r:") || inputProcessed.startsWith("radius:")) { - argument = argument.replaceAll("radius:", "").replaceAll("r:", ""); - inputProcessed = argument.toLowerCase(Locale.ROOT); - if ((processWorldEdit && (inputProcessed.equals("#worldedit") || inputProcessed.equals("#we"))) || inputProcessed.equals("#global") || inputProcessed.equals("global") || inputProcessed.equals("off") || inputProcessed.equals("-1") || inputProcessed.equals("none") || inputProcessed.equals("false")) { - world_id = 0; - } - else if (inputProcessed.startsWith("#")) { - world_id = WorldUtils.matchWorld(inputProcessed); - if (world_id == -1 && !requireLoaded) { - world_id = ConfigHandler.worlds.getOrDefault(argument.replaceFirst("#", ""), -1); - } - } - next = 0; - } - else { - next = 0; - } - } - count++; - } - return world_id; - } - - protected static boolean parseWorldEdit(String[] inputArguments) { - String[] argumentArray = inputArguments.clone(); - boolean result = false; - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("r:") || argument.equals("radius:")) { - next = 2; - } - else if (next == 2 || argument.startsWith("r:") || argument.startsWith("radius:")) { - argument = argument.replaceAll("radius:", ""); - argument = argument.replaceAll("r:", ""); - if (argument.equals("#worldedit") || argument.equals("#we")) { - result = true; - } - next = 0; - } - else { - next = 0; - } - } - count++; - } - return result; - } - - protected static String parseWorldName(String[] inputArguments, boolean processWorldEdit) { - String[] argumentArray = inputArguments.clone(); - String worldName = ""; - int count = 0; - int next = 0; - for (String argument : argumentArray) { - if (count > 0) { - argument = argument.trim().toLowerCase(Locale.ROOT); - argument = argument.replaceAll("\\\\", ""); - argument = argument.replaceAll("'", ""); - - if (argument.equals("r:") || argument.equals("radius:")) { - next = 2; - } - else if (next == 2 || argument.startsWith("r:") || argument.startsWith("radius:")) { - argument = argument.replaceAll("radius:", ""); - argument = argument.replaceAll("r:", ""); - if ((processWorldEdit && (argument.equals("#worldedit") || argument.equals("#we"))) || argument.equals("#global") || argument.equals("global") || argument.equals("off") || argument.equals("-1") || argument.equals("none") || argument.equals("false")) { - worldName = ""; - } - else if (argument.startsWith("#")) { - worldName = argument.replaceFirst("#", ""); - } - next = 0; - } - else { - next = 0; - } - } - count++; - } - return worldName; - } - - protected static Map> getTags() { - Map> tagMap = new HashMap<>(); - tagMap.put("#button", BlockGroup.BUTTONS); - tagMap.put("#container", BlockGroup.CONTAINERS); - tagMap.put("#door", BlockGroup.DOORS); - tagMap.put("#natural", BlockGroup.NATURAL_BLOCKS); - tagMap.put("#pressure_plate", BlockGroup.PRESSURE_PLATES); - tagMap.put("#shulker_box", BlockGroup.SHULKER_BOXES); - return tagMap; - } - - protected static boolean checkTags(String argument) { - return getTags().containsKey(argument); - } - - protected static boolean checkTags(String argument, Map list) { - for (Entry> entry : getTags().entrySet()) { - String tag = entry.getKey(); - Set materials = entry.getValue(); - - if (argument.equals(tag)) { - for (Material block : materials) { - list.put(block, false); - } - - return true; - } - } - - return false; - } - - protected static boolean checkTags(String argument, List list) { - for (Entry> entry : getTags().entrySet()) { - String tag = entry.getKey(); - Set materials = entry.getValue(); - - if (argument.equals(tag)) { - list.addAll(materials); - return true; - } - } - - return false; - } - - private static void validUserCheck(List users, String user) { - List badUsers = Arrays.asList("n", "noisy", "v", "verbose", "#v", "#verbose", "#silent", "#preview", "#preview_cancel", "#count", "#sum"); - String check = user.replaceAll("[\\s'\"]", ""); - if (check.equals(user) && check.length() > 0) { - if (user.equalsIgnoreCase("#global")) { - user = "#global"; - } - if (!badUsers.contains(user.toLowerCase(Locale.ROOT))) { - users.add(user); - } - } - } - @Override public boolean onCommand(CommandSender user, Command command, String commandLabel, String[] argumentArray) { String commandName = command.getName().toLowerCase(Locale.ROOT); diff --git a/src/main/java/net/coreprotect/command/CommandParser.java b/src/main/java/net/coreprotect/command/CommandParser.java new file mode 100644 index 0000000..56e855d --- /dev/null +++ b/src/main/java/net/coreprotect/command/CommandParser.java @@ -0,0 +1,329 @@ +package net.coreprotect.command; + +import java.math.BigDecimal; +import java.util.List; +import java.util.Map; +import java.util.Set; + +import org.bukkit.Location; +import org.bukkit.Material; +import org.bukkit.command.CommandSender; + +import net.coreprotect.command.parser.ActionParser; +import net.coreprotect.command.parser.LocationParser; +import net.coreprotect.command.parser.MaterialParser; +import net.coreprotect.command.parser.TimeParser; +import net.coreprotect.command.parser.UserParser; +import net.coreprotect.command.parser.WorldParser; + +/** + * Main parser class for CoreProtect commands. + * Delegates to specialized parser classes for specific functionality. + */ +public class CommandParser { + + /** + * Parse page number from command arguments + * + * @param argumentArray + * The command arguments + * @return The modified argument array + */ + protected static String[] parsePage(String[] argumentArray) { + return ActionParser.parsePage(argumentArray); + } + + /** + * Parse action type from command arguments + * + * @param inputArguments + * The command arguments + * @return A list of action type integers + */ + protected static List parseAction(String[] inputArguments) { + return ActionParser.parseAction(inputArguments); + } + + /** + * Parse coordinates from command arguments + * + * @param location + * The base location + * @param inputArguments + * The command arguments + * @param worldId + * The world ID + * @return The parsed location + */ + protected static Location parseCoordinates(Location location, String[] inputArguments, int worldId) { + return LocationParser.parseCoordinates(location, inputArguments, worldId); + } + + /** + * Parse count flag from command arguments + * + * @param inputArguments + * The command arguments + * @return true if the count flag is present + */ + protected static boolean parseCount(String[] inputArguments) { + return ActionParser.parseCount(inputArguments); + } + + /** + * Parse excluded materials and entities from command arguments + * + * @param player + * The command sender + * @param inputArguments + * The command arguments + * @param argAction + * The list of actions to include + * @return A map of excluded materials and entities + */ + protected static Map parseExcluded(CommandSender player, String[] inputArguments, List argAction) { + return MaterialParser.parseExcluded(player, inputArguments, argAction); + } + + /** + * Parse excluded users from command arguments + * + * @param player + * The command sender + * @param inputArguments + * The command arguments + * @return A list of excluded users + */ + protected static List parseExcludedUsers(CommandSender player, String[] inputArguments) { + return UserParser.parseExcludedUsers(player, inputArguments); + } + + /** + * Parse force global flag from command arguments + * + * @param inputArguments + * The command arguments + * @return true if global search should be forced + */ + protected static boolean parseForceGlobal(String[] inputArguments) { + return WorldParser.parseForceGlobal(inputArguments); + } + + /** + * Parse location from command sender and command arguments + * + * @param user + * The command sender + * @param argumentArray + * The command arguments + * @return The parsed location + */ + protected static Location parseLocation(CommandSender user, String[] argumentArray) { + return LocationParser.parseLocation(user, argumentArray); + } + + /** + * Parse noisy/verbose flag from command arguments + * + * @param inputArguments + * The command arguments + * @return 1 if noisy/verbose mode is enabled, 0 otherwise + */ + protected static int parseNoisy(String[] inputArguments) { + return ActionParser.parseNoisy(inputArguments); + } + + /** + * Parse preview flag from command arguments + * + * @param inputArguments + * The command arguments + * @return 1 for preview, 2 for preview cancel, 0 otherwise + */ + protected static int parsePreview(String[] inputArguments) { + return ActionParser.parsePreview(inputArguments); + } + + /** + * Parse radius from command arguments + * + * @param inputArguments + * The command arguments + * @param user + * The command sender + * @param location + * The base location + * @return The parsed radius + */ + protected static Integer[] parseRadius(String[] inputArguments, CommandSender user, Location location) { + Integer[] result = LocationParser.parseRadius(inputArguments, user, location); + + // Handle WorldEdit case which LocationParser returned as null + if (result == null && WorldParser.parseWorldEdit(inputArguments)) { + if (user.getServer().getPluginManager().getPlugin("WorldEdit") != null) { + Integer[] worldEditResult = WorldEditHandler.runWorldEditCommand(user); + if (worldEditResult != null) { + result = worldEditResult; + } + } + } + + return result; + } + + /** + * Parse restricted materials and entities from command arguments + * + * @param player + * The command sender + * @param inputArguments + * The command arguments + * @param argAction + * The list of actions to include + * @return A list of restricted materials and entities + */ + protected static List parseRestricted(CommandSender player, String[] inputArguments, List argAction) { + return MaterialParser.parseRestricted(player, inputArguments, argAction); + } + + /** + * Parse time from command arguments + * + * @param inputArguments + * The command arguments + * @return An array of two longs - [time1, time2] + */ + protected static long[] parseTime(String[] inputArguments) { + return TimeParser.parseTime(inputArguments); + } + + /** + * Parse time string from command arguments for display + * + * @param inputArguments + * The command arguments + * @return A formatted time string + */ + protected static String parseTimeString(String[] inputArguments) { + return TimeParser.parseTimeString(inputArguments); + } + + /** + * Parse rows from command arguments + * + * @param inputArguments + * The command arguments + * @return The number of rows + */ + protected static int parseRows(String[] inputArguments) { + return TimeParser.parseRows(inputArguments); + } + + /** + * Parse world from command arguments + * + * @param inputArguments + * The command arguments + * @param processWorldEdit + * Whether to process WorldEdit arguments + * @param requireLoaded + * Whether the world must be loaded + * @return The world ID + */ + protected static int parseWorld(String[] inputArguments, boolean processWorldEdit, boolean requireLoaded) { + return WorldParser.parseWorld(inputArguments, processWorldEdit, requireLoaded); + } + + /** + * Parse whether to use WorldEdit for radius + * + * @param inputArguments + * The command arguments + * @return true if WorldEdit should be used + */ + protected static boolean parseWorldEdit(String[] inputArguments) { + return WorldParser.parseWorldEdit(inputArguments); + } + + /** + * Parse world name from command arguments + * + * @param inputArguments + * The command arguments + * @param processWorldEdit + * Whether to process WorldEdit arguments + * @return The world name + */ + protected static String parseWorldName(String[] inputArguments, boolean processWorldEdit) { + return WorldParser.parseWorldName(inputArguments, processWorldEdit); + } + + /** + * Get a map of block tags and their associated materials + * + * @return A map of block tags and their associated materials + */ + protected static Map> getTags() { + return MaterialParser.getTags(); + } + + /** + * Check if an argument matches a block tag + * + * @param argument + * The argument to check + * @return true if the argument matches a block tag + */ + protected static boolean checkTags(String argument) { + return MaterialParser.checkTags(argument); + } + + /** + * Check if an argument matches a block tag and add the associated materials to the list + * + * @param argument + * The argument to check + * @param list + * The list to add the associated materials to + * @return true if the argument matches a block tag + */ + protected static boolean checkTags(String argument, Map list) { + return MaterialParser.checkTags(argument, list); + } + + /** + * Check if an argument matches a block tag and add the associated materials to the list + * + * @param argument + * The argument to check + * @param list + * The list to add the associated materials to + * @return true if the argument matches a block tag + */ + protected static boolean checkTags(String argument, List list) { + return MaterialParser.checkTags(argument, list); + } + + /** + * Parse users from command arguments + * + * @param inputArguments + * The command arguments + * @return A list of parsed users + */ + protected static List parseUsers(String[] inputArguments) { + return UserParser.parseUsers(inputArguments); + } + + /** + * Helper method for formatting BigDecimal values + * + * @param input + * The BigDecimal value to format + * @return The formatted string + */ + private static String timeString(BigDecimal input) { + return input.stripTrailingZeros().toPlainString(); + } + +} diff --git a/src/main/java/net/coreprotect/command/LookupCommand.java b/src/main/java/net/coreprotect/command/LookupCommand.java index ea1e8f1..4137e29 100755 --- a/src/main/java/net/coreprotect/command/LookupCommand.java +++ b/src/main/java/net/coreprotect/command/LookupCommand.java @@ -45,31 +45,30 @@ import net.coreprotect.utility.EntityUtils; import net.coreprotect.utility.ItemUtils; import net.coreprotect.utility.MaterialUtils; import net.coreprotect.utility.StringUtils; -import net.coreprotect.utility.Util; import net.coreprotect.utility.WorldUtils; public class LookupCommand { protected static void runCommand(CommandSender player, Command command, boolean permission, String[] args) { int resultc = args.length; - args = CommandHandler.parsePage(args); - Location lo = CommandHandler.parseLocation(player, args); + args = CommandParser.parsePage(args); + Location lo = CommandParser.parseLocation(player, args); // List arg_uuids = new ArrayList(); - List argUsers = CommandHandler.parseUsers(args); - Integer[] argRadius = CommandHandler.parseRadius(args, player, lo); - int argNoisy = CommandHandler.parseNoisy(args); - List argAction = CommandHandler.parseAction(args); - List argBlocks = CommandHandler.parseRestricted(player, args, argAction); - Map argExclude = CommandHandler.parseExcluded(player, args, argAction); - List argExcludeUsers = CommandHandler.parseExcludedUsers(player, args); - String ts = CommandHandler.parseTimeString(args); - long[] argTime = CommandHandler.parseTime(args); + List argUsers = CommandParser.parseUsers(args); + Integer[] argRadius = CommandParser.parseRadius(args, player, lo); + int argNoisy = CommandParser.parseNoisy(args); + List argAction = CommandParser.parseAction(args); + List argBlocks = CommandParser.parseRestricted(player, args, argAction); + Map argExclude = CommandParser.parseExcluded(player, args, argAction); + List argExcludeUsers = CommandParser.parseExcludedUsers(player, args); + String ts = CommandParser.parseTimeString(args); + long[] argTime = CommandParser.parseTime(args); long startTime = argTime[0]; long endTime = argTime[1]; - int argWid = CommandHandler.parseWorld(args, true, true); - int parseRows = CommandHandler.parseRows(args); - boolean count = CommandHandler.parseCount(args); - boolean worldedit = CommandHandler.parseWorldEdit(args); - boolean forceglobal = CommandHandler.parseForceGlobal(args); + int argWid = CommandParser.parseWorld(args, true, true); + int parseRows = CommandParser.parseRows(args); + boolean count = CommandParser.parseCount(args); + boolean worldedit = CommandParser.parseWorldEdit(args); + boolean forceglobal = CommandParser.parseForceGlobal(args); boolean pageLookup = false; if (argBlocks == null || argExclude == null || argExcludeUsers == null) { @@ -126,7 +125,7 @@ public class LookupCommand { } if (argWid == -1) { - String worldName = CommandHandler.parseWorldName(args, true); + String worldName = CommandParser.parseWorldName(args, true); Chat.sendMessage(player, new ChatMessage(Phrase.build(Phrase.WORLD_NOT_FOUND, worldName)).build()); return; } diff --git a/src/main/java/net/coreprotect/command/PurgeCommand.java b/src/main/java/net/coreprotect/command/PurgeCommand.java index 6245a8c..58fd8a6 100755 --- a/src/main/java/net/coreprotect/command/PurgeCommand.java +++ b/src/main/java/net/coreprotect/command/PurgeCommand.java @@ -36,14 +36,14 @@ public class PurgeCommand extends Consumer { protected static void runCommand(final CommandSender player, boolean permission, String[] args) { int resultc = args.length; - Location location = CommandHandler.parseLocation(player, args); - final Integer[] argRadius = CommandHandler.parseRadius(args, player, location); - final List argAction = CommandHandler.parseAction(args); - final List argBlocks = CommandHandler.parseRestricted(player, args, argAction); - final Map argExclude = CommandHandler.parseExcluded(player, args, argAction); - final List argExcludeUsers = CommandHandler.parseExcludedUsers(player, args); - final long[] argTime = CommandHandler.parseTime(args); - final int argWid = CommandHandler.parseWorld(args, false, false); + Location location = CommandParser.parseLocation(player, args); + final Integer[] argRadius = CommandParser.parseRadius(args, player, location); + final List argAction = CommandParser.parseAction(args); + final List argBlocks = CommandParser.parseRestricted(player, args, argAction); + final Map argExclude = CommandParser.parseExcluded(player, args, argAction); + final List argExcludeUsers = CommandParser.parseExcludedUsers(player, args); + final long[] argTime = CommandParser.parseTime(args); + final int argWid = CommandParser.parseWorld(args, false, false); final List supportedActions = Arrays.asList(); long startTime = argTime[1] > 0 ? argTime[0] : 0; long endTime = argTime[1] > 0 ? argTime[1] : argTime[0]; @@ -77,7 +77,7 @@ public class PurgeCommand extends Consumer { return; } if (argWid == -1) { - String worldName = CommandHandler.parseWorldName(args, false); + String worldName = CommandParser.parseWorldName(args, false); Chat.sendMessage(player, new ChatMessage(Phrase.build(Phrase.WORLD_NOT_FOUND, worldName)).build()); return; } @@ -202,7 +202,7 @@ public class PurgeCommand extends Consumer { } if (argWid > 0) { - String worldName = CommandHandler.parseWorldName(args, false); + String worldName = CommandParser.parseWorldName(args, false); Chat.sendGlobalMessage(player, Phrase.build(Phrase.PURGE_STARTED, worldName)); } else { diff --git a/src/main/java/net/coreprotect/command/RollbackRestoreCommand.java b/src/main/java/net/coreprotect/command/RollbackRestoreCommand.java index 92416d8..690dfab 100755 --- a/src/main/java/net/coreprotect/command/RollbackRestoreCommand.java +++ b/src/main/java/net/coreprotect/command/RollbackRestoreCommand.java @@ -29,29 +29,28 @@ import net.coreprotect.language.Phrase; import net.coreprotect.language.Selector; import net.coreprotect.utility.Chat; import net.coreprotect.utility.Color; -import net.coreprotect.utility.Util; import net.coreprotect.utility.WorldUtils; public class RollbackRestoreCommand { protected static void runCommand(CommandSender player, Command command, boolean permission, String[] args, Location argLocation, long forceStart, long forceEnd) { - Location lo = (argLocation != null ? argLocation : CommandHandler.parseLocation(player, args)); + Location lo = (argLocation != null ? argLocation : CommandParser.parseLocation(player, args)); List argUuids = new ArrayList<>(); - List argUsers = CommandHandler.parseUsers(args); - Integer[] argRadius = CommandHandler.parseRadius(args, player, lo); - int argNoisy = CommandHandler.parseNoisy(args); - List argAction = CommandHandler.parseAction(args); - List argBlocks = CommandHandler.parseRestricted(player, args, argAction); - Map argExclude = CommandHandler.parseExcluded(player, args, argAction); - List argExcludeUsers = CommandHandler.parseExcludedUsers(player, args); - String ts = CommandHandler.parseTimeString(args); - long[] argTime = CommandHandler.parseTime(args); + List argUsers = CommandParser.parseUsers(args); + Integer[] argRadius = CommandParser.parseRadius(args, player, lo); + int argNoisy = CommandParser.parseNoisy(args); + List argAction = CommandParser.parseAction(args); + List argBlocks = CommandParser.parseRestricted(player, args, argAction); + Map argExclude = CommandParser.parseExcluded(player, args, argAction); + List argExcludeUsers = CommandParser.parseExcludedUsers(player, args); + String ts = CommandParser.parseTimeString(args); + long[] argTime = CommandParser.parseTime(args); long startTime = argTime[0]; long endTime = argTime[1]; - int argWid = CommandHandler.parseWorld(args, true, true); - boolean count = CommandHandler.parseCount(args); - boolean worldedit = CommandHandler.parseWorldEdit(args); - boolean forceglobal = CommandHandler.parseForceGlobal(args); - int preview = CommandHandler.parsePreview(args); + int argWid = CommandParser.parseWorld(args, true, true); + boolean count = CommandParser.parseCount(args); + boolean worldedit = CommandParser.parseWorldEdit(args); + boolean forceglobal = CommandParser.parseForceGlobal(args); + int preview = CommandParser.parsePreview(args); String corecommand = args[0].toLowerCase(Locale.ROOT); if (argBlocks == null || argExclude == null || argExcludeUsers == null) { @@ -112,7 +111,7 @@ public class RollbackRestoreCommand { return; } if (argWid == -1) { - String worldName = CommandHandler.parseWorldName(args, true); + String worldName = CommandParser.parseWorldName(args, true); Chat.sendMessage(player, Color.DARK_AQUA + "CoreProtect " + Color.WHITE + "- " + Phrase.build(Phrase.WORLD_NOT_FOUND, worldName)); return; } diff --git a/src/main/java/net/coreprotect/command/TabHandler.java b/src/main/java/net/coreprotect/command/TabHandler.java index b0c6508..23d019b 100755 --- a/src/main/java/net/coreprotect/command/TabHandler.java +++ b/src/main/java/net/coreprotect/command/TabHandler.java @@ -318,7 +318,7 @@ public class TabHandler implements TabCompleter { } // add custom tags - for (String tag : CommandHandler.getTags().keySet()) { + for (String tag : CommandParser.getTags().keySet()) { materialList.add(tag); } diff --git a/src/main/java/net/coreprotect/command/parser/ActionParser.java b/src/main/java/net/coreprotect/command/parser/ActionParser.java new file mode 100644 index 0000000..4ade7a7 --- /dev/null +++ b/src/main/java/net/coreprotect/command/parser/ActionParser.java @@ -0,0 +1,228 @@ +package net.coreprotect.command.parser; + +import java.util.ArrayList; +import java.util.List; +import java.util.Locale; + +/** + * Parser for action-related command arguments + */ +public class ActionParser { + + /** + * Parse page from command arguments + * + * @param argumentArray + * The command arguments + * @return The processed argument array + */ + public static String[] parsePage(String[] argumentArray) { + if (argumentArray.length == 2) { + argumentArray[1] = argumentArray[1].replaceFirst("page:", ""); + } + + return argumentArray; + } + + /** + * Parse action from command arguments + * + * @param inputArguments + * The command arguments + * @return A list of action integers + */ + public static List parseAction(String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + List result = new ArrayList<>(); + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("a:") || argument.equals("action:")) { + next = 1; + } + else if (next == 1 || argument.startsWith("a:") || argument.startsWith("action:")) { + result.clear(); + argument = argument.replaceAll("action:", ""); + argument = argument.replaceAll("a:", ""); + if (argument.startsWith("#")) { + argument = argument.replaceFirst("#", ""); + } + if (argument.equals("broke") || argument.equals("break") || argument.equals("remove") || argument.equals("destroy") || argument.equals("block-break") || argument.equals("block-remove") || argument.equals("-block") || argument.equals("-blocks") || argument.equals("block-")) { + result.add(0); + } + else if (argument.equals("placed") || argument.equals("place") || argument.equals("block-place") || argument.equals("+block") || argument.equals("+blocks") || argument.equals("block+")) { + result.add(1); + } + else if (argument.equals("block") || argument.equals("blocks") || argument.equals("block-change") || argument.equals("change") || argument.equals("changes")) { + result.add(0); + result.add(1); + } + else if (argument.equals("click") || argument.equals("clicks") || argument.equals("interact") || argument.equals("interaction") || argument.equals("player-interact") || argument.equals("player-interaction") || argument.equals("player-click")) { + result.add(2); + } + else if (argument.equals("death") || argument.equals("deaths") || argument.equals("entity-death") || argument.equals("entity-deaths") || argument.equals("kill") || argument.equals("kills") || argument.equals("entity-kill") || argument.equals("entity-kills")) { + result.add(3); + } + else if (argument.equals("container") || argument.equals("container-change") || argument.equals("containers") || argument.equals("chest") || argument.equals("transaction") || argument.equals("transactions")) { + result.add(4); + } + else if (argument.equals("-container") || argument.equals("container-") || argument.equals("remove-container")) { + result.add(4); + result.add(0); + } + else if (argument.equals("+container") || argument.equals("container+") || argument.equals("container-add") || argument.equals("add-container")) { + result.add(4); + result.add(1); + } + else if (argument.equals("chat") || argument.equals("chats")) { + result.add(6); + } + else if (argument.equals("command") || argument.equals("commands")) { + result.add(7); + } + else if (argument.equals("logins") || argument.equals("login") || argument.equals("+session") || argument.equals("+sessions") || argument.equals("session+") || argument.equals("+connection") || argument.equals("connection+")) { + result.add(8); + result.add(1); + } + else if (argument.equals("logout") || argument.equals("logouts") || argument.equals("-session") || argument.equals("-sessions") || argument.equals("session-") || argument.equals("-connection") || argument.equals("connection-")) { + result.add(8); + result.add(0); + } + else if (argument.equals("session") || argument.equals("sessions") || argument.equals("connection") || argument.equals("connections")) { + result.add(8); + } + else if (argument.equals("username") || argument.equals("usernames") || argument.equals("user") || argument.equals("users") || argument.equals("name") || argument.equals("names") || argument.equals("uuid") || argument.equals("uuids") || argument.equals("username-change") || argument.equals("username-changes") || argument.equals("name-change") || argument.equals("name-changes")) { + result.add(9); + } + else if (argument.equals("sign") || argument.equals("signs")) { + result.add(10); + } + else if (argument.equals("inv") || argument.equals("inventory") || argument.equals("inventories")) { + result.add(4); // container + result.add(11); // item + } + else if (argument.equals("-inv") || argument.equals("inv-") || argument.equals("-inventory") || argument.equals("inventory-") || argument.equals("-inventories")) { + result.add(4); + result.add(11); + result.add(1); + } + else if (argument.equals("+inv") || argument.equals("inv+") || argument.equals("+inventory") || argument.equals("inventory+") || argument.equals("+inventories")) { + result.add(4); + result.add(11); + result.add(0); + } + else if (argument.equals("item") || argument.equals("items")) { + result.add(11); + } + else if (argument.equals("-item") || argument.equals("item-") || argument.equals("-items") || argument.equals("items-") || argument.equals("drop") || argument.equals("drops") || argument.equals("deposit") || argument.equals("deposits") || argument.equals("deposited")) { + result.add(11); + result.add(0); + } + else if (argument.equals("+item") || argument.equals("item+") || argument.equals("+items") || argument.equals("items+") || argument.equals("pickup") || argument.equals("pickups") || argument.equals("withdraw") || argument.equals("withdraws") || argument.equals("withdrew")) { + result.add(11); + result.add(1); + } + else { + result.add(-1); + } + next = 0; + } + else { + next = 0; + } + } + count++; + } + return result; + } + + /** + * Parse count flag from command arguments + * + * @param inputArguments + * The command arguments + * @return true if the count flag is present + */ + public static boolean parseCount(String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + boolean result = false; + int count = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + if (argument.equals("#count") || argument.equals("#sum")) { + result = true; + } + } + count++; + } + return result; + } + + /** + * Parse noisy flag from command arguments + * + * @param inputArguments + * The command arguments + * @return 1 if noisy/verbose mode is enabled, 0 otherwise + */ + public static int parseNoisy(String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + int noisy = 0; + int count = 0; + if (net.coreprotect.config.Config.getGlobal().VERBOSE) { + noisy = 1; + } + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("n") || argument.equals("noisy") || argument.equals("v") || argument.equals("verbose") || argument.equals("#v") || argument.equals("#verbose")) { + noisy = 1; + } + else if (argument.equals("#silent")) { + noisy = 0; + } + } + count++; + } + return noisy; + } + + /** + * Parse preview flag from command arguments + * + * @param inputArguments + * The command arguments + * @return 1 for preview, 2 for preview cancel, 0 otherwise + */ + public static int parsePreview(String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + int result = 0; + int count = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + if (argument.equals("#preview")) { + result = 1; + } + else if (argument.equals("#preview_cancel")) { + result = 2; + } + } + count++; + } + return result; + } +} diff --git a/src/main/java/net/coreprotect/command/parser/LocationParser.java b/src/main/java/net/coreprotect/command/parser/LocationParser.java new file mode 100644 index 0000000..c78eb96 --- /dev/null +++ b/src/main/java/net/coreprotect/command/parser/LocationParser.java @@ -0,0 +1,229 @@ +package net.coreprotect.command.parser; + +import java.util.Locale; + +import org.bukkit.Bukkit; +import org.bukkit.Location; +import org.bukkit.command.BlockCommandSender; +import org.bukkit.command.CommandSender; +import org.bukkit.entity.Player; + +import net.coreprotect.bukkit.BukkitAdapter; +import net.coreprotect.utility.WorldUtils; + +/** + * Parser for location-related command arguments + */ +public class LocationParser { + + /** + * Parse location from command sender and command arguments + * + * @param user + * The command sender + * @param argumentArray + * The command arguments + * @return The parsed location + */ + public static Location parseLocation(CommandSender user, String[] argumentArray) { + Location location = null; + if (user instanceof Player) { + location = ((Player) user).getLocation(); + } + else if (user instanceof BlockCommandSender) { + location = ((BlockCommandSender) user).getBlock().getLocation(); + } + + return parseCoordinates(location, argumentArray, WorldParser.parseWorld(argumentArray, true, true)); + } + + /** + * Parse coordinates from command arguments and apply them to a location + * + * @param location + * The base location + * @param inputArguments + * The command arguments + * @param worldId + * The world ID + * @return The modified location + */ + public static Location parseCoordinates(Location location, String[] inputArguments, int worldId) { + String[] argumentArray = inputArguments.clone(); + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("position:") || argument.equals("location:") || argument.equals("c:") || argument.equals("coord:") || argument.equals("coords:") || argument.equals("cord:") || argument.equals("cords:") || argument.equals("coordinate:") || argument.equals("coordinates:") || argument.equals("cordinate:") || argument.equals("cordinates:")) { + next = 2; + } + else if (next == 2 || argument.startsWith("c:") || argument.startsWith("coord:") || argument.startsWith("coords:") || argument.startsWith("cord:") || argument.startsWith("cords:") || argument.startsWith("coordinate:") || argument.startsWith("coordinates:") || argument.startsWith("cordinate:") || argument.startsWith("cordinates:")) { + argument = argument.replaceAll("coordinates:", ""); + argument = argument.replaceAll("coordinate:", ""); + argument = argument.replaceAll("cordinates:", ""); + argument = argument.replaceAll("cordinate:", ""); + argument = argument.replaceAll("coords:", ""); + argument = argument.replaceAll("coord:", ""); + argument = argument.replaceAll("cords:", ""); + argument = argument.replaceAll("cord:", ""); + argument = argument.replaceAll("c:", ""); + if (argument.contains(",")) { + String[] i2 = argument.split(","); + double x = 0.00; + double y = 0.00; + double z = 0.00; + int cCount = 0; + for (String coord : i2) { + coord = coord.replaceAll("[^0-9.\\-]", ""); + if (coord.length() > 0 && !coord.equals(".") && !coord.equals("-") && coord.indexOf('.') == coord.lastIndexOf('.')) { + double parsedCoord = Double.parseDouble(coord); + if (cCount == 0) { + x = parsedCoord; + } + else if (cCount == 1) { + z = parsedCoord; + } + else if (cCount == 2) { + y = z; + z = parsedCoord; + } + cCount++; + } + } + if (cCount > 1) { + if (location == null && worldId > 0) { + location = new Location(Bukkit.getWorld(WorldUtils.getWorldName(worldId)), 0, 0, 0); + } + if (location != null) { + int worldMaxHeight = location.getWorld().getMaxHeight() - 1; + int worldMinHeight = BukkitAdapter.ADAPTER.getMinHeight(location.getWorld()); + + if (y < worldMinHeight) { + y = Double.valueOf(worldMinHeight); + } + if (y > worldMaxHeight) { + y = Double.valueOf(worldMaxHeight); + } + + location.setX(x); + location.setY(y); + location.setZ(z); + } + } + } + next = 0; + } + else { + next = 0; + } + } + count++; + } + return location; + } + + /** + * Parse radius from command arguments + * + * @param inputArguments + * The command arguments + * @param user + * The command sender + * @param location + * The base location + * @return The parsed radius + */ + public static Integer[] parseRadius(String[] inputArguments, CommandSender user, Location location) { + String[] argumentArray = inputArguments.clone(); + Integer[] radius = null; + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("r:") || argument.equals("radius:")) { + next = 2; + } + else if (next == 2 || argument.startsWith("r:") || argument.startsWith("radius:")) { + argument = argument.replaceAll("radius:", ""); + argument = argument.replaceAll("r:", ""); + if (argument.equals("#worldedit") || argument.equals("#we")) { + // For WorldEdit, we'll need to use the original CommandParser since + // the WorldEditHandler.runWorldEditCommand method is protected + return null; // Let CommandParser handle this case + } + else if ((argument.startsWith("#") && argument.length() > 1) || argument.equals("global") || argument.equals("off") || argument.equals("-1") || argument.equals("none") || argument.equals("false")) { + // radius = -2; + } + else { + int rcount = 0; + int r_x = 0; + int r_y = -1; + int r_z = 0; + String[] r_dat = new String[] { argument }; + boolean validRadius = false; + if (argument.contains("x")) { + r_dat = argument.split("x"); + } + for (String value : r_dat) { + String i4 = value.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.length() == value.length() && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + double a1 = Double.parseDouble(i4); + if (rcount == 0) { // x + r_x = (int) a1; + r_z = (int) a1; + } + else if (rcount == 1) { // y + r_y = (int) a1; + } + else if (rcount == 2) { // z + r_z = (int) a1; + } + validRadius = true; + } + rcount++; + } + if (location != null) { + Integer xmin = location.getBlockX() - r_x; + Integer xmax = location.getBlockX() + r_x; + Integer ymin = null; + Integer ymax = null; + Integer zmin = location.getBlockZ() - r_z; + Integer zmax = location.getBlockZ() + r_z; + if (r_y > -1) { + ymin = location.getBlockY() - r_y; + ymax = location.getBlockY() + r_y; + } + int max = r_x; + if (r_y > max) { + max = r_y; + } + if (r_z > max) { + max = r_z; + } + if (validRadius) { + radius = new Integer[] { max, xmin, xmax, ymin, ymax, zmin, zmax, 0 }; + } + else { + radius = new Integer[] { -1 }; + } + } + } + next = 0; + } + else { + next = 0; + } + } + count++; + } + return radius; + } +} diff --git a/src/main/java/net/coreprotect/command/parser/MaterialParser.java b/src/main/java/net/coreprotect/command/parser/MaterialParser.java new file mode 100644 index 0000000..1272111 --- /dev/null +++ b/src/main/java/net/coreprotect/command/parser/MaterialParser.java @@ -0,0 +1,308 @@ +package net.coreprotect.command.parser; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Locale; +import java.util.Map; +import java.util.Map.Entry; +import java.util.Set; + +import org.bukkit.Material; +import org.bukkit.command.CommandSender; +import org.bukkit.entity.EntityType; + +import net.coreprotect.language.Phrase; +import net.coreprotect.model.BlockGroup; +import net.coreprotect.utility.Chat; +import net.coreprotect.utility.Color; +import net.coreprotect.utility.EntityUtils; +import net.coreprotect.utility.MaterialUtils; + +/** + * Parser for material and entity related command arguments + */ +public class MaterialParser { + + /** + * Parse restricted materials and entities from command arguments + * + * @param player + * The command sender + * @param inputArguments + * The command arguments + * @param argAction + * The list of actions to include + * @return A list of restricted materials and entities + */ + public static List parseRestricted(CommandSender player, String[] inputArguments, List argAction) { + String[] argumentArray = inputArguments.clone(); + List restricted = new ArrayList<>(); + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("i:") || argument.equals("include:") || argument.equals("item:") || argument.equals("items:") || argument.equals("b:") || argument.equals("block:") || argument.equals("blocks:")) { + next = 4; + } + else if (next == 4 || argument.startsWith("i:") || argument.startsWith("include:") || argument.startsWith("item:") || argument.startsWith("items:") || argument.startsWith("b:") || argument.startsWith("block:") || argument.startsWith("blocks:")) { + argument = argument.replaceAll("include:", ""); + argument = argument.replaceAll("i:", ""); + argument = argument.replaceAll("items:", ""); + argument = argument.replaceAll("item:", ""); + argument = argument.replaceAll("blocks:", ""); + argument = argument.replaceAll("block:", ""); + argument = argument.replaceAll("b:", ""); + if (argument.contains(",")) { + String[] i2 = argument.split(","); + for (String i3 : i2) { + if (!checkTags(i3, restricted)) { + Material i3_material = MaterialUtils.getType(i3); + if (i3_material != null && (i3_material.isBlock() || argAction.contains(4))) { + restricted.add(i3_material); + } + else { + EntityType i3_entity = EntityUtils.getEntityType(i3); + if (i3_entity != null) { + restricted.add(i3_entity); + } + else if (i3_material != null) { + restricted.add(i3_material); + } + else { + Chat.sendMessage(player, Color.DARK_AQUA + "CoreProtect " + Color.WHITE + "- " + Phrase.build(Phrase.INVALID_INCLUDE, i3)); + // Functions.sendMessage(player, Color.DARK_AQUA + "CoreProtect " + Color.WHITE + "- " + Phrase.build(Phrase.MISSING_PARAMETERS, "/co help include")); + return null; + } + } + } + } + if (argument.endsWith(",")) { + next = 4; + } + else { + next = 0; + } + } + else { + if (!checkTags(argument, restricted)) { + Material material = MaterialUtils.getType(argument); + if (material != null && (material.isBlock() || argAction.contains(4))) { + restricted.add(material); + } + else { + EntityType entityType = EntityUtils.getEntityType(argument); + if (entityType != null) { + restricted.add(entityType); + } + else if (material != null) { + restricted.add(material); + } + else { + Chat.sendMessage(player, Color.DARK_AQUA + "CoreProtect " + Color.WHITE + "- " + Phrase.build(Phrase.INVALID_INCLUDE, argument)); + // Functions.sendMessage(player, Color.DARK_AQUA + "CoreProtect " + Color.WHITE + "- " + Phrase.build(Phrase.MISSING_PARAMETERS, "/co help include")); + return null; + } + } + } + next = 0; + } + } + else { + next = 0; + } + } + count++; + } + return restricted; + } + + /** + * Parse excluded materials and entities from command arguments + * + * @param player + * The command sender + * @param inputArguments + * The command arguments + * @param argAction + * The list of actions to include + * @return A map of excluded materials and entities + */ + public static Map parseExcluded(CommandSender player, String[] inputArguments, List argAction) { + String[] argumentArray = inputArguments.clone(); + Map excluded = new HashMap<>(); + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("e:") || argument.equals("exclude:")) { + next = 5; + } + else if (next == 5 || argument.startsWith("e:") || argument.startsWith("exclude:")) { + argument = argument.replaceAll("exclude:", ""); + argument = argument.replaceAll("e:", ""); + if (argument.contains(",")) { + String[] i2 = argument.split(","); + for (String i3 : i2) { + if (!checkTags(i3, excluded)) { + Material i3_material = MaterialUtils.getType(i3); + if (i3_material != null && (i3_material.isBlock() || argAction.contains(4))) { + excluded.put(i3_material, false); + } + else { + EntityType i3_entity = EntityUtils.getEntityType(i3); + if (i3_entity != null) { + excluded.put(i3_entity, false); + } + else if (i3_material != null) { + excluded.put(i3_material, false); + } + } + } + } + if (argument.endsWith(",")) { + next = 5; + } + else { + next = 0; + } + } + else { + if (!checkTags(argument, excluded)) { + Material iMaterial = MaterialUtils.getType(argument); + if (iMaterial != null && (iMaterial.isBlock() || argAction.contains(4))) { + excluded.put(iMaterial, false); + } + else { + EntityType iEntity = EntityUtils.getEntityType(argument); + if (iEntity != null) { + excluded.put(iEntity, false); + } + else if (iMaterial != null) { + excluded.put(iMaterial, false); + } + } + } + next = 0; + } + } + else { + next = 0; + } + } + count++; + } + return excluded; + } + + /** + * Get a map of block tags and their associated materials + * + * @return A map of block tags and their associated materials + */ + public static Map> getTags() { + Map> tagMap = new HashMap<>(); + tagMap.put("#button", BlockGroup.BUTTONS); + tagMap.put("#container", BlockGroup.CONTAINERS); + tagMap.put("#door", BlockGroup.DOORS); + tagMap.put("#natural", BlockGroup.NATURAL_BLOCKS); + tagMap.put("#pressure_plate", BlockGroup.PRESSURE_PLATES); + tagMap.put("#shulker_box", BlockGroup.SHULKER_BOXES); + return tagMap; + } + + /** + * Check if an argument matches a block tag + * + * @param argument + * The argument to check + * @return true if the argument matches a block tag + */ + public static boolean checkTags(String argument) { + return getTags().containsKey(argument); + } + + /** + * Check if an argument matches a block tag and add the associated materials to the list + * + * @param argument + * The argument to check + * @param list + * The list to add the associated materials to + * @return true if the argument matches a block tag + */ + public static boolean checkTags(String argument, Map list) { + for (Entry> entry : getTags().entrySet()) { + String tag = entry.getKey(); + Set materials = entry.getValue(); + + if (argument.equals(tag)) { + for (Material block : materials) { + list.put(block, false); + } + + return true; + } + } + + return false; + } + + /** + * Check if an argument matches a block tag and add the associated materials to the list + * + * @param argument + * The argument to check + * @param list + * The list to add the associated materials to + * @return true if the argument matches a block tag + */ + public static boolean checkTags(String argument, List list) { + for (Entry> entry : getTags().entrySet()) { + String tag = entry.getKey(); + Set materials = entry.getValue(); + + if (argument.equals(tag)) { + list.addAll(materials); + return true; + } + } + + return false; + } + + /** + * Check if a string represents a block or entity + * + * @param argument + * The string to check + * @return true if the string represents a block or entity + */ + public static boolean isBlockOrEntity(String argument) { + boolean isBlock = false; + if (checkTags(argument)) { + isBlock = true; + } + else { + Material material = MaterialUtils.getType(argument); + if (material != null) { + isBlock = true; + } + else { + EntityType entityType = EntityUtils.getEntityType(argument); + if (entityType != null) { + isBlock = true; + } + } + } + return isBlock; + } +} diff --git a/src/main/java/net/coreprotect/command/parser/TimeParser.java b/src/main/java/net/coreprotect/command/parser/TimeParser.java new file mode 100644 index 0000000..b58be33 --- /dev/null +++ b/src/main/java/net/coreprotect/command/parser/TimeParser.java @@ -0,0 +1,298 @@ +package net.coreprotect.command.parser; + +import java.math.BigDecimal; +import java.util.Locale; + +import net.coreprotect.language.Phrase; +import net.coreprotect.language.Selector; + +/** + * Parser for time-related command arguments + */ +public class TimeParser { + + /** + * Parse time from command arguments + * + * @param inputArguments + * The command arguments + * @return An array of two longs - [time1, time2] + */ + public static long[] parseTime(String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + long timeStart = 0; + long timeEnd = 0; + int count = 0; + int next = 0; + boolean range = false; + double w = 0; + double d = 0; + double h = 0; + double m = 0; + double s = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("t:") || argument.equals("time:")) { + next = 1; + } + else if (next == 1 || argument.startsWith("t:") || argument.startsWith("time:")) { + // time arguments + argument = argument.replaceAll("time:", ""); + argument = argument.replaceAll("t:", ""); + argument = argument.replaceAll("y", "y:"); + argument = argument.replaceAll("m", "m:"); + argument = argument.replaceAll("w", "w:"); + argument = argument.replaceAll("d", "d:"); + argument = argument.replaceAll("h", "h:"); + argument = argument.replaceAll("s", "s:"); + range = argument.contains("-"); + + int argCount = 0; + String[] i2 = argument.split(":"); + for (String i3 : i2) { + if (range && argCount > 0 && timeStart == 0 && i3.startsWith("-")) { + timeStart = (long) (((w * 7 * 24 * 60 * 60) + (d * 24 * 60 * 60) + (h * 60 * 60) + (m * 60) + s)); + w = 0; + d = 0; + h = 0; + m = 0; + s = 0; + } + + if (i3.endsWith("w") && w == 0) { + String i4 = i3.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + w = Double.parseDouble(i4); + } + } + else if (i3.endsWith("d") && d == 0) { + String i4 = i3.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + d = Double.parseDouble(i4); + } + } + else if (i3.endsWith("h") && h == 0) { + String i4 = i3.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + h = Double.parseDouble(i4); + } + } + else if (i3.endsWith("m") && m == 0) { + String i4 = i3.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + m = Double.parseDouble(i4); + } + } + else if (i3.endsWith("s") && s == 0) { + String i4 = i3.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + s = Double.parseDouble(i4); + } + } + + argCount++; + } + if (timeStart > 0) { + timeEnd = (long) (((w * 7 * 24 * 60 * 60) + (d * 24 * 60 * 60) + (h * 60 * 60) + (m * 60) + s)); + } + else { + timeStart = (long) (((w * 7 * 24 * 60 * 60) + (d * 24 * 60 * 60) + (h * 60 * 60) + (m * 60) + s)); + } + next = 0; + } + else { + next = 0; + } + } + count++; + } + + if (timeEnd >= timeStart) { + return new long[] { timeEnd, timeStart }; + } + else { + return new long[] { timeStart, timeEnd }; + } + } + + /** + * Parse time string from command arguments for display + * + * @param inputArguments + * The command arguments + * @return A formatted time string + */ + public static String parseTimeString(String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + String time = ""; + int count = 0; + int next = 0; + boolean range = false; + BigDecimal w = new BigDecimal(0); + BigDecimal d = new BigDecimal(0); + BigDecimal h = new BigDecimal(0); + BigDecimal m = new BigDecimal(0); + BigDecimal s = new BigDecimal(0); + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("t:") || argument.equals("time:")) { + next = 1; + } + else if (next == 1 || argument.startsWith("t:") || argument.startsWith("time:")) { + // time arguments + argument = argument.replaceAll("time:", ""); + argument = argument.replaceAll("t:", ""); + argument = argument.replaceAll("y", "y:"); + argument = argument.replaceAll("m", "m:"); + argument = argument.replaceAll("w", "w:"); + argument = argument.replaceAll("d", "d:"); + argument = argument.replaceAll("h", "h:"); + argument = argument.replaceAll("s", "s:"); + range = argument.contains("-"); + + int argCount = 0; + String[] i2 = argument.split(":"); + for (String i3 : i2) { + if (range && argCount > 0 && !time.contains("-") && i3.startsWith("-")) { + w = new BigDecimal(0); + d = new BigDecimal(0); + h = new BigDecimal(0); + m = new BigDecimal(0); + s = new BigDecimal(0); + time = time + " -"; + } + + if (i3.endsWith("w") && w.intValue() == 0) { + String i4 = i3.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + w = new BigDecimal(i4); + if (range) { + time = time + " " + timeString(w) + "w"; + } + else { + time = time + " " + Phrase.build(Phrase.TIME_WEEKS, timeString(w), (w.doubleValue() == 1 ? Selector.FIRST : Selector.SECOND)); + } + } + } + else if (i3.endsWith("d") && d.intValue() == 0) { + String i4 = i3.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + d = new BigDecimal(i4); + if (range) { + time = time + " " + timeString(d) + "d"; + } + else { + time = time + " " + Phrase.build(Phrase.TIME_DAYS, timeString(d), (d.doubleValue() == 1 ? Selector.FIRST : Selector.SECOND)); + } + } + } + else if (i3.endsWith("h") && h.intValue() == 0) { + String i4 = i3.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + h = new BigDecimal(i4); + if (range) { + time = time + " " + timeString(h) + "h"; + } + else { + time = time + " " + Phrase.build(Phrase.TIME_HOURS, timeString(h), (h.doubleValue() == 1 ? Selector.FIRST : Selector.SECOND)); + } + } + } + else if (i3.endsWith("m") && m.intValue() == 0) { + String i4 = i3.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + m = new BigDecimal(i4); + if (range) { + time = time + " " + timeString(m) + "m"; + } + else { + time = time + " " + Phrase.build(Phrase.TIME_MINUTES, timeString(m), (m.doubleValue() == 1 ? Selector.FIRST : Selector.SECOND)); + } + } + } + else if (i3.endsWith("s") && s.intValue() == 0) { + String i4 = i3.replaceAll("[^0-9.]", ""); + if (i4.length() > 0 && i4.replaceAll("[^0-9]", "").length() > 0 && i4.indexOf('.') == i4.lastIndexOf('.')) { + s = new BigDecimal(i4); + if (range) { + time = time + " " + timeString(s) + "s"; + } + else { + time = time + " " + Phrase.build(Phrase.TIME_SECONDS, timeString(s), (s.doubleValue() == 1 ? Selector.FIRST : Selector.SECOND)); + } + } + } + + argCount++; + } + next = 0; + } + else { + next = 0; + } + } + count++; + } + + if (time.startsWith(" ")) { + time = time.substring(1); + } + + return time; + } + + /** + * Parse rows from command arguments + * + * @param inputArguments + * The command arguments + * @return The number of rows + */ + public static int parseRows(String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + int rows = 0; + int count = 0; + int next = 0; + + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("rows:")) { + next = 1; + } + else if (next == 1 || argument.startsWith("rows:")) { + argument = argument.replaceAll("rows:", "").trim(); + if (!argument.startsWith("-")) { + String i2 = argument.replaceAll("[^0-9]", ""); + if (i2.length() > 0 && i2.length() < 10) { + rows = Integer.parseInt(i2); + } + } + + next = 0; + } + else { + next = 0; + } + } + count++; + } + + return rows; + } + + private static String timeString(BigDecimal input) { + return input.stripTrailingZeros().toPlainString(); + } +} diff --git a/src/main/java/net/coreprotect/command/parser/UserParser.java b/src/main/java/net/coreprotect/command/parser/UserParser.java new file mode 100644 index 0000000..b77da27 --- /dev/null +++ b/src/main/java/net/coreprotect/command/parser/UserParser.java @@ -0,0 +1,160 @@ +package net.coreprotect.command.parser; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; +import java.util.Locale; + +import org.bukkit.command.CommandSender; + +/** + * Parser for user-related command arguments + */ +public class UserParser { + + /** + * Parse users from command arguments + * + * @param inputArguments + * The command arguments + * @return A list of parsed users + */ + public static List parseUsers(String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + List users = new ArrayList<>(); + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (next == 2) { + if (argument.endsWith(",")) { + next = 2; + } + else { + next = 0; + } + } + else if (argument.equals("p:") || argument.equals("user:") || argument.equals("users:") || argument.equals("u:")) { + next = 1; + } + else if (next == 1 || argument.startsWith("p:") || argument.startsWith("user:") || argument.startsWith("users:") || argument.startsWith("u:")) { + argument = argument.replaceAll("user:", ""); + argument = argument.replaceAll("users:", ""); + argument = argument.replaceAll("p:", ""); + argument = argument.replaceAll("u:", ""); + if (argument.contains(",")) { + String[] i2 = argument.split(","); + for (String i3 : i2) { + parseUser(users, i3); + } + if (argument.endsWith(",")) { + next = 1; + } + else { + next = 0; + } + } + else { + parseUser(users, argument); + next = 0; + } + } + else if (argument.endsWith(",") || argument.endsWith(":")) { + next = 2; + } + else if (argument.contains(":")) { + next = 0; + } + else { + parseUser(users, argument); + next = 0; + } + } + count++; + } + return users; + } + + /** + * Parse excluded users from command arguments + * + * @param player + * The command sender + * @param inputArguments + * The command arguments + * @return A list of excluded users + */ + public static List parseExcludedUsers(CommandSender player, String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + List excluded = new ArrayList<>(); + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("e:") || argument.equals("exclude:")) { + next = 5; + } + else if (next == 5 || argument.startsWith("e:") || argument.startsWith("exclude:")) { + argument = argument.replaceAll("exclude:", ""); + argument = argument.replaceAll("e:", ""); + if (argument.contains(",")) { + String[] i2 = argument.split(","); + for (String i3 : i2) { + boolean isBlock = MaterialParser.isBlockOrEntity(i3); + if (!isBlock) { + excluded.add(i3); + } + } + if (argument.endsWith(",")) { + next = 5; + } + else { + next = 0; + } + } + else { + boolean isBlock = MaterialParser.isBlockOrEntity(argument); + if (!isBlock) { + excluded.add(argument); + } + next = 0; + } + } + else { + next = 0; + } + } + count++; + } + return excluded; + } + + /** + * Process a user string and add it to the users list if valid + * + * @param users + * The list to add the user to + * @param user + * The user string to process + */ + private static void parseUser(List users, String user) { + List badUsers = Arrays.asList("n", "noisy", "v", "verbose", "#v", "#verbose", "#silent", "#preview", "#preview_cancel", "#count", "#sum"); + String check = user.replaceAll("[\\s'\"]", ""); + if (check.equals(user) && check.length() > 0) { + if (user.equalsIgnoreCase("#global")) { + user = "#global"; + } + if (!badUsers.contains(user.toLowerCase(Locale.ROOT))) { + users.add(user); + } + } + } +} diff --git a/src/main/java/net/coreprotect/command/parser/WorldParser.java b/src/main/java/net/coreprotect/command/parser/WorldParser.java new file mode 100644 index 0000000..619a717 --- /dev/null +++ b/src/main/java/net/coreprotect/command/parser/WorldParser.java @@ -0,0 +1,186 @@ +package net.coreprotect.command.parser; + +import java.util.Locale; + +import net.coreprotect.config.ConfigHandler; +import net.coreprotect.utility.WorldUtils; + +/** + * Parser for world-related command arguments + */ +public class WorldParser { + + /** + * Parse world from command arguments + * + * @param inputArguments + * The command arguments + * @param processWorldEdit + * Whether to process WorldEdit arguments + * @param requireLoaded + * Whether the world must be loaded + * @return The world ID + */ + public static int parseWorld(String[] inputArguments, boolean processWorldEdit, boolean requireLoaded) { + String[] argumentArray = inputArguments.clone(); + int world_id = 0; + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim(); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + String inputProcessed = argument.toLowerCase(Locale.ROOT); + if (inputProcessed.equals("r:") || inputProcessed.equals("radius:")) { + next = 2; + } + else if (next == 2 || inputProcessed.startsWith("r:") || inputProcessed.startsWith("radius:")) { + argument = argument.replaceAll("radius:", "").replaceAll("r:", ""); + inputProcessed = argument.toLowerCase(Locale.ROOT); + if ((processWorldEdit && (inputProcessed.equals("#worldedit") || inputProcessed.equals("#we"))) || inputProcessed.equals("#global") || inputProcessed.equals("global") || inputProcessed.equals("off") || inputProcessed.equals("-1") || inputProcessed.equals("none") || inputProcessed.equals("false")) { + world_id = 0; + } + else if (inputProcessed.startsWith("#")) { + world_id = WorldUtils.matchWorld(inputProcessed); + if (world_id == -1 && !requireLoaded) { + world_id = ConfigHandler.worlds.getOrDefault(argument.replaceFirst("#", ""), -1); + } + } + next = 0; + } + else { + next = 0; + } + } + count++; + } + return world_id; + } + + /** + * Parse world name from command arguments + * + * @param inputArguments + * The command arguments + * @param processWorldEdit + * Whether to process WorldEdit arguments + * @return The world name + */ + public static String parseWorldName(String[] inputArguments, boolean processWorldEdit) { + String[] argumentArray = inputArguments.clone(); + String worldName = ""; + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("r:") || argument.equals("radius:")) { + next = 2; + } + else if (next == 2 || argument.startsWith("r:") || argument.startsWith("radius:")) { + argument = argument.replaceAll("radius:", ""); + argument = argument.replaceAll("r:", ""); + if ((processWorldEdit && (argument.equals("#worldedit") || argument.equals("#we"))) || argument.equals("#global") || argument.equals("global") || argument.equals("off") || argument.equals("-1") || argument.equals("none") || argument.equals("false")) { + worldName = ""; + } + else if (argument.startsWith("#")) { + worldName = argument.replaceFirst("#", ""); + } + next = 0; + } + else { + next = 0; + } + } + count++; + } + return worldName; + } + + /** + * Parse whether to use WorldEdit for radius + * + * @param inputArguments + * The command arguments + * @return true if WorldEdit should be used + */ + public static boolean parseWorldEdit(String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + boolean result = false; + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("r:") || argument.equals("radius:")) { + next = 2; + } + else if (next == 2 || argument.startsWith("r:") || argument.startsWith("radius:")) { + argument = argument.replaceAll("radius:", ""); + argument = argument.replaceAll("r:", ""); + if (argument.equals("#worldedit") || argument.equals("#we")) { + result = true; + } + next = 0; + } + else { + next = 0; + } + } + count++; + } + return result; + } + + /** + * Parse whether to force global search + * + * @param inputArguments + * The command arguments + * @return true if global search should be forced + */ + public static boolean parseForceGlobal(String[] inputArguments) { + String[] argumentArray = inputArguments.clone(); + boolean result = false; + int count = 0; + int next = 0; + for (String argument : argumentArray) { + if (count > 0) { + argument = argument.trim().toLowerCase(Locale.ROOT); + argument = argument.replaceAll("\\\\", ""); + argument = argument.replaceAll("'", ""); + + if (argument.equals("r:") || argument.equals("radius:")) { + next = 2; + } + else if (next == 2 || argument.startsWith("r:") || argument.startsWith("radius:")) { + argument = argument.replaceAll("radius:", ""); + argument = argument.replaceAll("r:", ""); + if (argument.equals("#global") || argument.equals("global") || argument.equals("off") || argument.equals("-1") || argument.equals("none") || argument.equals("false")) { + result = true; + } + else if (argument.startsWith("#")) { + int worldId = WorldUtils.matchWorld(argument); + if (worldId > 0) { + result = true; + } + } + next = 0; + } + else { + next = 0; + } + } + count++; + } + return result; + } +}