using System.Net.Http;
using System.Text.RegularExpressions;

namespace AxCopilot.Services;

/// <summary>
/// Phase L3-2: 웹 페이지 콘텐츠 추출기.
/// HTML을 가져와 태그를 제거하고 핵심 본문 텍스트를 반환합니다.
/// 사내 모드에서는 사용 불가 (외부 HTTP 차단).
/// </summary>
public static class ContentExtractor
{
    private static readonly HttpClient _client = new()
    {
        Timeout = TimeSpan.FromSeconds(10),
        DefaultRequestHeaders = { { "User-Agent", "Mozilla/5.0 (compatible; AXCopilot/1.0)" } }
    };

    // 제거 대상 태그 (script, style, nav, header, footer, aside)
    private static readonly Regex ScriptStyle = new(
        @"<(script|style|nav|header|footer|aside|noscript)[^>]*>[\s\S]*?</\1>",
        RegexOptions.IgnoreCase | RegexOptions.Compiled);

    private static readonly Regex HtmlTags = new(@"<[^>]+>", RegexOptions.Compiled);
    private static readonly Regex MultiWhitespace = new(@"\s{2,}", RegexOptions.Compiled);
    private static readonly Regex HtmlEntities = new(@"&(?:amp|lt|gt|quot|nbsp|#\d+);", RegexOptions.Compiled);

    /// <summary>URL에서 웹 페이지를 가져와 정제된 텍스트를 반환합니다.</summary>
    public static async Task<string> ExtractAsync(string url, int maxChars = 3000, CancellationToken ct = default)
    {
        try
        {
            var html = await _client.GetStringAsync(url, ct);
            return ExtractTextFromHtml(html, maxChars);
        }
        catch (Exception ex)
        {
            return $"[콘텐츠 추출 실패: {ex.Message}]";
        }
    }

    /// <summary>HTML 문자열에서 텍스트를 추출합니다.</summary>
    public static string ExtractTextFromHtml(string html, int maxChars = 3000)
    {
        // script/style/nav 제거
        var text = ScriptStyle.Replace(html, " ");

        // HTML 태그 제거
        text = HtmlTags.Replace(text, " ");

        // HTML 엔터티 변환
        text = HtmlEntities.Replace(text, m => m.Value switch
        {
            "&amp;"  => "&",
            "&lt;"   => "<",
            "&gt;"   => ">",
            "&quot;" => "\"",
            "&nbsp;" => " ",
            _        => " "
        });

        // 연속 공백 정리
        text = MultiWhitespace.Replace(text, " ").Trim();

        // 최대 길이 제한
        return text.Length > maxChars ? text[..maxChars] + "…" : text;
    }
}
