Use JedisPool instead of single Jedis connection

feat/data-edit-commands
William 3 years ago
parent 4ec4ba9a1e
commit 93be26a946

@ -17,7 +17,6 @@ import org.bukkit.scheduler.BukkitTask;
import java.io.IOException; import java.io.IOException;
import java.util.UUID; import java.util.UUID;
import java.util.concurrent.CompletableFuture;
import java.util.logging.Level; import java.util.logging.Level;
public final class HuskSyncBukkit extends JavaPlugin { public final class HuskSyncBukkit extends JavaPlugin {
@ -32,6 +31,8 @@ public final class HuskSyncBukkit extends JavaPlugin {
public static BukkitDataCache bukkitCache; public static BukkitDataCache bukkitCache;
public static BukkitRedisListener redisListener;
// Used for establishing a handshake with redis // Used for establishing a handshake with redis
public static UUID serverUUID; public static UUID serverUUID;
@ -120,7 +121,8 @@ public final class HuskSyncBukkit extends JavaPlugin {
getServer().getPluginManager().registerEvents(new BukkitEventListener(), this); getServer().getPluginManager().registerEvents(new BukkitEventListener(), this);
// Initialize the redis listener // Initialize the redis listener
if (!new BukkitRedisListener().isActiveAndEnabled) { redisListener = new BukkitRedisListener();
if (!redisListener.isActiveAndEnabled) {
getPluginLoader().disablePlugin(this); getPluginLoader().disablePlugin(this);
getLogger().severe("Failed to initialize Redis; disabling HuskSync (" + getServer().getName() + ") v" + getDescription().getVersion()); getLogger().severe("Failed to initialize Redis; disabling HuskSync (" + getServer().getName() + ") v" + getDescription().getVersion());
return; return;

@ -26,6 +26,7 @@ public class BukkitRedisListener extends RedisListener {
// Initialize the listener on the bukkit server // Initialize the listener on the bukkit server
public BukkitRedisListener() { public BukkitRedisListener() {
super();
listen(); listen();
} }

@ -3,12 +3,12 @@ package me.william278.husksync;
import me.william278.husksync.bungeecord.command.BungeeCommand; import me.william278.husksync.bungeecord.command.BungeeCommand;
import me.william278.husksync.bungeecord.config.ConfigLoader; import me.william278.husksync.bungeecord.config.ConfigLoader;
import me.william278.husksync.bungeecord.config.ConfigManager; import me.william278.husksync.bungeecord.config.ConfigManager;
import me.william278.husksync.proxy.data.DataManager;
import me.william278.husksync.bungeecord.listener.BungeeEventListener; import me.william278.husksync.bungeecord.listener.BungeeEventListener;
import me.william278.husksync.bungeecord.listener.BungeeRedisListener; import me.william278.husksync.bungeecord.listener.BungeeRedisListener;
import me.william278.husksync.migrator.MPDBMigrator;
import me.william278.husksync.bungeecord.util.BungeeLogger; import me.william278.husksync.bungeecord.util.BungeeLogger;
import me.william278.husksync.bungeecord.util.BungeeUpdateChecker; import me.william278.husksync.bungeecord.util.BungeeUpdateChecker;
import me.william278.husksync.migrator.MPDBMigrator;
import me.william278.husksync.proxy.data.DataManager;
import me.william278.husksync.redis.RedisMessage; import me.william278.husksync.redis.RedisMessage;
import me.william278.husksync.util.Logger; import me.william278.husksync.util.Logger;
import net.byteflux.libby.BungeeLibraryManager; import net.byteflux.libby.BungeeLibraryManager;
@ -48,6 +48,8 @@ public final class HuskSyncBungeeCord extends Plugin {
public static MPDBMigrator mpdbMigrator; public static MPDBMigrator mpdbMigrator;
public static BungeeRedisListener redisListener;
private Logger logger; private Logger logger;
public Logger getBungeeLogger() { public Logger getBungeeLogger() {
@ -98,7 +100,8 @@ public final class HuskSyncBungeeCord extends Plugin {
} }
// Initialize the redis listener // Initialize the redis listener
if (!new BungeeRedisListener().isActiveAndEnabled) { redisListener = new BungeeRedisListener();
if (!redisListener.isActiveAndEnabled) {
getBungeeLogger().severe("Failed to initialize Redis; HuskSync will now abort loading itself (" + getProxy().getName() + ") v" + getDescription().getVersion()); getBungeeLogger().severe("Failed to initialize Redis; HuskSync will now abort loading itself (" + getProxy().getName() + ") v" + getDescription().getVersion());
return; return;
} }

@ -2,16 +2,16 @@ package me.william278.husksync.bungeecord.command;
import de.themoep.minedown.MineDown; import de.themoep.minedown.MineDown;
import me.william278.husksync.HuskSyncBungeeCord; import me.william278.husksync.HuskSyncBungeeCord;
import me.william278.husksync.Server;
import me.william278.husksync.bungeecord.util.BungeeUpdateChecker;
import me.william278.husksync.proxy.command.HuskSyncCommand;
import me.william278.husksync.util.MessageManager;
import me.william278.husksync.PlayerData; import me.william278.husksync.PlayerData;
import me.william278.husksync.Server;
import me.william278.husksync.Settings; import me.william278.husksync.Settings;
import me.william278.husksync.bungeecord.config.ConfigLoader; import me.william278.husksync.bungeecord.config.ConfigLoader;
import me.william278.husksync.bungeecord.config.ConfigManager; import me.william278.husksync.bungeecord.config.ConfigManager;
import me.william278.husksync.bungeecord.util.BungeeUpdateChecker;
import me.william278.husksync.migrator.MPDBMigrator; import me.william278.husksync.migrator.MPDBMigrator;
import me.william278.husksync.proxy.command.HuskSyncCommand;
import me.william278.husksync.redis.RedisMessage; import me.william278.husksync.redis.RedisMessage;
import me.william278.husksync.util.MessageManager;
import net.md_5.bungee.api.CommandSender; import net.md_5.bungee.api.CommandSender;
import net.md_5.bungee.api.ProxyServer; import net.md_5.bungee.api.ProxyServer;
import net.md_5.bungee.api.connection.ProxiedPlayer; import net.md_5.bungee.api.connection.ProxiedPlayer;
@ -301,7 +301,7 @@ public class BungeeCommand extends Command implements TabExecutor, HuskSyncComma
HuskSyncBungeeCord.synchronisedServers)) { HuskSyncBungeeCord.synchronisedServers)) {
ProxyServer.getInstance().getScheduler().runAsync(plugin, () -> ProxyServer.getInstance().getScheduler().runAsync(plugin, () ->
HuskSyncBungeeCord.mpdbMigrator.executeMigrationOperations(HuskSyncBungeeCord.dataManager, HuskSyncBungeeCord.mpdbMigrator.executeMigrationOperations(HuskSyncBungeeCord.dataManager,
HuskSyncBungeeCord.synchronisedServers)); HuskSyncBungeeCord.synchronisedServers, HuskSyncBungeeCord.redisListener));
} }
} }
default -> sender.sendMessage(new MineDown("Error: Invalid argument for migration. Use \"husksync migrate\" to start the process").toComponent()); default -> sender.sendMessage(new MineDown("Error: Invalid argument for migration. Use \"husksync migrate\" to start the process").toComponent());

@ -24,6 +24,7 @@ public class BungeeRedisListener extends RedisListener {
// Initialize the listener on the bungee // Initialize the listener on the bungee
public BungeeRedisListener() { public BungeeRedisListener() {
super();
listen(); listen();
} }

@ -6,6 +6,7 @@ import me.william278.husksync.Settings;
import me.william278.husksync.proxy.data.DataManager; import me.william278.husksync.proxy.data.DataManager;
import me.william278.husksync.proxy.data.sql.Database; import me.william278.husksync.proxy.data.sql.Database;
import me.william278.husksync.proxy.data.sql.MySQL; import me.william278.husksync.proxy.data.sql.MySQL;
import me.william278.husksync.redis.RedisListener;
import me.william278.husksync.redis.RedisMessage; import me.william278.husksync.redis.RedisMessage;
import me.william278.husksync.util.Logger; import me.william278.husksync.util.Logger;
@ -95,7 +96,7 @@ public class MPDBMigrator {
} }
// Carry out the migration // Carry out the migration
public void executeMigrationOperations(DataManager dataManager, HashSet<Server> synchronisedServers) { public void executeMigrationOperations(DataManager dataManager, HashSet<Server> synchronisedServers, RedisListener redisListener) {
// Prepare the target database for insertion // Prepare the target database for insertion
prepareTargetDatabase(dataManager); prepareTargetDatabase(dataManager);
@ -109,7 +110,7 @@ public class MPDBMigrator {
getExperienceData(); getExperienceData();
// Send the encoded data to the Bukkit servers for conversion // Send the encoded data to the Bukkit servers for conversion
sendEncodedData(synchronisedServers); sendEncodedData(synchronisedServers, redisListener);
} }
// Clear the new database out of current data // Clear the new database out of current data
@ -200,7 +201,7 @@ public class MPDBMigrator {
} }
} }
private void sendEncodedData(HashSet<Server> synchronisedServers) { private void sendEncodedData(HashSet<Server> synchronisedServers, RedisListener redisListener) {
for (Server processingServer : synchronisedServers) { for (Server processingServer : synchronisedServers) {
if (processingServer.hasMySqlPlayerDataBridge()) { if (processingServer.hasMySqlPlayerDataBridge()) {
for (MPDBPlayerData data : mpdbPlayerData) { for (MPDBPlayerData data : mpdbPlayerData) {

@ -1,9 +1,7 @@
package me.william278.husksync.redis; package me.william278.husksync.redis;
import me.william278.husksync.Settings; import me.william278.husksync.Settings;
import redis.clients.jedis.Jedis; import redis.clients.jedis.*;
import redis.clients.jedis.JedisClientConfig;
import redis.clients.jedis.JedisPubSub;
import redis.clients.jedis.exceptions.JedisException; import redis.clients.jedis.exceptions.JedisException;
import java.io.IOException; import java.io.IOException;
@ -16,6 +14,18 @@ public abstract class RedisListener {
*/ */
public boolean isActiveAndEnabled; public boolean isActiveAndEnabled;
/**
* Pool of connections to the Redis server
*/
private static JedisPool jedisPool;
/**
* Creates a new RedisListener and initialises the Redis connection
*/
public RedisListener() {
jedisPool = new JedisPool(new JedisPoolConfig(), Settings.redisHost, Settings.redisPort);
}
/** /**
* Handle an incoming {@link RedisMessage} * Handle an incoming {@link RedisMessage}
* *
@ -31,20 +41,34 @@ public abstract class RedisListener {
*/ */
public abstract void log(Level level, String message); public abstract void log(Level level, String message);
/**
* Fetch a connection to the Redis server from the JedisPool
*
* @return Jedis instance from the pool
*/
public static Jedis getJedisConnection() {
return jedisPool.getResource();
}
/** /**
* Start the Redis listener * Start the Redis listener
*/ */
public final void listen() { public final void listen() {
try (Jedis jedis = new Jedis(Settings.redisHost, Settings.redisPort)) {
final String jedisPassword = Settings.redisPassword; final String jedisPassword = Settings.redisPassword;
jedis.connect(); new Thread(() -> {
if (jedis.isConnected()) { try (Jedis jedis = getJedisConnection()) {
if (!jedisPassword.equals("")) { if (!jedisPassword.equals("")) {
jedis.auth(jedisPassword); jedis.auth(jedisPassword);
} }
if (jedis.isConnected()) {
isActiveAndEnabled = true; isActiveAndEnabled = true;
log(Level.INFO, "Enabled Redis listener successfully!"); log(Level.INFO, "Enabled Redis listener successfully!");
new Thread(() -> jedis.subscribe(new JedisPubSub() { } else {
isActiveAndEnabled = false;
log(Level.SEVERE, "Connection to the Redis server could not be established, please check the credentials.");
return;
}
jedis.subscribe(new JedisPubSub() {
@Override @Override
public void onMessage(String channel, String message) { public void onMessage(String channel, String message) {
// Only accept messages to the HuskSync channel // Only accept messages to the HuskSync channel
@ -59,13 +83,11 @@ public abstract class RedisListener {
log(Level.SEVERE, "Failed to deserialize message target"); log(Level.SEVERE, "Failed to deserialize message target");
} }
} }
}, RedisMessage.REDIS_CHANNEL), "Redis Subscriber").start(); }, RedisMessage.REDIS_CHANNEL);
} else { } catch (JedisException | IllegalStateException e) {
log(Level.SEVERE, "An exception occurred with the Jedis Subscriber!");
isActiveAndEnabled = false; isActiveAndEnabled = false;
log(Level.SEVERE, "Failed to initialize the redis listener!");
}
} catch (JedisException e) {
log(Level.SEVERE, "Failed to establish a connection to the Redis server!");
} }
}, "Redis Subscriber").start();
} }
} }

@ -22,6 +22,7 @@ public class RedisMessage {
/** /**
* Create a new RedisMessage * Create a new RedisMessage
*
* @param type The type of the message * @param type The type of the message
* @param target Who will receive this message * @param target Who will receive this message
* @param messageData The message data elements * @param messageData The message data elements
@ -38,6 +39,7 @@ public class RedisMessage {
/** /**
* Get a new RedisMessage from an incoming message string * Get a new RedisMessage from an incoming message string
*
* @param messageString The message string to parse * @param messageString The message string to parse
*/ */
public RedisMessage(String messageString) throws IOException, ClassNotFoundException { public RedisMessage(String messageString) throws IOException, ClassNotFoundException {
@ -49,6 +51,7 @@ public class RedisMessage {
/** /**
* Returns the full, formatted message string with type, target & data * Returns the full, formatted message string with type, target & data
*
* @return The fully formatted message * @return The fully formatted message
*/ */
private String getFullMessage() throws IOException { private String getFullMessage() throws IOException {
@ -61,7 +64,7 @@ public class RedisMessage {
* Send the redis message * Send the redis message
*/ */
public void send() throws IOException { public void send() throws IOException {
try (Jedis publisher = new Jedis(Settings.redisHost, Settings.redisPort)) { try (Jedis publisher = RedisListener.getJedisConnection()) {
final String jedisPassword = Settings.redisPassword; final String jedisPassword = Settings.redisPassword;
publisher.connect(); publisher.connect();
if (!jedisPassword.equals("")) { if (!jedisPassword.equals("")) {
@ -75,7 +78,9 @@ public class RedisMessage {
return messageData; return messageData;
} }
public String[] getMessageDataElements() { return messageData.split(MESSAGE_DATA_SEPARATOR); } public String[] getMessageDataElements() {
return messageData.split(MESSAGE_DATA_SEPARATOR);
}
public MessageType getMessageType() { public MessageType getMessageType() {
return messageType; return messageType;
@ -173,7 +178,9 @@ public class RedisMessage {
/** /**
* A record that defines the target of a plugin message; a spigot server or the proxy server(s). For Bukkit servers, the name of the server must also be specified * A record that defines the target of a plugin message; a spigot server or the proxy server(s). For Bukkit servers, the name of the server must also be specified
*/ */
public record MessageTarget(Settings.ServerType targetServerType, UUID targetPlayerUUID, String targetClusterId) implements Serializable { } public record MessageTarget(Settings.ServerType targetServerType, UUID targetPlayerUUID,
String targetClusterId) implements Serializable {
}
/** /**
* Deserialize an object from a Base64 string * Deserialize an object from a Base64 string

@ -69,6 +69,8 @@ public class HuskSyncVelocity {
public static DataManager dataManager; public static DataManager dataManager;
public static VelocityRedisListener redisListener;
public static MPDBMigrator mpdbMigrator; public static MPDBMigrator mpdbMigrator;
private final Logger logger; private final Logger logger;
@ -146,7 +148,8 @@ public class HuskSyncVelocity {
} }
// Initialize the redis listener // Initialize the redis listener
if (!new VelocityRedisListener().isActiveAndEnabled) { redisListener = new VelocityRedisListener();
if (!redisListener.isActiveAndEnabled) {
getVelocityLogger().severe("Failed to initialize Redis; HuskSync will now abort loading itself (Velocity) v" + VERSION); getVelocityLogger().severe("Failed to initialize Redis; HuskSync will now abort loading itself (Velocity) v" + VERSION);
return; return;
} }

@ -294,7 +294,7 @@ public class VelocityCommand implements SimpleCommand, HuskSyncCommand {
HuskSyncVelocity.synchronisedServers)) { HuskSyncVelocity.synchronisedServers)) {
plugin.getProxyServer().getScheduler().buildTask(plugin, () -> plugin.getProxyServer().getScheduler().buildTask(plugin, () ->
HuskSyncVelocity.mpdbMigrator.executeMigrationOperations(HuskSyncVelocity.dataManager, HuskSyncVelocity.mpdbMigrator.executeMigrationOperations(HuskSyncVelocity.dataManager,
HuskSyncVelocity.synchronisedServers)).schedule(); HuskSyncVelocity.synchronisedServers, HuskSyncVelocity.redisListener)).schedule();
} }
} }
default -> sender.sendMessage(new MineDown("Error: Invalid argument for migration. Use \"husksync migrate\" to start the process").toComponent()); default -> sender.sendMessage(new MineDown("Error: Invalid argument for migration. Use \"husksync migrate\" to start the process").toComponent());

@ -23,6 +23,7 @@ public class VelocityRedisListener extends RedisListener {
// Initialize the listener on the bungee // Initialize the listener on the bungee
public VelocityRedisListener() { public VelocityRedisListener() {
super();
listen(); listen();
} }

Loading…
Cancel
Save