namespace ConfigurationPannel.Services;

public class LogoService
{
    private readonly IWebHostEnvironment _env;
    private readonly string _logosPath;
    private readonly ILogger<LogoService> _logger;

    public LogoService(IWebHostEnvironment env, ILogger<LogoService> logger)
    {
        _env = env;
        _logger = logger;
        _logosPath = Path.Combine(_env.WebRootPath, "logos");

        // Ensure logos directory exists
        if (!Directory.Exists(_logosPath))
        {
            Directory.CreateDirectory(_logosPath);
        }
    }

    public async Task<string> SaveLogoAsync(IFormFile file)
    {
        if (file == null || file.Length == 0)
            throw new ArgumentException("No file provided");

        // Validate file type
        var allowedExtensions = new[] { ".png", ".jpg", ".jpeg", ".gif", ".bmp" };
        var extension = Path.GetExtension(file.FileName).ToLowerInvariant();

        if (!allowedExtensions.Contains(extension))
            throw new ArgumentException($"Invalid file type. Allowed: {string.Join(", ", allowedExtensions)}");

        // Generate unique filename to avoid collisions
        var fileName = $"{Path.GetFileNameWithoutExtension(file.FileName)}_{Guid.NewGuid().ToString("N").Substring(0, 8)}{extension}";
        var filePath = Path.Combine(_logosPath, fileName);

        using (var stream = new FileStream(filePath, FileMode.Create))
        {
            await file.CopyToAsync(stream);
        }

        _logger.LogInformation("Logo uploaded: {FileName}", fileName);
        return fileName;
    }

    public List<string> GetAllLogos()
    {
        if (!Directory.Exists(_logosPath))
            return new List<string>();

        return Directory.GetFiles(_logosPath)
            .Select(Path.GetFileName)
            .Where(f => f != null)
            .Select(f => f!)
            .OrderBy(f => f)
            .ToList();
    }

    public string GetLogoUrl(string? filename)
    {
        if (string.IsNullOrEmpty(filename))
            return string.Empty;

        return $"/logos/{filename}";
    }

    public bool LogoExists(string filename)
    {
        return File.Exists(Path.Combine(_logosPath, filename));
    }

    public void DeleteLogo(string filename)
    {
        var filePath = Path.Combine(_logosPath, filename);
        if (File.Exists(filePath))
        {
            File.Delete(filePath);
            _logger.LogInformation("Logo deleted: {FileName}", filename);
        }
    }

    public List<string> CleanUnusedLogos(IEnumerable<string> usedLogoFilenames)
    {
        var allLogos = GetAllLogos();
        var usedSet = new HashSet<string>(usedLogoFilenames.Where(f => !string.IsNullOrEmpty(f))!);
        var unusedLogos = allLogos.Where(logo => !usedSet.Contains(logo)).ToList();

        foreach (var logo in unusedLogos)
        {
            DeleteLogo(logo);
        }

        _logger.LogInformation("Cleaned {Count} unused logos", unusedLogos.Count);
        return unusedLogos;
    }

    public void CopyLogoToDirectory(string filename, string targetDirectory)
    {
        if (string.IsNullOrEmpty(filename))
            return;

        var sourcePath = Path.Combine(_logosPath, filename);
        if (!File.Exists(sourcePath))
        {
            _logger.LogWarning("Logo file not found for copy: {FileName}", filename);
            return;
        }

        if (!Directory.Exists(targetDirectory))
        {
            Directory.CreateDirectory(targetDirectory);
        }

        var targetPath = Path.Combine(targetDirectory, filename);
        File.Copy(sourcePath, targetPath, overwrite: true);
        _logger.LogInformation("Logo copied to: {TargetPath}", targetPath);
    }
}
