Source code for minim.api.tidal._private_api.artists

from __future__ import annotations
from typing import TYPE_CHECKING

from ..._shared import TTLCache, _copy_docstring
from ._shared import PrivateTIDALResourceAPI
from .pages import PrivatePagesAPI
from .users import PrivateUsersAPI

if TYPE_CHECKING:
    from typing import Any

    from ...._types import Collection


[docs] class PrivateArtistsAPI(PrivateTIDALResourceAPI): """ Artists API endpoints for the private TIDAL API. .. important:: This class is managed by :class:`~minim.api.tidal.PrivateTIDALAPIClient` and should not be instantiated directly. """ _ALBUM_TYPES = {"COMPILATIONS", "EPSANDSINGLES"} __slots__ = ()
[docs] @TTLCache.cached_method(ttl="popularity") def get_artist( self, artist_id: int | str, /, country_code: str | None = None ) -> dict[str, Any]: """ Get TIDAL catalog information for an artist. Parameters ---------- artist_id : int or str; positional-only TIDAL ID of the artist. **Examples**: :code:`1566`, :code:`"4676988"`. country_code : str; optional ISO 3166-1 alpha-2 country code. If not provided, the country associated with the current user account or IP address is used. **Example**: :code:`"US"`. Returns ------- artist : dict[str, Any] TIDAL metadata for the artist. .. admonition:: Sample response :class: response dropdown .. code-block:: { "artistRoles": [ { "category": <str>, "categoryId": <int> } ], "artistTypes": <list[str]>, "handle": <str>, "id": <int>, "mixes": { "ARTIST_MIX": <str> }, "name": <str>, "picture": <str>, "popularity": <int>, "selectedAlbumCoverFallback": None, "spotlighted": <bool>, "url": <str>, "userId": <int> } """ return self._get_resource( "artists", artist_id, country_code=country_code )
[docs] @TTLCache.cached_method(ttl="popularity") def get_artist_albums( self, artist_id: int | str, /, country_code: str | None = None, *, album_type: str | None = None, limit: int | None = None, offset: int | None = None, ) -> dict[str, Any]: """ Get TIDAL catalog information for albums by an artist. Parameters ---------- artist_id : int or str; positional-only TIDAL ID of the artist. **Examples**: :code:`1566`, :code:`"4676988"`. country_code : str; optional ISO 3166-1 alpha-2 country code. If not provided, the country associated with the current user account or IP address is used. **Example**: :code:`"US"`. album_type : str; keyword-only; optional Album type to return. **Valid values**: :code:`"COMPILATIONS"`, :code:`"EPSANDSINGLES"`. limit : int; keyword-only; optional Maximum number of albums to return. **Valid range**: :code:`1` to :code:`100`. **API default**: :code:`10`. offset : int; keyword-only; optional Index of the first album to return. Use with `limit` to get the next batch of albums. **Minimum value**: :code:`0`. **API default**: :code:`0`. Returns ------- albums : dict[str, Any] Page of TIDAL metadata for the artist's albums. .. admonition:: Sample response :class: response dropdown .. code-block:: { "items": [ { "adSupportedStreamReady": <bool>, "allowStreaming": <bool>, "artist": { "handle": <str>, "id": <int>, "name": <str>, "picture": <str>, "type": <str> }, "artists": [ { "handle": <str>, "id": <int>, "name": <str>, "picture": <str>, "type": <str> } ], "audioModes": <list[str]>, "audioQuality": <str>, "copyright": <str>, "cover": <str>, "djReady": <bool>, "duration": <int>, "explicit": <bool>, "id": <int>, "mediaMetadata": { "tags": <list[str]> }, "numberOfTracks": <int>, "numberOfVideos": <int>, "numberOfVolumes": <int>, "payToStream": <bool>, "popularity": <int>, "premiumStreamingOnly": <bool>, "releaseDate": <str>, "stemReady": <bool>, "streamReady": <bool>, "streamStartDate": <str>, "title": <str>, "type": <str>, "upc": <str>, "upload": <bool>, "url": <str>, "version": <str>, "vibrantColor": <str>, "videoCover": <str> } ], "limit": <int>, "offset": <int>, "totalNumberOfItems": <int> } """ params = {} if album_type is not None: if album_type not in self._ALBUM_TYPES: raise ValueError( f"Invalid album type {album_type!r}. Valid values: " f"{self._join_values(self._ALBUM_TYPES)}." ) params["filter"] = album_type return self._get_resource_relationship( "artists", artist_id, "albums", country_code=country_code, limit=limit, offset=offset, params=params, )
[docs] @TTLCache.cached_method(ttl="static") def get_artist_biography( self, artist_id: int | str, /, country_code: str | None = None ) -> dict[str, Any]: """ Get an artist's biography. Parameters ---------- artist_id : int or str; positional-only TIDAL ID of the artist. **Examples**: :code:`1566`, :code:`"4676988"`. country_code : str; optional ISO 3166-1 alpha-2 country code. If not provided, the country associated with the current user account or IP address is used. **Example**: :code:`"US"`. Returns ------- biography : dict[str, Any] Metadata for the artist's biography. .. admonition:: Sample response :class: response dropdown .. code-block:: { "lastUpdated": <str>, "source": <str>, "summary": <str>, "text": <str> } """ return self._get_resource_relationship( "artists", artist_id, "bio", country_code=country_code )
[docs] @TTLCache.cached_method(ttl="static") def get_artist_mix_id( self, artist_id: int | str, /, country_code: str | None = None ) -> dict[str, str]: """ Get the TIDAL ID of an artist's mix. Parameters ---------- artist_id : int or str; positional-only TIDAL ID of the artist. **Examples**: :code:`1566`, :code:`"4676988"`. country_code : str; optional ISO 3166-1 alpha-2 country code. If not provided, the country associated with the current user account or IP address is used. **Example**: :code:`"US"`. Returns ------- mix_id : dict[str, str] TIDAL ID of the artist's mix. **Sample response**: :code:`{"id": <str>}`. """ return self._get_resource_relationship( "artists", artist_id, "mix", country_code=country_code )
[docs] @TTLCache.cached_method(ttl="popularity") def get_artist_mix( self, artist_id: int | str, /, country_code: str | None = None, *, limit: int | None = None, offset: int | None = None, ) -> dict[str, Any]: """ Get TIDAL catalog information for an artist's mix. Parameters ---------- artist_id : int or str; positional-only TIDAL ID of the artist. **Examples**: :code:`1566`, :code:`"4676988"`. country_code : str; optional ISO 3166-1 alpha-2 country code. If not provided, the country associated with the current user account or IP address is used. **Example**: :code:`"US"`. limit : int; keyword-only; optional Maximum number of tracks to return. **Valid range**: :code:`1` to :code:`100`. **API default**: :code:`10`. offset : int; keyword-only; optional Index of the first track to return. Use with `limit` to get the next batch of tracks. **Minimum value**: :code:`0`. **API default**: :code:`0`. Returns ------- mix : dict[str, Any] Page of TIDAL metadata for the tracks in the artist's mix. .. admonition:: Sample response :class: response dropdown .. code-block:: { "items": [ { "accessType": <str>, "adSupportedStreamReady": <bool>, "album": { "cover": <str>, "id": <int>, "title": <str>, "vibrantColor": <str>, "videoCover": <str> }, "allowStreaming": <bool>, "artist": { "handle": <str>, "id": <int>, "name": <str>, "picture": <str>, "type": <str> }, "artists": [ { "handle": <str>, "id": <int>, "name": <str>, "picture": <str>, "type": <str> } ], "audioModes": <list[str]>, "audioQuality": <str>, "bpm": <int>, "copyright": <str>, "djReady": <bool>, "duration": <int>, "editable": <bool>, "explicit": <bool>, "id": <int>, "isrc": <str>, "key": <str>, "keyScale": <str>, "mediaMetadata": { "tags": <list[str]> }, "mixes": { "TRACK_MIX": <str> }, "payToStream": <bool>, "peak": <float>, "popularity": <int>, "premiumStreamingOnly": <bool>, "replayGain": <float>, "spotlighted": <bool>, "stemReady": <bool>, "streamReady": <bool>, "streamStartDate": <str>, "title": <str>, "trackNumber": <int>, "upload": <bool>, "url": <str>, "version": <str>, "volumeNumber": <int> } ], "limit": <int>, "offset": <int>, "totalNumberOfItems": <int> } """ return self._get_resource_relationship( "artists", artist_id, "radio", country_code=country_code, limit=limit, offset=offset, )
[docs] @TTLCache.cached_method(ttl="popularity") def get_artist_top_tracks( self, artist_id: int | str, /, country_code: str | None = None, *, limit: int | None = None, offset: int | None = None, ) -> dict[str, Any]: """ Get TIDAL catalog information for top tracks by an artist. Parameters ---------- artist_id : int or str; positional-only TIDAL ID of the artist. **Examples**: :code:`1566`, :code:`"4676988"`. country_code : str; optional ISO 3166-1 alpha-2 country code. If not provided, the country associated with the current user account or IP address is used. **Example**: :code:`"US"`. limit : int; keyword-only; optional Maximum number of tracks to return. **Valid range**: :code:`1` to :code:`100`. **API default**: :code:`10`. offset : int; keyword-only; optional Index of the first track to return. Use with `limit` to get the next batch of tracks. **Minimum value**: :code:`0`. **API default**: :code:`0`. Returns ------- top_tracks : dict[str, Any] Page of TIDAL metadata for the artist's top tracks. .. admonition:: Sample response :class: response dropdown .. code-block:: { "items": [ { "accessType": <str>, "adSupportedStreamReady": <bool>, "album": { "cover": <str>, "id": <int>, "title": <str>, "vibrantColor": <str>, "videoCover": <str> }, "allowStreaming": <bool>, "artist": { "handle": <str>, "id": <int>, "name": <str>, "picture": <str>, "type": <str> }, "artists": [ { "handle": <str>, "id": <int>, "name": <str>, "picture": <str>, "type": <str> } ], "audioModes": <list[str]>, "audioQuality": <str>, "bpm": <int>, "copyright": <str>, "djReady": <bool>, "duration": <int>, "editable": <bool>, "explicit": <bool>, "id": <int>, "isrc": <str>, "key": <str>, "keyScale": <str>, "mediaMetadata": { "tags": <list[str]> }, "mixes": { "TRACK_MIX": <str> }, "payToStream": <bool>, "peak": <float>, "popularity": <int>, "premiumStreamingOnly": <bool>, "replayGain": <float>, "spotlighted": <bool>, "stemReady": <bool>, "streamReady": <bool>, "streamStartDate": <str>, "title": <str>, "trackNumber": <int>, "upload": <bool>, "url": <str>, "version": <str>, "volumeNumber": <int> } ], "limit": <int>, "offset": <int>, "totalNumberOfItems": <int> } """ return self._get_resource_relationship( "artists", artist_id, "toptracks", country_code=country_code, limit=limit, offset=offset, )
[docs] @TTLCache.cached_method(ttl="popularity") def get_artist_videos( self, artist_id: int | str, /, country_code: str | None = None, *, limit: int | None = None, offset: int | None = None, ) -> dict[str, Any]: """ Get TIDAL catalog information for videos by an artist. Parameters ---------- artist_id : int or str; positional-only TIDAL ID of the artist. **Examples**: :code:`1566`, :code:`"4676988"`. country_code : str; optional ISO 3166-1 alpha-2 country code. If not provided, the country associated with the current user account or IP address is used. **Example**: :code:`"US"`. limit : int; keyword-only; optional Maximum number of videos to return. **Valid range**: :code:`1` to :code:`100`. **API default**: :code:`10`. offset : int; keyword-only; optional Index of the first video to return. Use with `limit` to get the next batch of videos. **Minimum value**: :code:`0`. **API default**: :code:`0`. Returns ------- videos : dict[str, Any] Page of TIDAL metadata for the artist's videos. .. admonition:: Sample response :class: response dropdown .. code-block:: { "items": [ { "adSupportedStreamReady": <bool>, "adsPrePaywallOnly": <bool>, "adsUrl": <str>, "album": { "cover": <str>, "id": <int>, "title": <str>, "vibrantColor": <str>, "videoCover": <str> }, "allowStreaming": <bool>, "artist": { "handle": <str>, "id": <int>, "name": <str>, "picture": <str>, "type": <str> }, "artists": [ { "handle": <str>, "id": <int>, "name": <str>, "picture": <str>, "type": <str> } ], "djReady": <bool>, "duration": <int>, "explicit": <bool>, "id": <int>, "imageId": <str>, "imagePath": <str>, "popularity": <int>, "quality": <str>, "releaseDate": <str>, "stemReady": <bool>, "streamReady": <bool>, "streamStartDate": <str>, "title": <str>, "trackNumber": <int>, "type": <str>, "vibrantColor": <str>, "volumeNumber": <int> } ], "limit": <int>, "offset": <int>, "totalNumberOfItems": <int> } """ return self._get_resource_relationship( "artists", artist_id, "videos", country_code=country_code, limit=limit, offset=offset, )
[docs] @TTLCache.cached_method(ttl="popularity") def get_similar_artists( self, artist_id: int | str, /, country_code: str | None = None, *, limit: int | None = None, offset: int | None = None, ) -> dict[str, Any]: """ Get TIDAL catalog information for similar artists. Parameters ---------- artist_id : int or str; positional-only TIDAL ID of the artist. **Examples**: :code:`1566`, :code:`"4676988"`. country_code : str; optional ISO 3166-1 alpha-2 country code. If not provided, the country associated with the user account is used. **Example**: :code:`"US"`. limit : int; keyword-only; optional Maximum number of artists to return. **Valid range**: :code:`1` to :code:`100`. **API default**: :code:`10`. offset : int; keyword-only; optional Index of the first artist to return. Use with `limit` to get the next batch of artists. **Minimum value**: :code:`0`. **API default**: :code:`0`. Returns ------- similar_artists : dict[str, Any] Page of TIDAL metadata for the similar artists. .. admonition:: Sample response :class: response dropdown .. code-block:: { "items": [ { "artistRoles": <list[str]>, "artistTypes": <list[str]>, "banner": <str>, "handle": <str>, "id": <int>, "mixes": { "ARTIST_MIX": <str> }, "name": <str>, "picture": <str>, "popularity": <int>, "relationType": <str>, "selectedAlbumCoverFallback": None, "spotlighted": <bool>, "type": <str>, "url": <str>, "userId": <int> } ], "limit": <int>, "offset": <int>, "source": <str>, "totalNumberOfItems": <int> } """ return self._get_resource_relationship( "artists", artist_id, "similar", country_code=country_code, limit=limit, offset=offset, )
[docs] @_copy_docstring(PrivatePagesAPI.get_artist_page) def get_artist_page( self, artist_id: int | str, /, country_code: str | None = None, *, device_type: str = "BROWSER", locale: str | None = None, ) -> dict[str, Any]: return self._client.pages.get_artist_page( artist_id, country_code, device_type=device_type, locale=locale )
[docs] @_copy_docstring(PrivateUsersAPI.get_user_blocked_artists) def get_user_blocked_artists( self, user_id: int | str | None = None, /, *, limit: int | None = None, offset: int | None = None, ) -> dict[str, Any]: return self._client.users.get_user_blocked_artists( user_id, limit=limit, offset=offset )
[docs] @_copy_docstring(PrivateUsersAPI.block_artist) def block_artist( self, artist_id: int | str, /, user_id: int | str | None = None ) -> None: self._client.users.block_artists(artist_id, user_id)
[docs] @_copy_docstring(PrivateUsersAPI.unblock_artist) def unblock_artist( self, artist_id: int | str, /, user_id: int | str | None = None ) -> None: self._client.users.unblock_artists(artist_id, user_id)
[docs] @_copy_docstring(PrivateUsersAPI.follow_artists) def get_user_followed_artists( self, user_id: int | str | None = None, /, country_code: str | None = None, *, limit: int | None = None, offset: int | None = None, sort_by: str | None = None, descending: bool | None = None, ) -> dict[str, Any]: return self._client.users.get_user_followed_artists( user_id, country_code, limit=limit, offset=offset, sort_by=sort_by, descending=descending, )
[docs] @_copy_docstring(PrivateUsersAPI.follow_artists) def follow_artists( self, artist_ids: int | str | Collection[int | str], /, user_id: int | str | None = None, country_code: str | None = None, *, missing_ok: bool | None = None, ) -> None: self._client.users.follow_artists( artist_ids, user_id, country_code, missing_ok=missing_ok, )
[docs] @_copy_docstring(PrivateUsersAPI.unfollow_artists) def unfollow_artists( self, artist_ids: int | str | Collection[int | str], /, user_id: int | str | None = None, ) -> None: self._client.users.unfollow_artists(artist_ids, user_id)