"""
Compatibility Generator - Cross-Version Support for Anvil Development

This module provides version-agnostic code generation that works across
different Anvil versions, with fallback patterns and progressive enhancement.
"""

from typing import Dict, List, Optional, Any, Union, Tuple
from dataclasses import dataclass, field
from pathlib import Path
import logging
import re

from ..responses.response_builder import ResponseBuilder
from ..errors.hephaestus_errors import GenerationError


@dataclass
class VersionCompatibilityConfig:
    """Configuration for version compatibility generation."""

    target_versions: List[str] = field(
        default_factory=lambda: ["1.0", "1.2", "1.3", "1.4", "1.5"]
    )
    fallback_strategy: str = "graceful"  # graceful, strict, progressive
    enable_progressive_enhancement: bool = True
    compatibility_level: str = "broad"  # broad, moderate, strict
    feature_detection: bool = True


@dataclass
class VersionFeature:
    """Represents a feature available in specific Anvil versions."""

    name: str
    min_version: str
    max_version: Optional[str] = None
    fallback_alternative: Optional[str] = None
    description: str = ""
    deprecated_in: Optional[str] = None


@dataclass
class CompatibilityMatrix:
    """Matrix for tracking feature compatibility across versions."""

    features: List[VersionFeature] = field(default_factory=list)
    version_support: Dict[str, List[str]] = field(default_factory=dict)
    fallback_mappings: Dict[str, str] = field(default_factory=dict)


