Update checking, plugin disabling, code cleanup

Now compatible with various plugin managers:
- Will attempt to unload depending/softdepending plugins on disable
- Will attempt to load disabled depending/softdepending plugins on
enable

Update checking:
- Currently subscribed to be notified about updates on Spigot
- You can use "/plot update" to download the latest version, or specify
a new source URL

Plugin disabling:
- new command /plot disable
This commit is contained in:
boy0001 2015-07-06 19:38:37 +10:00
parent e0941c6225
commit 0b0461f5f4
16 changed files with 579 additions and 128 deletions

View File

@ -8,7 +8,7 @@
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties> </properties>
<artifactId>PlotSquared</artifactId> <artifactId>PlotSquared</artifactId>
<version>2.11.27</version> <version>2.12.0</version>
<name>PlotSquared</name> <name>PlotSquared</name>
<packaging>jar</packaging> <packaging>jar</packaging>
<build> <build>

View File

@ -1,21 +1,35 @@
package com.intellectualcrafters.plot; package com.intellectualcrafters.plot;
import java.io.File; import java.io.File;
import java.io.IOException;
import java.io.PrintWriter;
import java.lang.reflect.Field;
import java.net.URLClassLoader;
import java.nio.file.Files;
import java.util.Arrays; import java.util.Arrays;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Stack;
import java.util.UUID; import java.util.UUID;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.ChatColor; import org.bukkit.ChatColor;
import org.bukkit.Chunk; import org.bukkit.Chunk;
import org.bukkit.World; import org.bukkit.World;
import org.bukkit.command.Command;
import org.bukkit.command.PluginCommand; import org.bukkit.command.PluginCommand;
import org.bukkit.command.SimpleCommandMap;
import org.bukkit.entity.Entity; import org.bukkit.entity.Entity;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.event.Listener; import org.bukkit.event.Listener;
import org.bukkit.generator.ChunkGenerator; import org.bukkit.generator.ChunkGenerator;
import org.bukkit.plugin.Plugin; import org.bukkit.plugin.Plugin;
import org.bukkit.plugin.PluginManager;
import org.bukkit.plugin.java.JavaPlugin; import org.bukkit.plugin.java.JavaPlugin;
import org.bukkit.plugin.java.JavaPluginLoader;
import com.intellectualcrafters.plot.commands.Add; import com.intellectualcrafters.plot.commands.Add;
import com.intellectualcrafters.plot.commands.Auto; import com.intellectualcrafters.plot.commands.Auto;
@ -42,6 +56,7 @@ import com.intellectualcrafters.plot.commands.DebugSaveTest;
import com.intellectualcrafters.plot.commands.DebugUUID; import com.intellectualcrafters.plot.commands.DebugUUID;
import com.intellectualcrafters.plot.commands.Delete; import com.intellectualcrafters.plot.commands.Delete;
import com.intellectualcrafters.plot.commands.Deny; import com.intellectualcrafters.plot.commands.Deny;
import com.intellectualcrafters.plot.commands.Disable;
import com.intellectualcrafters.plot.commands.FlagCmd; import com.intellectualcrafters.plot.commands.FlagCmd;
import com.intellectualcrafters.plot.commands.Help; import com.intellectualcrafters.plot.commands.Help;
import com.intellectualcrafters.plot.commands.Home; import com.intellectualcrafters.plot.commands.Home;
@ -73,6 +88,7 @@ import com.intellectualcrafters.plot.commands.Unclaim;
import com.intellectualcrafters.plot.commands.Undeny; import com.intellectualcrafters.plot.commands.Undeny;
import com.intellectualcrafters.plot.commands.Unlink; import com.intellectualcrafters.plot.commands.Unlink;
import com.intellectualcrafters.plot.commands.Untrust; import com.intellectualcrafters.plot.commands.Untrust;
import com.intellectualcrafters.plot.commands.Update;
import com.intellectualcrafters.plot.commands.Visit; import com.intellectualcrafters.plot.commands.Visit;
import com.intellectualcrafters.plot.commands.WE_Anywhere; import com.intellectualcrafters.plot.commands.WE_Anywhere;
import com.intellectualcrafters.plot.commands.list; import com.intellectualcrafters.plot.commands.list;
@ -152,8 +168,7 @@ public class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
if (version.length == 3) { if (version.length == 3) {
version[2] = Integer.parseInt(split[2]); version[2] = Integer.parseInt(split[2]);
} }
} } catch (Exception e) {
catch (Exception e) {
return false; return false;
} }
} }
@ -175,6 +190,18 @@ public class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
} else { } else {
log("&dUsing metrics will allow us to improve the plugin, please consider it :)"); log("&dUsing metrics will allow us to improve the plugin, please consider it :)");
} }
File file = new File(this.getDirectory() + File.separator + "disabled.yml");
if (file.exists()) {
try {
String[] split = new String(Files.readAllBytes(file.toPath())).split(",");
for (String plugin : split) {
loadPlugin(plugin);
}
} catch (IOException e) {
e.printStackTrace();
}
file.delete();
}
List<World> worlds = Bukkit.getWorlds(); List<World> worlds = Bukkit.getWorlds();
if (worlds.size() > 0) { if (worlds.size() > 0) {
UUIDHandler.cacheAll(worlds.get(0).getName()); UUIDHandler.cacheAll(worlds.get(0).getName());
@ -189,10 +216,13 @@ public class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
} }
} }
@Override @Override
public void onDisable() { public void onDisable() {
PS.get().disable(); PS.get().disable();
try {
unloadRecursively(this);
}
catch (Exception e) {};
THIS = null; THIS = null;
} }
@ -202,15 +232,18 @@ public class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
return; return;
} }
message = message.replaceAll("\u00B2", "2"); message = message.replaceAll("\u00B2", "2");
if ((THIS == null) || (Bukkit.getServer().getConsoleSender() == null)) { if (THIS != null && Bukkit.getServer().getConsoleSender() != null) {
System.out.println(ChatColor.stripColor(ConsoleColors.fromString(message))); try {
} else { message = ChatColor.translateAlternateColorCodes('&', message);
message = ChatColor.translateAlternateColorCodes('&', message); if (!Settings.CONSOLE_COLOR) {
if (!Settings.CONSOLE_COLOR) { message = ChatColor.stripColor(message);
message = ChatColor.stripColor(message); }
Bukkit.getServer().getConsoleSender().sendMessage(message);
return;
} }
Bukkit.getServer().getConsoleSender().sendMessage(message); catch (Throwable e) {};
} }
System.out.println(ConsoleColors.fromString(message));
} }
@Override @Override
@ -235,6 +268,8 @@ public class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
@Override @Override
public void registerCommands() { public void registerCommands() {
new MainCommand(); new MainCommand();
MainCommand.subCommands.add(new Disable());
MainCommand.subCommands.add(new Update());
MainCommand.subCommands.add(new Template()); MainCommand.subCommands.add(new Template());
MainCommand.subCommands.add(new Setup()); MainCommand.subCommands.add(new Setup());
MainCommand.subCommands.add(new DebugUUID()); MainCommand.subCommands.add(new DebugUUID());
@ -257,14 +292,12 @@ public class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
if (Settings.ENABLE_CLUSTERS) { if (Settings.ENABLE_CLUSTERS) {
MainCommand.subCommands.add(new Cluster()); MainCommand.subCommands.add(new Cluster());
} }
MainCommand.subCommands.add(new Trust()); MainCommand.subCommands.add(new Trust());
MainCommand.subCommands.add(new Add()); MainCommand.subCommands.add(new Add());
MainCommand.subCommands.add(new Deny()); MainCommand.subCommands.add(new Deny());
MainCommand.subCommands.add(new Untrust()); MainCommand.subCommands.add(new Untrust());
MainCommand.subCommands.add(new Remove()); MainCommand.subCommands.add(new Remove());
MainCommand.subCommands.add(new Undeny()); MainCommand.subCommands.add(new Undeny());
MainCommand.subCommands.add(new Info()); MainCommand.subCommands.add(new Info());
MainCommand.subCommands.add(new list()); MainCommand.subCommands.add(new list());
MainCommand.subCommands.add(new Help()); MainCommand.subCommands.add(new Help());
@ -355,6 +388,163 @@ public class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
}, 20); }, 20);
} }
public boolean unloadPlugin(Plugin plugin) {
try {
plugin.getClass().getClassLoader().getResources("*");
} catch (IOException e1) {
e1.printStackTrace();
}
PluginManager pm = Bukkit.getServer().getPluginManager();
Map<String, Plugin> ln;
List<Plugin> pl;
try {
Field lnF = pm.getClass().getDeclaredField("lookupNames");
lnF.setAccessible(true);
ln = (Map) lnF.get(pm);
Field plF = pm.getClass().getDeclaredField("plugins");
plF.setAccessible(true);
pl = (List) plF.get(pm);
} catch (Exception e) {
e.printStackTrace();
return false;
}
pm.disablePlugin(plugin);
synchronized (pm) {
ln.remove(plugin.getName());
pl.remove(plugin);
}
JavaPluginLoader jpl = (JavaPluginLoader) plugin.getPluginLoader();
Field loadersF = null;
try {
loadersF = jpl.getClass().getDeclaredField("loaders");
loadersF.setAccessible(true);
} catch (Exception e) {
e.printStackTrace();
}
try {
Map<String, ?> loaderMap = (Map) loadersF.get(jpl);
loaderMap.remove(plugin.getDescription().getName());
} catch (Exception e) {
e.printStackTrace();
}
closeClassLoader(plugin);
System.gc();
System.gc();
return true;
}
public boolean closeClassLoader(Plugin plugin) {
try {
((URLClassLoader) plugin.getClass().getClassLoader()).close();
return true;
} catch (IOException e) {
e.printStackTrace();
}
return false;
}
public boolean unloadRecursively(Plugin plugin) {
try {
Stack<String> pluginFiles = unloadRecursively(plugin.getName(), plugin, new Stack());
File file = new File(this.getDirectory() + File.separator + "disabled.yml");
file.createNewFile();
String prefix = "";
String all = "";
while (pluginFiles.size() > 0) {
String pop = pluginFiles.pop();
all += prefix + pop.substring(0, pop.length() - 4);
prefix = ",";
}
if (all.length() != 0) {
PrintWriter out = new PrintWriter(this.getDirectory() + File.separator + "disabled.yml");
out.write(all);
out.close();
}
} catch (Exception e) {
e.printStackTrace();
}
return true;
}
@Override
public void loadPlugin(String name) {
try {
PluginManager manager = Bukkit.getServer().getPluginManager();
Plugin plugin = manager.getPlugin(name);
if (plugin != null) {
manager.enablePlugin(plugin);
return;
}
plugin = manager.loadPlugin(new File("plugins" + File.separator + name + (name.endsWith(".jar") ? "" : ".jar")));
plugin.onLoad();
manager.enablePlugin(plugin);
} catch (Exception e) {}
}
@Override
public File getFile() {
return getFile(this);
}
public File getFile(JavaPlugin p) {
try {
Field f = JavaPlugin.class.getDeclaredField("file");
f.setAccessible(true);
return (File) f.get(p);
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
public Stack<String> unloadRecursively(String doNotLoad, Plugin plugin, Stack<String> pluginFiles) {
if (!plugin.getName().equals(doNotLoad)) {
File file = getFile((JavaPlugin) plugin);
pluginFiles.push(file.getName());
}
PluginManager pm = Bukkit.getPluginManager();
for (Plugin p : pm.getPlugins()) {
List<String> depend = p.getDescription().getDepend();
if (depend != null) {
for (String s : depend) {
if (s.equals(plugin.getName())) {
unloadRecursively(doNotLoad, p, pluginFiles);
}
}
}
List<String> softDepend = p.getDescription().getSoftDepend();
if (softDepend != null) {
for (String s : softDepend) {
if (s.equals(plugin.getName())) {
unloadRecursively(doNotLoad, p, pluginFiles);
}
}
}
}
if (unloadPlugin(plugin)) {
List<String> depend = plugin.getDescription().getDepend();
if (depend != null) {
for (String s : depend) {
Plugin p = pm.getPlugin(s);
if (p != null) {
unloadRecursively(doNotLoad, p, pluginFiles);
}
}
}
List<String> softDepend = plugin.getDescription().getSoftDepend();
if (softDepend != null) {
for (String s : softDepend) {
Plugin p = pm.getPlugin(s);
if (p != null) {
unloadRecursively(doNotLoad, p, pluginFiles);
}
}
}
}
return pluginFiles;
}
@Override @Override
final public ChunkGenerator getDefaultWorldGenerator(final String world, final String id) { final public ChunkGenerator getDefaultWorldGenerator(final String world, final String id) {
WorldEvents.lastWorld = world; WorldEvents.lastWorld = world;
@ -495,8 +685,7 @@ public class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
if (Settings.OFFLINE_MODE) { if (Settings.OFFLINE_MODE) {
if (Settings.UUID_LOWERCASE) { if (Settings.UUID_LOWERCASE) {
UUIDHandler.uuidWrapper = new LowerOfflineUUIDWrapper(); UUIDHandler.uuidWrapper = new LowerOfflineUUIDWrapper();
} } else {
else {
UUIDHandler.uuidWrapper = new OfflineUUIDWrapper(); UUIDHandler.uuidWrapper = new OfflineUUIDWrapper();
} }
Settings.OFFLINE_MODE = true; Settings.OFFLINE_MODE = true;
@ -506,8 +695,7 @@ public class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
} else { } else {
if (Settings.UUID_LOWERCASE) { if (Settings.UUID_LOWERCASE) {
UUIDHandler.uuidWrapper = new LowerOfflineUUIDWrapper(); UUIDHandler.uuidWrapper = new LowerOfflineUUIDWrapper();
} } else {
else {
UUIDHandler.uuidWrapper = new OfflineUUIDWrapper(); UUIDHandler.uuidWrapper = new OfflineUUIDWrapper();
} }
Settings.OFFLINE_MODE = true; Settings.OFFLINE_MODE = true;
@ -520,8 +708,7 @@ public class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
AbstractTitle.TITLE_CLASS = new DefaultTitle(); AbstractTitle.TITLE_CLASS = new DefaultTitle();
if (UUIDHandler.uuidWrapper instanceof DefaultUUIDWrapper) { if (UUIDHandler.uuidWrapper instanceof DefaultUUIDWrapper) {
Settings.TWIN_MODE_UUID = true; Settings.TWIN_MODE_UUID = true;
} } else if (UUIDHandler.uuidWrapper instanceof OfflineUUIDWrapper && !Bukkit.getOnlineMode()) {
else if (UUIDHandler.uuidWrapper instanceof OfflineUUIDWrapper && !Bukkit.getOnlineMode()) {
Settings.TWIN_MODE_UUID = true; Settings.TWIN_MODE_UUID = true;
} }
} }

View File

@ -24,6 +24,8 @@ public interface IPlotMain {
public File getDirectory(); public File getDirectory();
public File getFile();
public void disable(); public void disable();
public String getVersion(); public String getVersion();
@ -79,4 +81,6 @@ public interface IPlotMain {
public PlayerManager initPlayerManager(); public PlayerManager initPlayerManager();
public boolean checkVersion(int major, int minor, int minor2); public boolean checkVersion(int major, int minor, int minor2);
public void loadPlugin(String plugin);
} }

View File

@ -1,9 +1,16 @@
package com.intellectualcrafters.plot; package com.intellectualcrafters.plot;
import java.io.BufferedReader;
import java.io.File; import java.io.File;
import java.io.FileInputStream; import java.io.FileInputStream;
import java.io.FileOutputStream; import java.io.FileOutputStream;
import java.io.IOException; import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;
import java.nio.file.Files;
import java.nio.file.StandardCopyOption;
import java.sql.Connection; import java.sql.Connection;
import java.sql.DatabaseMetaData; import java.sql.DatabaseMetaData;
import java.sql.SQLException; import java.sql.SQLException;
@ -21,9 +28,12 @@ import java.util.Map;
import java.util.Map.Entry; import java.util.Map.Entry;
import java.util.Set; import java.util.Set;
import java.util.UUID; import java.util.UUID;
import java.util.regex.Pattern;
import java.util.zip.ZipEntry; import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream; import java.util.zip.ZipInputStream;
import org.bukkit.Bukkit;
import com.intellectualcrafters.configuration.file.YamlConfiguration; import com.intellectualcrafters.configuration.file.YamlConfiguration;
import com.intellectualcrafters.plot.config.C; import com.intellectualcrafters.plot.config.C;
import com.intellectualcrafters.plot.config.Configuration; import com.intellectualcrafters.plot.config.Configuration;
@ -95,6 +105,7 @@ public class PS {
public YamlConfiguration storage; public YamlConfiguration storage;
public IPlotMain IMP = null; public IPlotMain IMP = null;
public TaskManager TASK; public TaskManager TASK;
public URL update;
// private: // private:
private File styleFile; private File styleFile;
@ -178,6 +189,20 @@ public class PS {
// Player manager // Player manager
PlayerManager.manager = IMP.initPlayerManager(); PlayerManager.manager = IMP.initPlayerManager();
// Check for updates
TaskManager.runTaskAsync(new Runnable() {
@Override
public void run() {
URL url = getUpdate();
if (url != null) {
update = url;
log("&6You are running an older version of PlotSquared...");
log("&8 - &3Use: &7/plot update");
log("&8 - &3Or: &7" + url);
}
}
});
// PlotMe // PlotMe
if (Settings.CONVERT_PLOTME || Settings.CACHE_PLOTME) { if (Settings.CONVERT_PLOTME || Settings.CACHE_PLOTME) {
TaskManager.runTaskLater(new Runnable() { TaskManager.runTaskLater(new Runnable() {
@ -805,6 +830,123 @@ public class PS {
return true; return true;
} }
private boolean canUpdate(String current, String other) {
String s1 = normalisedVersion(current);
String s2 = normalisedVersion(other);
int cmp = s1.compareTo(s2);
return cmp < 0;
}
public String normalisedVersion(String version) {
return normalisedVersion(version, ".", 4);
}
public String normalisedVersion(String version, String sep, int maxWidth) {
String[] split = Pattern.compile(sep, Pattern.LITERAL).split(version);
StringBuilder sb = new StringBuilder();
for (String s : split) {
sb.append(String.format("%" + maxWidth + 's', s));
}
return sb.toString();
}
/**
* Gets the default update URL, or null if the plugin is up to date
* @return
*/
public URL getUpdate() {
String resource = "plotsquared.1177";
String url = "https://www.spigotmc.org/resources/" + resource + "/history";
String download = "<a href=\"resources/" + resource + "/download?version=";
String version = "<td class=\"version\">";
try {
URL history = new URL(url);
URLConnection con = history.openConnection();
con.addRequestProperty("User-Agent", "Mozilla/4.0");
InputStream stream = con.getInputStream();
BufferedReader in = new BufferedReader(new InputStreamReader(stream));
String l;
URL link = null;
String cur_ver = config.getString("version");
String new_ver = null;
while ((l = in.readLine()) != null) {
if (l.length() > version.length() && l.startsWith(version)) {
new_ver = l.substring(version.length(), l.length() - 5);
break;
}
if (link == null && l.length() > download.length() && l.startsWith(download)) {
String subString = l.substring(download.length());
link = new URL("https://www.spigotmc.org/resources/" + resource + "/download?version=" + subString.substring(0, subString.indexOf("\"")));
continue;
}
}
stream.close();
in.close();
if (new_ver == null || !canUpdate(cur_ver, new_ver)) {
PS.log("&7PlotSquared is already up to date!");
return null;
}
if (link == null) {
PS.log("&dCould not check for updates");
PS.log("&7 - Manually check for updates: " + url);
return null;
}
return link;
} catch (Exception e) {
PS.log("&dCould not check for updates");
PS.log("&7 - Manually check for updates: " + url);
return null;
}
}
public boolean update(URL url) {
if (url == null) {
return false;
}
try {
File jar = PS.get().IMP.getFile();
File newJar = new File("plugins/update/PlotSquared.jar");
PS.log("&6Downloading from provided URL: &7" + url);
PS.log("&7 - User-Agent: " + "Mozilla/4.0");
URLConnection con = url.openConnection();
con.addRequestProperty("User-Agent", "Mozilla/4.0");
InputStream stream = con.getInputStream();
File parent = newJar.getParentFile();
if (!parent.exists()) {
parent.mkdirs();
}
PS.log("&7 - Output: " + newJar);
newJar.delete();
Files.copy(stream, newJar.toPath());
stream.close();
PS.log("&6Disabling PlotSquared");
PS.get().IMP.disable();
System.out.println("Deleting file: " + jar);
jar.delete();
System.out.println("Copying: " + jar + " >> " + newJar);
try {
Files.move(newJar.toPath(), jar.toPath(), StandardCopyOption.REPLACE_EXISTING);
} catch (IOException e) {
System.out.println("Failed to reload PlotSquared");
System.out.println(" - Restart the server manually");
System.out.println("============ Stacktrace ============");
e.printStackTrace();
System.out.println("====================================");
return false;
}
Bukkit.reload();
return true;
}
catch (Exception e) {
System.out.println("Failed to update PlotSquared");
System.out.println(" - Please update manually");
System.out.println("============ Stacktrace ============");
e.printStackTrace();
System.out.println("====================================");
}
return false;
}
/** /**
* Get the database connection * Get the database connection
@ -876,7 +1018,7 @@ public class PS {
public void setupDatabase() { public void setupDatabase() {
if (Settings.DB.USE_MYSQL) { if (Settings.DB.USE_MYSQL) {
try { try {
database = new MySQL(this, Settings.DB.HOST_NAME, Settings.DB.PORT, Settings.DB.DATABASE, Settings.DB.USER, Settings.DB.PASSWORD); database = new MySQL(Settings.DB.HOST_NAME, Settings.DB.PORT, Settings.DB.DATABASE, Settings.DB.USER, Settings.DB.PASSWORD);
connection = database.openConnection(); connection = database.openConnection();
{ {
if (DBFunc.dbManager == null) { if (DBFunc.dbManager == null) {
@ -904,7 +1046,7 @@ public class PS {
log(C.PREFIX.s() + "MongoDB is not yet implemented"); log(C.PREFIX.s() + "MongoDB is not yet implemented");
} else if (Settings.DB.USE_SQLITE) { } else if (Settings.DB.USE_SQLITE) {
try { try {
this.database = new SQLite(this, IMP.getDirectory() + File.separator + Settings.DB.SQLITE_DB + ".db"); this.database = new SQLite(IMP.getDirectory() + File.separator + Settings.DB.SQLITE_DB + ".db");
connection = this.database.openConnection(); connection = this.database.openConnection();
{ {
DBFunc.dbManager = new SQLManager(connection, Settings.DB.PREFIX); DBFunc.dbManager = new SQLManager(connection, Settings.DB.PREFIX);

View File

@ -92,7 +92,7 @@ public class Database extends SubCommand {
} }
Connection n; Connection n;
try { try {
n = new MySQL(PS.get(), host, port, database, username, password).openConnection(); n = new MySQL(host, port, database, username, password).openConnection();
// Connection // Connection
if (n.isClosed()) { if (n.isClosed()) {
return sendMessage(plr, "Failed to open connection"); return sendMessage(plr, "Failed to open connection");

View File

@ -0,0 +1,47 @@
////////////////////////////////////////////////////////////////////////////////////////////////////
// PlotSquared - A plot manager and world generator for the Bukkit API /
// Copyright (c) 2014 IntellectualSites/IntellectualCrafters /
// /
// This program is free software; you can redistribute it and/or modify /
// it under the terms of the GNU General Public License as published by /
// the Free Software Foundation; either version 3 of the License, or /
// (at your option) any later version. /
// /
// This program is distributed in the hope that it will be useful, /
// but WITHOUT ANY WARRANTY; without even the implied warranty of /
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the /
// GNU General Public License for more details. /
// /
// You should have received a copy of the GNU General Public License /
// along with this program; if not, write to the Free Software Foundation, /
// Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA /
// /
// You can contact us via: support@intellectualsites.com /
////////////////////////////////////////////////////////////////////////////////////////////////////
package com.intellectualcrafters.plot.commands;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import com.intellectualcrafters.plot.PS;
import com.intellectualcrafters.plot.object.PlotPlayer;
import com.intellectualcrafters.plot.util.MainUtil;
import com.intellectualcrafters.plot.util.TaskManager;
public class Disable extends SubCommand {
public static String downloads, version;
public Disable() {
super("disable", "plots.admin", "Disable PlotSquared", "disable", "unload", CommandCategory.DEBUG, false);
}
@Override
public boolean execute(final PlotPlayer plr, final String... args) {
PS.log("&cDisabling PlotSquared and all dependencies!");
PS.get().IMP.disable();
return true;
}
}

View File

@ -0,0 +1,83 @@
////////////////////////////////////////////////////////////////////////////////////////////////////
// PlotSquared - A plot manager and world generator for the Bukkit API /
// Copyright (c) 2014 IntellectualSites/IntellectualCrafters /
// /
// This program is free software; you can redistribute it and/or modify /
// it under the terms of the GNU General Public License as published by /
// the Free Software Foundation; either version 3 of the License, or /
// (at your option) any later version. /
// /
// This program is distributed in the hope that it will be useful, /
// but WITHOUT ANY WARRANTY; without even the implied warranty of /
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the /
// GNU General Public License for more details. /
// /
// You should have received a copy of the GNU General Public License /
// along with this program; if not, write to the Free Software Foundation, /
// Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA /
// /
// You can contact us via: support@intellectualsites.com /
////////////////////////////////////////////////////////////////////////////////////////////////////
package com.intellectualcrafters.plot.commands;
import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import java.nio.file.Files;
import java.nio.file.StandardCopyOption;
import java.util.ArrayList;
import javax.net.ssl.HttpsURLConnection;
import org.bukkit.Bukkit;
import com.intellectualcrafters.plot.PS;
import com.intellectualcrafters.plot.config.C;
import com.intellectualcrafters.plot.object.PlotPlayer;
import com.intellectualcrafters.plot.util.MainUtil;
import com.intellectualcrafters.plot.util.TaskManager;
public class Update extends SubCommand {
public static String downloads, version;
public Update() {
super("update", "plots.admin", "Update PlotSquared", "update", "updateplugin", CommandCategory.DEBUG, false);
}
@Override
public boolean execute(final PlotPlayer plr, final String... args) {
if (plr != null) {
MainUtil.sendMessage(plr, C.NOT_CONSOLE);
return false;
}
URL url;
if (args.length == 0) {
url = PS.get().update;
}
else if (args.length == 1) {
try {
url = new URL(args[0]);
} catch (MalformedURLException e) {
MainUtil.sendMessage(plr, "&cInvalid url: " + args[0]);
MainUtil.sendMessage(plr, C.COMMAND_SYNTAX, "/plot update [url]");
return false;
}
}
else {
MainUtil.sendMessage(plr, C.COMMAND_SYNTAX, "/plot update");
return false;
}
if (url == null) {
MainUtil.sendMessage(plr, "&cNo update found!");
MainUtil.sendMessage(plr, "&cTo manually specify an update URL: /plot update <url>");
return false;
}
PS.get().update(url);
return true;
}
}

View File

@ -32,36 +32,11 @@ import com.intellectualcrafters.plot.util.MainUtil;
import com.intellectualcrafters.plot.util.TaskManager; import com.intellectualcrafters.plot.util.TaskManager;
public class plugin extends SubCommand { public class plugin extends SubCommand {
public static String downloads, version;
public plugin() { public plugin() {
super("plugin", "plots.use", "Show plugin information", "plugin", "version", CommandCategory.INFO, false); super("plugin", "plots.use", "Show plugin information", "plugin", "version", CommandCategory.INFO, false);
} }
public static void setup() {
TaskManager.runTaskAsync(new Runnable() {
@Override
public void run() {
try {
downloads = convertToNumericString(getInfo("https://intellectualsites.com/spigot_api.php?method=downloads&url=http://www.spigotmc.org/resources/plotsquared.1177/"), false);
} catch (final Exception e) {
downloads = "unknown";
}
}
});
TaskManager.runTaskLaterAsync(new Runnable() {
@Override
public void run() {
try {
version = convertToNumericString(getInfo("https://intellectualsites.com/spigot_api.php?method=version&resource=1177"), true);
} catch (final Exception e) {
// Let's just ignore this, most likely error 500...
version = "unknown";
}
}
}, 200);
}
private static String convertToNumericString(final String str, final boolean dividers) { private static String convertToNumericString(final String str, final boolean dividers) {
final StringBuilder builder = new StringBuilder(); final StringBuilder builder = new StringBuilder();
for (final char c : str.toCharArray()) { for (final char c : str.toCharArray()) {
@ -94,10 +69,9 @@ public class plugin extends SubCommand {
final ArrayList<String> strings = new ArrayList<String>() { final ArrayList<String> strings = new ArrayList<String>() {
{ {
add(String.format("&c>> &6PlotSquared (Version: %s)", PS.get().IMP.getVersion())); add(String.format("&c>> &6PlotSquared (Version: %s)", PS.get().IMP.getVersion()));
add(String.format("&c>> &6Made by Citymonstret and Empire92")); add(String.format("&c>> &6Authors: Citymonstret and Empire92"));
add(String.format("&c>> &6Download at &lhttp://www.spigotmc.org/resources/1177")); add(String.format("&c>> &6Wiki: \n&chttps://github.com/IntellectualCrafters/PlotSquared/wiki"));
add(String.format("&c>> &cNewest Version (Spigot): %s", version)); add(String.format("&c>> &6Newest Version:\n&c" + (PS.get().update == null ? PS.get().IMP.getVersion() : PS.get().update)));
add(String.format("&c>> &cTotal Downloads (Spigot): %s", downloads));
} }
}; };
for (final String s : strings) { for (final String s : strings) {

View File

@ -24,8 +24,6 @@ import java.sql.Connection;
import java.sql.ResultSet; import java.sql.ResultSet;
import java.sql.SQLException; import java.sql.SQLException;
import com.intellectualcrafters.plot.PS;
/** /**
* Abstract Database class, serves as a base for any connection method (MySQL, SQLite, etc.) * Abstract Database class, serves as a base for any connection method (MySQL, SQLite, etc.)
* *
@ -33,19 +31,6 @@ import com.intellectualcrafters.plot.PS;
* @author tips48 * @author tips48
*/ */
public abstract class Database { public abstract class Database {
/**
* Plugin instance, use for plugin.getDataFolder()
*/
protected final PS plotsquared;
/**
* Creates a new Database
*
* @param plotsquared Plugin instance
*/
protected Database(final PS plotsquared) {
this.plotsquared = plotsquared;
}
public abstract Connection forceConnection() throws SQLException, ClassNotFoundException ; public abstract Connection forceConnection() throws SQLException, ClassNotFoundException ;

View File

@ -26,8 +26,6 @@ import java.sql.ResultSet;
import java.sql.SQLException; import java.sql.SQLException;
import java.sql.Statement; import java.sql.Statement;
import com.intellectualcrafters.plot.PS;
/** /**
* Connects to and uses a MySQL database * Connects to and uses a MySQL database
* *
@ -51,8 +49,7 @@ public class MySQL extends Database {
* @param username Username * @param username Username
* @param password Password * @param password Password
*/ */
public MySQL(final PS plotsquared, final String hostname, final String port, final String database, final String username, final String password) { public MySQL(final String hostname, final String port, final String database, final String username, final String password) {
super(plotsquared);
this.hostname = hostname; this.hostname = hostname;
this.port = port; this.port = port;
this.database = database; this.database = database;

View File

@ -45,8 +45,7 @@ public class SQLite extends Database {
* *
* @param dbLocation Location of the Database (Must end in .db) * @param dbLocation Location of the Database (Must end in .db)
*/ */
public SQLite(final PS plotsquared, final String dbLocation) { public SQLite(final String dbLocation) {
super(plotsquared);
this.dbLocation = dbLocation; this.dbLocation = dbLocation;
} }

View File

@ -48,7 +48,7 @@ public class ClassicPlotMeConnector extends APlotMeConnector {
return DriverManager.getConnection(con, user, password); return DriverManager.getConnection(con, user, password);
// return new MySQL(plotsquared, hostname, port, database, username, password) // return new MySQL(plotsquared, hostname, port, database, username, password)
} else { } else {
return new SQLite(PS.get(), dataFolder + File.separator + "plots.db").openConnection(); return new SQLite(dataFolder + File.separator + "plots.db").openConnection();
} }
} }
catch (SQLException | ClassNotFoundException e) {} catch (SQLException | ClassNotFoundException e) {}

View File

@ -334,6 +334,9 @@ public class PlayerEvents extends com.intellectualcrafters.plot.listeners.PlotLi
WEManager.bypass.add(pp.getName()); WEManager.bypass.add(pp.getName());
} }
} }
if (PS.get().update != null && pp.hasPermission("plots.admin")) {
MainUtil.sendMessage(pp, "&6An update for PlotSquared is available: &7/plot update");
}
final Location loc = BukkitUtil.getLocation(player.getLocation()); final Location loc = BukkitUtil.getLocation(player.getLocation());
final Plot plot = MainUtil.getPlot(loc); final Plot plot = MainUtil.getPlot(loc);
if (plot == null) { if (plot == null) {

View File

@ -20,12 +20,10 @@
//////////////////////////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////////////////////////
package com.intellectualcrafters.plot.util; package com.intellectualcrafters.plot.util;
import org.bukkit.ChatColor;
public class ConsoleColors { public class ConsoleColors {
public static String fromString(String input) { public static String fromString(String input) {
input = input.replaceAll("&0", fromChatColor(ChatColor.BLACK)).replaceAll("&1", fromChatColor(ChatColor.DARK_BLUE)).replaceAll("&2", fromChatColor(ChatColor.DARK_GREEN)).replaceAll("&3", fromChatColor(ChatColor.DARK_AQUA)).replaceAll("&4", fromChatColor(ChatColor.DARK_RED)).replaceAll("&5", fromChatColor(ChatColor.DARK_PURPLE)).replaceAll("&6", fromChatColor(ChatColor.GOLD)).replaceAll("&7", fromChatColor(ChatColor.GRAY)).replaceAll("&8", fromChatColor(ChatColor.DARK_GRAY)).replaceAll("&9", fromChatColor(ChatColor.BLUE)).replaceAll("&a", fromChatColor(ChatColor.GREEN)).replaceAll("&b", fromChatColor(ChatColor.AQUA)).replaceAll("&c", fromChatColor(ChatColor.RED)).replaceAll("&d", fromChatColor(ChatColor.LIGHT_PURPLE)).replaceAll("&e", fromChatColor(ChatColor.YELLOW)).replaceAll("&f", fromChatColor(ChatColor.WHITE)).replaceAll("&k", fromChatColor(ChatColor.MAGIC)).replaceAll("&l", fromChatColor(ChatColor.BOLD)).replaceAll("&m", fromChatColor(ChatColor.STRIKETHROUGH)) input = input.replaceAll("&0", fromChatColor("&0")).replaceAll("&1", fromChatColor("&1")).replaceAll("&2", fromChatColor("&2")).replaceAll("&3", fromChatColor("&3")).replaceAll("&4", fromChatColor("&4")).replaceAll("&5", fromChatColor("&5")).replaceAll("&6", fromChatColor("&6")).replaceAll("&7", fromChatColor("&7")).replaceAll("&8", fromChatColor("&8")).replaceAll("&9", fromChatColor("&9")).replaceAll("&a", fromChatColor("&a")).replaceAll("&b", fromChatColor("&b")).replaceAll("&c", fromChatColor("&c")).replaceAll("&d", fromChatColor("&d")).replaceAll("&e", fromChatColor("&e")).replaceAll("&f", fromChatColor("&f")).replaceAll("&k", fromChatColor("&k")).replaceAll("&l", fromChatColor("&l")).replaceAll("&m", fromChatColor("&m"))
.replaceAll("&n", fromChatColor(ChatColor.UNDERLINE)).replaceAll("&o", fromChatColor(ChatColor.ITALIC)).replaceAll("&r", fromChatColor(ChatColor.RESET)); .replaceAll("&n", fromChatColor("&n")).replaceAll("&o", fromChatColor("&o")).replaceAll("&r", fromChatColor("&r"));
return input + "\u001B[0m"; return input + "\u001B[0m";
} }
@ -41,42 +39,42 @@ public class ConsoleColors {
* String ANSI_UNDERLINE = "\033[0m"; public static final String ANSI_ITALIC * String ANSI_UNDERLINE = "\033[0m"; public static final String ANSI_ITALIC
* = "\033[3m]"; * = "\033[3m]";
*/ */
public static String fromChatColor(final ChatColor color) { public static String fromChatColor(final String color) {
return chatColor(color).getLin(); return chatColor(color).getLin();
} }
public static ConsoleColor chatColor(final ChatColor color) { public static ConsoleColor chatColor(final String color) {
switch (color) { switch (color) {
case RESET: case "&r":
return ConsoleColor.RESET; return ConsoleColor.RESET;
case GRAY: case "&7":
case DARK_GRAY: case "&8":
return ConsoleColor.WHITE; return ConsoleColor.WHITE;
case BLACK: case "&0":
return ConsoleColor.BLACK; return ConsoleColor.BLACK;
case DARK_RED: case "&4":
case RED: case "&c":
return ConsoleColor.RED; return ConsoleColor.RED;
case GOLD: case "&6":
case YELLOW: case "&e":
return ConsoleColor.YELLOW; return ConsoleColor.YELLOW;
case DARK_GREEN: case "&a":
case GREEN: case "&2":
return ConsoleColor.GREEN; return ConsoleColor.GREEN;
case AQUA: case "&b":
case DARK_AQUA: case "&3":
return ConsoleColor.CYAN; return ConsoleColor.CYAN;
case LIGHT_PURPLE: case "&d":
case DARK_PURPLE: case "&5":
return ConsoleColor.PURPLE; return ConsoleColor.PURPLE;
case BLUE: case "&9":
case DARK_BLUE: case "&1":
return ConsoleColor.BLUE; return ConsoleColor.BLUE;
case UNDERLINE: case "&n":
return ConsoleColor.UNDERLINE; return ConsoleColor.UNDERLINE;
case ITALIC: case "&o":
return ConsoleColor.ITALIC; return ConsoleColor.ITALIC;
case BOLD: case "&l":
return ConsoleColor.BOLD; return ConsoleColor.BOLD;
default: default:
return ConsoleColor.RESET; return ConsoleColor.RESET;

View File

@ -0,0 +1,32 @@
package com.intellectualcrafters.plot.util;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
public class Updater {
public Updater() {
// https://www.spigotmc.org/resources/plotsquared.1177/history
try {
String resource = "plotsquared.1177";
String url = "https://www.spigotmc.org/resources/" + resource + "/history";
String download = "<a href=\"resources/" + resource + "/download?version=";
URL history = new URL(url);
BufferedReader in = new BufferedReader(new InputStreamReader(history.openStream()));
String inputLine;
while ((inputLine = in.readLine()) != null)
if (inputLine.length() > download.length() && inputLine.startsWith(download)) {
System.out.println("===========================");
System.out.println("FOUND LINE");
System.out.println("===========================");
}
System.out.println(inputLine);
in.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}

View File

@ -126,7 +126,7 @@ public class UUIDHandler {
toAdd.put(new StringWrapper("*"), DBFunc.everyone); toAdd.put(new StringWrapper("*"), DBFunc.everyone);
if (Settings.TWIN_MODE_UUID) { if (Settings.TWIN_MODE_UUID) {
HashSet<UUID> all = getAllUUIDS(); HashSet<UUID> all = getAllUUIDS();
PS.log("&aFast mod UUID caching enabled!"); PS.log("&aFast mode UUID caching enabled!");
final File playerdataFolder = new File(container, world + File.separator + "playerdata"); final File playerdataFolder = new File(container, world + File.separator + "playerdata");
String[] dat = playerdataFolder.list(new FilenameFilter() { String[] dat = playerdataFolder.list(new FilenameFilter() {
@Override @Override