Files
mapo-iob-man/IOB-MAN.Core/StatsCollector.cs
T
2025-06-17 09:15:06 +02:00

164 lines
4.9 KiB
C#

using System;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace IOB_MAN.Core
{
/// <summary>
/// Oggetto collezione statistiche x report status applicazione
/// </summary>
public class StatsCollector
{
#region Public Properties
/// <summary>
/// Calcola uptime del processo
/// </summary>
public static string UptimeCurr
{
get
{
string answ = "ND";
var upT = DateTime.Now.Subtract(StartTime);
// formatto secondo durata...
if (upT.TotalDays > 1)
{
answ = $"{upT.Days:00} d {upT.Hours:00}h {upT.Minutes:00}m";
}
else
{
answ = $"{upT.Hours:00}h {upT.Minutes:00}m {upT.Seconds:00} s";
}
return answ;
}
}
#endregion Public Properties
#region Public Methods
/// <summary>
/// Restituisce l'oggetto statistiche come dizionario di tutti gli eventi
/// </summary>
/// <returns></returns>
public static Dictionary<string, string> CurrentInfo()
{
Dictionary<string, string> result = new Dictionary<string, string>();
// ciclo sugli oggetti calcolando durate e ultima call
foreach (var item in Counter)
{
string sRec = $"{Counter[item.Key]} x {formElaps((Duration[item.Key]) / Counter[item.Key])}";
result.Add(item.Key, sRec);
result.Add($"{item.Key}Last", $"{LastCall[item.Key]:yyyy-MM-dd HH:mm:ss}");
}
// infine metto stata avvio e uptime
result.Add("Startup", $"{StartTime:yyyy-MM-dd HH:mm:ss}");
result.Add("Uptime", UptimeCurr);
return result;
}
/// <summary>
/// Reset collezione statistiche
/// </summary>
public static void ResetData()
{
StartTime = DateTime.Now;
Counter = new ConcurrentDictionary<string, long>();
Duration = new ConcurrentDictionary<string, TimeSpan>();
LastCall = new ConcurrentDictionary<string, DateTime>();
}
/// <summary>
/// Upsert statistica gestita
/// </summary>
/// <param name="functionName"></param>
/// <param name="elaps"></param>
public static void UpdateStat(string functionName, TimeSpan elaps)
{
if (!Duration.ContainsKey(functionName))
{
Duration.TryAdd(functionName, elaps);
}
else
{
Duration[functionName] += elaps;
}
if (!Counter.ContainsKey(functionName))
{
Counter.TryAdd(functionName, 1);
}
else
{
Counter[functionName]++;
}
// salvo anche ultima call ad adesso
DateTime adesso = DateTime.Now;
if (!LastCall.ContainsKey(functionName))
{
LastCall.TryAdd(functionName, adesso);
}
else
{
LastCall[functionName] = adesso;
}
}
#endregion Public Methods
#region Private Fields
/// <summary>
/// Dizionario contatori esecuzione
/// </summary>
private static ConcurrentDictionary<string, long> Counter = new ConcurrentDictionary<string, long>();
/// <summary>
/// Dizionario durate esecuzoine
/// </summary>
private static ConcurrentDictionary<string, TimeSpan> Duration = new ConcurrentDictionary<string, TimeSpan>();
/// <summary>
/// Dizionario durate esecuzoine
/// </summary>
private static ConcurrentDictionary<string, DateTime> LastCall = new ConcurrentDictionary<string, DateTime>();
/// <summary>
/// DataOra avvio processo
/// </summary>
private static DateTime StartTime = DateTime.Now;
#endregion Private Fields
#region Private Methods
private static string formElaps(TimeSpan ts)
{
string answ = "";
// formatto secondo durata
if (ts.Milliseconds < 1)
{
answ = $"{ts.TotalMilliseconds:N3} ns";
}
else if (ts.TotalSeconds < 1)
{
answ = $"{ts.TotalMilliseconds:N1} ms";
}
else if (ts.TotalSeconds < 300)
{
answ = $"{ts.TotalSeconds:N1} sec";
}
else
{
answ = $"{ts.TotalMinutes:N1} min";
}
return answ;
}
#endregion Private Methods
}
}