"""Multi-state merge — combine inventories from multiple state files.

Deduplicates by (address, source_state), detects mixed clouds,
and computes deterministic multi-state cache keys.
"""

from __future__ import annotations

import hashlib
import sys
from typing import TYPE_CHECKING

from complyform.core.errors import MixedCloudMultiStateError

if TYPE_CHECKING:
    from pathlib import Path

    from complyform.core.scanner.state_parser import ResourceRecord, StateMetadata

_PROVIDER_CLOUD_MAP: dict[str, str] = {
    "google": "gcp",
    "aws": "aws",
    "azurerm": "azure",
}


def merge_state_inventories(
    inventories: list[tuple[str, list[ResourceRecord], StateMetadata]],
) -> tuple[list[ResourceRecord], list[StateMetadata]]:
    """Merge multiple state scan inventories into unified resource list.

    Args:
        inventories: List of (source_label, resources, metadata) tuples.

    Returns:
        (merged_resources, all_metadata).

    Raises:
        MixedCloudMultiStateError: Resources span >1 cloud provider.
    """
    all_metadata: list[StateMetadata] = []
    seen: dict[tuple[str, str], int] = {}
    merged: list[ResourceRecord] = []

    for _label, resources, metadata in inventories:
        all_metadata.append(metadata)
        for r in resources:
            key = (r.address, r.source_state)
            if key in seen:
                print(
                    f"Warning: Duplicate resource {r.address}"
                    f" in source {r.source_state} — keeping last.",
                    file=sys.stderr,
                )
                merged[seen[key]] = r
            else:
                seen[key] = len(merged)
                merged.append(r)

    # Detect mixed clouds
    clouds: set[str] = set()
    for r in merged:
        cloud = _PROVIDER_CLOUD_MAP.get(r.provider, r.provider)
        clouds.add(cloud)

    if len(clouds) > 1:
        raise MixedCloudMultiStateError(clouds)

    return merged, all_metadata


def compute_multi_state_cache_key(state_paths: list[Path]) -> str:
    """Compute deterministic cache key for multi-state scan.

    Sort paths, hash each file's content, join with '|',
    hash the result, truncate to 16 chars.
    """
    sorted_paths = sorted(state_paths, key=str)
    hashes: list[str] = []
    for p in sorted_paths:
        content = p.read_bytes()
        hashes.append(hashlib.sha256(content).hexdigest())

    combined = "|".join(hashes)
    return hashlib.sha256(combined.encode("utf-8")).hexdigest()[:16]
