# coding: utf-8

"""
    Mozart platform API

    API for interacting with the Mozart platform.

    The version of the OpenAPI document: 0.2.0
    Contact: support@bang-olufsen.dk
    Generated by OpenAPI Generator (https://openapi-generator.tech)

    Do not edit the class manually.
"""  # noqa: E501


from __future__ import annotations
import pprint
import re  # noqa: F401
import json


from typing import Optional, Union

try:
    from pydantic.v1 import BaseModel, Field, StrictStr, confloat, conint, validator
except ImportError:
    from pydantic import BaseModel, Field, StrictStr, confloat, conint, validator

from mozart_api.models.play_queue_item import PlayQueueItem
from mozart_api.models.play_queue_settings import PlayQueueSettings
from mozart_api.models.source_type_enum import SourceTypeEnum
from mozart_api.models.stand_position import StandPosition


class Action(BaseModel):
    """
    An action object. Examples:  RadioAction: ```json {   \"type\": \"radio\",   \"radioStationId\": \"8779112938791514\" } ```  ToneAction: ```json {   \"type\": \"tone\",   \"toneName\": \"alarm_2\" } ```  SourcePresetAction: ```json {   \"type\": \"sourcePreset\",   \"source\": {     \"value\": \"spotify\"   },   \"presetKey\": \"Preset3\" } ```  DeezerFlowAction: ```json {   \"type\": \"deezerFlow\",   \"deezerUserId\": \"1234\" } ```  ActivateSourceAction: ```json {   \"type\": \"activateSource\",   \"source\": {     \"value\": \"spotify\"   } } ```  PlayQueueAction: ```   {     \"type\": \"playQueue\",     \"queueItem\": {       \"provider\": {         \"value\": \"deezer\"       },       \"startNowFromPosition\": 0,       \"type\": \"playlist\",       \"uri\": \"playlist:8074581462\"     },     \"queueSettings\": {       \"consume\": false,       \"repeat\": \"none\",       \"shuffle\": false     }   } ```  StandbyAction: ```json {   \"type\": \"standby\" } ```  AllStandbyAction: ```json {   \"type\": \"allStandby\" } ```  TouchToJoinAction: ```json {   \"type\": \"touchToJoin\" } ```  ButtonShortPressAction: ```json {   \"type\": \"buttonShortPress\",   \"buttonName\": \"preset1\" } ```  FallbackAction: ```json {   \"type\": \"fallback\" } ```  VolumeAction: ```json {   \"type\": \"volume\",   \"volumeLevel\": 25 } ```  StopAction: ```json {   \"type\": \"stop\",   \"stopDuration\": 1300 } ```  TriggerContentAction: ```json {   \"contentId\": \"tv://netflix\",   \"type\": \"triggerContent\" } ```  SpeakerGroupAction: ```json {   \"type\": \"speakerGroup\",   \"speakerGroupId\": \"00112233-4455-6677-8899-aabbccddeeff\" } ```  ListeningModeAction: ```json {   \"type\": \"listeningMode\",   \"listeningModeId\": 1234 } ```  StandAction: ```json {   \"type\": \"stand\",   \"standPosition\": {     \"angle\": 7.5   } } ```  GainAction: ```json {   \"type\": \"sourceGain\",   \"source\": {     \"value\": \"spotify\"   },   \"gainDb\": 1.0 } ```   # noqa: E501
    """

    button_name: Optional[StrictStr] = Field(
        default=None,
        alias="buttonName",
        description="Name of the Button used for button-press types ('buttonShortPress')",
    )
    content_id: Optional[StrictStr] = Field(
        default=None,
        alias="contentId",
        description="Id of content only used for 'type=triggerContent'",
    )
    deezer_user_id: Optional[StrictStr] = Field(
        default=None,
        alias="deezerUserId",
        description="Id of user only used for 'type=deezerFlow' and is optional",
    )
    gain_db: Optional[
        Union[confloat(le=12, ge=-12, strict=True), conint(le=12, ge=-12, strict=True)]
    ] = Field(
        default=None, alias="gainDb", description="Only usef for 'type=sourceGain'"
    )
    listening_mode_id: Optional[conint(strict=True, ge=0)] = Field(
        default=None, alias="listeningModeId"
    )
    preset_key: Optional[StrictStr] = Field(
        default=None, alias="presetKey", description="Only used for 'type=sourcePreset'"
    )
    queue_item: Optional[PlayQueueItem] = Field(default=None, alias="queueItem")
    queue_settings: Optional[PlayQueueSettings] = Field(
        default=None, alias="queueSettings"
    )
    radio_station_id: Optional[StrictStr] = Field(
        default=None,
        alias="radioStationId",
        description="Id of RadioStation only used for 'type=radio'",
    )
    source: Optional[SourceTypeEnum] = None
    speaker_group_id: Optional[StrictStr] = Field(default=None, alias="speakerGroupId")
    stand_position: Optional[StandPosition] = Field(default=None, alias="standPosition")
    stop_duration: Optional[conint(strict=True, ge=0)] = Field(
        default=None,
        alias="stopDuration",
        description="The duration to wait (seconds) until stopping only used for 'type=stop'",
    )
    tone_name: Optional[StrictStr] = Field(
        default=None,
        alias="toneName",
        description="Name of the tone only used for 'type=tone'",
    )
    type: StrictStr = Field(default=..., description="The type of Action")
    volume_level: Optional[conint(strict=True, le=100, ge=0)] = Field(
        default=None,
        alias="volumeLevel",
        description="The volume level to configure only used for 'type=volume'",
    )
    __properties = [
        "buttonName",
        "contentId",
        "deezerUserId",
        "gainDb",
        "listeningModeId",
        "presetKey",
        "queueItem",
        "queueSettings",
        "radioStationId",
        "source",
        "speakerGroupId",
        "standPosition",
        "stopDuration",
        "toneName",
        "type",
        "volumeLevel",
    ]

    @validator("button_name")
    def button_name_validate_enum(cls, value):
        """Validates the enum"""
        if value is None:
            return value

        if value not in ("preset1", "preset2", "preset3", "preset4"):
            raise ValueError(
                "must be one of enum values ('preset1', 'preset2', 'preset3', 'preset4')"
            )
        return value

    @validator("tone_name")
    def tone_name_validate_enum(cls, value):
        """Validates the enum"""
        if value is None:
            return value

        if value not in ("alarm_1", "alarm_2"):
            raise ValueError("must be one of enum values ('alarm_1', 'alarm_2')")
        return value

    @validator("type")
    def type_validate_enum(cls, value):
        """Validates the enum"""
        if value not in (
            "standby",
            "tone",
            "radio",
            "sourcePreset",
            "deezerFlow",
            "activateSource",
            "playQueue",
            "buttonShortPress",
            "allStandby",
            "touchToJoin",
            "fallback",
            "volume",
            "stop",
            "triggerContent",
            "speakerGroup",
            "listeningMode",
            "stand",
            "sourceGain",
        ):
            raise ValueError(
                "must be one of enum values ('standby', 'tone', 'radio', 'sourcePreset', 'deezerFlow', 'activateSource', 'playQueue', 'buttonShortPress', 'allStandby', 'touchToJoin', 'fallback', 'volume', 'stop', 'triggerContent', 'speakerGroup', 'listeningMode', 'stand', 'sourceGain')"
            )
        return value

    class Config:
        """Pydantic configuration"""

        allow_population_by_field_name = True
        validate_assignment = True

    def to_str(self) -> str:
        """Returns the string representation of the model using alias"""
        return pprint.pformat(self.dict(by_alias=True))

    def to_json(self) -> str:
        """Returns the JSON representation of the model using alias"""
        return json.dumps(self.to_dict())

    @classmethod
    def from_json(cls, json_str: str) -> Action:
        """Create an instance of Action from a JSON string"""
        return cls.from_dict(json.loads(json_str))

    def to_dict(self):
        """Returns the dictionary representation of the model using alias"""
        _dict = self.dict(by_alias=True, exclude={}, exclude_none=True)
        # override the default output from pydantic by calling `to_dict()` of queue_item
        if self.queue_item:
            _dict["queueItem"] = self.queue_item.to_dict()
        # override the default output from pydantic by calling `to_dict()` of queue_settings
        if self.queue_settings:
            _dict["queueSettings"] = self.queue_settings.to_dict()
        # override the default output from pydantic by calling `to_dict()` of source
        if self.source:
            _dict["source"] = self.source.to_dict()
        # override the default output from pydantic by calling `to_dict()` of stand_position
        if self.stand_position:
            _dict["standPosition"] = self.stand_position.to_dict()
        # set to None if button_name (nullable) is None
        # and __fields_set__ contains the field
        if self.button_name is None and "button_name" in self.__fields_set__:
            _dict["buttonName"] = None

        # set to None if content_id (nullable) is None
        # and __fields_set__ contains the field
        if self.content_id is None and "content_id" in self.__fields_set__:
            _dict["contentId"] = None

        # set to None if deezer_user_id (nullable) is None
        # and __fields_set__ contains the field
        if self.deezer_user_id is None and "deezer_user_id" in self.__fields_set__:
            _dict["deezerUserId"] = None

        # set to None if preset_key (nullable) is None
        # and __fields_set__ contains the field
        if self.preset_key is None and "preset_key" in self.__fields_set__:
            _dict["presetKey"] = None

        # set to None if radio_station_id (nullable) is None
        # and __fields_set__ contains the field
        if self.radio_station_id is None and "radio_station_id" in self.__fields_set__:
            _dict["radioStationId"] = None

        # set to None if stop_duration (nullable) is None
        # and __fields_set__ contains the field
        if self.stop_duration is None and "stop_duration" in self.__fields_set__:
            _dict["stopDuration"] = None

        # set to None if tone_name (nullable) is None
        # and __fields_set__ contains the field
        if self.tone_name is None and "tone_name" in self.__fields_set__:
            _dict["toneName"] = None

        # set to None if volume_level (nullable) is None
        # and __fields_set__ contains the field
        if self.volume_level is None and "volume_level" in self.__fields_set__:
            _dict["volumeLevel"] = None

        return _dict

    @classmethod
    def from_dict(cls, obj: dict) -> Action:
        """Create an instance of Action from a dict"""
        if obj is None:
            return None

        if not isinstance(obj, dict):
            return Action.parse_obj(obj)

        _obj = Action.parse_obj(
            {
                "button_name": obj.get("buttonName"),
                "content_id": obj.get("contentId"),
                "deezer_user_id": obj.get("deezerUserId"),
                "gain_db": obj.get("gainDb"),
                "listening_mode_id": obj.get("listeningModeId"),
                "preset_key": obj.get("presetKey"),
                "queue_item": (
                    PlayQueueItem.from_dict(obj.get("queueItem"))
                    if obj.get("queueItem") is not None
                    else None
                ),
                "queue_settings": (
                    PlayQueueSettings.from_dict(obj.get("queueSettings"))
                    if obj.get("queueSettings") is not None
                    else None
                ),
                "radio_station_id": obj.get("radioStationId"),
                "source": (
                    SourceTypeEnum.from_dict(obj.get("source"))
                    if obj.get("source") is not None
                    else None
                ),
                "speaker_group_id": obj.get("speakerGroupId"),
                "stand_position": (
                    StandPosition.from_dict(obj.get("standPosition"))
                    if obj.get("standPosition") is not None
                    else None
                ),
                "stop_duration": obj.get("stopDuration"),
                "tone_name": obj.get("toneName"),
                "type": obj.get("type"),
                "volume_level": obj.get("volumeLevel"),
            }
        )
        return _obj
