import json
import os
from datetime import UTC, datetime
from pathlib import Path
from typing import Literal, cast

import questionary
from dotenv import load_dotenv

from tariff_fetch.openei.utility_rates import UtilityRateSector, UtilityRatesResponseItem, iter_utility_rates

from . import console, prompt_filename
from .types import Utility


def _prompt_sector() -> UtilityRateSector:
    return cast(
        UtilityRateSector,
        questionary.select(
            message="Select sector",
            choices=[
                "Residential",
                "Commercial",
                "Industrial",
                "Lighting",
            ],
        ).ask(),
    )


def _prompt_detail_level() -> Literal["full", "minimal"]:
    return cast(
        Literal["full", "minimal"],
        questionary.select(
            message="Select level of detail",
            choices=["full", "minimal"],
        ).ask(),
    )


def _get_tariffs(
    eia_id: int, sector: UtilityRateSector, detail: Literal["full", "minimal"]
) -> list[UtilityRatesResponseItem]:
    api_key = os.getenv("OPENEI_API_KEY")
    if not api_key:
        raise ValueError("API Key is not set (via OPENEI_API_KEY variable)")
    with console.status("Fetching rates..."):
        iterator = iter_utility_rates(
            api_key,
            effective_on_date=datetime.now(UTC),
            sector=sector,
            detail=detail,
            eia=eia_id,
        )
        return list(iterator)


def _prompt_tariffs(tariffs: list[UtilityRatesResponseItem]) -> list[UtilityRatesResponseItem]:
    return cast(
        list[UtilityRatesResponseItem],
        questionary.checkbox(
            message="Select tariffs to include",
            choices=[questionary.Choice(title=_["name"], value=_, checked=True) for _ in tariffs],
        ).ask(),
    )


def process_openei(utility: Utility, output_folder: Path):
    _ = load_dotenv()
    if not os.getenv("OPENEI_API_KEY"):
        console.print("[b]OPENEI_API_KEY[/] environment variable is not set")
        console.print("Cannot use OpenEI API due to missing credentials")
        _ = console.input("Press enter to proceed...")
        return

    if not (sector := _prompt_sector()):
        return
    if not (detail_level := _prompt_detail_level()):
        return
    tariffs = _get_tariffs(utility.eia_id, sector, detail_level)
    if not tariffs:
        console.print("[red]No tariffs found[/]")
        _ = console.input("Press enter to proceed...")
        return
    tariffs = _prompt_tariffs(tariffs)
    if not tariffs:
        console.print("[red]No tariffs selected[/]")
        _ = console.input("Press enter to proceed...")
        return

    suggested_filename = f"openei_{utility.name}_{sector}_{detail_level}"
    if not (filepath := prompt_filename(output_folder, suggested_filename, "json")):
        return

    filepath.parent.mkdir(exist_ok=True)
    print(filepath)
    _ = filepath.write_text(json.dumps(tariffs, indent=2))
    console.print(f"Wrote [blue]{len(tariffs)}[/] items to {filepath}")
