2025-07-03 15:22:40 +03:00
|
|
|
|
// File: Services/Scanners/AbstractScanner.cs
|
|
|
|
|
|
|
|
|
|
using WebmrAPI.Utils;
|
|
|
|
|
|
|
|
|
|
namespace WebmrAPI.Services.Scanners
|
|
|
|
|
{
|
|
|
|
|
public abstract class AbstractScanner<T> : IScannable where T : new()
|
|
|
|
|
{
|
|
|
|
|
internal IScanProvider _provider;
|
|
|
|
|
LazyConcurrentContainer<T> _container;
|
|
|
|
|
|
|
|
|
|
abstract public ScanTarget Target { get; }
|
|
|
|
|
|
|
|
|
|
internal IScanProvider Provider { get => _provider; }
|
|
|
|
|
internal LazyConcurrentContainer<T> Container { get => _container; }
|
|
|
|
|
internal int Timeout { get => _provider.GetTimeout(Target); }
|
|
|
|
|
|
|
|
|
|
internal bool IsActual()
|
|
|
|
|
{
|
|
|
|
|
return (DateTime.UtcNow - Container.LastUpdate).TotalSeconds < Timeout;
|
|
|
|
|
}
|
|
|
|
|
internal bool GetFromCacheOrNew(long key, out T res)
|
|
|
|
|
{
|
|
|
|
|
var cache = Container.Container;
|
|
|
|
|
|
|
|
|
|
bool result = true;
|
|
|
|
|
T? found;
|
|
|
|
|
if (cache == null || !cache.TryGetValue(key, out found))
|
|
|
|
|
{
|
|
|
|
|
result = false;
|
|
|
|
|
found = new();
|
|
|
|
|
}
|
|
|
|
|
res = found;
|
|
|
|
|
return result;
|
|
|
|
|
}
|
|
|
|
|
|
2025-07-03 20:01:19 +03:00
|
|
|
|
abstract internal Task<bool> ScanAsync(Dictionary<long, T> data);
|
2025-07-03 15:22:40 +03:00
|
|
|
|
|
2025-07-03 20:01:19 +03:00
|
|
|
|
public async Task ScanAsync()
|
2025-07-03 15:22:40 +03:00
|
|
|
|
{
|
|
|
|
|
bool success = false;
|
|
|
|
|
if (Container.Container != null && IsActual()) return;
|
|
|
|
|
|
|
|
|
|
try
|
|
|
|
|
{
|
2025-07-03 20:01:19 +03:00
|
|
|
|
Dictionary<long, T> data = new();
|
|
|
|
|
|
|
|
|
|
if (success = await ScanAsync(data))
|
2025-07-03 15:22:40 +03:00
|
|
|
|
{
|
|
|
|
|
Container.SetContainer(data);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
finally
|
|
|
|
|
{
|
|
|
|
|
if (!success)
|
|
|
|
|
{
|
|
|
|
|
Container.CleanContainer();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public AbstractScanner(IScanProvider scanProvider, LazyConcurrentContainer<T> container)
|
|
|
|
|
{
|
|
|
|
|
_provider = scanProvider;
|
|
|
|
|
_container = container;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|