using e_suite.API.Common; using e_suite.API.Common.models; using e_suite.API.Common.repository; using e_suite.Database.Audit; using e_suite.Modules.BlockedIPsManager.Extensions; using e_suite.Utilities.Pagination; using eSuite.Core.Clock; using Microsoft.Extensions.Configuration; using System.Linq.Expressions; namespace e_suite.Modules.BlockedIPsManager; public class BlockedIPsManager : IBlockedIPsManager { private readonly IClock _clock; private readonly IConfiguration _configuration; private readonly IBlockedIPsManagerRepository _blockedIPsManagerRepository; public BlockedIPsManager(IBlockedIPsManagerRepository blockedIPsManagerRepository, IClock clock, IConfiguration configuration) { _blockedIPsManagerRepository = blockedIPsManagerRepository; _clock = clock; _configuration = configuration; } public async Task> GetBlockedIPs(Paging paging, CancellationToken cancellationToken) { //Can I make this move, its a copied code from the sentinal var loginAttemptTimeoutMinutes = _configuration.GetValue("Sentinel:LoginAttemptTimeoutMinutes"); var maxLoginAttempts = _configuration.GetValue("Sentinel:MaxLoginAttempts"); var earliestAttemptTime = _clock.GetNow.AddMinutes(-loginAttemptTimeoutMinutes); var blockedIPs = _blockedIPsManagerRepository.GetBlockedIPs(earliestAttemptTime); var dateTimeNow = _clock.GetNow; var data = blockedIPs.GroupBy(g => g.IPAddress) .Select(x => new BlockedIPs { IpAddress = x.First().IPAddress, NumberOfAttempts = x.Count(), BlockedAt = x.Max(t => t.AttemptedTime), UnblockedIn = GetUnlockedMinutes(x.Min(t => t.AttemptedTime), loginAttemptTimeoutMinutes, dateTimeNow) .ToInteger() }); var paginatedData = await PaginatedData.Paginate(data, paging, KeySelector, cancellationToken); return paginatedData; } public static double GetUnlockedMinutes(DateTimeOffset attemptedTime, int loginAttemptTimeoutMinutes, DateTimeOffset dateTimeNow) { return Math.Floor(attemptedTime.AddMinutes(loginAttemptTimeoutMinutes).Subtract(dateTimeNow).TotalMinutes); } private Expression> KeySelector(string? sortKey) { return sortKey?.ToLowerInvariant() switch { "ipaddress" => x => x.IpAddress, "numberofattempts" => x => x.NumberOfAttempts, "blockedat" => x => x.BlockedAt, "unblockedin" => x => x.UnblockedIn, _ => x => x.IpAddress }; } public async Task UnblockIPAddress(AuditUserDetails auditUserDetails, string ipaddress, CancellationToken cancellationToken) { await _blockedIPsManagerRepository.UnBlockIP(auditUserDetails, ipaddress, cancellationToken); } }