feat: add thread-safe ActivityLog with bounded capacity
This commit is contained in:
48
src/SpamGuard/Services/ActivityLog.cs
Normal file
48
src/SpamGuard/Services/ActivityLog.cs
Normal file
@@ -0,0 +1,48 @@
|
|||||||
|
namespace SpamGuard.Services;
|
||||||
|
|
||||||
|
using SpamGuard.Models;
|
||||||
|
|
||||||
|
public sealed class ActivityLog
|
||||||
|
{
|
||||||
|
private readonly List<ActivityEntry> _entries = new();
|
||||||
|
private readonly object _lock = new();
|
||||||
|
private readonly int _maxEntries;
|
||||||
|
|
||||||
|
public int TodayChecked => GetTodayCount(_ => true);
|
||||||
|
public int TodaySpam => GetTodayCount(e => e.Verdict == Verdict.Spam);
|
||||||
|
|
||||||
|
public ActivityLog(int maxEntries = 500)
|
||||||
|
{
|
||||||
|
_maxEntries = maxEntries;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Add(ActivityEntry entry)
|
||||||
|
{
|
||||||
|
lock (_lock)
|
||||||
|
{
|
||||||
|
_entries.Add(entry);
|
||||||
|
if (_entries.Count > _maxEntries)
|
||||||
|
_entries.RemoveAt(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<ActivityEntry> GetRecent(int count = 100)
|
||||||
|
{
|
||||||
|
lock (_lock)
|
||||||
|
{
|
||||||
|
return _entries
|
||||||
|
.OrderByDescending(e => e.Timestamp)
|
||||||
|
.Take(count)
|
||||||
|
.ToList();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private int GetTodayCount(Func<ActivityEntry, bool> predicate)
|
||||||
|
{
|
||||||
|
var today = DateTime.UtcNow.Date;
|
||||||
|
lock (_lock)
|
||||||
|
{
|
||||||
|
return _entries.Count(e => e.Timestamp.Date == today && predicate(e));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user