Skip to content

Commit 3219133

Browse files
authored
Add support for fetching multiple audiobooks (#357)
1 parent 3fcee45 commit 3219133

5 files changed

Lines changed: 13489 additions & 1 deletion

File tree

src/spotifyaio/models.py

Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -585,3 +585,73 @@ class AudioFeatures(DataClassORJSONMixin):
585585
valence: float
586586
tempo: float
587587
time_signature: TimeSignature
588+
589+
590+
@dataclass
591+
class Chapter(DataClassORJSONMixin):
592+
"""Chapter model."""
593+
594+
chapter_id: str = field(metadata=field_options(alias="id"))
595+
chapter_number: int
596+
duration_ms: int
597+
images: list[Image]
598+
languages: list[str]
599+
name: str
600+
explicit: bool
601+
type: str
602+
uri: str
603+
external_urls: dict[str, str]
604+
605+
606+
@dataclass
607+
class Author(DataClassORJSONMixin):
608+
"""Author model."""
609+
610+
name: str
611+
612+
613+
@dataclass
614+
class Narrator(DataClassORJSONMixin):
615+
"""Narrator model."""
616+
617+
name: str
618+
619+
620+
@dataclass
621+
class Audiobook(DataClassORJSONMixin):
622+
"""Audiobook model."""
623+
624+
authors: list[Author]
625+
chapters: list[Chapter]
626+
description: str
627+
edition: str
628+
external_urls: dict[str, str]
629+
explicit: bool
630+
html_description: str
631+
audiobook_id: str = field(metadata=field_options(alias="id"))
632+
images: list[Image]
633+
languages: list[str]
634+
name: str
635+
narrators: list[Narrator]
636+
publisher: str
637+
total_chapters: int
638+
type: str
639+
uri: str
640+
641+
@classmethod
642+
def __pre_deserialize__(cls, d: dict[str, Any]) -> dict[str, Any]:
643+
"""Pre deserialize hook."""
644+
return {**d, "chapters": d.get("chapters", {}).pop("items", [])}
645+
646+
647+
@dataclass
648+
class AudiobooksResponse(DataClassORJSONMixin):
649+
"""Audiobooks response model."""
650+
651+
audiobooks: list[Audiobook]
652+
653+
@classmethod
654+
def __pre_deserialize__(cls, d: dict[str, Any]) -> dict[str, Any]:
655+
"""Pre deserialize hook."""
656+
items = [item for item in d["audiobooks"] if item is not None]
657+
return {"audiobooks": items}

src/spotifyaio/spotify.py

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@
1919
AlbumTracksResponse,
2020
Artist,
2121
ArtistResponse,
22+
Audiobook,
23+
AudiobooksResponse,
2224
AudioFeatures,
2325
BasePlaylist,
2426
BaseUserProfile,
@@ -251,7 +253,12 @@ async def get_artist_albums(self, artist_id: str) -> list[SimplifiedAlbum]:
251253

252254
# Get audiobook
253255

254-
# Get several audiobooks
256+
async def get_audiobooks(self, audiobook_ids: list[str]) -> list[Audiobook]:
257+
"""Get audiobooks."""
258+
identifiers = [get_identifier(i) for i in audiobook_ids]
259+
params: dict[str, Any] = {"ids": ",".join(identifiers)}
260+
response = await self._get("v1/audiobooks", params=params)
261+
return AudiobooksResponse.from_json(response).audiobooks
255262

256263
# Get an audiobook's episodes
257264

0 commit comments

Comments
 (0)