diff --git a/src/main/java/us/tastybento/bskyblock/BSkyBlock.java b/src/main/java/us/tastybento/bskyblock/BSkyBlock.java index a79b5d1f1..94637f3c1 100755 --- a/src/main/java/us/tastybento/bskyblock/BSkyBlock.java +++ b/src/main/java/us/tastybento/bskyblock/BSkyBlock.java @@ -11,6 +11,7 @@ import org.bukkit.Material; import org.bukkit.command.CommandSender; import org.bukkit.entity.Player; import org.bukkit.inventory.ItemStack; +import org.bukkit.plugin.PluginManager; import org.bukkit.plugin.java.JavaPlugin; import us.tastybento.bskyblock.commands.IslandCommand; @@ -18,11 +19,11 @@ import us.tastybento.bskyblock.config.BSBLocale; import us.tastybento.bskyblock.config.PluginConfig; import us.tastybento.bskyblock.config.Settings; import us.tastybento.bskyblock.database.BSBDatabase; -import us.tastybento.bskyblock.database.BSBDatabase.DatabaseType; import us.tastybento.bskyblock.database.managers.IslandsManager; import us.tastybento.bskyblock.database.managers.OfflineHistoryMessages; import us.tastybento.bskyblock.database.managers.PlayersManager; import us.tastybento.bskyblock.generators.IslandWorld; +import us.tastybento.bskyblock.listeners.JoinLeaveListener; import us.tastybento.bskyblock.schematics.SchematicsMgr; import us.tastybento.bskyblock.util.FileLister; import us.tastybento.bskyblock.util.VaultHelper; @@ -132,8 +133,6 @@ public class BSkyBlock extends JavaPlugin{ getLogger().info("DEBUG: ************ Finished saving, now loading *************"); */ - - playersManager.load(); islandsManager.load(); // Load schematics @@ -153,6 +152,10 @@ public class BSkyBlock extends JavaPlugin{ Settings.defaultLanguage = "en-US"; loadLocales(); + // Register Listeners + PluginManager manager = getServer().getPluginManager(); + // Player join events + manager.registerEvents(new JoinLeaveListener(plugin), plugin); /* *DEBUG CODE Island loadedIsland = islandsManager.getIsland(owner); diff --git a/src/main/java/us/tastybento/bskyblock/config/Settings.java b/src/main/java/us/tastybento/bskyblock/config/Settings.java index 94a1b047d..d4e524f36 100755 --- a/src/main/java/us/tastybento/bskyblock/config/Settings.java +++ b/src/main/java/us/tastybento/bskyblock/config/Settings.java @@ -214,4 +214,6 @@ public class Settings { public static int islandZOffset; public static int islandStartZ; + public static boolean logInRemoveMobs; + } diff --git a/src/main/java/us/tastybento/bskyblock/database/DatabaseConnecter.java b/src/main/java/us/tastybento/bskyblock/database/DatabaseConnecter.java index 1ce9d230e..0e1a8a858 100644 --- a/src/main/java/us/tastybento/bskyblock/database/DatabaseConnecter.java +++ b/src/main/java/us/tastybento/bskyblock/database/DatabaseConnecter.java @@ -33,6 +33,14 @@ public interface DatabaseConnecter { * @return a unique key for this record */ public String getUniqueId(String tableName); + + /** + * Check if a key exists in the database in this table or not + * @param simpleName + * @param key + * @return true if it exists + */ + public boolean uniqueIdExists(String simpleName, String key); /** * Loads a YAML file. Used by the flat file database @@ -49,5 +57,6 @@ public interface DatabaseConnecter { * @param fileName - the name of the record. Must be unique. */ public void saveYamlFile(YamlConfiguration yamlFile, String tableName, String fileName); + } diff --git a/src/main/java/us/tastybento/bskyblock/database/flatfile/FlatFileDatabaseConnecter.java b/src/main/java/us/tastybento/bskyblock/database/flatfile/FlatFileDatabaseConnecter.java index 900c5a8f7..4b96a6aff 100644 --- a/src/main/java/us/tastybento/bskyblock/database/flatfile/FlatFileDatabaseConnecter.java +++ b/src/main/java/us/tastybento/bskyblock/database/flatfile/FlatFileDatabaseConnecter.java @@ -111,4 +111,10 @@ public class FlatFileDatabaseConnecter implements DatabaseConnecter { return uuid.toString(); } + @Override + public boolean uniqueIdExists(String tableName, String key) { + File file = new File(dataFolder, tableName + File.separator + key + ".yml"); + return file.exists(); + } + } diff --git a/src/main/java/us/tastybento/bskyblock/database/flatfile/FlatFileDatabaseHandler.java b/src/main/java/us/tastybento/bskyblock/database/flatfile/FlatFileDatabaseHandler.java index 6f8fa6029..59ace12d5 100644 --- a/src/main/java/us/tastybento/bskyblock/database/flatfile/FlatFileDatabaseHandler.java +++ b/src/main/java/us/tastybento/bskyblock/database/flatfile/FlatFileDatabaseHandler.java @@ -71,6 +71,11 @@ public class FlatFileDatabaseHandler extends AbstractDatabaseHandler { YamlConfiguration config = databaseConnecter.loadYamlFile(type.getSimpleName(), key); return createObject(config); } + + @Override + public boolean objectExits(String key) { + return databaseConnecter.uniqueIdExists(type.getSimpleName(), key); + } /** * Loads all the records in this table and returns a list of them diff --git a/src/main/java/us/tastybento/bskyblock/database/managers/AbstractDatabaseHandler.java b/src/main/java/us/tastybento/bskyblock/database/managers/AbstractDatabaseHandler.java index 0aa8fe398..4bf22c475 100644 --- a/src/main/java/us/tastybento/bskyblock/database/managers/AbstractDatabaseHandler.java +++ b/src/main/java/us/tastybento/bskyblock/database/managers/AbstractDatabaseHandler.java @@ -159,4 +159,11 @@ public abstract class AbstractDatabaseHandler { */ public abstract void deleteObject(T instance) throws IllegalAccessException, IllegalArgumentException, InvocationTargetException, IntrospectionException, SQLException, NoSuchMethodException, SecurityException; + /** + * Checks if a key exists or not + * @param key + * @return true if this key exists + */ + public abstract boolean objectExits(String key); + } diff --git a/src/main/java/us/tastybento/bskyblock/database/managers/IslandsManager.java b/src/main/java/us/tastybento/bskyblock/database/managers/IslandsManager.java index 7be405843..2d0998f8f 100644 --- a/src/main/java/us/tastybento/bskyblock/database/managers/IslandsManager.java +++ b/src/main/java/us/tastybento/bskyblock/database/managers/IslandsManager.java @@ -1,7 +1,5 @@ package us.tastybento.bskyblock.database.managers; -import java.beans.IntrospectionException; -import java.lang.reflect.InvocationTargetException; import java.util.HashSet; import java.util.Map.Entry; import java.util.Set; @@ -386,7 +384,7 @@ public class IslandsManager { /** * @param playerUUID - * @return ture if player has island + * @return true if player has island */ public boolean hasIsland(UUID playerUUID) { return islandsByUUID.containsKey(playerUUID); @@ -991,4 +989,12 @@ public class IslandsManager { return handler; } + /** + * @param location + */ + public void removeMobs(Location location) { + // TODO Auto-generated method stub + + } + } diff --git a/src/main/java/us/tastybento/bskyblock/database/managers/PlayersManager.java b/src/main/java/us/tastybento/bskyblock/database/managers/PlayersManager.java index b97d83a29..f83de2c1e 100644 --- a/src/main/java/us/tastybento/bskyblock/database/managers/PlayersManager.java +++ b/src/main/java/us/tastybento/bskyblock/database/managers/PlayersManager.java @@ -1,5 +1,8 @@ package us.tastybento.bskyblock.database.managers; +import java.beans.IntrospectionException; +import java.lang.reflect.InvocationTargetException; +import java.sql.SQLException; import java.util.HashMap; import java.util.HashSet; import java.util.Set; @@ -42,7 +45,7 @@ public class PlayersManager{ } /** - * Load all players + * Load all players - not normally used as to load all players into memory will be wasteful */ public void load(){ playerCache.clear(); @@ -108,14 +111,26 @@ public class PlayersManager{ public Players addPlayer(final UUID playerUUID) { if (playerUUID == null) return null; - //plugin.getLogger().info("DEBUG: added player " + playerUUID); + plugin.getLogger().info("DEBUG: adding player " + playerUUID); if (!playerCache.containsKey(playerUUID)) { - plugin.getLogger().info("DEBUG: new player"); - final Players player = new Players(playerUUID); + plugin.getLogger().info("DEBUG: player not in cache"); + Players player = null; + // If the player is in the database, load it, otherwise create a new player + if (handler.objectExits(playerUUID.toString())) { + plugin.getLogger().info("DEBUG: player in database"); + try { + player = handler.loadObject(playerUUID.toString()); + } catch (Exception e) { + e.printStackTrace(); + } + } else { + plugin.getLogger().info("DEBUG: new player"); + player = new Players(playerUUID); + } playerCache.put(playerUUID, player); return player; } else { - //plugin.getLogger().info("DEBUG: known player"); + plugin.getLogger().info("DEBUG: known player"); return playerCache.get(playerUUID); } } @@ -127,10 +142,18 @@ public class PlayersManager{ * */ public void removeOnlinePlayer(final UUID player) { + // plugin.getLogger().info("Removing player from cache: " + player); if (playerCache.containsKey(player)) { - //database.savePlayerData(playerCache.get(player)); - playerCache.remove(player); - // plugin.getLogger().info("Removing player from cache: " + player); + try { + handler.saveObject(playerCache.get(player)); + playerCache.remove(player); + } catch (IllegalAccessException | IllegalArgumentException + | InvocationTargetException | SecurityException + | InstantiationException | NoSuchMethodException + | IntrospectionException | SQLException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } } } @@ -139,7 +162,7 @@ public class PlayersManager{ */ public void removeAllPlayers() { for (UUID pl : playerCache.keySet()) { - //database.savePlayerData(playerCache.get(pl)); + removeOnlinePlayer(pl); } playerCache.clear(); } @@ -163,9 +186,7 @@ public class PlayersManager{ return true; } else { // Get from the database - do not add to cache yet - //return database.isPlayerKnown(uniqueID) ? true: false; - // TODO - return false; + return handler.objectExits(uniqueID.toString()); } } @@ -301,7 +322,6 @@ public class PlayersManager{ * @param adminCheck - if made via an admin call, this will go out to the 'net and grab - may cause lag * @return UUID of player or null if unknown */ - @SuppressWarnings("deprecation") public UUID getUUID(String string, boolean adminCheck) { // Look in the database if it ready //return database.getUUID(string, adminCheck); @@ -556,7 +576,7 @@ public class PlayersManager{ public void removeInTeleport(UUID uniqueId) { inTeleport.remove(uniqueId); } - + /** * @param uniqueId * @return true if a player is mid-teleport @@ -571,8 +591,28 @@ public class PlayersManager{ */ public void resetPlayer(Player player) { // TODO Auto-generated method stub - - } - + } + + /** + * Saves the player to the database + * @param playerUUID + */ + public void save(UUID playerUUID) { + if (playerCache.containsKey(playerUUID)) { + Players player = playerCache.get(playerUUID); + try { + handler.saveObject(player); + plugin.getLogger().info("DEBUG: " + playerUUID + " saved"); + } catch (IllegalAccessException | IllegalArgumentException + | InvocationTargetException | SecurityException + | InstantiationException | NoSuchMethodException + | IntrospectionException | SQLException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } else { + plugin.getLogger().info("DEBUG: " + playerUUID + " is not in the cache to save"); + } + } } diff --git a/src/main/java/us/tastybento/bskyblock/database/mysql/MySQLDatabaseConnecter.java b/src/main/java/us/tastybento/bskyblock/database/mysql/MySQLDatabaseConnecter.java index d473bf1b5..554208573 100644 --- a/src/main/java/us/tastybento/bskyblock/database/mysql/MySQLDatabaseConnecter.java +++ b/src/main/java/us/tastybento/bskyblock/database/mysql/MySQLDatabaseConnecter.java @@ -60,4 +60,10 @@ public class MySQLDatabaseConnecter implements DatabaseConnecter { } + @Override + public boolean uniqueIdExists(String simpleName, String key) { + // Not used + return false; + } + } diff --git a/src/main/java/us/tastybento/bskyblock/database/mysql/MySQLDatabaseHandler.java b/src/main/java/us/tastybento/bskyblock/database/mysql/MySQLDatabaseHandler.java index 9bf1ecde6..ba1028f2f 100644 --- a/src/main/java/us/tastybento/bskyblock/database/mysql/MySQLDatabaseHandler.java +++ b/src/main/java/us/tastybento/bskyblock/database/mysql/MySQLDatabaseHandler.java @@ -260,8 +260,6 @@ public class MySQLDatabaseHandler extends AbstractDatabaseHandler { sb.append("SELECT "); sb.append(super.getColumns(false)); sb.append(" FROM "); - - /* We assume the table-name exactly matches the canonical Name of T */ sb.append("`"); sb.append(type.getCanonicalName()); sb.append("`"); @@ -269,6 +267,7 @@ public class MySQLDatabaseHandler extends AbstractDatabaseHandler { return sb.toString(); } + /* (non-Javadoc) * @see us.tastybento.bskyblock.database.managers.AbstractDatabaseHandler#createInsertQuery() */ @@ -292,6 +291,7 @@ public class MySQLDatabaseHandler extends AbstractDatabaseHandler { return sb.toString(); } + @Override protected String createDeleteQuery() { return "DELETE FROM [table_name] WHERE uniqueId = ?"; } @@ -781,6 +781,30 @@ public class MySQLDatabaseHandler extends AbstractDatabaseHandler { } - + /* (non-Javadoc) + * @see us.tastybento.bskyblock.database.managers.AbstractDatabaseHandler#objectExits(java.lang.String) + */ + @Override + public boolean objectExits(String key) { + Connection connection = null; + PreparedStatement preparedStatement = null; + ResultSet resultSet = null; + String query = "SELECT * FROM `" + type.getCanonicalName() + "` WHERE uniqueId = ?"; + try { + connection = databaseConnecter.createConnection(); + preparedStatement = connection.prepareStatement(query); + preparedStatement.setString(1, key); + resultSet = preparedStatement.executeQuery(); + return resultSet.next(); + } catch (SQLException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } finally { + MySQLDatabaseResourceCloser.close(resultSet); + MySQLDatabaseResourceCloser.close(preparedStatement); + MySQLDatabaseResourceCloser.close(connection); + } + return false; + } } diff --git a/src/main/java/us/tastybento/bskyblock/database/objects/Island.java b/src/main/java/us/tastybento/bskyblock/database/objects/Island.java index df5286fa1..af16fe800 100755 --- a/src/main/java/us/tastybento/bskyblock/database/objects/Island.java +++ b/src/main/java/us/tastybento/bskyblock/database/objects/Island.java @@ -836,4 +836,11 @@ public class Island extends DataObject { this.levelHandicap = levelHandicap; } + /** + * @return true if island is locked, false if not + */ + public boolean isLocked() { + return locked; + } + } \ No newline at end of file diff --git a/src/main/java/us/tastybento/bskyblock/database/objects/Players.java b/src/main/java/us/tastybento/bskyblock/database/objects/Players.java index a526e2601..6d601a2e2 100755 --- a/src/main/java/us/tastybento/bskyblock/database/objects/Players.java +++ b/src/main/java/us/tastybento/bskyblock/database/objects/Players.java @@ -44,6 +44,7 @@ public class Players extends DataObject { this.locale = ""; this.useControlPanel = Settings.useControlPanel; this.kickedList = new HashMap(); + this.playerName = Bukkit.getServer().getOfflinePlayer(uniqueId).getName(); } /** diff --git a/src/main/java/us/tastybento/bskyblock/listeners/JoinLeaveListener.java b/src/main/java/us/tastybento/bskyblock/listeners/JoinLeaveListener.java new file mode 100644 index 000000000..ee7303924 --- /dev/null +++ b/src/main/java/us/tastybento/bskyblock/listeners/JoinLeaveListener.java @@ -0,0 +1,93 @@ +package us.tastybento.bskyblock.listeners; + +import java.util.UUID; + +import org.bukkit.ChatColor; +import org.bukkit.entity.Player; +import org.bukkit.event.EventHandler; +import org.bukkit.event.EventPriority; +import org.bukkit.event.Listener; +import org.bukkit.event.player.PlayerJoinEvent; +import org.bukkit.event.player.PlayerQuitEvent; + +import us.tastybento.bskyblock.BSkyBlock; +import us.tastybento.bskyblock.config.Settings; +import us.tastybento.bskyblock.database.managers.PlayersManager; +import us.tastybento.bskyblock.database.objects.Island; +import us.tastybento.bskyblock.util.Util; +import us.tastybento.bskyblock.util.VaultHelper; + +public class JoinLeaveListener implements Listener { + + private static final boolean DEBUG = false; + private BSkyBlock plugin; + private PlayersManager players; + + /** + * @param plugin + */ + public JoinLeaveListener(BSkyBlock plugin) { + this.plugin = plugin; + this.players = plugin.getPlayers(); + } + + @EventHandler(priority = EventPriority.NORMAL, ignoreCancelled = true) + public void onPlayerJoin(final PlayerJoinEvent event) { + Player player = event.getPlayer(); + if (player == null) { + return; + } + UUID playerUUID = player.getUniqueId(); + if (playerUUID == null) { + return; + } + if (plugin.getPlayers().isAKnownPlayer(playerUUID)) { + plugin.getLogger().info("DEBUG: known player"); + // Load player + players.addPlayer(playerUUID); + // Reset resets if the admin changes it to or from unlimited + if (Settings.resetLimit < players.getResetsLeft(playerUUID) || (Settings.resetLimit >= 0 && players.getResetsLeft(playerUUID) < 0)) { + players.setResetsLeft(playerUUID, Settings.resetLimit); + } + if (DEBUG) + plugin.getLogger().info("DEBUG: Setting player's name"); + // Set the player's name (it may have changed), but only if it isn't empty + if (!player.getName().isEmpty()) { + if (DEBUG) + plugin.getLogger().info("DEBUG: Player name is " + player.getName()); + players.setPlayerName(playerUUID, player.getName()); + if (DEBUG) + plugin.getLogger().info("DEBUG: Saving player"); + players.save(playerUUID); + } else { + plugin.getLogger().warning("Player that just logged in has no name! " + playerUUID.toString()); + } + if (Settings.logInRemoveMobs) { + if (DEBUG) + plugin.getLogger().info("DEBUG: Removing mobs"); + plugin.getIslands().removeMobs(player.getLocation()); + } + + // Check if they logged in to a locked island and expel them or if they are banned + Island currentIsland = plugin.getIslands().getIslandAt(player.getLocation()); + if (currentIsland != null && (currentIsland.isLocked() || plugin.getPlayers().isBanned(currentIsland.getOwner(),player.getUniqueId()))) { + if (DEBUG) + plugin.getLogger().info("DEBUG: Current island is locked, or player is banned"); + if (!currentIsland.getMembers().contains(playerUUID) && !player.isOp() + && !VaultHelper.hasPerm(player, Settings.PERMPREFIX + "mod.bypassprotect")) { + if (DEBUG) + plugin.getLogger().info("DEBUG: No bypass - teleporting"); + Util.sendMessage(player, ChatColor.RED + plugin.getLocale(player.getUniqueId()).get("locked.islandlocked")); + plugin.getIslands().homeTeleport(player); + } + } + } else { + plugin.getLogger().info("DEBUG: not a known player"); + } + } + + @EventHandler(priority = EventPriority.NORMAL) + public void onPlayerQuit(final PlayerQuitEvent event) { + players.removeOnlinePlayer(event.getPlayer().getUniqueId()); + } +}