diff --git a/MCGalaxy/Commands/Chat/CmdColor.cs b/MCGalaxy/Commands/Chat/CmdColor.cs index eb5203aae..539536b38 100644 --- a/MCGalaxy/Commands/Chat/CmdColor.cs +++ b/MCGalaxy/Commands/Chat/CmdColor.cs @@ -63,7 +63,7 @@ namespace MCGalaxy.Commands.Chatting { Entities.GlobalRespawn(who); who.SetPrefix(); - PlayerData.Update(who.name, PlayerData.ColumnColor, color); + PlayerDB.Update(who.name, PlayerData.ColumnColor, color); } public override void Help(Player p) { diff --git a/MCGalaxy/Commands/Chat/CmdIgnore.cs b/MCGalaxy/Commands/Chat/CmdIgnore.cs index 55d5a92f0..ed7acb6ce 100644 --- a/MCGalaxy/Commands/Chat/CmdIgnore.cs +++ b/MCGalaxy/Commands/Chat/CmdIgnore.cs @@ -55,7 +55,7 @@ namespace MCGalaxy.Commands.Chatting { if (p.Ignores.Names.CaselessRemove(action)) { Player.Message(p, "&aNo longer ignoring {0}", action); } else { - int matches = 0; + int matches; Player who = PlayerInfo.FindMatches(p, action, out matches); if (who == null) { if (matches == 0) diff --git a/MCGalaxy/Commands/Chat/CmdLoginMessage.cs b/MCGalaxy/Commands/Chat/CmdLoginMessage.cs index 33a5551e1..f04299e16 100644 --- a/MCGalaxy/Commands/Chat/CmdLoginMessage.cs +++ b/MCGalaxy/Commands/Chat/CmdLoginMessage.cs @@ -15,7 +15,6 @@ or implied. See the Licenses for the specific language governing permissions and limitations under the Licenses. */ -using System.IO; using MCGalaxy.DB; namespace MCGalaxy.Commands.Chatting { @@ -33,16 +32,14 @@ namespace MCGalaxy.Commands.Chatting { UsePlayer(p, message, "login message"); } - protected override void SetPlayerData(Player p, Player who, string loginMsg) { - if (loginMsg.Length == 0) { - string path = PlayerDB.LoginPath(who.name); - if (File.Exists(path)) File.Delete(path); + protected override void SetPlayerData(Player p, Player who, string msg) { + PlayerDB.SetLoginMessage(who.name, msg); + if (msg.Length == 0) { Player.Message(p, "Login message of {0} %Swas removed.", who.ColoredName); } else { - PlayerDB.SetLoginMessage(who.name, loginMsg); Player.Message(p, "Login message of {0} %Swas changed to: {1}", - who.ColoredName, loginMsg); + who.ColoredName, msg); } } diff --git a/MCGalaxy/Commands/Chat/CmdLogoutMessage.cs b/MCGalaxy/Commands/Chat/CmdLogoutMessage.cs index 0d3a24d44..72b637fbf 100644 --- a/MCGalaxy/Commands/Chat/CmdLogoutMessage.cs +++ b/MCGalaxy/Commands/Chat/CmdLogoutMessage.cs @@ -15,7 +15,6 @@ or implied. See the Licenses for the specific language governing permissions and limitations under the Licenses. */ -using System.IO; using MCGalaxy.DB; namespace MCGalaxy.Commands.Chatting { @@ -33,16 +32,14 @@ namespace MCGalaxy.Commands.Chatting { UsePlayer(p, message, "logout message"); } - protected override void SetPlayerData(Player p, Player who, string logoutMsg) { - if (logoutMsg.Length == 0) { - string path = PlayerDB.LogoutPath(who.name); - if (File.Exists(path)) File.Delete(path); + protected override void SetPlayerData(Player p, Player who, string msg) { + PlayerDB.SetLogoutMessage(who.name, msg); + if (msg.Length == 0) { Player.Message(p, "Logout message of {0} %Swas removed.", who.ColoredName); - } else { - PlayerDB.SetLogoutMessage(who.name, logoutMsg); + } else { Player.Message(p, "Logout message of {0} %Swas changed to: {1}", - who.ColoredName, logoutMsg); + who.ColoredName, msg); } } diff --git a/MCGalaxy/Commands/Chat/CmdNick.cs b/MCGalaxy/Commands/Chat/CmdNick.cs index 23c396b49..6949e202d 100644 --- a/MCGalaxy/Commands/Chat/CmdNick.cs +++ b/MCGalaxy/Commands/Chat/CmdNick.cs @@ -57,7 +57,7 @@ namespace MCGalaxy.Commands.Chatting { } protected override void SetPlayerData(Player p, Player who, string nick) { - if (nick.Length == 0) { + if (nick.Length == 0) { Chat.MessageFrom(who, "λNICK %Shad their custom nick reset"); who.DisplayName = who.truename; } else { @@ -65,8 +65,7 @@ namespace MCGalaxy.Commands.Chatting { Chat.MessageFrom(who, "λNICK %Shad their nick set to " + who.color + nick); who.DisplayName = nick; - } - + } PlayerDB.Save(who); } diff --git a/MCGalaxy/Commands/Chat/CmdTColor.cs b/MCGalaxy/Commands/Chat/CmdTColor.cs index 2b8148c2d..0b94f0d20 100644 --- a/MCGalaxy/Commands/Chat/CmdTColor.cs +++ b/MCGalaxy/Commands/Chat/CmdTColor.cs @@ -44,7 +44,7 @@ namespace MCGalaxy.Commands.Chatting { who.titlecolor = color; who.SetPrefix(); - PlayerData.Update(who.name, PlayerData.ColumnTColor, color); + PlayerDB.Update(who.name, PlayerData.ColumnTColor, color); } public override void Help(Player p) { diff --git a/MCGalaxy/Commands/Chat/CmdTitle.cs b/MCGalaxy/Commands/Chat/CmdTitle.cs index aa393a653..e33720e85 100644 --- a/MCGalaxy/Commands/Chat/CmdTitle.cs +++ b/MCGalaxy/Commands/Chat/CmdTitle.cs @@ -45,7 +45,7 @@ namespace MCGalaxy.Commands.Chatting { who.title = title; who.SetPrefix(); - PlayerData.Update(who.name, PlayerData.ColumnTitle, title.UnicodeToCp437()); + PlayerDB.Update(who.name, PlayerData.ColumnTitle, title.UnicodeToCp437()); } public override void Help(Player p) { diff --git a/MCGalaxy/Commands/Information/CmdSeen.cs b/MCGalaxy/Commands/Information/CmdSeen.cs index 8c4663964..03a99b759 100644 --- a/MCGalaxy/Commands/Information/CmdSeen.cs +++ b/MCGalaxy/Commands/Information/CmdSeen.cs @@ -37,7 +37,7 @@ namespace MCGalaxy.Commands.Info { } Player.Message(p, "Searching PlayerDB.."); - PlayerData target = PlayerInfo.FindOfflineMatches(p, message); + PlayerData target = PlayerDB.Match(p, message); if (target == null) return; Show(p, target.Name, target.FirstLogin, target.LastLogin); } diff --git a/MCGalaxy/Commands/Information/CmdWhoNick.cs b/MCGalaxy/Commands/Information/CmdWhoNick.cs index 46121f02d..e60809cc2 100644 --- a/MCGalaxy/Commands/Information/CmdWhoNick.cs +++ b/MCGalaxy/Commands/Information/CmdWhoNick.cs @@ -14,12 +14,12 @@ BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the Licenses for the specific language governing permissions and limitations under the Licenses. -*/ + */ using System.Data; using MCGalaxy.SQL; namespace MCGalaxy.Commands.Info { - public sealed class CmdWhoNick : Command { + public sealed class CmdWhoNick : Command { public override string name { get { return "WhoNick"; } } public override string shortcut { get { return "RealName"; } } public override string type { get { return CommandTypes.Information; } } @@ -31,14 +31,14 @@ namespace MCGalaxy.Commands.Info { if (nick == null) return; Player.Message(p, "This player's real username is " + nick.name); - } - + } + static Player FindNick(Player p, string nick) { nick = Colors.Strip(nick); Player[] players = PlayerInfo.Online.Items; - int matches = 0; - return Matcher.Find(p, nick, out matches, players, pl => Entities.CanSee(p, pl), - pl => Colors.Strip(pl.DisplayName), "online player nicks"); + int matches; + return Matcher.Find(p, nick, out matches, players, pl => Entities.CanSee(p, pl), + pl => Colors.Strip(pl.DisplayName), "online player nicks"); } public override void Help(Player p) { diff --git a/MCGalaxy/Commands/Information/CmdWhois.cs b/MCGalaxy/Commands/Information/CmdWhois.cs index 216264d3c..9297db7b8 100644 --- a/MCGalaxy/Commands/Information/CmdWhois.cs +++ b/MCGalaxy/Commands/Information/CmdWhois.cs @@ -40,7 +40,7 @@ namespace MCGalaxy.Commands.Info { if (matches == 0) { if (!Formatter.ValidName(p, message, "player")) return; Player.Message(p, "Searching database for the player.."); - PlayerData target = PlayerInfo.FindOfflineMatches(p, message); + PlayerData target = PlayerDB.Match(p, message); if (target == null) return; foreach (OfflineStatPrinter printer in OfflineStat.Stats) { diff --git a/MCGalaxy/Commands/Maintenance/CmdPlayerEdit.cs b/MCGalaxy/Commands/Maintenance/CmdPlayerEdit.cs index c931fc355..524082eb6 100644 --- a/MCGalaxy/Commands/Maintenance/CmdPlayerEdit.cs +++ b/MCGalaxy/Commands/Maintenance/CmdPlayerEdit.cs @@ -73,7 +73,7 @@ namespace MCGalaxy.Commands.Maintenance { who.SetPrefix(); } - PlayerData.Update(args[0], PlayerData.ColumnTitle, args[2].UnicodeToCp437()); + PlayerDB.Update(args[0], PlayerData.ColumnTitle, args[2].UnicodeToCp437()); MessageDataChanged(p, args[0], args[1], args[2]); } else if (opt == "modified") { SetInteger(p, args, PlayerData.ColumnTotalBlocks, int.MaxValue, who, @@ -123,7 +123,7 @@ namespace MCGalaxy.Commands.Maintenance { args[0] = who.name; } - PlayerData.Update(args[0], column, col); + PlayerDB.Update(args[0], column, col); MessageDataChanged(p, args[0], args[1], args[2]); } @@ -141,7 +141,7 @@ namespace MCGalaxy.Commands.Maintenance { } if (who != null) setter(date); - PlayerData.Update(args[0], column, args[2]); + PlayerDB.Update(args[0], column, args[2]); MessageDataChanged(p, args[0], args[1], args[2]); } @@ -159,7 +159,7 @@ namespace MCGalaxy.Commands.Maintenance { setter(span); } else { long secs = (long)span.TotalSeconds; - PlayerData.Update(args[0], column, secs.ToString()); + PlayerDB.Update(args[0], column, secs.ToString()); } MessageDataChanged(p, args[0], args[1], span.Shorten(true)); } @@ -193,7 +193,7 @@ namespace MCGalaxy.Commands.Maintenance { packed |= ((long)value) << PlayerData.LowerBits; dbValue = packed.ToString(); } - PlayerData.Update(args[0], column, dbValue); + PlayerDB.Update(args[0], column, dbValue); } MessageDataChanged(p, args[0], args[1], args[2]); } diff --git a/MCGalaxy/Commands/Moderation/CmdHighlight.cs b/MCGalaxy/Commands/Moderation/CmdHighlight.cs index 037767661..8d2aad57a 100644 --- a/MCGalaxy/Commands/Moderation/CmdHighlight.cs +++ b/MCGalaxy/Commands/Moderation/CmdHighlight.cs @@ -49,7 +49,7 @@ namespace MCGalaxy.Commands.Moderation { delta = TimeSpan.FromMinutes(30); } - parts[0] = PlayerInfo.FindOfflineNameMatches(p, parts[0]); + parts[0] = PlayerDB.MatchNames(p, parts[0]); if (parts[0] == null) return; int[] ids = NameConverter.FindIds(parts[0]); diff --git a/MCGalaxy/Commands/Moderation/CmdReport.cs b/MCGalaxy/Commands/Moderation/CmdReport.cs index 743b7c2ce..b41fec38c 100644 --- a/MCGalaxy/Commands/Moderation/CmdReport.cs +++ b/MCGalaxy/Commands/Moderation/CmdReport.cs @@ -20,6 +20,7 @@ using System; using System.Collections.Generic; using System.IO; +using MCGalaxy.DB; namespace MCGalaxy.Commands.Moderation { public sealed class CmdReport : Command { @@ -93,7 +94,7 @@ namespace MCGalaxy.Commands.Moderation { Player.Message(p, "You need to provide a player's name."); return; } if (!CheckExtraPerm(p, 1)) return; - string target = PlayerInfo.FindOfflineNameMatches(p, args[1]); + string target = PlayerDB.MatchNames(p, args[1]); if (target == null) return; if (!File.Exists("extra/reported/" + target + ".txt")) { @@ -109,7 +110,7 @@ namespace MCGalaxy.Commands.Moderation { Player.Message(p, "You need to provide a player's name."); return; } if (!CheckExtraPerm(p, 1)) return; - string target = PlayerInfo.FindOfflineNameMatches(p, args[1]); + string target = PlayerDB.MatchNames(p, args[1]); if (target == null) return; if (!File.Exists("extra/reported/" + target + ".txt")) { @@ -142,7 +143,7 @@ namespace MCGalaxy.Commands.Moderation { if (args.Length != 2) { Player.Message(p, "You need to provide a reason for the report."); return; } - string target = PlayerInfo.FindOfflineNameMatches(p, args[0]); + string target = PlayerDB.MatchNames(p, args[0]); if (target == null) return; List reports = new List(); diff --git a/MCGalaxy/Commands/Moderation/CmdUndoPlayer.cs b/MCGalaxy/Commands/Moderation/CmdUndoPlayer.cs index 4757f6b1d..f0a716630 100644 --- a/MCGalaxy/Commands/Moderation/CmdUndoPlayer.cs +++ b/MCGalaxy/Commands/Moderation/CmdUndoPlayer.cs @@ -105,7 +105,7 @@ namespace MCGalaxy.Commands.Moderation { names = new string[count]; for (int i = 0; i < names.Length; i++) { - names[i] = PlayerInfo.FindOfflineNameMatches(p, parts[i]); + names[i] = PlayerDB.MatchNames(p, parts[i]); if (names[i] == null) return null; Group grp = PlayerInfo.GetGroup(names[i]); diff --git a/MCGalaxy/Commands/Moderation/CmdWarn.cs b/MCGalaxy/Commands/Moderation/CmdWarn.cs index 724e93e3c..5fd8453eb 100644 --- a/MCGalaxy/Commands/Moderation/CmdWarn.cs +++ b/MCGalaxy/Commands/Moderation/CmdWarn.cs @@ -15,6 +15,7 @@ or implied. See the Licenses for the specific language governing permissions and limitations under the Licenses. */ +using MCGalaxy.DB; using MCGalaxy.Events; namespace MCGalaxy.Commands.Moderation { @@ -44,7 +45,7 @@ namespace MCGalaxy.Commands.Moderation { static void WarnOffline(Player p, string[] args, string reason) { Player.Message(p, "Searching PlayerDB.."); - string offName = PlayerInfo.FindOfflineNameMatches(p, args[0]); + string offName = PlayerDB.MatchNames(p, args[0]); if (offName == null) return; ModAction action = new ModAction(offName, p, ModActionType.Warned, reason); diff --git a/MCGalaxy/Commands/Moderation/ModActionCmd.cs b/MCGalaxy/Commands/Moderation/ModActionCmd.cs index 6f050d14d..eb046bfdb 100644 --- a/MCGalaxy/Commands/Moderation/ModActionCmd.cs +++ b/MCGalaxy/Commands/Moderation/ModActionCmd.cs @@ -92,7 +92,7 @@ namespace MCGalaxy.Commands.Moderation { if (who == null) return; Entities.DespawnEntities(who, false); - string dbCol = PlayerData.FindDBColor(who); + string dbCol = PlayerDB.FindColor(who); if (dbCol.Length == 0) who.color = newRank.Color; who.group = newRank; @@ -150,13 +150,13 @@ namespace MCGalaxy.Commands.Moderation { } static string MatchName(Player p, ref string name) { - int matches = 0; + int matches; Player target = PlayerInfo.FindMatches(p, name, out matches); if (matches > 1) return null; if (matches == 1) { name = target.name; return name; } Player.Message(p, "Searching PlayerDB..."); - return PlayerInfo.FindOfflineNameMatches(p, name); + return PlayerDB.MatchNames(p, name); } static string IsConfirmed(string reason) { diff --git a/MCGalaxy/Commands/Scripting/CmdPlugin.cs b/MCGalaxy/Commands/Scripting/CmdPlugin.cs index d69889285..3433e9b54 100644 --- a/MCGalaxy/Commands/Scripting/CmdPlugin.cs +++ b/MCGalaxy/Commands/Scripting/CmdPlugin.cs @@ -85,8 +85,8 @@ namespace MCGalaxy.Commands.Scripting { static void UnloadPlugin(Player p, string name) { int matches; - Plugin plugin = Matcher.Find(p, name, out matches, Plugin.all, - null, pln => pln.name, "plugins"); + Plugin plugin = Matcher.Find(p, name, out matches, Plugin.all, + null, pln => pln.name, "plugins"); if (plugin == null) return; if (Plugin.core.Contains(plugin)) { diff --git a/MCGalaxy/CorePlugin/MiscHandlers.cs b/MCGalaxy/CorePlugin/MiscHandlers.cs index c11b8edcc..f1b5d1213 100644 --- a/MCGalaxy/CorePlugin/MiscHandlers.cs +++ b/MCGalaxy/CorePlugin/MiscHandlers.cs @@ -111,7 +111,7 @@ namespace MCGalaxy.Core { if (p.group == null) p.group = Group.standard; p.SetPrefix(); - string dbCol = PlayerData.FindDBColor(p); + string dbCol = PlayerDB.FindColor(p); if (dbCol.Length == 0 && p.color != p.group.Color) { p.color = p.group.Color; Entities.GlobalRespawn(p); diff --git a/MCGalaxy/Database/PlayerDB.cs b/MCGalaxy/Database/PlayerDB.cs index 6598ace16..576f5b4d2 100644 --- a/MCGalaxy/Database/PlayerDB.cs +++ b/MCGalaxy/Database/PlayerDB.cs @@ -17,35 +17,27 @@ */ using System; using System.Collections.Generic; +using System.Data; using System.IO; +using MCGalaxy.SQL; namespace MCGalaxy.DB { /// Stores per-player persistent data. public static class PlayerDB { - public static string LoginPath(string name) { - return "text/login/" + name.ToLower() + ".txt"; - } - - public static string LogoutPath(string name) { - return "text/logout/" + name.ToLower() + ".txt"; - } - - public static string InfectPath(string name) { - return "text/infect/" + name.ToLower() + ".txt"; - } - + static string LoginPath(string name) { return "text/login/" + name.ToLower() + ".txt"; } + static string LogoutPath(string name) { return "text/logout/" + name.ToLower() + ".txt"; } static char[] trimChars = new char[] {'='}; - public static bool Load( Player p ) { + public static bool Load(Player p) { if (!File.Exists("players/" + p.name + "DB.txt")) return false; - string[] lines = File.ReadAllLines( "players/" + p.name + "DB.txt"); + string[] lines = File.ReadAllLines("players/" + p.name + "DB.txt"); foreach (string line in lines) { if (line.Length == 0 || line[0] == '#') continue; string[] parts = line.Split(trimChars, 2); - if (parts.Length < 2) continue; + if (parts.Length < 2) continue; string key = parts[0].Trim(), value = parts[1].Trim(); if (key.CaselessEq("nick")) @@ -67,53 +59,89 @@ namespace MCGalaxy.DB { Directory.CreateDirectory("text/login"); string path = LoginPath(p.name); - if (File.Exists(path)) return File.ReadAllText(path); + if (File.Exists(path)) return File.ReadAllText(path); // Unix is case sensitive (older files used correct casing of name) path = "text/login/" + p.name + ".txt"; return File.Exists(path) ? File.ReadAllText(path) : "connected"; } - /// Retrieves the logout message set for the given player. public static string GetLogoutMessage(Player p) { if (p.name == null) return "disconnected"; if (!Directory.Exists("text/logout")) Directory.CreateDirectory("text/logout"); string path = LogoutPath(p.name); - if (File.Exists(path)) return File.ReadAllText(path); + if (File.Exists(path)) return File.ReadAllText(path); path = "text/logout/" + p.name + ".txt"; return File.Exists(path) ? File.ReadAllText(path) : "disconnected"; } - - /// Retrieves the ZS infect messages list for the given player. - public static List GetInfectMessages(Player p) { - if (p.name == null || !Directory.Exists("text/infect")) return null; - string path = InfectPath(p.name); + + static void SetMessage(string path, string msg) { + if (msg.Length > 0) { + File.WriteAllText(path, msg); + } else if (File.Exists(path)) { + File.Delete(path); + } + } + + public static void SetLoginMessage(string name, string msg) { + SetMessage(LoginPath(name), msg); + } + + public static void SetLogoutMessage(string name, string msg) { + SetMessage(LogoutPath(name), msg); + } + + + public static void Update(string name, string column, string value) { + Database.Backend.UpdateRows("Players", column + "=@1", "WHERE Name=@0", name, value); + } + + public static string FindColor(Player p) { + string raw = Database.ReadString("Players", "Color", "WHERE ID=@0", p.DatabaseID); + if (raw == null) return ""; + return PlayerData.ParseCol(raw); + } + + + public static string MatchNames(Player p, string name) { + List names = new List(); + MatchMulti("Players", "Name", names, Database.ReadList); - if (!File.Exists(path)) return null; - string[] lines = File.ReadAllLines(path); - return new List(lines); + int matches; + return Matcher.Find(p, name, out matches, names, + null, n => n, "players", 20); } - - /// Sets the login message for the given player. - public static void SetLoginMessage(string name, string loginMsg) { - File.WriteAllText(LoginPath(name), loginMsg); - } - - /// Sets the logout message for the given player. - public static void SetLogoutMessage(string name, string logoutMsg) { - File.WriteAllText(LogoutPath(name), logoutMsg); - } - - public static void AppendInfectMessage(string name, string infectMsg) { - if (!Directory.Exists("text/infect")) - Directory.CreateDirectory("text/infect"); + public static string[] MatchValues(Player p, string name, string columns) { + List name_values = new List(); + MatchMulti("Players", columns, name_values, Database.ReadFields); - string path = InfectPath(name); - using (StreamWriter w = new StreamWriter(path, true)) - w.WriteLine(infectMsg); + int matches; + return Matcher.Find(p, name, out matches, name_values, + null, n => n[0], "players", 20); + } + + static object ReadStats(IDataRecord record, object arg) { + PlayerData stats = PlayerData.Parse(record); + ((List)arg).Add(stats); return arg; + } + + public static PlayerData Match(Player p, string name) { + List stats = new List(); + MatchMulti("Players", "*", stats, Database.ReadList); + + int matches; + return Matcher.Find(p, name, out matches, stats, + null, stat => stat.Name, "players", 20); + } + + static void MatchMulti(string name, string columns, object arg, ReaderCallback callback) { + string suffix = Database.Backend.CaselessLikeSuffix; + Database.Backend.ReadRows("Players", columns, arg, callback, + "WHERE Name LIKE @0 ESCAPE '#' LIMIT 21" + suffix, + "%" + name.Replace("_", "#_") + "%"); } } } \ No newline at end of file diff --git a/MCGalaxy/Database/PlayerData.cs b/MCGalaxy/Database/PlayerData.cs index 79df7f9ae..79cff450c 100644 --- a/MCGalaxy/Database/PlayerData.cs +++ b/MCGalaxy/Database/PlayerData.cs @@ -125,15 +125,9 @@ namespace MCGalaxy.DB { data.TotalDrawn = cuboided & LowerBitsMask; data.TotalDeleted = cuboided >> LowerBits; return data; - } - + } internal static object Read(IDataRecord record, object arg) { return Parse(record); } - internal static DateTime ParseDate(object value) { - if (value is DateTime) return (DateTime)value; - return DateTime.Parse(value.ToString()); - } - internal static long ParseLong(string value) { return (value.Length == 0 || value.CaselessEq("null")) ? 0 : long.Parse(value); } @@ -142,7 +136,7 @@ namespace MCGalaxy.DB { return (value.Length == 0 || value.CaselessEq("null")) ? 0 : int.Parse(value); } - static string ParseCol(string raw) { + internal static string ParseCol(string raw) { if (raw.Length == 0) return raw; // Try parse color name, then color code @@ -162,16 +156,5 @@ namespace MCGalaxy.DB { public const int LowerBits = 38; public const long LowerBitsMask = (1L << LowerBits) - 1; - - - public static void Update(string name, string column, string value) { - Database.Backend.UpdateRows("Players", column + "=@1", "WHERE Name=@0", name, value); - } - - public static string FindDBColor(Player p) { - string raw = Database.ReadString("Players", "Color", "WHERE ID=@0", p.DatabaseID); - if (raw == null) return ""; - return ParseCol(raw); - } } } diff --git a/MCGalaxy/Economy/Economy.DB.cs b/MCGalaxy/Economy/Economy.DB.cs index dc491f63d..8df2566d4 100644 --- a/MCGalaxy/Economy/Economy.DB.cs +++ b/MCGalaxy/Economy/Economy.DB.cs @@ -58,11 +58,13 @@ namespace MCGalaxy.Eco { } public static string FindMatches(Player p, string name, out int money) { - return PlayerInfo.FindOfflineMoneyMatches(p, name, out money); + string[] match = PlayerDB.MatchValues(p, name, "Name,Money"); + money = match == null ? 0 : int.Parse(match[1]); + return match == null ? null : match[0]; } public static void UpdateMoney(string name, int money) { - PlayerData.Update(name, PlayerData.ColumnMoney, money.ToString()); + PlayerDB.Update(name, PlayerData.ColumnMoney, money.ToString()); } diff --git a/MCGalaxy/Economy/MessageItems.cs b/MCGalaxy/Economy/MessageItems.cs index 683383dd6..27efff182 100644 --- a/MCGalaxy/Economy/MessageItems.cs +++ b/MCGalaxy/Economy/MessageItems.cs @@ -36,15 +36,15 @@ namespace MCGalaxy.Eco { return; } - string text = message.SplitSpaces(2)[1]; // keep spaces this way - if (text == PlayerDB.GetLoginMessage(p)) { + string msg = message.SplitSpaces(2)[1]; // keep spaces this way + if (msg == PlayerDB.GetLoginMessage(p)) { Player.Message(p, "&cYou already have that login message."); return; } - if (text.Length > NetUtils.StringSize) { + if (msg.Length > NetUtils.StringSize) { Player.Message(p, "&cLogin message must be 64 characters or less."); return; } - Command.Find("LoginMessage").Use(p, "-own " + text); - Economy.MakePurchase(p, Price, "%3LoginMessage: %f" + text); + Command.Find("LoginMessage").Use(p, "-own " + msg); + Economy.MakePurchase(p, Price, "%3LoginMessage: %f" + msg); } } @@ -64,15 +64,15 @@ namespace MCGalaxy.Eco { return; } - string text = message.SplitSpaces(2)[1]; // keep spaces this way - if (text == PlayerDB.GetLogoutMessage(p)) { + string msg = message.SplitSpaces(2)[1]; // keep spaces this way + if (msg == PlayerDB.GetLogoutMessage(p)) { Player.Message(p, "&cYou already have that logout message."); return; } - if (text.Length > NetUtils.StringSize) { + if (msg.Length > NetUtils.StringSize) { Player.Message(p, "&cLogin message must be 64 characters or less."); return; } - Command.Find("LogoutMessage").Use(p, "-own " + text); - Economy.MakePurchase(p, Price, "%3LogoutMessage: %f" + text); + Command.Find("LogoutMessage").Use(p, "-own " + msg); + Economy.MakePurchase(p, Price, "%3LogoutMessage: %f" + msg); } } } diff --git a/MCGalaxy/Economy/ZombieItems.cs b/MCGalaxy/Economy/ZombieItems.cs index b1976dfe3..4a1999e61 100644 --- a/MCGalaxy/Economy/ZombieItems.cs +++ b/MCGalaxy/Economy/ZombieItems.cs @@ -109,7 +109,7 @@ namespace MCGalaxy.Eco { if (data.InfectMessages == null) data.InfectMessages = new List(); data.InfectMessages.Add(text); - PlayerDB.AppendInfectMessage(p.name, text); + ZSConfig.AppendPlayerInfectMessage(p.name, text); Player.Message(p, "&aAdded infect message: &f" + text); Economy.MakePurchase(p, Price, "%3InfectMessage: " + message); } diff --git a/MCGalaxy/Games/ZombieSurvival/ZSConfig.cs b/MCGalaxy/Games/ZombieSurvival/ZSConfig.cs index 7b86d9ec9..ea8ddfba9 100644 --- a/MCGalaxy/Games/ZombieSurvival/ZSConfig.cs +++ b/MCGalaxy/Games/ZombieSurvival/ZSConfig.cs @@ -26,23 +26,14 @@ namespace MCGalaxy.Games { public static class ZSConfig { - /// How precise collision detection is between alive and dead players. (Where 1 block = 32 units) [ConfigInt("zombie-hitbox-precision", "Zombie", 32)] public static int HitboxPrecision = 32; - - /// The maximum distance a player is allowed to move between movement packets. [ConfigInt("zombie-maxmove-distance", "Zombie", 50)] public static int MaxMoveDistance = 50; - - /// Whether the server's main level should be set to the current level at the end of each round. [ConfigBool("zombie-survival-only-server", "Zombie", false)] public static bool SetMainLevel; - - /// Whether zombie survival should start upon server startup. [ConfigBool("zombie-on-server-start", "Zombie", false)] public static bool StartImmediately; - - /// Whether the current level name should be shown in the heartbeats sent. [ConfigBool("zombie-map-inheartbeat", "Zombie", false)] public static bool IncludeMapInHeartbeat; @@ -117,5 +108,42 @@ namespace MCGalaxy.Games { Logger.Log(LogType.Warning, "\"{0}\" was not a recognised zombie survival property key.", key); } } + + + static string[] defMessages = new string[] { "{0} WIKIWOO'D {1}", "{0} stuck their teeth into {1}", + "{0} licked {1}'s brain ", "{0} danubed {1}", "{0} made {1} meet their maker", "{0} tripped {1}", + "{0} made some zombie babies with {1}", "{0} made {1} see the dark side", "{0} tweeted {1}", + "{0} made {1} open source", "{0} infected {1}", "{0} iDotted {1}", "{1} got nommed on", + "{0} transplanted {1}'s living brain" }; + + public static List LoadInfectMessages() { + List msgs = new List(); + try { + if (!File.Exists("text/infectmessages.txt")) { + File.WriteAllLines("text/infectmessages.txt", defMessages); + } + msgs = Utils.ReadAllLinesList("text/infectmessages.txt"); + } catch (Exception ex) { + Logger.LogError(ex); + } + + if (msgs.Count == 0) msgs = new List(defMessages); + return msgs; + } + + static string InfectPath(string name) { return "text/infect/" + name.ToLower() + ".txt"; } + public static List LoadPlayerInfectMessages(string name) { + string path = InfectPath(name); + if (!File.Exists(path)) return null; + return Utils.ReadAllLinesList(path); + } + + public static void AppendPlayerInfectMessage(string name, string msg) { + if (!Directory.Exists("text/infect")) + Directory.CreateDirectory("text/infect"); + + string path = InfectPath(name); + File.AppendAllText(path, msg + Environment.NewLine); + } } } diff --git a/MCGalaxy/Games/ZombieSurvival/ZSGame.cs b/MCGalaxy/Games/ZombieSurvival/ZSGame.cs index 0cff81375..ae2eace26 100644 --- a/MCGalaxy/Games/ZombieSurvival/ZSGame.cs +++ b/MCGalaxy/Games/ZombieSurvival/ZSGame.cs @@ -76,7 +76,7 @@ namespace MCGalaxy.Games { public VolatileArray Infected = new VolatileArray(); public string QueuedZombie; public VolatileArray Bounties = new VolatileArray(); - List infectMessages = new List(); + internal List infectMessages = new List(); const string zsExtrasKey = "MCG_ZS_DATA"; internal static ZSData Get(Player p) { @@ -97,7 +97,7 @@ namespace MCGalaxy.Games { } static void InitData(ZSData data, Player p) { - data.InfectMessages = PlayerDB.GetInfectMessages(p); + data.InfectMessages = ZSConfig.LoadPlayerInfectMessages(p.name); ZombieStats stats = LoadStats(p.name); data.MaxInfected = stats.MaxInfected; data.TotalInfected = stats.TotalInfected; data.MaxRoundsSurvived = stats.MaxRounds; data.TotalRoundsSurvived = stats.TotalRounds; @@ -304,26 +304,8 @@ namespace MCGalaxy.Games { else if (winStreak > 0) prefix += "&6" + winStreak + p.color; } - static string[] defMessages = new string[] { "{0} WIKIWOO'D {1}", "{0} stuck their teeth into {1}", - "{0} licked {1}'s brain ", "{0} danubed {1}", "{0} made {1} meet their maker", "{0} tripped {1}", - "{0} made some zombie babies with {1}", "{0} made {1} see the dark side", "{0} tweeted {1}", - "{0} made {1} open source", "{0} infected {1}", "{0} iDotted {1}", "{1} got nommed on", - "{0} transplanted {1}'s living brain" }; - public void LoadInfectMessages() { - infectMessages.Clear(); - try { - if (!File.Exists("text/infectmessages.txt")) - File.WriteAllLines("text/infectmessages.txt", defMessages); - infectMessages = Utils.ReadAllLinesList("text/infectmessages.txt"); - } catch (Exception ex) { - Logger.LogError(ex); - } - if (infectMessages.Count == 0) - infectMessages = new List(defMessages); - } - public bool IsZombieMap(string name) { if (!Running) return false; if (ZSConfig.IgnoredLevelList.CaselessContains(name)) return false; diff --git a/MCGalaxy/Player/List/PlayerList.cs b/MCGalaxy/Player/List/PlayerList.cs index 2602aeb88..9aff50c33 100644 --- a/MCGalaxy/Player/List/PlayerList.cs +++ b/MCGalaxy/Player/List/PlayerList.cs @@ -65,8 +65,8 @@ namespace MCGalaxy { /// Finds matches within this list for the given name. public string FindMatches(Player p, string name, string type, out int matches) { lock (locker) { - return Matcher.Find(p, name, out matches, names, - null, n => n, type, 20); + return Matcher.Find(p, name, out matches, names, + null, n => n, type, 20); } } diff --git a/MCGalaxy/Player/List/PlayerMetaList.cs b/MCGalaxy/Player/List/PlayerMetaList.cs index d40e3d7b2..6261f1cb6 100644 --- a/MCGalaxy/Player/List/PlayerMetaList.cs +++ b/MCGalaxy/Player/List/PlayerMetaList.cs @@ -61,7 +61,7 @@ namespace MCGalaxy { } public List FindMatches(Player p, string name, string group) { - int matches = 0; + int matches; return Matcher.FindMulti(p, name, out matches, AllLines(), null, GetName, group); } diff --git a/MCGalaxy/Player/PlayerInfo.cs b/MCGalaxy/Player/PlayerInfo.cs index ba010a740..9d8eb7149 100644 --- a/MCGalaxy/Player/PlayerInfo.cs +++ b/MCGalaxy/Player/PlayerInfo.cs @@ -46,7 +46,7 @@ namespace MCGalaxy { } public static Player FindMatches(Player pl, string name, bool onlyCanSee = true) { - int matches = 0; return FindMatches(pl, name, out matches, onlyCanSee); + int matches; return FindMatches(pl, name, out matches, onlyCanSee); } public static Player FindMatches(Player pl, string name, @@ -54,20 +54,20 @@ namespace MCGalaxy { matches = 0; if (!Formatter.ValidName(pl, name, "player")) return null; - return Matcher.Find(pl, name, out matches, Online.Items, - p => Entities.CanSee(pl, p) || !onlyCanSee, - p => p.name, "online players"); + return Matcher.Find(pl, name, out matches, Online.Items, + p => Entities.CanSee(pl, p) || !onlyCanSee, + p => p.name, "online players"); } public static string FindMatchesPreferOnline(Player p, string name) { if (!Formatter.ValidName(p, name, "player")) return null; - int matches = 0; + int matches; Player target = FindMatches(p, name, out matches); if (matches > 1) return null; if (target != null) return target.name; Player.Message(p, "Searching PlayerDB for \"{0}\"..", name); - return FindOfflineNameMatches(p, name); + return PlayerDB.MatchNames(p, name); } /// Finds the online player whose name caselessly exactly matches the given name. @@ -100,50 +100,12 @@ namespace MCGalaxy { return Database.ReadString("Players", "IP", "WHERE Name=@0" + suffix, name); } - - static object ReadStats(IDataRecord record, object arg) { - PlayerData stats = PlayerData.Parse(record); - ((List)arg).Add(stats); return arg; - } - - public static PlayerData FindOfflineMatches(Player p, string name) { - List stats = new List(); - MatchMulti("Players", "*", stats, Database.ReadList); - - int matches = 0; - return Matcher.Find(p, name, out matches, stats, - null, stat => stat.Name, "players", 20); - } - - public static string FindOfflineNameMatches(Player p, string name) { - List names = new List(); - MatchMulti("Players", "Name", names, Database.ReadList); - - int matches = 0; - return Matcher.Find(p, name, out matches, names, - null, n => n, "players", 20); - } - - static string[] MatchValues(Player p, string name, string columns) { - List name_values = new List(); - MatchMulti("Players", columns, name_values, Database.ReadFields); - - int matches = 0; - return Matcher.Find(p, name, out matches, name_values, - null, n => n[0], "players", 20); - } - public static string FindOfflineIPMatches(Player p, string name, out string ip) { - string[] match = MatchValues(p, name, "Name,IP"); + string[] match = PlayerDB.MatchValues(p, name, "Name,IP"); ip = match == null ? null : match[1]; return match == null ? null : match[0]; } - public static string FindOfflineMoneyMatches(Player p, string name, out int money) { - string[] match = MatchValues(p, name, "Name,Money"); - money = match == null ? 0 : int.Parse(match[1]); - return match == null ? null : match[0]; - } static object ReadAccounts(IDataRecord record, object arg) { List names = (List)arg; @@ -168,12 +130,5 @@ namespace MCGalaxy { } return names; } - - static void MatchMulti(string name, string columns, object arg, ReaderCallback callback) { - string suffix = Database.Backend.CaselessLikeSuffix; - Database.Backend.ReadRows("Players", columns, arg, callback, - "WHERE Name LIKE @0 ESCAPE '#' LIMIT 21" + suffix, - "%" + name.Replace("_", "#_") + "%"); - } } } diff --git a/MCGalaxy/Server/Server.cs b/MCGalaxy/Server/Server.cs index 97d1392e2..43e9a0fa6 100644 --- a/MCGalaxy/Server/Server.cs +++ b/MCGalaxy/Server/Server.cs @@ -190,7 +190,7 @@ namespace MCGalaxy { plugin.Unload(false); } - zombie.LoadInfectMessages(); + zombie.infectMessages = ZSConfig.LoadInfectMessages(); Colors.LoadList(); Alias.Load(); BlockDefinition.LoadGlobal(); diff --git a/MCGalaxy/util/Formatting/Matcher.cs b/MCGalaxy/util/Formatting/Matcher.cs index 736fc77b0..0275826fd 100644 --- a/MCGalaxy/util/Formatting/Matcher.cs +++ b/MCGalaxy/util/Formatting/Matcher.cs @@ -30,74 +30,69 @@ namespace MCGalaxy { /// Finds partial matches of 'name' against the list of all awards. public static string FindAwards(Player p, string name) { - int matches = 0; - Awards.Award award = Find(p, name, out matches, Awards.AwardsList, - null, a => a.Name, "awards"); + int matches; + Awards.Award award = Find(p, name, out matches, Awards.AwardsList, + null, a => a.Name, "awards"); return award == null ? null : award.Name; } /// Finds partial matches of 'color' against the list of colors. public static string FindColor(Player p, string color) { - int matches = 0; - ColorDesc desc = Find(p, color, out matches, Colors.List, - col => !col.Undefined, col => col.Name, "colors", 20); + int matches; + ColorDesc desc = Find(p, color, out matches, Colors.List, + col => !col.Undefined, col => col.Name, "colors", 20); return desc.Undefined ? null : "&" + desc.Code; } /// Finds partial matches of 'name' against the list of bots in same level as player. public static PlayerBot FindBots(Player p, string name) { - int matches = 0; - return Find(p, name, out matches, p.level.Bots.Items, - b => b.level == p.level, b => b.name, "bots"); + int matches; + return Find(p, name, out matches, p.level.Bots.Items, + null, b => b.name, "bots"); } /// Find partial matches of 'name' against the list of loaded maps/levels. public static Level FindLevels(Player p, string name) { - int matches = 0; - return Find(p, name, out matches, LevelInfo.Loaded.Items, - null, l => l.name, "loaded levels"); + int matches; + return Find(p, name, out matches, LevelInfo.Loaded.Items, + null, l => l.name, "loaded levels"); } /// Find partial matches of 'name' against the list of all map files. public static string FindMaps(Player pl, string name) { - int matches = 0; - if (!Formatter.ValidName(pl, name, "level")) return null; - - string[] files = LevelInfo.AllMapFiles(); - string map = Find(pl, name, out matches, files, - null, l => Path.GetFileNameWithoutExtension(l), "levels", 10); - - if (map != null) map = Path.GetFileNameWithoutExtension(map); - return map; + if (!Formatter.ValidName(pl, name, "level")) return null; + int matches; + return Find(pl, name, out matches, LevelInfo.AllMapNames(), + null, l => l, "levels", 10); } /// Find partial matches of 'name' against the list of ranks. public static Group FindRanks(Player p, string name) { Group.MapName(ref name); - int matches = 0; - return Find(p, name, out matches, Group.GroupList, - null, g => Colors.Strip(g.Name), "ranks"); + int matches; + return Find(p, name, out matches, Group.GroupList, + null, g => Colors.Strip(g.Name), "ranks"); } /// Find partial matches of 'name' against a list of warps. public static Warp FindWarps(Player p, WarpList warps, string name) { string group = (warps == WarpList.Global) ? "warps" : "waypoints"; int matches; - return Find(p, name, out matches, warps.Items, - null, wp => wp.Name, group); + return Find(p, name, out matches, warps.Items, + null, wp => wp.Name, group); } /// Find partial matches of 'name' against the list of zones in a map. public static Zone FindZones(Player p, Level lvl, string name) { - int matches = 0; - return Find(p, name, out matches, lvl.Zones.Items, - null, z => z.Config.Name, "zones"); + int matches; + return Find(p, name, out matches, lvl.Zones.Items, + null, z => z.Config.Name, "zones"); } /// Finds partial matches of 'name' against the names of the items in the 'items' enumerable. /// If exactly one match, the matching item. - public static T Find(Player p, string name, out int matches, IEnumerable items, + public static T Find(Player p, string name, out int matches, IEnumerable items, Predicate filter, StringFormatter nameGetter, string group, int limit = 5) { T match = default(T); matches = 0; StringBuilder nameMatches = new StringBuilder(); diff --git a/MCGalaxy/util/Utils.cs b/MCGalaxy/util/Utils.cs index e8f179109..f26e993c8 100644 --- a/MCGalaxy/util/Utils.cs +++ b/MCGalaxy/util/Utils.cs @@ -86,9 +86,7 @@ namespace MCGalaxy { List lines = new List(); using (StreamReader r = new StreamReader(path)) { string item; - while ((item = r.ReadLine()) != null) { - lines.Add(item); - } + while ((item = r.ReadLine()) != null) { lines.Add(item); } } return lines; }