diff --git a/maloja/database/__init__.py b/maloja/database/__init__.py index 24419d4..a68d6c5 100644 --- a/maloja/database/__init__.py +++ b/maloja/database/__init__.py @@ -399,9 +399,11 @@ def get_charts_artists(dbconn=None,resolve_ids=True,**keys): (since,to) = keys.get('timerange').timestamps() separate = keys.get('separate',False) result = sqldb.count_scrobbles_by_artist(since=since,to=to,resolve_ids=resolve_ids,associated=(not separate),dbconn=dbconn) + + map = sqldb.get_associated_artist_map([entry['artist'] for entry in result if 'artist' in entry]) for entry in result: if "artist" in entry: - entry['associated_artists'] = sqldb.get_associated_artists(entry['artist']) + entry['associated_artists'] = map[entry['artist']] return result @waitfordb diff --git a/maloja/database/sqldb.py b/maloja/database/sqldb.py index c3d8c63..282a680 100644 --- a/maloja/database/sqldb.py +++ b/maloja/database/sqldb.py @@ -1429,6 +1429,40 @@ def get_associated_artists(*artists,resolve_ids=True,dbconn=None): else: return [a.id for a in result] +@cached_wrapper +@connection_provider +def get_associated_artist_map(artists,resolve_ids=True,dbconn=None): + artist_ids = [get_artist_id(a,dbconn=dbconn) for a in artists] + + + jointable = sql.join( + DB['associated_artists'], + DB['artists'], + DB['associated_artists'].c.source_artist == DB['artists'].c.id + ) + + # we need to select to avoid multiple 'id' columns that will then + # be misinterpreted by the row-dict converter + op = sql.select( + DB['artists'], + DB['associated_artists'].c.target_artist + ).select_from(jointable).where( + DB['associated_artists'].c.target_artist.in_(artist_ids) + ) + result = dbconn.execute(op).all() + + artists_to_associated = {a_id:[] for a_id in artist_ids} + for row in result: + if resolve_ids: + artists_to_associated[row.target_artist].append(artists_db_to_dict([row],dbconn=dbconn)[0]) + else: + artists_to_associated[row.target_artist].append(row.id) + + artists_to_associated = {artists[artist_ids.index(k)]:v for k,v in artists_to_associated.items()} + + return artists_to_associated + + @cached_wrapper @connection_provider def get_credited_artists(*artists,dbconn=None):