Enrich Amazon album track durations via search results
media_from_asin returns no duration data. get_album_tracks now does one search_raw call using the album name + primary artist from stream tags, filters hits by albumAsin == requested asin, and builds a duration_map (track asin → duration_ms). Search failures are swallowed — duration_ms falls back to 0 so the existing behaviour is preserved on error. 2 new tests: duration populated when search returns matching hit; duration stays 0 when search endpoint returns an error.
This commit is contained in:
parent
c2fcef45c2
commit
96a1c8b7b8
2 changed files with 41 additions and 1 deletions
|
|
@ -501,12 +501,28 @@ class AmazonClient:
|
|||
streams = self.media_from_asin(asin)
|
||||
except AmazonClientError:
|
||||
return None
|
||||
|
||||
# media_from_asin has no duration — enrich from search results which do.
|
||||
duration_map: Dict[str, int] = {} # track asin → duration_ms
|
||||
if streams:
|
||||
album_name = _strip_edition(streams[0].album)
|
||||
artist_name = _primary_artist(streams[0].artist)
|
||||
try:
|
||||
search_items = self.search_raw(
|
||||
f"{album_name} {artist_name}", types="track,album"
|
||||
)
|
||||
for item in search_items:
|
||||
if item.album_asin == asin and item.duration_seconds:
|
||||
duration_map[item.asin] = item.duration_seconds * 1000
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
items = [
|
||||
{
|
||||
"id": s.asin,
|
||||
"name": _strip_edition(s.title),
|
||||
"artists": [{"name": _primary_artist(s.artist), "id": ""}],
|
||||
"duration_ms": 0,
|
||||
"duration_ms": duration_map.get(s.asin, 0),
|
||||
"track_number": s.track_number,
|
||||
"disc_number": s.disc_number,
|
||||
"release_date": s.date or "",
|
||||
|
|
|
|||
|
|
@ -844,6 +844,30 @@ class TestGetAlbumTracks:
|
|||
assert item["track_number"] == 3
|
||||
assert item["disc_number"] == 1
|
||||
|
||||
def test_duration_enriched_from_search(self):
|
||||
search_resp = {
|
||||
"results": [{"hits": [
|
||||
{"document": {
|
||||
"asin": "B09XYZ1234", "__type": "track",
|
||||
"title": "Not Like Us", "artistName": "Kendrick Lamar",
|
||||
"albumAsin": "B09XYZ1234", "duration": 217,
|
||||
}},
|
||||
]}]
|
||||
}
|
||||
client = _make_client({
|
||||
"amazon-music/media-from-asin": [MEDIA_RESPONSE_FLAC],
|
||||
"amazon-music/search": search_resp,
|
||||
})
|
||||
with patch("core.amazon_client._rate_limit"):
|
||||
result = client.get_album_tracks("B09XYZ1234")
|
||||
assert result["items"][0]["duration_ms"] == 217_000
|
||||
|
||||
def test_duration_zero_when_search_fails(self):
|
||||
client = _make_client({"amazon-music/media-from-asin": [MEDIA_RESPONSE_FLAC]})
|
||||
with patch("core.amazon_client._rate_limit"):
|
||||
result = client.get_album_tracks("B09XYZ1234")
|
||||
assert result["items"][0]["duration_ms"] == 0
|
||||
|
||||
def test_returns_none_on_api_error(self):
|
||||
client = _make_client()
|
||||
client.session.get.return_value = _mock_response({}, 500)
|
||||
|
|
|
|||
Loading…
Reference in a new issue