"""Input Type Models für Questra Data API.

Diese Dataclasses dienen als typsichere Wrapper für GraphQL Input-Typen
basierend auf dem Schema.
"""

from __future__ import annotations

from dataclasses import asdict, dataclass, field
from typing import Any

from .inventory import DataType, RelationType
from .timeseries import (
    Aggregation,
    QuotationBehavior,
    TimeUnit,
    ValueAlignment,
    ValueAvailability,
)


@dataclass
class StringPropertyConfig:
    """
    Konfiguration für String-Properties.

    Entspricht _CreateInventoryPropertyString__InputType aus dem GraphQL Schema.

    Attributes:
        maxLength: Maximale Länge in Zeichen (int wird intern zu LongNumberString konvertiert)
        isCaseSensitive: Groß-/Kleinschreibung beachten (Standard: False)

    Beispiele:
        StringPropertyConfig(maxLength=100)         # Wird zu "100" für GraphQL
        StringPropertyConfig(maxLength=200)
    """

    maxLength: int  # Wird zu LongNumberString (str) konvertiert
    isCaseSensitive: bool = False

    def to_dict(self) -> dict[str, Any]:
        """Konvertiert zu Dictionary mit maxLength als String für GraphQL."""
        return {
            "maxLength": str(self.maxLength),  # int -> str für GraphQL LongNumberString
            "isCaseSensitive": self.isCaseSensitive,
        }


@dataclass
class FilePropertyConfig:
    """
    Konfiguration für File-Properties.

    Entspricht _CreateInventoryPropertyFile__InputType aus dem GraphQL Schema.

    Attributes:
        maxLength: Maximale Länge in Bytes (int, unbegrenzt in Python 3, wird zu LongNumberString konvertiert)

    Beispiele:
        FilePropertyConfig(maxLength=1048576)      # 1 MB
        FilePropertyConfig(maxLength=10737418240)  # 10 GB, große Werte sind möglich
    """

    maxLength: (
        int  # Python 3 int ist unbegrenzt, wird zu LongNumberString (str) konvertiert
    )

    def to_dict(self) -> dict[str, Any]:
        """Konvertiert zu Dictionary mit maxLength als String für GraphQL."""
        return {
            "maxLength": str(self.maxLength)  # int -> str für GraphQL LongNumberString
        }


@dataclass
class IntervalConfig:
    """
    Zeitintervall-Konfiguration.

    Entspricht _Interval__InputType aus dem GraphQL Schema.

    Attributes:
        timeUnit: Zeiteinheit (TimeUnit Enum)
        multiplier: Multiplikator für das Intervall (int, wird zu IntNumberString konvertiert, Standard: 1)

    Beispiele:
        - IntervalConfig(timeUnit=TimeUnit.MINUTE, multiplier=15) für "15 MINUTE"
        - IntervalConfig(timeUnit=TimeUnit.HOUR, multiplier=1) für "1 HOUR"
        - IntervalConfig(timeUnit=TimeUnit.DAY) für "1 DAY" (Standard-Multiplikator)
    """

    timeUnit: TimeUnit
    multiplier: int = 1

    def to_dict(self) -> dict[str, Any]:
        """Konvertiert zu Dictionary mit Enum-Werten und multiplier als String für GraphQL."""
        return {
            "timeUnit": self.timeUnit.value,  # Enum -> str
            "multiplier": str(
                self.multiplier
            ),  # int -> str für GraphQL IntNumberString
        }


