From 46f8453b5b83a0c8a14d85f7f0e463aadda41513 Mon Sep 17 00:00:00 2001 From: Niels Boehm Date: Mon, 23 Sep 2019 14:54:35 +0200 Subject: [PATCH 001/109] Ensure archors are saved in a machine-readable way `locationToString()` is primarily used by the AnchorManager to persist anchors to disk (the other use is for logging). In a locale that uses periods as decimal separator, this works fine and the anchors can be loaded when the server restarts. However, in a locale that doesn't use periods (but commas, for instance) this produces an `anchors.yml` that cannot be parsed when loaded. Tying the string formatting in `locationToString()` to an English locale makes it behave as expected, regardless of the external locale setting. --- .../MultiverseCore/utils/SimpleLocationManipulation.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/SimpleLocationManipulation.java b/src/main/java/com/onarandombox/MultiverseCore/utils/SimpleLocationManipulation.java index 3d0436b1..17f770e1 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/SimpleLocationManipulation.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/SimpleLocationManipulation.java @@ -19,6 +19,7 @@ import com.onarandombox.MultiverseCore.api.LocationManipulation; import java.text.DecimalFormat; import java.util.Collections; import java.util.HashMap; +import java.util.Locale; import java.util.Map; /** @@ -52,7 +53,7 @@ public class SimpleLocationManipulation implements LocationManipulation { if (location == null) { return ""; } - return String.format("%s:%.2f,%.2f,%.2f:%.2f:%.2f", location.getWorld().getName(), + return String.format(Locale.ENGLISH, "%s:%.2f,%.2f,%.2f:%.2f:%.2f", location.getWorld().getName(), location.getX(), location.getY(), location.getZ(), location.getYaw(), location.getPitch()); } From 9d42a05759228dab197e311242e79750055dd071 Mon Sep 17 00:00:00 2001 From: A248 Date: Thu, 16 Apr 2020 18:31:23 -0400 Subject: [PATCH 002/109] Fix NPE for invalid world argument in gamerule cmd Stumbled upon an NPE when using /mv gamerule. I realised it was because I had specified a nonexistent world. This will fix it. --- .../MultiverseCore/commands/GameruleCommand.java | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/GameruleCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/GameruleCommand.java index 5cc91d9f..01eddae6 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/GameruleCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/GameruleCommand.java @@ -62,6 +62,11 @@ public class GameruleCommand extends MultiverseCommand { world = p.getWorld(); } else { world = Bukkit.getWorld(args.get(2)); + if (world == null) { + sender.sendMessage(ChatColor.RED + "Failure!" + ChatColor.WHITE + " World " + ChatColor.AQUA + args.get(2) + + ChatColor.WHITE + " does not exist."); + return; + } } if (world.setGameRuleValue(gameRule, value)) { From c70e254dbfb6fa0bb6128ea3d18121c896d3289a Mon Sep 17 00:00:00 2001 From: wellnesscookie <46493763+wellnesscookie@users.noreply.github.com> Date: Thu, 30 Apr 2020 20:43:11 +0200 Subject: [PATCH 003/109] Fixes alias not clearing after cloning the world This will rather set an alias to an empty string which will automatically be resulted in alias being as same as the name of the cloned world. Previously, it was not working as intended and kept the alias of the oldWorld. --- .../com/onarandombox/MultiverseCore/utils/WorldManager.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java b/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java index 41cd707e..d3fcb8c6 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java @@ -199,7 +199,7 @@ public class WorldManager implements MVWorldManager { MVWorld newWorld = (MVWorld) this.getMVWorld(newName); newWorld.copyValues(this.worldsFromTheConfig.get(oldName)); // don't keep the alias the same -- that would be useless - newWorld.setAlias(null); + newWorld.setAlias(""); return true; } } From 1fac13247f297a5d6043b475cade3d18f5d54c2b Mon Sep 17 00:00:00 2001 From: nicegamer7 Date: Wed, 6 May 2020 13:07:48 -0400 Subject: [PATCH 004/109] Fix Travis Builds for Pull Requests (#2208) * fix travis * I don't think we need this * we don't use circleci anymore --- .travis.yml | 3 +-- circle.yml | 3 --- 2 files changed, 1 insertion(+), 5 deletions(-) delete mode 100644 circle.yml diff --git a/.travis.yml b/.travis.yml index 1ecfa2d1..2e7dbb32 100644 --- a/.travis.yml +++ b/.travis.yml @@ -3,5 +3,4 @@ jdk: - oraclejdk8 notifications: email: false -before_install: - - sed -i.bak -e 's|https://nexus.codehaus.org/snapshots/|https://oss.sonatype.org/content/repositories/codehaus-snapshots/|g' ~/.m2/settings.xml +dist: trusty diff --git a/circle.yml b/circle.yml deleted file mode 100644 index 593dfcb2..00000000 --- a/circle.yml +++ /dev/null @@ -1,3 +0,0 @@ -machine: - java: - version: oraclejdk8 \ No newline at end of file From 4894abd1f1b66a87f7793487cd772cc5d3b7e0fd Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sat, 6 Jun 2020 13:36:53 -0400 Subject: [PATCH 005/109] switch to bStats --- pom.xml | 15 +-- .../MultiverseCore/MultiverseCore.java | 120 +++++------------- 2 files changed, 42 insertions(+), 93 deletions(-) diff --git a/pom.xml b/pom.xml index 47757389..0949061f 100644 --- a/pom.xml +++ b/pom.xml @@ -33,10 +33,9 @@ minebench-repo https://repo.minebench.de/ - - elmakers-repo - http://maven.elmakers.com/repository/ + CodeMC + https://repo.codemc.org/repository/maven-public @@ -203,8 +202,8 @@ com.onarandombox.buscript - org.mcstats - com.onarandombox.mcstats + org.bstats + com.onarandombox.bstats com.dumptruckman.minecraft.util.Logging @@ -283,9 +282,9 @@ 2.0-SNAPSHOT - org.mcstats.bukkit - metrics - R8-SNAPSHOT + org.bstats + bstats-bukkit + 1.7 org.bukkit diff --git a/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java b/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java index dbe1ca56..be090a6c 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java +++ b/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java @@ -17,11 +17,9 @@ import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.HashMap; -import java.util.HashSet; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; -import java.util.Set; import java.util.logging.Level; import buscript.Buscript; @@ -105,11 +103,11 @@ import com.onarandombox.MultiverseCore.utils.WorldManager; import com.pneumaticraft.commandhandler.CommandHandler; import me.main__.util.SerializationConfig.NoSuchPropertyException; import me.main__.util.SerializationConfig.SerializationConfig; +import org.bstats.bukkit.Metrics; import org.bukkit.ChatColor; import org.bukkit.Difficulty; import org.bukkit.GameMode; import org.bukkit.Location; -import org.bukkit.World.Environment; import org.bukkit.command.Command; import org.bukkit.command.CommandSender; import org.bukkit.configuration.Configuration; @@ -122,7 +120,6 @@ import org.bukkit.plugin.PluginDescriptionFile; import org.bukkit.plugin.PluginManager; import org.bukkit.plugin.java.JavaPlugin; import org.bukkit.plugin.java.JavaPluginLoader; -import org.mcstats.Metrics; /** * The implementation of the Multiverse-{@link Core}. @@ -355,95 +352,48 @@ public class MultiverseCore extends JavaPlugin implements MVPlugin, Core { buscript.setScriptVariable("multiverse", this); } - /** - * Plotter for Environment-Values. - */ - private static final class EnvironmentPlotter extends Metrics.Plotter { - private MultiverseCore core; - private final Environment env; - - public EnvironmentPlotter(MultiverseCore core, Environment env) { - super(envToString(env)); - this.core = core; - this.env = env; - } - - private static String envToString(Environment env) { - return new StringBuilder().append(env.name().toUpperCase().charAt(0)) - .append(env.name().toLowerCase().substring(1)).toString(); - } - - @Override - public int getValue() { - int count = 0; - for (MultiverseWorld w : core.getMVWorldManager().getMVWorlds()) - if (w.getEnvironment() == env) - count++; - core.log(Level.FINE, String.format("Tracking %d worlds of type %s", count, env)); - return count; - } - } - - /** - * Plotter for Generator-Values. - */ - private static final class GeneratorPlotter extends Metrics.Plotter { - private MultiverseCore core; - private final String gen; - - public GeneratorPlotter(MultiverseCore core, String gen) { - super(gen); - this.core = core; - this.gen = gen; - } - - @Override - public int getValue() { - int count = 0; - for (MultiverseWorld w : core.getMVWorldManager().getMVWorlds()) - if (gen.equals(w.getGenerator())) - count++; - core.log(Level.FINE, String.format("Tracking %d worlds of type %s", count, gen)); - return count; - } - } - private void setupMetrics() { try { - Metrics m = new Metrics(this); + Metrics metrics = new Metrics(this, 7765); - Metrics.Graph envGraph = m.createGraph("Worlds by environment"); - for (Environment env : Environment.values()) - envGraph.addPlotter(new EnvironmentPlotter(this, env)); - - Metrics.Graph loadedWorldsGraph = m.createGraph("Worlds by environment"); - loadedWorldsGraph.addPlotter(new Metrics.Plotter("Loaded worlds") { - @Override - public int getValue() { - return getMVWorldManager().getMVWorlds().size(); + metrics.addCustomChart(new Metrics.AdvancedPie("custom_generators", () -> { + Map map = new HashMap<>(); + for (MultiverseWorld w : this.getMVWorldManager().getMVWorlds()) { + if (w.getGenerator() != null && !w.getGenerator().equalsIgnoreCase("null")) { + map.putIfAbsent(w.getGenerator(), 0); + map.put(w.getGenerator(), map.get(w.getGenerator()) + 1); + } } - }); - loadedWorldsGraph.addPlotter(new Metrics.Plotter("Total number of worlds") { - @Override - public int getValue() { - return getMVWorldManager().getMVWorlds().size() - + getMVWorldManager().getUnloadedWorlds().size(); + + return map; + })); + + metrics.addCustomChart(new Metrics.AdvancedPie("environments", () -> { + Map map = new HashMap<>(); + for (MultiverseWorld w : this.getMVWorldManager().getMVWorlds()) { + StringBuilder environment = new StringBuilder(); + String[] environmentArray = w.getEnvironment().name().split("_"); + + for (int i = 0; i < environmentArray.length; i++) { + environment.append(environmentArray[i].substring(0, 1).toUpperCase()); + environment.append(environmentArray[i].substring(1).toLowerCase()); + if (i != environmentArray.length - 1) environment.append(" "); + } + + String e = environment.toString(); + map.putIfAbsent(e, 0); + map.put(e, map.get(e) + 1); } - }); - Set gens = new HashSet(); - for (MultiverseWorld w : this.getMVWorldManager().getMVWorlds()) - gens.add(w.getGenerator()); - gens.remove(null); - gens.remove("null"); - Metrics.Graph genGraph = m.createGraph("Custom Generators"); - for (String gen : gens) - genGraph.addPlotter(new GeneratorPlotter(this, gen)); + // TODO: add Worlds vs Loaded Worlds once bStats adds support for multi-line charts - m.start(); - log(Level.FINE, "Metrics have run!"); + return map; + })); + + log(Level.FINE, "Metrics were set up!"); } catch (Exception e) { - log(Level.WARNING, "There was an issue while enabling metrics: " + e.getMessage()); + log(Level.WARNING, "There was an issue while enabling metrics:"); + e.printStackTrace(); } } From 1cbe901e4df8e8c66a558b9681008b96a234180c Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sat, 6 Jun 2020 13:38:03 -0400 Subject: [PATCH 006/109] lead dev should be the first author listed --- src/main/resources/plugin.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/resources/plugin.yml b/src/main/resources/plugin.yml index d65a3779..5a4dfeba 100644 --- a/src/main/resources/plugin.yml +++ b/src/main/resources/plugin.yml @@ -1,6 +1,6 @@ name: Multiverse-Core main: com.onarandombox.MultiverseCore.MultiverseCore -authors: ['Rigby', 'fernferret', 'lithium3141', 'main--', 'dumptruckman'] +authors: ['dumptruckman', 'Rigby', 'fernferret', 'lithium3141', 'main--'] website: 'https://dev.bukkit.org/projects/multiverse-core' api-version: 1.13 version: maven-version-number From 8983a0c0244acc53a7241604cd341562fae91a5f Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sun, 7 Jun 2020 19:31:51 -0400 Subject: [PATCH 007/109] add vault as softdepend --- src/main/resources/plugin.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/src/main/resources/plugin.yml b/src/main/resources/plugin.yml index 5a4dfeba..5359af21 100644 --- a/src/main/resources/plugin.yml +++ b/src/main/resources/plugin.yml @@ -2,6 +2,7 @@ name: Multiverse-Core main: com.onarandombox.MultiverseCore.MultiverseCore authors: ['dumptruckman', 'Rigby', 'fernferret', 'lithium3141', 'main--'] website: 'https://dev.bukkit.org/projects/multiverse-core' +softdepend: ['Vault'] api-version: 1.13 version: maven-version-number commands: From 268c4982c3b392784297725dba1160710797be00 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Fri, 12 Jun 2020 23:50:17 -0400 Subject: [PATCH 008/109] update metric implementations --- .../MultiverseCore/MultiverseCore.java | 27 +++++++------------ 1 file changed, 9 insertions(+), 18 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java b/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java index be090a6c..52b9074a 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java +++ b/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java @@ -103,6 +103,7 @@ import com.onarandombox.MultiverseCore.utils.WorldManager; import com.pneumaticraft.commandhandler.CommandHandler; import me.main__.util.SerializationConfig.NoSuchPropertyException; import me.main__.util.SerializationConfig.SerializationConfig; +import org.apache.commons.lang.StringUtils; import org.bstats.bukkit.Metrics; import org.bukkit.ChatColor; import org.bukkit.Difficulty; @@ -359,10 +360,9 @@ public class MultiverseCore extends JavaPlugin implements MVPlugin, Core { metrics.addCustomChart(new Metrics.AdvancedPie("custom_generators", () -> { Map map = new HashMap<>(); for (MultiverseWorld w : this.getMVWorldManager().getMVWorlds()) { - if (w.getGenerator() != null && !w.getGenerator().equalsIgnoreCase("null")) { - map.putIfAbsent(w.getGenerator(), 0); - map.put(w.getGenerator(), map.get(w.getGenerator()) + 1); - } + String gen = w.getGenerator() != null ? w.getGenerator() : "N/A"; + map.putIfAbsent(gen, 0); + map.put(gen, map.get(gen) + 1); } return map; @@ -371,25 +371,16 @@ public class MultiverseCore extends JavaPlugin implements MVPlugin, Core { metrics.addCustomChart(new Metrics.AdvancedPie("environments", () -> { Map map = new HashMap<>(); for (MultiverseWorld w : this.getMVWorldManager().getMVWorlds()) { - StringBuilder environment = new StringBuilder(); - String[] environmentArray = w.getEnvironment().name().split("_"); - - for (int i = 0; i < environmentArray.length; i++) { - environment.append(environmentArray[i].substring(0, 1).toUpperCase()); - environment.append(environmentArray[i].substring(1).toLowerCase()); - if (i != environmentArray.length - 1) environment.append(" "); - } - - String e = environment.toString(); - map.putIfAbsent(e, 0); - map.put(e, map.get(e) + 1); + String env = w.getEnvironment().name().replace('_', ' '); + env = StringUtils.capitalize(env.toLowerCase()); + map.putIfAbsent(env, 0); + map.put(env, map.get(env) + 1); } - // TODO: add Worlds vs Loaded Worlds once bStats adds support for multi-line charts - return map; })); + // TODO: add Worlds vs Loaded Worlds once bStats adds support for multi-line charts log(Level.FINE, "Metrics were set up!"); } catch (Exception e) { log(Level.WARNING, "There was an issue while enabling metrics:"); From 04c65cc59e5949cb2138654e4f7482ba081883ef Mon Sep 17 00:00:00 2001 From: Jeremy Wood Date: Sat, 13 Jun 2020 00:51:18 -0400 Subject: [PATCH 009/109] Cleanup new metrics implementation. (#2286) * Refactor metrics initialization into its own class. * Simplify the creation of metrics. * Clean up new metrics. * Refactor out duplicate metrics code. --- .../MultiverseCore/MultiverseCore.java | 42 +---------- .../utils/metrics/MetricsConfigurator.java | 71 +++++++++++++++++++ .../utils/metrics/MetricsHelper.java | 26 +++++++ 3 files changed, 100 insertions(+), 39 deletions(-) create mode 100644 src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java create mode 100644 src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsHelper.java diff --git a/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java b/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java index 52b9074a..772a4c72 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java +++ b/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java @@ -32,7 +32,6 @@ import com.onarandombox.MultiverseCore.api.MVPlugin; import com.onarandombox.MultiverseCore.api.MVWorldManager; import com.onarandombox.MultiverseCore.api.MultiverseCoreConfig; import com.onarandombox.MultiverseCore.api.MultiverseMessaging; -import com.onarandombox.MultiverseCore.api.MultiverseWorld; import com.onarandombox.MultiverseCore.api.SafeTTeleporter; import com.onarandombox.MultiverseCore.commands.AnchorCommand; import com.onarandombox.MultiverseCore.commands.CheckCommand; @@ -94,6 +93,7 @@ import com.onarandombox.MultiverseCore.utils.MVMessaging; import com.onarandombox.MultiverseCore.utils.MVPermissions; import com.onarandombox.MultiverseCore.utils.MVPlayerSession; import com.onarandombox.MultiverseCore.utils.MaterialConverter; +import com.onarandombox.MultiverseCore.utils.metrics.MetricsConfigurator; import com.onarandombox.MultiverseCore.utils.SimpleBlockSafety; import com.onarandombox.MultiverseCore.utils.SimpleLocationManipulation; import com.onarandombox.MultiverseCore.utils.SimpleSafeTTeleporter; @@ -103,8 +103,6 @@ import com.onarandombox.MultiverseCore.utils.WorldManager; import com.pneumaticraft.commandhandler.CommandHandler; import me.main__.util.SerializationConfig.NoSuchPropertyException; import me.main__.util.SerializationConfig.SerializationConfig; -import org.apache.commons.lang.StringUtils; -import org.bstats.bukkit.Metrics; import org.bukkit.ChatColor; import org.bukkit.Difficulty; import org.bukkit.GameMode; @@ -333,7 +331,8 @@ public class MultiverseCore extends JavaPlugin implements MVPlugin, Core { getServer().getPluginManager().registerEvents(this.chatListener, this); this.initializeBuscript(); - this.setupMetrics(); + + MetricsConfigurator.configureMetrics(this); // Output a little snippet to show it's enabled. Logging.config("Version %s (API v%s) Enabled - By %s", this.getDescription().getVersion(), PROTOCOL, getAuthors()); @@ -353,41 +352,6 @@ public class MultiverseCore extends JavaPlugin implements MVPlugin, Core { buscript.setScriptVariable("multiverse", this); } - private void setupMetrics() { - try { - Metrics metrics = new Metrics(this, 7765); - - metrics.addCustomChart(new Metrics.AdvancedPie("custom_generators", () -> { - Map map = new HashMap<>(); - for (MultiverseWorld w : this.getMVWorldManager().getMVWorlds()) { - String gen = w.getGenerator() != null ? w.getGenerator() : "N/A"; - map.putIfAbsent(gen, 0); - map.put(gen, map.get(gen) + 1); - } - - return map; - })); - - metrics.addCustomChart(new Metrics.AdvancedPie("environments", () -> { - Map map = new HashMap<>(); - for (MultiverseWorld w : this.getMVWorldManager().getMVWorlds()) { - String env = w.getEnvironment().name().replace('_', ' '); - env = StringUtils.capitalize(env.toLowerCase()); - map.putIfAbsent(env, 0); - map.put(env, map.get(env) + 1); - } - - return map; - })); - - // TODO: add Worlds vs Loaded Worlds once bStats adds support for multi-line charts - log(Level.FINE, "Metrics were set up!"); - } catch (Exception e) { - log(Level.WARNING, "There was an issue while enabling metrics:"); - e.printStackTrace(); - } - } - private void initializeDestinationFactory() { this.destFactory = new DestinationFactory(this); this.destFactory.registerDestinationType(WorldDestination.class, ""); diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java new file mode 100644 index 00000000..30cc0353 --- /dev/null +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java @@ -0,0 +1,71 @@ +package com.onarandombox.MultiverseCore.utils.metrics; + +import java.util.Map; +import java.util.function.Consumer; + +import com.dumptruckman.minecraft.util.Logging; +import com.onarandombox.MultiverseCore.MultiverseCore; +import com.onarandombox.MultiverseCore.api.MultiverseWorld; +import org.apache.commons.lang.StringUtils; +import org.bstats.bukkit.Metrics; +import org.bukkit.World; + +public class MetricsConfigurator { + + private static final int PLUGIN_ID = 7765; + private static final String NO_GENERATOR_NAME = "N/A"; + + public static void configureMetrics(MultiverseCore plugin) { + MetricsConfigurator configurator = new MetricsConfigurator(plugin); + configurator.initMetrics(); + } + + private final MultiverseCore plugin; + private final Metrics metrics; + + private MetricsConfigurator(MultiverseCore plugin) { + this.plugin = plugin; + this.metrics = new Metrics(plugin, PLUGIN_ID); + } + + private void initMetrics() { + try { + addCustomGeneratorsMetric(); + createEnvironmentsMetric(); + + Logging.fine("Metrics enabled."); + } catch (Exception e) { + Logging.warning("There was an issue while enabling metrics:"); + e.printStackTrace(); + } + } + + private void addCustomGeneratorsMetric() { + addAdvancedPieMetric("custom_generators", map -> { + for (MultiverseWorld w : plugin.getMVWorldManager().getMVWorlds()) { + MetricsHelper.incrementCount(map, getGeneratorName(w)); + } + }); + } + + private String getGeneratorName(MultiverseWorld world) { + return world.getGenerator() != null ? world.getGenerator() : NO_GENERATOR_NAME; + } + + private void createEnvironmentsMetric() { + addAdvancedPieMetric("environments", map -> { + for (MultiverseWorld w : plugin.getMVWorldManager().getMVWorlds()) { + MetricsHelper.incrementCount(map, titleCaseEnv(w.getEnvironment())); + } + }); + } + + private String titleCaseEnv(World.Environment env) { + String envName = env.name().replaceAll("_+", " "); + return StringUtils.capitalize(envName.toLowerCase()); + } + + private void addAdvancedPieMetric(String chartId, Consumer> metricsFunc) { + metrics.addCustomChart(MetricsHelper.createAdvancedPieChart(chartId, metricsFunc)); + } +} diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsHelper.java b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsHelper.java new file mode 100644 index 00000000..b7a92a5e --- /dev/null +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsHelper.java @@ -0,0 +1,26 @@ +package com.onarandombox.MultiverseCore.utils.metrics; + +import java.util.HashMap; +import java.util.Map; +import java.util.function.Consumer; + +import org.bstats.bukkit.Metrics; + +enum MetricsHelper { + ; + + /** + * Adds one to the value in the given map with the given key. If the key does not exist in the map, it will be added with a value of 1. + */ + static void incrementCount(Map map, String key) { + Integer count = map.getOrDefault(key, 0); + map.put(key, count + 1); + } + + static Metrics.AdvancedPie createAdvancedPieChart(String chartId, Consumer> metricsFunc) { + Map map = new HashMap<>(); + metricsFunc.accept(map); + return new Metrics.AdvancedPie(chartId, () -> map); + } + +} From 582d6bef1aea750e1f802e45c13102e13c4fbc6f Mon Sep 17 00:00:00 2001 From: Jeremy Wood Date: Sat, 13 Jun 2020 01:17:00 -0400 Subject: [PATCH 010/109] Readd world count metric as multiline chart (for future use). --- .../utils/metrics/MetricsConfigurator.java | 31 ++++++++++++++++--- .../utils/metrics/MetricsHelper.java | 6 ++++ 2 files changed, 33 insertions(+), 4 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java index 30cc0353..25aaf009 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java @@ -1,10 +1,12 @@ package com.onarandombox.MultiverseCore.utils.metrics; +import java.util.Collection; import java.util.Map; import java.util.function.Consumer; import com.dumptruckman.minecraft.util.Logging; import com.onarandombox.MultiverseCore.MultiverseCore; +import com.onarandombox.MultiverseCore.api.MVWorldManager; import com.onarandombox.MultiverseCore.api.MultiverseWorld; import org.apache.commons.lang.StringUtils; import org.bstats.bukkit.Metrics; @@ -28,10 +30,19 @@ public class MetricsConfigurator { this.metrics = new Metrics(plugin, PLUGIN_ID); } + private MVWorldManager getWorldManager() { + return plugin.getMVWorldManager(); + } + + private Collection getMVWorlds() { + return getWorldManager().getMVWorlds(); + } + private void initMetrics() { try { addCustomGeneratorsMetric(); - createEnvironmentsMetric(); + addEnvironmentsMetric(); + addWorldCountMetric(); Logging.fine("Metrics enabled."); } catch (Exception e) { @@ -42,7 +53,7 @@ public class MetricsConfigurator { private void addCustomGeneratorsMetric() { addAdvancedPieMetric("custom_generators", map -> { - for (MultiverseWorld w : plugin.getMVWorldManager().getMVWorlds()) { + for (MultiverseWorld w : getMVWorlds()) { MetricsHelper.incrementCount(map, getGeneratorName(w)); } }); @@ -52,9 +63,9 @@ public class MetricsConfigurator { return world.getGenerator() != null ? world.getGenerator() : NO_GENERATOR_NAME; } - private void createEnvironmentsMetric() { + private void addEnvironmentsMetric() { addAdvancedPieMetric("environments", map -> { - for (MultiverseWorld w : plugin.getMVWorldManager().getMVWorlds()) { + for (MultiverseWorld w : getMVWorlds()) { MetricsHelper.incrementCount(map, titleCaseEnv(w.getEnvironment())); } }); @@ -65,7 +76,19 @@ public class MetricsConfigurator { return StringUtils.capitalize(envName.toLowerCase()); } + private void addWorldCountMetric() { + addMultiLineMetric("world_count", map -> { + int loadedWorldsCount = getMVWorlds().size(); + map.put("Loaded worlds", loadedWorldsCount); + map.put("Total number of worlds", loadedWorldsCount + getWorldManager().getUnloadedWorlds().size()); + }); + } + private void addAdvancedPieMetric(String chartId, Consumer> metricsFunc) { metrics.addCustomChart(MetricsHelper.createAdvancedPieChart(chartId, metricsFunc)); } + + private void addMultiLineMetric(String chartId, Consumer> metricsFunc) { + metrics.addCustomChart(MetricsHelper.createMultiLineChart(chartId, metricsFunc)); + } } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsHelper.java b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsHelper.java index b7a92a5e..23fb6eba 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsHelper.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsHelper.java @@ -23,4 +23,10 @@ enum MetricsHelper { return new Metrics.AdvancedPie(chartId, () -> map); } + static Metrics.MultiLineChart createMultiLineChart(String chartId, Consumer> metricsFunc) { + Map map = new HashMap<>(); + metricsFunc.accept(map); + return new Metrics.MultiLineChart(chartId, () -> map); + } + } From b3f23278b1323fd204b59c6043ad5220397af9fc Mon Sep 17 00:00:00 2001 From: Jeremy Wood Date: Sat, 13 Jun 2020 01:33:22 -0400 Subject: [PATCH 011/109] Yay for tests that use method names in strings. -.- --- .../com/onarandombox/MultiverseCore/MultiverseCore.java | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java b/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java index 772a4c72..43820a5a 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java +++ b/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java @@ -331,8 +331,7 @@ public class MultiverseCore extends JavaPlugin implements MVPlugin, Core { getServer().getPluginManager().registerEvents(this.chatListener, this); this.initializeBuscript(); - - MetricsConfigurator.configureMetrics(this); + this.setupMetrics(); // Output a little snippet to show it's enabled. Logging.config("Version %s (API v%s) Enabled - By %s", this.getDescription().getVersion(), PROTOCOL, getAuthors()); @@ -343,6 +342,10 @@ public class MultiverseCore extends JavaPlugin implements MVPlugin, Core { } } + private void setupMetrics() { + MetricsConfigurator.configureMetrics(this); + } + /** * Initializes the buscript javascript library. */ From f570c813663d7017b3be2c8704ab40d76d4ecf76 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Fri, 5 Jun 2020 20:00:00 -0400 Subject: [PATCH 012/109] update version command --- .../commands/VersionCommand.java | 123 +++++++++--------- .../utils/webpaste/HastebinPasteService.java | 1 - 2 files changed, 62 insertions(+), 62 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java index b2ac51e4..146d91ee 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java @@ -24,9 +24,12 @@ import org.bukkit.command.ConsoleCommandSender; import org.bukkit.entity.Player; import org.bukkit.permissions.PermissionDefault; import org.bukkit.scheduler.BukkitRunnable; -import org.bukkit.util.StringUtil; -import java.io.*; +import java.io.BufferedReader; +import java.io.File; +import java.io.FileNotFoundException; +import java.io.FileReader; +import java.io.IOException; import java.util.HashMap; import java.util.List; import java.util.Map; @@ -50,79 +53,74 @@ public class VersionCommand extends MultiverseCommand { } private String getLegacyString() { - StringBuilder legacyFile = new StringBuilder(); - legacyFile.append("[Multiverse-Core] Multiverse-Core Version: ").append(this.plugin.getDescription().getVersion()).append('\n'); - legacyFile.append("[Multiverse-Core] Bukkit Version: ").append(this.plugin.getServer().getVersion()).append('\n'); - legacyFile.append("[Multiverse-Core] Loaded Worlds: ").append(this.plugin.getMVWorldManager().getMVWorlds()).append('\n'); - legacyFile.append("[Multiverse-Core] Multiverse Plugins Loaded: ").append(this.plugin.getPluginCount()).append('\n'); - legacyFile.append("[Multiverse-Core] Economy being used: ").append(plugin.getEconomist().getEconomyName()).append('\n'); - legacyFile.append("[Multiverse-Core] Permissions Plugin: ").append(this.plugin.getMVPerms().getType()).append('\n'); - legacyFile.append("[Multiverse-Core] Dumping Config Values: (version ") - .append(this.plugin.getMVConfig().getVersion()).append(")").append('\n'); - legacyFile.append("[Multiverse-Core] messagecooldown: ").append(plugin.getMessaging().getCooldown()).append('\n'); - legacyFile.append("[Multiverse-Core] teleportcooldown: ").append(plugin.getMVConfig().getTeleportCooldown()).append('\n'); - legacyFile.append("[Multiverse-Core] worldnameprefix: ").append(plugin.getMVConfig().getPrefixChat()).append('\n'); - legacyFile.append("[Multiverse-Core] worldnameprefixFormat: ").append(plugin.getMVConfig().getPrefixChatFormat()).append('\n'); - legacyFile.append("[Multiverse-Core] enforceaccess: ").append(plugin.getMVConfig().getEnforceAccess()).append('\n'); - legacyFile.append("[Multiverse-Core] displaypermerrors: ").append(plugin.getMVConfig().getDisplayPermErrors()).append('\n'); - legacyFile.append("[Multiverse-Core] teleportintercept: ").append(plugin.getMVConfig().getTeleportIntercept()).append('\n'); - legacyFile.append("[Multiverse-Core] firstspawnoverride: ").append(plugin.getMVConfig().getFirstSpawnOverride()).append('\n'); - legacyFile.append("[Multiverse-Core] firstspawnworld: ").append(plugin.getMVConfig().getFirstSpawnWorld()).append('\n'); - legacyFile.append("[Multiverse-Core] debug: ").append(plugin.getMVConfig().getGlobalDebug()).append('\n'); - legacyFile.append("[Multiverse-Core] Special Code: FRN002").append('\n'); - return legacyFile.toString(); + return "[Multiverse-Core] Multiverse-Core Version: " + this.plugin.getDescription().getVersion() + System.lineSeparator() + + "[Multiverse-Core] Bukkit Version: " + this.plugin.getServer().getVersion() + System.lineSeparator() + + "[Multiverse-Core] Loaded Worlds: " + this.plugin.getMVWorldManager().getMVWorlds() + System.lineSeparator() + + "[Multiverse-Core] Multiverse Plugins Loaded: " + this.plugin.getPluginCount() + System.lineSeparator() + + "[Multiverse-Core] Economy being used: " + plugin.getEconomist().getEconomyName() + System.lineSeparator() + + "[Multiverse-Core] Permissions Plugin: " + this.plugin.getMVPerms().getType() + System.lineSeparator() + + "[Multiverse-Core] Dumping Config Values: (version " + this.plugin.getMVConfig().getVersion() + ")" + System.lineSeparator() + + "[Multiverse-Core] messagecooldown: " + plugin.getMessaging().getCooldown() + System.lineSeparator() + + "[Multiverse-Core] teleportcooldown: " + plugin.getMVConfig().getTeleportCooldown() + System.lineSeparator() + + "[Multiverse-Core] worldnameprefix: " + plugin.getMVConfig().getPrefixChat() + System.lineSeparator() + + "[Multiverse-Core] worldnameprefixFormat: " + plugin.getMVConfig().getPrefixChatFormat() + System.lineSeparator() + + "[Multiverse-Core] enforceaccess: " + plugin.getMVConfig().getEnforceAccess() + System.lineSeparator() + + "[Multiverse-Core] displaypermerrors: " + plugin.getMVConfig().getDisplayPermErrors() + System.lineSeparator() + + "[Multiverse-Core] teleportintercept: " + plugin.getMVConfig().getTeleportIntercept() + System.lineSeparator() + + "[Multiverse-Core] firstspawnoverride: " + plugin.getMVConfig().getFirstSpawnOverride() + System.lineSeparator() + + "[Multiverse-Core] firstspawnworld: " + plugin.getMVConfig().getFirstSpawnWorld() + System.lineSeparator() + + "[Multiverse-Core] debug: " + plugin.getMVConfig().getGlobalDebug() + System.lineSeparator() + + "[Multiverse-Core] Special Code: FRN002" + System.lineSeparator(); } private String getMarkdownString() { - StringBuilder markdownString = new StringBuilder(); - markdownString.append("# Multiverse-Core\n"); - markdownString.append("## Overview\n"); - markdownString.append("| Name | Value |\n"); - markdownString.append("| --- | --- |\n"); - markdownString.append("| Multiverse-Core Version | `").append(this.plugin.getDescription().getVersion()).append("` |\n"); - markdownString.append("| Bukkit Version | `").append(this.plugin.getServer().getVersion()).append("` |\n"); - //markdownString.append("| Loaded Worlds | `").append(this.plugin.getMVWorldManager().getMVWorlds()).append("` |\n"); - markdownString.append("| Multiverse Plugins Loaded | `").append(this.plugin.getPluginCount()).append("` |\n"); - markdownString.append("| Economy being used | `").append(plugin.getEconomist().getEconomyName()).append("` |\n"); - markdownString.append("| Permissions Plugin | `").append(this.plugin.getMVPerms().getType()).append("` |\n"); - markdownString.append("## Parsed Config\n"); - markdownString.append("These are what Multiverse thought the in-memory values of the config were.\n\n"); - markdownString.append("| Config Key | Value |\n"); - markdownString.append("| --- | --- |\n"); - markdownString.append("| version | `").append(this.plugin.getMVConfig().getVersion()).append("` |\n"); - markdownString.append("| messagecooldown | `").append(plugin.getMessaging().getCooldown()).append("` |\n"); - markdownString.append("| teleportcooldown | `").append(plugin.getMVConfig().getTeleportCooldown()).append("` |\n"); - markdownString.append("| worldnameprefix | `").append(plugin.getMVConfig().getPrefixChat()).append("` |\n"); - markdownString.append("| worldnameprefixFormat | `").append(plugin.getMVConfig().getPrefixChatFormat()).append("` |\n"); - markdownString.append("| enforceaccess | `").append(plugin.getMVConfig().getEnforceAccess()).append("` |\n"); - markdownString.append("| displaypermerrors | `").append(plugin.getMVConfig().getDisplayPermErrors()).append("` |\n"); - markdownString.append("| teleportintercept | `").append(plugin.getMVConfig().getTeleportIntercept()).append("` |\n"); - markdownString.append("| firstspawnoverride | `").append(plugin.getMVConfig().getFirstSpawnOverride()).append("` |\n"); - markdownString.append("| firstspawnworld | `").append(plugin.getMVConfig().getFirstSpawnWorld()).append("` |\n"); - markdownString.append("| debug | `").append(plugin.getMVConfig().getGlobalDebug()).append("` |\n"); - return markdownString.toString(); + return "# Multiverse-Core" + System.lineSeparator() + + "## Overview" + System.lineSeparator() + + "| Name | Value |" + System.lineSeparator() + + "| --- | --- |" + System.lineSeparator() + + "| Multiverse-Core Version | `" + this.plugin.getDescription().getVersion() + "` |" + System.lineSeparator() + + "| Bukkit Version | `" + this.plugin.getServer().getVersion() + "` |" + System.lineSeparator() + + //"| Loaded Worlds | `" + this.plugin.getMVWorldManager().getMVWorlds() + "` |" + System.lineSeparator() + + "| Multiverse Plugins Loaded | `" + this.plugin.getPluginCount() + "` |" + System.lineSeparator() + + "| Economy being used | `" + plugin.getEconomist().getEconomyName() + "` |" + System.lineSeparator() + + "| Permissions Plugin | `" + this.plugin.getMVPerms().getType() + "` |" + System.lineSeparator() + + "## Parsed Config" + System.lineSeparator() + + "These are what Multiverse thought the in-memory values of the config were." + System.lineSeparator() + System.lineSeparator() + + "| Config Key | Value |" + System.lineSeparator() + + "| --- | --- |" + System.lineSeparator() + + "| version | `" + this.plugin.getMVConfig().getVersion() + "` |" + System.lineSeparator() + + "| messagecooldown | `" + plugin.getMessaging().getCooldown() + "` |" + System.lineSeparator() + + "| teleportcooldown | `" + plugin.getMVConfig().getTeleportCooldown() + "` |" + System.lineSeparator() + + "| worldnameprefix | `" + plugin.getMVConfig().getPrefixChat() + "` |" + System.lineSeparator() + + "| worldnameprefixFormat | `" + plugin.getMVConfig().getPrefixChatFormat() + "` |" + System.lineSeparator() + + "| enforceaccess | `" + plugin.getMVConfig().getEnforceAccess() + "` |" + System.lineSeparator() + + "| displaypermerrors | `" + plugin.getMVConfig().getDisplayPermErrors() + "` |" + System.lineSeparator() + + "| teleportintercept | `" + plugin.getMVConfig().getTeleportIntercept() + "` |" + System.lineSeparator() + + "| firstspawnoverride | `" + plugin.getMVConfig().getFirstSpawnOverride() + "` |" + System.lineSeparator() + + "| firstspawnworld | `" + plugin.getMVConfig().getFirstSpawnWorld() + "` |" + System.lineSeparator() + + "| debug | `" + plugin.getMVConfig().getGlobalDebug() + "` |" + System.lineSeparator(); } private String readFile(final String filename) { - String result; + StringBuilder result; try { FileReader reader = new FileReader(filename); BufferedReader bufferedReader = new BufferedReader(reader); String line; - result = ""; + result = new StringBuilder(); while ((line = bufferedReader.readLine()) != null) { - result += line + '\n'; + result.append(line).append(System.lineSeparator()); } } catch (FileNotFoundException e) { Logging.severe("Unable to find %s. Here's the traceback: %s", filename, e.getMessage()); e.printStackTrace(); - result = String.format("ERROR: Could not load: %s", filename); + result = new StringBuilder(String.format("ERROR: Could not load: %s", filename)); } catch (IOException e) { Logging.severe("Something bad happend when reading %s. Here's the traceback: %s", filename, e.getMessage()); e.printStackTrace(); - result = String.format("ERROR: Could not load: %s", filename); + result = new StringBuilder(String.format("ERROR: Could not load: %s", filename)); } - return result; + return result.toString(); } private Map getVersionFiles() { @@ -155,13 +153,13 @@ public class VersionCommand extends MultiverseCommand { String versionInfo = versionEvent.getVersionInfo(); if (CommandHandler.hasFlag("--include-plugin-list", args)) { - versionInfo = versionInfo + "\nPlugins: " + getPluginList(); + versionInfo = versionInfo + System.lineSeparator() + "Plugins: " + getPluginList(); } final String data = versionInfo; // log to console - String[] lines = data.split("\n"); + String[] lines = data.split(System.lineSeparator()); for (String line : lines) { if (!line.isEmpty()) { Logging.info(line); @@ -177,7 +175,7 @@ public class VersionCommand extends MultiverseCommand { // private post to pastebin pasteUrl = postToService(PasteServiceType.PASTEBIN, true, data, files); } else if (CommandHandler.hasFlag("-h", args)) { - // private post to pastebin + // private post to hastebin pasteUrl = postToService(PasteServiceType.HASTEBIN, true, data, files); } else { return; @@ -216,8 +214,11 @@ public class VersionCommand extends MultiverseCommand { } return SHORTENER.shorten(result); } catch (PasteFailedException e) { - System.out.print(e); - return "Error posting to service"; + e.printStackTrace(); + return "Error posting to service."; + } catch (NullPointerException e) { + e.printStackTrace(); + return "That service isn't supported yet."; } } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java index 69438cfd..590c521e 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java @@ -1,6 +1,5 @@ package com.onarandombox.MultiverseCore.utils.webpaste; -import com.google.gson.JsonElement; import com.google.gson.JsonParser; import java.io.BufferedReader; From eb91eefc80ddf3b267e2813313740aa46e3cb156 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Fri, 5 Jun 2020 21:22:14 -0400 Subject: [PATCH 013/109] fix BitlyURLShortener --- .../MultiverseCore/utils/webpaste/BitlyURLShortener.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java index e700c2e3..ea52cbcc 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java @@ -23,7 +23,7 @@ public class BitlyURLShortener extends HttpAPIClient implements URLShortener { public String shorten(String longUrl) { try { String result = this.exec(longUrl); - if (!result.startsWith("http://j.mp/")) // ... then it's failed :/ + if (!result.startsWith("https://j.mp/")) // ... then it's failed :/ throw new IOException(result); return result; } catch (IOException e) { From d69c492577eaebbd9fff7f7958528125fd6f5436 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Fri, 5 Jun 2020 22:09:08 -0400 Subject: [PATCH 014/109] cleanup GitHub and Pastebin paste services --- .../utils/webpaste/GithubPasteService.java | 6 +++--- .../utils/webpaste/PastebinPasteService.java | 11 +++++------ 2 files changed, 8 insertions(+), 9 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GithubPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GithubPasteService.java index 6d840969..fe7fafc4 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GithubPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GithubPasteService.java @@ -49,7 +49,9 @@ public class GithubPasteService implements PasteService { public URL getPostURL() { try { return new URL("https://api.github.com/gists"); - //return new URL("http://jsonplaceholder.typicode.com/posts"); + + // the following can be used for testing purposes + // return new URL("http://jsonplaceholder.typicode.com/posts"); } catch (MalformedURLException e) { return null; // should never hit here } @@ -68,8 +70,6 @@ public class GithubPasteService implements PasteService { rd = new BufferedReader(new InputStreamReader(conn.getInputStream())); String line; - String pastieUrl = ""; - //Pattern pastiePattern = this.getURLMatchingPattern(); StringBuilder responseString = new StringBuilder(); while ((line = rd.readLine()) != null) { diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java index 3f06f612..7aeba797 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java @@ -40,12 +40,11 @@ public class PastebinPasteService implements PasteService { @Override public String encodeData(String data) { try { - String encData = URLEncoder.encode("api_dev_key", "UTF-8") + "=" + URLEncoder.encode("d61d68d31e8e0392b59b50b277411c71", "UTF-8"); - encData += "&" + URLEncoder.encode("api_option", "UTF-8") + "=" + URLEncoder.encode("paste", "UTF-8"); - encData += "&" + URLEncoder.encode("api_paste_code", "UTF-8") + "=" + URLEncoder.encode(data, "UTF-8"); - encData += "&" + URLEncoder.encode("api_paste_private", "UTF-8") + "=" + URLEncoder.encode(this.isPrivate ? "1" : "0", "UTF-8"); - encData += "&" + URLEncoder.encode("api_paste_format", "UTF-8") + "=" + URLEncoder.encode("yaml", "UTF-8"); - return encData; + return URLEncoder.encode("api_dev_key", "UTF-8") + "=" + URLEncoder.encode("d61d68d31e8e0392b59b50b277411c71", "UTF-8") + + "&" + URLEncoder.encode("api_option", "UTF-8") + "=" + URLEncoder.encode("paste", "UTF-8") + + "&" + URLEncoder.encode("api_paste_code", "UTF-8") + "=" + URLEncoder.encode(data, "UTF-8") + + "&" + URLEncoder.encode("api_paste_private", "UTF-8") + "=" + URLEncoder.encode(this.isPrivate ? "1" : "0", "UTF-8") + + "&" + URLEncoder.encode("api_paste_format", "UTF-8") + "=" + URLEncoder.encode("yaml", "UTF-8"); } catch (UnsupportedEncodingException e) { return ""; // should never hit here } From e821611744208ec90a787ed380e8428c8a5632d7 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sat, 6 Jun 2020 20:05:33 -0400 Subject: [PATCH 015/109] fix pasting to hastebin --- .../utils/webpaste/HastebinPasteService.java | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java index 590c521e..407ec354 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java @@ -9,6 +9,7 @@ import java.io.OutputStreamWriter; import java.net.MalformedURLException; import java.net.URL; import java.net.URLConnection; +import java.nio.charset.StandardCharsets; import java.util.Map; /** @@ -43,14 +44,19 @@ public class HastebinPasteService implements PasteService { URLConnection conn = url.openConnection(); conn.setDoOutput(true); - wr = new OutputStreamWriter(conn.getOutputStream()); - rd = new BufferedReader(new InputStreamReader(conn.getInputStream())); + // hastebin needs a user-agent + conn.addRequestProperty("User-Agent", "placeholder"); + // this isn't required, but is technically correct + conn.addRequestProperty("Content-Type", "text/plain; charset=utf-8"); + wr = new OutputStreamWriter(conn.getOutputStream(), StandardCharsets.UTF_8.newEncoder()); wr.write(encodedData); wr.flush(); String line; StringBuilder responseString = new StringBuilder(); + // this has to be initialized AFTER the data has been flushed! + rd = new BufferedReader(new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8)); while ((line = rd.readLine()) != null) { responseString.append(line); } From 676c3a2e3d338c1789172f57edb804ac353ff057 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sat, 6 Jun 2020 20:16:42 -0400 Subject: [PATCH 016/109] make pasting more system agnostic --- ...ithubPasteService.java => GitHubPasteService.java} | 11 ++++++++--- .../MultiverseCore/utils/webpaste/HttpAPIClient.java | 5 +++-- .../utils/webpaste/PastebinPasteService.java | 10 ++++++++-- 3 files changed, 19 insertions(+), 7 deletions(-) rename src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/{GithubPasteService.java => GitHubPasteService.java} (88%) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GithubPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java similarity index 88% rename from src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GithubPasteService.java rename to src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java index fe7fafc4..f098e295 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GithubPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java @@ -11,6 +11,7 @@ import java.io.OutputStreamWriter; import java.net.MalformedURLException; import java.net.URL; import java.net.URLConnection; +import java.nio.charset.StandardCharsets; import java.util.HashMap; import java.util.Map; @@ -64,14 +65,18 @@ public class GithubPasteService implements PasteService { try { URLConnection conn = url.openConnection(); conn.setDoOutput(true); - wr = new OutputStreamWriter(conn.getOutputStream()); + + // this isn't required, but is technically correct + conn.addRequestProperty("Content-Type", "application/json; charset=utf-8"); + + wr = new OutputStreamWriter(conn.getOutputStream(), StandardCharsets.UTF_8); wr.write(encodedData); wr.flush(); - rd = new BufferedReader(new InputStreamReader(conn.getInputStream())); String line; StringBuilder responseString = new StringBuilder(); - + // this has to be initialized AFTER the data has been flushed! + rd = new BufferedReader(new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8)); while ((line = rd.readLine()) != null) { responseString.append(line); } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java index 55d69c5c..962fa356 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java @@ -5,6 +5,7 @@ import java.io.IOException; import java.io.InputStreamReader; import java.net.URL; import java.net.URLConnection; +import java.nio.charset.StandardCharsets; /** * HTTP API-client. @@ -32,11 +33,11 @@ public abstract class HttpAPIClient { StringBuilder ret = new StringBuilder(); BufferedReader reader = null; try { - reader = new BufferedReader(new InputStreamReader(conn.getInputStream())); + reader = new BufferedReader(new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8)); while (!reader.ready()); // wait until reader is ready, may not be necessary, SUPPRESS CHECKSTYLE: EmptyStatement while (reader.ready()) { - ret.append(reader.readLine()).append('\n'); + ret.append(reader.readLine()).append(System.lineSeparator()); } } finally { if (reader != null) { diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java index 7aeba797..c370c1d2 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java @@ -9,6 +9,7 @@ import java.net.MalformedURLException; import java.net.URL; import java.net.URLConnection; import java.net.URLEncoder; +import java.nio.charset.StandardCharsets; import java.util.Map; /** @@ -65,13 +66,18 @@ public class PastebinPasteService implements PasteService { try { URLConnection conn = url.openConnection(); conn.setDoOutput(true); - wr = new OutputStreamWriter(conn.getOutputStream()); + + // this isn't required, but is technically correct + conn.addRequestProperty("Content-Type", "application/x-www-form-urlencoded; charset=utf-8"); + + wr = new OutputStreamWriter(conn.getOutputStream(), StandardCharsets.UTF_8); wr.write(encodedData); wr.flush(); - rd = new BufferedReader(new InputStreamReader(conn.getInputStream())); String line; String pastebinUrl = ""; + // this has to be initialized AFTER the data has been flushed! + rd = new BufferedReader(new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8)); while ((line = rd.readLine()) != null) { pastebinUrl = line; } From e17e9c8ce9658ae5b88ceb272be319e3ab77fc38 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sat, 6 Jun 2020 20:17:05 -0400 Subject: [PATCH 017/109] rename GithubPasteService as GitHubPasteService --- .../MultiverseCore/utils/webpaste/GitHubPasteService.java | 4 ++-- .../MultiverseCore/utils/webpaste/PasteServiceFactory.java | 2 +- .../MultiverseCore/utils/webpaste/PasteServiceType.java | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java index f098e295..6c0b9890 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java @@ -15,11 +15,11 @@ import java.nio.charset.StandardCharsets; import java.util.HashMap; import java.util.Map; -public class GithubPasteService implements PasteService { +public class GitHubPasteService implements PasteService { private final boolean isPrivate; - public GithubPasteService(boolean isPrivate) { + public GitHubPasteService(boolean isPrivate) { this.isPrivate = isPrivate; } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceFactory.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceFactory.java index df4fb831..2275dc58 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceFactory.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceFactory.java @@ -19,7 +19,7 @@ public class PasteServiceFactory { case HASTEBIN: return new HastebinPasteService(); case GITHUB: - return new GithubPasteService(isPrivate); + return new GitHubPasteService(isPrivate); default: return null; } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceType.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceType.java index 0bd93e63..6b6d7a48 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceType.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceType.java @@ -16,7 +16,7 @@ public enum PasteServiceType { */ HASTEBIN, /** - * @see GithubPasteService + * @see GitHubPasteService */ GITHUB } From 343695e23e0200f7cb12b781247a9fbdfc6feb07 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sat, 6 Jun 2020 20:20:54 -0400 Subject: [PATCH 018/109] add notice as to why pasting to GitHub is disabled --- .../MultiverseCore/commands/VersionCommand.java | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java index 146d91ee..ef6eabed 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java @@ -174,7 +174,15 @@ public class VersionCommand extends MultiverseCommand { if (CommandHandler.hasFlag("-b", args)) { // private post to pastebin pasteUrl = postToService(PasteServiceType.PASTEBIN, true, data, files); - } else if (CommandHandler.hasFlag("-h", args)) { + } + + // pasting to GitHub now requires an account, so we've disabled it + /* else if (CommandHandler.hasFlag("-g", args)) { + // private post to github + pasteUrl = postToService(PasteServiceType.GITHUB, true, data, files); + } */ + + else if (CommandHandler.hasFlag("-h", args)) { // private post to hastebin pasteUrl = postToService(PasteServiceType.HASTEBIN, true, data, files); } else { From a53c4214f09b8810b5d7886527381ae196b2e2bd Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sat, 6 Jun 2020 20:23:25 -0400 Subject: [PATCH 019/109] add extra space for readability --- .../commands/VersionCommand.java | 20 +++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java index ef6eabed..9d9f78ce 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java @@ -60,16 +60,16 @@ public class VersionCommand extends MultiverseCommand { "[Multiverse-Core] Economy being used: " + plugin.getEconomist().getEconomyName() + System.lineSeparator() + "[Multiverse-Core] Permissions Plugin: " + this.plugin.getMVPerms().getType() + System.lineSeparator() + "[Multiverse-Core] Dumping Config Values: (version " + this.plugin.getMVConfig().getVersion() + ")" + System.lineSeparator() + - "[Multiverse-Core] messagecooldown: " + plugin.getMessaging().getCooldown() + System.lineSeparator() + - "[Multiverse-Core] teleportcooldown: " + plugin.getMVConfig().getTeleportCooldown() + System.lineSeparator() + - "[Multiverse-Core] worldnameprefix: " + plugin.getMVConfig().getPrefixChat() + System.lineSeparator() + - "[Multiverse-Core] worldnameprefixFormat: " + plugin.getMVConfig().getPrefixChatFormat() + System.lineSeparator() + - "[Multiverse-Core] enforceaccess: " + plugin.getMVConfig().getEnforceAccess() + System.lineSeparator() + - "[Multiverse-Core] displaypermerrors: " + plugin.getMVConfig().getDisplayPermErrors() + System.lineSeparator() + - "[Multiverse-Core] teleportintercept: " + plugin.getMVConfig().getTeleportIntercept() + System.lineSeparator() + - "[Multiverse-Core] firstspawnoverride: " + plugin.getMVConfig().getFirstSpawnOverride() + System.lineSeparator() + - "[Multiverse-Core] firstspawnworld: " + plugin.getMVConfig().getFirstSpawnWorld() + System.lineSeparator() + - "[Multiverse-Core] debug: " + plugin.getMVConfig().getGlobalDebug() + System.lineSeparator() + + "[Multiverse-Core] messagecooldown: " + plugin.getMessaging().getCooldown() + System.lineSeparator() + + "[Multiverse-Core] teleportcooldown: " + plugin.getMVConfig().getTeleportCooldown() + System.lineSeparator() + + "[Multiverse-Core] worldnameprefix: " + plugin.getMVConfig().getPrefixChat() + System.lineSeparator() + + "[Multiverse-Core] worldnameprefixFormat: " + plugin.getMVConfig().getPrefixChatFormat() + System.lineSeparator() + + "[Multiverse-Core] enforceaccess: " + plugin.getMVConfig().getEnforceAccess() + System.lineSeparator() + + "[Multiverse-Core] displaypermerrors: " + plugin.getMVConfig().getDisplayPermErrors() + System.lineSeparator() + + "[Multiverse-Core] teleportintercept: " + plugin.getMVConfig().getTeleportIntercept() + System.lineSeparator() + + "[Multiverse-Core] firstspawnoverride: " + plugin.getMVConfig().getFirstSpawnOverride() + System.lineSeparator() + + "[Multiverse-Core] firstspawnworld: " + plugin.getMVConfig().getFirstSpawnWorld() + System.lineSeparator() + + "[Multiverse-Core] debug: " + plugin.getMVConfig().getGlobalDebug() + System.lineSeparator() + "[Multiverse-Core] Special Code: FRN002" + System.lineSeparator(); } From b9267a3dfc099230db7a2a40c54891963d794e38 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sat, 6 Jun 2020 20:25:12 -0400 Subject: [PATCH 020/109] update version command description --- .../onarandombox/MultiverseCore/commands/VersionCommand.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java index 9d9f78ce..f8435d73 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java @@ -49,7 +49,7 @@ public class VersionCommand extends MultiverseCommand { this.addKey("mvv"); this.addKey("mvversion"); this.setPermission("multiverse.core.version", - "Dumps version info to the console, optionally to pastie.org with -p or pastebin.com with a -b.", PermissionDefault.TRUE); + "Dumps version info to the console, optionally to pastebin.com with -b, or to hastebin.com using -h.", PermissionDefault.TRUE); } private String getLegacyString() { From 4f41b7aa6e3fb24f20e3f76fa032ffcb9b498ec6 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Tue, 9 Jun 2020 14:20:53 -0400 Subject: [PATCH 021/109] rework webpaste package --- pom.xml | 53 +++++++-- .../commands/VersionCommand.java | 26 +++-- .../utils/webpaste/BitlyURLShortener.java | 46 +++++--- .../utils/webpaste/GitHubPasteService.java | 102 ++++++------------ .../utils/webpaste/HastebinPasteService.java | 74 +++++-------- .../utils/webpaste/HttpAPIClient.java | 102 ++++++++++++++---- .../utils/webpaste/PasteService.java | 50 ++++----- .../utils/webpaste/PastebinPasteService.java | 96 ++++++----------- .../utils/webpaste/URLShortener.java | 10 +- .../utils/webpaste/URLShortenerFactory.java | 23 ++++ .../utils/webpaste/URLShortenerType.java | 14 +++ 11 files changed, 325 insertions(+), 271 deletions(-) create mode 100644 src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortenerFactory.java create mode 100644 src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortenerType.java diff --git a/pom.xml b/pom.xml index 0949061f..9c04f1e2 100644 --- a/pom.xml +++ b/pom.xml @@ -9,6 +9,7 @@ UTF-8 UNKNOWN + bitly-access-token @@ -69,6 +70,17 @@ ${env.BUILD_NUMBER} + + bitly + + + env.BITLY_ACCESS_TOKEN + + + + ${env.BITLY_ACCESS_TOKEN} + + @@ -90,21 +102,44 @@ 1.4.1 + replace-bitly-access-token + generate-sources + + replace + + + ${project.build.sourceDirectory} + + com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java + + + + bitly-access-token + ${project.bitly-access-token} + + + + + + replace-maven-version-number prepare-package replace + + ${project.build.directory}/classes + + plugin.yml + + + + maven-version-number + ${project.version}-b${project.build.number} + + + - - target/classes/plugin.yml - - - maven-version-number - ${project.version}-b${project.build.number} - - - diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java index f8435d73..c2665ca6 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java @@ -10,12 +10,13 @@ package com.onarandombox.MultiverseCore.commands; import com.dumptruckman.minecraft.util.Logging; import com.onarandombox.MultiverseCore.MultiverseCore; import com.onarandombox.MultiverseCore.event.MVVersionEvent; -import com.onarandombox.MultiverseCore.utils.webpaste.BitlyURLShortener; import com.onarandombox.MultiverseCore.utils.webpaste.PasteFailedException; import com.onarandombox.MultiverseCore.utils.webpaste.PasteService; import com.onarandombox.MultiverseCore.utils.webpaste.PasteServiceFactory; import com.onarandombox.MultiverseCore.utils.webpaste.PasteServiceType; import com.onarandombox.MultiverseCore.utils.webpaste.URLShortener; +import com.onarandombox.MultiverseCore.utils.webpaste.URLShortenerFactory; +import com.onarandombox.MultiverseCore.utils.webpaste.URLShortenerType; import com.pneumaticraft.commandhandler.CommandHandler; import org.apache.commons.lang.StringUtils; import org.bukkit.ChatColor; @@ -38,7 +39,7 @@ import java.util.Map; * Dumps version info to the console. */ public class VersionCommand extends MultiverseCommand { - private static final URLShortener SHORTENER = new BitlyURLShortener(); + private static final URLShortener SHORTENER = URLShortenerFactory.getService(URLShortenerType.BITLY); public VersionCommand(MultiverseCore plugin) { super(plugin); @@ -174,15 +175,10 @@ public class VersionCommand extends MultiverseCommand { if (CommandHandler.hasFlag("-b", args)) { // private post to pastebin pasteUrl = postToService(PasteServiceType.PASTEBIN, true, data, files); - } - - // pasting to GitHub now requires an account, so we've disabled it - /* else if (CommandHandler.hasFlag("-g", args)) { + } else if (CommandHandler.hasFlag("-g", args)) { // private post to github pasteUrl = postToService(PasteServiceType.GITHUB, true, data, files); - } */ - - else if (CommandHandler.hasFlag("-h", args)) { + } else if (CommandHandler.hasFlag("-h", args)) { // private post to hastebin pasteUrl = postToService(PasteServiceType.HASTEBIN, true, data, files); } else { @@ -210,17 +206,19 @@ public class VersionCommand extends MultiverseCommand { * @param pasteFiles Map of filenames/contents of debug info. * @return URL of visible paste */ - private static String postToService(PasteServiceType type, boolean isPrivate, String pasteData, - Map pasteFiles) { + private static String postToService(PasteServiceType type, boolean isPrivate, String pasteData, Map pasteFiles) { PasteService ps = PasteServiceFactory.getService(type, isPrivate); + try { String result; if (ps.supportsMultiFile()) { - result = ps.postData(ps.encodeData(pasteFiles), ps.getPostURL()); + result = ps.postData(pasteFiles); } else { - result = ps.postData(ps.encodeData(pasteData), ps.getPostURL()); + result = ps.postData(pasteData); } - return SHORTENER.shorten(result); + + if (SHORTENER != null) return SHORTENER.shorten(result); + return result; } catch (PasteFailedException e) { e.printStackTrace(); return "Error posting to service."; diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java index ea52cbcc..882c3790 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java @@ -1,19 +1,41 @@ package com.onarandombox.MultiverseCore.utils.webpaste; +import org.json.simple.JSONObject; +import org.json.simple.parser.JSONParser; +import org.json.simple.parser.ParseException; + import java.io.IOException; +import java.util.Map; /** * An {@link URLShortener} using {@code bit.ly}. */ -public class BitlyURLShortener extends HttpAPIClient implements URLShortener { - private static final String GENERIC_BITLY_REQUEST_FORMAT = "https://api-ssl.bitly.com/v3/shorten?format=txt&apiKey=%s&login=%s&longUrl=%s"; - - // I think it's no problem that these are public - private static final String USERNAME = "multiverse2"; - private static final String API_KEY = "R_9dbff4862a3bc0c4218a7d78cc10d0e0"; +class BitlyURLShortener extends URLShortener { + private static final String ACCESS_TOKEN = "Bearer bitly-access-token"; + private static final String BITLY_POST_REQUEST = "https://api-ssl.bitly.com/v4/shorten"; public BitlyURLShortener() { - super(String.format(GENERIC_BITLY_REQUEST_FORMAT, API_KEY, USERNAME, "%s")); + super(BITLY_POST_REQUEST, ACCESS_TOKEN); + if (ACCESS_TOKEN.endsWith("access-token")) throw new UnsupportedOperationException(); + } + + /** + * {@inheritDoc} + */ + @Override + protected String encodeData(String data) { + JSONObject json = new JSONObject(); + json.put("domain", "j.mp"); + json.put("long_url", data); + return json.toJSONString(); + } + + /** + * {@inheritDoc} + */ + @Override + protected String encodeData(Map data) { + throw new UnsupportedOperationException(); } /** @@ -22,13 +44,11 @@ public class BitlyURLShortener extends HttpAPIClient implements URLShortener { @Override public String shorten(String longUrl) { try { - String result = this.exec(longUrl); - if (!result.startsWith("https://j.mp/")) // ... then it's failed :/ - throw new IOException(result); - return result; - } catch (IOException e) { + String stringJSON = this.exec(encodeData(longUrl), ContentType.JSON); + return (String) ((JSONObject) new JSONParser().parse(stringJSON)).get("link"); + } catch (IOException | ParseException e) { e.printStackTrace(); - return longUrl; // sorry ... + return longUrl; } } } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java index 6c0b9890..0370a7ca 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java @@ -1,26 +1,23 @@ package com.onarandombox.MultiverseCore.utils.webpaste; -import com.google.gson.JsonObject; -import com.google.gson.JsonParser; -import com.google.gson.JsonPrimitive; +import org.json.simple.JSONObject; +import org.json.simple.parser.JSONParser; +import org.json.simple.parser.ParseException; -import java.io.BufferedReader; import java.io.IOException; -import java.io.InputStreamReader; -import java.io.OutputStreamWriter; -import java.net.MalformedURLException; -import java.net.URL; -import java.net.URLConnection; -import java.nio.charset.StandardCharsets; import java.util.HashMap; import java.util.Map; -public class GitHubPasteService implements PasteService { - +public class GitHubPasteService extends PasteService { private final boolean isPrivate; + // this access token must have the "gist" OAuth scope + private static final String ACCESS_TOKEN = "token github-access-token"; + private static final String GITHUB_POST_REQUEST = "https://api.github.com/gists"; public GitHubPasteService(boolean isPrivate) { + super(GITHUB_POST_REQUEST, ACCESS_TOKEN); this.isPrivate = isPrivate; + if (ACCESS_TOKEN.endsWith("access-token")) throw new UnsupportedOperationException(); } @Override @@ -32,68 +29,37 @@ public class GitHubPasteService implements PasteService { @Override public String encodeData(Map files) { - JsonObject root = new JsonObject(); - root.add("description", new JsonPrimitive("Multiverse-Core Debug Info")); - root.add("public", new JsonPrimitive(!this.isPrivate)); - JsonObject fileList = new JsonObject(); - for (Map.Entry entry : files.entrySet()) - { - JsonObject fileObject = new JsonObject(); - fileObject.add("content", new JsonPrimitive(entry.getValue())); - fileList.add(entry.getKey(), fileObject); + JSONObject root = new JSONObject(); + root.put("description", "Multiverse-Core Debug Info"); + root.put("public", !this.isPrivate); + JSONObject fileList = new JSONObject(); + for (Map.Entry entry : files.entrySet()) { + JSONObject fileObject = new JSONObject(); + fileObject.put("content", entry.getValue()); + fileList.put(entry.getKey(), fileObject); } - root.add("files", fileList); - return root.toString(); + + root.put("files", fileList); + return root.toJSONString(); } @Override - public URL getPostURL() { + public String postData(String data) throws PasteFailedException { try { - return new URL("https://api.github.com/gists"); - - // the following can be used for testing purposes - // return new URL("http://jsonplaceholder.typicode.com/posts"); - } catch (MalformedURLException e) { - return null; // should never hit here - } - } - - @Override - public String postData(String encodedData, URL url) throws PasteFailedException { - OutputStreamWriter wr = null; - BufferedReader rd = null; - try { - URLConnection conn = url.openConnection(); - conn.setDoOutput(true); - - // this isn't required, but is technically correct - conn.addRequestProperty("Content-Type", "application/json; charset=utf-8"); - - wr = new OutputStreamWriter(conn.getOutputStream(), StandardCharsets.UTF_8); - wr.write(encodedData); - wr.flush(); - - String line; - StringBuilder responseString = new StringBuilder(); - // this has to be initialized AFTER the data has been flushed! - rd = new BufferedReader(new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8)); - while ((line = rd.readLine()) != null) { - responseString.append(line); - } - return new JsonParser().parse(responseString.toString()).getAsJsonObject().get("html_url").getAsString(); - } catch (Exception e) { + String stringJSON = this.exec(encodeData(data), ContentType.JSON); + return (String) ((JSONObject) new JSONParser().parse(stringJSON)).get("html_url"); + } catch (IOException | ParseException e) { + throw new PasteFailedException(e); + } + } + + @Override + public String postData(Map data) throws PasteFailedException { + try { + String stringJSON = this.exec(encodeData(data), ContentType.JSON); + return (String) ((JSONObject) new JSONParser().parse(stringJSON)).get("html_url"); + } catch (IOException | ParseException e) { throw new PasteFailedException(e); - } finally { - if (wr != null) { - try { - wr.close(); - } catch (IOException ignore) { } - } - if (rd != null) { - try { - rd.close(); - } catch (IOException ignore) { } - } } } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java index 407ec354..c77e1f7b 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java @@ -1,81 +1,55 @@ package com.onarandombox.MultiverseCore.utils.webpaste; -import com.google.gson.JsonParser; +import org.json.simple.JSONObject; +import org.json.simple.parser.JSONParser; +import org.json.simple.parser.ParseException; -import java.io.BufferedReader; import java.io.IOException; -import java.io.InputStreamReader; -import java.io.OutputStreamWriter; -import java.net.MalformedURLException; -import java.net.URL; -import java.net.URLConnection; -import java.nio.charset.StandardCharsets; import java.util.Map; /** * Pastes to {@code hastebin.com}. */ -public class HastebinPasteService implements PasteService { +class HastebinPasteService extends PasteService { + private static final String HASTEBIN_POST_REQUEST = "https://hastebin.com/documents"; + public HastebinPasteService() { + super(HASTEBIN_POST_REQUEST, null); + } + + /** + * {@inheritDoc} + */ @Override public String encodeData(String data) { return data; } + /** + * {@inheritDoc} + */ @Override public String encodeData(Map data) { throw new UnsupportedOperationException(); } @Override - public URL getPostURL() { + public String postData(String data) throws PasteFailedException { try { - return new URL("https://hastebin.com/documents"); - } catch (MalformedURLException e) { - return null; // should never hit here + String stringJSON = this.exec(encodeData(data), ContentType.PLAINTEXT); + return "https://hastebin.com/" + ((JSONObject) new JSONParser().parse(stringJSON)).get("key"); + } catch (IOException | ParseException e) { + throw new PasteFailedException(e); } } @Override - public String postData(String encodedData, URL url) throws PasteFailedException { - OutputStreamWriter wr = null; - BufferedReader rd = null; + public String postData(Map data) throws PasteFailedException { try { - URLConnection conn = url.openConnection(); - conn.setDoOutput(true); - - // hastebin needs a user-agent - conn.addRequestProperty("User-Agent", "placeholder"); - // this isn't required, but is technically correct - conn.addRequestProperty("Content-Type", "text/plain; charset=utf-8"); - - wr = new OutputStreamWriter(conn.getOutputStream(), StandardCharsets.UTF_8.newEncoder()); - wr.write(encodedData); - wr.flush(); - - String line; - StringBuilder responseString = new StringBuilder(); - // this has to be initialized AFTER the data has been flushed! - rd = new BufferedReader(new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8)); - while ((line = rd.readLine()) != null) { - responseString.append(line); - } - String key = new JsonParser().parse(responseString.toString()).getAsJsonObject().get("key").getAsString(); - - return "https://hastebin.com/" + key; - } catch (Exception e) { + String stringJSON = this.exec(encodeData(data), ContentType.PLAINTEXT); + return "https://hastebin.com/" + ((JSONObject) new JSONParser().parse(stringJSON)).get("key"); + } catch (IOException | ParseException e) { throw new PasteFailedException(e); - } finally { - if (wr != null) { - try { - wr.close(); - } catch (IOException ignore) { } - } - if (rd != null) { - try { - rd.close(); - } catch (IOException ignore) { } - } } } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java index 962fa356..c8c4b2bf 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java @@ -1,51 +1,115 @@ package com.onarandombox.MultiverseCore.utils.webpaste; +import javax.net.ssl.HttpsURLConnection; import java.io.BufferedReader; import java.io.IOException; import java.io.InputStreamReader; +import java.io.OutputStreamWriter; import java.net.URL; -import java.net.URLConnection; import java.nio.charset.StandardCharsets; +import java.util.Map; /** * HTTP API-client. */ public abstract class HttpAPIClient { /** - * The URL for this API-request. + * The URL for this API-request, and if necessary, the access token. + * If an access token is not necessary, it should be set to null. */ - protected final String urlFormat; + private final String url; + private final String accessToken; - public HttpAPIClient(String urlFormat) { - this.urlFormat = urlFormat; + /** + * Types of data that can be sent. + */ + protected enum ContentType { + JSON, + PLAINTEXT, + URLENCODED + } + + public HttpAPIClient(String url, String accessToken) { + this.url = url; + this.accessToken = accessToken; + } + + private String getContentHeader(ContentType type) { + switch (type) { + case JSON: + return "application/json; charset=utf-8"; + case PLAINTEXT: + return "text/plain; charset=utf-8"; + case URLENCODED: + return "application/x-www-form-urlencoded; charset=utf-8"; + default: + throw new IllegalStateException("Unexpected value: " + type); + } } + /** + * Encode the given String data into a format suitable for transmission in an HTTP request. + * + * @param data The raw data to encode. + * @return A URL-encoded string. + */ + protected abstract String encodeData(String data); + + /** + * Encode the given Map data into a format suitable for transmission in an HTTP request. + * + * @param data The raw data to encode. + * @return A URL-encoded string. + */ + protected abstract String encodeData(Map data); + /** * Executes this API-Request. - * @param args Format-args. + * @param payload The data that will be sent. + * @param type The type of data that will be sent. * @return The result (as text). * @throws IOException When the I/O-operation failed. */ - protected final String exec(Object... args) throws IOException { + protected final String exec(String payload, ContentType type) throws IOException { + BufferedReader rd = null; + OutputStreamWriter wr = null; - URLConnection conn = new URL(String.format(this.urlFormat, args)).openConnection(); - conn.connect(); - StringBuilder ret = new StringBuilder(); - BufferedReader reader = null; try { - reader = new BufferedReader(new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8)); - while (!reader.ready()); // wait until reader is ready, may not be necessary, SUPPRESS CHECKSTYLE: EmptyStatement + HttpsURLConnection conn = (HttpsURLConnection) new URL(this.url).openConnection(); + conn.setRequestMethod("POST"); + conn.setDoOutput(true); - while (reader.ready()) { - ret.append(reader.readLine()).append(System.lineSeparator()); - } + // we can receive anything! + conn.addRequestProperty("Accept", "*/*"); + // set a dummy User-Agent + conn.addRequestProperty("User-Agent", "placeholder"); + // this isn't required, but is technically correct + conn.addRequestProperty("Content-Type", getContentHeader(type)); + // only some API requests require an access token + if (this.accessToken != null) conn.addRequestProperty("Authorization", this.accessToken); + + wr = new OutputStreamWriter(conn.getOutputStream(), StandardCharsets.UTF_8.newEncoder()); + wr.write(payload); + wr.flush(); + + String line; + StringBuilder responseString = new StringBuilder(); + // this has to be initialized AFTER the data has been flushed! + rd = new BufferedReader(new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8)); + + while ((line = rd.readLine()) != null) responseString.append(line); + return responseString.toString(); } finally { - if (reader != null) { + if (wr != null) { try { - reader.close(); + wr.close(); + } catch (IOException ignore) { } + } + if (rd != null) { + try { + rd.close(); } catch (IOException ignore) { } } } - return ret.toString(); } } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteService.java index 403f5ab8..1b3830ea 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteService.java @@ -1,6 +1,5 @@ package com.onarandombox.MultiverseCore.utils.webpaste; -import java.net.URL; import java.util.Map; /** @@ -15,41 +14,30 @@ import java.util.Map; * should implement a custom constructor that specifies which kind the PasteService * instance is submitting; an example of this is the PastebinPasteService class. */ -public interface PasteService { +public abstract class PasteService extends HttpAPIClient { + public PasteService(String url, String accessToken) { + super(url, accessToken); + } /** - * Encode the given String data into a format suitable for transmission in an HTTP request. + * Post data to the Web. * - * @param data The raw data to encode. - * @return A URL-encoded string. - */ - String encodeData(String data); - - /** - * Encode the given Map data into a format suitable for transmission in an HTTP request. - * - * @param data The raw data to encode. - * @return A URL-encoded string. - */ - String encodeData(Map data); - - /** - * Get the URL to which this paste service sends new pastes. - * - * @return The URL that will be accessed to complete the paste. - */ - URL getPostURL(); - - /** - * Post encoded data to the Web. - * - * @param encodedData A URL-encoded String containing the full request to post to - * the given URL. Can be the result of calling #encodeData(). - * @param url The URL to which to paste. Can be the result of calling #getPostURL(). + * @param data A URL-encoded String containing the full request to post to + * the given URL. Can be the result of calling #encodeData(). * @throws PasteFailedException When pasting/posting the data failed. * @return The URL at which the new paste is visible. */ - String postData(String encodedData, URL url) throws PasteFailedException; + public abstract String postData(String data) throws PasteFailedException; + + /** + * Post data to the Web. + * + * @param data A URL-encoded Map containing the full request to post to + * the given URL. Can be the result of calling #encodeData(). + * @throws PasteFailedException When pasting/posting the data failed. + * @return The URL at which the new paste is visible. + */ + public abstract String postData(Map data) throws PasteFailedException; /** * Does this service support uploading multiple files. @@ -59,5 +47,5 @@ public interface PasteService { * * @return True if this service supports multiple file upload. */ - boolean supportsMultiFile(); + public abstract boolean supportsMultiFile(); } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java index c370c1d2..85af5a47 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java @@ -1,40 +1,22 @@ package com.onarandombox.MultiverseCore.utils.webpaste; -import java.io.BufferedReader; import java.io.IOException; -import java.io.InputStreamReader; -import java.io.OutputStreamWriter; import java.io.UnsupportedEncodingException; -import java.net.MalformedURLException; -import java.net.URL; -import java.net.URLConnection; import java.net.URLEncoder; -import java.nio.charset.StandardCharsets; import java.util.Map; /** * Pastes to {@code pastebin.com}. */ -public class PastebinPasteService implements PasteService { - - private boolean isPrivate; +class PastebinPasteService extends PasteService { + private final boolean isPrivate; + private static final String PASTEBIN_POST_REQUEST = "https://pastebin.com/api/api_post.php"; public PastebinPasteService(boolean isPrivate) { + super(PASTEBIN_POST_REQUEST, null); this.isPrivate = isPrivate; } - /** - * {@inheritDoc} - */ - @Override - public URL getPostURL() { - try { - return new URL("http://pastebin.com/api/api_post.php"); - } catch (MalformedURLException e) { - return null; // should never hit here - } - } - /** * {@inheritDoc} */ @@ -42,59 +24,45 @@ public class PastebinPasteService implements PasteService { public String encodeData(String data) { try { return URLEncoder.encode("api_dev_key", "UTF-8") + "=" + URLEncoder.encode("d61d68d31e8e0392b59b50b277411c71", "UTF-8") + - "&" + URLEncoder.encode("api_option", "UTF-8") + "=" + URLEncoder.encode("paste", "UTF-8") + - "&" + URLEncoder.encode("api_paste_code", "UTF-8") + "=" + URLEncoder.encode(data, "UTF-8") + - "&" + URLEncoder.encode("api_paste_private", "UTF-8") + "=" + URLEncoder.encode(this.isPrivate ? "1" : "0", "UTF-8") + - "&" + URLEncoder.encode("api_paste_format", "UTF-8") + "=" + URLEncoder.encode("yaml", "UTF-8"); + "&" + URLEncoder.encode("api_option", "UTF-8") + "=" + URLEncoder.encode("paste", "UTF-8") + + "&" + URLEncoder.encode("api_paste_code", "UTF-8") + "=" + URLEncoder.encode(data, "UTF-8") + + "&" + URLEncoder.encode("api_paste_private", "UTF-8") + "=" + URLEncoder.encode(this.isPrivate ? "1" : "0", "UTF-8") + + "&" + URLEncoder.encode("api_paste_format", "UTF-8") + "=" + URLEncoder.encode("yaml", "UTF-8") + + "&" + URLEncoder.encode("api_paste_name", "UTF-8") + "=" + URLEncoder.encode("Multiverse-Core Debug Info", "UTF-8"); } catch (UnsupportedEncodingException e) { return ""; // should never hit here } } - @Override - public String encodeData(Map data) { - return null; - } - /** * {@inheritDoc} */ @Override - public String postData(String encodedData, URL url) throws PasteFailedException { - OutputStreamWriter wr = null; - BufferedReader rd = null; + public String encodeData(Map data) { + throw new UnsupportedOperationException(); + } + + /** + * {@inheritDoc} + */ + @Override + public String postData(String data) throws PasteFailedException { try { - URLConnection conn = url.openConnection(); - conn.setDoOutput(true); - - // this isn't required, but is technically correct - conn.addRequestProperty("Content-Type", "application/x-www-form-urlencoded; charset=utf-8"); - - wr = new OutputStreamWriter(conn.getOutputStream(), StandardCharsets.UTF_8); - wr.write(encodedData); - wr.flush(); - - String line; - String pastebinUrl = ""; - // this has to be initialized AFTER the data has been flushed! - rd = new BufferedReader(new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8)); - while ((line = rd.readLine()) != null) { - pastebinUrl = line; - } - return pastebinUrl; - } catch (Exception e) { + return this.exec(encodeData(data), ContentType.URLENCODED); + } catch (IOException e) { + throw new PasteFailedException(e); + } + } + + /** + * {@inheritDoc} + */ + @Override + public String postData(Map data) throws PasteFailedException { + try { + return this.exec(encodeData(data), ContentType.URLENCODED); + } catch (IOException e) { throw new PasteFailedException(e); - } finally { - if (wr != null) { - try { - wr.close(); - } catch (IOException ignore) { } - } - if (rd != null) { - try { - rd.close(); - } catch (IOException ignore) { } - } } } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortener.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortener.java index 75d50f63..0c6f592c 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortener.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortener.java @@ -3,11 +3,15 @@ package com.onarandombox.MultiverseCore.utils.webpaste; /** * URL-Shortener. */ -public interface URLShortener { +public abstract class URLShortener extends HttpAPIClient { + public URLShortener(String url, String accessToken) { + super(url, accessToken); + } + /** - * Shorten an URL. + * Shorten a URL. * @param longUrl The long form. * @return The shortened URL. */ - String shorten(String longUrl); + public abstract String shorten(String longUrl); } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortenerFactory.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortenerFactory.java new file mode 100644 index 00000000..c0f3cafa --- /dev/null +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortenerFactory.java @@ -0,0 +1,23 @@ +package com.onarandombox.MultiverseCore.utils.webpaste; + +/** + * Used to construct {@link URLShortener}s. + */ +public class URLShortenerFactory { + private URLShortenerFactory() { } + + /** + * Constructs a new {@link URLShortener}. + * @param type The {@link URLShortenerType}. + * @return The newly created {@link URLShortener}. + */ + public static URLShortener getService(URLShortenerType type) { + if (type == URLShortenerType.BITLY) { + try { + return new BitlyURLShortener(); + } catch (UnsupportedOperationException ignored) {} + } + + return null; + } +} \ No newline at end of file diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortenerType.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortenerType.java new file mode 100644 index 00000000..d2c809f5 --- /dev/null +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortenerType.java @@ -0,0 +1,14 @@ +package com.onarandombox.MultiverseCore.utils.webpaste; + +/** + * An enum containing all known {@link URLShortener}s. + * + * @see URLShortener + * @see URLShortenerFactory + */ +public enum URLShortenerType { + /** + * @see BitlyURLShortener + */ + BITLY +} From b4a4519876a440ae19377f527c91f16cd13ae875 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Tue, 9 Jun 2020 23:23:42 -0400 Subject: [PATCH 022/109] no need for protected access modifier --- .../MultiverseCore/utils/webpaste/BitlyURLShortener.java | 4 ++-- .../MultiverseCore/utils/webpaste/GitHubPasteService.java | 4 ++-- .../utils/webpaste/HastebinPasteService.java | 4 ++-- .../MultiverseCore/utils/webpaste/HttpAPIClient.java | 8 ++++---- .../utils/webpaste/PastebinPasteService.java | 4 ++-- 5 files changed, 12 insertions(+), 12 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java index 882c3790..90472344 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java @@ -23,7 +23,7 @@ class BitlyURLShortener extends URLShortener { * {@inheritDoc} */ @Override - protected String encodeData(String data) { + String encodeData(String data) { JSONObject json = new JSONObject(); json.put("domain", "j.mp"); json.put("long_url", data); @@ -34,7 +34,7 @@ class BitlyURLShortener extends URLShortener { * {@inheritDoc} */ @Override - protected String encodeData(Map data) { + String encodeData(Map data) { throw new UnsupportedOperationException(); } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java index 0370a7ca..32aeaf53 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java @@ -21,14 +21,14 @@ public class GitHubPasteService extends PasteService { } @Override - public String encodeData(String data) { + String encodeData(String data) { Map mapData = new HashMap(); mapData.put("multiverse.txt", data); return this.encodeData(mapData); } @Override - public String encodeData(Map files) { + String encodeData(Map files) { JSONObject root = new JSONObject(); root.put("description", "Multiverse-Core Debug Info"); root.put("public", !this.isPrivate); diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java index c77e1f7b..da0dcba8 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java @@ -21,7 +21,7 @@ class HastebinPasteService extends PasteService { * {@inheritDoc} */ @Override - public String encodeData(String data) { + String encodeData(String data) { return data; } @@ -29,7 +29,7 @@ class HastebinPasteService extends PasteService { * {@inheritDoc} */ @Override - public String encodeData(Map data) { + String encodeData(Map data) { throw new UnsupportedOperationException(); } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java index c8c4b2bf..353565d7 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java @@ -23,7 +23,7 @@ public abstract class HttpAPIClient { /** * Types of data that can be sent. */ - protected enum ContentType { + enum ContentType { JSON, PLAINTEXT, URLENCODED @@ -53,7 +53,7 @@ public abstract class HttpAPIClient { * @param data The raw data to encode. * @return A URL-encoded string. */ - protected abstract String encodeData(String data); + abstract String encodeData(String data); /** * Encode the given Map data into a format suitable for transmission in an HTTP request. @@ -61,7 +61,7 @@ public abstract class HttpAPIClient { * @param data The raw data to encode. * @return A URL-encoded string. */ - protected abstract String encodeData(Map data); + abstract String encodeData(Map data); /** * Executes this API-Request. @@ -70,7 +70,7 @@ public abstract class HttpAPIClient { * @return The result (as text). * @throws IOException When the I/O-operation failed. */ - protected final String exec(String payload, ContentType type) throws IOException { + final String exec(String payload, ContentType type) throws IOException { BufferedReader rd = null; OutputStreamWriter wr = null; diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java index 85af5a47..30c346ba 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java @@ -21,7 +21,7 @@ class PastebinPasteService extends PasteService { * {@inheritDoc} */ @Override - public String encodeData(String data) { + String encodeData(String data) { try { return URLEncoder.encode("api_dev_key", "UTF-8") + "=" + URLEncoder.encode("d61d68d31e8e0392b59b50b277411c71", "UTF-8") + "&" + URLEncoder.encode("api_option", "UTF-8") + "=" + URLEncoder.encode("paste", "UTF-8") + @@ -38,7 +38,7 @@ class PastebinPasteService extends PasteService { * {@inheritDoc} */ @Override - public String encodeData(Map data) { + String encodeData(Map data) { throw new UnsupportedOperationException(); } From 707eae92a80ecf7729e22de0b16dcf530ab34a6c Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Wed, 10 Jun 2020 00:05:22 -0400 Subject: [PATCH 023/109] improve javadocs, also, no need to make implementations public --- .../utils/webpaste/BitlyURLShortener.java | 4 ++-- .../utils/webpaste/GitHubPasteService.java | 24 ++++++++++++++++--- .../utils/webpaste/HastebinPasteService.java | 11 ++++++++- .../utils/webpaste/HttpAPIClient.java | 9 +++++-- .../utils/webpaste/PasteFailedException.java | 2 +- .../utils/webpaste/PasteService.java | 23 ++++++++---------- .../utils/webpaste/PastebinPasteService.java | 5 +++- .../utils/webpaste/URLShortener.java | 10 ++++++-- 8 files changed, 63 insertions(+), 25 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java index 90472344..96fadd22 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/BitlyURLShortener.java @@ -8,13 +8,13 @@ import java.io.IOException; import java.util.Map; /** - * An {@link URLShortener} using {@code bit.ly}. + * A {@link URLShortener} using {@code bit.ly}. Requires an access token. */ class BitlyURLShortener extends URLShortener { private static final String ACCESS_TOKEN = "Bearer bitly-access-token"; private static final String BITLY_POST_REQUEST = "https://api-ssl.bitly.com/v4/shorten"; - public BitlyURLShortener() { + BitlyURLShortener() { super(BITLY_POST_REQUEST, ACCESS_TOKEN); if (ACCESS_TOKEN.endsWith("access-token")) throw new UnsupportedOperationException(); } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java index 32aeaf53..717ac3c4 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/GitHubPasteService.java @@ -8,18 +8,24 @@ import java.io.IOException; import java.util.HashMap; import java.util.Map; -public class GitHubPasteService extends PasteService { +/** + * Pastes to {@code gist.github.com}. Requires an access token with the {@code gist} scope. + */ +class GitHubPasteService extends PasteService { private final boolean isPrivate; - // this access token must have the "gist" OAuth scope + // this access token must have the "gist" scope private static final String ACCESS_TOKEN = "token github-access-token"; private static final String GITHUB_POST_REQUEST = "https://api.github.com/gists"; - public GitHubPasteService(boolean isPrivate) { + GitHubPasteService(boolean isPrivate) { super(GITHUB_POST_REQUEST, ACCESS_TOKEN); this.isPrivate = isPrivate; if (ACCESS_TOKEN.endsWith("access-token")) throw new UnsupportedOperationException(); } + /** + * {@inheritDoc} + */ @Override String encodeData(String data) { Map mapData = new HashMap(); @@ -27,6 +33,9 @@ public class GitHubPasteService extends PasteService { return this.encodeData(mapData); } + /** + * {@inheritDoc} + */ @Override String encodeData(Map files) { JSONObject root = new JSONObject(); @@ -43,6 +52,9 @@ public class GitHubPasteService extends PasteService { return root.toJSONString(); } + /** + * {@inheritDoc} + */ @Override public String postData(String data) throws PasteFailedException { try { @@ -53,6 +65,9 @@ public class GitHubPasteService extends PasteService { } } + /** + * {@inheritDoc} + */ @Override public String postData(Map data) throws PasteFailedException { try { @@ -63,6 +78,9 @@ public class GitHubPasteService extends PasteService { } } + /** + * {@inheritDoc} + */ @Override public boolean supportsMultiFile() { return true; diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java index da0dcba8..46af2d29 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HastebinPasteService.java @@ -13,7 +13,7 @@ import java.util.Map; class HastebinPasteService extends PasteService { private static final String HASTEBIN_POST_REQUEST = "https://hastebin.com/documents"; - public HastebinPasteService() { + HastebinPasteService() { super(HASTEBIN_POST_REQUEST, null); } @@ -33,6 +33,9 @@ class HastebinPasteService extends PasteService { throw new UnsupportedOperationException(); } + /** + * {@inheritDoc} + */ @Override public String postData(String data) throws PasteFailedException { try { @@ -43,6 +46,9 @@ class HastebinPasteService extends PasteService { } } + /** + * {@inheritDoc} + */ @Override public String postData(Map data) throws PasteFailedException { try { @@ -53,6 +59,9 @@ class HastebinPasteService extends PasteService { } } + /** + * {@inheritDoc} + */ @Override public boolean supportsMultiFile() { return false; diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java index 353565d7..8e423fcc 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/HttpAPIClient.java @@ -12,7 +12,7 @@ import java.util.Map; /** * HTTP API-client. */ -public abstract class HttpAPIClient { +abstract class HttpAPIClient { /** * The URL for this API-request, and if necessary, the access token. * If an access token is not necessary, it should be set to null. @@ -29,11 +29,16 @@ public abstract class HttpAPIClient { URLENCODED } - public HttpAPIClient(String url, String accessToken) { + HttpAPIClient(String url, String accessToken) { this.url = url; this.accessToken = accessToken; } + /** + * Returns the HTTP Content-Type header that corresponds with each ContentType. + * @param type The type of data. + * @return The HTTP Content-Type header that corresponds with the type of data. + */ private String getContentHeader(ContentType type) { switch (type) { case JSON: diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteFailedException.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteFailedException.java index 85a803a4..82792f49 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteFailedException.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteFailedException.java @@ -1,7 +1,7 @@ package com.onarandombox.MultiverseCore.utils.webpaste; /** - * Thrown when pasting failed. + * Thrown when pasting fails. */ public class PasteFailedException extends Exception { public PasteFailedException() { diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteService.java index 1b3830ea..0c474c9e 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteService.java @@ -3,27 +3,25 @@ package com.onarandombox.MultiverseCore.utils.webpaste; import java.util.Map; /** - * An interface to a web-based text-pasting service. Classes implementing this - * interface should implement its methods to send data to an online text-sharing - * service, such as pastebin.com. Conventionally, a paste is accomplished by (given - * some PasteService instance ps): + * An interface to a web-based text-pasting service. Classes extending this + * should implement its methods to send data to an online text-sharing service, + * such as pastebin.com. Given some PasteService instance ps, a paste is accomplished by: * - * {@code ps.postData(ps.encodeData(someString), ps.getPostURL());} + * {@code ps.postData(someString);} * * Services that provide a distinction between "public" and "private" pastes - * should implement a custom constructor that specifies which kind the PasteService + * should implement a constructor that specifies which kind the PasteService * instance is submitting; an example of this is the PastebinPasteService class. */ public abstract class PasteService extends HttpAPIClient { - public PasteService(String url, String accessToken) { + PasteService(String url, String accessToken) { super(url, accessToken); } /** * Post data to the Web. * - * @param data A URL-encoded String containing the full request to post to - * the given URL. Can be the result of calling #encodeData(). + * @param data A String to post to the web. * @throws PasteFailedException When pasting/posting the data failed. * @return The URL at which the new paste is visible. */ @@ -32,8 +30,7 @@ public abstract class PasteService extends HttpAPIClient { /** * Post data to the Web. * - * @param data A URL-encoded Map containing the full request to post to - * the given URL. Can be the result of calling #encodeData(). + * @param data A Map to post to the web. * @throws PasteFailedException When pasting/posting the data failed. * @return The URL at which the new paste is visible. */ @@ -42,8 +39,8 @@ public abstract class PasteService extends HttpAPIClient { /** * Does this service support uploading multiple files. * - * Newer services like gist support multi-file which allows us to upload configs - * in addition to the standard logs. + * Newer services like GitHub's Gist support multi-file pastes, + * which allows us to upload configs in addition to the standard logs. * * @return True if this service supports multiple file upload. */ diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java index 30c346ba..ce7a4453 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PastebinPasteService.java @@ -12,7 +12,7 @@ class PastebinPasteService extends PasteService { private final boolean isPrivate; private static final String PASTEBIN_POST_REQUEST = "https://pastebin.com/api/api_post.php"; - public PastebinPasteService(boolean isPrivate) { + PastebinPasteService(boolean isPrivate) { super(PASTEBIN_POST_REQUEST, null); this.isPrivate = isPrivate; } @@ -66,6 +66,9 @@ class PastebinPasteService extends PasteService { } } + /** + * {@inheritDoc} + */ @Override public boolean supportsMultiFile() { return false; diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortener.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortener.java index 0c6f592c..be3d61b1 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortener.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/URLShortener.java @@ -1,10 +1,16 @@ package com.onarandombox.MultiverseCore.utils.webpaste; /** - * URL-Shortener. + * An interface to a web-based URL Shortener. Classes extending this should + * implement its methods to shorten links using the service. Given some + * URLShortener instance us, a URL is shortened by: + * + * {@code us.shorten(longUrl);} + * + * An example of this, is the BitlyURLShortener. */ public abstract class URLShortener extends HttpAPIClient { - public URLShortener(String url, String accessToken) { + URLShortener(String url, String accessToken) { super(url, accessToken); } From 94ca18e95c5fbfcf9f0f82654a7e72d79928c19a Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sat, 13 Jun 2020 14:20:36 -0400 Subject: [PATCH 024/109] correct some metrics --- .../MultiverseCore/utils/metrics/MetricsConfigurator.java | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java index 25aaf009..fd3470a6 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java @@ -8,7 +8,7 @@ import com.dumptruckman.minecraft.util.Logging; import com.onarandombox.MultiverseCore.MultiverseCore; import com.onarandombox.MultiverseCore.api.MVWorldManager; import com.onarandombox.MultiverseCore.api.MultiverseWorld; -import org.apache.commons.lang.StringUtils; +import org.apache.commons.lang.WordUtils; import org.bstats.bukkit.Metrics; import org.bukkit.World; @@ -60,7 +60,8 @@ public class MetricsConfigurator { } private String getGeneratorName(MultiverseWorld world) { - return world.getGenerator() != null ? world.getGenerator() : NO_GENERATOR_NAME; + String gen = world.getGenerator(); + return (gen != null && !gen.equalsIgnoreCase("null")) ? gen : NO_GENERATOR_NAME; } private void addEnvironmentsMetric() { @@ -73,7 +74,7 @@ public class MetricsConfigurator { private String titleCaseEnv(World.Environment env) { String envName = env.name().replaceAll("_+", " "); - return StringUtils.capitalize(envName.toLowerCase()); + return WordUtils.capitalizeFully(envName); } private void addWorldCountMetric() { From e01c646562d62c6d533cc84dfe10f3a90351a4e0 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sun, 14 Jun 2020 16:04:17 -0400 Subject: [PATCH 025/109] add paste.gg paste service --- .../commands/VersionCommand.java | 7 +- .../utils/webpaste/PasteGGPasteService.java | 90 +++++++++++++++++++ .../utils/webpaste/PasteServiceFactory.java | 2 + .../utils/webpaste/PasteServiceType.java | 4 + 4 files changed, 101 insertions(+), 2 deletions(-) create mode 100644 src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteGGPasteService.java diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java index c2665ca6..00912846 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java @@ -44,13 +44,13 @@ public class VersionCommand extends MultiverseCommand { public VersionCommand(MultiverseCore plugin) { super(plugin); this.setName("Multiverse Version"); - this.setCommandUsage("/mv version " + ChatColor.GOLD + "-[bh] [--include-plugin-list]"); + this.setCommandUsage("/mv version " + ChatColor.GOLD + "-[bhp] [--include-plugin-list]"); this.setArgRange(0, 2); this.addKey("mv version"); this.addKey("mvv"); this.addKey("mvversion"); this.setPermission("multiverse.core.version", - "Dumps version info to the console, optionally to pastebin.com with -b, or to hastebin.com using -h.", PermissionDefault.TRUE); + "Dumps version info to the console, optionally to pastebin.com with -b, to hastebin.com using -h, or to paste.gg with -p.", PermissionDefault.TRUE); } private String getLegacyString() { @@ -181,6 +181,9 @@ public class VersionCommand extends MultiverseCommand { } else if (CommandHandler.hasFlag("-h", args)) { // private post to hastebin pasteUrl = postToService(PasteServiceType.HASTEBIN, true, data, files); + } else if (CommandHandler.hasFlag("-p", args)) { + // private post to paste.gg + pasteUrl = postToService(PasteServiceType.PASTEGG, true, data, files); } else { return; } diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteGGPasteService.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteGGPasteService.java new file mode 100644 index 00000000..179bba00 --- /dev/null +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteGGPasteService.java @@ -0,0 +1,90 @@ +package com.onarandombox.MultiverseCore.utils.webpaste; + +import org.json.simple.JSONArray; +import org.json.simple.JSONObject; +import org.json.simple.parser.JSONParser; +import org.json.simple.parser.ParseException; + +import java.io.IOException; +import java.util.HashMap; +import java.util.Map; + +/** + * Pastes to {@code paste.gg}. + */ +class PasteGGPasteService extends PasteService { + private final boolean isPrivate; + private static final String PASTEGG_POST_REQUEST = "https://api.paste.gg/v1/pastes"; + + PasteGGPasteService(boolean isPrivate) { + super(PASTEGG_POST_REQUEST, null); + this.isPrivate = isPrivate; + } + + /** + * {@inheritDoc} + */ + @Override + String encodeData(String data) { + Map mapData = new HashMap(); + mapData.put("multiverse.txt", data); + return this.encodeData(mapData); + } + + /** + * {@inheritDoc} + */ + @Override + String encodeData(Map files) { + JSONObject root = new JSONObject(); + root.put("name", "Multiverse-Core Debug Info"); + root.put("visibility", this.isPrivate ? "unlisted" : "public"); + JSONArray fileList = new JSONArray(); + for (Map.Entry entry : files.entrySet()) { + JSONObject fileObject = new JSONObject(); + JSONObject contentObject = new JSONObject(); + fileObject.put("name", entry.getKey()); + fileObject.put("content", contentObject); + contentObject.put("format", "text"); + contentObject.put("value", entry.getValue()); + fileList.add(fileObject); + } + + root.put("files", fileList); + return root.toJSONString(); + } + + /** + * {@inheritDoc} + */ + @Override + public String postData(String data) throws PasteFailedException { + try { + String stringJSON = this.exec(encodeData(data), ContentType.JSON); + return (String) ((JSONObject) ((JSONObject) new JSONParser().parse(stringJSON)).get("result")).get("id"); + } catch (IOException | ParseException e) { + throw new PasteFailedException(e); + } + } + + /** + * {@inheritDoc} + */ + @Override + public String postData(Map data) throws PasteFailedException { + try { + String stringJSON = this.exec(encodeData(data), ContentType.JSON); + return "https://paste.gg/" + ((JSONObject) ((JSONObject) new JSONParser().parse(stringJSON)).get("result")).get("id"); + } catch (IOException | ParseException e) { + throw new PasteFailedException(e); + } + } + + /** + * {@inheritDoc} + */ + @Override + public boolean supportsMultiFile() { + return true; + } +} diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceFactory.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceFactory.java index 2275dc58..f6f63a1c 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceFactory.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceFactory.java @@ -14,6 +14,8 @@ public class PasteServiceFactory { */ public static PasteService getService(PasteServiceType type, boolean isPrivate) { switch(type) { + case PASTEGG: + return new PasteGGPasteService(isPrivate); case PASTEBIN: return new PastebinPasteService(isPrivate); case HASTEBIN: diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceType.java b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceType.java index 6b6d7a48..09424c0b 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceType.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/webpaste/PasteServiceType.java @@ -7,6 +7,10 @@ package com.onarandombox.MultiverseCore.utils.webpaste; * @see PasteServiceFactory */ public enum PasteServiceType { + /** + * @see PasteGGPasteService + */ + PASTEGG, /** * @see PastebinPasteService */ From 058c0837f0455d4a967d18dc22290d145482e701 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Sun, 14 Jun 2020 16:04:58 -0400 Subject: [PATCH 026/109] bring multi-file pastes to parity with single file pastes --- .../MultiverseCore/commands/VersionCommand.java | 7 ++++--- .../MultiverseCore/event/MVVersionEvent.java | 9 +++++++++ 2 files changed, 13 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java index 00912846..3f4b26f5 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java @@ -81,7 +81,7 @@ public class VersionCommand extends MultiverseCommand { "| --- | --- |" + System.lineSeparator() + "| Multiverse-Core Version | `" + this.plugin.getDescription().getVersion() + "` |" + System.lineSeparator() + "| Bukkit Version | `" + this.plugin.getServer().getVersion() + "` |" + System.lineSeparator() + - //"| Loaded Worlds | `" + this.plugin.getMVWorldManager().getMVWorlds() + "` |" + System.lineSeparator() + + "| Loaded Worlds | `" + this.plugin.getMVWorldManager().getMVWorlds() + "` |" + System.lineSeparator() + "| Multiverse Plugins Loaded | `" + this.plugin.getPluginCount() + "` |" + System.lineSeparator() + "| Economy being used | `" + plugin.getEconomist().getEconomyName() + "` |" + System.lineSeparator() + "| Permissions Plugin | `" + this.plugin.getMVPerms().getType() + "` |" + System.lineSeparator() + @@ -134,7 +134,7 @@ public class VersionCommand extends MultiverseCommand { File configFile = new File(this.plugin.getDataFolder(), "config.yml"); files.put(configFile.getName(), this.readFile(configFile.getAbsolutePath())); - // Add the config.yml + // Add the worlds.yml File worldConfig = new File(this.plugin.getDataFolder(), "worlds.yml"); files.put(worldConfig.getName(), this.readFile(worldConfig.getAbsolutePath())); return files; @@ -148,13 +148,14 @@ public class VersionCommand extends MultiverseCommand { } MVVersionEvent versionEvent = new MVVersionEvent(this.getLegacyString(), this.getVersionFiles()); - final Map files = this.getVersionFiles(); this.plugin.getServer().getPluginManager().callEvent(versionEvent); String versionInfo = versionEvent.getVersionInfo(); + Map files = versionEvent.getDetailedVersionInfo(); if (CommandHandler.hasFlag("--include-plugin-list", args)) { versionInfo = versionInfo + System.lineSeparator() + "Plugins: " + getPluginList(); + files.put("plugins.txt", "Plugins: " + getPluginList()); } final String data = versionInfo; diff --git a/src/main/java/com/onarandombox/MultiverseCore/event/MVVersionEvent.java b/src/main/java/com/onarandombox/MultiverseCore/event/MVVersionEvent.java index 43c1ddfc..a63d7020 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/event/MVVersionEvent.java +++ b/src/main/java/com/onarandombox/MultiverseCore/event/MVVersionEvent.java @@ -66,4 +66,13 @@ public class MVVersionEvent extends Event { public void appendVersionInfo(String moreVersionInfo) { this.versionInfoBuilder.append(moreVersionInfo); } + + /** + * Adds a file to to the detailed version-info currently saved in this event. + * @param filename The name of the file. + * @param text The file's content. + */ + public void putDetailedVersionInfo(String filename, String text) { + this.detailedVersionInfo.put(filename, text); + } } From d5013546d13c54a9a605bca19b1bf65ab52bcb73 Mon Sep 17 00:00:00 2001 From: Kermina Awad Date: Mon, 29 Jun 2020 11:40:01 -0400 Subject: [PATCH 027/109] don't report generator settings --- .../MultiverseCore/utils/metrics/MetricsConfigurator.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java index fd3470a6..5b34acad 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/metrics/MetricsConfigurator.java @@ -61,7 +61,7 @@ public class MetricsConfigurator { private String getGeneratorName(MultiverseWorld world) { String gen = world.getGenerator(); - return (gen != null && !gen.equalsIgnoreCase("null")) ? gen : NO_GENERATOR_NAME; + return (gen != null && !gen.equalsIgnoreCase("null")) ? gen.split(":")[0] : NO_GENERATOR_NAME; } private void addEnvironmentsMetric() { From 05cf0522044a7a25254ed84d636a9f15181c76b8 Mon Sep 17 00:00:00 2001 From: benwoo1110 <30431861+benwoo1110@users.noreply.github.com> Date: Thu, 27 Aug 2020 01:34:37 +0800 Subject: [PATCH 028/109] Add GitHub issue templates (#2385) * Added issue templates * Fixed a typo * Added more details to template Added dev build link Need to enter `/server` output Declaration that issue is reproducible with only mv plugins * Added capitalization to issue title --- .github/ISSUE_TEMPLATE/help.md | 53 +++++++++++++++++++ .github/ISSUE_TEMPLATE/report-a-bug.md | 56 +++++++++++++++++++++ .github/ISSUE_TEMPLATE/request-a-feature.md | 51 +++++++++++++++++++ 3 files changed, 160 insertions(+) create mode 100644 .github/ISSUE_TEMPLATE/help.md create mode 100644 .github/ISSUE_TEMPLATE/report-a-bug.md create mode 100644 .github/ISSUE_TEMPLATE/request-a-feature.md diff --git a/.github/ISSUE_TEMPLATE/help.md b/.github/ISSUE_TEMPLATE/help.md new file mode 100644 index 00000000..b9aded2f --- /dev/null +++ b/.github/ISSUE_TEMPLATE/help.md @@ -0,0 +1,53 @@ +--- +name: Help! +about: Encountered a problem with Multiverse-Core? Not sure how to fix it? + +--- + + + +### Information + +* **Server version:** + +* **Full output of `/mv version -b`:** + +* **Server log:** + +### Help request + +**Problem** + + +**What I have tried** + + +**Screenshots** + \ No newline at end of file diff --git a/.github/ISSUE_TEMPLATE/report-a-bug.md b/.github/ISSUE_TEMPLATE/report-a-bug.md new file mode 100644 index 00000000..36c8ca05 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/report-a-bug.md @@ -0,0 +1,56 @@ +--- +name: Report a Bug +about: Report an Multiverse-Core bug. Only use this if you're 100% sure it's something wrong with Multiverse-Core - otherwise, try "Help!". + +--- + + + +### Information + +* **Server version:** + +* **Full output of `/mv version -b`:** + +* **Server log:** + +### Details +I was **``** to reproduce my issue on a freshly setup and up-to-date server with the latest version of Multiverse plugins with no other plugins and with no kinds of other server or client mods. + +**Description** + + +**Steps to reproduce** + + +**Expected behavior** + + +**Screenshots** + \ No newline at end of file diff --git a/.github/ISSUE_TEMPLATE/request-a-feature.md b/.github/ISSUE_TEMPLATE/request-a-feature.md new file mode 100644 index 00000000..28f8fdd9 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/request-a-feature.md @@ -0,0 +1,51 @@ +--- +name: Request a Feature +about: Suggest a feature you want to see in Multiverse-Core! + +--- + + + +### Feature request + +**Feature description** + + +**How the feature is useful** + \ No newline at end of file From e1494808f3b2aa0fd667e339aa35a571aeab2783 Mon Sep 17 00:00:00 2001 From: benwoo1110 <30431861+benwoo1110@users.noreply.github.com> Date: Thu, 27 Aug 2020 20:47:57 +0800 Subject: [PATCH 029/109] Fixed inability to clone due to unable to copy session.lock (#2392) * Added ability to exclude files when copying folders * Remove wildcard imports * Added unit testing for ignoring files as well Co-authored-by: wben1110 (desktop) --- .../MultiverseCore/utils/FileUtils.java | 29 ++++++++++++++--- .../MultiverseCore/utils/WorldManager.java | 12 +++---- .../MultiverseCore/utils/FileUtilsTest.java | 31 +++++++++++++++++++ 3 files changed, 60 insertions(+), 12 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/FileUtils.java b/src/main/java/com/onarandombox/MultiverseCore/utils/FileUtils.java index ce793306..47fa80ed 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/FileUtils.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/FileUtils.java @@ -16,7 +16,9 @@ import java.nio.file.Files; import java.nio.file.Path; import java.nio.file.SimpleFileVisitor; import java.nio.file.attribute.BasicFileAttributes; +import java.util.Arrays; import java.util.Comparator; +import java.util.List; import java.util.logging.Level; import java.util.logging.Logger; import java.util.stream.Stream; @@ -72,14 +74,27 @@ public class FileUtils { * @param target Target-File * @param log A logger that logs the operation * - * @return if it had success + * @return true if it had success */ public static boolean copyFolder(File source, File target, Logger log) { + return copyFolder(source, target, null, log); + } + + /** + * Helper method to copy the world-folder. + * @param source Source-File + * @param target Target-File + * @param excludeFiles files to ignore and not copy over to Target-File + * @param log A logger that logs the operation + * + * @return true if it had success + */ + public static boolean copyFolder(File source, File target, List excludeFiles, Logger log) { Path sourceDir = source.toPath(); Path targetDir = target.toPath(); try { - Files.walkFileTree(sourceDir, new CopyDirFileVisitor(sourceDir, targetDir)); + Files.walkFileTree(sourceDir, new CopyDirFileVisitor(sourceDir, targetDir, excludeFiles)); return true; } catch (IOException e) { log.log(Level.WARNING, "Unable to copy directory", e); @@ -91,10 +106,12 @@ public class FileUtils { private final Path sourceDir; private final Path targetDir; + private final List excludeFiles; - private CopyDirFileVisitor(Path sourceDir, Path targetDir) { + private CopyDirFileVisitor(Path sourceDir, Path targetDir, List excludeFiles) { this.sourceDir = sourceDir; this.targetDir = targetDir; + this.excludeFiles = excludeFiles; } @Override @@ -108,9 +125,13 @@ public class FileUtils { @Override public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException { + // Pass files that are set to ignore + if (excludeFiles != null && excludeFiles.contains(file.getFileName().toString())) + return FileVisitResult.CONTINUE; + // Copy the files Path targetFile = targetDir.resolve(sourceDir.relativize(file)); Files.copy(file, targetFile, COPY_ATTRIBUTES); return FileVisitResult.CONTINUE; } } -} +} \ No newline at end of file diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java b/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java index d3fcb8c6..fb72d810 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java @@ -43,6 +43,7 @@ import java.util.Map; import java.util.Random; import java.util.Set; import java.util.Stack; +import java.util.Arrays; import java.util.concurrent.Callable; import java.util.concurrent.ConcurrentHashMap; import java.util.logging.Level; @@ -127,6 +128,7 @@ public class WorldManager implements MVWorldManager { final File oldWorldFile = new File(this.plugin.getServer().getWorldContainer(), oldName); final File newWorldFile = new File(this.plugin.getServer().getWorldContainer(), newName); + final List ignoreFiles = new ArrayList<>(Arrays.asList("session.lock", "uid.dat")); // Make sure the new world doesn't exist outside of multiverse. if (newWorldFile.exists()) { @@ -177,20 +179,14 @@ public class WorldManager implements MVWorldManager { oldWorld.getCBWorld().save(); } Logging.config("Copying files for world '%s'", oldName); - if (!FileUtils.copyFolder(oldWorldFile, newWorldFile, Logging.getLogger())) { + if (!FileUtils.copyFolder(oldWorldFile, newWorldFile, ignoreFiles, Logging.getLogger())) { Logging.warning("Failed to copy files for world '%s', see the log info", newName); return false; } if (oldWorld != null && wasAutoSave) { oldWorld.getCBWorld().setAutoSave(true); } - - File uidFile = new File(newWorldFile, "uid.dat"); - if (uidFile.exists() && !uidFile.delete()) { - Logging.warning("Failed to delete unique ID file for world '%s'", newName); - return false; - } - + if (newWorldFile.exists()) { Logging.fine("Succeeded at copying files"); if (this.addWorld(newName, environment, seedString, worldType, generateStructures, generator, useSpawnAdjust)) { diff --git a/src/test/java/com/onarandombox/MultiverseCore/utils/FileUtilsTest.java b/src/test/java/com/onarandombox/MultiverseCore/utils/FileUtilsTest.java index 0b5da6f0..015d2542 100644 --- a/src/test/java/com/onarandombox/MultiverseCore/utils/FileUtilsTest.java +++ b/src/test/java/com/onarandombox/MultiverseCore/utils/FileUtilsTest.java @@ -6,6 +6,9 @@ import static org.junit.Assert.assertTrue; import java.io.IOException; import java.nio.file.Files; import java.nio.file.Path; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; import com.dumptruckman.minecraft.util.Logging; import org.junit.After; @@ -86,6 +89,34 @@ public class FileUtilsTest { assertTrue(Files.isRegularFile(targetChildDirFile)); } + @Test + public void copyFolder_excludingSomeFiles() throws Exception { + Path targetDir = tempDir.resolve("target"); + Path targetFile = targetDir.resolve("parentDirFile.txt"); + Path targetIgnoreFile = targetDir.resolve("parentIgnoreFile.txt"); + Path targetChildDir = targetDir.resolve("childDir"); + Path targetChildDirFile = targetChildDir.resolve("childDirFile.txt"); + Path targetChildIgnoreFile = targetChildDir.resolve("childIgnoreFile.txt"); + + List excludeFiles = new ArrayList<>(Arrays.asList("parentIgnoreFile.txt", "childIgnoreFile.txt")); + + assertFalse(Files.isDirectory(targetDir)); + assertFalse(Files.isRegularFile(targetFile)); + assertFalse(Files.isRegularFile(targetIgnoreFile)); + assertFalse(Files.isDirectory(targetChildDir)); + assertFalse(Files.isRegularFile(targetChildDirFile)); + assertFalse(Files.isRegularFile(targetChildIgnoreFile)); + + assertTrue(FileUtils.copyFolder(parentDir.toFile(), targetDir.toFile(), excludeFiles, Logging.getLogger())); + + assertTrue(Files.isDirectory(targetDir)); + assertTrue(Files.isRegularFile(targetFile)); + assertFalse(Files.isRegularFile(targetIgnoreFile)); + assertTrue(Files.isDirectory(targetChildDir)); + assertTrue(Files.exists(targetChildDirFile)); + assertFalse(Files.isRegularFile(targetChildIgnoreFile)); + } + @Test public void copyFolder_intoExistingFolder() throws Exception { Path targetDir = Files.createDirectory(tempDir.resolve("target")); From faf20ee36eb92127862433950a3807bf935666e2 Mon Sep 17 00:00:00 2001 From: Jad Date: Thu, 10 Sep 2020 18:09:58 -0500 Subject: [PATCH 030/109] A, not an :P --- .github/ISSUE_TEMPLATE/report-a-bug.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/ISSUE_TEMPLATE/report-a-bug.md b/.github/ISSUE_TEMPLATE/report-a-bug.md index 36c8ca05..9d69d3c0 100644 --- a/.github/ISSUE_TEMPLATE/report-a-bug.md +++ b/.github/ISSUE_TEMPLATE/report-a-bug.md @@ -1,6 +1,6 @@ --- name: Report a Bug -about: Report an Multiverse-Core bug. Only use this if you're 100% sure it's something wrong with Multiverse-Core - otherwise, try "Help!". +about: Report a Multiverse-Core bug. Only use this if you're 100% sure it's something wrong with Multiverse-Core - otherwise, try "Help!". --- @@ -53,4 +53,4 @@ I was **``** to reproduce my issue on a freshly setup and up-to **Screenshots** - \ No newline at end of file + From 51e035eb3e8b9a125654c25ce27509d14a4a58ca Mon Sep 17 00:00:00 2001 From: nicegamer7 Date: Tue, 22 Sep 2020 15:02:03 -0400 Subject: [PATCH 031/109] Update GameMode command and increase Java support. (#2279) * update gamerule command * fix NPE in gamerules command and remove deprecated method * catch buscript initialization errors * update gamerule command to be more descriptive * undo GameruleCommand style changes * update legacy version reporting to include all config options * use LF line ending for files being pasted to the web * avoid duplicate code --- .../MultiverseCore/MultiverseCore.java | 11 ++-- .../commands/GameruleCommand.java | 50 ++++++++++++++++--- .../commands/GamerulesCommand.java | 8 ++- .../commands/ScriptCommand.java | 4 ++ .../commands/VersionCommand.java | 20 +++++--- 5 files changed, 75 insertions(+), 18 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java b/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java index 43820a5a..b4168ae0 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java +++ b/src/main/java/com/onarandombox/MultiverseCore/MultiverseCore.java @@ -350,9 +350,14 @@ public class MultiverseCore extends JavaPlugin implements MVPlugin, Core { * Initializes the buscript javascript library. */ private void initializeBuscript() { - buscript = new Buscript(this); - // Add global variable "multiverse" to javascript environment - buscript.setScriptVariable("multiverse", this); + try { + buscript = new Buscript(this); + // Add global variable "multiverse" to javascript environment + buscript.setScriptVariable("multiverse", this); + } catch (NullPointerException e) { + buscript = null; + Logging.warning("Buscript failed to load! The script command will be disabled!"); + } } private void initializeDestinationFactory() { diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/GameruleCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/GameruleCommand.java index 01eddae6..ca0e1e07 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/GameruleCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/GameruleCommand.java @@ -10,6 +10,7 @@ package com.onarandombox.MultiverseCore.commands; import com.onarandombox.MultiverseCore.MultiverseCore; import org.bukkit.Bukkit; import org.bukkit.ChatColor; +import org.bukkit.GameRule; import org.bukkit.World; import org.bukkit.command.CommandSender; import org.bukkit.entity.Player; @@ -55,7 +56,7 @@ public class GameruleCommand extends MultiverseCommand { return; } - final String gameRule = args.get(0); + final GameRule gameRule = GameRule.getByName(args.get(0)); final String value = args.get(1); final World world; if (args.size() == 2) { @@ -64,17 +65,52 @@ public class GameruleCommand extends MultiverseCommand { world = Bukkit.getWorld(args.get(2)); if (world == null) { sender.sendMessage(ChatColor.RED + "Failure!" + ChatColor.WHITE + " World " + ChatColor.AQUA + args.get(2) - + ChatColor.WHITE + " does not exist."); + + ChatColor.WHITE + " does not exist."); return; } } - if (world.setGameRuleValue(gameRule, value)) { - sender.sendMessage(ChatColor.GREEN + "Success!" + ChatColor.WHITE + " Gamerule " + ChatColor.AQUA + gameRule - + ChatColor.WHITE + " was set to " + ChatColor.GREEN + value); + if (gameRule == null) { + sender.sendMessage(ChatColor.RED + "Failure! " + ChatColor.AQUA + args.get(0) + ChatColor.WHITE + + " is not a valid gamerule."); } else { - sender.sendMessage(ChatColor.RED + "Failure!" + ChatColor.WHITE + " Gamerule " + ChatColor.AQUA + gameRule - + ChatColor.WHITE + " cannot be set to " + ChatColor.RED + value); + if (gameRule.getType() == Boolean.class) { + boolean booleanValue; + if (value.equalsIgnoreCase("true")) { + booleanValue = true; + } else if (value.equalsIgnoreCase("false")) { + booleanValue = false; + } else { + sender.sendMessage(getErrorMessage(gameRule.getName(), value) + "it can only be set to true or false."); + return; + } + + if (!world.setGameRule(gameRule, booleanValue)) { + sender.sendMessage(getErrorMessage(gameRule.getName(), value) + "something went wrong."); + return; + } + } else if (gameRule.getType() == Integer.class) { + try { + if (!world.setGameRule(gameRule, Integer.parseInt(value))) { + throw new NumberFormatException(); + } + } catch (NumberFormatException e) { + sender.sendMessage(getErrorMessage(gameRule.getName(), value) + "it can only be set to a positive integer."); + return; + } + } else { + sender.sendMessage(ChatColor.RED + "Failure!" + ChatColor.WHITE + " Gamerule " + ChatColor.AQUA + gameRule.getName() + + ChatColor.WHITE + " isn't supported yet, please let us know about it."); + return; + } + + sender.sendMessage(ChatColor.GREEN + "Success!" + ChatColor.WHITE + " Gamerule " + ChatColor.AQUA + gameRule.getName() + + ChatColor.WHITE + " was set to " + ChatColor.GREEN + value + ChatColor.WHITE + "."); } } + + private String getErrorMessage(String gameRule, String value) { + return ChatColor.RED + "Failure!" + ChatColor.WHITE + " Gamerule " + ChatColor.AQUA + gameRule + + ChatColor.WHITE + " could not be set to " + ChatColor.RED + value + ChatColor.WHITE + ", "; + } } diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/GamerulesCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/GamerulesCommand.java index 321ac090..62b3e060 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/GamerulesCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/GamerulesCommand.java @@ -10,6 +10,7 @@ package com.onarandombox.MultiverseCore.commands; import com.onarandombox.MultiverseCore.MultiverseCore; import org.bukkit.Bukkit; import org.bukkit.ChatColor; +import org.bukkit.GameRule; import org.bukkit.World; import org.bukkit.command.CommandSender; import org.bukkit.entity.Player; @@ -60,6 +61,11 @@ public class GamerulesCommand extends MultiverseCommand { world = p.getWorld(); } else { world = Bukkit.getWorld(args.get(0)); + if (world == null) { + sender.sendMessage(ChatColor.RED + "Failure!" + ChatColor.WHITE + " World " + ChatColor.AQUA + args.get(0) + + ChatColor.WHITE + " does not exist."); + return; + } } final StringBuilder gameRules = new StringBuilder(); @@ -68,7 +74,7 @@ public class GamerulesCommand extends MultiverseCommand { gameRules.append(ChatColor.WHITE).append(", "); } gameRules.append(ChatColor.AQUA).append(gameRule).append(ChatColor.WHITE).append(": "); - gameRules.append(ChatColor.GREEN).append(world.getGameRuleValue(gameRule)); + gameRules.append(ChatColor.GREEN).append(world.getGameRuleValue(GameRule.getByName(gameRule))); } sender.sendMessage("=== Gamerules for " + ChatColor.AQUA + world.getName() + ChatColor.WHITE + " ==="); sender.sendMessage(gameRules.toString()); diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/ScriptCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/ScriptCommand.java index 2896a8e7..665f6aa7 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/ScriptCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/ScriptCommand.java @@ -35,6 +35,10 @@ public class ScriptCommand extends MultiverseCommand { @Override public void runCommand(CommandSender sender, List args) { + if (plugin.getScriptAPI() == null) { + sender.sendMessage("Buscript failed to load while the server was starting. Scripts cannot be run."); + return; + } File file = new File(plugin.getScriptAPI().getScriptFolder(), args.get(0)); if (!file.exists()) { sender.sendMessage("That script file does not exist in the Multiverse-Core scripts directory!"); diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java index 3f4b26f5..29ac54d4 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java @@ -61,16 +61,22 @@ public class VersionCommand extends MultiverseCommand { "[Multiverse-Core] Economy being used: " + plugin.getEconomist().getEconomyName() + System.lineSeparator() + "[Multiverse-Core] Permissions Plugin: " + this.plugin.getMVPerms().getType() + System.lineSeparator() + "[Multiverse-Core] Dumping Config Values: (version " + this.plugin.getMVConfig().getVersion() + ")" + System.lineSeparator() + - "[Multiverse-Core] messagecooldown: " + plugin.getMessaging().getCooldown() + System.lineSeparator() + - "[Multiverse-Core] teleportcooldown: " + plugin.getMVConfig().getTeleportCooldown() + System.lineSeparator() + - "[Multiverse-Core] worldnameprefix: " + plugin.getMVConfig().getPrefixChat() + System.lineSeparator() + - "[Multiverse-Core] worldnameprefixFormat: " + plugin.getMVConfig().getPrefixChatFormat() + System.lineSeparator() + "[Multiverse-Core] enforceaccess: " + plugin.getMVConfig().getEnforceAccess() + System.lineSeparator() + - "[Multiverse-Core] displaypermerrors: " + plugin.getMVConfig().getDisplayPermErrors() + System.lineSeparator() + + "[Multiverse-Core] prefixchat: " + plugin.getMVConfig().getPrefixChat() + System.lineSeparator() + + "[Multiverse-Core] prefixchatformat: " + plugin.getMVConfig().getPrefixChatFormat() + System.lineSeparator() + + "[Multiverse-Core] useasyncchat: " + plugin.getMVConfig().getUseAsyncChat() + System.lineSeparator() + "[Multiverse-Core] teleportintercept: " + plugin.getMVConfig().getTeleportIntercept() + System.lineSeparator() + "[Multiverse-Core] firstspawnoverride: " + plugin.getMVConfig().getFirstSpawnOverride() + System.lineSeparator() + + "[Multiverse-Core] displaypermerrors: " + plugin.getMVConfig().getDisplayPermErrors() + System.lineSeparator() + + "[Multiverse-Core] globaldebug: " + plugin.getMVConfig().getGlobalDebug() + System.lineSeparator() + + "[Multiverse-Core] silentstart: " + plugin.getMVConfig().getSilentStart() + System.lineSeparator() + + "[Multiverse-Core] messagecooldown: " + plugin.getMessaging().getCooldown() + System.lineSeparator() + + "[Multiverse-Core] version: " + plugin.getMVConfig().getVersion() + System.lineSeparator() + "[Multiverse-Core] firstspawnworld: " + plugin.getMVConfig().getFirstSpawnWorld() + System.lineSeparator() + - "[Multiverse-Core] debug: " + plugin.getMVConfig().getGlobalDebug() + System.lineSeparator() + + "[Multiverse-Core] teleportcooldown: " + plugin.getMVConfig().getTeleportCooldown() + System.lineSeparator() + + "[Multiverse-Core] defaultportalsearch: " + plugin.getMVConfig().isUsingDefaultPortalSearch() + System.lineSeparator() + + "[Multiverse-Core] portalsearchradius: " + plugin.getMVConfig().getPortalSearchRadius() + System.lineSeparator() + + "[Multiverse-Core] autopurge: " + plugin.getMVConfig().isAutoPurgeEnabled() + System.lineSeparator() + "[Multiverse-Core] Special Code: FRN002" + System.lineSeparator(); } @@ -110,7 +116,7 @@ public class VersionCommand extends MultiverseCommand { String line; result = new StringBuilder(); while ((line = bufferedReader.readLine()) != null) { - result.append(line).append(System.lineSeparator()); + result.append(line).append("\n"); } } catch (FileNotFoundException e) { Logging.severe("Unable to find %s. Here's the traceback: %s", filename, e.getMessage()); From b8acd339b3e3b56ec48f590782a2a5ca5d081672 Mon Sep 17 00:00:00 2001 From: Robert Timm Date: Fri, 14 Aug 2020 00:10:54 +0200 Subject: [PATCH 032/109] load cloned world with doLoad() instead of addWorld() (fixes #2378) --- .../MultiverseCore/utils/WorldManager.java | 31 ++++++++++++++----- 1 file changed, 23 insertions(+), 8 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java b/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java index d3fcb8c6..ef8e75b9 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java +++ b/src/main/java/com/onarandombox/MultiverseCore/utils/WorldManager.java @@ -193,16 +193,31 @@ public class WorldManager implements MVWorldManager { if (newWorldFile.exists()) { Logging.fine("Succeeded at copying files"); - if (this.addWorld(newName, environment, seedString, worldType, generateStructures, generator, useSpawnAdjust)) { - // getMVWorld() doesn't actually return an MVWorld - Logging.fine("Succeeded at importing world"); - MVWorld newWorld = (MVWorld) this.getMVWorld(newName); - newWorld.copyValues(this.worldsFromTheConfig.get(oldName)); - // don't keep the alias the same -- that would be useless - newWorld.setAlias(""); - return true; + + // initialize new properties with old ones + WorldProperties newProps = new WorldProperties(); + newProps.copyValues(this.worldsFromTheConfig.get(oldName)); + // don't keep the alias the same -- that would be useless + newProps.setAlias(""); + // store the new properties in worlds config map + this.worldsFromTheConfig.put(newName, newProps); + + // save the worlds config to disk (worlds.yml) + if (!saveWorldsConfig()) { + this.plugin.log(Level.SEVERE, "Failed to save worlds.yml"); + return false; } + + // actually load the world + if (doLoad(newName)) { + this.plugin.log(Level.FINE, "Succeeded at loading cloned world '" + newName + "'"); + return true; + } + + this.plugin.log(Level.SEVERE, "Failed to load the cloned world '" + newName + "'"); + return false; } + Logging.warning("Failed to copy files for world '%s', see the log info", newName); return false; } From 9159dfbb7dd833c31f13755c564929201daeefff Mon Sep 17 00:00:00 2001 From: benwoo1110 Date: Mon, 5 Oct 2020 00:28:48 +0800 Subject: [PATCH 033/109] Updated plugin.yml commands and some missing alias --- .../MultiverseCore/commands/ListCommand.java | 2 +- .../commands/ReloadCommand.java | 1 + .../commands/SetSpawnCommand.java | 1 + .../commands/TeleportCommand.java | 2 +- .../commands/VersionCommand.java | 3 +- src/main/resources/plugin.yml | 174 +++++++----------- 6 files changed, 68 insertions(+), 115 deletions(-) diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/ListCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/ListCommand.java index e63ea4f2..d702bf93 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/ListCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/ListCommand.java @@ -26,7 +26,7 @@ public class ListCommand extends PaginatedCoreCommand { public ListCommand(MultiverseCore plugin) { super(plugin); this.setName("World Listing"); - this.setCommandUsage("/mv list"); + this.setCommandUsage("/mv list [page]"); this.setArgRange(0, 2); this.addKey("mvlist"); this.addKey("mvl"); diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/ReloadCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/ReloadCommand.java index 3481a4ea..abe2b0a6 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/ReloadCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/ReloadCommand.java @@ -27,6 +27,7 @@ public class ReloadCommand extends MultiverseCommand { this.setCommandUsage("/mv reload"); this.setArgRange(0, 0); this.addKey("mvreload"); + this.addKey("mvr"); this.addKey("mv reload"); this.addCommandExample("/mv reload"); this.setPermission("multiverse.core.reload", "Reloads worlds.yml and config.yml.", PermissionDefault.OP); diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/SetSpawnCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/SetSpawnCommand.java index 2c3c25a8..26dad442 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/SetSpawnCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/SetSpawnCommand.java @@ -30,6 +30,7 @@ public class SetSpawnCommand extends MultiverseCommand { this.setCommandUsage("/mv setspawn"); this.setArgRange(0, 6); this.addKey("mvsetspawn"); + this.addKey("mvsets"); this.addKey("mvss"); this.addKey("mv set spawn"); this.addKey("mv setspawn"); diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/TeleportCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/TeleportCommand.java index 847aa6d4..6f8264f4 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/TeleportCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/TeleportCommand.java @@ -40,7 +40,7 @@ public class TeleportCommand extends MultiverseCommand { Permission menu = new Permission("multiverse.teleport.*", "Allows you to display the teleport menu.", PermissionDefault.OP); this.setName("Teleport"); - this.setCommandUsage("/mv tp " + ChatColor.GOLD + "[PLAYER]" + ChatColor.GREEN + " {WORLD}"); + this.setCommandUsage("/mv tp " + ChatColor.GOLD + "[PLAYER]" + ChatColor.GREEN + " {DESTINATION}"); this.setArgRange(1, 2); this.addKey("mvtp"); this.addKey("mv tp"); diff --git a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java index 29ac54d4..9145a0c7 100644 --- a/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java +++ b/src/main/java/com/onarandombox/MultiverseCore/commands/VersionCommand.java @@ -44,9 +44,10 @@ public class VersionCommand extends MultiverseCommand { public VersionCommand(MultiverseCore plugin) { super(plugin); this.setName("Multiverse Version"); - this.setCommandUsage("/mv version " + ChatColor.GOLD + "-[bhp] [--include-plugin-list]"); + this.setCommandUsage("/mv version " + ChatColor.GOLD + "[-b|-h|-p] [--include-plugin-list]"); this.setArgRange(0, 2); this.addKey("mv version"); + this.addKey("mvver"); this.addKey("mvv"); this.addKey("mvversion"); this.setPermission("multiverse.core.version", diff --git a/src/main/resources/plugin.yml b/src/main/resources/plugin.yml index 5359af21..d46f0fd7 100644 --- a/src/main/resources/plugin.yml +++ b/src/main/resources/plugin.yml @@ -11,34 +11,24 @@ commands: usage: / mvcreate: description: World create command - usage: | - / - / creative normal -- Creates a world called 'creative' with a NORMAL environment. - / hellworld nether -- Creates a world called 'hellworld' with a NETHER environment. - mvc: - description: World create command + aliases: [mvc] usage: | / / creative normal -- Creates a world called 'creative' with a NORMAL environment. / hellworld nether -- Creates a world called 'hellworld' with a NETHER environment. mvimport: description: World import command + aliases: [mvim] usage: | - / - / creative normal -- Imports an existing world called 'creative' with a NORMAL environment. - / hellworld nether -- Imports an existing world called 'hellworld' with a NETHER environment. - mvim: - description: World import command - usage: | - / - / creative normal -- Imports an existing world called 'creative' with a NORMAL environment. - / hellworld nether -- Imports an existing world called 'hellworld' with a NETHER environment. + / [-g generator[:id]] [-n] + / creative normal -- Imports an existing world called 'creative' with a NORMAL environment. + / hellworld nether -- Imports an existing world called 'hellworld' with a NETHER environment. mvremove: - description: World remove command + description: Remove world from multiverse command usage: | / mvdelete: - description: World delete command + description: Delete world from server folders command usage: | / mvunload: @@ -47,103 +37,75 @@ commands: / mvmodify: description: Modify the settings of an existing world + aliases: [mvm] usage: | - /