"""Shared enum converters used across multiple converter modules.

Only enum converters that are imported by more than one converter file
belong here. Single-use converters should live in their domain converter.
"""

from __future__ import annotations

from radiens_core._generated import allegoserver_pb2, common_pb2
from radiens_core.models.ports import Port
from radiens_core.models.status import BackboneMode, RecordMode, StreamMode

# --- Port ---

_PORT_TO_PROTO: dict[Port, common_pb2.Port.ValueType] = {
    Port.A: common_pb2.A,
    Port.B: common_pb2.B,
    Port.C: common_pb2.C,
    Port.D: common_pb2.D,
    Port.E: common_pb2.E,
    Port.F: common_pb2.F,
    Port.G: common_pb2.G,
    Port.H: common_pb2.H,
}

_PORT_FROM_PROTO: dict[int, Port] = {
    int(common_pb2.A): Port.A,
    int(common_pb2.B): Port.B,
    int(common_pb2.C): Port.C,
    int(common_pb2.D): Port.D,
    int(common_pb2.E): Port.E,
    int(common_pb2.F): Port.F,
    int(common_pb2.G): Port.G,
    int(common_pb2.H): Port.H,
}


def port_to_proto(port: Port) -> common_pb2.Port.ValueType:
    """Convert domain Port to proto Port."""
    return _PORT_TO_PROTO[port]


def port_from_proto(pb: int) -> Port:
    """Convert proto Port int to domain Port."""
    return _PORT_FROM_PROTO[pb]


# --- BackboneMode ---

_BACKBONE_MODE_TO_PROTO: dict[BackboneMode, allegoserver_pb2.BackboneMode.ValueType] = {
    BackboneMode.SMARTBOX_PRO: allegoserver_pb2.SMARTBOX_PRO,
    BackboneMode.SMARTBOX_SIM_GEN_SINE: allegoserver_pb2.SMARTBOX_SIM_GEN_SINE,
    BackboneMode.SMARTBOX_SIM_GEN_SPIKES: allegoserver_pb2.SMARTBOX_SIM_GEN_SPIKES,
    BackboneMode.SMARTBOX_SIM_DATASOURCE: allegoserver_pb2.SMARTBOX_SIM_DATASOURCE,
    BackboneMode.OPEN_EPHYS_USB3: allegoserver_pb2.OPEN_EPHYS_USB3,
    BackboneMode.INTAN_RECORDING_CONTROLLER_1024: allegoserver_pb2.INTAN_RECORDING_CONTROLLER_1024,
    BackboneMode.SMARTBOX_CLASSIC: allegoserver_pb2.SMARTBOX_CLASSIC,
    BackboneMode.INTAN_RECORDING_CONTROLLER_512: allegoserver_pb2.INTAN_RECORDING_CONTROLLER_512,
    BackboneMode.OPEN_EPHYS_USB2: allegoserver_pb2.OPEN_EPHYS_USB2,
    BackboneMode.INTAN_USB2: allegoserver_pb2.INTAN_USB2,
    BackboneMode.SMARTBOX_SIM_GEN_SINE_MAPPED: allegoserver_pb2.SMARTBOX_SIM_GEN_SINE_MAPPED,
    BackboneMode.SMARTBOX_SIM_GEN_SINE_HIGH_FREQ: allegoserver_pb2.SMARTBOX_SIM_GEN_SINE_HIGH_FREQ,
    BackboneMode.SMARTBOX_SIM_GEN_SINE_MULTI_BAND: allegoserver_pb2.SMARTBOX_SIM_GEN_SINE_MULTI_BAND,
    BackboneMode.SMARTBOX_PRO_SINAPS_256: allegoserver_pb2.SMARTBOX_PRO_SINAPS_256,
    BackboneMode.SMARTBOX_PRO_SINAPS_1024: allegoserver_pb2.SMARTBOX_PRO_SINAPS_1024,
    BackboneMode.XDAQ_ONE_REC: allegoserver_pb2.XDAQ_ONE_REC,
    BackboneMode.XDAQ_ONE_STIM: allegoserver_pb2.XDAQ_ONE_STIM,
    BackboneMode.XDAQ_CORE_REC: allegoserver_pb2.XDAQ_CORE_REC,
    BackboneMode.XDAQ_CORE_STIM: allegoserver_pb2.XDAQ_CORE_STIM,
    BackboneMode.SMARTBOX_PRO_SINAPS_512: allegoserver_pb2.SMARTBOX_PRO_SINAPS_512,
    BackboneMode.XDAQ_GEN2_ONE_STIM: allegoserver_pb2.XDAQ_GEN2_ONE_STIM,
    BackboneMode.XDAQ_GEN2_CORE_STIM: allegoserver_pb2.XDAQ_GEN2_CORE_STIM,
    BackboneMode.XDAQ_GEN2_ONE_REC: allegoserver_pb2.XDAQ_GEN2_ONE_REC,
    BackboneMode.XDAQ_GEN2_CORE_REC: allegoserver_pb2.XDAQ_GEN2_CORE_REC,
    BackboneMode.SMARTBOX_SIM_GEN_LFP: allegoserver_pb2.SMARTBOX_SIM_GEN_LFP,
}

