DD.WellWorkover.Cloud/AsbCloudInfrastructure/Services/TelemetryTracker.cs

127 lines
4.7 KiB
C#
Raw Normal View History

2021-07-21 15:29:19 +05:00
using AsbCloudApp.Services;
using System;
using System.Collections.Generic;
using System.Linq;
using AsbCloudDb.Model;
using AsbCloudInfrastructure.Services.Cache;
using Microsoft.EntityFrameworkCore;
using System.Collections.Concurrent;
using System.Threading.Tasks;
namespace AsbCloudInfrastructure.Services
{
public class TelemetryTracker : ITelemetryTracker
{
class TrackerStat
{
//public int Id { get; set; }
public string RemoteUid { get; set; }
/// <summary>
/// Время последнего запроса (по времени сервера)
/// </summary>
public DateTime LastTimeServer { get; set; }
/// <summary>
/// Время указанное в данных последнего запроса (из удаленного источника)
/// </summary>
public DateTime LastTimeRemote { get; set; }
}
private readonly ConcurrentDictionary<string, TrackerStat> requests;
public TelemetryTracker(CacheDb cacheDb)
{
var options = new DbContextOptionsBuilder<AsbCloudDbContext>()
.UseNpgsql("Host=localhost;Database=postgres;Username=postgres;Password=q;Persist Security Info=True")
.Options;
using var db = new AsbCloudDbContext(options);
2021-10-27 17:48:19 +05:00
var cacheTelemetry = cacheDb.GetCachedTable<Telemetry>(db);
var keyValuePairs = new Dictionary<string, TrackerStat>(cacheTelemetry.Count());
foreach (var telemetry in cacheTelemetry)
{
2021-11-22 11:30:08 +05:00
var date = telemetry.Info?.DrillingStartDate
?? GetDateByUidOrDefault(telemetry.RemoteUid, DateTime.MinValue);
2021-11-22 11:30:08 +05:00
keyValuePairs[telemetry.RemoteUid] = new TrackerStat
{
RemoteUid = telemetry.RemoteUid,
LastTimeRemote = date,
LastTimeServer = date,
};
}
requests = new ConcurrentDictionary<string, TrackerStat>(keyValuePairs);
2021-11-22 11:30:08 +05:00
Task.Run(async () =>
{
db.Database.SetCommandTimeout(2 * 60);
var dates = await db.TelemetryDataSaub
.GroupBy(d => d.IdTelemetry)
.Select(g => new
{
IdTelemetry = g.Key,
2021-11-22 11:30:08 +05:00
DateMax = g.Max(d => d.Date),
DateMin = g.Min(d => d.Date),
})
.AsNoTracking()
.ToListAsync()
.ConfigureAwait(false);
db.Dispose();
var oldReqs = dates.Select(t => new
{
Uid = cacheTelemetry.FirstOrDefault(c => c.Id == t.IdTelemetry).RemoteUid,
2021-11-22 11:30:08 +05:00
t.DateMax,
});
foreach (var oldReq in oldReqs)
{
var request = requests.GetValueOrDefault(oldReq.Uid);
2021-11-22 11:30:08 +05:00
if (request is not null)
{
2021-11-22 11:30:08 +05:00
if (request.LastTimeRemote < oldReq.DateMax)
request.LastTimeRemote = oldReq.DateMax;
if (request.LastTimeServer < oldReq.DateMax)
request.LastTimeServer = oldReq.DateMax;
}
}
});
}
private static DateTime GetDateByUidOrDefault(string remoteUid, DateTime defaultValue = default)
{
//eg: uid = 20211102_173407926
if (string.IsNullOrEmpty(remoteUid) || (remoteUid.Length != 18))
return defaultValue;
if (DateTime.TryParseExact(remoteUid, "yyyyMMdd_HHmmssfff",
System.Globalization.CultureInfo.InvariantCulture,
System.Globalization.DateTimeStyles.AssumeUniversal,
out DateTime parsedDate))
return parsedDate;
return defaultValue;
}
public void SaveRequestDate(string uid, DateTime remoteDate)
{
var stat = requests.GetValueOrDefault(uid);
if(stat is null)
{
stat = new TrackerStat{ RemoteUid = uid };
requests[uid] = stat;
}
stat.LastTimeServer = DateTime.Now;
stat.LastTimeRemote = remoteDate;
}
public DateTime GetLastTelemetryDateByUid(string uid) =>
requests.GetValueOrDefault(uid)?.LastTimeRemote ?? default;
public IEnumerable<string> GetTransmittingTelemetriesUids() =>
requests.Keys;
}
}