"""
E2E tests for version differentiation between free and pro builds.

These tests verify that Blender can recognize pro as an upgrade over free
by checking that built packages have different version tuples and edition indicators.

Tests informed by DEBUG investigation:
- Root cause: Both versions have identical bl_info["version"] tuples: (1, 0, 0)
- Both use same folder name: text_texture_generator/
- No edition indicator in bl_info["name"]
- Result: Blender sees them as identical, not as an upgrade
"""

import ast
import subprocess
import tempfile
import zipfile
from pathlib import Path

import pytest


@pytest.fixture
def build_artifacts(tmp_path):
    """Build both free and pro packages and return their paths."""
    project_root = Path(__file__).parent.parent.parent
    
    # Run build script to create both packages
    result = subprocess.run(
        ["python", "scripts/build_addon.py", "--type", "all"],
        cwd=project_root,
        capture_output=True,
        text=True,
        timeout=30
    )
    
    if result.returncode != 0:
        pytest.fail(f"Build script failed: {result.stderr}")
    
    # Find the generated ZIP files in dist/
    dist_dir = project_root / "dist"
    
    # Get version from git or default to 1.0.0
    free_zip = None
    pro_zip = None
    
    for zip_file in dist_dir.glob("text_texture_generator_v*.zip"):
        if "_free.zip" in zip_file.name:
            free_zip = zip_file
        else:
            pro_zip = zip_file
    
    if not free_zip or not free_zip.exists():
        pytest.fail(f"Free build not found in {dist_dir}")
    if not pro_zip or not pro_zip.exists():
        pytest.fail(f"Pro build not found in {dist_dir}")
    
    yield {
        "free_zip": free_zip,
        "pro_zip": pro_zip,
        "extract_dir": tmp_path / "extracted"
    }
    
    # Note: Build artifacts are in dist/ - not cleaned up here
    # They may be needed for other tests or deployment


def extract_bl_info(zip_path: Path, extract_dir: Path) -> dict:
    """Extract bl_info dictionary from addon package using ast.literal_eval()."""
    edition = "free" if "_free" in zip_path.name else "pro"
    extract_path = extract_dir / edition
    extract_path.mkdir(parents=True, exist_ok=True)
    
    with zipfile.ZipFile(zip_path, 'r') as zip_ref:
        zip_ref.extractall(extract_path)
    
    # Find __init__.py in the extracted addon
    init_file = extract_path / "text_texture_generator" / "__init__.py"
    if not init_file.exists():
        pytest.fail(f"__init__.py not found in {zip_path.name}")
    
    # Parse bl_info using ast.literal_eval() (Blender's method)
    content = init_file.read_text()
    
    # Extract bl_info dictionary exactly as Blender does
    tree = ast.parse(content)
    for node in ast.walk(tree):
        if isinstance(node, ast.Assign):
            for target in node.targets:
                if isinstance(target, ast.Name) and target.id == "bl_info":
                    return ast.literal_eval(node.value)
    
    pytest.fail(f"bl_info not found in {init_file}")


def test_built_packages_have_different_version_tuples(build_artifacts):
    """
    Test that free and pro builds have different version tuples.
    
    Blender identifies addons by (name, version) tuple. If both free and pro
    have the same version, Blender won't recognize pro as an upgrade.
    
    This test is informed by DEBUG investigation showing both versions have
    identical version tuples: (1, 0, 0), causing Blender to see them as the
    same addon rather than an upgrade path.
    
    Expected to FAIL because currently both are (1, 0, 0).
    """
    free_bl_info = extract_bl_info(
        build_artifacts["free_zip"],
        build_artifacts["extract_dir"]
    )
    pro_bl_info = extract_bl_info(
        build_artifacts["pro_zip"],
        build_artifacts["extract_dir"]
    )
    
    free_version = free_bl_info["version"]
    pro_version = pro_bl_info["version"]
    
    assert free_version != pro_version, (
        f"Free and Pro versions must have different version tuples for Blender "
        f"to recognize upgrade. Expected different, got both: {free_version}"
    )


def test_bl_info_name_includes_edition_indicator(build_artifacts):
    """
    Test that bl_info names include edition indicators (Free/Pro).
    
    Users need to clearly see which edition they have installed in Blender's
    addon preferences. The bl_info["name"] should include "Free" or "Pro".
    
    This test is informed by DEBUG investigation showing both versions use the
    same name "Text Texture Generator" with no edition indicator, making it
    impossible for users to distinguish them in Blender's UI.
    
    Expected to FAIL because currently both just say "Text Texture Generator".
    """
    free_bl_info = extract_bl_info(
        build_artifacts["free_zip"],
        build_artifacts["extract_dir"]
    )
    pro_bl_info = extract_bl_info(
        build_artifacts["pro_zip"],
        build_artifacts["extract_dir"]
    )
    
    free_name = free_bl_info["name"]
    pro_name = pro_bl_info["name"]
    
    # Assert Free version has edition indicator
    assert "Free" in free_name, (
        f"bl_info name must indicate Free edition. "
        f"Expected 'Free' in name, got: '{free_name}'"
    )
    
    # Assert Pro version has edition indicator
    assert "Pro" in pro_name, (
        f"bl_info name must indicate Pro edition. "
        f"Expected 'Pro' in name, got: '{pro_name}'"
    )
    
    # Assert they are different
    assert free_name != pro_name, (
        f"bl_info name must indicate edition. "
        f"Free: '{free_name}', Pro: '{pro_name}'"
    )