public void SetScore(string nick, string channel, int?removals = null, int?deports = null, int?helicopters = null, bool createIfNotExists = true) { CuckHuntConfigModel.CuckConfig.CuckStat nickStats = GetCuckStat(nick, channel); bool existing = true; if (nickStats == null) { if (createIfNotExists) { existing = false; nickStats = new CuckHuntConfigModel.CuckConfig.CuckStat { Channel = channel, Nick = nick, GetEmOutCount = 0, KilledCount = 0, HelicopterCount = 0 }; } else { return; } } if (removals != null) { nickStats.GetEmOutCount = (int)removals; } if (deports != null) { nickStats.KilledCount = (int)deports; } if (helicopters != null) { nickStats.HelicopterCount = (int)helicopters; } if (existing) { _config.Stats.Remove(GetCuckStat(nick, channel)); } _config.Stats.Add(nickStats); SaveConfig(); }
public void RunCommand(IrcClient client, GroupCollection values, IrcEventArgs eventArgs, IrcBot ircBot) { string operation = values[1].Value.ToLower(); _log.Info($"Got operation: {operation}"); if (operation == "spawn") { if (values.Count > 2) { string channel = values[2].Value; _log.Info($"Spawning cuck in {channel}"); if (!ircBot.CuckHunt.IsCuckPresent(channel)) { ircBot.CuckHunt.CreateCuck(channel, manuallyCreated: true); ircBot.CuckHunt.LastAdminWhoSpawnedCuck = eventArgs.Data.Nick.GetNick(); client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Spawned cuck in {channel}"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Cuck is already present in {channel}"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Second parameter required"); } else if (operation == "list") { List <CuckHunt.Cuck> cucks = ircBot.CuckHunt.GetCucks(); _log.Info($"Got {cucks}"); client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"{cucks.Count} cuck(s) present"); foreach (CuckHunt.Cuck cuck in cucks) { client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Cuck in {cuck.Channel}, appeared at: {cuck.Appeared.ToLongTimeString()}"); } } else if (operation == "destroy") { if (values.Count > 2) { string channel = values[2].Value; _log.Info($"Destroying cuck in {channel}"); if (ircBot.CuckHunt.IsCuckPresent(channel)) { ircBot.CuckHunt.RemoveCuck(channel); client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Destroyed cuck in {channel}"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Cuck not present in {channel}"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Second parameter required"); } else if (operation == "start_hunt") { if (values.Count > 2) { string channel = values[2].Value; if (channel[0] != '#') { client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Second parameter must start with #"); return; } if (ircBot.CuckHunt.IsCuckHuntActive(channel)) { client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"The hunt is already active in {channel}"); return; } ircBot.CuckHunt.StartHunt(channel); client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Enabled hunt in {channel}"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Second parameter required"); } else if (operation == "stop_hunt") { if (values.Count > 2) { string channel = values[2].Value; if (channel[0] != '#') { client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Second parameter must start with #"); return; } if (!ircBot.CuckHunt.IsCuckHuntActive(channel)) { client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Hunt is already inactive in {channel}"); return; } ircBot.CuckHunt.DestroyThread(channel); client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Hunt is now disabled in {channel}"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Second parameter required"); } else if (operation == "ignore") { if (values.Count > 2) { string nick = values[2].Value; ircBot.CuckHunt.Ignore(nick); client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Successfully ignoring {nick}. Currently ignoring: {string.Join(", ", ircBot.CuckHunt.GetIgnoreList())}"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Second parameter required"); } else if (operation == "unignore") { if (values.Count > 2) { string nick = values[2].Value; ircBot.CuckHunt.UnIgnore(nick); client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Successfully unignored {nick}. Currently ignoring: {string.Join(", ", ircBot.CuckHunt.GetIgnoreList())}"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Second parameter required"); } else if (operation == "ignore_list" || operation == "ignorelist") { client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Currently ignored nicks: {string.Join(", ", ircBot.CuckHunt.GetIgnoreList())}"); } else if (operation == "rehash" || operation == "reload") { ircBot.CuckHunt.ReloadConfig(); client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Successfully rehashed the cuckhunt configuration"); } else if (operation == "help") { List <string> responses = new List <string> { "The following commands are available: ", "spawn <channel> -- Spawns a cuck in the given channel", "list -- Gives a list of all cucks that are currently active", "destroy <channel> -- Destroys a cuck in the channel", "start_hunt <channel> -- Begins a hunt in a channel (spawns thread, begins hunt, use 'spawn' command if you need a cuck present immediately after enabling. Does not save to config, will be lost on bot restart!)", "stop_hunt <channel> -- Stops an active hunt in a channel (destroys thread, does not save to config, hunt will restart if in 'Channels' property on config)", "ignore <nick> -- Ignore a nickname when it attempts to !getout or !deport", "unignore <nick> -- Remove a nickname from the ignore list", "ignore_list | ignorelist -- Get a list of all ignored nicks", "merge_stats | merge_stats_ignore_missing_new_user <channel> <old> <new> -- Move old user's scores to new user (resets old user's scores to 0)", "stats <channel> <user> -- Display user's stats", "help -- Display this text" }; foreach (string response in responses) { client.SendMessage(SendType.Message, eventArgs.Data.Channel, response); } } else if (operation == "merge_scores" || operation == "mergescores" || operation == "merge_scores_ignore_missing_new_user" || operation == "merge_stats" || operation == "merge_stats_ignore_missing_new_user") { if (values.Count > 4) { bool ignoreMissingNewUser = operation == "merge_scores_ignore_missing_new_user" || operation == "merge_stats_ignore_missing_new_user"; string channel = values[2].Value; string oldUser = values[3].Value; string newUser = values[4].Value; CuckHuntConfigModel.CuckConfig.CuckStat oldUserStats = ircBot.CuckHunt.GetCuckStat(oldUser, channel); CuckHuntConfigModel.CuckConfig.CuckStat newUserStats = ircBot.CuckHunt.GetCuckStat(newUser, channel); if (oldUserStats == null) { client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Old user not found"); return; } if (newUserStats == null && !ignoreMissingNewUser) { client.SendMessage(SendType.Message, eventArgs.Data.Channel, "New user not found, change operation to 'merge_stats_ignore_missing_new_user' to bypass this check"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"Old user's stats: Channel={oldUserStats.Channel}; Nick={oldUserStats.Nick}; GetEmOutCount={oldUserStats.GetEmOutCount}; KilledCount={oldUserStats.KilledCount}; HelicopterCount={oldUserStats.HelicopterCount}"); if (newUserStats != null) { client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"New user's stats: Channel={newUserStats.Channel}; Nick={newUserStats.Nick}; GetEmOutCount={newUserStats.GetEmOutCount}; KilledCount={newUserStats.KilledCount}; HelicopterCount={newUserStats.HelicopterCount}"); ircBot.CuckHunt.SetScore(newUser, channel, oldUserStats.GetEmOutCount + newUserStats.GetEmOutCount, oldUserStats.KilledCount + newUserStats.KilledCount, oldUserStats.HelicopterCount + newUserStats.HelicopterCount, createIfNotExists: true); } else { client.SendMessage(SendType.Message, eventArgs.Data.Channel, "New user is null, will be created when scores are set."); ircBot.CuckHunt.SetScore(newUser, channel, oldUserStats.GetEmOutCount, oldUserStats.KilledCount, oldUserStats.HelicopterCount, createIfNotExists: true); } ircBot.CuckHunt.SetScore(oldUser, channel, 0, 0, 0); client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Stats merged and saved"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Not enough arguments"); } else if (operation == "stats" || operation == "get_stats") { if (values.Count > 3) { string channel = values[2].Value; string nick = values[3].Value; CuckHuntConfigModel.CuckConfig.CuckStat stats = ircBot.CuckHunt.GetCuckStat(nick, channel); if (stats == null) { client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Could not find the user"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, $"User's stats: Channel={stats.Channel}; Nick={stats.Nick}; GetEmOutCount={stats.GetEmOutCount}; KilledCount={stats.KilledCount}; HelicopterCount={stats.HelicopterCount}"); return; } client.SendMessage(SendType.Message, eventArgs.Data.Channel, "Not enough arguments"); } }
public void ProcessMessage(object sender, IrcEventArgs eventArgs) { if (eventArgs.Data.Message == null) { return; } string nick = eventArgs.Data.From.Split('!')[0]; string channel = eventArgs.Data.Channel; if (eventArgs.Data.Message[0] == CommandPrefix && !_config.IgnoreList.Contains(nick)) { string message = eventArgs.Data.Message.TrimStart(CommandPrefix); if (message.ToLower().StartsWith("cucks")) // Not ToLowering before this because case does matter for looking up user stats { List <string> args = message.Split(' ').ToList(); if (args.Count > 1) { string requestedNick = args[1]; CuckHuntConfigModel.CuckConfig.CuckStat stat = GetCuckStat(requestedNick, channel); if (stat == null) { _client.SendMessage(SendType.Message, channel, $"Requested nick '{requestedNick}' has no stats."); } else { _client.SendMessage(SendType.Message, channel, $"{stat.GetEmOutCount} cucks removed, {stat.KilledCount} cucks deported and {stat.HelicopterCount} taken for a helicopter ride by {stat.Nick}"); } } else { string getOutMessage = "Cucks Removed:"; List <CuckHuntConfigModel.CuckConfig.CuckStat> channelStats = (from stat in _config.Stats where stat.Channel == channel select stat).ToList(); channelStats.Sort((x, y) => y.GetEmOutCount.CompareTo(x.GetEmOutCount)); int i = 0; foreach (CuckHuntConfigModel.CuckConfig.CuckStat stat in channelStats) { if (i == 10) { break; } getOutMessage += $" {stat.Nick.Insert(stat.Nick.Length / 2, "\u2063").Insert(1, "\u2063")}: {stat.GetEmOutCount};"; i++; } i = 0; string deportedMessage = "Cucks Deported:"; channelStats.Sort((x, y) => y.KilledCount.CompareTo(x.KilledCount)); foreach (CuckHuntConfigModel.CuckConfig.CuckStat stat in channelStats) { if (i == 10) { break; } deportedMessage += $" {stat.Nick.Insert(stat.Nick.Length / 2, "\u2063").Insert(1, "\u2063")}: {stat.KilledCount};"; i++; } i = 0; string helicopterMessage = "Cucks Helicopter'd:"; channelStats.Sort((x, y) => y.HelicopterCount.CompareTo(x.HelicopterCount)); foreach (CuckHuntConfigModel.CuckConfig.CuckStat stat in channelStats) { if (i == 10) { break; } helicopterMessage += $" {stat.Nick.Insert(stat.Nick.Length / 2, "\u2063").Insert(1, "\u2063")}: {stat.HelicopterCount};"; i++; } _client.SendMessage(SendType.Message, channel, getOutMessage); _client.SendMessage(SendType.Message, channel, deportedMessage); _client.SendMessage(SendType.Message, channel, helicopterMessage); } } message = message.ToLower(); // Case doesn't matter at this point if (message.StartsWith("deport") || message.StartsWith("getout") || message.StartsWith("helicopter")) { bool kill = message.StartsWith("deport"); bool helicopter = message.StartsWith("helicopter"); Cuck currentCuck = GetCuck(channel); if (currentCuck == null && !_config.CuckPresentExempt.Contains(nick)) { if (_lastDeportedCuck == null) { _client.SendMessage(SendType.Message, channel, "What? There are no cucks around!"); } else { _client.SendMessage(SendType.Message, channel, $"What? There are no cucks around! A cuck was last removed {(DateTimeOffset.UtcNow - _lastDeportedCuck).Value.TotalSeconds} seconds ago"); } return; } TimeSpan timeElapsed; if (currentCuck != null) { timeElapsed = DateTime.Now - currentCuck.Appeared; RemoveCuck(channel); } else if (_config.CuckPresentExempt.Contains(nick)) { timeElapsed = new TimeSpan(1); } else { _backtraceClient.Attributes.Add("Nick", nick); _backtraceClient.Send("currentCuck was null, user was not cuck exempt yet somehow we got this far."); throw new Exception("currentCuck was null, user was not cuck exempt yet somehow we got this far."); } ReloadConfig(); CuckHuntConfigModel.CuckConfig.CuckStat cuckStat = GetCuckStat(nick, channel) ?? new CuckHuntConfigModel.CuckConfig.CuckStat { Channel = channel, GetEmOutCount = 0, KilledCount = 0, Nick = nick, HelicopterCount = 0 }; if (kill) { SetScore(nick, channel, null, cuckStat.KilledCount + 1, createIfNotExists: true); cuckStat = GetCuckStat(nick, channel); if (_config.AssumeMaleGender) { _client.SendMessage(SendType.Message, channel, $"{nick} deported the cuck in {(int)timeElapsed.TotalSeconds}.{timeElapsed.Milliseconds} seconds! He has deported {cuckStat.KilledCount} cucks within {cuckStat.Channel}"); } else { _client.SendMessage(SendType.Message, channel, $"{nick} deported the cuck in {(int)timeElapsed.TotalSeconds}.{timeElapsed.Milliseconds} seconds! They have deported {cuckStat.KilledCount} cucks within {cuckStat.Channel}"); } } else if (helicopter) { SetScore(nick, channel, null, helicopters: cuckStat.HelicopterCount + 1, createIfNotExists: true); cuckStat = GetCuckStat(nick, channel); if (_config.AssumeMaleGender) { _client.SendMessage(SendType.Message, channel, $"{nick} took the cuck for a helicopter ride in {(int)timeElapsed.TotalSeconds}.{timeElapsed.Milliseconds} seconds! He has helicopter'd {cuckStat.HelicopterCount} cucks within {cuckStat.Channel}"); } else { _client.SendMessage(SendType.Message, channel, $"{nick} took the cuck for a helicopter ride in {(int)timeElapsed.TotalSeconds}.{timeElapsed.Milliseconds} seconds! They have helicopter'd {cuckStat.HelicopterCount} cucks within {cuckStat.Channel}"); } } else { SetScore(nick, channel, cuckStat.GetEmOutCount + 1, createIfNotExists: true); cuckStat = GetCuckStat(nick, channel); if (_config.AssumeMaleGender) { _client.SendMessage(SendType.Message, channel, $"{nick} got rid of the cuck in {(int)timeElapsed.TotalSeconds}.{timeElapsed.Milliseconds} seconds! He has gotten rid of {cuckStat.GetEmOutCount} cucks within {cuckStat.Channel}"); } else { _client.SendMessage(SendType.Message, channel, $"{nick} got rid of the cuck in {(int)timeElapsed.TotalSeconds}.{timeElapsed.Milliseconds} seconds! They have gotten rid of {cuckStat.GetEmOutCount} cucks within {cuckStat.Channel}"); } } if (_config.PunishAdmins) { if (LastAdminWhoSpawnedCuck == nick) { _client.SendMessage(SendType.Message, channel, $"{nick} is cheating scum, 10 points will be removed from his scores."); SetScore(nick, channel, cuckStat.GetEmOutCount - 10, cuckStat.KilledCount - 10, cuckStat.HelicopterCount - 10); } LastAdminWhoSpawnedCuck = string.Empty; } _log.Info($"{nick} removed a cuck in {timeElapsed.TotalMilliseconds} ms ({(int)timeElapsed.TotalSeconds}s) kill={kill}, helicopter={helicopter}. cuckStat.KilledCount={cuckStat.KilledCount}, cuckStat.HelicopterCount={cuckStat.HelicopterCount}, cuckStat.GetEmOutCount={cuckStat.GetEmOutCount}"); if (currentCuck != null) { if (!currentCuck.ManuallyCreated) { CreateThread(channel); } } // Early return is necessary so cuckhunt commands don't count as "channel activity" // tfw I f****d it up and the activity feature never worked return; } } if (LastActivity.ContainsKey(channel)) { LastActivity[channel].LastMessage = DateTime.Now; } else { LastActivity.Add(channel, new ActivityTime { LastCuckSpawn = DateTime.MinValue, LastMessage = DateTime.Now }); } }