using Meezi.API.Models.Public;
using Meezi.Core.Entities;
using Meezi.Infrastructure.Data;
using Microsoft.EntityFrameworkCore;

namespace Meezi.API.Services;

public class PushDeviceService : IPushDeviceService
{
    private readonly AppDbContext _db;

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

    public async Task RegisterAsync(RegisterPushDeviceRequest request, CancellationToken ct = default)
    {
        if (string.IsNullOrWhiteSpace(request.Token)) return;

        var existing = await _db.PushDevices
            .FirstOrDefaultAsync(d => d.Token == request.Token, ct);

        if (existing is null)
        {
            _db.PushDevices.Add(new PushDevice
            {
                Token = request.Token,
                Platform = string.IsNullOrWhiteSpace(request.Platform) ? "android" : request.Platform,
                City = request.City,
                ConsumerAccountId = request.ConsumerAccountId,
                LastSeenAt = DateTime.UtcNow,
            });
        }
        else
        {
            existing.City = request.City ?? existing.City;
            existing.ConsumerAccountId = request.ConsumerAccountId ?? existing.ConsumerAccountId;
            existing.LastSeenAt = DateTime.UtcNow;
            existing.DeletedAt = null; // re-activate if it was previously removed
        }

        await _db.SaveChangesAsync(ct);
    }

    public async Task UnregisterAsync(string token, CancellationToken ct = default)
    {
        if (string.IsNullOrWhiteSpace(token)) return;

        var device = await _db.PushDevices.FirstOrDefaultAsync(d => d.Token == token, ct);
        if (device is null) return;

        device.DeletedAt = DateTime.UtcNow;
        await _db.SaveChangesAsync(ct);
    }

    public async Task<IReadOnlyList<string>> GetTokensForConsumerAsync(
        string consumerAccountId, CancellationToken ct = default)
    {
        if (string.IsNullOrWhiteSpace(consumerAccountId)) return [];

        return await _db.PushDevices
            .Where(d => d.ConsumerAccountId == consumerAccountId)
            .Select(d => d.Token)
            .ToListAsync(ct);
    }
}