@dataclass
class TimeSeriesPropertyConfig:
    """
    Konfiguration für TimeSeries-Properties.

    Entspricht _CreateInventoryPropertyTimeSeries__InputType aus dem GraphQL Schema.

    Attributes:
        interval: Zeitintervall (IntervalConfig)
        unit: Einheit (z.B. "kW", "kWh", "g")
        valueAlignment: Wert-Ausrichtung (ValueAlignment Enum, Standard: LEFT)
        valueAvailability: Verfügbarkeit (ValueAvailability Enum, Standard: AT_INTERVAL_BEGIN)
        timeZone: Zeitzone (Standard: "Europe/Berlin")
        defaultAggregation: Standard-Aggregation (Aggregation Enum, optional)
        startOfTime: Start-Zeitpunkt (optional, ISO-8601 mit Mikrosekunden)
        enableAudit: Audit aktivieren (Standard: False)
        enableQuotation: Quotierung aktivieren (Standard: False)
        defaultQuotationBehavior: Standard-Quotierungsverhalten (QuotationBehavior Enum, Standard: LATEST)
        allowSpecificsPerInstance: Spezifikationen pro Instanz erlauben (Standard: False)
    """

    interval: IntervalConfig
    unit: str
    valueAlignment: ValueAlignment = ValueAlignment.LEFT
    valueAvailability: ValueAvailability = ValueAvailability.AT_INTERVAL_BEGIN
    timeZone: str = "Europe/Berlin"
    defaultAggregation: Aggregation | None = None
    startOfTime: str | None = None
    enableAudit: bool = False
    enableQuotation: bool = False
    defaultQuotationBehavior: QuotationBehavior = QuotationBehavior.LATEST
    allowSpecificsPerInstance: bool = False

    def to_dict(self) -> dict[str, Any]:
        """Konvertiert zu Dictionary mit Enum-Werten, filtert None-Werte."""
        result = {}
        for key in [
            "interval",
            "unit",
            "valueAlignment",
            "valueAvailability",
            "timeZone",
            "defaultAggregation",
            "startOfTime",
            "enableAudit",
            "enableQuotation",
            "defaultQuotationBehavior",
            "allowSpecificsPerInstance",
        ]:
            value = getattr(self, key, None)

            if value is None:
                continue

            # Konvertiere IntervalConfig zu Dict (ruft dessen to_dict() auf)
            if key == "interval":
                result[key] = value.to_dict()
            # Konvertiere Enum zu String
            elif hasattr(value, "value"):
                result[key] = value.value
            else:
                result[key] = value

        return result


@dataclass
class InventoryProperty:
    """
    Property-Definition für Inventory-Erstellung.

    Entspricht _CreateInventoryProperty__InputType aus dem GraphQL Schema.

    Attributes:
        propertyName: Name der Property
        dataType: Datentyp (DataType Enum)
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung
        string: String-spezifische Konfiguration (bei DataType.STRING)
        file: File-spezifische Konfiguration (bei DataType.FILE)
        timeSeries: TimeSeries-spezifische Konfiguration (bei DataType.TIME_SERIES)

    Beispiele:
        # Einfaches String-Property
        InventoryProperty(
            propertyName="Name",
            dataType=DataType.STRING,
            isRequired=True,
            string=StringPropertyConfig(maxLength="200")
        )

        # Integer-Property
        InventoryProperty(
            propertyName="Age",
            dataType=DataType.INT,
            isRequired=False
        )

        # TimeSeries-Property
        InventoryProperty(
            propertyName="messwerte_Energie",
            dataType=DataType.TIME_SERIES,
            timeSeries=TimeSeriesPropertyConfig(
                interval=IntervalConfig(timeUnit="MINUTE", multiplier="15"),
                unit="kWh"
            )
        )
    """

    propertyName: str
    dataType: DataType
    isRequired: bool = True
    isUnique: bool = False
    isArray: bool = False
    description: str | None = None
    string: StringPropertyConfig | None = None
    file: FilePropertyConfig | None = None
    timeSeries: TimeSeriesPropertyConfig | None = None

    def to_dict(self) -> dict[str, Any]:
        """
        Konvertiert die Dataclass zu einem Dictionary für GraphQL Input.

        Filtert None-Werte und konvertiert verschachtelte Dataclasses.
        Ruft to_dict() auf Config-Objekten auf, die diese Methode haben.

        Returns:
            Dictionary bereit für GraphQL Variables
        """
        result = {}

        # Iteriere über die tatsächlichen Attribute (nicht asdict, da wir Kontrolle brauchen)
        for key in [
            "propertyName",
            "dataType",
            "isRequired",
            "isUnique",
            "isArray",
            "description",
            "string",
            "file",
            "timeSeries",
        ]:
            value = getattr(self, key, None)

            if value is None:
                continue

            # Konvertiere Enum zu String
            if hasattr(value, "value"):
                result[key] = value.value
            # Rufe to_dict() auf Config-Objekten auf
            elif hasattr(value, "to_dict"):
                result[key] = value.to_dict()
            else:
                result[key] = value

        return result


