"""
Plantillas CSV para Cambio de régimen y Regularización (encabezado y partidas).
Por ahora misma estructura que encabezado/partidas de exportación; luego se ajustan columnas si difieren.
"""

from typing import Dict, List, Any, Optional

from ..common.cell_value import cell_to_str
from ..common.inject_csv_labels_en import inject_en_labels_into_template_columns
from ..common.template_locale import merge_download_header_into_lookup, merge_labels_into_lookup

# Cambio de régimen: cam_reg_header, cam_reg_details
# Regularización: regulariz_header, regulariz_details
TEMPLATE_COLUMNS: Dict[str, List[Dict[str, Any]]] = {
    "cam_reg_header": [
        {"canonical": "NUMERO FACTURA", "aliases": ["NUM FACTURA", "FACTURA", "ID"]},
        {"canonical": "FECHA FACTURA", "aliases": ["FECHA"]},
        {"canonical": "FECHA EMISION"},
        {"canonical": "CLAVE PROVEEDOR"},
        {"canonical": "CLAVE VENDIDO A"},
        {"canonical": "CLAVE ENVIADO A"},
        {"canonical": "REGIMEN", "aliases": ["CLAVEDOCUMENTO"]},
        {"canonical": "ADUANA DE CRUCE"},
        {"canonical": "CLAVE MONEDA"},
        {"canonical": "CLAVE INCOTERM"},
        {"canonical": "TIPO MONEDA"},
        {"canonical": "TIPO DE CAMBIO"},
        {"canonical": "TIPO PESO"},
        {"canonical": "TIPO TRANSPORTE"},
        {"canonical": "REMESA"},
        {"canonical": "AGENTE ADUANAL"},
        {"canonical": "FLETES"},
        {"canonical": "VALOR SEGUROS"},
        {"canonical": "SEGUROS"},
        {"canonical": "EMBALAJES"},
        {"canonical": "OTROS INCREMENTABLES"},
        {"canonical": "NUM PROYECTO", "aliases": ["NUMPROYECTO"]},
        {"canonical": "ORDEN COMPRA", "aliases": ["ORDENCOMPRA"]},
        {"canonical": "FACTURA ALTERNA"},
        {"canonical": "FACTURA EXPO REF", "aliases": ["FACTURAEXPOREF"]},
        {"canonical": "OBSERVACIONES E"},
        {"canonical": "OBSERVACIONES I"},
        {"canonical": "E DOCUMENT"},
        {"canonical": "NUM OPERACION"},
        {"canonical": "CLAVE TRANSPORTISTA"},
        {"canonical": "NOMBRE CONDUCTOR"},
        {"canonical": "NUMERO TRANSPORTE"},
        {"canonical": "PRECINTO"},
    ],
    "cam_reg_details": [
        {"canonical": "NUMERO FACTURA", "aliases": ["NUM FACTURA", "FACTURA"]},
        {"canonical": "LINEA", "aliases": ["RENGLON", "PARTIDA"]},
        {"canonical": "NUMPARTE", "aliases": ["NUMERO PARTE"]},
        {"canonical": "PRECIO UNITARIO", "aliases": ["PRECIOUNITARIO"]},
        {"canonical": "VALOR COMERCIAL", "aliases": ["VALORCOMERCIAL"]},
        {"canonical": "CANTIDAD"},
        {"canonical": "CANTIDAD BULTOS", "aliases": ["CANTIDADBULTOS"]},
        {"canonical": "DESCRIPCION"},
        {"canonical": "PAIS ORIGEN", "aliases": ["PAISORIGEN"]},
        {"canonical": "FRACCION"},
        {"canonical": "ORDEN DE COMPRA", "aliases": ["ORDENCOMPRA"]},
    ],
    "regulariz_header": [
        {"canonical": "NUMERO FACTURA", "aliases": ["NUM FACTURA", "FACTURA", "ID"]},
        {"canonical": "FECHA FACTURA", "aliases": ["FECHA"]},
        {"canonical": "FECHA EMISION"},
        {"canonical": "CLAVE PROVEEDOR"},
        {"canonical": "CLAVE VENDIDO A"},
        {"canonical": "CLAVE ENVIADO A"},
        {"canonical": "REGIMEN", "aliases": ["CLAVEDOCUMENTO"]},
        {"canonical": "ADUANA DE CRUCE"},
        {"canonical": "CLAVE MONEDA"},
        {"canonical": "CLAVE INCOTERM"},
        {"canonical": "TIPO MONEDA"},
        {"canonical": "TIPO DE CAMBIO"},
        {"canonical": "TIPO PESO"},
        {"canonical": "TIPO TRANSPORTE"},
        {"canonical": "REMESA"},
        {"canonical": "AGENTE ADUANAL"},
        {"canonical": "FLETES"},
        {"canonical": "VALOR SEGUROS"},
        {"canonical": "SEGUROS"},
        {"canonical": "EMBALAJES"},
        {"canonical": "OTROS INCREMENTABLES"},
        {"canonical": "NUM PROYECTO", "aliases": ["NUMPROYECTO"]},
        {"canonical": "ORDEN COMPRA", "aliases": ["ORDENCOMPRA"]},
        {"canonical": "FACTURA ALTERNA"},
        {"canonical": "FACTURA EXPO REF", "aliases": ["FACTURAEXPOREF"]},
        {"canonical": "OBSERVACIONES E"},
        {"canonical": "OBSERVACIONES I"},
        {"canonical": "E DOCUMENT"},
        {"canonical": "NUM OPERACION"},
        {"canonical": "CLAVE TRANSPORTISTA"},
        {"canonical": "NOMBRE CONDUCTOR"},
        {"canonical": "NUMERO TRANSPORTE"},
        {"canonical": "PRECINTO"},
    ],
    "regulariz_details": [
        {"canonical": "NUMERO FACTURA", "aliases": ["NUM FACTURA", "FACTURA"]},
        {"canonical": "LINEA", "aliases": ["RENGLON", "PARTIDA"]},
        {"canonical": "NUMPARTE", "aliases": ["NUMERO PARTE"]},
        {"canonical": "PRECIO UNITARIO", "aliases": ["PRECIOUNITARIO"]},
        {"canonical": "VALOR COMERCIAL", "aliases": ["VALORCOMERCIAL"]},
        {"canonical": "CANTIDAD"},
        {"canonical": "CANTIDAD BULTOS", "aliases": ["CANTIDADBULTOS"]},
        {"canonical": "DESCRIPCION"},
        {"canonical": "PAIS ORIGEN", "aliases": ["PAISORIGEN"]},
        {"canonical": "FRACCION"},
        {"canonical": "ORDEN DE COMPRA", "aliases": ["ORDENCOMPRA"]},
    ],
}