class CompatibilityGenerator:
    """
    Cross-version code generator for Anvil development.

    This generator creates code that works across multiple Anvil versions,
    with intelligent fallbacks and progressive enhancement capabilities.
    """

    def __init__(self, project_path: Union[str, Path]):
        self.project_path = Path(project_path)
        self.logger = logging.getLogger(__name__)
        self.response_builder = ResponseBuilder()

        # Initialize compatibility matrix
        self.compatibility_matrix = self._build_compatibility_matrix()

        # Version detection cache
        self._version_cache: Dict[str, str] = {}

    def generate_compatible_component(
        self,
        component_name: str,
        component_type: str,
        properties: Dict[str, Any],
        config: Optional[VersionCompatibilityConfig] = None,
    ) -> Dict[str, Any]:
        """
        Generate a component that's compatible across multiple Anvil versions.

        Args:
            component_name: Name of the component to generate
            component_type: Type of component (form, custom_component, etc.)
            properties: Component properties and configuration
            config: Compatibility configuration

        Returns:
            Generated component with cross-version compatibility
        """
        try:
            if config is None:
                config = VersionCompatibilityConfig()

            # Detect target Anvil version
            target_version = self._detect_anvil_version()

            # Analyze required features
            required_features = self._analyze_required_features(
                component_type, properties
            )

            # Generate version-compatible code
            component_def = self._generate_version_aware_component(
                component_name,
                component_type,
                properties,
                required_features,
                target_version,
                config,
            )

            # Add progressive enhancement if enabled
            if config.enable_progressive_enhancement:
                component_def = self._add_progressive_enhancement(
                    component_def, required_features, config
                )

            # Validate compatibility
            compatibility_report = self._validate_compatibility(
                component_def, config.target_versions
            )

            return self.response_builder.success_response(
                data=component_def,
                message=f"Generated compatible component: {component_name}",
                metadata={
                    "target_version": target_version,
                    "compatibility_report": compatibility_report,
                    "features_used": required_features,
                    "progressive_enhancement": config.enable_progressive_enhancement,
                },
            )

        except Exception as e:
            self.logger.error(
                f"Error generating compatible component {component_name}: {e}"
            )
            raise GenerationError(f"Failed to generate compatible component: {e}")

    def create_version_migration_plan(
        self,
        current_version: str,
        target_version: str,
        components: List[str],
        config: Optional[VersionCompatibilityConfig] = None,
    ) -> Dict[str, Any]:
        """
        Create a migration plan between Anvil versions.

        Args:
            current_version: Current Anvil version
            target_version: Target Anvil version
            components: List of components to migrate
            config: Compatibility configuration

        Returns:
            Migration plan with step-by-step instructions
        """
        try:
            if config is None:
                config = VersionCompatibilityConfig()

            # Analyze version differences
            version_diff = self._analyze_version_differences(
                current_version, target_version
            )

            # Create migration steps
            migration_steps = self._create_migration_steps(
                components, version_diff, config
            )

            # Generate compatibility matrix
            compatibility_matrix = self._generate_migration_matrix(
                current_version, target_version, components
            )

            # Create rollback plan
            rollback_plan = self._create_rollback_plan(
                current_version, target_version, components
            )

            migration_plan = {
                "current_version": current_version,
                "target_version": target_version,
                "components": components,
                "version_differences": version_diff,
                "migration_steps": migration_steps,
                "compatibility_matrix": compatibility_matrix,
                "rollback_plan": rollback_plan,
                "estimated_effort": self._estimate_migration_effort(
                    components, version_diff
                ),
                "breaking_changes": self._identify_breaking_changes(version_diff),
                "new_features": self._identify_new_features(version_diff),
            }

            return self.response_builder.success_response(
                data=migration_plan,
                message=f"Created migration plan: {current_version} → {target_version}",
                metadata={
                    "steps_count": len(migration_steps),
                    "breaking_changes_count": len(migration_plan["breaking_changes"]),
                    "new_features_count": len(migration_plan["new_features"]),
                },
            )

        except Exception as e:
            self.logger.error(f"Error creating migration plan: {e}")
            raise GenerationError(f"Failed to create migration plan: {e}")

    def generate_fallback_component(
        self,
        component_name: str,
        component_type: str,
        properties: Dict[str, Any],
        unsupported_features: List[str],
        config: Optional[VersionCompatibilityConfig] = None,
    ) -> Dict[str, Any]:
        """
        Generate a component with fallbacks for unsupported features.

        Args:
            component_name: Name of the component
            component_type: Type of component
            properties: Component properties
            unsupported_features: List of features not supported in target version
            config: Compatibility configuration

        Returns:
            Component with fallback implementations
        """
        try:
            if config is None:
                config = VersionCompatibilityConfig()

            # Generate base component
            component_def = self._generate_base_component(
                component_name, component_type, properties
            )

            # Add fallback implementations
            fallbacks = self._generate_fallback_implementations(
                unsupported_features, config
            )

            # Add feature detection code
            feature_detection = self._generate_feature_detection(
                unsupported_features, config
            )

            # Combine everything
            compatible_component = {
                **component_def,
                "fallbacks": fallbacks,
                "feature_detection": feature_detection,
                "compatibility_mode": config.fallback_strategy,
                "unsupported_features": unsupported_features,
            }

            return self.response_builder.success_response(
                data=compatible_component,
                message=f"Generated fallback component: {component_name}",
                metadata={
                    "fallbacks_count": len(fallbacks),
                    "unsupported_features_count": len(unsupported_features),
                    "fallback_strategy": config.fallback_strategy,
                },
            )

        except Exception as e:
            self.logger.error(
                f"Error generating fallback component {component_name}: {e}"
            )
            raise GenerationError(f"Failed to generate fallback component: {e}")

    def _build_compatibility_matrix(self) -> CompatibilityMatrix:
        """Build the comprehensive compatibility matrix."""
        features = [
            VersionFeature(
                name="material_3_components",
                min_version="1.4",
                description="Material Design 3 components",
                fallback_alternative="classic_components",
            ),
            VersionFeature(
                name="official_routing",
                min_version="1.3",
                description="Official Anvil routing",
                fallback_alternative="hash_routing",
            ),
            VersionFeature(
                name="reactive_library",
                min_version="1.2",
                description="Reactive state management",
                fallback_alternative="manual_state_management",
            ),
            VersionFeature(
                name="model_classes",
                min_version="1.3",
                description="Type-safe model classes",
                fallback_alternative="data_tables",
            ),
            VersionFeature(
                name="layout_system",
                min_version="1.4",
                description="Modern slot-based layouts",
                fallback_alternative="panel_layouts",
            ),
            VersionFeature(
                name="tabulator_integration",
                min_version="1.3",
                description="Advanced data tables",
                fallback_alternative="data_grid",
            ),
            VersionFeature(
                name="theme_system",
                min_version="1.0",
                description="Theme and styling system",
                fallback_alternative="inline_styles",
            ),
            VersionFeature(
                name="form_validation",
                min_version="1.1",
                description="Built-in form validation",
                fallback_alternative="manual_validation",
            ),
        ]

        # Build version support mapping
        version_support = {}
        for version in ["1.0", "1.1", "1.2", "1.3", "1.4", "1.5"]:
            supported_features = []
            for feature in features:
                if self._version_compare(version, feature.min_version) >= 0:
                    if (
                        feature.max_version is None
                        or self._version_compare(version, feature.max_version) <= 0
                    ):
                        supported_features.append(feature.name)
            version_support[version] = supported_features

        # Build fallback mappings
        fallback_mappings = {}
        for feature in features:
            if feature.fallback_alternative:
                fallback_mappings[feature.name] = feature.fallback_alternative

        return CompatibilityMatrix(
            features=features,
            version_support=version_support,
            fallback_mappings=fallback_mappings,
        )

    def _detect_anvil_version(self) -> str:
        """Detect the Anvil version of the current project."""
        cache_key = str(self.project_path)
        if cache_key in self._version_cache:
            return self._version_cache[cache_key]

        try:
            # Check for version in various files
            version_files = [
                "anvil.yaml",
                "anvil.json",
                "requirements.txt",
                "pyproject.toml",
            ]

            for filename in version_files:
                file_path = self.project_path / filename
                if file_path.exists():
                    version = self._extract_version_from_file(file_path)
                    if version:
                        self._version_cache[cache_key] = version
                        return version

            # Default to latest if no version found
            default_version = "1.5"
            self._version_cache[cache_key] = default_version
            return default_version

        except Exception as e:
            self.logger.warning(f"Error detecting Anvil version: {e}")
            default_version = "1.5"
            self._version_cache[cache_key] = default_version
            return default_version

    def _extract_version_from_file(self, file_path: Path) -> Optional[str]:
        """Extract version information from a file."""
        try:
            content = file_path.read_text(encoding="utf-8")

            # Look for version patterns
            version_patterns = [
                r'anvil:\s*["\']?(\d+\.\d+)["\']?',
                r'version["\']?\s*[:=]\s*["\']?(\d+\.\d+)["\']?',
                r'anvil[>=<]*["\']?(\d+\.\d+)["\']?',
            ]

            for pattern in version_patterns:
                match = re.search(pattern, content, re.IGNORECASE)
                if match:
                    return match.group(1)

            return None

        except Exception:
            return None

    def _analyze_required_features(
        self, component_type: str, properties: Dict[str, Any]
    ) -> List[str]:
        """Analyze which features are required for the component."""
        required_features = []

        # Check for Material 3 components
        if any("role" in str(prop).lower() for prop in properties.values()):
            required_features.append("material_3_components")

        # Check for routing features
        if "routing" in str(properties).lower():
            required_features.append("official_routing")

        # Check for reactive features
        if any("reactive" in str(prop).lower() for prop in properties.values()):
            required_features.append("reactive_library")

        # Check for model features
        if any("model" in str(prop).lower() for prop in properties.values()):
            required_features.append("model_classes")

        # Check for layout features
        if "layout" in str(component_type).lower():
            required_features.append("layout_system")

        # Check for data table features
        if (
            "table" in str(component_type).lower()
            or "grid" in str(component_type).lower()
        ):
            required_features.append("tabulator_integration")

        # Check for theme features
        if any("theme" in str(prop).lower() for prop in properties.values()):
            required_features.append("theme_system")

        # Check for validation features
        if "validation" in str(properties).lower():
            required_features.append("form_validation")

        return required_features

    def _generate_version_aware_component(
        self,
        component_name: str,
        component_type: str,
        properties: Dict[str, Any],
        required_features: List[str],
        target_version: str,
        config: VersionCompatibilityConfig,
    ) -> Dict[str, Any]:
        """Generate a component aware of version constraints."""

        # Filter properties based on version compatibility
        compatible_properties = self._filter_properties_by_version(
            properties, required_features, target_version
        )

        # Generate base component structure
        component_def = {
            "name": component_name,
            "type": component_type,
            "properties": compatible_properties,
            "version": target_version,
            "compatibility_features": [],
        }

        # Add version-specific code
        for feature in required_features:
            if self._is_feature_supported(feature, target_version):
                component_def["compatibility_features"].append(
                    {"feature": feature, "supported": True, "implementation": "native"}
                )
            else:
                fallback = self._get_fallback_for_feature(feature)
                component_def["compatibility_features"].append(
                    {
                        "feature": feature,
                        "supported": False,
                        "fallback": fallback,
                        "implementation": "fallback",
                    }
                )

        return component_def

    def _filter_properties_by_version(
        self,
        properties: Dict[str, Any],
        required_features: List[str],
        target_version: str,
    ) -> Dict[str, Any]:
        """Filter properties based on version compatibility."""
        filtered_properties = {}

        for key, value in properties.items():
            # Check if property requires unsupported features
            property_features = self._analyze_property_features(key, value)

            if all(
                self._is_feature_supported(f, target_version) for f in property_features
            ):
                filtered_properties[key] = value
            else:
                # Add version comment
                filtered_properties[f"{key}_v{target_version}_fallback"] = value

        return filtered_properties

    def _analyze_property_features(self, key: str, value: Any) -> List[str]:
        """Analyze what features a property requires."""
        features = []
        value_str = str(value).lower()

        if "role" in key.lower() and "material" in value_str:
            features.append("material_3_components")

        if "reactive" in value_str:
            features.append("reactive_library")

        if "model" in value_str:
            features.append("model_classes")

        return features

    def _is_feature_supported(self, feature: str, version: str) -> bool:
        """Check if a feature is supported in a given version."""
        if feature not in self.compatibility_matrix.fallback_mappings:
            return True  # No version constraint

        # Find the feature definition
        for feat in self.compatibility_matrix.features:
            if feat.name == feature:
                return self._version_compare(version, feat.min_version) >= 0

        return False

    def _get_fallback_for_feature(self, feature: str) -> Optional[str]:
        """Get the fallback implementation for a feature."""
        return self.compatibility_matrix.fallback_mappings.get(feature)

    def _add_progressive_enhancement(
        self,
        component_def: Dict[str, Any],
        required_features: List[str],
        config: VersionCompatibilityConfig,
    ) -> Dict[str, Any]:
        """Add progressive enhancement capabilities to the component."""

        enhancement_code = []

        for feature in required_features:
            if not self._is_feature_supported(feature, "1.0"):
                # Add feature detection and progressive loading
                detection_code = self._generate_feature_detection_code(feature)
                enhancement_code.append(detection_code)

        component_def["progressive_enhancement"] = {
            "enabled": True,
            "code": enhancement_code,
            "features": required_features,
        }

        return component_def

    def _generate_feature_detection_code(self, feature: str) -> str:
        """Generate code to detect feature availability."""
        feature_checks = {
            "material_3_components": "typeof anvil.Material !== 'undefined'",
            "official_routing": "typeof anvil.routing !== 'undefined'",
            "reactive_library": "typeof anvil.reactive !== 'undefined'",
            "model_classes": "typeof anvil.server.model_class !== 'undefined'",
            "layout_system": "typeof anvil.Layout !== 'undefined'",
            "tabulator_integration": "typeof anvil.Tabulator !== 'undefined'",
            "theme_system": "typeof anvil.Theme !== 'undefined'",
            "form_validation": "typeof anvil.Form !== 'undefined'",
        }

        check = feature_checks.get(feature, "true")
        return f"if ({check}) {{ /* {feature} available */ }}"

    def _validate_compatibility(
        self, component_def: Dict[str, Any], target_versions: List[str]
    ) -> Dict[str, Any]:
        """Validate component compatibility across target versions."""

        compatibility_report = {
            "compatible_versions": [],
            "incompatible_versions": [],
            "fallback_required": [],
            "issues": [],
        }

        for version in target_versions:
            version_issues = []

            # Check each feature
            for feature_info in component_def.get("compatibility_features", []):
                feature = feature_info["feature"]
                if not feature_info["supported"]:
                    if feature_info.get("fallback"):
                        compatibility_report["fallback_required"].append(
                            {
                                "version": version,
                                "feature": feature,
                                "fallback": feature_info["fallback"],
                            }
                        )
                    else:
                        version_issues.append(f"Feature {feature} not supported")

            if version_issues:
                compatibility_report["incompatible_versions"].append(
                    {"version": version, "issues": version_issues}
                )
                compatibility_report["issues"].extend(version_issues)
            else:
                compatibility_report["compatible_versions"].append(version)

        return compatibility_report

    def _version_compare(self, version1: str, version2: str) -> int:
        """Compare two version strings."""
        v1_parts = [int(x) for x in version1.split(".")]
        v2_parts = [int(x) for x in version2.split(".")]

        # Pad with zeros
        max_len = max(len(v1_parts), len(v2_parts))
        v1_parts.extend([0] * (max_len - len(v1_parts)))
        v2_parts.extend([0] * (max_len - len(v2_parts)))

        for v1, v2 in zip(v1_parts, v2_parts):
            if v1 < v2:
                return -1
            elif v1 > v2:
                return 1

        return 0

    def _analyze_version_differences(
        self, current_version: str, target_version: str
    ) -> Dict[str, Any]:
        """Analyze differences between two Anvil versions."""

        comparison = self._version_compare(current_version, target_version)

        if comparison == 0:
            return {
                "type": "same",
                "new_features": [],
                "deprecated_features": [],
                "breaking_changes": [],
            }
        elif comparison < 0:
            return {
                "type": "upgrade",
                "new_features": self._get_new_features_between(
                    current_version, target_version
                ),
                "deprecated_features": self._get_deprecated_features_between(
                    current_version, target_version
                ),
                "breaking_changes": self._get_breaking_changes_between(
                    current_version, target_version
                ),
            }
        else:
            return {
                "type": "downgrade",
                "lost_features": self._get_new_features_between(
                    target_version, current_version
                ),
                "compatibility_issues": self._get_compatibility_issues_between(
                    target_version, current_version
                ),
            }

    def _get_new_features_between(
        self, from_version: str, to_version: str
    ) -> List[str]:
        """Get features introduced between two versions."""
        new_features = []

        for feature in self.compatibility_matrix.features:
            if (
                self._version_compare(from_version, feature.min_version) < 0
                and self._version_compare(to_version, feature.min_version) >= 0
            ):
                new_features.append(feature.name)

        return new_features

    def _get_deprecated_features_between(
        self, from_version: str, to_version: str
    ) -> List[str]:
        """Get features deprecated between two versions."""
        deprecated = []

        for feature in self.compatibility_matrix.features:
            if feature.deprecated_in:
                if (
                    self._version_compare(from_version, feature.deprecated_in) < 0
                    and self._version_compare(to_version, feature.deprecated_in) >= 0
                ):
                    deprecated.append(feature.name)

        return deprecated

    def _get_breaking_changes_between(
        self, from_version: str, to_version: str
    ) -> List[str]:
        """Get breaking changes between two versions."""
        # This would be populated with actual breaking changes from Anvil release notes
        breaking_changes = []

        # Example breaking changes
        if (
            self._version_compare(from_version, "1.3") < 0
            and self._version_compare(to_version, "1.3") >= 0
        ):
            breaking_changes.append("Component property changes in 1.3")

        if (
            self._version_compare(from_version, "1.4") < 0
            and self._version_compare(to_version, "1.4") >= 0
        ):
            breaking_changes.append("Layout system changes in 1.4")

        return breaking_changes

    def _get_compatibility_issues_between(
        self, from_version: str, to_version: str
    ) -> List[str]:
        """Get compatibility issues when downgrading."""
        issues = []

        for feature in self.compatibility_matrix.features:
            if (
                self._version_compare(to_version, feature.min_version) < 0
                and self._version_compare(from_version, feature.min_version) >= 0
            ):
                issues.append(f"Feature {feature.name} not available in {to_version}")

        return issues

    def _create_migration_steps(
        self,
        components: List[str],
        version_diff: Dict[str, Any],
        config: VersionCompatibilityConfig,
    ) -> List[Dict[str, Any]]:
        """Create step-by-step migration plan."""

        steps = []

        # Preparation steps
        steps.append(
            {
                "phase": "preparation",
                "title": "Backup Current Code",
                "description": "Create a complete backup of the current project",
                "priority": "high",
            }
        )

        steps.append(
            {
                "phase": "preparation",
                "title": "Update Dependencies",
                "description": "Update Anvil dependencies to target version",
                "priority": "high",
            }
        )

        # Feature migration steps
        if version_diff["type"] == "upgrade":
            for feature in version_diff["new_features"]:
                steps.append(
                    {
                        "phase": "feature_migration",
                        "title": f"Migrate to {feature}",
                        "description": f"Update components to use {feature}",
                        "priority": "medium",
                        "affected_components": components,
                    }
                )

        # Breaking changes steps
        for breaking_change in version_diff["breaking_changes"]:
            steps.append(
                {
                    "phase": "breaking_changes",
                    "title": f"Address: {breaking_change}",
                    "description": f"Fix breaking change: {breaking_change}",
                    "priority": "high",
                    "affected_components": components,
                }
            )

        # Testing steps
        steps.append(
            {
                "phase": "testing",
                "title": "Test Migration",
                "description": "Test all components with new version",
                "priority": "high",
            }
        )

        return steps

    def _generate_migration_matrix(
        self, current_version: str, target_version: str, components: List[str]
    ) -> Dict[str, Any]:
        """Generate a compatibility matrix for migration."""

        matrix = {
            "current_version": current_version,
            "target_version": target_version,
            "components": {},
        }

        for component in components:
            matrix["components"][component] = {
                "current_compatibility": self._check_component_compatibility(
                    component, current_version
                ),
                "target_compatibility": self._check_component_compatibility(
                    component, target_version
                ),
                "migration_required": False,
                "migration_complexity": "low",
            }

            # Determine if migration is required
            current_compat = matrix["components"][component]["current_compatibility"]
            target_compat = matrix["components"][component]["target_compatibility"]

            if current_compat["compatible"] and not target_compat["compatible"]:
                matrix["components"][component]["migration_required"] = True
                matrix["components"][component]["migration_complexity"] = "medium"
            elif not current_compat["compatible"] and target_compat["compatible"]:
                matrix["components"][component]["migration_complexity"] = "low"
            elif not current_compat["compatible"] and not target_compat["compatible"]:
                matrix["components"][component]["migration_complexity"] = "high"

        return matrix

    def _check_component_compatibility(
        self, component: str, version: str
    ) -> Dict[str, Any]:
        """Check if a component is compatible with a version."""
        # This would analyze the actual component code
        # For now, return a basic compatibility check
        return {"compatible": True, "issues": [], "features_used": []}

    def _create_rollback_plan(
        self, current_version: str, target_version: str, components: List[str]
    ) -> Dict[str, Any]:
        """Create a rollback plan for migration."""

        return {
            "rollback_available": True,
            "rollback_steps": [
                "Restore backup from preparation phase",
                "Revert dependency changes",
                "Test rollback functionality",
            ],
            "rollback_triggers": [
                "Critical functionality broken",
                "Performance degradation > 20%",
                "Compatibility issues with dependencies",
            ],
            "estimated_rollback_time": "30-60 minutes",
        }

    def _estimate_migration_effort(
        self, components: List[str], version_diff: Dict[str, Any]
    ) -> Dict[str, Any]:
        """Estimate the effort required for migration."""

        base_effort = len(components) * 2  # 2 hours per component

        # Add effort for breaking changes
        breaking_effort = (
            len(version_diff["breaking_changes"]) * 4
        )  # 4 hours per breaking change

        # Add effort for new features
        feature_effort = len(version_diff["new_features"]) * 1  # 1 hour per new feature

        total_effort = base_effort + breaking_effort + feature_effort

        return {
            "total_hours": total_effort,
            "component_effort": base_effort,
            "breaking_change_effort": breaking_effort,
            "feature_effort": feature_effort,
            "complexity": "medium" if total_effort < 20 else "high",
        }

    def _identify_breaking_changes(self, version_diff: Dict[str, Any]) -> List[str]:
        """Identify breaking changes from version differences."""
        return version_diff.get("breaking_changes", [])

    def _identify_new_features(self, version_diff: Dict[str, Any]) -> List[str]:
        """Identify new features from version differences."""
        return version_diff.get("new_features", [])

    def _generate_base_component(
        self, component_name: str, component_type: str, properties: Dict[str, Any]
    ) -> Dict[str, Any]:
        """Generate a basic component structure."""
        return {
            "name": component_name,
            "type": component_type,
            "properties": properties,
            "base_generation": True,
        }

    def _generate_fallback_implementations(
        self, unsupported_features: List[str], config: VersionCompatibilityConfig
    ) -> List[Dict[str, Any]]:
        """Generate fallback implementations for unsupported features."""

        fallbacks = []

        for feature in unsupported_features:
            fallback_impl = self._get_fallback_for_feature(feature)
            if fallback_impl:
                fallbacks.append(
                    {
                        "feature": feature,
                        "fallback": fallback_impl,
                        "strategy": config.fallback_strategy,
                    }
                )

        return fallbacks

    def _generate_feature_detection(
        self, unsupported_features: List[str], config: VersionCompatibilityConfig
    ) -> Dict[str, Any]:
        """Generate feature detection code."""

        detection_code = {}

        for feature in unsupported_features:
            detection_code[feature] = self._generate_feature_detection_code(feature)

        return {
            "enabled": config.feature_detection,
            "code": detection_code,
            "features": unsupported_features,
        }