@dataclass
class TimeSeriesSpecifics:
    """
    Optionale Spezifikationen für TimeSeries bei der Erstellung.

    Entspricht _TimeSeriesSpecifics__InputType aus dem GraphQL Schema.

    Attributes:
        interval: Zeitintervall (IntervalConfig, optional)
        valueAlignment: Wert-Ausrichtung (ValueAlignment Enum, optional)
        valueAvailability: Verfügbarkeit (ValueAvailability Enum, optional)
        unit: Einheit (str, optional)
        timeZone: Zeitzone (str, optional)
        defaultAggregation: Standard-Aggregation (Aggregation Enum, optional)
        startOfTime: Start-Zeitpunkt (str, optional, ISO-8601 mit Mikrosekunden)
        defaultQuotationBehavior: Standard-Quotierungsverhalten (QuotationBehavior Enum, optional)

    Beispiele:
        # Mit allen Optionen
        TimeSeriesSpecifics(
            interval=IntervalConfig(timeUnit=TimeUnit.MINUTE, multiplier=15),
            valueAlignment=ValueAlignment.LEFT,
            valueAvailability=ValueAvailability.AT_INTERVAL_BEGIN,
            unit="kWh",
            timeZone="Europe/Berlin",
            defaultAggregation=Aggregation.AVERAGE,
            defaultQuotationBehavior=QuotationBehavior.LATEST
        )

        # Minimal (alle Felder optional)
        TimeSeriesSpecifics(
            interval=IntervalConfig(timeUnit=TimeUnit.HOUR, multiplier=1),
            unit="kW"
        )
    """

    interval: IntervalConfig | None = None
    valueAlignment: ValueAlignment | None = None
    valueAvailability: ValueAvailability | None = None
    unit: str | None = None
    timeZone: str | None = None
    defaultAggregation: Aggregation | None = None
    startOfTime: str | None = None
    defaultQuotationBehavior: QuotationBehavior | None = None

    def to_dict(self) -> dict[str, Any]:
        """Konvertiert zu Dictionary mit Enum-Werten, filtert None-Werte."""
        result = {}
        for key in [
            "interval",
            "valueAlignment",
            "valueAvailability",
            "unit",
            "timeZone",
            "defaultAggregation",
            "startOfTime",
            "defaultQuotationBehavior",
        ]:
            value = getattr(self, key, None)

            if value is None:
                continue

            # Konvertiere IntervalConfig zu Dict (ruft dessen to_dict() auf)
            if key == "interval":
                result[key] = value.to_dict()
            # Konvertiere Enum zu String
            elif hasattr(value, "value"):
                result[key] = value.value
            else:
                result[key] = value

        return result


@dataclass
class CreateTimeSeriesInput:
    """
    Input für die Erstellung einer TimeSeries.

    Entspricht _CreateTimeSeries__InputType aus dem GraphQL Schema.

    Attributes:
        inventoryName: Name des Inventars
        propertyName: Name der Property
        namespaceName: Optionaler Namespace (Standard: None)
        specifics: Optionale TimeSeries-Spezifikationen (TimeSeriesSpecifics)

    Beispiele:
        # Mit Spezifikationen
        CreateTimeSeriesInput(
            inventoryName="Sensoren",
            propertyName="messwerte_temperatur",
            namespaceName="TestDaten",
            specifics=TimeSeriesSpecifics(
                interval=IntervalConfig(timeUnit=TimeUnit.MINUTE, multiplier=15),
                unit="°C"
            )
        )

        # Ohne Spezifikationen (nutzt Property-Defaults)
        CreateTimeSeriesInput(
            inventoryName="Sensoren",
            propertyName="messwerte_energie"
        )
    """

    inventoryName: str
    propertyName: str
    namespaceName: str | None = None
    specifics: TimeSeriesSpecifics | None = None

    def to_dict(self) -> dict[str, Any]:
        """Konvertiert zu Dictionary für GraphQL Input, filtert None-Werte."""
        result = {}
        for key in ["inventoryName", "propertyName", "namespaceName", "specifics"]:
            value = getattr(self, key, None)

            if value is None:
                continue

            # Rufe to_dict() auf TimeSeriesSpecifics auf
            if hasattr(value, "to_dict"):
                result[key] = value.to_dict()
            else:
                result[key] = value

        return result


@dataclass
class InventoryRelation:
    """
    Relation-Definition für Inventory-Erstellung.

    Entspricht _CreateInventoryRelation__InputType aus dem GraphQL Schema.

    Attributes:
        propertyName: Name der Relation-Property im Child-Inventory
        relationType: Typ der Relation (RelationType Enum)
        parentInventoryName: Name des Parent-Inventorys
        parentPropertyName: Name der Relation-Property im Parent-Inventory
        isRequired: Pflicht-Relation (optional)
        parentNamespaceName: Namespace des Parent-Inventorys (optional)

    Beispiele:
        # One-to-Many Relation: Anlagen -> Technologie
        InventoryRelation(
            propertyName="Technologie",
            relationType=RelationType.ONE_TO_MANY,
            parentInventoryName="TEC",
            parentPropertyName="Anlagen"
        )

        # One-to-Many: Viele Mitarbeiter gehören zu einer Abteilung
        InventoryRelation(
            propertyName="Abteilung",
            relationType=RelationType.ONE_TO_MANY,
            parentInventoryName="Departments",
            parentPropertyName="Mitarbeiter",
            parentNamespaceName="HR",
            isRequired=True
        )
    """

    propertyName: str
    relationType: RelationType
    parentInventoryName: str
    parentPropertyName: str
    isRequired: bool | None = None
    parentNamespaceName: str | None = None

    def to_dict(self) -> dict[str, Any]:
        """
        Konvertiert die Dataclass zu einem Dictionary für GraphQL Input.

        Filtert None-Werte und konvertiert Enums.

        Returns:
            Dictionary bereit für GraphQL Variables
        """
        result = {}

        for key, value in asdict(self).items():
            if value is None:
                continue

            # Konvertiere Enum zu String
            if hasattr(value, "value"):
                result[key] = value.value
            else:
                result[key] = value

        return result


