mirror of
https://gitlab.com/Kwoth/nadekobot.git
synced 2025-09-11 17:58:26 -04:00
- Renamed CustomReaction model to NadekoExpression
- Used structured logging everywhere
This commit is contained in:
@@ -63,7 +63,7 @@ public partial class Administration
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Log.Warning(ex.ToString());
|
||||
Log.Warning(ex, "Exception in the mute command");
|
||||
await ReplyErrorLocalizedAsync(strs.mute_error);
|
||||
}
|
||||
}
|
||||
@@ -124,7 +124,7 @@ public partial class Administration
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Log.Warning(ex.ToString());
|
||||
Log.Warning(ex, "Exception in the chatmute command");
|
||||
await ReplyErrorLocalizedAsync(strs.mute_error);
|
||||
}
|
||||
}
|
||||
@@ -148,7 +148,7 @@ public partial class Administration
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Log.Warning(ex.ToString());
|
||||
Log.Warning(ex, "Error in chatmute command");
|
||||
await ReplyErrorLocalizedAsync(strs.mute_error);
|
||||
}
|
||||
}
|
||||
|
@@ -221,7 +221,6 @@ public class ProtectionService : INService
|
||||
if (stats.Count >= spamSettings.AntiSpamSettings.MessageThreshold)
|
||||
if (spamSettings.UserStats.TryRemove(msg.Author.Id, out stats))
|
||||
{
|
||||
stats.Dispose();
|
||||
var settings = spamSettings.AntiSpamSettings;
|
||||
await PunishUsers(settings.Action,
|
||||
ProtectionType.Spamming,
|
||||
@@ -319,10 +318,8 @@ public class ProtectionService : INService
|
||||
|
||||
public bool TryStopAntiSpam(ulong guildId)
|
||||
{
|
||||
if (_antiSpamGuilds.TryRemove(guildId, out var removed))
|
||||
if (_antiSpamGuilds.TryRemove(guildId, out _))
|
||||
{
|
||||
foreach (var (_, val) in removed.UserStats) val.Dispose();
|
||||
|
||||
using var uow = _db.GetDbContext();
|
||||
var gc = uow.GuildConfigsForId(guildId,
|
||||
set => set.Include(x => x.AntiSpamSetting).ThenInclude(x => x.IgnoredChannels));
|
||||
|
@@ -1,52 +1,65 @@
|
||||
#nullable disable
|
||||
namespace NadekoBot.Modules.Administration;
|
||||
|
||||
public sealed class UserSpamStats : IDisposable
|
||||
public sealed class UserSpamStats
|
||||
{
|
||||
public int Count
|
||||
=> timers.Count;
|
||||
{
|
||||
get
|
||||
{
|
||||
lock (_applyLock)
|
||||
{
|
||||
Cleanup();
|
||||
Log.Information("{Count}",_messageTracker.Count.ToString());
|
||||
return _messageTracker.Count;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public string LastMessage { get; set; }
|
||||
private string lastMessage;
|
||||
|
||||
private ConcurrentQueue<Timer> timers;
|
||||
private readonly Queue<DateTime> _messageTracker;
|
||||
|
||||
private readonly object _applyLock = new();
|
||||
|
||||
private readonly TimeSpan _maxTime = TimeSpan.FromMinutes(30);
|
||||
|
||||
public UserSpamStats(IUserMessage msg)
|
||||
{
|
||||
LastMessage = msg.Content.ToUpperInvariant();
|
||||
timers = new();
|
||||
lastMessage = msg.Content.ToUpperInvariant();
|
||||
_messageTracker = new();
|
||||
|
||||
ApplyNextMessage(msg);
|
||||
}
|
||||
|
||||
public void ApplyNextMessage(IUserMessage message)
|
||||
{
|
||||
var upperMsg = message.Content.ToUpperInvariant();
|
||||
|
||||
lock (_applyLock)
|
||||
{
|
||||
var upperMsg = message.Content.ToUpperInvariant();
|
||||
if (upperMsg != LastMessage || (string.IsNullOrWhiteSpace(upperMsg) && message.Attachments.Any()))
|
||||
if (upperMsg != lastMessage || (string.IsNullOrWhiteSpace(upperMsg) && message.Attachments.Any()))
|
||||
{
|
||||
LastMessage = upperMsg;
|
||||
while (timers.TryDequeue(out var old))
|
||||
old.Change(Timeout.Infinite, Timeout.Infinite);
|
||||
// if it's a new message, reset spam counter
|
||||
lastMessage = upperMsg;
|
||||
_messageTracker.Clear();
|
||||
}
|
||||
|
||||
var t = new Timer(_ =>
|
||||
{
|
||||
if (timers.TryDequeue(out var old))
|
||||
old.Change(Timeout.Infinite, Timeout.Infinite);
|
||||
},
|
||||
null,
|
||||
TimeSpan.FromMinutes(30),
|
||||
TimeSpan.FromMinutes(30));
|
||||
timers.Enqueue(t);
|
||||
_messageTracker.Enqueue(DateTime.UtcNow);
|
||||
}
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
private void Cleanup()
|
||||
{
|
||||
while (timers.TryDequeue(out var old))
|
||||
old.Change(Timeout.Infinite, Timeout.Infinite);
|
||||
lock (_applyLock)
|
||||
{
|
||||
while (_messageTracker.TryPeek(out var dateTime))
|
||||
{
|
||||
if (DateTime.UtcNow - dateTime < _maxTime)
|
||||
break;
|
||||
|
||||
_messageTracker.Dequeue();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -18,7 +18,7 @@ public sealed class SelfService : ILateExecutor, IReadyExecutor, INService
|
||||
private ImmutableDictionary<ulong, IDMChannel> ownerChannels =
|
||||
new Dictionary<ulong, IDMChannel>().ToImmutableDictionary();
|
||||
|
||||
private ConcurrentDictionary<ulong?, ConcurrentDictionary<int, Timer>> _autoCommands = new();
|
||||
private ConcurrentDictionary<ulong?, ConcurrentDictionary<int, Timer>> autoCommands = new();
|
||||
|
||||
private readonly IImageCache _imgs;
|
||||
private readonly IHttpClientFactory _httpFactory;
|
||||
@@ -75,12 +75,12 @@ public sealed class SelfService : ILateExecutor, IReadyExecutor, INService
|
||||
if (server.OwnerId != _client.CurrentUser.Id)
|
||||
{
|
||||
await server.LeaveAsync();
|
||||
Log.Information($"Left server {server.Name} [{server.Id}]");
|
||||
Log.Information("Left server {Name} [{Id}]", server.Name, server.Id);
|
||||
}
|
||||
else
|
||||
{
|
||||
await server.DeleteAsync();
|
||||
Log.Information($"Deleted server {server.Name} [{server.Id}]");
|
||||
Log.Information("Deleted server {Name} [{Id}]", server.Name, server.Id);
|
||||
}
|
||||
});
|
||||
}
|
||||
@@ -89,7 +89,7 @@ public sealed class SelfService : ILateExecutor, IReadyExecutor, INService
|
||||
{
|
||||
await using var uow = _db.GetDbContext();
|
||||
|
||||
_autoCommands = uow.AutoCommands.AsNoTracking()
|
||||
autoCommands = uow.AutoCommands.AsNoTracking()
|
||||
.Where(x => x.Interval >= 5)
|
||||
.AsEnumerable()
|
||||
.GroupBy(x => x.GuildId)
|
||||
@@ -145,7 +145,7 @@ public sealed class SelfService : ILateExecutor, IReadyExecutor, INService
|
||||
|
||||
if (cmd.Interval >= 5)
|
||||
{
|
||||
var autos = _autoCommands.GetOrAdd(cmd.GuildId, new ConcurrentDictionary<int, Timer>());
|
||||
var autos = autoCommands.GetOrAdd(cmd.GuildId, new ConcurrentDictionary<int, Timer>());
|
||||
autos.AddOrUpdate(cmd.Id,
|
||||
_ => TimerFromAutoCommand(cmd),
|
||||
(_, old) =>
|
||||
@@ -185,9 +185,9 @@ public sealed class SelfService : ILateExecutor, IReadyExecutor, INService
|
||||
|
||||
if (!ownerChannels.Any())
|
||||
Log.Warning(
|
||||
"No owner channels created! Make sure you've specified the correct OwnerId in the creds.yml file and invited the bot to a Discord server.");
|
||||
"No owner channels created! Make sure you've specified the correct OwnerId in the creds.yml file and invited the bot to a Discord server");
|
||||
else
|
||||
Log.Information($"Created {ownerChannels.Count} out of {_creds.OwnerIds.Count} owner message channels.");
|
||||
Log.Information("Created {OwnerChannelCount} out of {TotalOwnerChannelCount} owner message channels", ownerChannels.Count, _creds.OwnerIds.Count);
|
||||
}
|
||||
|
||||
public Task LeaveGuild(string guildStr)
|
||||
@@ -220,7 +220,7 @@ public sealed class SelfService : ILateExecutor, IReadyExecutor, INService
|
||||
}
|
||||
catch
|
||||
{
|
||||
Log.Warning("Can't contact owner with id {0}", ownerCh.Recipient.Id);
|
||||
Log.Warning("Can't contact owner with id {OwnerId}", ownerCh.Recipient.Id);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -262,7 +262,7 @@ public sealed class SelfService : ILateExecutor, IReadyExecutor, INService
|
||||
if (cmd is not null)
|
||||
{
|
||||
uow.Remove(cmd);
|
||||
if (_autoCommands.TryGetValue(cmd.GuildId, out var autos))
|
||||
if (autoCommands.TryGetValue(cmd.GuildId, out var autos))
|
||||
if (autos.TryRemove(cmd.Id, out var timer))
|
||||
timer.Change(Timeout.Infinite, Timeout.Infinite);
|
||||
uow.SaveChanges();
|
||||
|
@@ -86,7 +86,7 @@ public partial class Administration
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Log.Warning(ex.Message);
|
||||
Log.Warning(ex, "Exception occured while warning a user");
|
||||
var errorEmbed = _eb.Create().WithErrorColor().WithDescription(GetText(strs.cant_apply_punishment));
|
||||
|
||||
if (dmFailed) errorEmbed.WithFooter("⚠️ " + GetText(strs.unable_to_dm_user));
|
||||
@@ -565,7 +565,7 @@ public partial class Administration
|
||||
{
|
||||
var bans = await ctx.Guild.GetBansAsync();
|
||||
|
||||
var bun = bans.FirstOrDefault(x => x.User.ToString().ToLowerInvariant() == user.ToLowerInvariant());
|
||||
var bun = bans.FirstOrDefault(x => x.User.ToString()!.ToLowerInvariant() == user.ToLowerInvariant());
|
||||
|
||||
if (bun is null)
|
||||
{
|
||||
|
@@ -162,7 +162,9 @@ public class UserPunishService : INService
|
||||
}
|
||||
else
|
||||
{
|
||||
Log.Warning($"Can't find role {roleId.Value} on server {guild.Id} to apply punishment.");
|
||||
Log.Warning("Can't find role {RoleId} on server {GuildId} to apply punishment",
|
||||
roleId.Value,
|
||||
guild.Id);
|
||||
}
|
||||
|
||||
break;
|
||||
@@ -217,7 +219,9 @@ WHERE GuildId in (SELECT GuildId FROM GuildConfigs WHERE WarnExpireHours > 0 AND
|
||||
AND DateAdded < datetime('now', (SELECT '-' || WarnExpireHours || ' hours' FROM GuildConfigs as gc WHERE gc.GuildId = Warnings.GuildId));");
|
||||
|
||||
if (cleared > 0 || deleted > 0)
|
||||
Log.Information($"Cleared {cleared} warnings and deleted {deleted} warnings due to expiry.");
|
||||
Log.Information("Cleared {ClearedWarnings} warnings and deleted {DeletedWarnings} warnings due to expiry",
|
||||
cleared,
|
||||
deleted);
|
||||
}
|
||||
|
||||
public async Task CheckWarnExpiresAsync(ulong guildId)
|
||||
@@ -305,7 +309,8 @@ WHERE GuildId={guildId}
|
||||
IRole role = null)
|
||||
{
|
||||
// these 3 don't make sense with time
|
||||
if (punish is PunishmentAction.Softban or PunishmentAction.Kick or PunishmentAction.RemoveRoles && time is not null)
|
||||
if (punish is PunishmentAction.Softban or PunishmentAction.Kick or PunishmentAction.RemoveRoles
|
||||
&& time is not null)
|
||||
return false;
|
||||
if (number <= 0 || (time is not null && time.Time > TimeSpan.FromDays(49)))
|
||||
return false;
|
||||
|
Reference in New Issue
Block a user