from api.v1.schemas.home import HomeArtist, HomeSection, ServicePrompt from api.v1.schemas.common import GenreArtistMap, IntegrationStatus from api.v1.schemas.weekly_exploration import WeeklyExplorationSection from models.youtube import YouTubeQuotaResponse as YouTubeQuotaResponse from infrastructure.msgspec_fastapi import AppStruct class BecauseYouListenTo(AppStruct): seed_artist: str seed_artist_mbid: str section: HomeSection listen_count: int = 0 banner_url: str | None = None wide_thumb_url: str | None = None fanart_url: str | None = None class DiscoverQueueItemLight(AppStruct): release_group_mbid: str album_name: str artist_name: str artist_mbid: str recommendation_reason: str cover_url: str | None = None is_wildcard: bool = False in_library: bool = False class DiscoverQueueEnrichment(AppStruct): artist_mbid: str | None = None release_date: str | None = None country: str | None = None tags: list[str] = [] youtube_url: str | None = None youtube_search_url: str = "" youtube_search_available: bool = False artist_description: str | None = None listen_count: int | None = None class DiscoverQueueItemFull(DiscoverQueueItemLight): enrichment: DiscoverQueueEnrichment | None = None class YouTubeSearchResponse(AppStruct): video_id: str | None = None embed_url: str | None = None error: str | None = None cached: bool = False class TrackCacheCheckItem(AppStruct): artist: str track: str class TrackCacheCheckRequest(AppStruct): items: list[TrackCacheCheckItem] = [] class TrackCacheCheckResponseItem(AppStruct): artist: str track: str cached: bool = False class TrackCacheCheckResponse(AppStruct): items: list[TrackCacheCheckResponseItem] = [] class DiscoverQueueResponse(AppStruct): items: list[DiscoverQueueItemLight | DiscoverQueueItemFull] = [] queue_id: str = "" class DiscoverQueueIgnoreRequest(AppStruct): release_group_mbid: str artist_mbid: str release_name: str artist_name: str class DiscoverQueueValidateRequest(AppStruct): release_group_mbids: list[str] class DiscoverQueueValidateResponse(AppStruct): in_library: list[str] = [] class QueueSettings(AppStruct): queue_size: int queue_ttl: int seed_artists: int wildcard_slots: int similar_artists_limit: int albums_per_similar: int enrich_ttl: int lastfm_mbid_max_lookups: int class DiscoverQueueStatusResponse(AppStruct): status: str source: str queue_id: str | None = None item_count: int | None = None built_at: float | None = None stale: bool | None = None error: str | None = None class QueueGenerateRequest(AppStruct): source: str | None = None force: bool = False class QueueGenerateResponse(AppStruct): action: str status: str source: str queue_id: str | None = None item_count: int | None = None built_at: float | None = None stale: bool | None = None error: str | None = None class DiscoverIgnoredRelease(AppStruct): release_group_mbid: str artist_mbid: str release_name: str artist_name: str ignored_at: float class DiscoverIntegrationStatus(IntegrationStatus): pass class DiscoverResponse(AppStruct): because_you_listen_to: list[BecauseYouListenTo] = [] discover_queue_enabled: bool = True fresh_releases: HomeSection | None = None missing_essentials: HomeSection | None = None rediscover: HomeSection | None = None artists_you_might_like: HomeSection | None = None popular_in_your_genres: HomeSection | None = None genre_list: HomeSection | None = None globally_trending: HomeSection | None = None weekly_exploration: WeeklyExplorationSection | None = None integration_status: DiscoverIntegrationStatus | None = None service_prompts: list[ServicePrompt] = [] genre_artists: GenreArtistMap = {} genre_artist_images: GenreArtistMap = {} lastfm_weekly_artist_chart: HomeSection | None = None lastfm_weekly_album_chart: HomeSection | None = None lastfm_recent_scrobbles: HomeSection | None = None refreshing: bool = False service_status: dict[str, str] | None = None