using Microsoft.Extensions.Logging;
using PARR.Core.Services.Shortcodes.Enums;
using PARR.Core.Services.Shortcodes.Models;
using System.Text.RegularExpressions;

namespace PARR.Core.Services.Shortcodes.Handlers;

internal class TagShortcodeHandler : IShortcodeHandler
{
    private readonly ILogger<TagShortcodeHandler> logger;

    public int Order => 70;

    private static readonly Regex _pattern = new(@"%ТЕГ:([^%]+)%", RegexOptions.Compiled | RegexOptions.IgnoreCase);
    public Regex Pattern => _pattern;

    public ShortcodeDataRequirementsEnum Requirements => ShortcodeDataRequirementsEnum.UnitTags;

    public TagShortcodeHandler(ILogger<TagShortcodeHandler> logger)
    {
        this.logger = logger;
    }

    public Task<string> ResolveAsync(string input, TemplateForShortcode data, string caller, CancellationToken ct = default)
    {
        var matches = Pattern.Matches(input);
        if (matches.Count == 0) return Task.FromResult(input);

        var uniqueTags = matches.Cast<Match>()
            .Select(m => m.Groups[1].Value.Trim())
            .Distinct(StringComparer.OrdinalIgnoreCase)
            .ToList();

        var resolved = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
        foreach (var tagName in uniqueTags)
        {
            resolved[$"%ТЕГ:{tagName}%"] = GetTagValue(data.UnitTags, tagName, caller);
        }

        var result = input;
        foreach (Match m in matches)
        {
            if (resolved.TryGetValue(m.Value, out var val))
            {
                result = result.Replace(m.Value, val, StringComparison.OrdinalIgnoreCase);
            }
        }

        return Task.FromResult(result);
    }

    private string GetTagValue(List<string>? unitTags, string tagName, string caller)
    {
        if (unitTags == null || unitTags.Count == 0)
        {
            return string.Empty;
        }

        var prefix = tagName + ":";
        // Ищем тег, который начинается с префикса и двоеточия (например, "БД_в_ЗО_РГ:")
        var matchedTag = unitTags.FirstOrDefault(t => t.StartsWith(prefix, StringComparison.OrdinalIgnoreCase));

        if (matchedTag != null)
        {
            // Возвращаем часть строки после двоеточия
            return matchedTag.Substring(prefix.Length);
        }

        // Резервный вариант: если тег совпадает полностью без двоеточия
        var exactTag = unitTags.FirstOrDefault(t => t.Equals(tagName, StringComparison.OrdinalIgnoreCase));
        if (exactTag != null)
        {
            return exactTag;
        }

        logger.LogDebug("[{Caller}] Тег с префиксом '{Prefix}' не найден в UnitTags.", caller, prefix);
        return string.Empty;
    }
}