"""Core hardware configuration models."""

from __future__ import annotations

from pydantic import BaseModel, ConfigDict, Field

from radiens_core.models.ports import Port
from radiens_core.models.status import BackboneMode


class CableDelay(BaseModel):
    """Cable delay configuration for a specific port.

    Attributes:
        port: The hardware port for which the cable delay is configured. References Port.
        cable_delay: The cable delay value in units specific to the hardware.
        is_auto: Whether the cable delay is automatically determined by the system.
    """

    model_config = ConfigDict(frozen=True, populate_by_name=True)

    port: Port
    cable_delay: int = Field(alias="cableDelay")
    is_auto: bool = Field(alias="isAuto")


class CoreConfig(BaseModel):
    """Core hardware configuration retrieved from the server.

    Attributes:
        allego_core_server_port: The network port used by the Allego Core server.
        base_samp_freq: Base sampling frequency in Hertz.
        stream_loop_dur_ms: Stream loop duration in milliseconds.
        backbone_mode: Current hardware backbone mode. References BackboneMode.
        has_xdaq_gpio_expander: Whether the system is equipped with an XDAQ GPIO expander.
        cable_delays: Mapping of port indices to their respective CableDelay configurations.
    """

    model_config = ConfigDict(frozen=True, populate_by_name=True)

    allego_core_server_port: str = Field(alias="allegoCoreServerPort")
    base_samp_freq: float = Field(alias="baseSampFreq")
    stream_loop_dur_ms: int = Field(alias="streamLoopDurMs")
    backbone_mode: BackboneMode = Field(alias="backboneMode")
    has_xdaq_gpio_expander: bool = Field(alias="hasXDAQGPIOExpander")
    cable_delays: dict[int, CableDelay] = Field(alias="cableDelays")


class SetCoreConfigRequest(BaseModel):
    """Request to update core hardware configuration.

    Attributes:
        samp_freq: Target sampling frequency in Hertz. Defaults to None.
        loop_dur: Target loop duration in milliseconds. Defaults to None.
        pcache_persistence: PCache persistence duration. Defaults to None.
        cable_delay: Specific cable delay configuration to set. References CableDelay. Defaults to None.
    """

    model_config = ConfigDict(frozen=True, populate_by_name=True)

    samp_freq: float | None = Field(default=None, alias="sampFreq")
    loop_dur: float | None = Field(default=None, alias="loopDur")
    pcache_persistence: float | None = Field(default=None, alias="pcachePersistence")
    cable_delay: CableDelay | None = Field(default=None, alias="cableDelay")