_BACKBONE_MODE_FROM_PROTO: dict[int, BackboneMode] = {
    int(allegoserver_pb2.SMARTBOX_PRO): BackboneMode.SMARTBOX_PRO,
    int(allegoserver_pb2.SMARTBOX_SIM_GEN_SINE): BackboneMode.SMARTBOX_SIM_GEN_SINE,
    int(allegoserver_pb2.SMARTBOX_SIM_GEN_SPIKES): BackboneMode.SMARTBOX_SIM_GEN_SPIKES,
    int(allegoserver_pb2.SMARTBOX_SIM_DATASOURCE): BackboneMode.SMARTBOX_SIM_DATASOURCE,
    int(allegoserver_pb2.OPEN_EPHYS_USB3): BackboneMode.OPEN_EPHYS_USB3,
    int(allegoserver_pb2.INTAN_RECORDING_CONTROLLER_1024): BackboneMode.INTAN_RECORDING_CONTROLLER_1024,
    int(allegoserver_pb2.SMARTBOX_CLASSIC): BackboneMode.SMARTBOX_CLASSIC,
    int(allegoserver_pb2.INTAN_RECORDING_CONTROLLER_512): BackboneMode.INTAN_RECORDING_CONTROLLER_512,
    int(allegoserver_pb2.OPEN_EPHYS_USB2): BackboneMode.OPEN_EPHYS_USB2,
    int(allegoserver_pb2.INTAN_USB2): BackboneMode.INTAN_USB2,
    int(allegoserver_pb2.SMARTBOX_SIM_GEN_SINE_MAPPED): BackboneMode.SMARTBOX_SIM_GEN_SINE_MAPPED,
    int(allegoserver_pb2.SMARTBOX_SIM_GEN_SINE_HIGH_FREQ): BackboneMode.SMARTBOX_SIM_GEN_SINE_HIGH_FREQ,
    int(allegoserver_pb2.SMARTBOX_SIM_GEN_SINE_MULTI_BAND): BackboneMode.SMARTBOX_SIM_GEN_SINE_MULTI_BAND,
    int(allegoserver_pb2.SMARTBOX_PRO_SINAPS_256): BackboneMode.SMARTBOX_PRO_SINAPS_256,
    int(allegoserver_pb2.SMARTBOX_PRO_SINAPS_1024): BackboneMode.SMARTBOX_PRO_SINAPS_1024,
    int(allegoserver_pb2.XDAQ_ONE_REC): BackboneMode.XDAQ_ONE_REC,
    int(allegoserver_pb2.XDAQ_ONE_STIM): BackboneMode.XDAQ_ONE_STIM,
    int(allegoserver_pb2.XDAQ_CORE_REC): BackboneMode.XDAQ_CORE_REC,
    int(allegoserver_pb2.XDAQ_CORE_STIM): BackboneMode.XDAQ_CORE_STIM,
    int(allegoserver_pb2.SMARTBOX_PRO_SINAPS_512): BackboneMode.SMARTBOX_PRO_SINAPS_512,
    int(allegoserver_pb2.XDAQ_GEN2_ONE_STIM): BackboneMode.XDAQ_GEN2_ONE_STIM,
    int(allegoserver_pb2.XDAQ_GEN2_CORE_STIM): BackboneMode.XDAQ_GEN2_CORE_STIM,
    int(allegoserver_pb2.XDAQ_GEN2_ONE_REC): BackboneMode.XDAQ_GEN2_ONE_REC,
    int(allegoserver_pb2.XDAQ_GEN2_CORE_REC): BackboneMode.XDAQ_GEN2_CORE_REC,
    int(allegoserver_pb2.SMARTBOX_SIM_GEN_LFP): BackboneMode.SMARTBOX_SIM_GEN_LFP,
}


def backbone_mode_to_proto(bm: BackboneMode) -> allegoserver_pb2.BackboneMode.ValueType:
    """Convert domain BackboneMode to proto BackboneMode."""
    return _BACKBONE_MODE_TO_PROTO[bm]


def backbone_mode_from_proto(pb: int) -> BackboneMode:
    """Convert proto BackboneMode int to domain BackboneMode."""
    return _BACKBONE_MODE_FROM_PROTO[pb]


# --- RecordMode ---

_RECORD_MODE_TO_PROTO: dict[RecordMode, allegoserver_pb2.RecordMode.ValueType] = {
    RecordMode.OFF: allegoserver_pb2.R_OFF,
    RecordMode.ON: allegoserver_pb2.R_ON,
}

_RECORD_MODE_FROM_PROTO: dict[int, RecordMode] = {
    int(allegoserver_pb2.R_OFF): RecordMode.OFF,
    int(allegoserver_pb2.R_ON): RecordMode.ON,
}


def record_mode_to_proto(rm: RecordMode) -> allegoserver_pb2.RecordMode.ValueType:
    """Convert domain RecordMode to proto RecordMode."""
    return _RECORD_MODE_TO_PROTO[rm]


def record_mode_from_proto(pb: int) -> RecordMode:
    """Convert proto RecordMode int to domain RecordMode."""
    return _RECORD_MODE_FROM_PROTO[pb]


# --- StreamMode ---

_STREAM_MODE_TO_PROTO: dict[StreamMode, allegoserver_pb2.StreamMode.ValueType] = {
    StreamMode.OFF: allegoserver_pb2.S_OFF,
    StreamMode.ON: allegoserver_pb2.S_ON,
}

_STREAM_MODE_FROM_PROTO: dict[int, StreamMode] = {
    int(allegoserver_pb2.S_OFF): StreamMode.OFF,
    int(allegoserver_pb2.S_ON): StreamMode.ON,
}


def stream_mode_to_proto(sm: StreamMode) -> allegoserver_pb2.StreamMode.ValueType:
    """Convert domain StreamMode to proto StreamMode."""
    return _STREAM_MODE_TO_PROTO[sm]


def stream_mode_from_proto(pb: int) -> StreamMode:
    """Convert proto StreamMode int to domain StreamMode."""
    return _STREAM_MODE_FROM_PROTO[pb]