# ==============================================================================
# Spezialisierte Property-Klassen (flache Hierarchie)
# ==============================================================================


@dataclass
class BaseProperty:
    """
    Basisklasse für alle spezialisierten Property-Klassen.

    Attributes:
        propertyName: Name der Property
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung
    """

    propertyName: str
    isRequired: bool = field(default=True, kw_only=True)
    isUnique: bool = field(default=False, kw_only=True)
    isArray: bool = field(default=False, kw_only=True)
    description: str | None = field(default=None, kw_only=True)


@dataclass
class StringProperty(BaseProperty):
    """
    String-Property. Ersetzt InventoryProperty(dataType=STRING, string=StringPropertyConfig(...)).

    Attributes:
        propertyName: Name der Property
        maxLength: Maximale Länge in Zeichen
        isCaseSensitive: Groß-/Kleinschreibung beachten (Standard: False)
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        StringProperty(
            propertyName="gebaeudename", maxLength=100, isRequired=True, isUnique=True
        )
        ```
    """

    maxLength: int
    isCaseSensitive: bool = False

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.STRING,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
            string=StringPropertyConfig(
                maxLength=self.maxLength, isCaseSensitive=self.isCaseSensitive
            ),
        )


@dataclass
class IntProperty(BaseProperty):
    """
    Integer-Property. Ersetzt InventoryProperty(dataType=INT).

    Attributes:
        propertyName: Name der Property
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        IntProperty(propertyName="baujahr", isRequired=False)
        ```
    """

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.INT,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
        )


@dataclass
class DecimalProperty(BaseProperty):
    """
    Decimal-Property. Ersetzt InventoryProperty(dataType=DECIMAL).

    Attributes:
        propertyName: Name der Property
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        DecimalProperty(propertyName="preis", isRequired=True)
        ```
    """

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.DECIMAL,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
        )


@dataclass
class LongProperty(BaseProperty):
    """
    Long-Property. Ersetzt InventoryProperty(dataType=LONG).

    Attributes:
        propertyName: Name der Property
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        LongProperty(propertyName="artikel_nummer", isRequired=False)
        ```
    """

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.LONG,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
        )


@dataclass
class BoolProperty(BaseProperty):
    """
    Boolean-Property. Ersetzt InventoryProperty(dataType=BOOLEAN).

    Attributes:
        propertyName: Name der Property
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        BoolProperty(propertyName="aktiv", isRequired=True)
        ```
    """

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.BOOLEAN,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
        )


@dataclass
class DateTimeProperty(BaseProperty):
    """
    DateTime-Property. Ersetzt InventoryProperty(dataType=DATE_TIME).

    Attributes:
        propertyName: Name der Property
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        DateTimeProperty(propertyName="erstellt_am", isRequired=True)
        ```
    """

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.DATE_TIME,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
        )


@dataclass
class DateTimeOffsetProperty(BaseProperty):
    """
    DateTimeOffset-Property. Ersetzt InventoryProperty(dataType=DATE_TIME_OFFSET).

    Attributes:
        propertyName: Name der Property
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        DateTimeOffsetProperty(propertyName="letzte_aenderung", isRequired=True)
        ```
    """

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.DATE_TIME_OFFSET,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
        )


@dataclass
class DateProperty(BaseProperty):
    """
    Date-Property. Ersetzt InventoryProperty(dataType=DATE).

    Attributes:
        propertyName: Name der Property
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        DateProperty(propertyName="geburtsdatum", isRequired=True)
        ```
    """

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.DATE,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
        )


@dataclass
class TimeProperty(BaseProperty):
    """
    Time-Property. Ersetzt InventoryProperty(dataType=TIME).

    Attributes:
        propertyName: Name der Property
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        TimeProperty(propertyName="oeffnungszeit", isRequired=True)
        ```
    """

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.TIME,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
        )


