Stage 2 of IP -> UUID migration: changing the admin list to use UUIDs

This commit is contained in:
Video 2022-04-15 07:09:23 -06:00
parent 98388d0d23
commit 05745c4210
8 changed files with 49 additions and 116 deletions

View File

@ -3,7 +3,10 @@ package me.totalfreedom.totalfreedommod;
import io.papermc.lib.PaperLib; import io.papermc.lib.PaperLib;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import java.util.UUID;
import java.util.regex.Pattern; import java.util.regex.Pattern;
import me.totalfreedom.totalfreedommod.admin.Admin;
import me.totalfreedom.totalfreedommod.config.ConfigEntry; import me.totalfreedom.totalfreedommod.config.ConfigEntry;
import me.totalfreedom.totalfreedommod.player.FPlayer; import me.totalfreedom.totalfreedommod.player.FPlayer;
import me.totalfreedom.totalfreedommod.player.PlayerData; import me.totalfreedom.totalfreedommod.player.PlayerData;
@ -58,13 +61,13 @@ public class LoginProcess extends FreedomService
@EventHandler(priority = EventPriority.NORMAL) @EventHandler(priority = EventPriority.NORMAL)
public void onPlayerPreLogin(AsyncPlayerPreLoginEvent event) public void onPlayerPreLogin(AsyncPlayerPreLoginEvent event)
{ {
final String ip = event.getAddress().getHostAddress().trim(); final Admin entry = plugin.al.getEntryByUuid(event.getUniqueId());
final boolean isAdmin = plugin.al.getEntryByIp(ip) != null; final boolean isAdmin = entry != null && entry.isActive();
// Check if the player is already online // Check if the player is already online
for (Player onlinePlayer : server.getOnlinePlayers()) for (Player onlinePlayer : server.getOnlinePlayers())
{ {
if (!onlinePlayer.getName().equalsIgnoreCase(event.getName())) if (!onlinePlayer.getUniqueId().equals(event.getUniqueId()))
{ {
continue; continue;
} }
@ -86,7 +89,7 @@ public class LoginProcess extends FreedomService
{ {
final Player player = event.getPlayer(); final Player player = event.getPlayer();
final String username = player.getName(); final String username = player.getName();
final String ip = event.getAddress().getHostAddress().trim(); final UUID uuid = player.getUniqueId();
// Check username length // Check username length
if (username.length() < MIN_USERNAME_LENGTH || username.length() > MAX_USERNAME_LENGTH) if (username.length() < MIN_USERNAME_LENGTH || username.length() > MAX_USERNAME_LENGTH)
@ -120,7 +123,8 @@ public class LoginProcess extends FreedomService
} }
// Validation below this point // Validation below this point
if (plugin.al.getEntryByIp(ip) != null) // Check if player is admin final Admin entry = plugin.al.getEntryByUuid(uuid);
if (entry != null && entry.isActive()) // Check if player is admin
{ {
// Force-allow log in // Force-allow log in
event.allow(); event.allow();

View File

@ -2,11 +2,8 @@ package me.totalfreedom.totalfreedommod.admin;
import java.sql.ResultSet; import java.sql.ResultSet;
import java.sql.SQLException; import java.sql.SQLException;
import java.util.ArrayList; import java.util.*;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import me.totalfreedom.totalfreedommod.LogViewer.LogsRegistrationMode; import me.totalfreedom.totalfreedommod.LogViewer.LogsRegistrationMode;
import me.totalfreedom.totalfreedommod.TotalFreedomMod; import me.totalfreedom.totalfreedommod.TotalFreedomMod;
import me.totalfreedom.totalfreedommod.rank.Rank; import me.totalfreedom.totalfreedommod.rank.Rank;
@ -18,10 +15,8 @@ import org.bukkit.entity.Player;
public class Admin public class Admin
{ {
private final List<String> ips = new ArrayList<>(); private final List<String> ips = new ArrayList<>();
private String name; private UUID uuid;
private boolean active = true; private boolean active = true;
private Rank rank = Rank.ADMIN; private Rank rank = Rank.ADMIN;
private Date lastLogin = new Date(); private Date lastLogin = new Date();
@ -32,7 +27,7 @@ public class Admin
public Admin(Player player) public Admin(Player player)
{ {
this.name = player.getName(); uuid = player.getUniqueId();
this.ips.add(FUtil.getIp(player)); this.ips.add(FUtil.getIp(player));
} }
@ -40,7 +35,7 @@ public class Admin
{ {
try try
{ {
this.name = resultSet.getString("username"); this.uuid = UUID.fromString(resultSet.getString("uuid"));
this.active = resultSet.getBoolean("active"); this.active = resultSet.getBoolean("active");
this.rank = Rank.findRank(resultSet.getString("rank")); this.rank = Rank.findRank(resultSet.getString("rank"));
this.ips.clear(); this.ips.clear();
@ -62,7 +57,7 @@ public class Admin
{ {
final StringBuilder output = new StringBuilder(); final StringBuilder output = new StringBuilder();
output.append("Admin: ").append(name).append("\n") output.append("Admin: ").append(getName()).append("\n")
.append("- IPs: ").append(StringUtils.join(ips, ", ")).append("\n") .append("- IPs: ").append(StringUtils.join(ips, ", ")).append("\n")
.append("- Last Login: ").append(FUtil.dateToString(lastLogin)).append("\n") .append("- Last Login: ").append(FUtil.dateToString(lastLogin)).append("\n")
.append("- Rank: ").append(rank.getName()).append("\n") .append("- Rank: ").append(rank.getName()).append("\n")
@ -78,7 +73,7 @@ public class Admin
{ {
Map<String, Object> map = new HashMap<String, Object>() Map<String, Object> map = new HashMap<String, Object>()
{{ {{
put("username", name); put("uuid", uuid.toString());
put("active", active); put("active", active);
put("rank", rank.toString()); put("rank", rank.toString());
put("ips", FUtil.listToString(ips)); put("ips", FUtil.listToString(ips));
@ -120,20 +115,20 @@ public class Admin
public boolean isValid() public boolean isValid()
{ {
return name != null return uuid != null
&& rank != null && rank != null
&& !ips.isEmpty() && !ips.isEmpty()
&& lastLogin != null; && lastLogin != null;
} }
public String getName() public UUID getUuid()
{ {
return name; return uuid;
} }
public void setName(String name) public String getName()
{ {
this.name = name; return Bukkit.getOfflinePlayer(uuid).getName();
} }
public boolean isActive() public boolean isActive()

View File

@ -4,11 +4,7 @@ import com.google.common.collect.Maps;
import com.google.common.collect.Sets; import com.google.common.collect.Sets;
import java.sql.ResultSet; import java.sql.ResultSet;
import java.sql.SQLException; import java.sql.SQLException;
import java.util.ArrayList; import java.util.*;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import me.totalfreedom.totalfreedommod.FreedomService; import me.totalfreedom.totalfreedommod.FreedomService;
import me.totalfreedom.totalfreedommod.config.ConfigEntry; import me.totalfreedom.totalfreedommod.config.ConfigEntry;
@ -26,6 +22,7 @@ public class AdminList extends FreedomService
private final Set<Admin> allAdmins = Sets.newHashSet(); // Includes disabled admins private final Set<Admin> allAdmins = Sets.newHashSet(); // Includes disabled admins
// Only active admins below // Only active admins below
private final Set<Admin> activeAdmins = Sets.newHashSet(); private final Set<Admin> activeAdmins = Sets.newHashSet();
private final Map<UUID, Admin> uuidTable = Maps.newHashMap();
private final Map<String, Admin> nameTable = Maps.newHashMap(); private final Map<String, Admin> nameTable = Maps.newHashMap();
private final Map<String, Admin> ipTable = Maps.newHashMap(); private final Map<String, Admin> ipTable = Maps.newHashMap();
@ -66,7 +63,7 @@ public class AdminList extends FreedomService
} }
updateTables(); updateTables();
FLog.info("Loaded " + allAdmins.size() + " admins (" + nameTable.size() + " active, " + ipTable.size() + " IPs)"); FLog.info("Loaded " + allAdmins.size() + " admins (" + uuidTable.size() + " active, " + ipTable.size() + " IPs)");
} }
public void messageAllAdmins(String message) public void messageAllAdmins(String message)
@ -154,40 +151,20 @@ public class AdminList extends FreedomService
public Admin getAdmin(Player player) public Admin getAdmin(Player player)
{ {
// Find admin final String ip = FUtil.getIp(player);
String ip = FUtil.getIp(player); final Admin entry = getEntryByUuid(player.getUniqueId());
Admin admin = getEntryByName(player.getName());
// Admin by name if (entry != null && !entry.getIps().contains(ip))
if (admin != null)
{ {
// Check if we're in online mode, entry.addIp(ip);
// Or the players IP is in the admin entry
if (Bukkit.getOnlineMode() || admin.getIps().contains(ip))
{
if (!admin.getIps().contains(ip))
{
// Add the new IP if we have to
admin.addIp(ip);
save(admin);
updateTables();
}
return admin;
}
} }
// Admin by ip return entry;
admin = getEntryByIp(ip);
if (admin != null)
{
// Set the new username
String oldName = admin.getName();
admin.setName(player.getName());
plugin.sql.updateAdminName(oldName, admin.getName());
updateTables();
} }
return null; public Admin getEntryByUuid(UUID uuid)
{
return uuidTable.get(uuid);
} }
public Admin getEntryByName(String name) public Admin getEntryByName(String name)
@ -200,25 +177,6 @@ public class AdminList extends FreedomService
return ipTable.get(ip); return ipTable.get(ip);
} }
public Admin getEntryByIpFuzzy(String needleIp)
{
final Admin directAdmin = getEntryByIp(needleIp);
if (directAdmin != null)
{
return directAdmin;
}
for (String ip : ipTable.keySet())
{
if (FUtil.fuzzyIpMatch(needleIp, ip, 3))
{
return ipTable.get(ip);
}
}
return null;
}
public void updateLastLogin(Player player) public void updateLastLogin(Player player)
{ {
final Admin admin = getAdmin(player); final Admin admin = getAdmin(player);
@ -228,13 +186,12 @@ public class AdminList extends FreedomService
} }
admin.setLastLogin(new Date()); admin.setLastLogin(new Date());
admin.setName(player.getName());
save(admin); save(admin);
} }
public boolean isAdminImpostor(Player player) public boolean isAdminImpostor(Player player)
{ {
return getEntryByName(player.getName()) != null && !isAdmin(player) && !isVerifiedAdmin(player); return getEntryByUuid(player.getUniqueId()) != null && !isAdmin(player) && !isVerifiedAdmin(player);
} }
public boolean isVerifiedAdmin(Player player) public boolean isVerifiedAdmin(Player player)
@ -297,6 +254,7 @@ public class AdminList extends FreedomService
public void updateTables() public void updateTables()
{ {
activeAdmins.clear(); activeAdmins.clear();
uuidTable.clear();
nameTable.clear(); nameTable.clear();
ipTable.clear(); ipTable.clear();
@ -308,13 +266,13 @@ public class AdminList extends FreedomService
} }
activeAdmins.add(admin); activeAdmins.add(admin);
uuidTable.put(admin.getUuid(), admin);
nameTable.put(admin.getName().toLowerCase(), admin); nameTable.put(admin.getName().toLowerCase(), admin);
for (String ip : admin.getIps()) for (String ip : admin.getIps())
{ {
ipTable.put(ip, admin); ipTable.put(ip, admin);
} }
} }
} }
@ -332,11 +290,10 @@ public class AdminList extends FreedomService
{ {
try try
{ {
ResultSet currentSave = plugin.sql.getAdminByName(admin.getName()); ResultSet currentSave = plugin.sql.getAdminByUuid(admin.getUuid());
for (Map.Entry<String, Object> entry : admin.toSQLStorable().entrySet()) for (Map.Entry<String, Object> entry : admin.toSQLStorable().entrySet())
{ {
Object storedValue = plugin.sql.getValue(currentSave, entry.getKey(), entry.getValue()); Object storedValue = plugin.sql.getValue(currentSave, entry.getKey(), entry.getValue()); if (storedValue != null && !storedValue.equals(entry.getValue()) || storedValue == null && entry.getValue() != null || entry.getValue() == null)
if (storedValue != null && !storedValue.equals(entry.getValue()) || storedValue == null && entry.getValue() != null || entry.getValue() == null)
{ {
plugin.sql.setAdminValue(admin, entry.getKey(), entry.getValue()); plugin.sql.setAdminValue(admin, entry.getKey(), entry.getValue());
} }

View File

@ -42,7 +42,7 @@ public class BukkitTelnetBridge extends FreedomService
return; return;
} }
final Admin admin = plugin.al.getEntryByIpFuzzy(ip); final Admin admin = plugin.al.getEntryByIp(ip);
if (admin == null || !admin.isActive() || !admin.getRank().hasConsoleVariant()) if (admin == null || !admin.isActive() || !admin.getRank().hasConsoleVariant())
{ {

View File

@ -205,15 +205,7 @@ public class Command_saconfig extends FreedomCommand
else // Existing admin else // Existing admin
{ {
FUtil.adminAction(sender.getName(), "Re-adding " + player.getName() + " to the admin list", true); FUtil.adminAction(sender.getName(), "Re-adding " + player.getName() + " to the admin list", true);
String oldName = admin.getName();
if (!oldName.equals(player.getName()))
{
admin.setName(player.getName());
plugin.sql.updateAdminName(oldName, admin.getName());
}
admin.addIp(FUtil.getIp(player)); admin.addIp(FUtil.getIp(player));
admin.setActive(true); admin.setActive(true);
admin.setLastLogin(new Date()); admin.setLastLogin(new Date());

View File

@ -24,7 +24,7 @@ public class PrivateMessageListener extends ListenerAdapter
player.setDiscordID(event.getMessage().getAuthor().getId()); player.setDiscordID(event.getMessage().getAuthor().getId());
player.setVerification(true); player.setVerification(true);
Admin admin = TotalFreedomMod.getPlugin().al.getEntryByName(name); Admin admin = TotalFreedomMod.getPlugin().al.getEntryByUuid(player.getUuid());
if (admin != null) if (admin != null)
{ {
Discord.syncRoles(admin, player.getDiscordID()); Discord.syncRoles(admin, player.getDiscordID());

View File

@ -100,7 +100,7 @@ public class PlayerList extends FreedomService
public boolean isTelnetMasterBuilder(PlayerData playerData) public boolean isTelnetMasterBuilder(PlayerData playerData)
{ {
Admin admin = plugin.al.getEntryByName(playerData.getName()); Admin admin = plugin.al.getEntryByUuid(playerData.getUuid());
return admin != null && admin.getRank().isAtLeast(Rank.ADMIN) && playerData.isMasterBuilder(); return admin != null && admin.getRank().isAtLeast(Rank.ADMIN) && playerData.isMasterBuilder();
} }
@ -165,7 +165,7 @@ public class PlayerList extends FreedomService
if (plugin.al.isAdminImpostor(player)) if (plugin.al.isAdminImpostor(player))
{ {
Admin admin = plugin.al.getEntryByName(player.getName()); Admin admin = plugin.al.getEntryByUuid(player.getUniqueId());
admin.setLastLogin(new Date()); admin.setLastLogin(new Date());
admin.addIp(FUtil.getIp(player)); admin.addIp(FUtil.getIp(player));
plugin.al.updateTables(); plugin.al.updateTables();
@ -185,7 +185,7 @@ public class PlayerList extends FreedomService
public void syncIps(PlayerData playerData) public void syncIps(PlayerData playerData)
{ {
Admin admin = plugin.al.getEntryByName(playerData.getName()); Admin admin = plugin.al.getEntryByUuid(playerData.getUuid());
if (admin != null && admin.isActive()) if (admin != null && admin.isActive())
{ {

View File

@ -84,7 +84,7 @@ public class SQLite extends FreedomService
{ {
try try
{ {
connection.createStatement().execute("CREATE TABLE `admins` (`username` VARCHAR NOT NULL, `ips` VARCHAR NOT NULL, `rank` VARCHAR NOT NULL, `active` BOOLEAN NOT NULL, `last_login` LONG NOT NULL, `command_spy` BOOLEAN NOT NULL, `potion_spy` BOOLEAN NOT NULL, `ac_format` VARCHAR, `ptero_id` VARCHAR);"); connection.createStatement().execute("CREATE TABLE `admins` (`uuid` VARCHAR NOT NULL, `ips` VARCHAR NOT NULL, `rank` VARCHAR NOT NULL, `active` BOOLEAN NOT NULL, `last_login` LONG NOT NULL, `command_spy` BOOLEAN NOT NULL, `potion_spy` BOOLEAN NOT NULL, `ac_format` VARCHAR, `ptero_id` VARCHAR);");
} }
catch (SQLException e) catch (SQLException e)
{ {
@ -135,8 +135,8 @@ public class SQLite extends FreedomService
{ {
try try
{ {
Object[] data = {key, admin.getName()}; Object[] data = {key, admin.getUuid()};
PreparedStatement statement = connection.prepareStatement(MessageFormat.format("UPDATE admins SET {0}=? WHERE username=''{1}''", data)); PreparedStatement statement = connection.prepareStatement(MessageFormat.format("UPDATE admins SET {0}=? WHERE uuid=''{1}''", data));
statement = setUnknownType(statement, 1, value); statement = setUnknownType(statement, 1, value);
statement.executeUpdate(); statement.executeUpdate();
@ -164,21 +164,6 @@ public class SQLite extends FreedomService
} }
} }
public void updateAdminName(String oldName, String newName)
{
try
{
PreparedStatement statement = connection.prepareStatement(MessageFormat.format("UPDATE admins SET username=? WHERE username=''{0}''", oldName));
statement = setUnknownType(statement, 1, newName);
statement.executeUpdate();
}
catch (SQLException e)
{
FLog.severe("Failed to update admin name: " + e.getMessage());
}
}
public PreparedStatement setUnknownType(PreparedStatement statement, int index, Object value) throws SQLException public PreparedStatement setUnknownType(PreparedStatement statement, int index, Object value) throws SQLException
{ {
if (value == null) if (value == null)
@ -235,7 +220,7 @@ public class SQLite extends FreedomService
try try
{ {
PreparedStatement statement = connection.prepareStatement("INSERT INTO admins VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)"); PreparedStatement statement = connection.prepareStatement("INSERT INTO admins VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)");
statement.setString(1, admin.getName()); statement.setString(1, admin.getUuid().toString());
statement.setString(2, FUtil.listToString(admin.getIps())); statement.setString(2, FUtil.listToString(admin.getIps()));
statement.setString(3, admin.getRank().toString()); statement.setString(3, admin.getRank().toString());
statement.setBoolean(4, admin.isActive()); statement.setBoolean(4, admin.isActive());
@ -282,11 +267,11 @@ public class SQLite extends FreedomService
} }
} }
public ResultSet getAdminByName(String name) public ResultSet getAdminByUuid(UUID uuid)
{ {
try try
{ {
ResultSet resultSet = connection.createStatement().executeQuery(MessageFormat.format("SELECT * FROM admins WHERE username=''{0}''", name)); ResultSet resultSet = connection.createStatement().executeQuery(MessageFormat.format("SELECT * FROM admins WHERE uuid=''{0}''", uuid.toString()));
if (resultSet.next()) if (resultSet.next())
{ {
return resultSet; return resultSet;