"""
This submodule contains the Track class and TrackPlaylist, which is used to represent a Lavalink track and playlist.
"""
import re
import typing

from pydantic import BaseModel

from .utils import MISSING


class Track(BaseModel):
    """
    This class is based on :class:`BaseModel` and is used to represent a Wavelink Track.
    """

    id_: str
    info: dict
    query: typing.Optional[str] = MISSING
    dead: bool = False
    thumb: typing.Optional[str] = MISSING
    requester: typing.Any = MISSING

    @property
    def title(self) -> str:
        """
        This property returns the track title.
        """
        title = self.info.get("title")
        return title

    @property
    def ytid(self) -> typing.Optional[str]:
        """
        This property returns the YouTube ID of the track.
        """
        youtube_id = self.identifier if re.match(r"^[a-zA-Z0-9_-]{11}$", self.identifier) else None
        return youtube_id

    @property
    def is_stream(self) -> bool:
        """
        This property returns whether the track is a stream or not.
        """
        return self.info.get("isStream")

    @property
    def identifier(self) -> typing.Optional[str]:
        """
        This property returns the tracks' identifier.
        """
        return self.info.get("identifier")

    @property
    def uri(self) -> typing.Optional[str]:
        """
        This property returns the tracks' URI.
        """
        return self.info.get("uri")

    @property
    def author(self):
        return self.info.get("author")

    @property
    def length(self) -> int:
        """
        This property returns the duration of the track in milliseconds.
        """
        length = int(self.info.get("length"))
        return length

    @property
    def duration(self):
        """
        Alias to `length`
        """
        return self.length

    @property
    def thumbnail(self) -> typing.Optional[str]:
        """
        This property returns the thumbnail URL associated with the track.
        """
        if self.ytid:
            self.thumb = f"https://img.youtube.com/vi/{self.ytid}/hqdefault.jpg"
        else:
            self.thumb = "https://via.placeholder.com/150%"
        return self.thumb

    def __str__(self):
        return self.title

    def __repr__(self):
        return f"<wavelink.Track title={self.title}, uri={self.uri}>"

    @property
    def is_dead(self):
        return self.dead


class TrackPlaylist(BaseModel):
    """
    This class is based on :class:`BaseModel` and is used to represent a :class:`Track` Playlist containing multiple
    :class:`Track`'s.
    """

    data: dict

    @property
    def tracks(self) -> list[Track]:
        """
        This property returns a list of individual :class:`Track` objects from the playlist.
        """
        tracks = [Track(id_=track["track"], info=track["info"]) for track in self.data["tracks"]]
        return tracks

    def __repr__(self):
        return f"<wavelink.TrackPlaylist tracks={self.tracks}>"

"""
This submodule contains the Track class and TrackPlaylist, which is used to represent a Lavalink track and playlist.
"""
import re
import typing

from pydantic import BaseModel

from .utils import MISSING


class Track(BaseModel):
    """
    This class is based on :class:`BaseModel` and is used to represent a Wavelink Track.
    """

    id_: str
    info: dict
    query: typing.Optional[str] = MISSING
    dead: bool = False
    thumb: typing.Optional[str] = MISSING
    requester: typing.Any = MISSING

    @property
    def title(self) -> str:
        """
        This property returns the track title.
        """
        title = self.info.get("title")
        return title

    @property
    def ytid(self) -> typing.Optional[str]:
        """
        This property returns the YouTube ID of the track.
        """
        youtube_id = self.identifier if re.match(r"^[a-zA-Z0-9_-]{11}$", self.identifier) else None
        return youtube_id

    @property
    def is_stream(self) -> bool:
        """
        This property returns whether the track is a stream or not.
        """
        return self.info.get("isStream")

    @property
    def identifier(self) -> typing.Optional[str]:
        """
        This property returns the tracks' identifier.
        """
        return self.info.get("identifier")

    @property
    def uri(self) -> typing.Optional[str]:
        """
        This property returns the tracks' URI.
        """
        return self.info.get("uri")

    @property
    def author(self):
        return self.info.get("author")

    @property
    def length(self) -> int:
        """
        This property returns the duration of the track in milliseconds.
        """
        length = int(self.info.get("length"))
        return length

    @property
    def duration(self):
        """
        Alias to `length`
        """
        return self.length

    @property
    def thumbnail(self) -> typing.Optional[str]:
        """
        This property returns the thumbnail URL associated with the track.
        """
        if self.ytid:
            self.thumb = f"https://img.youtube.com/vi/{self.ytid}/hqdefault.jpg"
        else:
            self.thumb = "https://via.placeholder.com/150%"
        return self.thumb

    def __str__(self):
        return self.title

    def __repr__(self):
        return f"<wavelink.Track title={self.title}, uri={self.uri}>"

    @property
    def is_dead(self):
        return self.dead


class TrackPlaylist(BaseModel):
    """
    This class is based on :class:`BaseModel` and is used to represent a :class:`Track` Playlist containing multiple
    :class:`Track`'s.
    """

    data: dict

    @property
    def tracks(self) -> list[Track]:
        """
        This property returns a list of individual :class:`Track` objects from the playlist.
        """
        tracks = [Track(id_=track["track"], info=track["info"]) for track in self.data["tracks"]]
        return tracks

    def __repr__(self):
        return f"<wavelink.TrackPlaylist tracks={self.tracks}>"

This submodule contains the Track class and TrackPlaylist, which is used to represent a Lavalink track and playlist. This class is based on :class:`BaseModel` and is used to represent a Wavelink Track. This property returns the track title. This property returns the YouTube ID of the track. This property returns whether the track is a stream or not. This property returns the tracks' identifier. This property returns the tracks' URI. This property returns the duration of the track in milliseconds. Alias to `length` This property returns the thumbnail URL associated with the track. This class is based on :class:`BaseModel` and is used to represent a :class:`Track` Playlist containing multiple     :class:`Track`'s. This property returns a list of individual :class:`Track` objects from the playlist.