
import os
import logging
from typing import Dict, List, Any, Tuple
from dotenv import load_dotenv
from services.tag_service import extract_vendor_tags

load_dotenv()
logger = logging.getLogger(__name__)

PASS_PERCENTAGE = int(os.getenv("PASS_PERCENTAGE", 80))  # Note: typo in .env matches


def _extract_plain_id(value: str) -> str:
    """Extract plain ID from HTML-wrapped ID like <a href='...'>56449211</a>."""
    import re
    if isinstance(value, str) and '<a' in value:
        match = re.search(r'>([^<]+)</a>', value)
        if match:
            return match.group(1).strip()
    return str(value).strip()


def get_microsoft_test_ids(test_cases: List[Dict[str, Any]]) -> set:
    """Get set of Test Case IDs that have #microsoft tag."""
    microsoft_ids = set()
    for tc in test_cases:
        tags = extract_vendor_tags(tc)
        if "#microsoft" in tags:
            tc_id = str(tc.get("id", "")).strip()
            microsoft_ids.add(tc_id)
    return microsoft_ids


def get_microsoft_results(test_results: List[Dict[str, Any]], microsoft_ids: set) -> List[Dict[str, Any]]:
    """Get test results for Microsoft test cases only."""
    import re
    microsoft_results = []
    for r in test_results:
        # Get Test Case ID from result row - may be HTML wrapped
        result_tc_id_raw = str(r.get("Test Case ID", "")).strip()
        
        # Extract plain ID from HTML-wrapped ID like <a href='...'>56449211</a>
        if '<a' in result_tc_id_raw:
            match = re.search(r'>([^<]+)</a>', result_tc_id_raw)
            if match:
                result_tc_id = match.group(1).strip()
            else:
                result_tc_id = result_tc_id_raw
        else:
            result_tc_id = result_tc_id_raw
        
        if result_tc_id in microsoft_ids:
            microsoft_results.append(r)
    return microsoft_results


def calculate_pass_percentage(test_results: List[Dict[str, Any]]) -> float:
    """Calculate pass percentage from test results."""
    if not test_results:
        return 0.0
    
    passed = sum(
        1 for r in test_results 
        if str(r.get("Status", r.get("status", ""))).lower() == "passed"
    )
    total = len(test_results)
    percent = (passed / total * 100) if total > 0 else 0.0
    return percent


def should_send_client_email(microsoft_results: List[Dict[str, Any]]) -> bool:
    """Check if Microsoft test pass% meets threshold."""
    pass_percent = calculate_pass_percentage(microsoft_results)
    should_send = pass_percent >= PASS_PERCENTAGE
    return should_send


def prepare_client_report(
    test_results: List[Dict[str, Any]],
    all_test_cases: List[Dict[str, Any]],
    detailed_report: Dict[str, Any],
    summary_data: Dict[str, Any],
    test_summary: Dict[str, Any]
) -> Tuple[bool, Dict[str, Any]]:
    
    # Get Microsoft test case IDs
    microsoft_ids = get_microsoft_test_ids(all_test_cases)
    
    # Get Microsoft test results only
    microsoft_results = get_microsoft_results(test_results, microsoft_ids)
    
    # Check if should send
    should_send = should_send_client_email(microsoft_results)
    
    # Filter test cases to Microsoft only
    client_test_cases = [
        tc for tc in all_test_cases 
        if str(tc.get("id", "")).strip() in microsoft_ids
    ]
    
    # Filter detailed report: only Microsoft rows, no HCL column
    client_detailed_report = {
        "columns": [
            col for col in detailed_report.get("columns", [])
            if col.lower() != "hcltech ado id"
        ],
        "rows": [
            {k: v for k, v in row.items() if k != "HCLTech ADO ID"}
            for row in detailed_report.get("rows", [])
            if _extract_plain_id(str(row.get("Test Case ID", ""))) in microsoft_ids
        ]
    }
    
    # Calculate summary for Microsoft results
    total_microsoft = len(microsoft_results)
    passed_microsoft = sum(1 for r in microsoft_results if str(r.get("Status", "")).lower() == "passed")
    failed_microsoft = total_microsoft - passed_microsoft
    pass_percent_microsoft = (passed_microsoft / total_microsoft * 100) if total_microsoft > 0 else 0.0
    
    client_summary = {
        "Total": total_microsoft,
        "Passed": passed_microsoft,
        "Failed": failed_microsoft,
        "Pass %": f"{int(pass_percent_microsoft)}%"
    }
    
    client_report_data = {
        "test_cases": client_test_cases,
        "detailed_report": client_detailed_report,
        "summary_data": {
            **summary_data, 
            "Total Steps": total_microsoft,
            "Total Steps Passed": passed_microsoft,
            "Total Steps Failed": failed_microsoft
        },
        "test_summary": {
            "columns": test_summary.get("columns", []),
            "values": [
                total_microsoft,
                passed_microsoft,
                failed_microsoft,
                0,  # Skipped
                client_summary.get("Pass %", "0%")
            ]
        }
    }
    
    return should_send, client_report_data


def prepare_internal_report(
    test_results: List[Dict[str, Any]],
    all_test_cases: List[Dict[str, Any]],
    detailed_report: Dict[str, Any],
    summary_data: Dict[str, Any],
    test_summary: Dict[str, Any]
) -> Dict[str, Any]:

    # Internal report has no filtering, use original data as-is
    internal_report_data = {
        "test_cases": all_test_cases,
        "detailed_report": detailed_report,
        "summary_data": summary_data,
        "test_summary": test_summary
    }
    
    return internal_report_data


__all__ = [
    "filter_test_cases_for_client",
    "calculate_pass_percentage",
    "should_send_client_email",
    "filter_detailed_report_for_client",
    "filter_summary_for_client",
    "prepare_client_report",
    "prepare_internal_report",
]