inject_en_labels_into_template_columns(TEMPLATE_COLUMNS)


def _resolve_template_columns(template_id: str) -> Optional[List[Dict[str, Any]]]:
    return TEMPLATE_COLUMNS.get(template_id)


def build_normalized_lookup(template_id: str, normalize_header_fn) -> Dict[str, str]:
    """normalized_header -> canonical_name."""
    cols = _resolve_template_columns(template_id)
    if not cols:
        return {}
    lookup: Dict[str, str] = {}
    for item in cols:
        canonical = item["canonical"]
        lookup[normalize_header_fn(canonical)] = canonical
        for alias in item.get("aliases") or []:
            lookup[normalize_header_fn(alias)] = canonical
        merge_labels_into_lookup(item, canonical, normalize_header_fn, lookup)
        merge_download_header_into_lookup(item, canonical, normalize_header_fn, lookup)
    return lookup


def row_from_template(row: Dict[str, Any], template_id: str, normalize_header_fn) -> Dict[str, Any]:
    """Fila CSV -> dict con nombres canónicos de la plantilla."""
    lookup = build_normalized_lookup(template_id, normalize_header_fn)
    if not lookup:
        return {normalize_header_fn(k): cell_to_str(v) for k, v in row.items()}
    out: Dict[str, Any] = {}
    for csv_header, value in row.items():
        key_norm = normalize_header_fn(csv_header)
        if key_norm in lookup:
            out[lookup[key_norm]] = cell_to_str(value)
    return out
