Skip to content

Commit 6fe4788

Browse files
authored
Merge pull request #330 from EbbLabs/feature/get_radio_mix
Add Track.get_radio_mix and Artist.get_radio_mix to get radio as Mix
2 parents f45189e + ebdbe76 commit 6fe4788

File tree

4 files changed

+82
-17
lines changed

4 files changed

+82
-17
lines changed

tests/test_artist.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020

2121
import tidalapi
2222
from tidalapi.exceptions import ObjectNotFound
23+
from tidalapi.mix import MixType
2324

2425
from .cover import verify_image_cover
2526

@@ -140,6 +141,15 @@ def test_get_radio(session):
140141
assert radio[0].artist.name == artist.name
141142

142143

144+
def test_get_radio_mix(session):
145+
artist = session.artist(3514310)
146+
radio = artist.get_radio_mix()
147+
assert radio.id == "000038b3b74d5ce3a17b43a36d62bb"
148+
assert radio.title == "The Turtles"
149+
assert radio.sub_title == "Artist Radio"
150+
assert radio.mix_type == MixType.artist
151+
152+
143153
def test_artist_image(session):
144154
artist = session.artist(4822757)
145155
verify_image_cover(session, artist, [160, 320, 480, 750])

tests/test_media.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@
3131
MimeType,
3232
Quality,
3333
)
34+
from tidalapi.mix import MixType
3435

3536
from .cover import verify_image_resolution, verify_video_resolution
3637

@@ -448,6 +449,15 @@ def test_get_track_radio_limit_100(session):
448449
assert len(similar_tracks) == 100
449450

450451

452+
def test_get_radio_mix(session):
453+
track = session.track(12445712)
454+
radio = track.get_radio_mix()
455+
assert radio.id == "001c2cbc32b5b7c17f8c0aa55d9541"
456+
assert radio.title == "Happy Together"
457+
assert radio.sub_title == "The Turtles"
458+
assert radio.mix_type == MixType.track
459+
460+
451461
def test_get_stream_bts(session):
452462
track = session.track(77646170) # Beck: Sea Change, Track: The Golden Age
453463
# Set session as BTS type (i.e. low_320k/HIGH Quality)

tidalapi/artist.py

Lines changed: 39 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -25,9 +25,11 @@
2525
import dateutil.parser
2626
from typing_extensions import NoReturn
2727

28-
from tidalapi.exceptions import ObjectNotFound, TooManyRequests
28+
from tidalapi.exceptions import MetadataNotAvailable, ObjectNotFound, TooManyRequests
2929
from tidalapi.types import JsonObj
3030

31+
from . import mix
32+
3133
if TYPE_CHECKING:
3234
from tidalapi.album import Album
3335
from tidalapi.media import Track, Video
@@ -226,21 +228,45 @@ def get_similar(self) -> List["Artist"]:
226228
),
227229
)
228230

229-
def get_radio(self) -> List["Track"]:
230-
"""Queries TIDAL for the artist radio, which is a mix of tracks that are similar
231-
to what the artist makes.
231+
def get_radio(self, limit: int = 100) -> List["Track"]:
232+
"""Queries TIDAL for the artist radio, i.e. a list of tracks similar to this
233+
artist.
232234
233235
:return: A list of :class:`Tracks <tidalapi.media.Track>`
234236
"""
235-
params = {"limit": 100}
236-
return cast(
237-
List["Track"],
238-
self.request.map_request(
239-
f"artists/{self.id}/radio",
240-
params=params,
241-
parse=self.session.parse_track,
242-
),
243-
)
237+
params = {"limit": limit}
238+
239+
try:
240+
request = self.request.request(
241+
"GET", "artists/%s/radio" % self.id, params=params
242+
)
243+
except ObjectNotFound:
244+
raise MetadataNotAvailable("Track radio not available for this track")
245+
except TooManyRequests:
246+
raise TooManyRequests("Track radio unavailable")
247+
else:
248+
json_obj = request.json()
249+
radio = self.request.map_json(json_obj, parse=self.session.parse_track)
250+
assert isinstance(radio, list)
251+
return cast(List["Track"], radio)
252+
253+
def get_radio_mix(self) -> mix.Mix:
254+
"""Queries TIDAL for the artist radio, i.e. mix of tracks that are similar to
255+
this artist.
256+
257+
:return: A :class:`Mix <tidalapi.mix.Mix>`
258+
:raises: A :class:`exceptions.MetadataNotAvailable` if no track radio mix is available
259+
"""
260+
261+
try:
262+
request = self.request.request("GET", "artists/%s/mix" % self.id)
263+
except ObjectNotFound:
264+
raise MetadataNotAvailable("Artist radio not available for this artist")
265+
except TooManyRequests:
266+
raise TooManyRequests("Artist radio unavailable")
267+
else:
268+
json_obj = request.json()
269+
return self.session.mix(json_obj.get("id"))
244270

245271
def items(self) -> List[NoReturn]:
246272
"""The artist page does not supply any items. This only exists for symmetry with

tidalapi/media.py

Lines changed: 23 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,8 @@
5151
)
5252
from tidalapi.types import JsonObj
5353

54+
from . import mix
55+
5456

5557
class Quality(str, Enum):
5658
low_96k: str = "LOW"
@@ -385,11 +387,11 @@ def lyrics(self) -> "Lyrics":
385387
return cast("Lyrics", lyrics)
386388

387389
def get_track_radio(self, limit: int = 100) -> List["Track"]:
388-
"""Queries TIDAL for the track radio, which is a mix of tracks that are similar
389-
to this track.
390+
"""Queries TIDAL for the track radio mix as a list of tracks similar to this
391+
track.
390392
391393
:return: A list of :class:`Tracks <tidalapi.media.Track>`
392-
:raises: A :class:`exceptions.MetadataNotAvailable` if no track radio is available
394+
:raises: A :class:`exceptions.MetadataNotAvailable` if no track radio mix is available
393395
"""
394396
params = {"limit": limit}
395397

@@ -400,13 +402,30 @@ def get_track_radio(self, limit: int = 100) -> List["Track"]:
400402
except ObjectNotFound:
401403
raise MetadataNotAvailable("Track radio not available for this track")
402404
except TooManyRequests:
403-
raise TooManyRequests("Track radio unavailable)")
405+
raise TooManyRequests("Track radio unavailable")
404406
else:
405407
json_obj = request.json()
406408
tracks = self.requests.map_json(json_obj, parse=self.session.parse_track)
407409
assert isinstance(tracks, list)
408410
return cast(List["Track"], tracks)
409411

412+
def get_radio_mix(self) -> mix.Mix:
413+
"""Queries TIDAL for the track radio mix of tracks that are similar to this
414+
track.
415+
416+
:return: A :class:`Mix <tidalapi.mix.Mix>`
417+
:raises: A :class:`exceptions.MetadataNotAvailable` if no track radio mix is available
418+
"""
419+
try:
420+
request = self.requests.request("GET", "tracks/%s/mix" % self.id)
421+
except ObjectNotFound:
422+
raise MetadataNotAvailable("Track radio not available for this track")
423+
except TooManyRequests:
424+
raise TooManyRequests("Track radio unavailable")
425+
else:
426+
json_obj = request.json()
427+
return self.session.mix(json_obj.get("id"))
428+
410429
def get_stream(self) -> "Stream":
411430
"""Retrieves the track streaming object, allowing for audio transmission.
412431

0 commit comments

Comments
 (0)