using System.Diagnostics.Metrics;
namespace HSchool.Server.Game;
/// Per-school tick counters surfaced in the Aspire dashboard.
internal sealed class GameMetrics : IDisposable
{
public const string MeterName = "HSchool.Server.Game";
private readonly Meter _meter;
private readonly Counter _ticks;
private readonly Histogram _tickDuration;
private readonly UpDownCounter _connections;
private int _schools;
public GameMetrics(IMeterFactory meterFactory)
{
_meter = meterFactory.Create(MeterName);
_ticks = _meter.CreateCounter("hschool.game.ticks", "{tick}", "Simulation steps executed.");
_tickDuration = _meter.CreateHistogram("hschool.game.tick.duration", "ms", "Wall time of one simulation step.");
_connections = _meter.CreateUpDownCounter("hschool.game.connections", "{connection}", "Open WebSocket connections.");
_meter.CreateObservableGauge("hschool.game.schools", () => Volatile.Read(ref _schools), "{school}", "Schools that currently exist.");
}
public void RecordTick(double durationMs)
{
_ticks.Add(1);
_tickDuration.Record(durationMs);
}
public void ClientConnected() => _connections.Add(1);
public void ClientDisconnected() => _connections.Add(-1);
public void SchoolsChanged(int count) => Volatile.Write(ref _schools, count);
public void Dispose() => _meter.Dispose();
}