[GH-ISSUE #321] [BUG] Change in Metadata : Cause "Cannot get alternative track" #58

Closed
opened 2026-02-27 08:11:41 +03:00 by kerem · 49 comments
Owner

Originally created by @Scrameupeutchi on GitHub (Nov 6, 2025).
Original GitHub issue: https://github.com/kokarare1212/librespot-python/issues/321

Describe the bug
While we were used to encounter this bug due to various circumstances in the past, here it comes again since a few hours, preventing the use of the library. The now usual dreaded error message is appearing :

Traceback (most recent call last):
  File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/zotify/track.py", line 304, in download_track
    stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/zotify/zotify.py", line 53, in get_content_stream
    return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/librespot/audio/__init__.py", line 771, in load
    return self.load_track(playable_id, audio_quality_picker, preload,
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/librespot/audio/__init__.py", line 825, in load_track
    raise RuntimeError("Cannot get alternative track")
RuntimeError: Cannot get alternative track

From what I could understand from the way the track's URL is retrieved, the Metadata should contain a "file" field to get the information from. However, the result I'm getting in debug does not seems to include that parameter anymore :

> id: "v\335\317\256TGG\216\242\'i\032A\200\253\030"
> name: "Butterfly"
> album {
>   gid: "{\341\320\325E(GT\216P\214\234\273\254[N"
>   name: "Smile"
>   artist {
>     gid: "\030\206\261\217\231\361G:\202\3048\330F\334\023\361"
>     name: "SMiLE.dk"
>   }
>   label: "Parlophone Denmark"
>   date {
>     year: 1998
>     month: 7
>     day: 13
>   }
>   cover_group {
>     image {
>       file_id: "\253gam\000\000\036\002\326j\306id-u\333\265)E\253"
>       size: DEFAULT
>       width: 300
>       height: 300
>     }
>     image {
>       file_id: "\253gam\000\000HQ\326j\306id-u\333\265)E\253"
>       size: SMALL
>       width: 64
>       height: 64
>     }
>     image {
>       file_id: "\253gam\000\000\262s\326j\306id-u\333\265)E\253"
>       size: LARGE
>       width: 640
>       height: 640
>     }
>   }
> }
> artist {
>   gid: "\030\206\261\217\231\361G:\202\3048\330F\334\023\361"
>   name: "SMiLE.dk"
> }
> number: 1
> disc_number: 1
> duration: 177453
> popularity: 64
> external_id {
>   type: "isrc"
>   id: "DKABA9814003"
> }
> earliest_live_timestamp: 413146860
> has_lyrics: true
> licensor {
>   uuid: "\2037\246\256\254\247D\247\263 P\360\306n\023\217"
> }

And then, the value of Metadata.Track is None. No alternatives could be found either.
Looks Spotify is still up to shenanigans, let's hope we can find an alternative.

To Reproduce
Steps to reproduce the behavior:

  1. Use librespot-python (last version)
  2. Try to get a track
  3. It won't get through

Expected behavior
The track is downloaded and converted if needed.

Client Information (please complete the following information):

  • OS: Linux Mint 22.04
  • Python Version : 3.12.3
  • Library Version Last main branch revision

Additional context
Add any other context about the problem here.

Originally created by @Scrameupeutchi on GitHub (Nov 6, 2025). Original GitHub issue: https://github.com/kokarare1212/librespot-python/issues/321 **Describe the bug** While we were used to encounter this bug due to various circumstances in the past, here it comes again since a few hours, preventing the use of the library. The now usual dreaded error message is appearing : ``` Traceback (most recent call last): File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/zotify/track.py", line 304, in download_track stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/zotify/zotify.py", line 53, in get_content_stream return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/librespot/audio/__init__.py", line 771, in load return self.load_track(playable_id, audio_quality_picker, preload, ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/librespot/audio/__init__.py", line 825, in load_track raise RuntimeError("Cannot get alternative track") RuntimeError: Cannot get alternative track ``` From what I could understand from the way the track's URL is retrieved, the Metadata should contain a "file" field to get the information from. However, the result I'm getting in debug does not seems to include that parameter anymore : ``` > id: "v\335\317\256TGG\216\242\'i\032A\200\253\030" > name: "Butterfly" > album { > gid: "{\341\320\325E(GT\216P\214\234\273\254[N" > name: "Smile" > artist { > gid: "\030\206\261\217\231\361G:\202\3048\330F\334\023\361" > name: "SMiLE.dk" > } > label: "Parlophone Denmark" > date { > year: 1998 > month: 7 > day: 13 > } > cover_group { > image { > file_id: "\253gam\000\000\036\002\326j\306id-u\333\265)E\253" > size: DEFAULT > width: 300 > height: 300 > } > image { > file_id: "\253gam\000\000HQ\326j\306id-u\333\265)E\253" > size: SMALL > width: 64 > height: 64 > } > image { > file_id: "\253gam\000\000\262s\326j\306id-u\333\265)E\253" > size: LARGE > width: 640 > height: 640 > } > } > } > artist { > gid: "\030\206\261\217\231\361G:\202\3048\330F\334\023\361" > name: "SMiLE.dk" > } > number: 1 > disc_number: 1 > duration: 177453 > popularity: 64 > external_id { > type: "isrc" > id: "DKABA9814003" > } > earliest_live_timestamp: 413146860 > has_lyrics: true > licensor { > uuid: "\2037\246\256\254\247D\247\263 P\360\306n\023\217" > } ``` And then, the value of Metadata.Track is None. No alternatives could be found either. Looks Spotify is still up to shenanigans, let's hope we can find an alternative. **To Reproduce** Steps to reproduce the behavior: 1. Use librespot-python (last version) 2. Try to get a track 3. It won't get through **Expected behavior** The track is downloaded and converted if needed. **Client Information (please complete the following information):** - OS: Linux Mint 22.04 - Python Version : 3.12.3 - Library Version Last main branch revision **Additional context** Add any other context about the problem here.
kerem 2026-02-27 08:11:41 +03:00
  • closed this issue
  • added the
    bug
    label
Author
Owner

@shayanmaher commented on GitHub (Nov 6, 2025):

Describe the bug While we were used to encounter this bug due to various circumstances in the past, here it comes again since a few hours, preventing the use of the library. The now usual dreaded error message is appearing :

Traceback (most recent call last):
  File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/zotify/track.py", line 304, in download_track
    stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/zotify/zotify.py", line 53, in get_content_stream
    return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/librespot/audio/__init__.py", line 771, in load
    return self.load_track(playable_id, audio_quality_picker, preload,
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/librespot/audio/__init__.py", line 825, in load_track
    raise RuntimeError("Cannot get alternative track")
RuntimeError: Cannot get alternative track

From what I could understand from the way the track's URL is retrieved, the Metadata should contain a "file" field to get the information from. However, the result I'm getting in debug does not seems to include that parameter anymore :

> id: "v\335\317\256TGG\216\242\'i\032A\200\253\030"
> name: "Butterfly"
> album {
>   gid: "{\341\320\325E(GT\216P\214\234\273\254[N"
>   name: "Smile"
>   artist {
>     gid: "\030\206\261\217\231\361G:\202\3048\330F\334\023\361"
>     name: "SMiLE.dk"
>   }
>   label: "Parlophone Denmark"
>   date {
>     year: 1998
>     month: 7
>     day: 13
>   }
>   cover_group {
>     image {
>       file_id: "\253gam\000\000\036\002\326j\306id-u\333\265)E\253"
>       size: DEFAULT
>       width: 300
>       height: 300
>     }
>     image {
>       file_id: "\253gam\000\000HQ\326j\306id-u\333\265)E\253"
>       size: SMALL
>       width: 64
>       height: 64
>     }
>     image {
>       file_id: "\253gam\000\000\262s\326j\306id-u\333\265)E\253"
>       size: LARGE
>       width: 640
>       height: 640
>     }
>   }
> }
> artist {
>   gid: "\030\206\261\217\231\361G:\202\3048\330F\334\023\361"
>   name: "SMiLE.dk"
> }
> number: 1
> disc_number: 1
> duration: 177453
> popularity: 64
> external_id {
>   type: "isrc"
>   id: "DKABA9814003"
> }
> earliest_live_timestamp: 413146860
> has_lyrics: true
> licensor {
>   uuid: "\2037\246\256\254\247D\247\263 P\360\306n\023\217"
> }

And then, the value of Metadata.Track is None. No alternatives could be found either. Looks Spotify is still up to shenanigans, let's hope we can find an alternative.

To Reproduce Steps to reproduce the behavior:

  1. Use librespot-python (last version)
  2. Try to get a track
  3. It won't get through

Expected behavior The track is downloaded and converted if needed.

Client Information (please complete the following information):

  • OS: Linux Mint 22.04
  • Python Version : 3.12.3
  • Library Version Last main branch revision

Additional context Add any other context about the problem here.

also i have this problem form a few hours

<!-- gh-comment-id:3499089363 --> @shayanmaher commented on GitHub (Nov 6, 2025): > **Describe the bug** While we were used to encounter this bug due to various circumstances in the past, here it comes again since a few hours, preventing the use of the library. The now usual dreaded error message is appearing : > > ``` > Traceback (most recent call last): > File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/zotify/track.py", line 304, in download_track > stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY) > ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ > File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/zotify/zotify.py", line 53, in get_content_stream > return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None) > ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ > File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/librespot/audio/__init__.py", line 771, in load > return self.load_track(playable_id, audio_quality_picker, preload, > ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ > File "/home/scrameupeutchi/.local/share/pipx/venvs/zotify/lib/python3.12/site-packages/librespot/audio/__init__.py", line 825, in load_track > raise RuntimeError("Cannot get alternative track") > RuntimeError: Cannot get alternative track > ``` > > From what I could understand from the way the track's URL is retrieved, the Metadata should contain a "file" field to get the information from. However, the result I'm getting in debug does not seems to include that parameter anymore : > > ``` > > id: "v\335\317\256TGG\216\242\'i\032A\200\253\030" > > name: "Butterfly" > > album { > > gid: "{\341\320\325E(GT\216P\214\234\273\254[N" > > name: "Smile" > > artist { > > gid: "\030\206\261\217\231\361G:\202\3048\330F\334\023\361" > > name: "SMiLE.dk" > > } > > label: "Parlophone Denmark" > > date { > > year: 1998 > > month: 7 > > day: 13 > > } > > cover_group { > > image { > > file_id: "\253gam\000\000\036\002\326j\306id-u\333\265)E\253" > > size: DEFAULT > > width: 300 > > height: 300 > > } > > image { > > file_id: "\253gam\000\000HQ\326j\306id-u\333\265)E\253" > > size: SMALL > > width: 64 > > height: 64 > > } > > image { > > file_id: "\253gam\000\000\262s\326j\306id-u\333\265)E\253" > > size: LARGE > > width: 640 > > height: 640 > > } > > } > > } > > artist { > > gid: "\030\206\261\217\231\361G:\202\3048\330F\334\023\361" > > name: "SMiLE.dk" > > } > > number: 1 > > disc_number: 1 > > duration: 177453 > > popularity: 64 > > external_id { > > type: "isrc" > > id: "DKABA9814003" > > } > > earliest_live_timestamp: 413146860 > > has_lyrics: true > > licensor { > > uuid: "\2037\246\256\254\247D\247\263 P\360\306n\023\217" > > } > ``` > > And then, the value of Metadata.Track is None. No alternatives could be found either. Looks Spotify is still up to shenanigans, let's hope we can find an alternative. > > **To Reproduce** Steps to reproduce the behavior: > > 1. Use librespot-python (last version) > 2. Try to get a track > 3. It won't get through > > **Expected behavior** The track is downloaded and converted if needed. > > **Client Information (please complete the following information):** > > * OS: Linux Mint 22.04 > * Python Version : 3.12.3 > * Library Version Last main branch revision > > **Additional context** Add any other context about the problem here. also i have this problem form a few hours
Author
Owner

@Scrameupeutchi commented on GitHub (Nov 6, 2025):

Remote librespot-org seems to have found a workaround by using extended-metada endpoint that still contains the File parameter. ( See https://github.com/librespot-org/librespot/pull/1622 ) . However, I don't clearly know how to actually adapt the fix to this repository, so I hope someone could be up to it.

<!-- gh-comment-id:3499277014 --> @Scrameupeutchi commented on GitHub (Nov 6, 2025): Remote librespot-org seems to have found a workaround by using extended-metada endpoint that still contains the File parameter. ( See https://github.com/librespot-org/librespot/pull/1622 ) . However, I don't clearly know how to actually adapt the fix to this repository, so I hope someone could be up to it.
Author
Owner

@IsaacAgulhas commented on GitHub (Nov 7, 2025):

Remote librespot-org seems to have found a workaround by using extended-metada endpoint that still contains the File parameter. ( See librespot-org/librespot#1622 ) . However, I don't clearly know how to actually adapt the fix to this repository, so I hope someone could be up to it.

the challenge is that this repo is built in python whereas the main librepsot repo is built in rust, and additionally the librespot devs are always very fast with finding and implementing fixes when these issues arise, however we are then stuck waiting for a language specific implementation of that fix

since zotify itself is built in python, and rust modules can be used in python, maybe a correct approach would be to build a fork of zotify that implements librespot as a rust dependency and not as a python module. That way we can keep up with the speed at which the main librespot team finds and implements their fixes.

<!-- gh-comment-id:3502571213 --> @IsaacAgulhas commented on GitHub (Nov 7, 2025): > Remote librespot-org seems to have found a workaround by using extended-metada endpoint that still contains the File parameter. ( See [librespot-org/librespot#1622](https://github.com/librespot-org/librespot/pull/1622) ) . However, I don't clearly know how to actually adapt the fix to this repository, so I hope someone could be up to it. the challenge is that this repo is built in python whereas the main librepsot repo is built in rust, and additionally the librespot devs are always very fast with finding and implementing fixes when these issues arise, however we are then stuck waiting for a language specific implementation of that fix since zotify itself is built in python, and rust modules can be used in python, maybe a correct approach would be to build a fork of zotify that implements librespot as a rust dependency and not as a python module. That way we can keep up with the speed at which the main librespot team finds and implements their fixes.
Author
Owner

@Masterolic commented on GitHub (Nov 7, 2025):

Remote librespot-org seems to have found a workaround by using extended-metada endpoint that still contains the File parameter. ( See librespot-org/librespot#1622 ) . However, I don't clearly know how to actually adapt the fix to this repository, so I hope someone could be up to it.

the challenge is that this repo is built in python whereas the main librepsot repo is built in rust, and additionally the librespot devs are always very fast with finding and implementing fixes when these issues arise, however we are then stuck waiting for a language specific implementation of that fix

since zotify itself is built in python, and rust modules can be used in python, maybe a correct approach would be to build a fork of zotify that implements librespot as a rust dependency and not as a python module. That way we can keep up with the speed at which the main librespot team finds and implements their fixes.

I have a doubt is that we need to add extendedmetadata proto files in librespot-python?

<!-- gh-comment-id:3502841883 --> @Masterolic commented on GitHub (Nov 7, 2025): > > Remote librespot-org seems to have found a workaround by using extended-metada endpoint that still contains the File parameter. ( See [librespot-org/librespot#1622](https://github.com/librespot-org/librespot/pull/1622) ) . However, I don't clearly know how to actually adapt the fix to this repository, so I hope someone could be up to it. > > the challenge is that this repo is built in python whereas the main librepsot repo is built in rust, and additionally the librespot devs are always very fast with finding and implementing fixes when these issues arise, however we are then stuck waiting for a language specific implementation of that fix > > since zotify itself is built in python, and rust modules can be used in python, maybe a correct approach would be to build a fork of zotify that implements librespot as a rust dependency and not as a python module. That way we can keep up with the speed at which the main librespot team finds and implements their fixes. I have a doubt is that we need to add extendedmetadata proto files in librespot-python?
Author
Owner

@abdullahrahimoon commented on GitHub (Nov 7, 2025):

ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this.

<!-- gh-comment-id:3502847741 --> @abdullahrahimoon commented on GitHub (Nov 7, 2025): ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this.
Author
Owner

@Masterolic commented on GitHub (Nov 7, 2025):

@kokarare1212 bro can you please check around this issue

<!-- gh-comment-id:3502874463 --> @Masterolic commented on GitHub (Nov 7, 2025): @kokarare1212 bro can you please check around this issue
Author
Owner

@Masterolic commented on GitHub (Nov 7, 2025):

ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this.

Bro do you know to implement?
Anyway the above mentioned issue i had imported proto files from rust program

https://github.com/Masterolic/librespot-python/blob/main/librespot/proto/extended_metadata_pb2.py

<!-- gh-comment-id:3502884566 --> @Masterolic commented on GitHub (Nov 7, 2025): > ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this. Bro do you know to implement? Anyway the above mentioned issue i had imported proto files from rust program https://github.com/Masterolic/librespot-python/blob/main/librespot/proto/extended_metadata_pb2.py
Author
Owner

@IsaacAgulhas commented on GitHub (Nov 7, 2025):

ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this.

Bro do you know to implement? Anyway the above mentioned issue i had imported proto files from rust program

https://github.com/Masterolic/librespot-python/blob/main/librespot/proto/extended_metadata_pb2.py

performing the proto imports will be very similar to how the guys did the patch for the Login5 authentication since that also performed a proto import, you have to do it in a try catch structured import. Here is code snippet of the Login5 they did so you can see the structure:

from librespot.proto.ExplicitContentPubsub_pb2 import UserAttributesUpdate
try:
    from librespot.proto.spotify.login5.v3 import Login5_pb2 as Login5
    from librespot.proto.spotify.login5.v3 import ClientInfo_pb2 as Login5ClientInfo
    from librespot.proto.spotify.login5.v3.credentials import Credentials_pb2 as Login5Credentials
    LOGIN5_AVAILABLE = True
except ImportError as e:
    # Login5 protobuf files not available, will use fallback
    LOGIN5_AVAILABLE = False
    Login5 = None
    Login5ClientInfo = None
    Login5Credentials = None
<!-- gh-comment-id:3502952427 --> @IsaacAgulhas commented on GitHub (Nov 7, 2025): > > ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this. > > Bro do you know to implement? Anyway the above mentioned issue i had imported proto files from rust program > > https://github.com/Masterolic/librespot-python/blob/main/librespot/proto/extended_metadata_pb2.py performing the proto imports will be very similar to how the guys did the patch for the Login5 authentication since that also performed a proto import, you have to do it in a try catch structured import. Here is code snippet of the Login5 they did so you can see the structure: ```python from librespot.proto.ExplicitContentPubsub_pb2 import UserAttributesUpdate try: from librespot.proto.spotify.login5.v3 import Login5_pb2 as Login5 from librespot.proto.spotify.login5.v3 import ClientInfo_pb2 as Login5ClientInfo from librespot.proto.spotify.login5.v3.credentials import Credentials_pb2 as Login5Credentials LOGIN5_AVAILABLE = True except ImportError as e: # Login5 protobuf files not available, will use fallback LOGIN5_AVAILABLE = False Login5 = None Login5ClientInfo = None Login5Credentials = None ```
Author
Owner

@Masterolic commented on GitHub (Nov 7, 2025):

ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this.

Bro do you know to implement? Anyway the above mentioned issue i had imported proto files from rust program
https://github.com/Masterolic/librespot-python/blob/main/librespot/proto/extended_metadata_pb2.py

performing the proto imports will be very similar to how the guys did the patch for the Login5 authentication since that also performed a proto import, you have to do it in a try catch structured import. Here is code snippet of the Login5 they did so you can see the structure:

from librespot.proto.ExplicitContentPubsub_pb2 import UserAttributesUpdate
try:
from librespot.proto.spotify.login5.v3 import Login5_pb2 as Login5
from librespot.proto.spotify.login5.v3 import ClientInfo_pb2 as Login5ClientInfo
from librespot.proto.spotify.login5.v3.credentials import Credentials_pb2 as Login5Credentials
LOGIN5_AVAILABLE = True
except ImportError as e:
# Login5 protobuf files not available, will use fallback
LOGIN5_AVAILABLE = False
Login5 = None
Login5ClientInfo = None
Login5Credentials = None

Ha buddy understood i was just trying to fix because my projects are stuck now...so when i tried to fix its ended with 400 status error i dont have much interal knowledge of librespot-python and proto

<!-- gh-comment-id:3502994351 --> @Masterolic commented on GitHub (Nov 7, 2025): > > > ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this. > > > > > > Bro do you know to implement? Anyway the above mentioned issue i had imported proto files from rust program > > https://github.com/Masterolic/librespot-python/blob/main/librespot/proto/extended_metadata_pb2.py > > performing the proto imports will be very similar to how the guys did the patch for the Login5 authentication since that also performed a proto import, you have to do it in a try catch structured import. Here is code snippet of the Login5 they did so you can see the structure: > > from librespot.proto.ExplicitContentPubsub_pb2 import UserAttributesUpdate > try: > from librespot.proto.spotify.login5.v3 import Login5_pb2 as Login5 > from librespot.proto.spotify.login5.v3 import ClientInfo_pb2 as Login5ClientInfo > from librespot.proto.spotify.login5.v3.credentials import Credentials_pb2 as Login5Credentials > LOGIN5_AVAILABLE = True > except ImportError as e: > # Login5 protobuf files not available, will use fallback > LOGIN5_AVAILABLE = False > Login5 = None > Login5ClientInfo = None > Login5Credentials = None Ha buddy understood i was just trying to fix because my projects are stuck now...so when i tried to fix its ended with 400 status error i dont have much interal knowledge of librespot-python and proto
Author
Owner

@IsaacAgulhas commented on GitHub (Nov 7, 2025):

ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this.

Bro do you know to implement? Anyway the above mentioned issue i had imported proto files from rust program
https://github.com/Masterolic/librespot-python/blob/main/librespot/proto/extended_metadata_pb2.py

performing the proto imports will be very similar to how the guys did the patch for the Login5 authentication since that also performed a proto import, you have to do it in a try catch structured import. Here is code snippet of the Login5 they did so you can see the structure:
from librespot.proto.ExplicitContentPubsub_pb2 import UserAttributesUpdate
try:
from librespot.proto.spotify.login5.v3 import Login5_pb2 as Login5
from librespot.proto.spotify.login5.v3 import ClientInfo_pb2 as Login5ClientInfo
from librespot.proto.spotify.login5.v3.credentials import Credentials_pb2 as Login5Credentials
LOGIN5_AVAILABLE = True
except ImportError as e:

Login5 protobuf files not available, will use fallback

LOGIN5_AVAILABLE = False
Login5 = None
Login5ClientInfo = None
Login5Credentials = None

Ha buddy understood i was just trying to fix because my projects are stuck now...so when i tried to fix its ended with 400 status error i dont have much interal knowledge of librespot-python and proto

where did you get the librespot/proto/extended_metadata_pb2.py in the first place, because in my project it is not there. Did you recompile the librespot protos from source?

<!-- gh-comment-id:3503029793 --> @IsaacAgulhas commented on GitHub (Nov 7, 2025): > > > > ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this. > > > > > > > > > Bro do you know to implement? Anyway the above mentioned issue i had imported proto files from rust program > > > https://github.com/Masterolic/librespot-python/blob/main/librespot/proto/extended_metadata_pb2.py > > > > > > performing the proto imports will be very similar to how the guys did the patch for the Login5 authentication since that also performed a proto import, you have to do it in a try catch structured import. Here is code snippet of the Login5 they did so you can see the structure: > > from librespot.proto.ExplicitContentPubsub_pb2 import UserAttributesUpdate > > try: > > from librespot.proto.spotify.login5.v3 import Login5_pb2 as Login5 > > from librespot.proto.spotify.login5.v3 import ClientInfo_pb2 as Login5ClientInfo > > from librespot.proto.spotify.login5.v3.credentials import Credentials_pb2 as Login5Credentials > > LOGIN5_AVAILABLE = True > > except ImportError as e: > > # Login5 protobuf files not available, will use fallback > > LOGIN5_AVAILABLE = False > > Login5 = None > > Login5ClientInfo = None > > Login5Credentials = None > > Ha buddy understood i was just trying to fix because my projects are stuck now...so when i tried to fix its ended with 400 status error i dont have much interal knowledge of librespot-python and proto where did you get the librespot/proto/extended_metadata_pb2.py in the first place, because in my project it is not there. Did you recompile the librespot protos from source?
Author
Owner

@Masterolic commented on GitHub (Nov 7, 2025):

ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this.

Bro do you know to implement? Anyway the above mentioned issue i had imported proto files from rust program
https://github.com/Masterolic/librespot-python/blob/main/librespot/proto/extended_metadata_pb2.py

performing the proto imports will be very similar to how the guys did the patch for the Login5 authentication since that also performed a proto import, you have to do it in a try catch structured import. Here is code snippet of the Login5 they did so you can see the structure:
from librespot.proto.ExplicitContentPubsub_pb2 import UserAttributesUpdate
try:
from librespot.proto.spotify.login5.v3 import Login5_pb2 as Login5
from librespot.proto.spotify.login5.v3 import ClientInfo_pb2 as Login5ClientInfo
from librespot.proto.spotify.login5.v3.credentials import Credentials_pb2 as Login5Credentials
LOGIN5_AVAILABLE = True
except ImportError as e:

Login5 protobuf files not available, will use fallback

LOGIN5_AVAILABLE = False
Login5 = None
Login5ClientInfo = None
Login5Credentials = None

Ha buddy understood i was just trying to fix because my projects are stuck now...so when i tried to fix its ended with 400 status error i dont have much interal knowledge of librespot-python and proto

where did you get the librespot/proto/extended_metadata_pb2.py in the first place, because in my project it is not there. Did you recompile the librespot protos from source?

Yes buddy
github.com/photovoltex/librespot@9a0c96bd8c/protocol/proto/extended_metadata.proto

From there 2,3 proto files had recompiled and implemented

<!-- gh-comment-id:3503089504 --> @Masterolic commented on GitHub (Nov 7, 2025): > > > > > ModuleNotFoundError: No module named 'extended_metadata_pb2' getting this. > > > > > > > > > > > > Bro do you know to implement? Anyway the above mentioned issue i had imported proto files from rust program > > > > https://github.com/Masterolic/librespot-python/blob/main/librespot/proto/extended_metadata_pb2.py > > > > > > > > > performing the proto imports will be very similar to how the guys did the patch for the Login5 authentication since that also performed a proto import, you have to do it in a try catch structured import. Here is code snippet of the Login5 they did so you can see the structure: > > > from librespot.proto.ExplicitContentPubsub_pb2 import UserAttributesUpdate > > > try: > > > from librespot.proto.spotify.login5.v3 import Login5_pb2 as Login5 > > > from librespot.proto.spotify.login5.v3 import ClientInfo_pb2 as Login5ClientInfo > > > from librespot.proto.spotify.login5.v3.credentials import Credentials_pb2 as Login5Credentials > > > LOGIN5_AVAILABLE = True > > > except ImportError as e: > > > # Login5 protobuf files not available, will use fallback > > > LOGIN5_AVAILABLE = False > > > Login5 = None > > > Login5ClientInfo = None > > > Login5Credentials = None > > > > > > Ha buddy understood i was just trying to fix because my projects are stuck now...so when i tried to fix its ended with 400 status error i dont have much interal knowledge of librespot-python and proto > > where did you get the librespot/proto/extended_metadata_pb2.py in the first place, because in my project it is not there. Did you recompile the librespot protos from source? Yes buddy https://github.com/photovoltex/librespot/blob/9a0c96bd8c97d716ded9088dbbe7b1d088f7bf80/protocol/proto/extended_metadata.proto From there 2,3 proto files had recompiled and implemented
Author
Owner

@Masterolic commented on GitHub (Nov 7, 2025):

@photovoltex can you fix this python version too :)

<!-- gh-comment-id:3503177464 --> @Masterolic commented on GitHub (Nov 7, 2025): @photovoltex can you fix this python version too :)
Author
Owner

@IsaacAgulhas commented on GitHub (Nov 7, 2025):

@photovoltex can you fix this python version too :)

@Masterolic is your version now working?!

<!-- gh-comment-id:3503200953 --> @IsaacAgulhas commented on GitHub (Nov 7, 2025): > [@photovoltex](https://github.com/photovoltex) can you fix this python version too :) @Masterolic is your version now working?!
Author
Owner

@Masterolic commented on GitHub (Nov 7, 2025):

@photovoltex can you fix this python version too :)

@Masterolic is your version now working?!

My version doesn't it returns 400 always idk how to implement protobuff request to that endpoints:)

<!-- gh-comment-id:3503215872 --> @Masterolic commented on GitHub (Nov 7, 2025): > > [@photovoltex](https://github.com/photovoltex) can you fix this python version too :) > > [@Masterolic](https://github.com/Masterolic) is your version now working?! My version doesn't it returns 400 always idk how to implement protobuff request to that endpoints:)
Author
Owner

@shayanmaher commented on GitHub (Nov 7, 2025):

@photovoltex can you fix this python version too :)

@Masterolic is your version now working?!

My version doesn't it returns 400 always idk how to implement protobuff request to that endpoints:)

can you push your local library on git to fork that?

<!-- gh-comment-id:3503748954 --> @shayanmaher commented on GitHub (Nov 7, 2025): > > > [@photovoltex](https://github.com/photovoltex) can you fix this python version too :) > > > > > > [@Masterolic](https://github.com/Masterolic) is your version now working?! > > My version doesn't it returns 400 always idk how to implement protobuff request to that endpoints:) can you push your local library on git to fork that?
Author
Owner

@Masterolic commented on GitHub (Nov 7, 2025):

@photovoltex can you fix this python version too :)

@Masterolic is your version now working?!

My version doesn't it returns 400 always idk how to implement protobuff request to that endpoints:)

can you push your local library on git to fork that?

That doesn't work mate return 400 i don't know what i made is correct anyway proto files updated are public

--- PASTE THIS ENTIRE BLOCK INTO YOUR CLASS ---

import typing
from requests.structures import CaseInsensitiveDict
from librespot.proto import extended_metadata_pb2
from librespot.proto import extension_kind_pb2
from librespot.proto import metadata_pb2 as Metadata

Assuming your TrackId type is imported from somewhere

from librespot.structure import TrackId

def get_extended_metadata(
self, request_proto: extended_metadata_pb2.BatchedEntityRequest
) -> extended_metadata_pb2.BatchedExtensionResponse:
"""
(New - Sync - FIX 2) Performs the raw POST request to the extended-metadata endpoint.
This version uses sendToUrl to ensure the correct base URL is used.
"""
endpoint_suffix = "/extended-metadata/v0/extended-metadata"
# Use the same base URL that the old get_metadata_4_track was using
base_url = "https://spclient.wg.spotify.com"

request_data = request_proto.SerializeToString()

request_headers = CaseInsensitiveDict()
request_headers["Content-Type"] = "application/x-protobuf"

# *** THIS IS THE FIX: ***
# Changed self.send() to self.sendToUrl() and provided the explicit base_url.
response = self.sendToUrl(
    method="POST",
    url=base_url, 
    suffix=endpoint_suffix,
    headers=request_headers,
    body=request_data
)

# Check status code, just like your old function
ApiClient.StatusCodeException.check_status(response)

body = response.content
if body is None:
    raise RuntimeError("No body in response from get_extended_metadata")

# Parse the protobuf response
response_proto = extended_metadata_pb2.BatchedExtensionResponse()
response_proto.ParseFromString(body)
return response_proto

def get_metadata(self, kind: extension_kind_pb2.ExtensionKind, uri: str) -> bytes:
"""
(New - Sync) Generic wrapper to build a request and unpack the response
for a single metadata entity.
"""
# 1. Build the Protobuf request
request_proto = extended_metadata_pb2.BatchedEntityRequest()
entity_request = request_proto.entity_request.add()
entity_request.entity_uri = uri

query = entity_request.query.add()
query.extension_kind = kind

# 2. Call the new synchronous endpoint
response_proto = self.get_extended_metadata(request_proto)

# 3. Unpack the response
if not response_proto.extended_metadata:
    raise Exception("No extended_metadata in response")
    
extended_metadata = response_proto.extended_metadata[0]

if not extended_metadata.extension_data:
    raise Exception("No extension_data in response")
    
data = extended_metadata.extension_data[0]

if not data.HasField("extension_data"):
    raise Exception("No data in extension_data")
    
return data.extension_data.value

def get_track_metadata(self, track_uri: str) -> bytes:
"""
(New - Sync) Specific helper for getting track metadata bytes.
"""
return self.get_metadata(extension_kind_pb2.TRACK_V4, track_uri)

--- THIS REPLACES your old get_metadata_4_track ---

def get_metadata_4_track(self, track: TrackId) -> Metadata.Track:
"""
(FIXED - Sync) Fetches track metadata using the new
extended-metadata endpoint.

:param track: TrackId:
"""

# 1. Get the full Spotify URI string (e.g., "spotify:track:...")
try:
    track_uri = track.to_uri()
except AttributeError:
    # Fallback if the method is named differently
    track_uri = track.to_spotify_uri() 

# 2. Call the new synchronous helper to get the raw bytes
#    THIS IS THE SECOND MOST LIKELY PLACE FOR AN ERROR:
#    If 'track_uri' is not a valid string (like "spotify:track:...")
#    the server will return a 400.
body = self.get_track_metadata(track_uri)

if body is None:
    raise RuntimeError("No data returned from get_track_metadata")

# 3. Parse the bytes into the Track protobuf
proto = Metadata.Track()
proto.ParseFromString(body)
return proto

--- END OF BLOCK ---

This way i had tried

<!-- gh-comment-id:3503810645 --> @Masterolic commented on GitHub (Nov 7, 2025): > > > > [@photovoltex](https://github.com/photovoltex) can you fix this python version too :) > > > > > > > > > [@Masterolic](https://github.com/Masterolic) is your version now working?! > > > > > > My version doesn't it returns 400 always idk how to implement protobuff request to that endpoints:) > > can you push your local library on git to fork that? That doesn't work mate return 400 i don't know what i made is correct anyway proto files updated are public # --- PASTE THIS ENTIRE BLOCK INTO YOUR CLASS --- import typing from requests.structures import CaseInsensitiveDict from librespot.proto import extended_metadata_pb2 from librespot.proto import extension_kind_pb2 from librespot.proto import metadata_pb2 as Metadata # Assuming your TrackId type is imported from somewhere # from librespot.structure import TrackId def get_extended_metadata( self, request_proto: extended_metadata_pb2.BatchedEntityRequest ) -> extended_metadata_pb2.BatchedExtensionResponse: """ (New - Sync - FIX 2) Performs the raw POST request to the extended-metadata endpoint. This version uses sendToUrl to ensure the correct base URL is used. """ endpoint_suffix = "/extended-metadata/v0/extended-metadata" # Use the same base URL that the old get_metadata_4_track was using base_url = "https://spclient.wg.spotify.com" request_data = request_proto.SerializeToString() request_headers = CaseInsensitiveDict() request_headers["Content-Type"] = "application/x-protobuf" # *** THIS IS THE FIX: *** # Changed self.send() to self.sendToUrl() and provided the explicit base_url. response = self.sendToUrl( method="POST", url=base_url, suffix=endpoint_suffix, headers=request_headers, body=request_data ) # Check status code, just like your old function ApiClient.StatusCodeException.check_status(response) body = response.content if body is None: raise RuntimeError("No body in response from get_extended_metadata") # Parse the protobuf response response_proto = extended_metadata_pb2.BatchedExtensionResponse() response_proto.ParseFromString(body) return response_proto def get_metadata(self, kind: extension_kind_pb2.ExtensionKind, uri: str) -> bytes: """ (New - Sync) Generic wrapper to build a request and unpack the response for a single metadata entity. """ # 1. Build the Protobuf request request_proto = extended_metadata_pb2.BatchedEntityRequest() entity_request = request_proto.entity_request.add() entity_request.entity_uri = uri query = entity_request.query.add() query.extension_kind = kind # 2. Call the new synchronous endpoint response_proto = self.get_extended_metadata(request_proto) # 3. Unpack the response if not response_proto.extended_metadata: raise Exception("No extended_metadata in response") extended_metadata = response_proto.extended_metadata[0] if not extended_metadata.extension_data: raise Exception("No extension_data in response") data = extended_metadata.extension_data[0] if not data.HasField("extension_data"): raise Exception("No data in extension_data") return data.extension_data.value def get_track_metadata(self, track_uri: str) -> bytes: """ (New - Sync) Specific helper for getting track metadata bytes. """ return self.get_metadata(extension_kind_pb2.TRACK_V4, track_uri) # --- THIS REPLACES your old get_metadata_4_track --- def get_metadata_4_track(self, track: TrackId) -> Metadata.Track: """ (FIXED - Sync) Fetches track metadata using the new extended-metadata endpoint. :param track: TrackId: """ # 1. Get the full Spotify URI string (e.g., "spotify:track:...") try: track_uri = track.to_uri() except AttributeError: # Fallback if the method is named differently track_uri = track.to_spotify_uri() # 2. Call the new synchronous helper to get the raw bytes # THIS IS THE SECOND MOST LIKELY PLACE FOR AN ERROR: # If 'track_uri' is not a valid string (like "spotify:track:...") # the server will return a 400. body = self.get_track_metadata(track_uri) if body is None: raise RuntimeError("No data returned from get_track_metadata") # 3. Parse the bytes into the Track protobuf proto = Metadata.Track() proto.ParseFromString(body) return proto # --- END OF BLOCK --- This way i had tried
Author
Owner

@photovoltex commented on GitHub (Nov 7, 2025):

@photovoltex can you fix this python version too :)

Obviously not. Python isn't my language of choice and besides that, the solution itself isn't all to complicated.

<!-- gh-comment-id:3504210126 --> @photovoltex commented on GitHub (Nov 7, 2025): > @photovoltex can you fix this python version too :) Obviously not. Python isn't my language of choice and besides that, the solution itself isn't all to complicated.
Author
Owner

@Masterolic commented on GitHub (Nov 8, 2025):

@photovoltex can you fix this python version too :)

Obviously not. Python isn't my language of choice and besides that, the solution itself isn't all to complicated.

Okay thank you buddy... Can i know one thing is that extended metadata only accept protobuff data? Have you ever faced 400 http status

<!-- gh-comment-id:3505660024 --> @Masterolic commented on GitHub (Nov 8, 2025): > > [@photovoltex](https://github.com/photovoltex) can you fix this python version too :) > > Obviously not. Python isn't my language of choice and besides that, the solution itself isn't all to complicated. Okay thank you buddy... Can i know one thing is that extended metadata only accept protobuff data? Have you ever faced 400 http status
Author
Owner

@Masterolic commented on GitHub (Nov 8, 2025):

@Googolplexed0 @C0rn3j @ @matseee @DraftKinner @root4loot @akbad @shauneccles
Just mention due to recent activity of this library.Kindly have a little time to checkout this issue

<!-- gh-comment-id:3506008592 --> @Masterolic commented on GitHub (Nov 8, 2025): @Googolplexed0 @C0rn3j @ @matseee @DraftKinner @root4loot @akbad @shauneccles Just mention due to recent activity of this library.Kindly have a little time to checkout this issue
Author
Owner

@Googolplexed0 commented on GitHub (Nov 9, 2025):

Looks like it will require the addition of a new protobuf file for extended metadata (plus some necessary components). I'm taking a crack at it.

<!-- gh-comment-id:3507538633 --> @Googolplexed0 commented on GitHub (Nov 9, 2025): Looks like it will require the addition of a new [protobuf file for extended metadata](https://github.com/librespot-org/librespot/blob/dev/protocol/proto/extended_metadata.proto) (plus some necessary components). I'm taking a crack at it.
Author
Owner

@Masterolic commented on GitHub (Nov 9, 2025):

Looks like it will require the addition of a new protobuf file for extended metadata (plus some necessary components). I'm taking a crack at it.

Thanks for the reply... i had tried but it ended upon 400 status code

Please fix soon as possible my project are under critical stage so please i can donate you some dollars if you do

Thanks wishing all the best!

<!-- gh-comment-id:3507629216 --> @Masterolic commented on GitHub (Nov 9, 2025): > Looks like it will require the addition of a new [protobuf file for extended metadata](https://github.com/librespot-org/librespot/blob/dev/protocol/proto/extended_metadata.proto) (plus some necessary components). I'm taking a crack at it. Thanks for the reply... [i had tried](https://github.com/kokarare1212/librespot-python/issues/321#issuecomment-3503810645) but it ended upon 400 status code Please fix soon as possible my project are under critical stage so please i can donate you some dollars if you do Thanks wishing all the best!
Author
Owner

@skellycode commented on GitHub (Nov 9, 2025):

Looks like it will require the addition of a new protobuf file for extended metadata (plus some necessary components). I'm taking a crack at it.

Best of luck - glad someone smarter than I is taking a look at it!
I’ve spent about 8 hours so far messing around with it but no matter what I try I end up with the 400 errors that @Masterolic is also getting. Fingers crossed there’s nothing too much more to it 🤞
Happy to share/help how I can!

<!-- gh-comment-id:3507853114 --> @skellycode commented on GitHub (Nov 9, 2025): > Looks like it will require the addition of a new [protobuf file for extended metadata](https://github.com/librespot-org/librespot/blob/dev/protocol/proto/extended_metadata.proto) (plus some necessary components). I'm taking a crack at it. Best of luck - glad someone smarter than I is taking a look at it! I’ve spent about 8 hours so far messing around with it but no matter what I try I end up with the 400 errors that @Masterolic is also getting. Fingers crossed there’s nothing too much more to it 🤞 Happy to share/help how I can!
Author
Owner

@Googolplexed0 commented on GitHub (Nov 9, 2025):

i had tried but it ended upon 400 status code

no matter what I try I end up with the 400 errors

All my attempts have ended with a Status 400 response as well. There must be something missing or malformed compared to the librespot Rust implementation, but I can't tell what. Rust isn't a language I can write, but I can read it well enough to understand and translate into Python. I am pretty confident I mirrored everything, checking all the way down to the request header fields as set by pub async fn request_with_options(), but no luck. Maybe a protobuf's defaults are set differently between Rust's ..Default::default() and Python's "just leave it unset"?

The changes I made are forked here, if anyone (especially @photovoltex if he would be willing) could give it a quick spot-check and find what my implementation is doing wrong. Also, it would probably be a better strategy to have everyone playing around with a single repo with until we find what's missing.

<!-- gh-comment-id:3507889697 --> @Googolplexed0 commented on GitHub (Nov 9, 2025): > i had tried but it ended upon 400 status code > no matter what I try I end up with the 400 errors All my attempts have ended with a Status 400 response as well. There must be something missing or malformed compared to the librespot Rust implementation, but I can't tell what. Rust isn't a language I can write, but I can read it well enough to understand and translate into Python. I am pretty confident I mirrored everything, checking all the way down to the request header fields as set by `pub async fn request_with_options()`, but no luck. _Maybe_ a protobuf's defaults are set differently between Rust's `..Default::default()` and Python's "just leave it unset"? The changes I made are forked [here](https://github.com/Googolplexed0/librespot-python/tree/proto-ext-metadata), if anyone (especially @photovoltex if he would be willing) could give it a quick spot-check and find what my implementation is doing wrong. Also, it would probably be a better strategy to have everyone playing around with a single repo with until we find what's missing.
Author
Owner

@photovoltex commented on GitHub (Nov 9, 2025):

Please stop pinging me on this topic, I can't help with your python code. Your change look fine from the names of the proto defs. But I don't know this codebase and can't help unless I would look at the code path your code is calling.

<!-- gh-comment-id:3508011456 --> @photovoltex commented on GitHub (Nov 9, 2025): Please stop pinging me on this topic, I can't help with your python code. Your change look fine from the names of the proto defs. But I don't know this codebase and can't help unless I would look at the code path your code is calling.
Author
Owner

@TomerGamerTV commented on GitHub (Nov 9, 2025):

Having the same issue

<!-- gh-comment-id:3508086253 --> @TomerGamerTV commented on GitHub (Nov 9, 2025): Having the same issue
Author
Owner

@sausa28 commented on GitHub (Nov 9, 2025):

@Googolplexed0 I've had a bit of mess around with your fork and I think the 400 errors are because its not sending the content-length header with the request, due the way the request is currently built (directly with a PreparedRequest rather than using request.Request() to build it).

I tried replacing the build_request method with the following, and that seems to get past the 400 errors, though it now fails on parsing the response, and I haven't looked at that.

def build_request(
        self,
        method: str,
        suffix: str,
        headers: typing.Union[None, CaseInsensitiveDict[str, str]],
        body: typing.Union[None, bytes],
        url: typing.Union[None, str],
    ) -> requests.PreparedRequest:
        """

        :param method: str:
        :param suffix: str:
        :param headers: typing.Union[None:
        :param CaseInsensitiveDict[str:
        :param str]]:
        :param body: typing.Union[None:
        :param bytes]:
        :param url: typing.Union[None:
        :param str]:

        """
        if self.__client_token_str is None:
            resp = self.__client_token()
            self.__client_token_str = resp.granted_token.token
            self.logger.debug("Updated client token: {}".format(
                self.__client_token_str))

        if url is None:
            url = self.__base_url + suffix
        else:
            url = url + suffix

        if headers is None:
            headers = {}
        headers["Authorization"] = "Bearer {}".format(
            self.__session.tokens().get("playlist-read"))
        headers["client-token"] = self.__client_token_str

        request = requests.Request(method, url, headers=headers, data=body)

        return request.prepare()

Edit: made a small PR to the fork https://github.com/Googolplexed0/librespot-python/pull/1

<!-- gh-comment-id:3508451966 --> @sausa28 commented on GitHub (Nov 9, 2025): @Googolplexed0 I've had a bit of mess around with your fork and I think the 400 errors are because its not sending the content-length header with the request, due the way the request is currently built (directly with a PreparedRequest rather than using request.Request() to build it). I tried replacing the `build_request` method with the following, and that seems to get past the 400 errors, though it now fails on parsing the response, and I haven't looked at that. ```python def build_request( self, method: str, suffix: str, headers: typing.Union[None, CaseInsensitiveDict[str, str]], body: typing.Union[None, bytes], url: typing.Union[None, str], ) -> requests.PreparedRequest: """ :param method: str: :param suffix: str: :param headers: typing.Union[None: :param CaseInsensitiveDict[str: :param str]]: :param body: typing.Union[None: :param bytes]: :param url: typing.Union[None: :param str]: """ if self.__client_token_str is None: resp = self.__client_token() self.__client_token_str = resp.granted_token.token self.logger.debug("Updated client token: {}".format( self.__client_token_str)) if url is None: url = self.__base_url + suffix else: url = url + suffix if headers is None: headers = {} headers["Authorization"] = "Bearer {}".format( self.__session.tokens().get("playlist-read")) headers["client-token"] = self.__client_token_str request = requests.Request(method, url, headers=headers, data=body) return request.prepare() ``` Edit: made a small PR to the fork https://github.com/Googolplexed0/librespot-python/pull/1
Author
Owner

@Masterolic commented on GitHub (Nov 9, 2025):

https://github.com/Masterolic/librespot-python

Extended metadata api issue had being fixed in above repo

Thanks to @sausa28 for fixing 400 status code
Thanks to @Googolplexed0 for implementing proto and extended api
Thanks to me for adding parse_batched response and stuck at 400 🙂
Thanks to @skellycode for his trying

And thanks to all who contributed
Happy to see some of us tried and was stuck at 400 status code which was fixed by @sausa28 maybe someone would fix earlier itself if 400 doesn't occurred

<!-- gh-comment-id:3508542703 --> @Masterolic commented on GitHub (Nov 9, 2025): https://github.com/Masterolic/librespot-python Extended metadata api issue had being fixed in above repo Thanks to @sausa28 for fixing 400 status code Thanks to @Googolplexed0 for implementing proto and extended api Thanks to me for adding parse_batched response and stuck at 400 🙂 Thanks to @skellycode for his trying And thanks to all who contributed Happy to see some of us tried and was stuck at 400 status code which was fixed by @sausa28 maybe someone would fix earlier itself if 400 doesn't occurred
Author
Owner

@rainrdx commented on GitHub (Nov 9, 2025):

Thank you @Masterolic for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you.

<!-- gh-comment-id:3508776396 --> @rainrdx commented on GitHub (Nov 9, 2025): Thank you @Masterolic for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you.
Author
Owner

@abdullahrahimoon commented on GitHub (Nov 9, 2025):

Thank you all, Have a good day

<!-- gh-comment-id:3508822962 --> @abdullahrahimoon commented on GitHub (Nov 9, 2025): Thank you all, Have a good day
Author
Owner

@Masterolic commented on GitHub (Nov 10, 2025):

Thank you @Masterolic for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you.

Kindly please checkout now seems it should work now

Some other issues are there because it returns 404

extended_metadata {
header {
provider_error_status: 200
cache_ttl_in_seconds: 86400
offline_ttl_in_seconds: 2592000
}
extension_kind: EPISODE_V4
extension_data {
header {
status_code: 404
cache_ttl_in_seconds: 86400
offline_ttl_in_seconds: 2592000
}
entity_uri: "Spotify:episode:4pMpCdLiuSGunf4Cs68k1Q"
}
}

<!-- gh-comment-id:3509176113 --> @Masterolic commented on GitHub (Nov 10, 2025): > Thank you [@Masterolic](https://github.com/Masterolic) for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you. Kindly please checkout now seems it should work now Some other issues are there because it returns 404 extended_metadata { header { provider_error_status: 200 cache_ttl_in_seconds: 86400 offline_ttl_in_seconds: 2592000 } extension_kind: EPISODE_V4 extension_data { header { status_code: 404 cache_ttl_in_seconds: 86400 offline_ttl_in_seconds: 2592000 } entity_uri: "Spotify:episode:4pMpCdLiuSGunf4Cs68k1Q" } }
Author
Owner

@Masterolic commented on GitHub (Nov 10, 2025):

Thank you all, Have a good day

Same to you:)

<!-- gh-comment-id:3509176474 --> @Masterolic commented on GitHub (Nov 10, 2025): > Thank you all, Have a good day Same to you:)
Author
Owner

@fafamobile commented on GitHub (Nov 10, 2025):

forced update and not seeming to work? how do i implement

<!-- gh-comment-id:3509177366 --> @fafamobile commented on GitHub (Nov 10, 2025): forced update and not seeming to work? how do i implement
Author
Owner

@rainrdx commented on GitHub (Nov 10, 2025):

Thank you @Masterolic for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you.

Kindly please checkout now seems it should work now

Thank you for doing this. Seems your / Googolplexed0's work both work. Thank you both!!

<!-- gh-comment-id:3509183016 --> @rainrdx commented on GitHub (Nov 10, 2025): > > Thank you [@Masterolic](https://github.com/Masterolic) for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you. > > Kindly please checkout now seems it should work now Thank you for doing this. Seems your / Googolplexed0's work both work. Thank you both!!
Author
Owner

@Masterolic commented on GitHub (Nov 10, 2025):

forced update and not seeming to work? how do i implement

Whar happened

<!-- gh-comment-id:3509272138 --> @Masterolic commented on GitHub (Nov 10, 2025): > forced update and not seeming to work? how do i implement Whar happened
Author
Owner

@Masterolic commented on GitHub (Nov 10, 2025):

Thank you @Masterolic for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you.

Buddy fixed episode issue..i think to get show ShowId is not yet implemented completely

<!-- gh-comment-id:3509370349 --> @Masterolic commented on GitHub (Nov 10, 2025): > Thank you [@Masterolic](https://github.com/Masterolic) for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you. Buddy fixed episode issue..i think to get show ShowId is not yet implemented completely
Author
Owner

@rainrdx commented on GitHub (Nov 10, 2025):

Thank you. I took a look again and there might be problems (I use some old code to archive some spotify online podcasts https://github.com/Yetangitu/Spodcast), but this could just be that the other code that relies on librespot is too old. I need to look again tomorrow. Already appreciate your working on this. Don't wanna report some thing before I get to investigate first.

<!-- gh-comment-id:3509518621 --> @rainrdx commented on GitHub (Nov 10, 2025): Thank you. I took a look again and there might be problems (I use some old code to archive some spotify online podcasts https://github.com/Yetangitu/Spodcast), but this could just be that the other code that relies on librespot is too old. I need to look again tomorrow. Already appreciate your working on this. Don't wanna report some thing before I get to investigate first.
Author
Owner

@Mariano228 commented on GitHub (Nov 10, 2025):

Thank you @Masterolic for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you.

Kindly please checkout now seems it should work now

Thank you for doing this. Seems your / Googolplexed0's work both work. Thank you both!!

why are yuo saying thank you ? IT's not fixed, im still getting this

PS C:\Users\Tony> zotify https://open.spotify.com/track/1xoBRdLtA9H4zKe0NRD4OJ?si=51a2d3f870054036

    [∙∙∙] Logging in...                                                                                                     [∙∙∙] Fetching track information...                                                                                     [●∙∙] Preparing download...                                                                                     

ERROR: SKIPPING SONG - GENERAL DOWNLOAD ERROR

Track_Label: Alexander Abreu - Silencio - Remix - Track_ID: 1xoBRdLtA9H4zKe0NRD4OJ

########################################################################################################################
{}
########################################################################################################################

Traceback (most recent call last):
File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\track.py", line 293, in download_track
stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY)
File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 628, in get_content_stream
raise e
File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 620, in get_content_stream
return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None)
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio_init_.py", line 740, in load
return self.load_track(playable_id, audio_quality_picker, preload,
~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
halt_listener)
^^^^^^^^^^^^^^
File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio_init_.py", line 792, in load_track
raise RuntimeError("Cannot get alternative track")
RuntimeError: Cannot get alternative track

<!-- gh-comment-id:3510426002 --> @Mariano228 commented on GitHub (Nov 10, 2025): > > > Thank you [@Masterolic](https://github.com/Masterolic) for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you. > > > > > > Kindly please checkout now seems it should work now > > Thank you for doing this. Seems your / Googolplexed0's work both work. Thank you both!! why are yuo saying thank you ? IT's not fixed, im still getting this PS C:\Users\Tony> zotify https://open.spotify.com/track/1xoBRdLtA9H4zKe0NRD4OJ?si=51a2d3f870054036 [∙∙∙] Logging in... [∙∙∙] Fetching track information... [●∙∙] Preparing download... ### ERROR: SKIPPING SONG - GENERAL DOWNLOAD ERROR ### ### Track_Label: Alexander Abreu - Silencio - Remix - Track_ID: 1xoBRdLtA9H4zKe0NRD4OJ ### ######################################################################################################################## {} ######################################################################################################################## Traceback (most recent call last): File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\track.py", line 293, in download_track stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY) File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 628, in get_content_stream raise e File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 620, in get_content_stream return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None) ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio\__init__.py", line 740, in load return self.load_track(playable_id, audio_quality_picker, preload, ~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ halt_listener) ^^^^^^^^^^^^^^ File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio\__init__.py", line 792, in load_track raise RuntimeError("Cannot get alternative track") RuntimeError: Cannot get alternative track
Author
Owner

@skellycode commented on GitHub (Nov 10, 2025):

Thank you @Masterolic for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you.

Kindly please checkout now seems it should work now

Thank you for doing this. Seems your / Googolplexed0's work both work. Thank you both!!

why are yuo saying thank you ? IT's not fixed, im still getting this

PS C:\Users\Tony> zotify https://open.spotify.com/track/1xoBRdLtA9H4zKe0NRD4OJ?si=51a2d3f870054036

    [∙∙∙] Logging in...                                                                                                     [∙∙∙] Fetching track information...                                                                                     [●∙∙] Preparing download...                                                                                     

ERROR: SKIPPING SONG - GENERAL DOWNLOAD ERROR

Track_Label: Alexander Abreu - Silencio - Remix - Track_ID: 1xoBRdLtA9H4zKe0NRD4OJ

######################################################################################################################## {} ########################################################################################################################

Traceback (most recent call last): File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\track.py", line 293, in download_track stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY) File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 628, in get_content_stream raise e File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 620, in get_content_stream return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None) ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio__init__.py", line 740, in load return self.load_track(playable_id, audio_quality_picker, preload, ~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ halt_listener) ^^^^^^^^^^^^^^ File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio__init__.py", line 792, in load_track raise RuntimeError("Cannot get alternative track") RuntimeError: Cannot get alternative track

That is because the solution so wonderfully implemented by @Masterolic, @Googolplexed0 and @sausa28 resolves the streaming aspect of the API change. You are attempting to use a downloading tool which pulls a file from the API which is not included in the scope of the patch.

<!-- gh-comment-id:3510519836 --> @skellycode commented on GitHub (Nov 10, 2025): > > > > Thank you [@Masterolic](https://github.com/Masterolic) for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you. > > > > > > > > > Kindly please checkout now seems it should work now > > > > > > Thank you for doing this. Seems your / Googolplexed0's work both work. Thank you both!! > > why are yuo saying thank you ? IT's not fixed, im still getting this > > PS C:\Users\Tony> zotify https://open.spotify.com/track/1xoBRdLtA9H4zKe0NRD4OJ?si=51a2d3f870054036 > > ``` > [∙∙∙] Logging in... [∙∙∙] Fetching track information... [●∙∙] Preparing download... > ``` > > ### ERROR: SKIPPING SONG - GENERAL DOWNLOAD ERROR > ### Track_Label: Alexander Abreu - Silencio - Remix - Track_ID: 1xoBRdLtA9H4zKe0NRD4OJ > > ######################################################################################################################## {} ######################################################################################################################## > > Traceback (most recent call last): File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\track.py", line 293, in download_track stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY) File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 628, in get_content_stream raise e File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 620, in get_content_stream return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None) ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio__init__.py", line 740, in load return self.load_track(playable_id, audio_quality_picker, preload, ~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ halt_listener) ^^^^^^^^^^^^^^ File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio__init__.py", line 792, in load_track raise RuntimeError("Cannot get alternative track") RuntimeError: Cannot get alternative track That is because the solution so wonderfully implemented by @Masterolic, @Googolplexed0 and @sausa28 resolves the **streaming** aspect of the API change. You are attempting to use a **downloading** tool which pulls a _file_ from the API which is not included in the scope of the patch.
Author
Owner

@IsaacAgulhas commented on GitHub (Nov 10, 2025):

Thank you @Masterolic for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you.

Kindly please checkout now seems it should work now

Thank you for doing this. Seems your / Googolplexed0's work both work. Thank you both!!

why are yuo saying thank you ? IT's not fixed, im still getting this
PS C:\Users\Tony> zotify https://open.spotify.com/track/1xoBRdLtA9H4zKe0NRD4OJ?si=51a2d3f870054036

    [∙∙∙] Logging in...                                                                                                     [∙∙∙] Fetching track information...                                                                                     [●∙∙] Preparing download...                                                                                     

ERROR: SKIPPING SONG - GENERAL DOWNLOAD ERROR

Track_Label: Alexander Abreu - Silencio - Remix - Track_ID: 1xoBRdLtA9H4zKe0NRD4OJ

######################################################################################################################## {} ########################################################################################################################
Traceback (most recent call last): File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\track.py", line 293, in download_track stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY) File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 628, in get_content_stream raise e File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 620, in get_content_stream return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None) ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio__init__.py", line 740, in load return self.load_track(playable_id, audio_quality_picker, preload, ~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ halt_listener) ^^^^^^^^^^^^^^ File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio__init__.py", line 792, in load_track raise RuntimeError("Cannot get alternative track") RuntimeError: Cannot get alternative track

That is because the solution so wonderfully implemented by @Masterolic, @Googolplexed0 and @sausa28 resolves the streaming aspect of the API change. You are attempting to use a downloading tool which pulls a file from the API which is not included in the scope of the patch.

ok this makes sense, thanks for clarifying and also thanks to all of the contributors for their hard work getting this patch complete, however the downloading is quite important, anyone working on a patch for that yet?

@Googolplexed0 are track downloads working on your zotify fork by any chance?

<!-- gh-comment-id:3510674570 --> @IsaacAgulhas commented on GitHub (Nov 10, 2025): > > > > > Thank you [@Masterolic](https://github.com/Masterolic) for fixing this. I primarily use librespot for podcasts. Curious if you might be interested in looking at get_metadata_4_show and get_metadata_4_episode as well? Thank you. > > > > > > > > > > > > Kindly please checkout now seems it should work now > > > > > > > > > Thank you for doing this. Seems your / Googolplexed0's work both work. Thank you both!! > > > > > > why are yuo saying thank you ? IT's not fixed, im still getting this > > PS C:\Users\Tony> zotify https://open.spotify.com/track/1xoBRdLtA9H4zKe0NRD4OJ?si=51a2d3f870054036 > > ``` > > [∙∙∙] Logging in... [∙∙∙] Fetching track information... [●∙∙] Preparing download... > > ``` > > > > > > > > > > > > > > > > > > > > > > > > ### ERROR: SKIPPING SONG - GENERAL DOWNLOAD ERROR > > ### Track_Label: Alexander Abreu - Silencio - Remix - Track_ID: 1xoBRdLtA9H4zKe0NRD4OJ > > ######################################################################################################################## {} ######################################################################################################################## > > Traceback (most recent call last): File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\track.py", line 293, in download_track stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY) File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 628, in get_content_stream raise e File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\zotify\config.py", line 620, in get_content_stream return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None) ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio__init__.py", line 740, in load return self.load_track(playable_id, audio_quality_picker, preload, ~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ halt_listener) ^^^^^^^^^^^^^^ File "C:\Users\Tony\pipx\venvs\zotify\Lib\site-packages\librespot\audio__init__.py", line 792, in load_track raise RuntimeError("Cannot get alternative track") RuntimeError: Cannot get alternative track > > That is because the solution so wonderfully implemented by [@Masterolic](https://github.com/Masterolic), [@Googolplexed0](https://github.com/Googolplexed0) and [@sausa28](https://github.com/sausa28) resolves the **streaming** aspect of the API change. You are attempting to use a **downloading** tool which pulls a _file_ from the API which is not included in the scope of the patch. ok this makes sense, thanks for clarifying and also thanks to all of the contributors for their hard work getting this patch complete, however the downloading is quite important, anyone working on a patch for that yet? @Googolplexed0 are track downloads working on your zotify fork by any chance?
Author
Owner

@Masterolic commented on GitHub (Nov 10, 2025):

Thank you @Masterolic for fixing this. I
That is because the solution so wonderfully implemented by @Masterolic, @Googolplexed0 and @sausa28 resolves the streaming aspect of the API change. You are attempting to use a downloading tool which pulls a file from the API which is not included in the scope of the patch.

No we had fixed it i think he is still using the req files of the tool instead changing to a fork or installing manually

Checkout the attachment image

Image

<!-- gh-comment-id:3512462907 --> @Masterolic commented on GitHub (Nov 10, 2025): > > > > > Thank you [@Masterolic](https://github.com/Masterolic) for fixing this. I > That is because the solution so wonderfully implemented by [@Masterolic](https://github.com/Masterolic), [@Googolplexed0](https://github.com/Googolplexed0) and [@sausa28](https://github.com/sausa28) resolves the **streaming** aspect of the API change. You are attempting to use a **downloading** tool which pulls a _file_ from the API which is not included in the scope of the patch. No we had fixed it i think he is still using the req files of the tool instead changing to a fork or installing manually Checkout the attachment image ![Image](https://github.com/user-attachments/assets/420505b7-d002-479a-b33c-df2f9ff77c90)
Author
Owner

@Masterolic commented on GitHub (Nov 10, 2025):

@Googolplexed0 are track downloads working on your zotify fork by any chance?

Checkout this hope you was referring this

<!-- gh-comment-id:3512473498 --> @Masterolic commented on GitHub (Nov 10, 2025): > [@Googolplexed0](https://github.com/Googolplexed0) are track downloads working on your zotify fork by any chance? [Checkout this ](https://github.com/kokarare1212/librespot-python/issues/321#issuecomment-3512462907) hope you was referring this
Author
Owner

@IsaacAgulhas commented on GitHub (Nov 10, 2025):

@Googolplexed0 are track downloads working on your zotify fork by any chance?

Checkout this hope you was referring this

I'm still using the main zotify repo as both yours and @Googolplexed0 does not want the save credentials.json and it asks me to login using the link, but after I do that it gives a page not found for a local host ip address and I never get past that point
Also, the credentials json file is rather tricky to generate (as you need to run the actual rust code files and that is a mission) but once you do then you have a fully valid stored credentials that you can use forever, so I don't know why both you guys dropped support for that in your forks

<!-- gh-comment-id:3512634601 --> @IsaacAgulhas commented on GitHub (Nov 10, 2025): > > [@Googolplexed0](https://github.com/Googolplexed0) are track downloads working on your zotify fork by any chance? > > [Checkout this ](https://github.com/kokarare1212/librespot-python/issues/321#issuecomment-3512462907) hope you was referring this I'm still using the main zotify repo as both yours and @Googolplexed0 does not want the save credentials.json and it asks me to login using the link, but after I do that it gives a page not found for a local host ip address and I never get past that point Also, the credentials json file is rather tricky to generate (as you need to run the actual rust code files and that is a mission) but once you do then you have a fully valid stored credentials that you can use forever, so I don't know why both you guys dropped support for that in your forks
Author
Owner

@Mariano228 commented on GitHub (Nov 10, 2025):

I have also tried uninstalling @Googolplexed0 and installing @DraftKinner's

when I do that , I get this

Thank you @Masterolic for fixing this. I
That is because the solution so wonderfully implemented by @Masterolic, @Googolplexed0 and @sausa28 resolves the streaming aspect of the API change. You are attempting to use a downloading tool which pulls a file from the API which is not included in the scope of the patch.

No we had fixed it i think he is still using the req files of the tool instead changing to a fork or installing manually

Checkout the attachment image

This is what i get when i install it from scratch @Googolplexed0 fork

PS C:\Users\Tony> python -m pip install git+https://github.com/Googolplexed0/zotify.git
Collecting git+https://github.com/Googolplexed0/zotify.git
Cloning https://github.com/Googolplexed0/zotify.git to c:\users\tony\appdata\local\temp\pip-req-build-aa_tbsnf
Running command git clone --filter=blob:none --quiet https://github.com/Googolplexed0/zotify.git 'C:\Users\Tony\AppData\Local\Temp\pip-req-build-aa_tbsnf'
Resolved https://github.com/Googolplexed0/zotify.git to commit af513c53d965ce61bc81a65fadb700f77dd9f84f
Installing build dependencies ... done
Getting requirements to build wheel ... done
Preparing metadata (pyproject.toml) ... done
Collecting librespot@ git+https://github.com/kokarare1212/librespot-python.git (from zotify==0.9.31)
Cloning https://github.com/kokarare1212/librespot-python.git to c:\users\tony\appdata\local\temp\pip-install-v0whtiqj\librespot_df5fa0a1fd6e46bf844fb24dd13b79ac
Running command git clone --filter=blob:none --quiet https://github.com/kokarare1212/librespot-python.git 'C:\Users\Tony\AppData\Local\Temp\pip-install-v0whtiqj\librespot_df5fa0a1fd6e46bf844fb24dd13b79ac'
Resolved https://github.com/kokarare1212/librespot-python.git to commit github.com/kokarare1212/librespot-python@8760279c64
Installing build dependencies ... done
Getting requirements to build wheel ... done
Preparing metadata (pyproject.toml) ... done
Requirement already satisfied: ffmpy in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (0.6.4)
Requirement already satisfied: music_tag in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (0.4.7)
Requirement already satisfied: Pillow in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (11.2.1)
Requirement already satisfied: pkce in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (1.0.3)
Requirement already satisfied: protobuf==3.20.1 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (3.20.1)
Requirement already satisfied: pwinput in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (1.0.3)
Requirement already satisfied: tabulate[widechars] in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (0.9.0)
Requirement already satisfied: tqdm in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (4.67.1)
Requirement already satisfied: defusedxml>=0.7.1 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (0.7.1)
Requirement already satisfied: pycryptodomex>=3.22.0 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (3.23.0)
Requirement already satisfied: pyogg>=0.6.14a.1 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (0.6.14a1)
Requirement already satisfied: requests>=2.32.3 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (2.32.5)
Requirement already satisfied: websocket-client>=1.8.0 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (1.9.0)
Requirement already satisfied: zeroconf>=0.146.4 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (0.148.0)
Requirement already satisfied: charset_normalizer<4,>=2 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from requests>=2.32.3->librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (3.4.4)
Requirement already satisfied: idna<4,>=2.5 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from requests>=2.32.3->librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (3.11)
Requirement already satisfied: urllib3<3,>=1.21.1 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from requests>=2.32.3->librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (2.5.0)
Requirement already satisfied: certifi>=2017.4.17 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from requests>=2.32.3->librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (2025.10.5)
Requirement already satisfied: ifaddr>=0.1.7 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zeroconf>=0.146.4->librespot@ git+https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31) (0.2.0)
Requirement already satisfied: mutagen in c:\users\tony\scoop\apps\python\current\lib\site-packages (from music_tag->zotify==0.9.31) (1.47.0)
Requirement already satisfied: wcwidth in c:\users\tony\scoop\apps\python\current\lib\site-packages (from tabulate[widechars]->zotify==0.9.31) (0.2.14)
Requirement already satisfied: colorama in c:\users\tony\appdata\roaming\python\python313\site-packages (from tqdm->zotify==0.9.31) (0.4.6)
Building wheels for collected packages: zotify, librespot
Building wheel for zotify (pyproject.toml) ... done
Created wheel for zotify: filename=zotify-0.9.31-py3-none-any.whl size=47330 sha256=30317f
Stored in directory: C:\Users\Tony\AppData\Local\Temp\pip-ephem-wheel-cache-cqm4k4yi\wheels\77\91\8c\ac76b6a3090b
Building wheel for librespot (pyproject.toml) ... done
Created wheel for librespot: filename=librespot-0.0.9-py3-none-any.whl size=133276 sha256=90d2b6631fab
Stored in directory: C:\Users\Tony\AppData\Local\Temp\pip-ephem-wheel-cache-cqm4k4yi\wheels\dc\d5\ed\915a5bc88883
Successfully built zotify librespot
Installing collected packages: librespot, zotify
Successfully installed librespot-0.0.9 zotify-0.9.31
PS C:\Users\Tony> zotify https://open.spotify.com/track/3AhXZa8sUQht0UEdBJgpGc

[∙∙∙] Logging in...                                                                                                     [●∙∙] Fetching track information...                                                                                     [●∙∙] Preparing download...                                                                                     

ERROR: SKIPPING SONG - GENERAL DOWNLOAD ERROR
Track_Label: Bob Dylan - Like a Rolling Stone - Track_ID: 3AhXZa8sUQht0UEdBJgpGc
########################################################################################################################
{}
########################################################################################################################

Traceback (most recent call last):
File "C:\Users\Tony\scoop\apps\python\current\Lib\site-packages\zotify\track.py", line 293, in download_track
stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY)
File "C:\Users\Tony\scoop\apps\python\current\Lib\site-packages\zotify\config.py", line 628, in get_content_stream
raise e
File "C:\Users\Tony\scoop\apps\python\current\Lib\site-packages\zotify\config.py", line 620, in get_content_stream
return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None)

File "C:\Users\Tony\scoop\apps\python\current\Lib\site-packages\librespot\audio_init_.py", line 740, in load
return self.load_track(playable_id, audio_quality_picker, preload, halt_listener)

File "C:\Users\Tony\scoop\apps\python\current\Lib\site-packages\librespot\audio_init_.py", line 792, in load_track
raise RuntimeError("Cannot get alternative track")
RuntimeError: Cannot get alternative track

If I try to remove the credentials.json then this is what I get when I try downloading a track

Click on the following link to login:
https://accounts.spotify.com/authorize?response_type=code&client_id=6[etc]&redirect_uri=http://127.0.0.1:4381/login&code_challenge=g[etc]&code_challenge_method=S256&scope=app-remote-control+playlist-modify+playlist-modify-private+playlist-modify-public+playlist-read+playlist-read-collaborative+playlist-read-private+streaming+ugc-image-upload+user-follow-modify+user-follow-read+user-library-modify+user-library-read+user-modify+user-modify-playback-state+user-modify-private+user-personalized+user-read-birthdate+user-read-currently-playing+user-read-email+user-read-play-history+user-read-playback-position+user-read-playback-state+user-read-private+user-read-recently-played+user-top-read

<!-- gh-comment-id:3514257896 --> @Mariano228 commented on GitHub (Nov 10, 2025): I have also tried uninstalling @Googolplexed0 and installing @DraftKinner's when I do that , I get this > > > > > > Thank you [@Masterolic](https://github.com/Masterolic) for fixing this. I > > > > > > That is because the solution so wonderfully implemented by [@Masterolic](https://github.com/Masterolic), [@Googolplexed0](https://github.com/Googolplexed0) and [@sausa28](https://github.com/sausa28) resolves the **streaming** aspect of the API change. You are attempting to use a **downloading** tool which pulls a _file_ from the API which is not included in the scope of the patch. > > No we had fixed it i think he is still using the req files of the tool instead changing to a fork or installing manually > > Checkout the attachment image > This is what i get when i install it from scratch @Googolplexed0 fork PS C:\Users\Tony> python -m pip install git+https://github.com/Googolplexed0/zotify.git Collecting git+https://github.com/Googolplexed0/zotify.git Cloning https://github.com/Googolplexed0/zotify.git to c:\users\tony\appdata\local\temp\pip-req-build-aa_tbsnf Running command git clone --filter=blob:none --quiet https://github.com/Googolplexed0/zotify.git 'C:\Users\Tony\AppData\Local\Temp\pip-req-build-aa_tbsnf' Resolved https://github.com/Googolplexed0/zotify.git to commit af513c53d965ce61bc81a65fadb700f77dd9f84f Installing build dependencies ... done Getting requirements to build wheel ... done Preparing metadata (pyproject.toml) ... done Collecting librespot@ git+https://github.com/kokarare1212/librespot-python.git (from zotify==0.9.31) Cloning https://github.com/kokarare1212/librespot-python.git to c:\users\tony\appdata\local\temp\pip-install-v0whtiqj\librespot_df5fa0a1fd6e46bf844fb24dd13b79ac Running command git clone --filter=blob:none --quiet https://github.com/kokarare1212/librespot-python.git 'C:\Users\Tony\AppData\Local\Temp\pip-install-v0whtiqj\librespot_df5fa0a1fd6e46bf844fb24dd13b79ac' Resolved https://github.com/kokarare1212/librespot-python.git to commit https://github.com/kokarare1212/librespot-python/commit/8760279c64230607d418d72b028e8f9b8ba7525e Installing build dependencies ... done Getting requirements to build wheel ... done Preparing metadata (pyproject.toml) ... done Requirement already satisfied: ffmpy in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (0.6.4) Requirement already satisfied: music_tag in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (0.4.7) Requirement already satisfied: Pillow in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (11.2.1) Requirement already satisfied: pkce in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (1.0.3) Requirement already satisfied: protobuf==3.20.1 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (3.20.1) Requirement already satisfied: pwinput in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (1.0.3) Requirement already satisfied: tabulate[widechars] in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (0.9.0) Requirement already satisfied: tqdm in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zotify==0.9.31) (4.67.1) Requirement already satisfied: defusedxml>=0.7.1 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (0.7.1) Requirement already satisfied: pycryptodomex>=3.22.0 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (3.23.0) Requirement already satisfied: pyogg>=0.6.14a.1 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (0.6.14a1) Requirement already satisfied: requests>=2.32.3 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (2.32.5) Requirement already satisfied: websocket-client>=1.8.0 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (1.9.0) Requirement already satisfied: zeroconf>=0.146.4 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (0.148.0) Requirement already satisfied: charset_normalizer<4,>=2 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from requests>=2.32.3->librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (3.4.4) Requirement already satisfied: idna<4,>=2.5 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from requests>=2.32.3->librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (3.11) Requirement already satisfied: urllib3<3,>=1.21.1 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from requests>=2.32.3->librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (2.5.0) Requirement already satisfied: certifi>=2017.4.17 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from requests>=2.32.3->librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (2025.10.5) Requirement already satisfied: ifaddr>=0.1.7 in c:\users\tony\scoop\apps\python\current\lib\site-packages (from zeroconf>=0.146.4->librespot@ git+[https://github.com/kokarare1212/librespot-python.git->zotify==0.9.31](https://github.com/kokarare1212/librespot-python.git-%3Ezotify==0.9.31)) (0.2.0) Requirement already satisfied: mutagen in c:\users\tony\scoop\apps\python\current\lib\site-packages (from music_tag->zotify==0.9.31) (1.47.0) Requirement already satisfied: wcwidth in c:\users\tony\scoop\apps\python\current\lib\site-packages (from tabulate[widechars]->zotify==0.9.31) (0.2.14) Requirement already satisfied: colorama in c:\users\tony\appdata\roaming\python\python313\site-packages (from tqdm->zotify==0.9.31) (0.4.6) Building wheels for collected packages: zotify, librespot Building wheel for zotify (pyproject.toml) ... done Created wheel for zotify: filename=zotify-0.9.31-py3-none-any.whl size=47330 sha256=30317f Stored in directory: C:\Users\Tony\AppData\Local\Temp\pip-ephem-wheel-cache-cqm4k4yi\wheels\77\91\8c\ac76b6a3090b Building wheel for librespot (pyproject.toml) ... done Created wheel for librespot: filename=librespot-0.0.9-py3-none-any.whl size=133276 sha256=90d2b6631fab Stored in directory: C:\Users\Tony\AppData\Local\Temp\pip-ephem-wheel-cache-cqm4k4yi\wheels\dc\d5\ed\915a5bc88883 Successfully built zotify librespot Installing collected packages: librespot, zotify Successfully installed librespot-0.0.9 zotify-0.9.31 PS C:\Users\Tony> zotify https://open.spotify.com/track/3AhXZa8sUQht0UEdBJgpGc [∙∙∙] Logging in... [●∙∙] Fetching track information... [●∙∙] Preparing download... ERROR: SKIPPING SONG - GENERAL DOWNLOAD ERROR Track_Label: Bob Dylan - Like a Rolling Stone - Track_ID: 3AhXZa8sUQht0UEdBJgpGc ######################################################################################################################## {} ######################################################################################################################## Traceback (most recent call last): File "C:\Users\Tony\scoop\apps\python\current\Lib\site-packages\zotify\track.py", line 293, in download_track stream = Zotify.get_content_stream(track, Zotify.DOWNLOAD_QUALITY) File "C:\Users\Tony\scoop\apps\python\current\Lib\site-packages\zotify\config.py", line 628, in get_content_stream raise e File "C:\Users\Tony\scoop\apps\python\current\Lib\site-packages\zotify\config.py", line 620, in get_content_stream return cls.SESSION.content_feeder().load(content_id, VorbisOnlyAudioQuality(quality), False, None) File "C:\Users\Tony\scoop\apps\python\current\Lib\site-packages\librespot\audio_init_.py", line 740, in load return self.load_track(playable_id, audio_quality_picker, preload, halt_listener) File "C:\Users\Tony\scoop\apps\python\current\Lib\site-packages\librespot\audio_init_.py", line 792, in load_track raise RuntimeError("Cannot get alternative track") RuntimeError: Cannot get alternative track If I try to remove the credentials.json then this is what I get when I try downloading a track Click on the following link to login: [https://accounts.spotify.com/authorize?response_type=code&client_id=6[etc]&redirect_uri=http://127.0.0.1:4381/login&code_challenge=g[etc]&code_challenge_method=S256&scope=app-remote-control+playlist-modify+playlist-modify-private+playlist-modify-public+playlist-read+playlist-read-collaborative+playlist-read-private+streaming+ugc-image-upload+user-follow-modify+user-follow-read+user-library-modify+user-library-read+user-modify+user-modify-playback-state+user-modify-private+user-personalized+user-read-birthdate+user-read-currently-playing+user-read-email+user-read-play-history+user-read-playback-position+user-read-playback-state+user-read-private+user-read-recently-played+user-top-read](https://accounts.spotify.com/authorize?response_type=code&client_id=6%5Betc%5D&redirect_uri=http://127.0.0.1:4381/login&code_challenge=g%5Betc%5D&code_challenge_method=S256&scope=app-remote-control+playlist-modify+playlist-modify-private+playlist-modify-public+playlist-read+playlist-read-collaborative+playlist-read-private+streaming+ugc-image-upload+user-follow-modify+user-follow-read+user-library-modify+user-library-read+user-modify+user-modify-playback-state+user-modify-private+user-personalized+user-read-birthdate+user-read-currently-playing+user-read-email+user-read-play-history+user-read-playback-position+user-read-playback-state+user-read-private+user-read-recently-played+user-top-read)
Author
Owner

@fafamobile commented on GitHub (Nov 11, 2025):

@Googolplexed0 are track downloads working on your zotify fork by any chance?

Checkout this hope you was referring this

i force updated Googolplxed0's fork for zotify, and same with this, and still getting same "cannot get alternative track" error

edit: here is debug

DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): apresolve.spotify.com:443
DEBUG:urllib3.connectionpool:https://apresolve.spotify.com:443 "GET /?type=accesspoint HTTP/1.1" 200 None
INFO:Librespot:Session:Created new session! device_id: 29df7e55860566cd75d5028b90be9e0d3faf36b8, ap: ap-gue1.spotify.com:443
INFO:Librespot:Session:Connection successfully!
INFO:Librespot:Session:Session.Receiver started
DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): apresolve.spotify.com:443
DEBUG:urllib3.connectionpool:https://apresolve.spotify.com:443 "GET /?type=spclient HTTP/1.1" 200 None
INFO:Librespot:Session:Skipping 02
INFO:Librespot:Session:Received license_version: 0
INFO:Librespot:Session:Received country_code: NZ
DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): apresolve.spotify.com:443
DEBUG:Librespot:Session:Parsed product info: {'type': 'free', 'ab-ad-player-targeting': '1', 'ab-watch-now': '0', 'ab_recently_played_feature_time_filter_threshold': 'com.spotify.gaia=30,driving-mode=120,spotify%3Ainternal%3Astartpage=30', 'ad-formats-preroll-video': '0', 'ad-session-persistence': '1', 'ads': '1', 'app-developer': '0', 'arsenal_country': '1', 'audio-preview-url-template': 'https://p.scdn.co/mp3-preview/{id}', 'audio-quality': '0', 'audiobook-onboarding-completed': '0', 'autoplay': '1', 'browse-overview-enabled': '1', 'capping-bar-threshold': '3601', 'catalogue': 'free', 'client-deprecated': '1', 'collection': '1', 'created_by_partner': None, 'employee-free-opt-in': '0', 'enable-annotations': '2', 'enable-annotations-read': '0', 'enable-crossfade': '1', 'explicit-content': '1', 'financial-product': 'pr:free,tc:0', 'head-file-caching': '1', 'head-files': '1', 'head-files-url': 'https://heads-fa-tls13.spotifycdn.com/head/{file_id}', 'high-bitrate': '0', 'image-url': 'https://i.scdn.co/image/{file_id}', 'incognito_mode_timeout': '21600', 'is_email_verified': '1', 'key-caching-auto-offline': '0', 'key-caching-max-count': '10000', 'key-caching-max-offline-seconds': '1800', 'key-memory-cache-mode': '1:15,300', 'libspotify': '0', 'license-acceptance-grace-days': '0', 'license-agreements': None, 'metadata-link-lookup-modes': '0', 'mobile': '0', 'mobile-payment': '0', 'name': 'Spotify Free', 'network-operator-premium-activation': '1', 'nft-disabled': '1', 'offline': '0', 'on-demand': '1', 'on-demand-trial-in-progress': '0', 'payments-locked-state': '0', 'player-license': 'on-demand', 'player-license-v2': 'on-demand', 'playlist-annotations-markup': '0', 'preferred-locale': 'en', 'prefetch-keys': '1', 'prefetch-strategy': '18', 'prefetch-window-max': '2', 'product-expiry': None, 'publish-activity': '0', 'publish-playlist': '1', 'radio': '1', 'rating-access': '1', 'remote-control': '6', 'restrict-playlist-collaboration': '0', 'send-email': '1', 'shows-collection': '1', 'shows-collection-jam': '0', 'shuffle': '0', 'shuffle-algorithm': 'FRESH', 'sidebar-navigation-enabled': '0', 'storage-size-config': '10240,90,500,3', 'streaming': '1', 'streaming-rules': None, 'subscription-enddate': None, 'ugc-abuse-report': '1', 'ugc-abuse-report-url': 'https://support.spotify.com/abuse/?uri={uri}', 'user-profile-show-invitation-codes': '0', 'video-cdn-sampling': '100', 'video-device-blacklisted': '0', 'video-keyframe-url': 'http://keyframes-fa.cdn.spotify.com/keyframes/v1/sources/{source_id}/keyframe/heights/{height}/timestamps/{timestamp_ms}.jpg', 'video-manifest-url': 'https://spclient.wg.spotify.com/manifests/v6/{type}/sources/{source_id}/options/supports_drm', 'widevine-license-url': 'https://spclient.wg.spotify.com/widevine-license/v1/video/license'}
INFO:Librespot:Session:Skipping 1f
INFO:Librespot:Session:Skipping 69
DEBUG:Librespot:MercuryClient:Handling packet, cmd: 0xb5, seq: -3379158768162963456, flags: b'\x01', parts: 1
DEBUG:Librespot:MercuryClient:Couldn't dispatch Mercury event seq: -3379158768162963456, uri: hm://pusher/v1/connections/MjlkZjdlNTU4NjA1NjZjZDc1ZDUwMjhiOTBiZTllMGQzZmFmMzZiOCtBUCt0Y3A6Ly8wYWIxNDA2Ny5pcC5ndWUxLnNwb3RpZnkubmV0OjUwMDkrOTYxMDE1MDc0M0RDOUVBRTdCQzNBMDUxREE0NUUyMzIzMTNENjNFNzhDQTU3RkRBMkE0QTVEQ0FBMzNBRDY5NQ%3D%3D, code: 200, payload: b''
DEBUG:Librespot:Session:Received 0x10: 44aa94cab8077c35eec759aee9675257d5e74091
DEBUG:urllib3.connectionpool:https://apresolve.spotify.com:443 "GET /?type=dealer HTTP/1.1" 200 None
DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): login5.spotify.com:443
INFO:Librespot:Session:Skipping unknown command cmd: 0x75, payload: b'\x00\x00\x01'
DEBUG:urllib3.connectionpool:https://login5.spotify.com:443 "POST /v3/login HTTP/1.1" 200 None
INFO:Librespot:TokenProvider:Login5 authentication successful, got access token
DEBUG:Librespot:TokenProvider:Using Login5 access token for scopes: ['playlist-read']
INFO:Librespot:Session:Authenticated as 31iwba233jptfr6bhwur2c4t45my!
DEBUG:zotify.debug:

Session Initialized Successfully

DEBUG:zotify.debug:Starting Download of 1 URLs

DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): login5.spotify.com:443
DEBUG:urllib3.connectionpool:https://login5.spotify.com:443 "POST /v3/login HTTP/1.1" 200 None
INFO:Librespot:TokenProvider:Login5 authentication successful, got access token
DEBUG:Librespot:TokenProvider:Using Login5 access token for scopes: ['user-read-email', 'playlist-read-private', 'user-library-read', 'user-follow-read']
DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): api.spotify.com:443
DEBUG:urllib3.connectionpool:https://api.spotify.com:443 "GET /v1/tracks?ids=41uNTPBOMkEnAcZuBWlNL9&market=from_token HTTP/1.1" 200 None
DEBUG:zotify.debug:

Duplicate Check
File Already Exists: False
song_id in Local Archive: False
song_id in Global Archive: False

DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): clienttoken.spotify.com:443
DEBUG:urllib3.connectionpool:https://clienttoken.spotify.com:443 "POST /v1/clienttoken HTTP/1.1" 200 None
DEBUG:Librespot:ApiClient:Updated client token: AAD32xtvv1K5LSoBYb3mna0aAjUv+J7rScQZl3iSCFIfuNT+nH1tjtNToMiHNH3B7pdPGZof+YgWGf+SHwWEQTvYrXarl0ZiaqdFBnheHtOASUYAU2VSYjdCqJC6Q11TwV5T0+hftzLWuhRvqz6bi0EQjpSwXGOpd59izJgC7TeKhUcg0RMhFDCuf3A4yG4hSVwaZ3PJlDpO88LA5Zwi+HLbml+ijJusxwd+ophkY+QC1ENLdaYQQG9MQFcf2O0ISEDscGiyIYI3Goo=
DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): spclient.wg.spotify.com:443
DEBUG:urllib3.connectionpool:https://spclient.wg.spotify.com:443 "GET /metadata/4/track/84387e61f41e4b7ca74a0073dcea7587 HTTP/1.1" 200 924
DEBUG:zotify.debug:

Total API Calls: 1

<!-- gh-comment-id:3514686552 --> @fafamobile commented on GitHub (Nov 11, 2025): > > [@Googolplexed0](https://github.com/Googolplexed0) are track downloads working on your zotify fork by any chance? > > [Checkout this ](https://github.com/kokarare1212/librespot-python/issues/321#issuecomment-3512462907) hope you was referring this i force updated Googolplxed0's fork for zotify, and same with this, and still getting same "cannot get alternative track" error edit: here is debug DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): apresolve.spotify.com:443 DEBUG:urllib3.connectionpool:https://apresolve.spotify.com:443 "GET /?type=accesspoint HTTP/1.1" 200 None INFO:Librespot:Session:Created new session! device_id: 29df7e55860566cd75d5028b90be9e0d3faf36b8, ap: ap-gue1.spotify.com:443 INFO:Librespot:Session:Connection successfully! INFO:Librespot:Session:Session.Receiver started DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): apresolve.spotify.com:443 DEBUG:urllib3.connectionpool:https://apresolve.spotify.com:443 "GET /?type=spclient HTTP/1.1" 200 None INFO:Librespot:Session:Skipping 02 INFO:Librespot:Session:Received license_version: 0 INFO:Librespot:Session:Received country_code: NZ DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): apresolve.spotify.com:443 DEBUG:Librespot:Session:Parsed product info: {'type': 'free', 'ab-ad-player-targeting': '1', 'ab-watch-now': '0', 'ab_recently_played_feature_time_filter_threshold': 'com.spotify.gaia=30,driving-mode=120,spotify%3Ainternal%3Astartpage=30', 'ad-formats-preroll-video': '0', 'ad-session-persistence': '1', 'ads': '1', 'app-developer': '0', 'arsenal_country': '1', 'audio-preview-url-template': 'https://p.scdn.co/mp3-preview/{id}', 'audio-quality': '0', 'audiobook-onboarding-completed': '0', 'autoplay': '1', 'browse-overview-enabled': '1', 'capping-bar-threshold': '3601', 'catalogue': 'free', 'client-deprecated': '1', 'collection': '1', 'created_by_partner': None, 'employee-free-opt-in': '0', 'enable-annotations': '2', 'enable-annotations-read': '0', 'enable-crossfade': '1', 'explicit-content': '1', 'financial-product': 'pr:free,tc:0', 'head-file-caching': '1', 'head-files': '1', 'head-files-url': 'https://heads-fa-tls13.spotifycdn.com/head/{file_id}', 'high-bitrate': '0', 'image-url': 'https://i.scdn.co/image/{file_id}', 'incognito_mode_timeout': '21600', 'is_email_verified': '1', 'key-caching-auto-offline': '0', 'key-caching-max-count': '10000', 'key-caching-max-offline-seconds': '1800', 'key-memory-cache-mode': '1:15,300', 'libspotify': '0', 'license-acceptance-grace-days': '0', 'license-agreements': None, 'metadata-link-lookup-modes': '0', 'mobile': '0', 'mobile-payment': '0', 'name': 'Spotify Free', 'network-operator-premium-activation': '1', 'nft-disabled': '1', 'offline': '0', 'on-demand': '1', 'on-demand-trial-in-progress': '0', 'payments-locked-state': '0', 'player-license': 'on-demand', 'player-license-v2': 'on-demand', 'playlist-annotations-markup': '0', 'preferred-locale': 'en', 'prefetch-keys': '1', 'prefetch-strategy': '18', 'prefetch-window-max': '2', 'product-expiry': None, 'publish-activity': '0', 'publish-playlist': '1', 'radio': '1', 'rating-access': '1', 'remote-control': '6', 'restrict-playlist-collaboration': '0', 'send-email': '1', 'shows-collection': '1', 'shows-collection-jam': '0', 'shuffle': '0', 'shuffle-algorithm': 'FRESH', 'sidebar-navigation-enabled': '0', 'storage-size-config': '10240,90,500,3', 'streaming': '1', 'streaming-rules': None, 'subscription-enddate': None, 'ugc-abuse-report': '1', 'ugc-abuse-report-url': 'https://support.spotify.com/abuse/?uri={uri}', 'user-profile-show-invitation-codes': '0', 'video-cdn-sampling': '100', 'video-device-blacklisted': '0', 'video-keyframe-url': 'http://keyframes-fa.cdn.spotify.com/keyframes/v1/sources/{source_id}/keyframe/heights/{height}/timestamps/{timestamp_ms}.jpg', 'video-manifest-url': 'https://spclient.wg.spotify.com/manifests/v6/{type}/sources/{source_id}/options/supports_drm', 'widevine-license-url': 'https://spclient.wg.spotify.com/widevine-license/v1/video/license'} INFO:Librespot:Session:Skipping 1f INFO:Librespot:Session:Skipping 69 DEBUG:Librespot:MercuryClient:Handling packet, cmd: 0xb5, seq: -3379158768162963456, flags: b'\x01', parts: 1 DEBUG:Librespot:MercuryClient:Couldn't dispatch Mercury event seq: -3379158768162963456, uri: hm://pusher/v1/connections/MjlkZjdlNTU4NjA1NjZjZDc1ZDUwMjhiOTBiZTllMGQzZmFmMzZiOCtBUCt0Y3A6Ly8wYWIxNDA2Ny5pcC5ndWUxLnNwb3RpZnkubmV0OjUwMDkrOTYxMDE1MDc0M0RDOUVBRTdCQzNBMDUxREE0NUUyMzIzMTNENjNFNzhDQTU3RkRBMkE0QTVEQ0FBMzNBRDY5NQ%3D%3D, code: 200, payload: b'' DEBUG:Librespot:Session:Received 0x10: 44aa94cab8077c35eec759aee9675257d5e74091 DEBUG:urllib3.connectionpool:https://apresolve.spotify.com:443 "GET /?type=dealer HTTP/1.1" 200 None DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): login5.spotify.com:443 INFO:Librespot:Session:Skipping unknown command cmd: 0x75, payload: b'\x00\x00\x01' DEBUG:urllib3.connectionpool:https://login5.spotify.com:443 "POST /v3/login HTTP/1.1" 200 None INFO:Librespot:TokenProvider:Login5 authentication successful, got access token DEBUG:Librespot:TokenProvider:Using Login5 access token for scopes: ['playlist-read'] INFO:Librespot:Session:Authenticated as 31iwba233jptfr6bhwur2c4t45my! DEBUG:zotify.debug: Session Initialized Successfully DEBUG:zotify.debug:Starting Download of 1 URLs DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): login5.spotify.com:443 DEBUG:urllib3.connectionpool:https://login5.spotify.com:443 "POST /v3/login HTTP/1.1" 200 None INFO:Librespot:TokenProvider:Login5 authentication successful, got access token DEBUG:Librespot:TokenProvider:Using Login5 access token for scopes: ['user-read-email', 'playlist-read-private', 'user-library-read', 'user-follow-read'] DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): api.spotify.com:443 DEBUG:urllib3.connectionpool:https://api.spotify.com:443 "GET /v1/tracks?ids=41uNTPBOMkEnAcZuBWlNL9&market=from_token HTTP/1.1" 200 None DEBUG:zotify.debug: Duplicate Check File Already Exists: False song_id in Local Archive: False song_id in Global Archive: False DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): clienttoken.spotify.com:443 DEBUG:urllib3.connectionpool:https://clienttoken.spotify.com:443 "POST /v1/clienttoken HTTP/1.1" 200 None DEBUG:Librespot:ApiClient:Updated client token: AAD32xtvv1K5LSoBYb3mna0aAjUv+J7rScQZl3iSCFIfuNT+nH1tjtNToMiHNH3B7pdPGZof+YgWGf+SHwWEQTvYrXarl0ZiaqdFBnheHtOASUYAU2VSYjdCqJC6Q11TwV5T0+hftzLWuhRvqz6bi0EQjpSwXGOpd59izJgC7TeKhUcg0RMhFDCuf3A4yG4hSVwaZ3PJlDpO88LA5Zwi+HLbml+ijJusxwd+ophkY+QC1ENLdaYQQG9MQFcf2O0ISEDscGiyIYI3Goo= DEBUG:urllib3.connectionpool:Starting new HTTPS connection (1): spclient.wg.spotify.com:443 DEBUG:urllib3.connectionpool:https://spclient.wg.spotify.com:443 "GET /metadata/4/track/84387e61f41e4b7ca74a0073dcea7587 HTTP/1.1" 200 924 DEBUG:zotify.debug: Total API Calls: 1
Author
Owner

@Googolplexed0 commented on GitHub (Nov 11, 2025):

@Googolplexed0 are track downloads working on your zotify fork by any chance?

Yes. The issue mentioned in my commit was due to my credentials.json being invalid. The changes to the API that necessitated the fix probably also expired old creds. If you are also experiencing ### FAILED TO FETCH AUDIO KEY ### issues with a premium account, refreshing credentials may help.

I will push the fix to my fork and create a pull request after a quick, final round of testing.

@Scrameupeutchi, once you see my pull request be accepted, this issue can be closed.

<!-- gh-comment-id:3514719367 --> @Googolplexed0 commented on GitHub (Nov 11, 2025): > [@Googolplexed0](https://github.com/Googolplexed0) are track downloads working on your zotify fork by any chance? Yes. The [issue mentioned in my commit](https://github.com/Googolplexed0/librespot-python/commit/5882f28213adaa113a07d68cf307a2ffd2464708#:~:text=unfortunately%2C%20now%20AudioKeyManager.get_audio_key()%20no%20longer%20works) was due to my `credentials.json` being invalid. The changes to the API that necessitated the fix probably also expired old creds. If you are also experiencing `### FAILED TO FETCH AUDIO KEY ###` issues with a premium account, refreshing credentials may help. I will push the fix to my fork and create a pull request after a quick, final round of testing. @Scrameupeutchi, once you see my pull request be accepted, this issue can be closed.
Author
Owner

@Masterolic commented on GitHub (Nov 11, 2025):

I'm still using the main zotify repo as both yours and @Googolplexed0 does not want the save credentials.json and it asks me to login using the link, but after I do that it gives a page not .....

from librespot.zeroconf import ZeroconfServer
import time
import logging
import pathlib

zs = ZeroconfServer.Builder().create()
logging.warning("Transfer playback from desktop client to librespot-python via Spotify Connect in order to store session")

while True:
    time.sleep(1)
    if zs._ZeroconfServer__session:
        logging.warning(f"Grabbed {zs._ZeroconfServer__session} for {zs._ZeroconfServer__session.username()}")

        if pathlib.Path("credentials.json").exists():
            logging.warning("Session stored in credentials.json. Now you can Ctrl+C")
            break

I use this to generate session file rather than librespot one

<!-- gh-comment-id:3515372376 --> @Masterolic commented on GitHub (Nov 11, 2025): > I'm still using the main zotify repo as both yours and [@Googolplexed0](https://github.com/Googolplexed0) does not want the save credentials.json and it asks me to login using the link, but after I do that it gives a page not ..... ``` from librespot.zeroconf import ZeroconfServer import time import logging import pathlib zs = ZeroconfServer.Builder().create() logging.warning("Transfer playback from desktop client to librespot-python via Spotify Connect in order to store session") while True: time.sleep(1) if zs._ZeroconfServer__session: logging.warning(f"Grabbed {zs._ZeroconfServer__session} for {zs._ZeroconfServer__session.username()}") if pathlib.Path("credentials.json").exists(): logging.warning("Session stored in credentials.json. Now you can Ctrl+C") break ``` I use this to generate session file rather than librespot one
Author
Owner

@Mariano228 commented on GitHub (Nov 11, 2025):

@Googolplexed0 are track downloads working on your zotify fork by any chance?

Yes. The issue mentioned in my commit was due to my credentials.json being invalid. The changes to the API that necessitated the fix probably also expired old creds. If you are also experiencing ### FAILED TO FETCH AUDIO KEY ### issues with a premium account, refreshing credentials may help.

I will push the fix to my fork and create a pull request after a quick, final round of testing.

@Scrameupeutchi, once you see my pull request be accepted, this issue can be closed.

Could you pls tell me why you think I’m still getting the cannot get alternative track message ? I removed zotici , removed librespot , removed librespot-spotizerr, removed the credentials.json file .. Installed your fork .. but still get the cannot get alternative track message

<!-- gh-comment-id:3518521048 --> @Mariano228 commented on GitHub (Nov 11, 2025): > > [@Googolplexed0](https://github.com/Googolplexed0) are track downloads working on your zotify fork by any chance? > > Yes. The [issue mentioned in my commit](https://github.com/Googolplexed0/librespot-python/commit/5882f28213adaa113a07d68cf307a2ffd2464708#:~:text=unfortunately%2C%20now%20AudioKeyManager.get_audio_key()%20no%20longer%20works) was due to my `credentials.json` being invalid. The changes to the API that necessitated the fix probably also expired old creds. If you are also experiencing `### FAILED TO FETCH AUDIO KEY ###` issues with a premium account, refreshing credentials may help. > > I will push the fix to my fork and create a pull request after a quick, final round of testing. > > [@Scrameupeutchi](https://github.com/Scrameupeutchi), once you see my pull request be accepted, this issue can be closed. Could you pls tell me why you think I’m still getting the cannot get alternative track message ? I removed zotici , removed librespot , removed librespot-spotizerr, removed the credentials.json file .. Installed your fork .. but still get the cannot get alternative track message
Author
Owner

@imthekiller00 commented on GitHub (Nov 11, 2025):

Was it the efficient-api branch? It's working for me.

<!-- gh-comment-id:3518587519 --> @imthekiller00 commented on GitHub (Nov 11, 2025): Was it the efficient-api branch? It's working for me.
Author
Owner

@Scrameupeutchi commented on GitHub (Nov 12, 2025):

@Scrameupeutchi, once you see my pull request be accepted, this issue can be closed.

@Googolplexed0
Thank you very much, I can also confirm the work of everyone and especially you and your fork is doing wonders =3
I'll close the issue upon seeing acceptance of your pull request, in hope a maintainer will be doing so soon.

<!-- gh-comment-id:3523703401 --> @Scrameupeutchi commented on GitHub (Nov 12, 2025): > [@Scrameupeutchi](https://github.com/Scrameupeutchi), once you see my pull request be accepted, this issue can be closed. @Googolplexed0 Thank you very much, I can also confirm the work of everyone and especially you and your fork is doing wonders =3 I'll close the issue upon seeing acceptance of your pull request, in hope a maintainer will be doing so soon.
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
starred/librespot-python-kokarare1212#58
No description provided.