using Newtonsoft.Json; using Oxide.Core.Plugins; using ProtoBuf; using System; using System.Collections.Generic; namespace Oxide.Plugins { [Info("Arkan AutoBan", "Miho", "1.0.0")] [Description("Autobans players for Arkan violations")] class ArkanAutoBan : RustPlugin { #region Fields static double GrabCurrentTime() => DateTime.UtcNow.Subtract(new DateTime(1970, 1, 1, 0, 0, 0)).TotalSeconds; #endregion #region Configuration private ConfigData config; private class ConfigData { [JsonProperty(PropertyName = "No Recoil Violation")] public ViolationSetting norecoilviolation; [JsonProperty(PropertyName = "Aimbot Violation")] public ViolationSetting aimbotviolation; [JsonProperty(PropertyName = "In Rock Violation")] public ViolationSetting inrockviolation; [JsonProperty(PropertyName = "Is logging enabled?")] public bool logenabled; [JsonProperty(PropertyName = "Version")] public string version; } private class ViolationSetting { [JsonProperty(PropertyName = "AutoBan Enabled")] public bool autobanenabled; [JsonProperty(PropertyName = "Violation Threshold")] public uint threshold; [JsonProperty(PropertyName = "Ban - True, Timed Ban - False")] public bool banortimedban; [JsonProperty(PropertyName = "Timed Ban Duration(in seconds) - If TimedBan")] public uint duration; } private ConfigData GetDefaultConfig() { return new ConfigData { norecoilviolation = new ViolationSetting { autobanenabled = true, threshold = 5, banortimedban = true, duration = 86400 }, aimbotviolation = new ViolationSetting { autobanenabled = true, threshold = 3, banortimedban = true, duration = 86400 }, inrockviolation = new ViolationSetting { autobanenabled = true, threshold = 2, banortimedban = true, duration = 86400 }, logenabled = true, version = "1.0.0" }; } protected override void LoadConfig() { base.LoadConfig(); try { config = Config.ReadObject(); if (config == null) { LoadDefaultConfig(); } } catch { LoadDefaultConfig(); } SaveConfig(); } protected override void LoadDefaultConfig() { PrintWarning("Configuration file is corrupt(or not exists), creating new one!"); config = GetDefaultConfig(); } protected override void SaveConfig() { Config.WriteObject(config); } #endregion #region ArkanHooks private void API_ArkanOnNoRecoilViolation(BasePlayer player, int NRViolationsNum, string json) { HandleViolation(player, NRViolationsNum, config.norecoilviolation, player.displayName, "No Recoil Violation"); } private void API_ArkanOnAimbotViolation(BasePlayer player, int AIMViolationsNum, string json) { HandleViolation(player, AIMViolationsNum, config.aimbotviolation, player.displayName, "Aimbot Violation"); } private void API_ArkanOnInRockViolation(BasePlayer player, int IRViolationsNum, string json) { HandleViolation(player, IRViolationsNum, config.inrockviolation, player.displayName, "In Rock Violation"); } #endregion #region Methods private void BanPlayer(BasePlayer player, string displayName, string reason) { if (player.IsConnected) player.Kick(lang.GetMessage("BanReason", this, player.UserIDString)); ServerUsers.Set(player.userID, ServerUsers.UserGroup.Banned, displayName, reason); ServerUsers.Save(); Server.Broadcast(string.Format(lang.GetMessage("Ban", this, player.UserIDString), displayName)); } private void TimedBanPlayer(BasePlayer player, string displayName, uint durationInSeconds, string reason) { if (player.IsConnected) player.Kick(string.Format(lang.GetMessage("TimedBanReason", this, player.UserIDString), durationInSeconds)); ServerUsers.Set(player.userID, ServerUsers.UserGroup.Banned, displayName, reason, (long)GrabCurrentTime() + durationInSeconds); ServerUsers.Save(); Server.Broadcast(string.Format(lang.GetMessage("TimedBan", this, player.UserIDString), displayName, durationInSeconds)); } private void HandleViolation(BasePlayer player, int violationsNum, ViolationSetting settings, string displayName, string violationType) { if (violationsNum >= settings.threshold && settings.autobanenabled) { string reason = $"Violation of {violationType}"; if (settings.banortimedban) { BanPlayer(player, displayName, reason); BanLog(displayName, violationsNum, reason, false); } else { TimedBanPlayer(player, displayName, settings.duration, reason); BanLog(displayName, violationsNum, reason, true, settings.duration); } } } #endregion #region Log private void BanLog(string playerName, int violationsNum, string reason, bool isTimedBan, uint durationInSeconds = 0) { string filename = isTimedBan ? "TimedBanLog" : "BanLog"; string durationInfo = isTimedBan ? $", Duration: {durationInSeconds} seconds" : ""; Log(filename, $"Player: {playerName}, Violations: {violationsNum}, Reason: {reason}{durationInfo}"); } private void Log(string filename, string key) { LogToFile(filename, $"[{DateTime.Now}] {key}", this); } #endregion #region Localization protected override void LoadDefaultMessages() { lang.RegisterMessages(new Dictionary { {"Ban", "{0} has been banned by Arkan AutoBan"}, {"TimedBan", "{0} has been timed banned for {1}seconds by Arkan AutoBan"}, {"BanReason", "You have been banned by Arkan AutoBan"}, {"TimedBanReason", "You have been timed banned for {0}seconds by Arkan AutoBan"} }, this); } #endregion } }