using Microsoft.EntityFrameworkCore;

public class GcsService : IGcsService
{
    private readonly AppDbContext _db;

    public GcsService(AppDbContext db) => _db = db;

    public async Task<GcsScore?> GetCurrentAsync(Guid encounterId)
    {
        return await _db.GcsScores
            .AsNoTracking()
            .Where(s => s.EncounterId == encounterId)
            .OrderByDescending(s => s.CalculatedAt)
            .FirstOrDefaultAsync();
    }

    public async Task<CursorPage<GcsScore>> GetHistoryAsync(
        Guid encounterId, int limit, string? cursorToken)
    {
        limit = Math.Clamp(limit, 1, 100);
        var cursor = GcsScoreCursor.Decode(cursorToken);

        var query = _db.GcsScores
            .AsNoTracking()
            .Where(s => s.EncounterId == encounterId);

        if (cursor is not null)
        {
            query = query.Where(s =>
                s.CalculatedAt < cursor.CalculatedAt ||
                (s.CalculatedAt == cursor.CalculatedAt && s.Id.CompareTo(cursor.Id) < 0));
        }

        var items = await query
            .OrderByDescending(s => s.CalculatedAt)
            .ThenByDescending(s => s.Id)
            .Take(limit + 1)
            .ToListAsync();

        var hasMore = items.Count > limit;
        if (hasMore) items.RemoveAt(limit);

        var nextCursor = hasMore
            ? new GcsScoreCursor(items[^1].CalculatedAt, items[^1].Id).Encode()
            : null;

        return new CursorPage<GcsScore>(items, nextCursor, hasMore);
    }
}