spotDL / spotify-downloader

Download your Spotify playlists and songs along with album art and metadata (from YouTube if a match is found).
https://spotdl.readthedocs.io/en/latest/
MIT License
17.31k stars 1.6k forks source link

JSONDecodeError upon trying to use download feature #1876

Closed kevinroche22 closed 1 year ago

kevinroche22 commented 1 year ago

System OS

MacOS

Python Version

3.8 (CPython)

Install Source

pip / PyPi

Install version / commit hash

4.1.11

Expected Behavior vs Actual Behavior

SpotDL worked successfully for me until the last few weeks. I've tried uninstalling and re-installing the most recent version, and I've tried a number of other versions as well (ie. nearly every version after 3.0.0). All versions throw an error, and versions after 4.0.0 point to this JSONDecodeError. There have been no changes to my system or python version since the last time I was able to successfully use spotdl and now.

Steps to reproduce - Ensure to include actual links!

pip install spotdl --upgrade # but have tried many versions spotdl download https://open.spotify.com/album/1WA44V7P0nv1spaWdsrxD2 # example link, does not work with any spotify link

Traceback

command: spotdl download https://open.spotify.com/album/1WA44V7P0nv1spaWdsrxD2?si=KwJ-a6SRRRiXCcIpkqnjtA
Processing query:                                                               
https://open.spotify.com/album/1WA44V7P0nv1spaWdsrxD2?si=KwJ-a6SRRRiXCcIpkqnjtA 