@dataclass
class GuidProperty(BaseProperty):
    """
    GUID-Property. Ersetzt InventoryProperty(dataType=GUID).

    Attributes:
        propertyName: Name der Property
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        GuidProperty(propertyName="external_id", isRequired=False)
        ```
    """

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.GUID,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
        )


@dataclass
class FileProperty(BaseProperty):
    """
    File-Property. Ersetzt InventoryProperty(dataType=FILE, file=FilePropertyConfig(...)).

    Attributes:
        propertyName: Name der Property
        maxLength: Maximale Länge in Bytes
        isRequired: Pflichtfeld (Standard: True)
        isUnique: Eindeutig (Standard: False)
        isArray: Array-Feld (Standard: False)
        description: Optionale Beschreibung

    Beispiel:
        ```python
        FileProperty(
            propertyName="dokument",
            maxLength=10485760,  # 10 MB
            isRequired=False,
        )
        ```
    """

    maxLength: int

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.FILE,
            isRequired=self.isRequired,
            isUnique=self.isUnique,
            isArray=self.isArray,
            description=self.description,
            file=FilePropertyConfig(maxLength=self.maxLength),
        )


@dataclass
class TimeSeriesProperty(BaseProperty):
    """
    TimeSeries-Property. Ersetzt InventoryProperty(dataType=TIME_SERIES, timeSeries=TimeSeriesPropertyConfig(...)).

    Attributes:
        propertyName: Name der Property
        timeUnit: Zeiteinheit (z.B. TimeUnit.MINUTE, TimeUnit.HOUR)
        unit: Einheit der Messwerte (z.B. "°C", "kWh", "%")
        multiplier: Multiplikator für Intervall (Standard: 1)
        timeZone: Zeitzone (Standard: "Europe/Berlin")
        valueAlignment: Wert-Ausrichtung (Standard: ValueAlignment.LEFT)
        valueAvailability: Verfügbarkeit (Standard: ValueAvailability.AT_INTERVAL_BEGIN)
        isRequired: Pflichtfeld (Standard: False, da TimeSeries optional sind)
        description: Optionale Beschreibung
        defaultAggregation: Standard-Aggregation (optional)
        startOfTime: Start-Zeitpunkt (optional, ISO-8601)
        enableAudit: Audit aktivieren (Standard: False)
        enableQuotation: Quotierung aktivieren (Standard: False)
        defaultQuotationBehavior: Standard-Quotierungsverhalten (Standard: QuotationBehavior.LATEST)
        allowSpecificsPerInstance: Spezifikationen pro Instanz erlauben (Standard: False)

    Beispiel:
        ```python
        TimeSeriesProperty(
            propertyName="messwerte_temperatur",
            timeUnit=TimeUnit.MINUTE,
            multiplier=15,
            unit="°C",
            timeZone="Europe/Berlin",
        )
        ```
    """

    timeUnit: TimeUnit
    unit: str
    multiplier: int = 1
    timeZone: str = "Europe/Berlin"
    valueAlignment: ValueAlignment = ValueAlignment.LEFT
    valueAvailability: ValueAvailability = ValueAvailability.AT_INTERVAL_BEGIN
    defaultAggregation: Aggregation | None = None
    startOfTime: str | None = None
    enableAudit: bool = False
    enableQuotation: bool = False
    defaultQuotationBehavior: QuotationBehavior = QuotationBehavior.LATEST
    allowSpecificsPerInstance: bool = False

    def to_inventory_property(self) -> InventoryProperty:
        """Konvertiert zu InventoryProperty für GraphQL-Kompatibilität."""
        return InventoryProperty(
            propertyName=self.propertyName,
            dataType=DataType.TIME_SERIES,
            isRequired=self.isRequired,
            isUnique=False,  # TimeSeries sind nie unique
            isArray=False,  # TimeSeries sind nie Arrays
            description=self.description,
            timeSeries=TimeSeriesPropertyConfig(
                interval=IntervalConfig(
                    timeUnit=self.timeUnit, multiplier=self.multiplier
                ),
                unit=self.unit,
                valueAlignment=self.valueAlignment,
                valueAvailability=self.valueAvailability,
                timeZone=self.timeZone,
                defaultAggregation=self.defaultAggregation,
                startOfTime=self.startOfTime,
                enableAudit=self.enableAudit,
                enableQuotation=self.enableQuotation,
                defaultQuotationBehavior=self.defaultQuotationBehavior,
                allowSpecificsPerInstance=self.allowSpecificsPerInstance,
            ),
        )
