diff --git a/requirements.txt b/requirements.txt index 517d2c0..5aae6f9 100755 --- a/requirements.txt +++ b/requirements.txt @@ -2,4 +2,4 @@ waitress==3.0.2 celery==5.5.3 Flask==3.1.1 flask_cors==6.0.0 -deezspot-spotizerr==1.4.0 +deezspot-spotizerr==1.4.1 diff --git a/routes/utils/album.py b/routes/utils/album.py index 48ca67b..ef17495 100755 --- a/routes/utils/album.py +++ b/routes/utils/album.py @@ -15,6 +15,7 @@ def download_album( custom_dir_format="%ar_album%/%album%/%copyright%", custom_track_format="%tracknum%. %music% - %artist%", pad_tracks=True, + save_cover=True, initial_retry_delay=5, retry_delay_increase=5, max_retries=3, @@ -114,6 +115,7 @@ def download_album( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries @@ -155,6 +157,7 @@ def download_album( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries @@ -195,6 +198,7 @@ def download_album( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries @@ -229,6 +233,7 @@ def download_album( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries diff --git a/routes/utils/celery_config.py b/routes/utils/celery_config.py index 4acd927..77bb47b 100644 --- a/routes/utils/celery_config.py +++ b/routes/utils/celery_config.py @@ -35,6 +35,7 @@ DEFAULT_MAIN_CONFIG = { 'customDirFormat': '%ar_album%/%album%', 'customTrackFormat': '%tracknum%. %music%', 'tracknum_padding': True, + 'save_cover': True, 'maxConcurrentDownloads': 3, 'maxRetries': 3, 'retryDelaySeconds': 5, diff --git a/routes/utils/celery_queue_manager.py b/routes/utils/celery_queue_manager.py index 362ec48..b5d3d96 100644 --- a/routes/utils/celery_queue_manager.py +++ b/routes/utils/celery_queue_manager.py @@ -57,6 +57,7 @@ def get_config_params(): 'customDirFormat': config.get('customDirFormat', '%ar_album%/%album%'), 'customTrackFormat': config.get('customTrackFormat', '%tracknum%. %music%'), 'tracknum_padding': config.get('tracknum_padding', True), + 'save_cover': config.get('save_cover', True), 'maxRetries': config.get('maxRetries', 3), 'retryDelaySeconds': config.get('retryDelaySeconds', 5), 'retry_delay_increase': config.get('retry_delay_increase', 5) @@ -74,6 +75,7 @@ def get_config_params(): 'customDirFormat': '%ar_album%/%album%', 'customTrackFormat': '%tracknum%. %music%', 'tracknum_padding': True, + 'save_cover': True, 'maxRetries': 3, 'retryDelaySeconds': 5, 'retry_delay_increase': 5 @@ -198,6 +200,7 @@ class CeleryDownloadQueueManager: "custom_dir_format": original_request.get("custom_dir_format", config_params['customDirFormat']), "custom_track_format": original_request.get("custom_track_format", config_params['customTrackFormat']), "pad_tracks": self._parse_bool_param(original_request.get("tracknum_padding"), config_params['tracknum_padding']), + "save_cover": self._parse_bool_param(original_request.get("save_cover"), config_params['save_cover']), "retry_count": 0, "original_request": original_request, "created_at": time.time() diff --git a/routes/utils/celery_tasks.py b/routes/utils/celery_tasks.py index 6f7001c..b5c857d 100644 --- a/routes/utils/celery_tasks.py +++ b/routes/utils/celery_tasks.py @@ -1086,6 +1086,7 @@ def download_track(self, **task_data): custom_dir_format = task_data.get("custom_dir_format", config_params.get("customDirFormat", "%ar_album%/%album%")) custom_track_format = task_data.get("custom_track_format", config_params.get("customTrackFormat", "%tracknum%. %music%")) pad_tracks = task_data.get("pad_tracks", config_params.get("tracknum_padding", True)) + save_cover = task_data.get("save_cover", config_params.get("save_cover", True)) # Execute the download - service is now determined from URL download_track_func( @@ -1098,6 +1099,7 @@ def download_track(self, **task_data): custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, progress_callback=self.progress_callback ) @@ -1153,6 +1155,7 @@ def download_album(self, **task_data): custom_dir_format = task_data.get("custom_dir_format", config_params.get("customDirFormat", "%ar_album%/%album%")) custom_track_format = task_data.get("custom_track_format", config_params.get("customTrackFormat", "%tracknum%. %music%")) pad_tracks = task_data.get("pad_tracks", config_params.get("tracknum_padding", True)) + save_cover = task_data.get("save_cover", config_params.get("save_cover", True)) # Execute the download - service is now determined from URL download_album_func( @@ -1165,6 +1168,7 @@ def download_album(self, **task_data): custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, progress_callback=self.progress_callback ) @@ -1220,6 +1224,7 @@ def download_playlist(self, **task_data): custom_dir_format = task_data.get("custom_dir_format", config_params.get("customDirFormat", "%ar_album%/%album%")) custom_track_format = task_data.get("custom_track_format", config_params.get("customTrackFormat", "%tracknum%. %music%")) pad_tracks = task_data.get("pad_tracks", config_params.get("tracknum_padding", True)) + save_cover = task_data.get("save_cover", config_params.get("save_cover", True)) # Get retry parameters initial_retry_delay = task_data.get("initial_retry_delay", config_params.get("retryDelaySeconds", 5)) @@ -1237,6 +1242,7 @@ def download_playlist(self, **task_data): custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries, diff --git a/routes/utils/playlist.py b/routes/utils/playlist.py index 457448b..cce34fd 100755 --- a/routes/utils/playlist.py +++ b/routes/utils/playlist.py @@ -15,6 +15,7 @@ def download_playlist( custom_dir_format="%ar_album%/%album%/%copyright%", custom_track_format="%tracknum%. %music% - %artist%", pad_tracks=True, + save_cover=True, initial_retry_delay=5, retry_delay_increase=5, max_retries=3, @@ -109,6 +110,7 @@ def download_playlist( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries, @@ -150,6 +152,7 @@ def download_playlist( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries @@ -190,6 +193,7 @@ def download_playlist( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries @@ -224,6 +228,7 @@ def download_playlist( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries diff --git a/routes/utils/track.py b/routes/utils/track.py index 43de5f2..97e9e0d 100755 --- a/routes/utils/track.py +++ b/routes/utils/track.py @@ -15,6 +15,7 @@ def download_track( custom_dir_format="%ar_album%/%album%/%copyright%", custom_track_format="%tracknum%. %music% - %artist%", pad_tracks=True, + save_cover=True, initial_retry_delay=5, retry_delay_increase=5, max_retries=3, @@ -108,6 +109,7 @@ def download_track( not_interface=False, custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries @@ -143,6 +145,7 @@ def download_track( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries @@ -176,6 +179,7 @@ def download_track( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries @@ -204,6 +208,7 @@ def download_track( custom_dir_format=custom_dir_format, custom_track_format=custom_track_format, pad_tracks=pad_tracks, + save_cover=save_cover, initial_retry_delay=initial_retry_delay, retry_delay_increase=retry_delay_increase, max_retries=max_retries diff --git a/src/js/config.ts b/src/js/config.ts index c172313..6146d07 100644 --- a/src/js/config.ts +++ b/src/js/config.ts @@ -121,6 +121,8 @@ async function loadConfig() { if (retryDelayIncrease) retryDelayIncrease.value = savedConfig.retry_delay_increase || '5'; const tracknumPaddingToggle = document.getElementById('tracknumPaddingToggle') as HTMLInputElement | null; if (tracknumPaddingToggle) tracknumPaddingToggle.checked = savedConfig.tracknum_padding === undefined ? true : !!savedConfig.tracknum_padding; + const saveCoverToggle = document.getElementById('saveCoverToggle') as HTMLInputElement | null; + if (saveCoverToggle) saveCoverToggle.checked = savedConfig.save_cover === undefined ? true : !!savedConfig.save_cover; // Update explicit filter status updateExplicitFilterStatus(savedConfig.explicitFilter); @@ -243,6 +245,7 @@ function setupEventListeners() { (document.getElementById('spotifyQualitySelect') as HTMLSelectElement | null)?.addEventListener('change', saveConfig); (document.getElementById('deezerQualitySelect') as HTMLSelectElement | null)?.addEventListener('change', saveConfig); (document.getElementById('tracknumPaddingToggle') as HTMLInputElement | null)?.addEventListener('change', saveConfig); + (document.getElementById('saveCoverToggle') as HTMLInputElement | null)?.addEventListener('change', saveConfig); (document.getElementById('maxRetries') as HTMLInputElement | null)?.addEventListener('change', saveConfig); (document.getElementById('retryDelaySeconds') as HTMLInputElement | null)?.addEventListener('change', saveConfig); @@ -843,7 +846,8 @@ async function saveConfig() { maxRetries: parseInt((document.getElementById('maxRetries') as HTMLInputElement | null)?.value || '3', 10) || 3, retryDelaySeconds: parseInt((document.getElementById('retryDelaySeconds') as HTMLInputElement | null)?.value || '5', 10) || 5, retry_delay_increase: parseInt((document.getElementById('retryDelayIncrease') as HTMLInputElement | null)?.value || '5', 10) || 5, - tracknum_padding: (document.getElementById('tracknumPaddingToggle') as HTMLInputElement | null)?.checked + tracknum_padding: (document.getElementById('tracknumPaddingToggle') as HTMLInputElement | null)?.checked, + save_cover: (document.getElementById('saveCoverToggle') as HTMLInputElement | null)?.checked }; try { @@ -901,6 +905,8 @@ async function saveConfig() { if (retryDelayIncrease) retryDelayIncrease.value = savedConfig.retry_delay_increase || '5'; const tracknumPaddingToggle = document.getElementById('tracknumPaddingToggle') as HTMLInputElement | null; if (tracknumPaddingToggle) tracknumPaddingToggle.checked = savedConfig.tracknum_padding === undefined ? true : !!savedConfig.tracknum_padding; + const saveCoverToggle = document.getElementById('saveCoverToggle') as HTMLInputElement | null; + if (saveCoverToggle) saveCoverToggle.checked = savedConfig.save_cover === undefined ? true : !!savedConfig.save_cover; // Update explicit filter status updateExplicitFilterStatus(savedConfig.explicitFilter); diff --git a/static/html/config.html b/static/html/config.html index 37c640c..ce5d8f4 100644 --- a/static/html/config.html +++ b/static/html/config.html @@ -201,6 +201,7 @@ %mood% - Mood information %rating% - Track rating %website% - Website information + %quality% - Quality of the track %replaygain_album_gain% - Album gain @@ -225,6 +226,17 @@ When enabled: "01. Track" - When disabled: "1. Track" + + + Save Cover Art: + + + + + + When enabled, cover art will saved as cover.jpg in the same directory as the track. + +