.antiraid .antispam .antilist .antispamignore added/improved
This commit is contained in:
		@@ -17,6 +17,62 @@ namespace NadekoBot.Migrations
 | 
			
		||||
            modelBuilder
 | 
			
		||||
                .HasAnnotation("ProductVersion", "1.1.0-rtm-22752");
 | 
			
		||||
 | 
			
		||||
            modelBuilder.Entity("NadekoBot.Services.Database.Models.AntiRaidSetting", b =>
 | 
			
		||||
                {
 | 
			
		||||
                    b.Property<int>("Id")
 | 
			
		||||
                        .ValueGeneratedOnAdd();
 | 
			
		||||
 | 
			
		||||
                    b.Property<int>("Action");
 | 
			
		||||
 | 
			
		||||
                    b.Property<int>("GuildConfigId");
 | 
			
		||||
 | 
			
		||||
                    b.Property<int>("Seconds");
 | 
			
		||||
 | 
			
		||||
                    b.Property<int>("UserThreshold");
 | 
			
		||||
 | 
			
		||||
                    b.HasKey("Id");
 | 
			
		||||
 | 
			
		||||
                    b.HasIndex("GuildConfigId")
 | 
			
		||||
                        .IsUnique();
 | 
			
		||||
 | 
			
		||||
                    b.ToTable("AntiRaidSetting");
 | 
			
		||||
                });
 | 
			
		||||
 | 
			
		||||
            modelBuilder.Entity("NadekoBot.Services.Database.Models.AntiSpamIgnore", b =>
 | 
			
		||||
                {
 | 
			
		||||
                    b.Property<int>("Id")
 | 
			
		||||
                        .ValueGeneratedOnAdd();
 | 
			
		||||
 | 
			
		||||
                    b.Property<int?>("AntiSpamSettingId");
 | 
			
		||||
 | 
			
		||||
                    b.Property<ulong>("ChannelId");
 | 
			
		||||
 | 
			
		||||
                    b.HasKey("Id");
 | 
			
		||||
 | 
			
		||||
                    b.HasIndex("AntiSpamSettingId");
 | 
			
		||||
 | 
			
		||||
                    b.ToTable("AntiSpamIgnore");
 | 
			
		||||
                });
 | 
			
		||||
 | 
			
		||||
            modelBuilder.Entity("NadekoBot.Services.Database.Models.AntiSpamSetting", b =>
 | 
			
		||||
                {
 | 
			
		||||
                    b.Property<int>("Id")
 | 
			
		||||
                        .ValueGeneratedOnAdd();
 | 
			
		||||
 | 
			
		||||
                    b.Property<int>("Action");
 | 
			
		||||
 | 
			
		||||
                    b.Property<int>("GuildConfigId");
 | 
			
		||||
 | 
			
		||||
                    b.Property<int>("MessageThreshold");
 | 
			
		||||
 | 
			
		||||
                    b.HasKey("Id");
 | 
			
		||||
 | 
			
		||||
                    b.HasIndex("GuildConfigId")
 | 
			
		||||
                        .IsUnique();
 | 
			
		||||
 | 
			
		||||
                    b.ToTable("AntiSpamSetting");
 | 
			
		||||
                });
 | 
			
		||||
 | 
			
		||||
            modelBuilder.Entity("NadekoBot.Services.Database.Models.BlacklistItem", b =>
 | 
			
		||||
                {
 | 
			
		||||
                    b.Property<int>("Id")
 | 
			
		||||
@@ -722,6 +778,29 @@ namespace NadekoBot.Migrations
 | 
			
		||||
                    b.ToTable("PokeGame");
 | 
			
		||||
                });
 | 
			
		||||
 | 
			
		||||
            modelBuilder.Entity("NadekoBot.Services.Database.Models.AntiRaidSetting", b =>
 | 
			
		||||
                {
 | 
			
		||||
                    b.HasOne("NadekoBot.Services.Database.Models.GuildConfig", "GuildConfig")
 | 
			
		||||
                        .WithOne("AntiRaidSetting")
 | 
			
		||||
                        .HasForeignKey("NadekoBot.Services.Database.Models.AntiRaidSetting", "GuildConfigId")
 | 
			
		||||
                        .OnDelete(DeleteBehavior.Cascade);
 | 
			
		||||
                });
 | 
			
		||||
 | 
			
		||||
            modelBuilder.Entity("NadekoBot.Services.Database.Models.AntiSpamIgnore", b =>
 | 
			
		||||
                {
 | 
			
		||||
                    b.HasOne("NadekoBot.Services.Database.Models.AntiSpamSetting")
 | 
			
		||||
                        .WithMany("IgnoredChannels")
 | 
			
		||||
                        .HasForeignKey("AntiSpamSettingId");
 | 
			
		||||
                });
 | 
			
		||||
 | 
			
		||||
            modelBuilder.Entity("NadekoBot.Services.Database.Models.AntiSpamSetting", b =>
 | 
			
		||||
                {
 | 
			
		||||
                    b.HasOne("NadekoBot.Services.Database.Models.GuildConfig", "GuildConfig")
 | 
			
		||||
                        .WithOne("AntiSpamSetting")
 | 
			
		||||
                        .HasForeignKey("NadekoBot.Services.Database.Models.AntiSpamSetting", "GuildConfigId")
 | 
			
		||||
                        .OnDelete(DeleteBehavior.Cascade);
 | 
			
		||||
                });
 | 
			
		||||
 | 
			
		||||
            modelBuilder.Entity("NadekoBot.Services.Database.Models.BlacklistItem", b =>
 | 
			
		||||
                {
 | 
			
		||||
                    b.HasOne("NadekoBot.Services.Database.Models.BotConfig")
 | 
			
		||||
 
 | 
			
		||||
@@ -1,272 +0,0 @@
 | 
			
		||||
using Discord;
 | 
			
		||||
using Discord.Commands;
 | 
			
		||||
using NadekoBot.Attributes;
 | 
			
		||||
using NadekoBot.Extensions;
 | 
			
		||||
using NLog;
 | 
			
		||||
using System;
 | 
			
		||||
using System.Collections.Concurrent;
 | 
			
		||||
using System.Linq;
 | 
			
		||||
using System.Threading.Tasks;
 | 
			
		||||
 | 
			
		||||
namespace NadekoBot.Modules.Administration
 | 
			
		||||
{
 | 
			
		||||
    public partial class Administration
 | 
			
		||||
    {
 | 
			
		||||
        public enum PunishmentAction
 | 
			
		||||
        {
 | 
			
		||||
            Mute,
 | 
			
		||||
            Kick,
 | 
			
		||||
            Ban,
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        public enum ProtectionType
 | 
			
		||||
        {
 | 
			
		||||
            Raiding,
 | 
			
		||||
            Spamming,
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        private class AntiRaidSetting
 | 
			
		||||
        {
 | 
			
		||||
            public int UserThreshold { get; set; }
 | 
			
		||||
            public int Seconds { get; set; }
 | 
			
		||||
            public PunishmentAction Action { get; set; }
 | 
			
		||||
            public int UsersCount { get; set; }
 | 
			
		||||
            public ConcurrentHashSet<IGuildUser> RaidUsers { get; set; } = new ConcurrentHashSet<IGuildUser>();
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        private class AntiSpamSetting
 | 
			
		||||
        {
 | 
			
		||||
            public PunishmentAction Action { get; set; }
 | 
			
		||||
            public int MessageThreshold { get; set; } = 3;
 | 
			
		||||
            public ConcurrentDictionary<ulong, UserSpamStats> UserStats { get; set; }
 | 
			
		||||
                = new ConcurrentDictionary<ulong, UserSpamStats>();
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        private class UserSpamStats
 | 
			
		||||
        {
 | 
			
		||||
            public int Count { get; set; }
 | 
			
		||||
            public string LastMessage { get; set; }
 | 
			
		||||
 | 
			
		||||
            public UserSpamStats(string msg)
 | 
			
		||||
            {
 | 
			
		||||
                Count = 1;
 | 
			
		||||
                LastMessage = msg.ToUpperInvariant();
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            public void ApplyNextMessage(string message)
 | 
			
		||||
            {
 | 
			
		||||
                var upperMsg = message.ToUpperInvariant();
 | 
			
		||||
                if (upperMsg == LastMessage)
 | 
			
		||||
                    Count++;
 | 
			
		||||
                else
 | 
			
		||||
                {
 | 
			
		||||
                    LastMessage = upperMsg;
 | 
			
		||||
                    Count = 0;
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        [Group]
 | 
			
		||||
        public class AntiRaidCommands : ModuleBase
 | 
			
		||||
        {
 | 
			
		||||
            private static ConcurrentDictionary<ulong, AntiRaidSetting> antiRaidGuilds =
 | 
			
		||||
                    new ConcurrentDictionary<ulong, AntiRaidSetting>();
 | 
			
		||||
            // guildId | (userId|messages)
 | 
			
		||||
            private static ConcurrentDictionary<ulong, AntiSpamSetting> antiSpamGuilds =
 | 
			
		||||
                    new ConcurrentDictionary<ulong, AntiSpamSetting>();
 | 
			
		||||
 | 
			
		||||
            private static Logger _log { get; }
 | 
			
		||||
 | 
			
		||||
            static AntiRaidCommands()
 | 
			
		||||
            {
 | 
			
		||||
                _log = LogManager.GetCurrentClassLogger();
 | 
			
		||||
 | 
			
		||||
                NadekoBot.Client.MessageReceived += async (imsg) =>
 | 
			
		||||
                {
 | 
			
		||||
 | 
			
		||||
                    try
 | 
			
		||||
                    {
 | 
			
		||||
                        var msg = imsg as IUserMessage;
 | 
			
		||||
                        if (msg == null || msg.Author.IsBot)
 | 
			
		||||
                            return;
 | 
			
		||||
 | 
			
		||||
                        var channel = msg.Channel as ITextChannel;
 | 
			
		||||
                        if (channel == null)
 | 
			
		||||
                            return;
 | 
			
		||||
                        AntiSpamSetting spamSettings;
 | 
			
		||||
                        if (!antiSpamGuilds.TryGetValue(channel.Guild.Id, out spamSettings))
 | 
			
		||||
                            return;
 | 
			
		||||
 | 
			
		||||
                        var stats = spamSettings.UserStats.AddOrUpdate(msg.Author.Id, new UserSpamStats(msg.Content),
 | 
			
		||||
                            (id, old) => { old.ApplyNextMessage(msg.Content); return old; });
 | 
			
		||||
 | 
			
		||||
                        if (stats.Count >= spamSettings.MessageThreshold)
 | 
			
		||||
                        {
 | 
			
		||||
                            if (spamSettings.UserStats.TryRemove(msg.Author.Id, out stats))
 | 
			
		||||
                            {
 | 
			
		||||
                                await PunishUsers(spamSettings.Action, ProtectionType.Spamming, (IGuildUser)msg.Author)
 | 
			
		||||
                                    .ConfigureAwait(false);
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    catch { }
 | 
			
		||||
                };
 | 
			
		||||
 | 
			
		||||
                NadekoBot.Client.UserJoined += async (usr) =>
 | 
			
		||||
                {
 | 
			
		||||
                    try
 | 
			
		||||
                    {
 | 
			
		||||
                        if (usr.IsBot)
 | 
			
		||||
                            return;
 | 
			
		||||
                        AntiRaidSetting settings;
 | 
			
		||||
                        if (!antiRaidGuilds.TryGetValue(usr.Guild.Id, out settings))
 | 
			
		||||
                            return;
 | 
			
		||||
                        if (!settings.RaidUsers.Add(usr))
 | 
			
		||||
                            return;
 | 
			
		||||
 | 
			
		||||
                        ++settings.UsersCount;
 | 
			
		||||
 | 
			
		||||
                        if (settings.UsersCount >= settings.UserThreshold)
 | 
			
		||||
                        {
 | 
			
		||||
                            var users = settings.RaidUsers.ToArray();
 | 
			
		||||
                            settings.RaidUsers.Clear();
 | 
			
		||||
 | 
			
		||||
                            await PunishUsers(settings.Action, ProtectionType.Raiding, users).ConfigureAwait(false);
 | 
			
		||||
                        }
 | 
			
		||||
                        await Task.Delay(1000 * settings.Seconds).ConfigureAwait(false);
 | 
			
		||||
 | 
			
		||||
                        settings.RaidUsers.TryRemove(usr);
 | 
			
		||||
                        --settings.UsersCount;
 | 
			
		||||
 | 
			
		||||
                    }
 | 
			
		||||
                    catch { }
 | 
			
		||||
                };
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            private static async Task PunishUsers(PunishmentAction action, ProtectionType pt, params IGuildUser[] gus)
 | 
			
		||||
            {
 | 
			
		||||
                foreach (var gu in gus)
 | 
			
		||||
                {
 | 
			
		||||
                    switch (action)
 | 
			
		||||
                    {
 | 
			
		||||
                        case PunishmentAction.Mute:
 | 
			
		||||
                            try
 | 
			
		||||
                            {
 | 
			
		||||
                                await MuteCommands.MuteUser(gu).ConfigureAwait(false);
 | 
			
		||||
                            }
 | 
			
		||||
                            catch (Exception ex) { _log.Warn(ex, "I can't apply punishement"); }
 | 
			
		||||
                            break;
 | 
			
		||||
                        case PunishmentAction.Kick:
 | 
			
		||||
                            try
 | 
			
		||||
                            {
 | 
			
		||||
                                await gu.Guild.AddBanAsync(gu, 7).ConfigureAwait(false);
 | 
			
		||||
                                try
 | 
			
		||||
                                {
 | 
			
		||||
                                    await gu.Guild.RemoveBanAsync(gu).ConfigureAwait(false);
 | 
			
		||||
                                }
 | 
			
		||||
                                catch
 | 
			
		||||
                                {
 | 
			
		||||
                                    await gu.Guild.RemoveBanAsync(gu).ConfigureAwait(false);
 | 
			
		||||
                                    // try it twice, really don't want to ban user if 
 | 
			
		||||
                                    // only kick has been specified as the punishement
 | 
			
		||||
                                }
 | 
			
		||||
                            }
 | 
			
		||||
                            catch (Exception ex) { _log.Warn(ex, "I can't apply punishment"); }
 | 
			
		||||
                            break;
 | 
			
		||||
                        case PunishmentAction.Ban:
 | 
			
		||||
                            try
 | 
			
		||||
                            {
 | 
			
		||||
                                await gu.Guild.AddBanAsync(gu, 7).ConfigureAwait(false);
 | 
			
		||||
                            }
 | 
			
		||||
                            catch (Exception ex) { _log.Warn(ex, "I can't apply punishment"); }
 | 
			
		||||
                            break;
 | 
			
		||||
                        default:
 | 
			
		||||
                            break;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                await LogCommands.TriggeredAntiProtection(gus, action, pt).ConfigureAwait(false);
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
            [NadekoCommand, Usage, Description, Aliases]
 | 
			
		||||
            [RequireContext(ContextType.Guild)]
 | 
			
		||||
            [RequireUserPermission(GuildPermission.Administrator)]
 | 
			
		||||
            public async Task AntiRaid(int userThreshold, int seconds, PunishmentAction action)
 | 
			
		||||
            {
 | 
			
		||||
                if (userThreshold < 2 || userThreshold > 30)
 | 
			
		||||
                {
 | 
			
		||||
                    await Context.Channel.SendErrorAsync("❗️User threshold must be between **2** and **30**.").ConfigureAwait(false);
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                if (seconds < 2 || seconds > 300)
 | 
			
		||||
                {
 | 
			
		||||
                    await Context.Channel.SendErrorAsync("❗️Time must be between **2** and **300** seconds.").ConfigureAwait(false);
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                try
 | 
			
		||||
                {
 | 
			
		||||
                    await MuteCommands.GetMuteRole(Context.Guild).ConfigureAwait(false);
 | 
			
		||||
                }
 | 
			
		||||
                catch (Exception ex)
 | 
			
		||||
                {
 | 
			
		||||
                    await Context.Channel.SendConfirmAsync("⚠️ Failed creating a mute role. Give me ManageRoles permission" +
 | 
			
		||||
                        "or create 'nadeko-mute' role with disabled SendMessages and try again.")
 | 
			
		||||
                            .ConfigureAwait(false);
 | 
			
		||||
                    _log.Warn(ex);
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                var setting = new AntiRaidSetting()
 | 
			
		||||
                {
 | 
			
		||||
                    Action = action,
 | 
			
		||||
                    Seconds = seconds,
 | 
			
		||||
                    UserThreshold = userThreshold,
 | 
			
		||||
                };
 | 
			
		||||
                antiRaidGuilds.AddOrUpdate(Context.Guild.Id, setting, (id, old) => setting);
 | 
			
		||||
 | 
			
		||||
                await Context.Channel.SendConfirmAsync($"ℹ️ {Context.User.Mention} If **{userThreshold}** or more users join within **{seconds}** seconds, I will **{action}** them.")
 | 
			
		||||
                        .ConfigureAwait(false);
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            [NadekoCommand, Usage, Description, Aliases]
 | 
			
		||||
            [RequireContext(ContextType.Guild)]
 | 
			
		||||
            [RequireUserPermission(GuildPermission.Administrator)]
 | 
			
		||||
            public async Task AntiSpam(int messageCount=3, PunishmentAction action = PunishmentAction.Mute)
 | 
			
		||||
            {
 | 
			
		||||
                if (messageCount < 2 || messageCount > 10)
 | 
			
		||||
                    return;
 | 
			
		||||
 | 
			
		||||
                AntiSpamSetting throwaway;
 | 
			
		||||
                if (antiSpamGuilds.TryRemove(Context.Guild.Id, out throwaway))
 | 
			
		||||
                {
 | 
			
		||||
                    await Context.Channel.SendConfirmAsync("🆗 **Anti-Spam feature** has been **disabled** on this server.").ConfigureAwait(false);
 | 
			
		||||
                }
 | 
			
		||||
                else
 | 
			
		||||
                {
 | 
			
		||||
                    try
 | 
			
		||||
                    {
 | 
			
		||||
                        await MuteCommands.GetMuteRole(Context.Guild).ConfigureAwait(false);
 | 
			
		||||
                    }
 | 
			
		||||
                    catch (Exception ex)
 | 
			
		||||
                    {
 | 
			
		||||
                        await Context.Channel.SendErrorAsync("⚠️ Failed creating a mute role. Give me ManageRoles permission" +
 | 
			
		||||
                            "or create 'nadeko-mute' role with disabled SendMessages and try again.")
 | 
			
		||||
                                .ConfigureAwait(false);
 | 
			
		||||
                        _log.Warn(ex);
 | 
			
		||||
                        return;
 | 
			
		||||
                    }
 | 
			
		||||
 | 
			
		||||
                    if (antiSpamGuilds.TryAdd(Context.Guild.Id, new AntiSpamSetting()
 | 
			
		||||
                    {
 | 
			
		||||
                        Action = action,
 | 
			
		||||
                        MessageThreshold = messageCount,
 | 
			
		||||
                    }))
 | 
			
		||||
                    await Context.Channel.SendConfirmAsync("✅ **Anti-Spam feature** has been **enabled** on this server.").ConfigureAwait(false);
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -91,13 +91,11 @@ namespace NadekoBot.Modules.Administration
 | 
			
		||||
            {
 | 
			
		||||
                var _log = LogManager.GetCurrentClassLogger();
 | 
			
		||||
                var sw = Stopwatch.StartNew();
 | 
			
		||||
                using (var uow = DbHandler.UnitOfWork())
 | 
			
		||||
                {
 | 
			
		||||
 | 
			
		||||
                repeaters = new ConcurrentDictionary<ulong, ConcurrentQueue<RepeatRunner>>(NadekoBot.AllGuildConfigs
 | 
			
		||||
                    .ToDictionary(gc => gc.GuildId,
 | 
			
		||||
                                    gc => new ConcurrentQueue<RepeatRunner>(gc.GuildRepeaters.Select(gr => new RepeatRunner(gr))
 | 
			
		||||
                                    .Where(gr => gr.Channel != null))));
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                sw.Stop();
 | 
			
		||||
                _log.Debug($"Loaded in {sw.Elapsed.TotalSeconds:F2}s");
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										54
									
								
								src/NadekoBot/Resources/CommandStrings.Designer.cs
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										54
									
								
								src/NadekoBot/Resources/CommandStrings.Designer.cs
									
									
									
										generated
									
									
									
								
							@@ -437,6 +437,33 @@ namespace NadekoBot.Resources {
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        ///    Looks up a localized string similar to antilist antilst.
 | 
			
		||||
        /// </summary>
 | 
			
		||||
        public static string antilist_cmd {
 | 
			
		||||
            get {
 | 
			
		||||
                return ResourceManager.GetString("antilist_cmd", resourceCulture);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        ///    Looks up a localized string similar to Shows currently enabled protection features..
 | 
			
		||||
        /// </summary>
 | 
			
		||||
        public static string antilist_desc {
 | 
			
		||||
            get {
 | 
			
		||||
                return ResourceManager.GetString("antilist_desc", resourceCulture);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        ///    Looks up a localized string similar to `{0}antilist`.
 | 
			
		||||
        /// </summary>
 | 
			
		||||
        public static string antilist_usage {
 | 
			
		||||
            get {
 | 
			
		||||
                return ResourceManager.GetString("antilist_usage", resourceCulture);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        ///    Looks up a localized string similar to antiraid.
 | 
			
		||||
        /// </summary>
 | 
			
		||||
@@ -491,6 +518,33 @@ namespace NadekoBot.Resources {
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        ///    Looks up a localized string similar to antispamignore.
 | 
			
		||||
        /// </summary>
 | 
			
		||||
        public static string antispamignore_cmd {
 | 
			
		||||
            get {
 | 
			
		||||
                return ResourceManager.GetString("antispamignore_cmd", resourceCulture);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        ///    Looks up a localized string similar to Toggles whether antispam ignores current channel. Antispam must be enabled..
 | 
			
		||||
        /// </summary>
 | 
			
		||||
        public static string antispamignore_desc {
 | 
			
		||||
            get {
 | 
			
		||||
                return ResourceManager.GetString("antispamignore_desc", resourceCulture);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        ///    Looks up a localized string similar to `{0}antispamignore`.
 | 
			
		||||
        /// </summary>
 | 
			
		||||
        public static string antispamignore_usage {
 | 
			
		||||
            get {
 | 
			
		||||
                return ResourceManager.GetString("antispamignore_usage", resourceCulture);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        ///    Looks up a localized string similar to asar.
 | 
			
		||||
        /// </summary>
 | 
			
		||||
 
 | 
			
		||||
@@ -2907,4 +2907,22 @@
 | 
			
		||||
  <data name="repeatremove_usage" xml:space="preserve">
 | 
			
		||||
    <value>`{0}reprm 2`</value>
 | 
			
		||||
  </data>
 | 
			
		||||
  <data name="antilist_cmd" xml:space="preserve">
 | 
			
		||||
    <value>antilist antilst</value>
 | 
			
		||||
  </data>
 | 
			
		||||
  <data name="antilist_desc" xml:space="preserve">
 | 
			
		||||
    <value>Shows currently enabled protection features.</value>
 | 
			
		||||
  </data>
 | 
			
		||||
  <data name="antilist_usage" xml:space="preserve">
 | 
			
		||||
    <value>`{0}antilist`</value>
 | 
			
		||||
  </data>
 | 
			
		||||
  <data name="antispamignore_cmd" xml:space="preserve">
 | 
			
		||||
    <value>antispamignore</value>
 | 
			
		||||
  </data>
 | 
			
		||||
  <data name="antispamignore_desc" xml:space="preserve">
 | 
			
		||||
    <value>Toggles whether antispam ignores current channel. Antispam must be enabled.</value>
 | 
			
		||||
  </data>
 | 
			
		||||
  <data name="antispamignore_usage" xml:space="preserve">
 | 
			
		||||
    <value>`{0}antispamignore`</value>
 | 
			
		||||
  </data>
 | 
			
		||||
</root>
 | 
			
		||||
@@ -1,4 +1,5 @@
 | 
			
		||||
using System.Collections.Generic;
 | 
			
		||||
using static NadekoBot.Modules.Administration.Administration;
 | 
			
		||||
 | 
			
		||||
namespace NadekoBot.Services.Database.Models
 | 
			
		||||
{
 | 
			
		||||
@@ -59,6 +60,11 @@ namespace NadekoBot.Services.Database.Models
 | 
			
		||||
        public string MuteRoleName { get; set; }
 | 
			
		||||
        public bool CleverbotEnabled { get; set; }
 | 
			
		||||
        public HashSet<GuildRepeater> GuildRepeaters { get; set; } = new HashSet<GuildRepeater>();
 | 
			
		||||
 | 
			
		||||
        public AntiRaidSetting AntiRaidSetting { get; set; }
 | 
			
		||||
        public AntiSpamSetting AntiSpamSetting { get; set; }
 | 
			
		||||
 | 
			
		||||
        //public List<ProtectionIgnoredChannel> ProtectionIgnoredChannels { get; set; } = new List<ProtectionIgnoredChannel>();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public class FilterChannelId : DbEntity
 | 
			
		||||
 
 | 
			
		||||
@@ -142,6 +142,17 @@ namespace NadekoBot.Services.Database
 | 
			
		||||
                .HasIndex(c => c.GuildId)
 | 
			
		||||
                .IsUnique();
 | 
			
		||||
 | 
			
		||||
            modelBuilder.Entity<AntiSpamSetting>()
 | 
			
		||||
                .HasOne(x => x.GuildConfig)
 | 
			
		||||
                .WithOne(x => x.AntiSpamSetting);
 | 
			
		||||
 | 
			
		||||
            modelBuilder.Entity<AntiRaidSetting>()
 | 
			
		||||
                .HasOne(x => x.GuildConfig)
 | 
			
		||||
                .WithOne(x => x.AntiRaidSetting);
 | 
			
		||||
 | 
			
		||||
            //modelBuilder.Entity<ProtectionIgnoredChannel>()
 | 
			
		||||
            //    .HasAlternateKey(c => new { c.ChannelId, c.ProtectionType });
 | 
			
		||||
 | 
			
		||||
            #endregion
 | 
			
		||||
 | 
			
		||||
            #region BotConfig
 | 
			
		||||
@@ -221,6 +232,11 @@ namespace NadekoBot.Services.Database
 | 
			
		||||
                .IsUnique();
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
            #endregion
 | 
			
		||||
 | 
			
		||||
            #region Protection
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
            #endregion
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 
 | 
			
		||||
@@ -27,6 +27,9 @@ namespace NadekoBot.Services.Database.Repositories.Impl
 | 
			
		||||
                .Include(gc => gc.FilteredWords)
 | 
			
		||||
                .Include(gc => gc.CommandCooldowns)
 | 
			
		||||
                .Include(gc => gc.GuildRepeaters)
 | 
			
		||||
                .Include(gc => gc.AntiRaidSetting)
 | 
			
		||||
                .Include(gc => gc.AntiSpamSetting)
 | 
			
		||||
                    .ThenInclude(x => x.IgnoredChannels)
 | 
			
		||||
                .ToList();
 | 
			
		||||
 | 
			
		||||
        /// <summary>
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user