An error occurred                                                               
╭───────────────────── Traceback (most recent call last) ──────────────────────╮
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotdl/console/entry_point.py:124 in console_entry_point                   │
│                                                                              │
│   121 │   try:                                                               │
│   122 │   │   # Pick the operation to perform                                │
│   123 │   │   # based on the name and run it!                                │
│ ❱ 124 │   │   OPERATIONS[arguments.operation](                               │
│   125 │   │   │   query=arguments.query,                                     │
│   126 │   │   │   downloader=downloader,                                     │
│   127 │   │   )                                                              │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotdl/console/download.py:25 in download                                  │
│                                                                              │
│   22 │   """                                                                 │
│   23 │                                                                       │
│   24 │   # Parse the query                                                   │
│ ❱ 25 │   songs = get_simple_songs(query, use_ytm_data=downloader.settings["y │
│   26 │                                                                       │
│   27 │   # Download the songs                                                │
│   28 │   downloader.download_multiple_songs(songs)                           │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotdl/utils/search.py:211 in get_simple_songs                             │
│                                                                              │
│   208 │   │   elif "open.spotify.com" in request and "playlist" in request:  │
│   209 │   │   │   lists.append(Playlist.from_url(request, fetch_songs=False) │
│   210 │   │   elif "open.spotify.com" in request and "album" in request:     │
│ ❱ 211 │   │   │   lists.append(Album.from_url(request, fetch_songs=False))   │
│   212 │   │   elif "open.spotify.com" in request and "artist" in request:    │
│   213 │   │   │   lists.append(Artist.from_url(request, fetch_songs=False))  │
│   214 │   │   elif "album:" in request:                                      │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotdl/types/song.py:296 in from_url                                       │
│                                                                              │
│   293 │   │   - The SongList object.                                         │
│   294 │   │   """                                                            │
│   295 │   │                                                                  │
│ ❱ 296 │   │   metadata, songs = cls.get_metadata(url)                        │
│   297 │   │   urls = [song.url for song in songs]                            │
│   298 │   │                                                                  │
│   299 │   │   if fetch_songs:                                                │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotdl/types/album.py:42 in get_metadata                                   │
│                                                                              │
│    39 │   │                                                                  │
│    40 │   │   spotify_client = SpotifyClient()                               │
│    41 │   │                                                                  │
│ ❱  42 │   │   album_metadata = spotify_client.album(url)                     │
│    43 │   │   if album_metadata is None:                                     │
│    44 │   │   │   raise AlbumError(                                          │
│    45 │   │   │   │   "Couldn't get metadata, check if you have passed corre │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotipy/client.py:461 in album                                             │
│                                                                              │
│    458 │   │   if market is not None:                                        │
│    459 │   │   │   return self._get("albums/" + trid + '?market=' + market)  │
│    460 │   │   else:                                                         │
│ ❱  461 │   │   │   return self._get("albums/" + trid)                        │
│    462 │                                                                     │
│    463 │   def album_tracks(self, album_id, limit=50, offset=0, market=None) │
│    464 │   │   """ Get Spotify catalog information about an album's tracks   │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotdl/utils/spotify.py:193 in _get                                        │
│                                                                              │
│   190 │   │   retries = self.max_retries  # type: ignore # pylint: disable=E │
│   191 │   │   while response is None:                                        │
│   192 │   │   │   try:                                                       │
│ ❱ 193 │   │   │   │   response = self._internal_call("GET", url, payload, kw │
│   194 │   │   │   except (requests.exceptions.Timeout, requests.ConnectionEr │
│   195 │   │   │   │   retries -= 1                                           │
│   196 │   │   │   │   if retries <= 0:                                       │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotipy/client.py:247 in _internal_call                                    │
│                                                                              │
│    244 │   │   args = dict(params=params)                                    │
│    245 │   │   if not url.startswith("http"):                                │
│    246 │   │   │   url = self.prefix + url                                   │
│ ❱  247 │   │   headers = self._auth_headers()                                │
│    248 │   │                                                                 │
│    249 │   │   if "content_type" in args["params"]:                          │
│    250 │   │   │   headers["Content-Type"] = args["params"]["content_type"]  │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotipy/client.py:238 in _auth_headers                                     │
│                                                                              │
│    235 │   │   if not self.auth_manager:                                     │
│    236 │   │   │   return {}                                                 │
│    237 │   │   try:                                                          │
│ ❱  238 │   │   │   token = self.auth_manager.get_access_token(as_dict=False) │
│    239 │   │   except TypeError:                                             │
│    240 │   │   │   token = self.auth_manager.get_access_token()              │
│    241 │   │   return {"Authorization": "Bearer {0}".format(token)}          │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotipy/oauth2.py:234 in get_access_token                                  │
│                                                                              │
│    231 │   │   │   )                                                         │
│    232 │   │                                                                 │
│    233 │   │   if check_cache:                                               │
│ ❱  234 │   │   │   token_info = self.cache_handler.get_cached_token()        │
│    235 │   │   │   if token_info and not self.is_token_expired(token_info):  │
│    236 │   │   │   │   return token_info if as_dict else token_info["access_ │
│    237                                                                       │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-package │
│ s/spotipy/cache_handler.py:81 in get_cached_token                            │
│                                                                              │
│    78 │   │   │   f = open(self.cache_path)                                  │
│    79 │   │   │   token_info_string = f.read()                               │
│    80 │   │   │   f.close()                                                  │
│ ❱  81 │   │   │   token_info = json.loads(token_info_string)                 │
│    82 │   │                                                                  │
│    83 │   │   except IOError as error:                                       │
│    84 │   │   │   if error.errno == errno.ENOENT:                            │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/json/__init_ │
│ _.py:357 in loads                                                            │
│                                                                              │
│   354 │   if (cls is None and object_hook is None and                        │
│   355 │   │   │   parse_int is None and parse_float is None and              │
│   356 │   │   │   parse_constant is None and object_pairs_hook is None and n │
│ ❱ 357 │   │   return _default_decoder.decode(s)                              │
│   358 │   if cls is None:                                                    │
│   359 │   │   cls = JSONDecoder                                              │
│   360 │   if object_hook is not None:                                        │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/json/decoder │
│ .py:337 in decode                                                            │
│                                                                              │
│   334 │   │   containing a JSON document).                                   │
│   335 │   │                                                                  │
│   336 │   │   """                                                            │
│ ❱ 337 │   │   obj, end = self.raw_decode(s, idx=_w(s, 0).end())              │
│   338 │   │   end = _w(s, end).end()                                         │
│   339 │   │   if end != len(s):                                              │
│   340 │   │   │   raise JSONDecodeError("Extra data", s, end)                │
│                                                                              │
│ /Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/json/decoder │
│ .py:355 in raw_decode                                                        │
│                                                                              │
│   352 │   │   try:                                                           │
│   353 │   │   │   obj, end = self.scan_once(s, idx)                          │
│   354 │   │   except StopIteration as err:                                   │
│ ❱ 355 │   │   │   raise JSONDecodeError("Expecting value", s, err.value) fro │
│   356 │   │   return obj, end                                                │
│   357                                                                        │
╰──────────────────────────────────────────────────────────────────────────────╯
JSONDecodeError: Expecting value: line 1 column 1 (char 0)

Other details

Mac is old - running macOS Sierra version 10.12.6. Storage is limited as well, but still have over 2GB available.

xnetcat commented 1 year ago

Looks like your spotipy cache file has been malformed. Remove it and run spotDL again. It's located in ~/.spotdl/.spotipy-cache

kevinroche22 commented 1 year ago

For those visiting in the future - there was no .spotipy-cache in ~/.spotdl/, so I just deleted the entirety of ~/.spotdl/. From there, I ran pip install spotdl --upgrade and then spotdl --download-ffmpeg, and after that it worked.

Thanks so much for your help! Love this project.