51 lines
1.6 KiB
C#
51 lines
1.6 KiB
C#
using OpenHarbor.CQRS.Abstractions;
|
|
using System.Diagnostics;
|
|
using Microsoft.EntityFrameworkCore;
|
|
using Microsoft.Extensions.Caching.Memory;
|
|
using CH.Dal;
|
|
namespace CH.CQRS.Query.Health;
|
|
public class HealthQuery
|
|
{
|
|
|
|
}
|
|
public class HealthQueryHandler(CHDbContext dbContext, IMemoryCache memoryCache) : IQueryHandler<HealthQuery, HealthQueryResult>
|
|
{
|
|
private const string HealthCheckCacheKey = "HealthStatus";
|
|
private const int CacheDurationInSeconds = 60;
|
|
public async Task<HealthQueryResult> HandleAsync(HealthQuery query, CancellationToken cancellationToken = new CancellationToken())
|
|
{
|
|
if (memoryCache.TryGetValue(HealthCheckCacheKey, out var memory))
|
|
{
|
|
return (HealthQueryResult)memory;
|
|
}
|
|
var (databaseStatus, databaseLatency) = await MeasureLatencyAsync(CheckDatabaseHealthAsync);
|
|
|
|
var healthCheckResult = new HealthQueryResult
|
|
{
|
|
ApiStatus = true,
|
|
DatabaseStatus = databaseStatus,
|
|
DatabaseLatency = $"{databaseLatency}ms",
|
|
};
|
|
memoryCache.Set(HealthCheckCacheKey, healthCheckResult, TimeSpan.FromSeconds(CacheDurationInSeconds));
|
|
return healthCheckResult;
|
|
}
|
|
public static async Task<(bool isHealthy, long latencyMs)> MeasureLatencyAsync(Func<Task<bool>> healthCheckAction)
|
|
{
|
|
var stopwatch = Stopwatch.StartNew();
|
|
var isHealthy = await healthCheckAction();
|
|
stopwatch.Stop();
|
|
return (isHealthy, stopwatch.ElapsedMilliseconds);
|
|
}
|
|
private async Task<bool> CheckDatabaseHealthAsync()
|
|
{
|
|
try
|
|
{
|
|
await dbContext.Database.ExecuteSqlRawAsync("SELECT 1");
|
|
return true;
|
|
}
|
|
catch
|
|
{
|
|
return false;
|
|
}
|
|
}
|
|
} |