diff --git a/README.md b/README.md
index 9b6ad09..12e7553 100644
--- a/README.md
+++ b/README.md
@@ -3,6 +3,16 @@ Install the dependencies using `pip install -r requirements.txt`
Run `python -m deemix --help` to see how to use the app
# TODO
-Making the download work in multi-threading
-Finish porting all features
-Make the GUI after all is implemented
+Finish porting all features:
+- logging
+- ?
+
+Settings not yet implemented:
+- fallbackBitrate (on by default)
+- fallbackSearch (off by default)
+- logSearched
+- savePlaylistAsCompilation
+- removeAlbumVersion
+- moveFeaturedToTitle
+- titleCasing
+- artistCasing
diff --git a/deemix/app/downloader.py b/deemix/app/downloader.py
index 62f6542..b72e25b 100644
--- a/deemix/app/downloader.py
+++ b/deemix/app/downloader.py
@@ -8,7 +8,6 @@ from requests import get
from requests.exceptions import HTTPError
from tempfile import gettempdir
from concurrent.futures import ThreadPoolExecutor
-import json
TEMPDIR = os.path.join(gettempdir(), 'deezloader-imgs')
if not os.path.isdir(TEMPDIR):
@@ -206,12 +205,13 @@ def getTrackData(dz, trackAPI_gw, trackAPI = None, albumAPI_gw = None, albumAPI
except APIError:
if not albumAPI_gw:
albumAPI_gw = dz.get_album_gw(track['album']['id'])
- track['album']['artist'] = {
+ track['album']['mainArtist'] = {
'id': albumAPI_gw['ART_ID'],
'name': albumAPI_gw['ART_NAME']
}
- artistAPI = dz.get_artist(track['album']['artist']['id'])
- track['album']['artist']['pic'] = artistAPI['picture_small'][artistAPI['picture_small'].find('artist/')+7:-24]
+ artistAPI = dz.get_artist(track['album']['mainArtist']['id'])
+ track['album']['artists'] = albumAPI_gw['ART_NAME']
+ track['album']['mainArtist']['pic'] = artistAPI['picture_small'][artistAPI['picture_small'].find('artist/')+7:-24]
track['album']['trackTotal'] = albumAPI_gw['NUMBER_TRACK']
track['album']['discTotal'] = albumAPI_gw['NUMBER_DISK']
track['album']['recordType'] = "Album"
@@ -278,8 +278,8 @@ def getTrackData(dz, trackAPI_gw, trackAPI = None, albumAPI_gw = None, albumAPI
# Create artists strings
track['mainArtistsString'] = ""
- tot = len(track['artist']['Main'])
- if tot > 0:
+ if 'Main' in track['artist']:
+ tot = len(track['artist']['Main'])
for i, art in enumerate(track['artist']['Main']):
track['mainArtistsString'] += art
if tot != i+1:
@@ -289,8 +289,8 @@ def getTrackData(dz, trackAPI_gw, trackAPI = None, albumAPI_gw = None, albumAPI
track['mainArtistsString'] += ", "
else:
track['mainArtistsString'] = track['mainArtist']['name']
- tot = len(track['artist']['Featured'])
- if tot > 0:
+ if 'Featured' in track['artist']:
+ tot = len(track['artist']['Featured'])
track['featArtistsString'] = "feat. "
for i, art in enumerate(track['artist']['Featured']):
track['featArtistsString'] += art
@@ -303,7 +303,7 @@ def getTrackData(dz, trackAPI_gw, trackAPI = None, albumAPI_gw = None, albumAPI
# Create title with feat
if "(feat." in track['title'].lower():
track['title_feat'] = track['title']
- elif len(artists['Featured'])>0:
+ elif 'Featured' in track['artist']:
track['title_feat'] = track['title']+" ({})".format(track['featArtistsString'])
else:
track['title_feat'] = track['title']
@@ -332,6 +332,10 @@ def downloadTrackObj(dz, trackAPI, settings, overwriteBitrate=False, extraTrack=
return downloadTrackObj(dz, trackAPI, settings, extraTrack=track)
else:
print("ERROR: Track not yet encoded!")
+ result['error'] = {
+ 'message': "Track not yet encoded!",
+ 'data': track
+ }
return result
# Get the selected bitrate
@@ -378,7 +382,9 @@ def downloadTrackObj(dz, trackAPI, settings, overwriteBitrate=False, extraTrack=
# Generate artist tag if needed
if settings['multitagSeparator'] != "default":
if settings['multitagSeparator'] == "andFeat":
- track['artistsString'] = track['mainArtistsString'] + " " + track['featArtistsString']
+ track['artistsString'] = track['mainArtistsString']
+ if 'featArtistsString' in track:
+ track['artistsString'] += " "+track['featArtistsString']
else:
track['artistsString'] = settings['multitagSeparator'].join(track[artists])
@@ -401,6 +407,10 @@ def downloadTrackObj(dz, trackAPI, settings, overwriteBitrate=False, extraTrack=
return downloadTrackObj(dz, trackAPI, settings, extraTrack=track)
else:
print("ERROR: Track not available on deezer's servers!")
+ result['error'] = {
+ 'message': "Track not available on deezer's servers!",
+ 'data': track
+ }
return result
if track['selectedFormat'] in [3, 1, 8]:
tagID3(writepath, track, settings['tags'], settings['saveID3v1'], settings['useNullSeparator'])
@@ -409,6 +419,33 @@ def downloadTrackObj(dz, trackAPI, settings, overwriteBitrate=False, extraTrack=
print("Done!")
return result
+def after_download(tracks, settings):
+ extrasPath = None
+ playlist = [None] * len(tracks)
+ errors = ""
+ for index in range(len(tracks)):
+ result = tracks[index].result()
+ if 'error' in result:
+ errors += f"{result['error']['data']['id']} | {result['error']['data']['mainArtist']['name']} - {result['error']['data']['title']} | {result['error']['message']}\r\n"
+ if not extrasPath and 'extrasPath' in result:
+ extrasPath = result['extrasPath']
+ if settings['saveArtwork'] and result['albumPath']:
+ downloadImage(result['albumURL'], result['albumPath'])
+ if settings['saveArtworkArtist'] and result['artistPath']:
+ downloadImage(result['artistURL'], result['artistPath'])
+ if 'playlistPosition' in result:
+ playlist[index] = result['playlistPosition']
+ else:
+ playlist[index] = ""
+ if settings['logErrors'] and extrasPath and errors != "":
+ with open(os.path.join(extrasPath, 'errors.txt'), 'w') as f:
+ f.write(errors)
+ if settings['createM3U8File'] and extrasPath:
+ with open(os.path.join(extrasPath, 'playlist.m3u8'), 'w') as f:
+ for line in playlist:
+ f.write(line+"\n")
+ return extrasPath
+
def download_track(dz, id, settings, overwriteBitrate=False):
trackAPI = dz.get_track_gw(id)
trackAPI['FILENAME_TEMPLATE'] = settings['tracknameTemplate']
@@ -437,24 +474,7 @@ def download_album(dz, id, settings, overwriteBitrate=False):
trackAPI['FILENAME_TEMPLATE'] = settings['albumTracknameTemplate']
playlist[pos-1] = executor.submit(downloadTrackObj, dz, trackAPI, settings, overwriteBitrate)
- extrasPath = None
- for index in range(len(playlist)):
- result = playlist[index].result()
- if not extrasPath:
- extrasPath = result['extrasPath']
- if settings['saveArtwork'] and result['albumPath']:
- downloadImage(result['albumURL'], result['albumPath'])
- if settings['saveArtworkArtist'] and result['artistPath']:
- downloadImage(result['artistURL'], result['artistPath'])
- if 'playlistPosition' in result:
- playlist[index] = result['playlistPosition']
- else:
- playlist[index] = ""
- if settings['createM3U8File'] and extrasPath:
- with open(os.path.join(extrasPath, 'playlist.m3u8'), 'w') as f:
- for line in playlist:
- f.write(line+"\n")
- return extrasPath
+ return after_download(playlist, settings)
def download_artist(dz, id, settings, overwriteBitrate=False):
artistAPI = dz.get_artist_albums(id)
@@ -472,22 +492,4 @@ def download_playlist(dz, id, settings, overwriteBitrate=False):
trackAPI['POSITION'] = pos
trackAPI['FILENAME_TEMPLATE'] = settings['playlistTracknameTemplate']
playlist[pos-1] = executor.submit(downloadTrackObj, dz, trackAPI, settings, overwriteBitrate)
-
- extrasPath = None
- for index in range(len(playlist)):
- result = playlist[index].result()
- if not extrasPath:
- extrasPath = result['extrasPath']
- if settings['saveArtwork'] and result['albumPath']:
- downloadImage(result['albumURL'], result['albumPath'])
- if settings['saveArtworkArtist'] and result['artistPath']:
- downloadImage(result['artistURL'], result['artistPath'])
- if 'playlistPosition' in result:
- playlist[index] = result['playlistPosition']
- else:
- playlist[index] = ""
- if settings['createM3U8File'] and extrasPath:
- with open(os.path.join(extrasPath, 'playlist.m3u8'), 'w') as f:
- for line in playlist:
- f.write(line+"\n")
- return extrasPath
+ return after_download(playlist, settings)