From 01dae8ada4408292d0218b6de7ec21cac4cbdbeb Mon Sep 17 00:00:00 2001 From: kokarare1212 Date: Wed, 24 Feb 2021 08:46:59 +0900 Subject: [PATCH] Initial Commit --- .gitignore | 16 +- LICENSE => LICENSE.txt | 2 +- README.md | 24 +- example/console.py | 98 + proto/authentication.proto | 168 + proto/canvaz-meta.proto | 14 + proto/canvaz.proto | 40 + proto/connect.proto | 173 + proto/context.proto | 18 + proto/context_page.proto | 16 + proto/context_player_options.proto | 18 + proto/context_track.proto | 13 + proto/explicit_content_pubsub.proto | 15 + proto/keyexchange.proto | 231 + proto/mercury.proto | 49 + proto/metadata.proto | 279 ++ proto/play_origin.proto | 16 + proto/playback.proto | 16 + proto/player.proto | 102 + proto/playlist4_external.proto | 229 + proto/playlist_annotate3.proto | 39 + proto/pubsub.proto | 11 + proto/queue.proto | 13 + proto/restrictions.proto | 30 + proto/session.proto | 17 + proto/spotify/login5/v3/challenges/code.proto | 19 + .../login5/v3/challenges/hashcash.proto | 16 + proto/spotify/login5/v3/client_info.proto | 9 + .../login5/v3/credentials/credentials.proto | 35 + .../login5/v3/identifiers/identifiers.proto | 10 + proto/spotify/login5/v3/login5.proto | 75 + proto/spotify/login5/v3/user_info.proto | 21 + proto/storage-resolve.proto | 18 + proto/transfer_state.proto | 19 + requirements.txt | 4 + setup.py | 19 + src/librespot/Version.py | 32 + src/librespot/__init__.py | 0 src/librespot/audio/AbsChunkedInputStream.py | 231 + src/librespot/audio/AudioKeyManager.py | 112 + src/librespot/audio/GeneralAudioStream.py | 20 + src/librespot/audio/GeneralWritableStream.py | 3 + src/librespot/audio/HaltListener.py | 6 + src/librespot/audio/NormalizationData.py | 50 + src/librespot/audio/PlayableContentFeeder.py | 141 + src/librespot/audio/StreamId.py | 30 + src/librespot/audio/__init__.py | 8 + src/librespot/audio/cdn/CdnFeedHelper.py | 85 + src/librespot/audio/cdn/CdnManager.py | 307 ++ src/librespot/audio/cdn/__init__.py | 2 + .../audio/decrypt/AesAudioDecrypt.py | 49 + src/librespot/audio/decrypt/AudioDecrypt.py | 6 + .../audio/decrypt/NoopAudioDecrypt.py | 9 + src/librespot/audio/decrypt/__init__.py | 3 + .../audio/format/AudioQualityPicker.py | 10 + .../audio/format/SuperAudioFormat.py | 27 + src/librespot/audio/format/__init__.py | 2 + src/librespot/audio/storage/AudioFile.py | 12 + .../audio/storage/AudioFileStreaming.py | 12 + src/librespot/audio/storage/ChannelManager.py | 146 + src/librespot/audio/storage/__init__.py | 3 + src/librespot/cache/CacheManager.py | 13 + src/librespot/cache/__init__.py | 1 + src/librespot/common/Base62.py | 88 + src/librespot/common/Utils.py | 31 + src/librespot/common/__init__.py | 2 + src/librespot/core/ApResolver.py | 33 + src/librespot/core/EventService.py | 103 + src/librespot/core/PacketsReceiver.py | 6 + src/librespot/core/SearchManager.py | 10 + src/librespot/core/Session.py | 1048 +++++ src/librespot/core/TimeProvider.py | 36 + src/librespot/core/TokenProvider.py | 84 + src/librespot/core/__init__.py | 7 + src/librespot/crypto/CipherPair.py | 62 + src/librespot/crypto/DiffieHellman.py | 38 + src/librespot/crypto/Packet.py | 66 + src/librespot/crypto/Shannon.py | 495 +++ src/librespot/crypto/Shannon_DEV.py | 311 ++ src/librespot/crypto/__init__.py | 4 + src/librespot/dealer/ApiClient.py | 129 + src/librespot/dealer/DealerClient.py | 19 + src/librespot/dealer/__init__.py | 2 + src/librespot/mercury/JsonMercuryRequest.py | 5 + src/librespot/mercury/MercuryClient.py | 256 ++ src/librespot/mercury/MercuryRequests.py | 18 + .../mercury/ProtobufMercuryRequest.py | 7 + src/librespot/mercury/RawMercuryRequest.py | 87 + src/librespot/mercury/SubListener.py | 7 + src/librespot/mercury/__init__.py | 6 + src/librespot/metadata/AlbumId.py | 40 + src/librespot/metadata/ArtistId.py | 43 + src/librespot/metadata/EpisodeId.py | 46 + src/librespot/metadata/PlayableId.py | 40 + src/librespot/metadata/ShowId.py | 42 + src/librespot/metadata/SpotifyId.py | 23 + src/librespot/metadata/TrackId.py | 42 + src/librespot/metadata/UnsupportedId.py | 17 + src/librespot/metadata/__init__.py | 8 + src/librespot/player/Player.py | 21 + src/librespot/player/PlayerConfiguration.py | 79 + src/librespot/player/StateWrapper.py | 13 + src/librespot/player/__init__.py | 3 + src/librespot/player/codecs/AudioQuality.py | 37 + .../player/codecs/VorbisOnlyAudioQuality.py | 42 + src/librespot/player/codecs/__init__.py | 2 + .../player/playback/PlayerSession.py | 6 + src/librespot/player/playback/__init__.py | 1 + src/librespot/proto/Authentication.py | 1984 +++++++++ src/librespot/proto/Connect.py | 2340 +++++++++++ src/librespot/proto/ExplicitContentPubsub.py | 147 + src/librespot/proto/Keyexchange.py | 2497 +++++++++++ src/librespot/proto/Mercury.py | 625 +++ src/librespot/proto/Metadata.py | 3698 +++++++++++++++++ src/librespot/proto/Pubsub.py | 112 + src/librespot/proto/StorageResolve.py | 154 + src/librespot/proto/__init__.py | 0 src/librespot/proto/canvaz_meta_pb2.py | 85 + src/librespot/proto/canvaz_pb2.py | 540 +++ src/librespot/proto/context_page_pb2.py | 229 + src/librespot/proto/context_pb2.py | 249 ++ .../proto/context_player_options_pb2.py | 206 + src/librespot/proto/context_track_pb2.py | 205 + src/librespot/proto/play_origin_pb2.py | 184 + src/librespot/proto/playback_pb2.py | 155 + src/librespot/proto/player_pb2.py | 1851 +++++++++ src/librespot/proto/playlist4_external_pb2.py | 3062 ++++++++++++++ src/librespot/proto/playlist_annotate3_pb2.py | 440 ++ src/librespot/proto/queue_pb2.py | 100 + src/librespot/proto/restrictions_pb2.py | 457 ++ src/librespot/proto/session_pb2.py | 143 + src/librespot/proto/spotify/__init__.py | 0 .../proto/spotify/login5/__init__.py | 0 .../proto/spotify/login5/v3/__init__.py | 0 .../spotify/login5/v3/challenges/__init__.py | 0 .../spotify/login5/v3/challenges/code_pb2.py | 214 + .../login5/v3/challenges/hashcash_pb2.py | 168 + .../spotify/login5/v3/client_info_pb2.py | 94 + .../spotify/login5/v3/credentials/__init__.py | 0 .../login5/v3/credentials/credentials_pb2.py | 463 +++ .../spotify/login5/v3/identifiers/__init__.py | 0 .../login5/v3/identifiers/identifiers_pb2.py | 114 + .../proto/spotify/login5/v3/login5_pb2.py | 910 ++++ .../proto/spotify/login5/v3/user_info_pb2.py | 249 ++ src/librespot/proto/transfer_state_pb2.py | 167 + src/librespot/standard/AutoCloseable.py | 3 + .../standard/ByteArrayOutputStream.py | 68 + src/librespot/standard/BytesInputStream.py | 42 + src/librespot/standard/BytesOutputStream.py | 24 + src/librespot/standard/Closeable.py | 6 + src/librespot/standard/DataInput.py | 48 + src/librespot/standard/DataInputStream.py | 118 + src/librespot/standard/DataOutput.py | 43 + src/librespot/standard/FilterInputStream.py | 41 + src/librespot/standard/Flushable.py | 3 + src/librespot/standard/InputStream.py | 240 ++ src/librespot/standard/OutputStream.py | 61 + src/librespot/standard/Proxy.py | 9 + src/librespot/standard/Runnable.py | 3 + src/librespot/standard/__init__.py | 14 + 160 files changed, 29238 insertions(+), 4 deletions(-) rename LICENSE => LICENSE.txt (99%) create mode 100644 example/console.py create mode 100644 proto/authentication.proto create mode 100644 proto/canvaz-meta.proto create mode 100644 proto/canvaz.proto create mode 100644 proto/connect.proto create mode 100644 proto/context.proto create mode 100644 proto/context_page.proto create mode 100644 proto/context_player_options.proto create mode 100644 proto/context_track.proto create mode 100644 proto/explicit_content_pubsub.proto create mode 100644 proto/keyexchange.proto create mode 100644 proto/mercury.proto create mode 100644 proto/metadata.proto create mode 100644 proto/play_origin.proto create mode 100644 proto/playback.proto create mode 100644 proto/player.proto create mode 100644 proto/playlist4_external.proto create mode 100644 proto/playlist_annotate3.proto create mode 100644 proto/pubsub.proto create mode 100644 proto/queue.proto create mode 100644 proto/restrictions.proto create mode 100644 proto/session.proto create mode 100644 proto/spotify/login5/v3/challenges/code.proto create mode 100644 proto/spotify/login5/v3/challenges/hashcash.proto create mode 100644 proto/spotify/login5/v3/client_info.proto create mode 100644 proto/spotify/login5/v3/credentials/credentials.proto create mode 100644 proto/spotify/login5/v3/identifiers/identifiers.proto create mode 100644 proto/spotify/login5/v3/login5.proto create mode 100644 proto/spotify/login5/v3/user_info.proto create mode 100644 proto/storage-resolve.proto create mode 100644 proto/transfer_state.proto create mode 100644 requirements.txt create mode 100644 setup.py create mode 100644 src/librespot/Version.py create mode 100644 src/librespot/__init__.py create mode 100644 src/librespot/audio/AbsChunkedInputStream.py create mode 100644 src/librespot/audio/AudioKeyManager.py create mode 100644 src/librespot/audio/GeneralAudioStream.py create mode 100644 src/librespot/audio/GeneralWritableStream.py create mode 100644 src/librespot/audio/HaltListener.py create mode 100644 src/librespot/audio/NormalizationData.py create mode 100644 src/librespot/audio/PlayableContentFeeder.py create mode 100644 src/librespot/audio/StreamId.py create mode 100644 src/librespot/audio/__init__.py create mode 100644 src/librespot/audio/cdn/CdnFeedHelper.py create mode 100644 src/librespot/audio/cdn/CdnManager.py create mode 100644 src/librespot/audio/cdn/__init__.py create mode 100644 src/librespot/audio/decrypt/AesAudioDecrypt.py create mode 100644 src/librespot/audio/decrypt/AudioDecrypt.py create mode 100644 src/librespot/audio/decrypt/NoopAudioDecrypt.py create mode 100644 src/librespot/audio/decrypt/__init__.py create mode 100644 src/librespot/audio/format/AudioQualityPicker.py create mode 100644 src/librespot/audio/format/SuperAudioFormat.py create mode 100644 src/librespot/audio/format/__init__.py create mode 100644 src/librespot/audio/storage/AudioFile.py create mode 100644 src/librespot/audio/storage/AudioFileStreaming.py create mode 100644 src/librespot/audio/storage/ChannelManager.py create mode 100644 src/librespot/audio/storage/__init__.py create mode 100644 src/librespot/cache/CacheManager.py create mode 100644 src/librespot/cache/__init__.py create mode 100644 src/librespot/common/Base62.py create mode 100644 src/librespot/common/Utils.py create mode 100644 src/librespot/common/__init__.py create mode 100644 src/librespot/core/ApResolver.py create mode 100644 src/librespot/core/EventService.py create mode 100644 src/librespot/core/PacketsReceiver.py create mode 100644 src/librespot/core/SearchManager.py create mode 100644 src/librespot/core/Session.py create mode 100644 src/librespot/core/TimeProvider.py create mode 100644 src/librespot/core/TokenProvider.py create mode 100644 src/librespot/core/__init__.py create mode 100644 src/librespot/crypto/CipherPair.py create mode 100644 src/librespot/crypto/DiffieHellman.py create mode 100644 src/librespot/crypto/Packet.py create mode 100644 src/librespot/crypto/Shannon.py create mode 100644 src/librespot/crypto/Shannon_DEV.py create mode 100644 src/librespot/crypto/__init__.py create mode 100644 src/librespot/dealer/ApiClient.py create mode 100644 src/librespot/dealer/DealerClient.py create mode 100644 src/librespot/dealer/__init__.py create mode 100644 src/librespot/mercury/JsonMercuryRequest.py create mode 100644 src/librespot/mercury/MercuryClient.py create mode 100644 src/librespot/mercury/MercuryRequests.py create mode 100644 src/librespot/mercury/ProtobufMercuryRequest.py create mode 100644 src/librespot/mercury/RawMercuryRequest.py create mode 100644 src/librespot/mercury/SubListener.py create mode 100644 src/librespot/mercury/__init__.py create mode 100644 src/librespot/metadata/AlbumId.py create mode 100644 src/librespot/metadata/ArtistId.py create mode 100644 src/librespot/metadata/EpisodeId.py create mode 100644 src/librespot/metadata/PlayableId.py create mode 100644 src/librespot/metadata/ShowId.py create mode 100644 src/librespot/metadata/SpotifyId.py create mode 100644 src/librespot/metadata/TrackId.py create mode 100644 src/librespot/metadata/UnsupportedId.py create mode 100644 src/librespot/metadata/__init__.py create mode 100644 src/librespot/player/Player.py create mode 100644 src/librespot/player/PlayerConfiguration.py create mode 100644 src/librespot/player/StateWrapper.py create mode 100644 src/librespot/player/__init__.py create mode 100644 src/librespot/player/codecs/AudioQuality.py create mode 100644 src/librespot/player/codecs/VorbisOnlyAudioQuality.py create mode 100644 src/librespot/player/codecs/__init__.py create mode 100644 src/librespot/player/playback/PlayerSession.py create mode 100644 src/librespot/player/playback/__init__.py create mode 100644 src/librespot/proto/Authentication.py create mode 100644 src/librespot/proto/Connect.py create mode 100644 src/librespot/proto/ExplicitContentPubsub.py create mode 100644 src/librespot/proto/Keyexchange.py create mode 100644 src/librespot/proto/Mercury.py create mode 100644 src/librespot/proto/Metadata.py create mode 100644 src/librespot/proto/Pubsub.py create mode 100644 src/librespot/proto/StorageResolve.py create mode 100644 src/librespot/proto/__init__.py create mode 100644 src/librespot/proto/canvaz_meta_pb2.py create mode 100644 src/librespot/proto/canvaz_pb2.py create mode 100644 src/librespot/proto/context_page_pb2.py create mode 100644 src/librespot/proto/context_pb2.py create mode 100644 src/librespot/proto/context_player_options_pb2.py create mode 100644 src/librespot/proto/context_track_pb2.py create mode 100644 src/librespot/proto/play_origin_pb2.py create mode 100644 src/librespot/proto/playback_pb2.py create mode 100644 src/librespot/proto/player_pb2.py create mode 100644 src/librespot/proto/playlist4_external_pb2.py create mode 100644 src/librespot/proto/playlist_annotate3_pb2.py create mode 100644 src/librespot/proto/queue_pb2.py create mode 100644 src/librespot/proto/restrictions_pb2.py create mode 100644 src/librespot/proto/session_pb2.py create mode 100644 src/librespot/proto/spotify/__init__.py create mode 100644 src/librespot/proto/spotify/login5/__init__.py create mode 100644 src/librespot/proto/spotify/login5/v3/__init__.py create mode 100644 src/librespot/proto/spotify/login5/v3/challenges/__init__.py create mode 100644 src/librespot/proto/spotify/login5/v3/challenges/code_pb2.py create mode 100644 src/librespot/proto/spotify/login5/v3/challenges/hashcash_pb2.py create mode 100644 src/librespot/proto/spotify/login5/v3/client_info_pb2.py create mode 100644 src/librespot/proto/spotify/login5/v3/credentials/__init__.py create mode 100644 src/librespot/proto/spotify/login5/v3/credentials/credentials_pb2.py create mode 100644 src/librespot/proto/spotify/login5/v3/identifiers/__init__.py create mode 100644 src/librespot/proto/spotify/login5/v3/identifiers/identifiers_pb2.py create mode 100644 src/librespot/proto/spotify/login5/v3/login5_pb2.py create mode 100644 src/librespot/proto/spotify/login5/v3/user_info_pb2.py create mode 100644 src/librespot/proto/transfer_state_pb2.py create mode 100644 src/librespot/standard/AutoCloseable.py create mode 100644 src/librespot/standard/ByteArrayOutputStream.py create mode 100644 src/librespot/standard/BytesInputStream.py create mode 100644 src/librespot/standard/BytesOutputStream.py create mode 100644 src/librespot/standard/Closeable.py create mode 100644 src/librespot/standard/DataInput.py create mode 100644 src/librespot/standard/DataInputStream.py create mode 100644 src/librespot/standard/DataOutput.py create mode 100644 src/librespot/standard/FilterInputStream.py create mode 100644 src/librespot/standard/Flushable.py create mode 100644 src/librespot/standard/InputStream.py create mode 100644 src/librespot/standard/OutputStream.py create mode 100644 src/librespot/standard/Proxy.py create mode 100644 src/librespot/standard/Runnable.py create mode 100644 src/librespot/standard/__init__.py diff --git a/.gitignore b/.gitignore index b6e4761..7333b6b 100644 --- a/.gitignore +++ b/.gitignore @@ -20,7 +20,6 @@ parts/ sdist/ var/ wheels/ -pip-wheel-metadata/ share/python-wheels/ *.egg-info/ .installed.cfg @@ -50,6 +49,7 @@ coverage.xml *.py,cover .hypothesis/ .pytest_cache/ +cover/ # Translations *.mo @@ -72,6 +72,7 @@ instance/ docs/_build/ # PyBuilder +.pybuilder/ target/ # Jupyter Notebook @@ -82,7 +83,9 @@ profile_default/ ipython_config.py # pyenv -.python-version +# For a library or package, you might want to ignore these files since the code is +# intended to run in multiple environments; otherwise, check them in: +# .python-version # pipenv # According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control. @@ -127,3 +130,12 @@ dmypy.json # Pyre type checker .pyre/ + +# pytype static type analyzer +.pytype/ + +# Cython debug symbols +cython_debug/ + +# for PyCharm +.idea/ diff --git a/LICENSE b/LICENSE.txt similarity index 99% rename from LICENSE rename to LICENSE.txt index 261eeb9..6e41bb8 100644 --- a/LICENSE +++ b/LICENSE.txt @@ -186,7 +186,7 @@ same "printed page" as the copyright notice for easier identification within third-party archives. - Copyright [yyyy] [name of copyright owner] + Copyright 2021 kokarare1212 Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. diff --git a/README.md b/README.md index 0832a0c..0bea93c 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,24 @@ -# librespot-python +![License](https://img.shields.io/github/license/kokarare1212/librespot-python.svg?style=for-the-badge) +![Stars](https://img.shields.io/github/stars/kokarare1212/librespot-python.svg?style=for-the-badge) +![Forks](https://img.shields.io/github/forks/kokarare1212/librespot-python.svg?style=for-the-badge) +# Librespot-Python Open Source Spotify Client +## About The Project +This project was developed to make the music streaming service Spotify available on any device. +## Note +We **DO NOT** encourage piracy and **DO NOT** support any form of downloader/recorder designed with the help of this repository and in general anything that goes against the Spotify ToS. +## Getting Started +### Prerequisites +* [Python](https://python.org/) +## Usage +Coming soon +## Roadmap +Coming soon +## License +Distributed under the Apache-2.0 License. See `LICENSE.txt` for more information. +## Related Projects +* [Librespot](https://github.com/librespot-org/librespot) (Concept) +* [Librespot-Java](https://github.com/librespot-org/librespot-java) (Core) +* [PySpotify2](https://github.com/pymedia/pyspotify2) (Shannon) +## Special thanks +Coming soon \ No newline at end of file diff --git a/example/console.py b/example/console.py new file mode 100644 index 0000000..7af85a7 --- /dev/null +++ b/example/console.py @@ -0,0 +1,98 @@ +from librespot.core import Session +from librespot.metadata import TrackId +from librespot.player.codecs import AudioQuality, VorbisOnlyAudioQuality +import logging +import os +import platform +import requests +import subprocess + +logging.basicConfig(level=logging.DEBUG) + + +def streaming(session: Session, uri: str, quality: AudioQuality): + stream = session.content_feeder().load(TrackId.from_uri(uri), VorbisOnlyAudioQuality(quality), False, None) + process = subprocess.Popen( + ["ffplay", "-autoexit", "-nodisp", "-loglevel", "quiet", "-"], + stdin=subprocess.PIPE) + while True: + i = stream.input_stream.stream().read() + if i == -1: + process.kill() + break + process.stdin.write(bytes([i])) + + +def main(): + session = Session.Builder().stored().create() + + quality: AudioQuality = AudioQuality.AudioQuality.VERY_HIGH + running: bool = True + while running: + try: + command = input("Librespot >>> ") + argv = command.split(" ") + + if argv[0] == "clear" or argv[0] == "cls": + if platform.system() == "Windows": + os.system("cls") + else: + os.system("clear") + continue + elif argv[0] == "play" or argv[0] == "p": + try: + track = argv[1] + except IndexError: + continue + + streaming(session, track, quality) + continue + elif argv[0] == "search" or argv[0] == "s": + try: + keyword = argv[1] + except IndexError: + continue + access_token = session.tokens().get("playlist-read") + resp = requests.get("https://api.spotify.com/v1/search?type=track&limit=5&q={}".format(keyword), headers={ + "Authorization": "Bearer {}".format(access_token), + "Accept-Language": "ja" + }) + obj = resp.json() + i = 1 + for track in obj["tracks"]["items"]: + print("{}, {} - {}".format(i, track["name"], ",".join([artist["name"] for artist in track["artists"]]))) + i += 1 + user_str = input("SELECT (1~5) | Librespot >>> ") + try: + selected_number = int(user_str) + except ValueError: + continue + if selected_number not in range(1, 6): + continue + streaming(session, obj["tracks"]["items"][selected_number - 1]["uri"], quality) + elif argv[0] == "quality": + try: + new_quality = argv[1] + except IndexError: + print("Current Quality: {}".format(quality)) + continue + if new_quality.lower() == "very_high": + quality = AudioQuality.AudioQuality.VERY_HIGH + elif new_quality.lower() == "high": + quality = AudioQuality.AudioQuality.HIGH + elif new_quality.lower() == "normal": + quality = AudioQuality.AudioQuality.NORMAL + else: + print("Unsupported Quality: {}".format(new_quality)) + continue + elif argv[0] == "quit" or argv[0] == "q" or argv[0] == "exit": + running = False + session.close() + continue + except KeyboardInterrupt: + running = False + session.close() + + +if __name__ == "__main__": + main() diff --git a/proto/authentication.proto b/proto/authentication.proto new file mode 100644 index 0000000..69c4f92 --- /dev/null +++ b/proto/authentication.proto @@ -0,0 +1,168 @@ +syntax = "proto2"; + +package spotify; +option java_package = "com.spotify"; + +message ClientResponseEncrypted { + required LoginCredentials login_credentials = 0xa; + optional AccountCreation account_creation = 0x14; + optional FingerprintResponseUnion fingerprint_response = 0x1e; + optional PeerTicketUnion peer_ticket = 0x28; + required SystemInfo system_info = 0x32; + optional string platform_model = 0x3c; + optional string version_string = 0x46; + optional LibspotifyAppKey appkey = 0x50; + optional ClientInfo client_info = 0x5a; +} + +message LoginCredentials { + optional string username = 0xa; + required AuthenticationType typ = 0x14; + optional bytes auth_data = 0x1e; +} + +enum AuthenticationType { + AUTHENTICATION_USER_PASS = 0x0; + AUTHENTICATION_STORED_SPOTIFY_CREDENTIALS = 0x1; + AUTHENTICATION_STORED_FACEBOOK_CREDENTIALS = 0x2; + AUTHENTICATION_SPOTIFY_TOKEN = 0x3; + AUTHENTICATION_FACEBOOK_TOKEN = 0x4; +} + +enum AccountCreation { + ACCOUNT_CREATION_ALWAYS_PROMPT = 0x1; + ACCOUNT_CREATION_ALWAYS_CREATE = 0x3; +} + +message FingerprintResponseUnion { + optional FingerprintGrainResponse grain = 0xa; + optional FingerprintHmacRipemdResponse hmac_ripemd = 0x14; +} + +message FingerprintGrainResponse { + required bytes encrypted_key = 0xa; +} + +message FingerprintHmacRipemdResponse { + required bytes hmac = 0xa; +} + +message PeerTicketUnion { + optional PeerTicketPublicKey public_key = 0xa; + optional PeerTicketOld old_ticket = 0x14; +} + +message PeerTicketPublicKey { + required bytes public_key = 0xa; +} + +message PeerTicketOld { + required bytes peer_ticket = 0xa; + required bytes peer_ticket_signature = 0x14; +} + +message SystemInfo { + required CpuFamily cpu_family = 0xa; + optional uint32 cpu_subtype = 0x14; + optional uint32 cpu_ext = 0x1e; + optional Brand brand = 0x28; + optional uint32 brand_flags = 0x32; + required Os os = 0x3c; + optional uint32 os_version = 0x46; + optional uint32 os_ext = 0x50; + optional string system_information_string = 0x5a; + optional string device_id = 0x64; +} + +enum CpuFamily { + CPU_UNKNOWN = 0x0; + CPU_X86 = 0x1; + CPU_X86_64 = 0x2; + CPU_PPC = 0x3; + CPU_PPC_64 = 0x4; + CPU_ARM = 0x5; + CPU_IA64 = 0x6; + CPU_SH = 0x7; + CPU_MIPS = 0x8; + CPU_BLACKFIN = 0x9; +} + +enum Brand { + BRAND_UNBRANDED = 0x0; + BRAND_INQ = 0x1; + BRAND_HTC = 0x2; + BRAND_NOKIA = 0x3; +} + +enum Os { + OS_UNKNOWN = 0x0; + OS_WINDOWS = 0x1; + OS_OSX = 0x2; + OS_IPHONE = 0x3; + OS_S60 = 0x4; + OS_LINUX = 0x5; + OS_WINDOWS_CE = 0x6; + OS_ANDROID = 0x7; + OS_PALM = 0x8; + OS_FREEBSD = 0x9; + OS_BLACKBERRY = 0xa; + OS_SONOS = 0xb; + OS_LOGITECH = 0xc; + OS_WP7 = 0xd; + OS_ONKYO = 0xe; + OS_PHILIPS = 0xf; + OS_WD = 0x10; + OS_VOLVO = 0x11; + OS_TIVO = 0x12; + OS_AWOX = 0x13; + OS_MEEGO = 0x14; + OS_QNXNTO = 0x15; + OS_BCO = 0x16; +} + +message LibspotifyAppKey { + required uint32 version = 0x1; + required bytes devkey = 0x2; + required bytes signature = 0x3; + required string useragent = 0x4; + required bytes callback_hash = 0x5; +} + +message ClientInfo { + optional bool limited = 0x1; + optional ClientInfoFacebook fb = 0x2; + optional string language = 0x3; +} + +message ClientInfoFacebook { + optional string machine_id = 0x1; +} + +message APWelcome { + required string canonical_username = 0xa; + required AccountType account_type_logged_in = 0x14; + required AccountType credentials_type_logged_in = 0x19; + required AuthenticationType reusable_auth_credentials_type = 0x1e; + required bytes reusable_auth_credentials = 0x28; + optional bytes lfs_secret = 0x32; + optional AccountInfo account_info = 0x3c; + optional AccountInfoFacebook fb = 0x46; +} + +enum AccountType { + Spotify = 0x0; + Facebook = 0x1; +} + +message AccountInfo { + optional AccountInfoSpotify spotify = 0x1; + optional AccountInfoFacebook facebook = 0x2; +} + +message AccountInfoSpotify { +} + +message AccountInfoFacebook { + optional string access_token = 0x1; + optional string machine_id = 0x2; +} diff --git a/proto/canvaz-meta.proto b/proto/canvaz-meta.proto new file mode 100644 index 0000000..e946ffd --- /dev/null +++ b/proto/canvaz-meta.proto @@ -0,0 +1,14 @@ +syntax = "proto3"; + +package com.spotify.canvaz; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.canvaz"; + +enum Type { + IMAGE = 0; + VIDEO = 1; + VIDEO_LOOPING = 2; + VIDEO_LOOPING_RANDOM = 3; + GIF = 4; +} diff --git a/proto/canvaz.proto b/proto/canvaz.proto new file mode 100644 index 0000000..af0a49b --- /dev/null +++ b/proto/canvaz.proto @@ -0,0 +1,40 @@ +syntax = "proto3"; + +package com.spotify.canvazcache; + +import "canvaz-meta.proto"; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.canvaz"; + +message Artist { + string uri = 1; + string name = 2; + string avatar = 3; +} + +message EntityCanvazResponse { + repeated Canvaz canvases = 1; + message Canvaz { + string id = 1; + string url = 2; + string file_id = 3; + canvaz.Type type = 4; + string entity_uri = 5; + Artist artist = 6; + bool explicit = 7; + string uploaded_by = 8; + string etag = 9; + string canvas_uri = 11; + } + + int64 ttl_in_seconds = 2; +} + +message EntityCanvazRequest { + repeated Entity entities = 1; + message Entity { + string entity_uri = 1; + string etag = 2; + } +} diff --git a/proto/connect.proto b/proto/connect.proto new file mode 100644 index 0000000..22ba764 --- /dev/null +++ b/proto/connect.proto @@ -0,0 +1,173 @@ +syntax = "proto3"; + +package connectstate; +import "player.proto"; + + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.connectstate"; + +message ClusterUpdate { + Cluster cluster = 1; + ClusterUpdateReason update_reason = 2; + string ack_id = 3; + repeated string devices_that_changed = 4; +} + +message Device { + DeviceInfo device_info = 1; + PlayerState player_state = 2; + PrivateDeviceInfo private_device_info = 3; +} + +message Cluster { + int64 timestamp = 1; + string active_device_id = 2; + PlayerState player_state = 3; + map device = 4; + bytes transfer_data = 5; +} + +message PutStateRequest { + string callback_url = 1; + Device device = 2; + MemberType member_type = 3; + bool is_active = 4; + PutStateReason put_state_reason = 5; + uint32 message_id = 6; + string last_command_sent_by_device_id = 7; + uint32 last_command_message_id = 8; + uint64 started_playing_at = 9; + uint64 has_been_playing_for_ms = 11; + uint64 client_side_timestamp = 12; + bool only_write_player_state = 13; +} + +message PrivateDeviceInfo { + string platform = 1; +} + +message SubscribeRequest { + string callback_url = 1; +} + +message DeviceInfo { + bool can_play = 1; + uint32 volume = 2; + string name = 3; + Capabilities capabilities = 4; + string device_software_version = 6; + DeviceType device_type = 7; + string spirc_version = 9; + string device_id = 10; + bool is_private_session = 11; + bool is_social_connect = 12; + string client_id = 13; + string brand = 14; + string model = 15; + map metadata_map = 16; +} + +message Capabilities { + bool can_be_player = 2; + bool restrict_to_local = 3; + bool gaia_eq_connect_id = 5; + bool supports_logout = 6; + bool is_observable = 7; + int32 volume_steps = 8; + repeated string supported_types = 9; + bool command_acks = 10; + bool supports_rename = 11; + bool hidden = 12; + bool disable_volume = 13; + bool connect_disabled = 14; + bool supports_playlist_v2 = 15; + bool is_controllable = 16; + bool supports_external_episodes = 17; + bool supports_set_backend_metadata = 18; + bool supports_transfer_command = 19; + bool supports_command_request = 20; + bool is_voice_enabled = 21; + bool needs_full_player_state = 22; + bool supports_gzip_pushes = 23; + // reserved 1, "supported_contexts"; +} + +message ConnectCommandOptions { + int32 message_id = 1; +} + +message LogoutCommand { + ConnectCommandOptions command_options = 1; +} + +message SetVolumeCommand { + int32 volume = 1; + ConnectCommandOptions command_options = 2; +} + +message RenameCommand { + string rename_to = 1; + ConnectCommandOptions command_options = 2; +} + +message SetBackendMetadataCommand { + map metadata = 1; +} + +enum SendCommandResult { + UNKNOWN_SEND_COMMAND_RESULT = 0; + SUCCESS = 1; + DEVICE_NOT_FOUND = 2; + CONTEXT_PLAYER_ERROR = 3; + DEVICE_DISAPPEARED = 4; + UPSTREAM_ERROR = 5; + DEVICE_DOES_NOT_SUPPORT_COMMAND = 6; + RATE_LIMITED = 7; +} + +enum PutStateReason { + UNKNOWN_PUT_STATE_REASON = 0; + SPIRC_HELLO = 1; + SPIRC_NOTIFY = 2; + NEW_DEVICE = 3; + PLAYER_STATE_CHANGED = 4; + VOLUME_CHANGED = 5; + PICKER_OPENED = 6; + BECAME_INACTIVE = 7; +} + +enum MemberType { + SPIRC_V2 = 0; + SPIRC_V3 = 1; + CONNECT_STATE = 2; +} + +enum ClusterUpdateReason { + UNKNOWN_CLUSTER_UPDATE_REASON = 0; + DEVICES_DISAPPEARED = 1; + DEVICE_STATE_CHANGED = 2; + NEW_DEVICE_APPEARED = 3; +} + +enum DeviceType { + UNKNOWN = 0; + COMPUTER = 1; + TABLET = 2; + SMARTPHONE = 3; + SPEAKER = 4; + TV = 5; + AVR = 6; + STB = 7; + AUDIO_DONGLE = 8; + GAME_CONSOLE = 9; + CAST_VIDEO = 10; + CAST_AUDIO = 11; + AUTOMOBILE = 12; + SMARTWATCH = 13; + CHROMEBOOK = 14; + UNKNOWN_SPOTIFY = 100; + CAR_THING = 101; + OBSERVER = 102; + HOME_THING = 103; +} diff --git a/proto/context.proto b/proto/context.proto new file mode 100644 index 0000000..853276d --- /dev/null +++ b/proto/context.proto @@ -0,0 +1,18 @@ +syntax = "proto2"; + +package spotify.player.proto; + +import "context_page.proto"; +import "restrictions.proto"; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.context"; + +message Context { + optional string uri = 1; + optional string url = 2; + map metadata = 3; + optional Restrictions restrictions = 4; + repeated ContextPage pages = 5; + optional bool loading = 6; +} diff --git a/proto/context_page.proto b/proto/context_page.proto new file mode 100644 index 0000000..d31cf1a --- /dev/null +++ b/proto/context_page.proto @@ -0,0 +1,16 @@ +syntax = "proto2"; + +package spotify.player.proto; + +import "context_track.proto"; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.context"; + +message ContextPage { + optional string page_url = 1; + optional string next_page_url = 2; + map metadata = 3; + repeated ContextTrack tracks = 4; + optional bool loading = 5; +} diff --git a/proto/context_player_options.proto b/proto/context_player_options.proto new file mode 100644 index 0000000..46a091c --- /dev/null +++ b/proto/context_player_options.proto @@ -0,0 +1,18 @@ +syntax = "proto2"; + +package spotify.player.proto; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.context"; + +message ContextPlayerOptions { + optional bool shuffling_context = 1; + optional bool repeating_context = 2; + optional bool repeating_track = 3; +} + +message ContextPlayerOptionOverrides { + optional bool shuffling_context = 1; + optional bool repeating_context = 2; + optional bool repeating_track = 3; +} diff --git a/proto/context_track.proto b/proto/context_track.proto new file mode 100644 index 0000000..c69aee4 --- /dev/null +++ b/proto/context_track.proto @@ -0,0 +1,13 @@ +syntax = "proto2"; + +package spotify.player.proto; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.context"; + +message ContextTrack { + optional string uri = 1; + optional string uid = 2; + optional bytes gid = 3; + map metadata = 4; +} diff --git a/proto/explicit_content_pubsub.proto b/proto/explicit_content_pubsub.proto new file mode 100644 index 0000000..f18b48f --- /dev/null +++ b/proto/explicit_content_pubsub.proto @@ -0,0 +1,15 @@ +syntax = "proto2"; + +package spotify.explicit_content.proto; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.explicit"; + +message KeyValuePair { + required string key = 1; + required string value = 2; +} + +message UserAttributesUpdate { + repeated KeyValuePair pairs = 1; +} diff --git a/proto/keyexchange.proto b/proto/keyexchange.proto new file mode 100644 index 0000000..3534783 --- /dev/null +++ b/proto/keyexchange.proto @@ -0,0 +1,231 @@ +syntax = "proto2"; + +package spotify; +option java_package = "com.spotify"; + +message ClientHello { + required BuildInfo build_info = 0xa; + repeated Fingerprint fingerprints_supported = 0x14; + repeated Cryptosuite cryptosuites_supported = 0x1e; + repeated Powscheme powschemes_supported = 0x28; + required LoginCryptoHelloUnion login_crypto_hello = 0x32; + required bytes client_nonce = 0x3c; + optional bytes padding = 0x46; + optional FeatureSet feature_set = 0x50; +} + + +message BuildInfo { + required Product product = 0xa; + repeated ProductFlags product_flags = 0x14; + required Platform platform = 0x1e; + required uint64 version = 0x28; +} + +enum Product { + PRODUCT_CLIENT = 0x0; + PRODUCT_LIBSPOTIFY = 0x1; + PRODUCT_MOBILE = 0x2; + PRODUCT_PARTNER = 0x3; + PRODUCT_LIBSPOTIFY_EMBEDDED = 0x5; +} + +enum ProductFlags { + PRODUCT_FLAG_NONE = 0x0; + PRODUCT_FLAG_DEV_BUILD = 0x1; +} + +enum Platform { + PLATFORM_WIN32_X86 = 0x0; + PLATFORM_OSX_X86 = 0x1; + PLATFORM_LINUX_X86 = 0x2; + PLATFORM_IPHONE_ARM = 0x3; + PLATFORM_S60_ARM = 0x4; + PLATFORM_OSX_PPC = 0x5; + PLATFORM_ANDROID_ARM = 0x6; + PLATFORM_WINDOWS_CE_ARM = 0x7; + PLATFORM_LINUX_X86_64 = 0x8; + PLATFORM_OSX_X86_64 = 0x9; + PLATFORM_PALM_ARM = 0xa; + PLATFORM_LINUX_SH = 0xb; + PLATFORM_FREEBSD_X86 = 0xc; + PLATFORM_FREEBSD_X86_64 = 0xd; + PLATFORM_BLACKBERRY_ARM = 0xe; + PLATFORM_SONOS = 0xf; + PLATFORM_LINUX_MIPS = 0x10; + PLATFORM_LINUX_ARM = 0x11; + PLATFORM_LOGITECH_ARM = 0x12; + PLATFORM_LINUX_BLACKFIN = 0x13; + PLATFORM_WP7_ARM = 0x14; + PLATFORM_ONKYO_ARM = 0x15; + PLATFORM_QNXNTO_ARM = 0x16; + PLATFORM_BCO_ARM = 0x17; +} + +enum Fingerprint { + FINGERPRINT_GRAIN = 0x0; + FINGERPRINT_HMAC_RIPEMD = 0x1; +} + +enum Cryptosuite { + CRYPTO_SUITE_SHANNON = 0x0; + CRYPTO_SUITE_RC4_SHA1_HMAC = 0x1; +} + +enum Powscheme { + POW_HASH_CASH = 0x0; +} + + +message LoginCryptoHelloUnion { + optional LoginCryptoDiffieHellmanHello diffie_hellman = 0xa; +} + + +message LoginCryptoDiffieHellmanHello { + required bytes gc = 0xa; + required uint32 server_keys_known = 0x14; +} + + +message FeatureSet { + optional bool autoupdate2 = 0x1; + optional bool current_location = 0x2; +} + + +message APResponseMessage { + optional APChallenge challenge = 0xa; + optional UpgradeRequiredMessage upgrade = 0x14; + optional APLoginFailed login_failed = 0x1e; +} + +message APChallenge { + required LoginCryptoChallengeUnion login_crypto_challenge = 0xa; + required FingerprintChallengeUnion fingerprint_challenge = 0x14; + required PoWChallengeUnion pow_challenge = 0x1e; + required CryptoChallengeUnion crypto_challenge = 0x28; + required bytes server_nonce = 0x32; + optional bytes padding = 0x3c; +} + +message LoginCryptoChallengeUnion { + optional LoginCryptoDiffieHellmanChallenge diffie_hellman = 0xa; +} + +message LoginCryptoDiffieHellmanChallenge { + required bytes gs = 0xa; + required int32 server_signature_key = 0x14; + required bytes gs_signature = 0x1e; +} + +message FingerprintChallengeUnion { + optional FingerprintGrainChallenge grain = 0xa; + optional FingerprintHmacRipemdChallenge hmac_ripemd = 0x14; +} + + +message FingerprintGrainChallenge { + required bytes kek = 0xa; +} + + +message FingerprintHmacRipemdChallenge { + required bytes challenge = 0xa; +} + + +message PoWChallengeUnion { + optional PoWHashCashChallenge hash_cash = 0xa; +} + +message PoWHashCashChallenge { + optional bytes prefix = 0xa; + optional int32 length = 0x14; + optional int32 target = 0x1e; +} + + +message CryptoChallengeUnion { + optional CryptoShannonChallenge shannon = 0xa; + optional CryptoRc4Sha1HmacChallenge rc4_sha1_hmac = 0x14; +} + + +message CryptoShannonChallenge { +} + + +message CryptoRc4Sha1HmacChallenge { +} + + +message UpgradeRequiredMessage { + required bytes upgrade_signed_part = 0xa; + required bytes signature = 0x14; + optional string http_suffix = 0x1e; +} + +message APLoginFailed { + required ErrorCode error_code = 0xa; + optional int32 retry_delay = 0x14; + optional int32 expiry = 0x1e; + optional string error_description = 0x28; +} + +enum ErrorCode { + ProtocolError = 0x0; + TryAnotherAP = 0x2; + BadConnectionId = 0x5; + TravelRestriction = 0x9; + PremiumAccountRequired = 0xb; + BadCredentials = 0xc; + CouldNotValidateCredentials = 0xd; + AccountExists = 0xe; + ExtraVerificationRequired = 0xf; + InvalidAppKey = 0x10; + ApplicationBanned = 0x11; +} + +message ClientResponsePlaintext { + required LoginCryptoResponseUnion login_crypto_response = 0xa; + required PoWResponseUnion pow_response = 0x14; + required CryptoResponseUnion crypto_response = 0x1e; +} + + +message LoginCryptoResponseUnion { + optional LoginCryptoDiffieHellmanResponse diffie_hellman = 0xa; +} + + +message LoginCryptoDiffieHellmanResponse { + required bytes hmac = 0xa; +} + + +message PoWResponseUnion { + optional PoWHashCashResponse hash_cash = 0xa; +} + + +message PoWHashCashResponse { + required bytes hash_suffix = 0xa; +} + + +message CryptoResponseUnion { + optional CryptoShannonResponse shannon = 0xa; + optional CryptoRc4Sha1HmacResponse rc4_sha1_hmac = 0x14; +} + + +message CryptoShannonResponse { + optional int32 dummy = 0x1; +} + + +message CryptoRc4Sha1HmacResponse { + optional int32 dummy = 0x1; +} + diff --git a/proto/mercury.proto b/proto/mercury.proto new file mode 100644 index 0000000..2b8688f --- /dev/null +++ b/proto/mercury.proto @@ -0,0 +1,49 @@ +syntax = "proto2"; + +package spotify; +option java_package = "com.spotify"; + +message MercuryMultiGetRequest { + repeated MercuryRequest request = 0x1; +} + +message MercuryMultiGetReply { + repeated MercuryReply reply = 0x1; +} + +message MercuryRequest { + optional string uri = 0x1; + optional string content_type = 0x2; + optional bytes body = 0x3; + optional bytes etag = 0x4; +} + +message MercuryReply { + optional sint32 status_code = 0x1; + optional string status_message = 0x2; + optional CachePolicy cache_policy = 0x3; + enum CachePolicy { + CACHE_NO = 0x1; + CACHE_PRIVATE = 0x2; + CACHE_PUBLIC = 0x3; + } + optional sint32 ttl = 0x4; + optional bytes etag = 0x5; + optional string content_type = 0x6; + optional bytes body = 0x7; +} + + +message Header { + optional string uri = 0x01; + optional string content_type = 0x02; + optional string method = 0x03; + optional sint32 status_code = 0x04; + repeated UserField user_fields = 0x06; +} + +message UserField { + optional string key = 0x01; + optional bytes value = 0x02; +} + diff --git a/proto/metadata.proto b/proto/metadata.proto new file mode 100644 index 0000000..5fa39c1 --- /dev/null +++ b/proto/metadata.proto @@ -0,0 +1,279 @@ +syntax = "proto2"; + +package spotify.metadata.proto; + +option optimize_for = CODE_SIZE; +option java_outer_classname = "Metadata"; +option java_package = "com.spotify.metadata"; + +message Artist { + optional bytes gid = 1; + optional string name = 2; + optional sint32 popularity = 3; + repeated TopTracks top_track = 4; + repeated AlbumGroup album_group = 5; + repeated AlbumGroup single_group = 6; + repeated AlbumGroup compilation_group = 7; + repeated AlbumGroup appears_on_group = 8; + repeated string genre = 9; + repeated ExternalId external_id = 10; + repeated Image portrait = 11; + repeated Biography biography = 12; + repeated ActivityPeriod activity_period = 13; + repeated Restriction restriction = 14; + repeated Artist related = 15; + optional bool is_portrait_album_cover = 16; + optional ImageGroup portrait_group = 17; + repeated SalePeriod sale_period = 18; + repeated Availability availability = 20; +} + +message Album { + optional bytes gid = 1; + optional string name = 2; + repeated Artist artist = 3; + + optional Type type = 4; + enum Type { + ALBUM = 1; + SINGLE = 2; + COMPILATION = 3; + EP = 4; + AUDIOBOOK = 5; + PODCAST = 6; + } + + optional string label = 5; + optional Date date = 6; + optional sint32 popularity = 7; + repeated string genre = 8; + repeated Image cover = 9; + repeated ExternalId external_id = 10; + repeated Disc disc = 11; + repeated string review = 12; + repeated Copyright copyright = 13; + repeated Restriction restriction = 14; + repeated Album related = 15; + repeated SalePeriod sale_period = 16; + optional ImageGroup cover_group = 17; + optional string original_title = 18; + optional string version_title = 19; + optional string type_str = 20; + repeated Availability availability = 23; +} + +message Track { + optional bytes gid = 1; + optional string name = 2; + optional Album album = 3; + repeated Artist artist = 4; + optional sint32 number = 5; + optional sint32 disc_number = 6; + optional sint32 duration = 7; + optional sint32 popularity = 8; + optional bool explicit = 9; + repeated ExternalId external_id = 10; + repeated Restriction restriction = 11; + repeated AudioFile file = 12; + repeated Track alternative = 13; + repeated SalePeriod sale_period = 14; + repeated AudioFile preview = 15; + repeated string tags = 16; + optional int64 earliest_live_timestamp = 17; + optional bool has_lyrics = 18; + repeated Availability availability = 19; + optional Licensor licensor = 21; +} + +message Show { + optional bytes gid = 1; + optional string name = 2; + optional string description = 64; + optional sint32 deprecated_popularity = 65 [deprecated = true]; + optional string publisher = 66; + optional string language = 67; + optional bool explicit = 68; + optional ImageGroup cover_image = 69; + repeated Episode episode = 70; + repeated Copyright copyright = 71; + repeated Restriction restriction = 72; + repeated string keyword = 73; + + optional MediaType media_type = 74; + enum MediaType { + MIXED = 0; + AUDIO = 1; + VIDEO = 2; + } + + optional ConsumptionOrder consumption_order = 75; + enum ConsumptionOrder { + SEQUENTIAL = 1; + EPISODIC = 2; + RECENT = 3; + } + + repeated Availability availability = 78; + optional string trailer_uri = 83; +} + +message Episode { + optional bytes gid = 1; + optional string name = 2; + optional sint32 duration = 7; + repeated AudioFile audio = 12; + optional string description = 64; + optional sint32 number = 65; + optional Date publish_time = 66; + optional sint32 deprecated_popularity = 67 [deprecated = true]; + optional ImageGroup cover_image = 68; + optional string language = 69; + optional bool explicit = 70; + optional Show show = 71; + repeated VideoFile video = 72; + repeated VideoFile video_preview = 73; + repeated AudioFile audio_preview = 74; + repeated Restriction restriction = 75; + optional ImageGroup freeze_frame = 76; + repeated string keyword = 77; + optional bool allow_background_playback = 81; + repeated Availability availability = 82; + optional string external_url = 83; + + optional .spotify.metadata.proto.Episode.EpisodeType type = 87; + enum EpisodeType { + FULL = 0; + TRAILER = 1; + BONUS = 2; + } +} + +message Licensor { + optional bytes uuid = 1; +} + +message TopTracks { + optional string country = 1; + repeated Track track = 2; +} + +message ActivityPeriod { + optional sint32 start_year = 1; + optional sint32 end_year = 2; + optional sint32 decade = 3; +} + +message AlbumGroup { + repeated Album album = 1; +} + +message Date { + optional sint32 year = 1; + optional sint32 month = 2; + optional sint32 day = 3; + optional sint32 hour = 4; + optional sint32 minute = 5; +} + +message Image { + optional bytes file_id = 1; + + optional Size size = 2; + enum Size { + DEFAULT = 0; + SMALL = 1; + LARGE = 2; + XLARGE = 3; + } + + optional sint32 width = 3; + optional sint32 height = 4; +} + +message ImageGroup { + repeated Image image = 1; +} + +message Biography { + optional string text = 1; + repeated Image portrait = 2; + repeated ImageGroup portrait_group = 3; +} + +message Disc { + optional sint32 number = 1; + optional string name = 2; + repeated Track track = 3; +} + +message Copyright { + optional Type type = 1; + enum Type { + P = 0; + C = 1; + } + + optional string text = 2; +} + +message Restriction { + repeated Catalogue catalogue = 1; + enum Catalogue { + AD = 0; + SUBSCRIPTION = 1; + CATALOGUE_ALL = 2; + SHUFFLE = 3; + COMMERCIAL = 4; + } + + optional Type type = 4; + enum Type { + STREAMING = 0; + } + + repeated string catalogue_str = 5; + + oneof country_restriction { + string countries_allowed = 2; + string countries_forbidden = 3; + } +} + +message Availability { + repeated string catalogue_str = 1; + optional Date start = 2; +} + +message SalePeriod { + repeated Restriction restriction = 1; + optional Date start = 2; + optional Date end = 3; +} + +message ExternalId { + optional string type = 1; + optional string id = 2; +} + +message AudioFile { + optional bytes file_id = 1; + + optional Format format = 2; + enum Format { + OGG_VORBIS_96 = 0; + OGG_VORBIS_160 = 1; + OGG_VORBIS_320 = 2; + MP3_256 = 3; + MP3_320 = 4; + MP3_160 = 5; + MP3_96 = 6; + MP3_160_ENC = 7; + AAC_24 = 8; + AAC_48 = 9; + AAC_24_NORM = 16; + } +} + +message VideoFile { + optional bytes file_id = 1; +} diff --git a/proto/play_origin.proto b/proto/play_origin.proto new file mode 100644 index 0000000..9cba9aa --- /dev/null +++ b/proto/play_origin.proto @@ -0,0 +1,16 @@ +syntax = "proto2"; + +package spotify.player.proto; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.context"; + +message PlayOrigin { + optional string feature_identifier = 1; + optional string feature_version = 2; + optional string view_uri = 3; + optional string external_referrer = 4; + optional string referrer_identifier = 5; + optional string device_identifier = 6; + repeated string feature_classes = 7; +} diff --git a/proto/playback.proto b/proto/playback.proto new file mode 100644 index 0000000..5273aaa --- /dev/null +++ b/proto/playback.proto @@ -0,0 +1,16 @@ +syntax = "proto2"; + +package spotify.player.proto.transfer; + +import "context_track.proto"; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.transfer"; + +message Playback { + optional int64 timestamp = 1; + optional int32 position_as_of_timestamp = 2; + optional double playback_speed = 3; + optional bool is_paused = 4; + optional ContextTrack current_track = 5; +} diff --git a/proto/player.proto b/proto/player.proto new file mode 100644 index 0000000..44f21d4 --- /dev/null +++ b/proto/player.proto @@ -0,0 +1,102 @@ +syntax = "proto3"; + +package connectstate; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.connectstate"; + +message PlayerState { + int64 timestamp = 1; + string context_uri = 2; + string context_url = 3; + Restrictions context_restrictions = 4; + PlayOrigin play_origin = 5; + ContextIndex index = 6; + ProvidedTrack track = 7; + string playback_id = 8; + double playback_speed = 9; + int64 position_as_of_timestamp = 10; + int64 duration = 11; + bool is_playing = 12; + bool is_paused = 13; + bool is_buffering = 14; + bool is_system_initiated = 15; + ContextPlayerOptions options = 16; + Restrictions restrictions = 17; + Suppressions suppressions = 18; + repeated ProvidedTrack prev_tracks = 19; + repeated ProvidedTrack next_tracks = 20; + map context_metadata = 21; + map page_metadata = 22; + string session_id = 23; + string queue_revision = 24; + int64 position = 25; + string entity_uri = 26; + repeated ProvidedTrack reverse = 27; + repeated ProvidedTrack future = 28; +} + +message ProvidedTrack { + string uri = 1; + string uid = 2; + map metadata = 3; + repeated string removed = 4; + repeated string blocked = 5; + string provider = 6; + Restrictions restrictions = 7; + string album_uri = 8; + repeated string disallow_reasons = 9; + string artist_uri = 10; + repeated string disallow_undecided = 11; +} + +message ContextIndex { + uint32 page = 1; + uint32 track = 2; +} + +message Restrictions { + repeated string disallow_pausing_reasons = 1; + repeated string disallow_resuming_reasons = 2; + repeated string disallow_seeking_reasons = 3; + repeated string disallow_peeking_prev_reasons = 4; + repeated string disallow_peeking_next_reasons = 5; + repeated string disallow_skipping_prev_reasons = 6; + repeated string disallow_skipping_next_reasons = 7; + repeated string disallow_toggling_repeat_context_reasons = 8; + repeated string disallow_toggling_repeat_track_reasons = 9; + repeated string disallow_toggling_shuffle_reasons = 10; + repeated string disallow_set_queue_reasons = 11; + repeated string disallow_interrupting_playback_reasons = 12; + repeated string disallow_transferring_playback_reasons = 13; + repeated string disallow_remote_control_reasons = 14; + repeated string disallow_inserting_into_next_tracks_reasons = 15; + repeated string disallow_inserting_into_context_tracks_reasons = 16; + repeated string disallow_reordering_in_next_tracks_reasons = 17; + repeated string disallow_reordering_in_context_tracks_reasons = 18; + repeated string disallow_removing_from_next_tracks_reasons = 19; + repeated string disallow_removing_from_context_tracks_reasons = 20; + repeated string disallow_updating_context_reasons = 21; + repeated string disallow_playing_reasons = 22; + repeated string disallow_stopping_reasons = 23; +} + +message PlayOrigin { + string feature_identifier = 1; + string feature_version = 2; + string view_uri = 3; + string external_referrer = 4; + string referrer_identifier = 5; + string device_identifier = 6; + repeated string feature_classes = 7; +} + +message ContextPlayerOptions { + bool shuffling_context = 1; + bool repeating_context = 2; + bool repeating_track = 3; +} + +message Suppressions { + repeated string providers = 1; +} diff --git a/proto/playlist4_external.proto b/proto/playlist4_external.proto new file mode 100644 index 0000000..3cae12b --- /dev/null +++ b/proto/playlist4_external.proto @@ -0,0 +1,229 @@ +syntax = "proto2"; + +package spotify.playlist4.proto; + +option optimize_for = CODE_SIZE; +option java_outer_classname = "Playlist4ApiProto"; +option java_package = "com.spotify.playlist4"; + +message Item { + required string uri = 1; + optional ItemAttributes attributes = 2; +} + +message MetaItem { + optional bytes revision = 1; + optional ListAttributes attributes = 2; + optional int32 length = 3; + optional int64 timestamp = 4; + optional string owner_username = 5; +} + +message ListItems { + required int32 pos = 1; + required bool truncated = 2; + repeated Item items = 3; + repeated MetaItem meta_items = 4; +} + +message FormatListAttribute { + optional string key = 1; + optional string value = 2; +} + +message ListAttributes { + optional string name = 1; + optional string description = 2; + optional bytes picture = 3; + optional bool collaborative = 4; + optional string pl3_version = 5; + optional bool deleted_by_owner = 6; + optional string client_id = 10; + optional string format = 11; + repeated FormatListAttribute format_attributes = 12; +} + +message ItemAttributes { + optional string added_by = 1; + optional int64 timestamp = 2; + optional int64 seen_at = 9; + optional bool public = 10; + repeated FormatListAttribute format_attributes = 11; + optional bytes item_id = 12; +} + +message Add { + optional int32 from_index = 1; + repeated Item items = 2; + optional bool add_last = 4; + optional bool add_first = 5; +} + +message Rem { + optional int32 from_index = 1; + optional int32 length = 2; + repeated Item items = 3; + optional bool items_as_key = 7; +} + +message Mov { + required int32 from_index = 1; + required int32 length = 2; + required int32 to_index = 3; +} + +message ItemAttributesPartialState { + required ItemAttributes values = 1; + repeated ItemAttributeKind no_value = 2; +} + +message ListAttributesPartialState { + required ListAttributes values = 1; + repeated ListAttributeKind no_value = 2; +} + +message UpdateItemAttributes { + required int32 index = 1; + required ItemAttributesPartialState new_attributes = 2; + optional ItemAttributesPartialState old_attributes = 3; +} + +message UpdateListAttributes { + required ListAttributesPartialState new_attributes = 1; + optional ListAttributesPartialState old_attributes = 2; +} + +message Op { + required Kind kind = 1; + enum Kind { + KIND_UNKNOWN = 0; + ADD = 2; + REM = 3; + MOV = 4; + UPDATE_ITEM_ATTRIBUTES = 5; + UPDATE_LIST_ATTRIBUTES = 6; + } + + optional Add add = 2; + optional Rem rem = 3; + optional Mov mov = 4; + optional UpdateItemAttributes update_item_attributes = 5; + optional UpdateListAttributes update_list_attributes = 6; +} + +message OpList { + repeated Op ops = 1; +} + +message ChangeInfo { + optional string user = 1; + optional int64 timestamp = 2; + optional bool admin = 3; + optional bool undo = 4; + optional bool redo = 5; + optional bool merge = 6; + optional bool compressed = 7; + optional bool migration = 8; + optional int32 split_id = 9; + optional SourceInfo source = 10; +} + +message SourceInfo { + optional Client client = 1; + enum Client { + CLIENT_UNKNOWN = 0; + NATIVE_HERMES = 1; + CLIENT = 2; + PYTHON = 3; + JAVA = 4; + WEBPLAYER = 5; + LIBSPOTIFY = 6; + } + + optional string app = 3; + optional string source = 4; + optional string version = 5; +} + +message Delta { + optional bytes base_version = 1; + repeated Op ops = 2; + optional ChangeInfo info = 4; +} + +message Diff { + required bytes from_revision = 1; + repeated Op ops = 2; + required bytes to_revision = 3; +} + +message ListChanges { + optional bytes base_revision = 1; + repeated Delta deltas = 2; + optional bool want_resulting_revisions = 3; + optional bool want_sync_result = 4; + repeated int64 nonces = 6; +} + +message SelectedListContent { + optional bytes revision = 1; + optional int32 length = 2; + optional ListAttributes attributes = 3; + optional ListItems contents = 5; + optional Diff diff = 6; + optional Diff sync_result = 7; + repeated bytes resulting_revisions = 8; + optional bool multiple_heads = 9; + optional bool up_to_date = 10; + repeated int64 nonces = 14; + optional int64 timestamp = 15; + optional string owner_username = 16; +} + +message CreateListReply { + required bytes uri = 1; + optional bytes revision = 2; +} + +message ModifyReply { + required bytes uri = 1; + optional bytes revision = 2; +} + +message SubscribeRequest { + repeated bytes uris = 1; +} + +message UnsubscribeRequest { + repeated bytes uris = 1; +} + +message PlaylistModificationInfo { + optional bytes uri = 1; + optional bytes new_revision = 2; + optional bytes parent_revision = 3; + repeated Op ops = 4; +} + +enum ListAttributeKind { + LIST_UNKNOWN = 0; + LIST_NAME = 1; + LIST_DESCRIPTION = 2; + LIST_PICTURE = 3; + LIST_COLLABORATIVE = 4; + LIST_PL3_VERSION = 5; + LIST_DELETED_BY_OWNER = 6; + LIST_CLIENT_ID = 10; + LIST_FORMAT = 11; + LIST_FORMAT_ATTRIBUTES = 12; +} + +enum ItemAttributeKind { + ITEM_UNKNOWN = 0; + ITEM_ADDED_BY = 1; + ITEM_TIMESTAMP = 2; + ITEM_SEEN_AT = 9; + ITEM_PUBLIC = 10; + ITEM_FORMAT_ATTRIBUTES = 11; + ITEM_ID = 12; +} diff --git a/proto/playlist_annotate3.proto b/proto/playlist_annotate3.proto new file mode 100644 index 0000000..05f57d6 --- /dev/null +++ b/proto/playlist_annotate3.proto @@ -0,0 +1,39 @@ +syntax = "proto2"; + +package spotify_playlist_annotate3.proto; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.playlist_annotate3"; + +message TakedownRequest { + optional AbuseReportState abuse_report_state = 1; +} + +message AnnotateRequest { + optional string description = 1; + optional string image_uri = 2; +} + +message TranscodedPicture { + optional string target_name = 1; + optional string uri = 2; +} + +message PlaylistAnnotation { + optional string description = 1; + optional string picture = 2; + optional RenderFeatures deprecated_render_features = 3 [default = NORMAL_FEATURES, deprecated = true]; + repeated TranscodedPicture transcoded_picture = 4; + optional bool is_abuse_reporting_enabled = 6 [default = true]; + optional AbuseReportState abuse_report_state = 7 [default = OK]; +} + +enum RenderFeatures { + NORMAL_FEATURES = 1; + EXTENDED_FEATURES = 2; +} + +enum AbuseReportState { + OK = 0; + TAKEN_DOWN = 1; +} diff --git a/proto/pubsub.proto b/proto/pubsub.proto new file mode 100644 index 0000000..ef7a9da --- /dev/null +++ b/proto/pubsub.proto @@ -0,0 +1,11 @@ +syntax = "proto2"; + +package spotify; +option java_package = "com.spotify"; + +message Subscription { + optional string uri = 0x1; + optional int32 expiry = 0x2; + optional int32 status_code = 0x3; +} + diff --git a/proto/queue.proto b/proto/queue.proto new file mode 100644 index 0000000..20fd54d --- /dev/null +++ b/proto/queue.proto @@ -0,0 +1,13 @@ +syntax = "proto2"; + +package spotify.player.proto.transfer; + +import "context_track.proto"; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.transfer"; + +message Queue { + repeated ContextTrack tracks = 1; + optional bool is_playing_queue = 2; +} diff --git a/proto/restrictions.proto b/proto/restrictions.proto new file mode 100644 index 0000000..8718941 --- /dev/null +++ b/proto/restrictions.proto @@ -0,0 +1,30 @@ +syntax = "proto2"; + +package spotify.player.proto; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.context"; + +message Restrictions { + repeated string disallow_pausing_reasons = 1; + repeated string disallow_resuming_reasons = 2; + repeated string disallow_seeking_reasons = 3; + repeated string disallow_peeking_prev_reasons = 4; + repeated string disallow_peeking_next_reasons = 5; + repeated string disallow_skipping_prev_reasons = 6; + repeated string disallow_skipping_next_reasons = 7; + repeated string disallow_toggling_repeat_context_reasons = 8; + repeated string disallow_toggling_repeat_track_reasons = 9; + repeated string disallow_toggling_shuffle_reasons = 10; + repeated string disallow_set_queue_reasons = 11; + repeated string disallow_interrupting_playback_reasons = 12; + repeated string disallow_transferring_playback_reasons = 13; + repeated string disallow_remote_control_reasons = 14; + repeated string disallow_inserting_into_next_tracks_reasons = 15; + repeated string disallow_inserting_into_context_tracks_reasons = 16; + repeated string disallow_reordering_in_next_tracks_reasons = 17; + repeated string disallow_reordering_in_context_tracks_reasons = 18; + repeated string disallow_removing_from_next_tracks_reasons = 19; + repeated string disallow_removing_from_context_tracks_reasons = 20; + repeated string disallow_updating_context_reasons = 21; +} diff --git a/proto/session.proto b/proto/session.proto new file mode 100644 index 0000000..d4f202c --- /dev/null +++ b/proto/session.proto @@ -0,0 +1,17 @@ +syntax = "proto2"; + +package spotify.player.proto.transfer; + +import "context.proto"; +import "context_player_options.proto"; +import "play_origin.proto"; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.transfer"; + +message Session { + optional PlayOrigin play_origin = 1; + optional Context context = 2; + optional string current_uid = 3; + optional ContextPlayerOptionOverrides option_overrides = 4; +} diff --git a/proto/spotify/login5/v3/challenges/code.proto b/proto/spotify/login5/v3/challenges/code.proto new file mode 100644 index 0000000..46e6881 --- /dev/null +++ b/proto/spotify/login5/v3/challenges/code.proto @@ -0,0 +1,19 @@ +syntax = "proto3"; + +package spotify.login5.v3.challenges; +option java_package = "com.spotify.login5v3"; + +message CodeChallenge { + enum Method { + UNKNOWN = 0; + SMS = 1; + } + .spotify.login5.v3.challenges.CodeChallenge.Method method = 1; + int32 code_length = 2; + int32 expires_in = 3; + string canonical_phone_number = 4; +} + +message CodeSolution { + string code = 1; +} diff --git a/proto/spotify/login5/v3/challenges/hashcash.proto b/proto/spotify/login5/v3/challenges/hashcash.proto new file mode 100644 index 0000000..4b47a06 --- /dev/null +++ b/proto/spotify/login5/v3/challenges/hashcash.proto @@ -0,0 +1,16 @@ +syntax = "proto3"; + +package spotify.login5.v3.challenges; +option java_package = "com.spotify.login5v3"; + +import "google/protobuf/duration.proto"; + +message HashcashChallenge { + bytes prefix = 1; + int32 length = 2; +} + +message HashcashSolution { + bytes suffix = 1; + .google.protobuf.Duration duration = 2; +} diff --git a/proto/spotify/login5/v3/client_info.proto b/proto/spotify/login5/v3/client_info.proto new file mode 100644 index 0000000..cec0f68 --- /dev/null +++ b/proto/spotify/login5/v3/client_info.proto @@ -0,0 +1,9 @@ +syntax = "proto3"; + +package spotify.login5.v3; +option java_package = "com.spotify.login5v3"; + +message ClientInfo { + string client_id = 1; + string device_id = 2; +} diff --git a/proto/spotify/login5/v3/credentials/credentials.proto b/proto/spotify/login5/v3/credentials/credentials.proto new file mode 100644 index 0000000..9273e90 --- /dev/null +++ b/proto/spotify/login5/v3/credentials/credentials.proto @@ -0,0 +1,35 @@ +syntax = "proto3"; + +package spotify.login5.v3.credentials; +option java_package = "com.spotify.login5v3"; + +message StoredCredential { + string username = 1; + bytes data = 2; +} + +message Password { + string id = 1; + string password = 2; + bytes padding = 3; +} + +message FacebookAccessToken { + string fb_uid = 1; + string access_token = 2; +} + +message OneTimeToken { + string token = 1; +} + +message ParentChildCredential { + string child_id = 1; + .spotify.login5.v3.credentials.StoredCredential parent_stored_credential = 2; +} + +message AppleSignInCredential { + string auth_code = 1; + string redirect_uri = 2; + string bundle_id = 3; +} diff --git a/proto/spotify/login5/v3/identifiers/identifiers.proto b/proto/spotify/login5/v3/identifiers/identifiers.proto new file mode 100644 index 0000000..250c076 --- /dev/null +++ b/proto/spotify/login5/v3/identifiers/identifiers.proto @@ -0,0 +1,10 @@ +syntax = "proto3"; + +package spotify.login5.v3.identifiers; +option java_package = "com.spotify.login5v3"; + +message PhoneNumber { + string number = 1; + string iso_country_code = 2; + string country_calling_code = 3; +} diff --git a/proto/spotify/login5/v3/login5.proto b/proto/spotify/login5/v3/login5.proto new file mode 100644 index 0000000..f959b71 --- /dev/null +++ b/proto/spotify/login5/v3/login5.proto @@ -0,0 +1,75 @@ +syntax = "proto3"; + +package spotify.login5.v3; +option java_package = "com.spotify.login5v3"; + +import "spotify/login5/v3/client_info.proto"; +import "spotify/login5/v3/user_info.proto"; +import "spotify/login5/v3/challenges/code.proto"; +import "spotify/login5/v3/challenges/hashcash.proto"; +import "spotify/login5/v3/credentials/credentials.proto"; +import "spotify/login5/v3/identifiers/identifiers.proto"; + +enum LoginError { + UNKNOWN_ERROR = 0; + INVALID_CREDENTIALS = 1; + BAD_REQUEST = 2; + UNSUPPORTED_LOGIN_PROTOCOL = 3; + TIMEOUT = 4; + UNKNOWN_IDENTIFIER = 5; + TOO_MANY_ATTEMPTS = 6; + INVALID_PHONENUMBER = 7; + TRY_AGAIN_LATER = 8; +} + +message Challenges { + repeated .spotify.login5.v3.Challenge challenges = 1; +} + +message Challenge { + .spotify.login5.v3.challenges.HashcashChallenge hashcash = 1; + .spotify.login5.v3.challenges.CodeChallenge code = 2; +} + +message ChallengeSolutions { + repeated .spotify.login5.v3.ChallengeSolution solutions = 1; +} + +message ChallengeSolution { + .spotify.login5.v3.challenges.HashcashSolution hashcash = 1; + .spotify.login5.v3.challenges.CodeSolution code = 2; +} + +message LoginRequest { + .spotify.login5.v3.ClientInfo client_info = 1; + bytes login_context = 2; + .spotify.login5.v3.ChallengeSolutions challenge_solutions = 3; + .spotify.login5.v3.credentials.StoredCredential stored_credential = 100; + .spotify.login5.v3.credentials.Password password = 101; + .spotify.login5.v3.credentials.FacebookAccessToken facebook_access_token = 102; + .spotify.login5.v3.identifiers.PhoneNumber phone_number = 103; + .spotify.login5.v3.credentials.OneTimeToken one_time_token = 104; + .spotify.login5.v3.credentials.ParentChildCredential parent_child_credential = 105; + .spotify.login5.v3.credentials.AppleSignInCredential apple_sign_in_credential = 106; +} + +message LoginOk { + string username = 1; + string access_token = 2; + bytes stored_credential = 3; + int32 access_token_expires_in = 4; +} + +message LoginResponse { + enum Warnings { + UNKNOWN_WARNING = 0; + DEPRECATED_PROTOCOL_VERSION = 1; + } + .spotify.login5.v3.LoginOk ok = 1; + .spotify.login5.v3.LoginError error = 2; + .spotify.login5.v3.Challenges challenges = 3; + repeated .spotify.login5.v3.LoginResponse.Warnings warnings = 4; + bytes login_context = 5; + string identifier_token = 6; + .spotify.login5.v3.UserInfo user_info = 7; +} diff --git a/proto/spotify/login5/v3/user_info.proto b/proto/spotify/login5/v3/user_info.proto new file mode 100644 index 0000000..f213e4c --- /dev/null +++ b/proto/spotify/login5/v3/user_info.proto @@ -0,0 +1,21 @@ +syntax = "proto3"; + +package spotify.login5.v3; +option java_package = "com.spotify.login5v3"; + +message UserInfo { + enum Gender { + UNKNOWN = 0; + MALE = 1; + FEMALE = 2; + NEUTRAL = 3; + } + string name = 1; + string email = 2; + bool email_verified = 3; + string birthdate = 4; + .spotify.login5.v3.UserInfo.Gender gender = 5; + string phone_number = 6; + bool phone_number_verified = 7; + bool email_already_registered = 8; +} diff --git a/proto/storage-resolve.proto b/proto/storage-resolve.proto new file mode 100644 index 0000000..3fb63e4 --- /dev/null +++ b/proto/storage-resolve.proto @@ -0,0 +1,18 @@ +syntax = "proto3"; + +package spotify.download.proto; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.storage"; + +message StorageResolveResponse { + Result result = 1; + enum Result { + CDN = 0; + STORAGE = 1; + RESTRICTED = 3; + } + + repeated string cdnurl = 2; + bytes fileid = 4; +} diff --git a/proto/transfer_state.proto b/proto/transfer_state.proto new file mode 100644 index 0000000..ddad42f --- /dev/null +++ b/proto/transfer_state.proto @@ -0,0 +1,19 @@ +syntax = "proto2"; + +package spotify.player.proto.transfer; + +import "context_player_options.proto"; +import "playback.proto"; +import "session.proto"; +import "queue.proto"; + +option optimize_for = CODE_SIZE; +option java_package = "com.spotify.transfer"; + +message TransferState { + optional ContextPlayerOptions options = 1; + optional Playback playback = 2; + optional Session current_session = 3; + optional Queue queue = 4; + optional int64 creation_timestamp = 5; +} diff --git a/requirements.txt b/requirements.txt new file mode 100644 index 0000000..2e11271 --- /dev/null +++ b/requirements.txt @@ -0,0 +1,4 @@ +defusedxml +protobuf +pycryptodome +requests \ No newline at end of file diff --git a/setup.py b/setup.py new file mode 100644 index 0000000..c3d1160 --- /dev/null +++ b/setup.py @@ -0,0 +1,19 @@ +import setuptools + +setuptools.setup( + name="librespot", + version="0.0.1-SNAPSHOT", + description="Open Source Spotify Client", + long_description=open("README.md").read(), + long_description_content_type="text/markdown", + author="kokarare1212", + url="https://github.com/kokarare1212/librespot-python", + license="Apache-2.0", + packages=setuptools.find_packages("src"), + package_dir={"": "src"}, + install_requires=["defusedxml", "protobuf", "pycryptodome", "requests"], + classifiers=[ + "Development Status :: 1 - Planning", + "License :: OSI Approved :: Apache Software License", + "Topic :: Multimedia :: Sound/Audio" + ]) diff --git a/src/librespot/Version.py b/src/librespot/Version.py new file mode 100644 index 0000000..b97e908 --- /dev/null +++ b/src/librespot/Version.py @@ -0,0 +1,32 @@ +from librespot.proto.Keyexchange import * +import platform + + +class Version: + version = "0.0.1-SNAPSHOT" + + @staticmethod + def platform() -> Platform: + if platform.system() == "Windows": + return Platform.PLATFORM_WIN32_X86 + elif platform.system() == "Darwin": + return Platform.PLATFORM_OSX_X86 + else: + return Platform.PLATFORM_LINUX_X86 + pass + + @staticmethod + def version_string(): + return "librespot-python " + Version.version + + @staticmethod + def system_info_string(): + return Version.version_string( + ) + "; Python " + platform.python_version() + "; " + platform.system() + + @staticmethod + def standard_build_info() -> BuildInfo: + return BuildInfo(product=Product.PRODUCT_CLIENT, + product_flags=[ProductFlags.PRODUCT_FLAG_NONE], + platform=Version.platform(), + version=112800721) diff --git a/src/librespot/__init__.py b/src/librespot/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/src/librespot/audio/AbsChunkedInputStream.py b/src/librespot/audio/AbsChunkedInputStream.py new file mode 100644 index 0000000..4c398ea --- /dev/null +++ b/src/librespot/audio/AbsChunkedInputStream.py @@ -0,0 +1,231 @@ +from librespot.audio.HaltListener import HaltListener +from librespot.audio.storage import ChannelManager +from librespot.standard.InputStream import InputStream +import math +import threading +import time +import typing + + +class AbsChunkedInputStream(InputStream, HaltListener): + preload_ahead: typing.Final[int] = 3 + preload_chunk_retries: typing.Final[int] = 2 + max_chunk_tries: typing.Final[int] = 128 + wait_lock: threading.Condition = threading.Condition() + retries: list[int] + retry_on_chunk_error: bool + chunk_exception = None + wait_for_chunk: int = -1 + _pos: int = 0 + _mark: int = 0 + closed: bool = False + _decoded_length: int = 0 + + def __init__(self, retry_on_chunk_error: bool): + self.retries: typing.Final[list[int]] = [ + 0 for _ in range(self.chunks()) + ] + self.retry_on_chunk_error = retry_on_chunk_error + + def is_closed(self) -> bool: + return self.closed + + def buffer(self) -> list[bytearray]: + raise NotImplementedError() + + def size(self) -> int: + raise NotImplementedError() + + def close(self) -> None: + self.closed = True + + with self.wait_lock: + self.wait_lock.notify_all() + + def available(self): + return self.size() - self._pos + + def mark_supported(self) -> bool: + return True + + def mark(self, read_ahead_limit: int) -> None: + self._mark = self._pos + + def reset(self) -> None: + self._pos = self._mark + + def pos(self) -> int: + return self._pos + + def seek(self, where: int) -> None: + if where < 0: + raise TypeError() + if self.closed: + raise IOError("Stream is closed!") + self._pos = where + + self.check_availability(int(self._pos / ChannelManager.CHUNK_SIZE), + False, False) + + def skip(self, n: int) -> int: + if n < 0: + raise TypeError() + if self.closed: + raise IOError("Stream is closed!") + + k = self.size() - self._pos + if n < k: + k = n + self._pos += k + + chunk = int(self._pos / ChannelManager.CHUNK_SIZE) + self.check_availability(chunk, False, False) + + return k + + def requested_chunks(self) -> list[bool]: + raise NotImplementedError() + + def available_chunks(self) -> list[bool]: + raise NotImplementedError() + + def chunks(self) -> int: + raise NotImplementedError() + + def request_chunk_from_stream(self, index: int) -> None: + raise NotImplementedError() + + def should_retry(self, chunk: int) -> bool: + if self.retries[chunk] < 1: + return True + if self.retries[chunk] > self.max_chunk_tries: + return False + return self.retry_on_chunk_error + + def check_availability(self, chunk: int, wait: bool, halted: bool) -> None: + if halted and not wait: + raise TypeError() + + if not self.requested_chunks()[chunk]: + self.request_chunk_from_stream(chunk) + self.requested_chunks()[chunk] = True + + for i in range(chunk + 1, + min(self.chunks() - 1, chunk + self.preload_ahead) + 1): + if self.requested_chunks( + )[i] and self.retries[i] < self.preload_chunk_retries: + self.request_chunk_from_stream(i) + self.requested_chunks()[chunk] = True + + if wait: + if self.available_chunks()[chunk]: + return + + retry = False + with self.wait_lock: + if not halted: + self.stream_read_halted(chunk, int(time.time() * 1000)) + + self.chunk_exception = None + self.wait_for_chunk = chunk + self.wait_lock.wait() + + if self.closed: + return + + if self.chunk_exception is not None: + if self.should_retry(chunk): + retry = True + else: + raise AbsChunkedInputStream.ChunkException + + if not retry: + self.stream_read_halted(chunk, int(time.time() * 1000)) + + if retry: + time.sleep(math.log10(self.retries[chunk])) + + self.check_availability(chunk, True, True) + + def read(self, + b: bytearray = None, + offset: int = None, + length: int = None) -> int: + if b is None and offset is None and length is None: + return self.internal_read() + elif not (b is not None and offset is not None and length is not None): + raise TypeError() + + if self.closed: + raise IOError("Stream is closed!") + + if offset < 0 or length < 0 or length > len(b) - offset: + raise IndexError("offset: {}, length: {}, buffer: {}".format( + offset, length, len(b))) + elif length == 0: + return 0 + + if self._pos >= self.size(): + return -1 + + i = 0 + while True: + chunk = int(self._pos / ChannelManager.CHUNK_SIZE) + chunk_off = int(self._pos % ChannelManager.CHUNK_SIZE) + + self.check_availability(chunk, True, False) + + copy = min(len(self.buffer()[chunk]) - chunk_off, length - i) + b[offset + 0:copy] = self.buffer()[chunk][chunk_off:chunk_off + + copy] + i += copy + self._pos += copy + + if i == length or self._pos >= self.size(): + return i + + def internal_read(self) -> int: + if self.closed: + raise IOError("Stream is closed!") + + if self._pos >= self.size(): + return -1 + + chunk = int(self._pos / ChannelManager.CHUNK_SIZE) + self.check_availability(chunk, True, False) + + b = self.buffer()[chunk][self._pos % ChannelManager.CHUNK_SIZE] + self._pos = self._pos + 1 + return b + + def notify_chunk_available(self, index: int) -> None: + self.available_chunks()[index] = True + self._decoded_length += len(self.buffer()[index]) + + with self.wait_lock: + if index == self.wait_for_chunk and not self.closed: + self.wait_for_chunk = -1 + self.wait_lock.notify_all() + + def notify_chunk_error(self, index: int, ex): + self.available_chunks()[index] = False + self.requested_chunks()[index] = False + self.retries[index] += 1 + + with self.wait_lock: + if index == self.wait_for_chunk and not self.closed: + self.chunk_exception = ex + self.wait_for_chunk = -1 + self.wait_lock.notify_all() + + def decoded_length(self): + return self._decoded_length + + class ChunkException(IOError): + def __init__(self, cause): + super().__init__(cause) + + @staticmethod + def from_stream_error(stream_error: int): + return AbsChunkedInputStream.ChunkException( + "Failed due to stream error, code: {}".format(stream_error)) diff --git a/src/librespot/audio/AudioKeyManager.py b/src/librespot/audio/AudioKeyManager.py new file mode 100644 index 0000000..2f10285 --- /dev/null +++ b/src/librespot/audio/AudioKeyManager.py @@ -0,0 +1,112 @@ +from __future__ import annotations +from librespot.common import Utils +from librespot.core import Session +from librespot.core.PacketsReceiver import PacketsReceiver +from librespot.crypto import Packet +from librespot.standard import BytesInputStream, BytesOutputStream +import logging +import queue +import threading + + +class AudioKeyManager(PacketsReceiver): + _ZERO_SHORT: bytes = bytes([0, 0]) + _LOGGER: logging = logging.getLogger(__name__) + _AUDIO_KEY_REQUEST_TIMEOUT: int = 20 + _seqHolder: int = 0 + _seqHolderLock: threading.Condition = threading.Condition() + _callbacks: dict[int, AudioKeyManager.Callback] = dict() + _session: Session = None + + def __init__(self, session: Session): + self._session = session + + def get_audio_key(self, + gid: bytes, + file_id: bytes, + retry: bool = True) -> bytes: + seq: int + with self._seqHolderLock: + seq = self._seqHolder + self._seqHolder += 1 + + out = BytesOutputStream() + out.write(file_id) + out.write(gid) + out.write_int(seq) + out.write(self._ZERO_SHORT) + + self._session.send(Packet.Type.request_key, out.buffer) + + callback = AudioKeyManager.SyncCallback(self) + self._callbacks[seq] = callback + + key = callback.wait_response() + if key is None: + if retry: + return self.get_audio_key(gid, file_id, False) + else: + raise RuntimeError( + "Failed fetching audio key! gid: {}, fileId: {}".format( + Utils.Utils.bytes_to_hex(gid), + Utils.Utils.bytes_to_hex(file_id))) + + return key + + def dispatch(self, packet: Packet) -> None: + payload = BytesInputStream(packet.payload) + seq = payload.read_int() + + callback = self._callbacks.get(seq) + if callback is None: + self._LOGGER.warning( + "Couldn't find callback for seq: {}".format(seq)) + return + + if packet.is_cmd(Packet.Type.aes_key): + key = payload.read(16) + callback.key(key) + elif packet.is_cmd(Packet.Type.aes_key_error): + code = payload.read_short() + callback.error(code) + else: + self._LOGGER.warning( + "Couldn't handle packet, cmd: {}, length: {}".format( + packet.cmd, len(packet.payload))) + + class Callback: + def key(self, key: bytes) -> None: + pass + + def error(self, code: int) -> None: + pass + + class SyncCallback(Callback): + _audioKeyManager: AudioKeyManager + reference = queue.Queue() + reference_lock = threading.Condition() + + def __init__(self, audio_key_manager: AudioKeyManager): + self._audioKeyManager = audio_key_manager + + def key(self, key: bytes) -> None: + with self.reference_lock: + self.reference.put(key) + self.reference_lock.notify_all() + + def error(self, code: int) -> None: + self._audioKeyManager._LOGGER.fatal( + "Audio key error, code: {}".format(code)) + with self.reference_lock: + self.reference.put(None) + self.reference_lock.notify_all() + + def wait_response(self) -> bytes: + with self.reference_lock: + self.reference_lock.wait( + AudioKeyManager._AUDIO_KEY_REQUEST_TIMEOUT) + return self.reference.get(block=False) + + class AesKeyException(IOError): + def __init__(self, ex): + super().__init__(ex) diff --git a/src/librespot/audio/GeneralAudioStream.py b/src/librespot/audio/GeneralAudioStream.py new file mode 100644 index 0000000..79e47ec --- /dev/null +++ b/src/librespot/audio/GeneralAudioStream.py @@ -0,0 +1,20 @@ +from __future__ import annotations +import typing + +if typing.TYPE_CHECKING: + from librespot.audio import AbsChunkedInputStream + from librespot.audio.format import SuperAudioFormat + + +class GeneralAudioStream: + def stream(self) -> AbsChunkedInputStream: + pass + + def codec(self) -> SuperAudioFormat: + pass + + def describe(self) -> str: + pass + + def decrypt_time_ms(self) -> int: + pass diff --git a/src/librespot/audio/GeneralWritableStream.py b/src/librespot/audio/GeneralWritableStream.py new file mode 100644 index 0000000..e723c1b --- /dev/null +++ b/src/librespot/audio/GeneralWritableStream.py @@ -0,0 +1,3 @@ +class GeneralWritableStream: + def write_chunk(self, buffer: bytearray, chunk_index: int, cached: bool): + pass diff --git a/src/librespot/audio/HaltListener.py b/src/librespot/audio/HaltListener.py new file mode 100644 index 0000000..f492053 --- /dev/null +++ b/src/librespot/audio/HaltListener.py @@ -0,0 +1,6 @@ +class HaltListener: + def stream_read_halted(self, chunk: int, _time: int) -> None: + pass + + def stream_read_resumed(self, chunk: int, _time: int): + pass diff --git a/src/librespot/audio/NormalizationData.py b/src/librespot/audio/NormalizationData.py new file mode 100644 index 0000000..87c28fb --- /dev/null +++ b/src/librespot/audio/NormalizationData.py @@ -0,0 +1,50 @@ +from __future__ import annotations +from librespot.standard import BytesInputStream, DataInputStream, InputStream +import logging +import math + + +class NormalizationData: + _LOGGER: logging = logging.getLogger(__name__) + track_gain_db: float + track_peak: float + album_gain_db: float + album_peak: float + + def __init__(self, track_gain_db: float, track_peak: float, + album_gain_db: float, album_peak: float): + self.track_gain_db = track_gain_db + self.track_peak = track_peak + self.album_gain_db = album_gain_db + self.album_peak = album_peak + + self._LOGGER.debug( + "Loaded normalization data, track_gain: {}, track_peak: {}, album_gain: {}, album_peak: {}" + .format(track_gain_db, track_peak, album_gain_db, album_peak)) + + @staticmethod + def read(input_stream: InputStream) -> NormalizationData: + data_input = DataInputStream(input_stream) + data_input.mark(16) + skip_bytes = data_input.skip_bytes(144) + if skip_bytes != 144: + raise IOError() + + data = bytearray(4 * 4) + data_input.read_fully(data) + data_input.reset() + + buffer = BytesInputStream(data, "<") + return NormalizationData(buffer.read_float(), buffer.read_float(), + buffer.read_float(), buffer.read_float()) + + def get_factor(self, normalisation_pregain) -> float: + normalisation_factor = float( + math.pow(10, (self.track_gain_db + normalisation_pregain) / 20)) + if normalisation_factor * self.track_peak > 1: + self._LOGGER.warning( + "Reducing normalisation factor to prevent clipping. Please add negative pregain to avoid." + ) + normalisation_factor = 1 / self.track_peak + + return normalisation_factor diff --git a/src/librespot/audio/PlayableContentFeeder.py b/src/librespot/audio/PlayableContentFeeder.py new file mode 100644 index 0000000..853523c --- /dev/null +++ b/src/librespot/audio/PlayableContentFeeder.py @@ -0,0 +1,141 @@ +from __future__ import annotations + +from librespot.audio import GeneralAudioStream, HaltListener, NormalizationData +from librespot.audio.cdn import CdnFeedHelper +from librespot.audio.format import AudioQualityPicker +from librespot.common.Utils import Utils +from librespot.core import Session +from librespot.metadata.PlayableId import PlayableId +from librespot.metadata.TrackId import TrackId +from librespot.proto import Metadata, StorageResolve +import logging +import typing + + +class PlayableContentFeeder: + _LOGGER: logging = logging.getLogger(__name__) + STORAGE_RESOLVE_INTERACTIVE: str = "/storage-resolve/files/audio/interactive/{}" + STORAGE_RESOLVE_INTERACTIVE_PREFETCH: str = "/storage-resolve/files/audio/interactive_prefetch/{}" + session: Session + + def __init__(self, session: Session): + self.session = session + + def pick_alternative_if_necessary(self, track: Metadata.Track): + if len(track.file) > 0: + return track + + for alt in track.alternative_list: + if len(alt.file) > 0: + pass + + return None + + def load(self, playable_id: PlayableId, + audio_quality_picker: AudioQualityPicker, preload: bool, + halt_listener: HaltListener): + if type(playable_id) is TrackId: + return self.load_track(playable_id, audio_quality_picker, preload, + halt_listener) + + def resolve_storage_interactive( + self, file_id: bytes, + preload: bool) -> StorageResolve.StorageResolveResponse: + resp = self.session.api().send( + "GET", (self.STORAGE_RESOLVE_INTERACTIVE_PREFETCH + if preload else self.STORAGE_RESOLVE_INTERACTIVE).format( + Utils.bytes_to_hex(file_id)), None, None) + if resp.status_code != 200: + raise RuntimeError(resp.status_code) + + body = resp.content + if body is None: + RuntimeError("Response body is empty!") + + storage_resolve_response = StorageResolve.StorageResolveResponse() + storage_resolve_response.ParseFromString(body) + return storage_resolve_response + + def load_track(self, track_id_or_track: typing.Union[TrackId, + Metadata.Track], + audio_quality_picker: AudioQualityPicker, preload: bool, + halt_listener: HaltListener): + if type(track_id_or_track) is TrackId: + original = self.session.api().get_metadata_4_track( + track_id_or_track) + track = self.pick_alternative_if_necessary(original) + if track is None: + raise + else: + track = track_id_or_track + file = audio_quality_picker.get_file(track.file) + if file is None: + self._LOGGER.fatal( + "Couldn't find any suitable audio file, available") + raise + + return self.load_stream(file, track, None, preload, halt_listener) + + def load_stream(self, file: Metadata.AudioFile, track: Metadata.Track, + episode: Metadata.Episode, preload: bool, + halt_lister: HaltListener): + if track is None and episode is None: + raise RuntimeError() + + resp = self.resolve_storage_interactive(file.file_id, preload) + if resp.result == StorageResolve.StorageResolveResponse.Result.CDN: + if track is not None: + return CdnFeedHelper.load_track(self.session, track, file, + resp, preload, halt_lister) + else: + return CdnFeedHelper.load_episode(self.session, episode, file, + resp, preload, halt_lister) + elif resp.result == StorageResolve.StorageResolveResponse.Result.STORAGE: + if track is None: + # return StorageFeedHelper + pass + elif resp.result == StorageResolve.StorageResolveResponse.Result.RESTRICTED: + raise RuntimeError("Content is restricted!") + elif resp.result == StorageResolve.StorageResolveResponse.Response.UNRECOGNIZED: + raise RuntimeError("Content is unrecognized!") + else: + raise RuntimeError("Unknown result: {}".format(resp.result)) + + class LoadedStream: + episode: Metadata.Episode + track: Metadata.Track + input_stream: GeneralAudioStream + normalization_data: NormalizationData + metrics: PlayableContentFeeder.Metrics + + def __init__(self, track_or_episode: typing.Union[Metadata.Track, + Metadata.Episode], + input_stream: GeneralAudioStream, + normalization_data: NormalizationData, + metrics: PlayableContentFeeder.Metrics): + if type(track_or_episode) is Metadata.Track: + self.track = track_or_episode + self.episode = None + elif type(track_or_episode) is Metadata.Episode: + self.track = None + self.episode = track_or_episode + else: + raise TypeError() + self.input_stream = input_stream + self.normalization_data = normalization_data + self.metrics = metrics + + class Metrics: + file_id: str + preloaded_audio_key: bool + audio_key_time: int + + def __init__(self, file_id: bytes, preloaded_audio_key: bool, + audio_key_time: int): + self.file_id = None if file_id is None else Utils.bytes_to_hex( + file_id) + self.preloaded_audio_key = preloaded_audio_key + self.audio_key_time = audio_key_time + + if preloaded_audio_key and audio_key_time != -1: + raise RuntimeError() diff --git a/src/librespot/audio/StreamId.py b/src/librespot/audio/StreamId.py new file mode 100644 index 0000000..42f9824 --- /dev/null +++ b/src/librespot/audio/StreamId.py @@ -0,0 +1,30 @@ +from librespot.common.Utils import Utils +from librespot.proto import Metadata + + +class StreamId: + file_id: bytes = None + episode_gid: bytes = None + + def __init__(self, + file: Metadata.AudioFile = None, + episode: Metadata.Episode = None): + if file is None and episode is None: + return + if file is not None: + self.file_id = file.file_id + if episode is not None: + self.episode_gid = episode.gid + + def get_file_id(self): + if self.file_id is None: + raise RuntimeError("Not a file!") + return Utils.bytes_to_hex(self.file_id) + + def is_episode(self): + return self.episode_gid is not None + + def get_episode_gid(self): + if self.episode_gid is None: + raise RuntimeError("Not an episode!") + return Utils.bytes_to_hex(self.episode_gid) diff --git a/src/librespot/audio/__init__.py b/src/librespot/audio/__init__.py new file mode 100644 index 0000000..4e38892 --- /dev/null +++ b/src/librespot/audio/__init__.py @@ -0,0 +1,8 @@ +from librespot.audio.AbsChunkedInputStream import AbsChunkedInputStream +from librespot.audio.AudioKeyManager import AudioKeyManager +from librespot.audio.GeneralAudioStream import GeneralAudioStream +from librespot.audio.GeneralWritableStream import GeneralWritableStream +from librespot.audio.HaltListener import HaltListener +from librespot.audio.NormalizationData import NormalizationData +from librespot.audio.PlayableContentFeeder import PlayableContentFeeder +from librespot.audio.StreamId import StreamId diff --git a/src/librespot/audio/cdn/CdnFeedHelper.py b/src/librespot/audio/cdn/CdnFeedHelper.py new file mode 100644 index 0000000..26e3d84 --- /dev/null +++ b/src/librespot/audio/cdn/CdnFeedHelper.py @@ -0,0 +1,85 @@ +from __future__ import annotations +from librespot.audio import NormalizationData, PlayableContentFeeder, HaltListener +from librespot.common import Utils +from librespot.core import Session +from librespot.proto import Metadata, StorageResolve +import logging +import random +import time +import typing + + +class CdnFeedHelper: + _LOGGER: logging = logging.getLogger(__name__) + + @staticmethod + def get_url(resp: StorageResolve.StorageResolveResponse) -> str: + return random.choice(resp.cdnurl) + + @staticmethod + def load_track(session: Session, track: Metadata.Track, file: Metadata.AudioFile, + resp_or_url: typing.Union[StorageResolve.StorageResolveResponse, str], + preload: bool, halt_listener: HaltListener)\ + -> PlayableContentFeeder.PlayableContentFeeder.LoadedStream: + if type(resp_or_url) is str: + url = resp_or_url + else: + url = CdnFeedHelper.get_url(resp_or_url) + start = int(time.time() * 1000) + key = session.audio_key().get_audio_key(track.gid, file.file_id) + audio_key_time = int(time.time() * 1000) - start + + streamer = session.cdn().stream_file(file, key, url, halt_listener) + input_stream = streamer.stream() + normalization_data = NormalizationData.read(input_stream) + if input_stream.skip(0xa7) != 0xa7: + raise IOError("Couldn't skip 0xa7 bytes!") + return PlayableContentFeeder.PlayableContentFeeder.LoadedStream( + track, streamer, normalization_data, + PlayableContentFeeder.PlayableContentFeeder.Metrics( + file.file_id, preload, audio_key_time)) + + @staticmethod + def load_episode_external( + session: Session, episode: Metadata.Episode, + halt_listener: HaltListener + ) -> PlayableContentFeeder.PlayableContentFeeder.LoadedStream: + resp = session.client().head(episode.external_url) + + if resp.status_code != 200: + CdnFeedHelper._LOGGER.warning("Couldn't resolve redirect!") + + url = resp.url + CdnFeedHelper._LOGGER.debug("Fetched external url for {}: {}".format( + Utils.Utils.bytes_to_hex(episode.gid), url)) + + streamer = session.cdn().stream_external_episode( + episode, url, halt_listener) + return PlayableContentFeeder.PlayableContentFeeder.LoadedStream( + episode, streamer, None, + PlayableContentFeeder.PlayableContentFeeder.Metrics( + None, False, -1)) + + @staticmethod + def load_episode( + session: Session, episode: Metadata.Episode, file: Metadata.AudioFile, + resp_or_url: typing.Union[StorageResolve.StorageResolveResponse, + str], halt_listener: HaltListener + ) -> PlayableContentFeeder.PlayableContentFeeder.LoadedStream: + if type(resp_or_url) is str: + url = resp_or_url + else: + url = CdnFeedHelper.get_url(resp_or_url) + start = int(time.time() * 1000) + key = session.audio_key().get_audio_key(episode.gid, file.file_id) + audio_key_time = int(time.time() * 1000) - start + + streamer = session.cdn().stream_file(file, key, url, halt_listener) + input_stream = streamer.stream() + normalization_data = NormalizationData.read(input_stream) + if input_stream.skip(0xa7) != 0xa7: + raise IOError("Couldn't skip 0xa7 bytes!") + return PlayableContentFeeder.PlayableContentFeeder.LoadedStream( + episode, streamer, normalization_data, + PlayableContentFeeder.PlayableContentFeeder.Metrics( + file.file_id, False, audio_key_time)) diff --git a/src/librespot/audio/cdn/CdnManager.py b/src/librespot/audio/cdn/CdnManager.py new file mode 100644 index 0000000..a5bbf35 --- /dev/null +++ b/src/librespot/audio/cdn/CdnManager.py @@ -0,0 +1,307 @@ +from __future__ import annotations +from librespot.audio.AbsChunkedInputStream import AbsChunkedInputStream +from librespot.audio import GeneralAudioStream, GeneralWritableStream, StreamId +from librespot.audio.decrypt import AesAudioDecrypt, NoopAudioDecrypt +from librespot.audio.format import SuperAudioFormat +from librespot.audio.storage import ChannelManager +from librespot.common import Utils +from librespot.proto import StorageResolve +import concurrent.futures +import logging +import math +import random +import time +import typing +import urllib.parse + +if typing.TYPE_CHECKING: + from librespot.audio.HaltListener import HaltListener + from librespot.audio.decrypt.AudioDecrypt import AudioDecrypt + from librespot.cache.CacheManager import CacheManager + from librespot.core.Session import Session + from librespot.proto import Metadata + + +class CdnManager: + _LOGGER: logging = logging.getLogger(__name__) + _session: Session = None + + def __init__(self, session: Session): + self._session = session + + def get_head(self, file_id: bytes): + resp = self._session.client() \ + .get(self._session.get_user_attribute("head-files-url", "https://heads-fa.spotify.com/head/{file_id}") + .replace("{file_id}", Utils.bytes_to_hex(file_id))) + + if resp.status_code != 200: + raise IOError("{}".format(resp.status_code)) + + body = resp.content + if body is None: + raise IOError("Response body is empty!") + + return body + + def stream_external_episode(self, episode: Metadata.Episode, + external_url: str, + halt_listener: HaltListener): + return CdnManager.Streamer(self._session, StreamId(episode), + SuperAudioFormat.MP3, + CdnManager.CdnUrl(self, None, external_url), + self._session.cache(), NoopAudioDecrypt(), + halt_listener) + + def stream_file(self, file: Metadata.AudioFile, key: bytes, url: str, + halt_listener: HaltListener): + return CdnManager.Streamer(self._session, StreamId.StreamId(file), + SuperAudioFormat.get(file.format), + CdnManager.CdnUrl(self, file.file_id, url), + self._session.cache(), AesAudioDecrypt(key), + halt_listener) + + def get_audio_url(self, file_id: bytes): + resp = self._session.api().send( + "GET", "/storage-resolve/files/audio/interactive/{}".format( + Utils.bytes_to_hex(file_id)), None, None) + + if resp.status_code != 200: + raise IOError(resp.status_code) + + body = resp.content + if body is None: + raise IOError("Response body is empty!") + + proto = StorageResolve.StorageResolveResponse() + proto.ParseFromString(body) + if proto.result == StorageResolve.StorageResolveResponse.Result.CDN: + url = random.choice(proto.cdnurl) + self._LOGGER.debug("Fetched CDN url for {}: {}".format( + Utils.bytes_to_hex(file_id), url)) + return url + else: + raise CdnManager.CdnException( + "Could not retrieve CDN url! result: {}".format(proto.result)) + + class CdnException(Exception): + def __init__(self, ex): + super().__init__(ex) + + class InternalResponse: + _buffer: bytearray + _headers: dict[str, str] + + def __init__(self, buffer: bytearray, headers: dict[str, str]): + self._buffer = buffer + self._headers = headers + + class CdnUrl: + _cdnManager = None + _fileId: bytes + _expiration: int + _url: str + + def __init__(self, cdn_manager, file_id: bytes, url: str): + self._cdnManager: CdnManager = cdn_manager + self._fileId = file_id + self.set_url(url) + + def url(self): + if self._expiration == -1: + return self._url + + if self._expiration <= int(time.time() * 1000) + 5 * 60 * 1000: + self._url = self._cdnManager.get_audio_url(self._fileId) + + return self.url + + def set_url(self, url: str): + self._url = url + + if self._fileId is not None: + token_url = urllib.parse.urlparse(url) + token_query = urllib.parse.parse_qs(token_url.query) + token_str = str(token_query.get("__token__")) + if token_str != "None" and len(token_str) != 0: + expire_at = None + split = token_str.split("~") + for s in split: + try: + i = s[0].index("=") + except ValueError: + continue + + if s[0][:i] == "exp": + expire_at = int(s[0][i:]) + break + + if expire_at is None: + self._expiration = -1 + self._cdnManager._LOGGER.warning( + "Invalid __token__ in CDN url: {}".format(url)) + return + + self._expiration = expire_at * 1000 + else: + try: + i = token_url.query.index("_") + except ValueError: + self._expiration = -1 + self._cdnManager._LOGGER.warning( + "Couldn't extract expiration, invalid parameter in CDN url: " + .format(url)) + return + + self._expiration = int(token_url.query[:i]) * 1000 + + else: + self._expiration = -1 + + class Streamer(GeneralAudioStream, GeneralWritableStream): + _session: Session = None + _streamId: StreamId = None + _executorService = concurrent.futures.ThreadPoolExecutor() + _audioFormat: SuperAudioFormat = None + _audioDecrypt: AudioDecrypt = None + _cdnUrl = None + _size: int + _buffer: list[bytearray] + _available: list[bool] + _requested: list[bool] + _chunks: int + _internalStream: CdnManager.Streamer.InternalStream = None + _haltListener: HaltListener = None + + def __init__(self, session: Session, stream_id: StreamId, + audio_format: SuperAudioFormat, cdn_url, + cache: CacheManager, audio_decrypt: AudioDecrypt, + halt_listener: HaltListener): + self._session = session + self._streamId = stream_id + self._audioFormat = audio_format + self._audioDecrypt = audio_decrypt + self._cdnUrl = cdn_url + self._haltListener = halt_listener + + resp = self.request(range_start=0, + range_end=ChannelManager.CHUNK_SIZE - 1) + content_range = resp._headers.get("Content-Range") + if content_range is None: + raise IOError("Missing Content-Range header!") + + split = Utils.split(content_range, "/") + self._size = int(split[1]) + self._chunks = int( + math.ceil(self._size / ChannelManager.CHUNK_SIZE)) + + first_chunk = resp._buffer + + self._available = [False for _ in range(self._chunks)] + self._requested = [False for _ in range(self._chunks)] + self._buffer = [bytearray() for _ in range(self._chunks)] + self._internalStream = CdnManager.Streamer.InternalStream( + self, False) + + self._requested[0] = True + self.write_chunk(first_chunk, 0, False) + + def write_chunk(self, chunk: bytes, chunk_index: int, + cached: bool) -> None: + if self._internalStream.is_closed(): + return + + self._session._LOGGER.debug( + "Chunk {}/{} completed, cached: {}, stream: {}".format( + chunk_index, self._chunks, cached, self.describe())) + + self._buffer[chunk_index] = self._audioDecrypt.decrypt_chunk( + chunk_index, chunk) + self._internalStream.notify_chunk_available(chunk_index) + + def stream(self) -> AbsChunkedInputStream: + return self._internalStream + + def codec(self) -> SuperAudioFormat: + return self._audioFormat + + def describe(self) -> str: + if self._streamId.is_episode(): + return "episode_gid: {}".format( + self._streamId.get_episode_gid()) + else: + return "file_id: {}".format(self._streamId.get_file_id()) + + def decrypt_time_ms(self) -> int: + return self._audioDecrypt.decrypt_time_ms() + + def request_chunk(self, index: int) -> None: + resp = self.request(index) + self.write_chunk(resp._buffer, index, False) + + def request(self, + chunk: int = None, + range_start: int = None, + range_end: int = None) -> CdnManager.InternalResponse: + if chunk is None and range_start is None and range_end is None: + raise TypeError() + + if chunk is not None: + range_start = ChannelManager.CHUNK_SIZE * chunk + range_end = (chunk + 1) * ChannelManager.CHUNK_SIZE - 1 + + resp = self._session.client().get(self._cdnUrl._url, + headers={ + "Range": + "bytes={}-{}".format( + range_start, range_end) + }) + + if resp.status_code != 206: + raise IOError(resp.status_code) + + body = resp.content + if body is None: + raise IOError("Response body is empty!") + + return CdnManager.InternalResponse(bytearray(body), resp.headers) + + class InternalStream(AbsChunkedInputStream): + streamer = None + + def __init__(self, streamer, retry_on_chunk_error: bool): + self.streamer: CdnManager.Streamer = streamer + super().__init__(retry_on_chunk_error) + + def close(self) -> None: + super().close() + + def buffer(self) -> list[bytearray]: + return self.streamer._buffer + + def size(self) -> int: + return self.streamer._size + + def requested_chunks(self) -> list[bool]: + return self.streamer._requested + + def available_chunks(self) -> list[bool]: + return self.streamer._available + + def chunks(self) -> int: + return self.streamer._chunks + + def request_chunk_from_stream(self, index: int) -> None: + self.streamer._executorService.submit( + lambda: self.streamer.request_chunk(index)) + + def stream_read_halted(self, chunk: int, _time: int) -> None: + if self.streamer._haltListener is not None: + self.streamer._executorService.submit( + lambda: self.streamer._haltListener.stream_read_halted( + chunk, _time)) + + def stream_read_resumed(self, chunk: int, _time: int) -> None: + if self.streamer._haltListener is not None: + self.streamer._executorService.submit( + lambda: self.streamer._haltListener. + stream_read_resumed(chunk, _time)) diff --git a/src/librespot/audio/cdn/__init__.py b/src/librespot/audio/cdn/__init__.py new file mode 100644 index 0000000..3eed8a6 --- /dev/null +++ b/src/librespot/audio/cdn/__init__.py @@ -0,0 +1,2 @@ +from librespot.audio.cdn.CdnFeedHelper import CdnFeedHelper +from librespot.audio.cdn.CdnManager import ChannelManager diff --git a/src/librespot/audio/decrypt/AesAudioDecrypt.py b/src/librespot/audio/decrypt/AesAudioDecrypt.py new file mode 100644 index 0000000..09fd17f --- /dev/null +++ b/src/librespot/audio/decrypt/AesAudioDecrypt.py @@ -0,0 +1,49 @@ +from Crypto.Cipher import AES +from Crypto.Util import Counter +from librespot.audio.storage.ChannelManager import ChannelManager +from librespot.audio.decrypt.AudioDecrypt import AudioDecrypt +import time + + +class AesAudioDecrypt(AudioDecrypt): + audio_aes_iv = bytes([ + 0x72, 0xe0, 0x67, 0xfb, 0xdd, 0xcb, 0xcf, 0x77, 0xeb, 0xe8, 0xbc, 0x64, + 0x3f, 0x63, 0x0d, 0x93 + ]) + iv_int = int.from_bytes(audio_aes_iv, "big") + iv_diff = 0x100 + cipher = None + decrypt_count = 0 + decrypt_total_time = 0 + key: bytes = None + + def __init__(self, key: bytes): + self.key = key + + def decrypt_chunk(self, chunk_index: int, buffer: bytes): + new_buffer = b"" + iv = self.iv_int + int(ChannelManager.CHUNK_SIZE * chunk_index / 16) + start = time.time_ns() + for i in range(0, len(buffer), 4096): + cipher = AES.new(key=self.key, + mode=AES.MODE_CTR, + counter=Counter.new(128, initial_value=iv)) + + count = min(4096, len(buffer) - i) + decrypted_buffer = cipher.decrypt(buffer[i:i + count]) + new_buffer += decrypted_buffer + if count != len(decrypted_buffer): + raise RuntimeError( + "Couldn't process all data, actual: {}, expected: {}". + format(len(decrypted_buffer), count)) + + iv += self.iv_diff + + self.decrypt_total_time += time.time_ns() + self.decrypt_count += 1 + + return new_buffer + + def decrypt_time_ms(self): + return 0 if self.decrypt_count == 0 else int( + (self.decrypt_total_time / self.decrypt_count) / 1000000) diff --git a/src/librespot/audio/decrypt/AudioDecrypt.py b/src/librespot/audio/decrypt/AudioDecrypt.py new file mode 100644 index 0000000..c7be936 --- /dev/null +++ b/src/librespot/audio/decrypt/AudioDecrypt.py @@ -0,0 +1,6 @@ +class AudioDecrypt: + def decrypt_chunk(self, chunk_index: int, buffer: bytes): + pass + + def decrypt_time_ms(self): + pass diff --git a/src/librespot/audio/decrypt/NoopAudioDecrypt.py b/src/librespot/audio/decrypt/NoopAudioDecrypt.py new file mode 100644 index 0000000..1c756a4 --- /dev/null +++ b/src/librespot/audio/decrypt/NoopAudioDecrypt.py @@ -0,0 +1,9 @@ +from librespot.audio.decrypt import AudioDecrypt + + +class NoopAudioDecrypt(AudioDecrypt): + def decrypt_chunk(self, chunk_index: int, buffer: bytes): + pass + + def decrypt_time_ms(self): + return 0 diff --git a/src/librespot/audio/decrypt/__init__.py b/src/librespot/audio/decrypt/__init__.py new file mode 100644 index 0000000..0af9c05 --- /dev/null +++ b/src/librespot/audio/decrypt/__init__.py @@ -0,0 +1,3 @@ +from librespot.audio.decrypt.AesAudioDecrypt import AesAudioDecrypt +from librespot.audio.decrypt.AudioDecrypt import AudioDecrypt +from librespot.audio.decrypt.NoopAudioDecrypt import NoopAudioDecrypt diff --git a/src/librespot/audio/format/AudioQualityPicker.py b/src/librespot/audio/format/AudioQualityPicker.py new file mode 100644 index 0000000..6f7780a --- /dev/null +++ b/src/librespot/audio/format/AudioQualityPicker.py @@ -0,0 +1,10 @@ +from __future__ import annotations +import typing + +if typing.TYPE_CHECKING: + from librespot.proto import Metadata + + +class AudioQualityPicker: + def get_file(self, files: list[Metadata.AudioFile]) -> Metadata.AudioFile: + pass diff --git a/src/librespot/audio/format/SuperAudioFormat.py b/src/librespot/audio/format/SuperAudioFormat.py new file mode 100644 index 0000000..d672bf8 --- /dev/null +++ b/src/librespot/audio/format/SuperAudioFormat.py @@ -0,0 +1,27 @@ +from librespot.proto import Metadata +import enum + + +class SuperAudioFormat(enum.Enum): + MP3 = 0x00 + VORBIS = 0x01 + AAC = 0x02 + + @staticmethod + def get(audio_format: Metadata.AudioFile.Format): + if audio_format == Metadata.AudioFile.Format.OGG_VORBIS_96 or \ + audio_format == Metadata.AudioFile.Format.OGG_VORBIS_160 or \ + audio_format == Metadata.AudioFile.Format.OGG_VORBIS_320: + return SuperAudioFormat.VORBIS + elif audio_format == Metadata.AudioFile.Format.MP3_256 or \ + audio_format == Metadata.AudioFile.Format.MP3_320 or \ + audio_format == Metadata.AudioFile.Format.MP3_160 or \ + audio_format == Metadata.AudioFile.Format.MP3_96 or \ + audio_format == Metadata.AudioFile.Format.MP3_160_ENC: + return SuperAudioFormat.MP3 + elif audio_format == Metadata.AudioFile.Format.AAC_24 or \ + audio_format == Metadata.AudioFile.Format.AAC_48 or \ + audio_format == Metadata.AudioFile.Format.AAC_24_NORM: + return SuperAudioFormat.AAC + else: + raise RuntimeError("Unknown audio format: {}".format(audio_format)) diff --git a/src/librespot/audio/format/__init__.py b/src/librespot/audio/format/__init__.py new file mode 100644 index 0000000..f27b14c --- /dev/null +++ b/src/librespot/audio/format/__init__.py @@ -0,0 +1,2 @@ +from librespot.audio.format.AudioQualityPicker import AudioQualityPicker +from librespot.audio.format.SuperAudioFormat import SuperAudioFormat diff --git a/src/librespot/audio/storage/AudioFile.py b/src/librespot/audio/storage/AudioFile.py new file mode 100644 index 0000000..b3cd41c --- /dev/null +++ b/src/librespot/audio/storage/AudioFile.py @@ -0,0 +1,12 @@ +from librespot.audio.GeneralWritableStream import GeneralWritableStream + + +class AudioFile(GeneralWritableStream): + def write_chunk(self, buffer: bytearray, chunk_index: int, cached: bool): + pass + + def write_header(self, chunk_id: int, b: bytearray, cached: bool): + pass + + def stream_error(self, chunk_index: int, code: int): + pass diff --git a/src/librespot/audio/storage/AudioFileStreaming.py b/src/librespot/audio/storage/AudioFileStreaming.py new file mode 100644 index 0000000..61382fd --- /dev/null +++ b/src/librespot/audio/storage/AudioFileStreaming.py @@ -0,0 +1,12 @@ +from __future__ import annotations +import typing + +if typing.TYPE_CHECKING: + from librespot.core.Session import Session + + +class AudioFileStreaming: + cache_handler = None + + def __init__(self, session: Session): + pass diff --git a/src/librespot/audio/storage/ChannelManager.py b/src/librespot/audio/storage/ChannelManager.py new file mode 100644 index 0000000..3c11f46 --- /dev/null +++ b/src/librespot/audio/storage/ChannelManager.py @@ -0,0 +1,146 @@ +from __future__ import annotations + +import queue + +from librespot.audio.storage import AudioFile +from librespot.common import Utils +from librespot.core import PacketsReceiver, Session +from librespot.crypto import Packet +from librespot.standard import BytesInputStream, BytesOutputStream, Closeable, Runnable +import concurrent.futures +import logging +import threading + + +class ChannelManager(Closeable, PacketsReceiver.PacketsReceiver): + CHUNK_SIZE: int = 128 * 1024 + _LOGGER: logging = logging.getLogger(__name__) + _channels: dict[int, Channel] = dict() + _seqHolder: int = 0 + _seqHolderLock: threading.Condition = threading.Condition() + _executorService: concurrent.futures.ThreadPoolExecutor = concurrent.futures.ThreadPoolExecutor( + ) + _session: Session = None + + def __init__(self, session: Session): + self._session = session + + def request_chunk(self, file_id: bytes, index: int, file: AudioFile): + start = int(index * self.CHUNK_SIZE / 4) + end = int((index + 1) * self.CHUNK_SIZE / 4) + + channel = ChannelManager.Channel(self, file, index) + self._channels[channel.chunkId] = channel + + out = BytesOutputStream() + out.write_short(channel.chunkId) + out.write_int(0x00000000) + out.write_int(0x00000000) + out.write_int(0x00004e20) + out.write_int(0x00030d40) + out.write(file_id) + out.write_int(start) + out.write_int(end) + + self._session.send(Packet.Type.stream_chunk, out.buffer) + + def dispatch(self, packet: Packet) -> None: + payload = BytesInputStream(packet.payload) + if packet.is_cmd(Packet.Type.stream_chunk_res): + chunk_id = payload.read_short() + channel = self._channels.get(chunk_id) + if channel is None: + self._LOGGER.warning( + "Couldn't find channel, id: {}, received: {}".format( + chunk_id, len(packet.payload))) + return + + channel._add_to_queue(payload) + elif packet.is_cmd(Packet.Type.channel_error): + chunk_id = payload.read_short() + channel = self._channels.get(chunk_id) + if channel is None: + self._LOGGER.warning( + "Dropping channel error, id: {}, code: {}".format( + chunk_id, payload.read_short())) + return + + channel.stream_error(payload.read_short()) + else: + self._LOGGER.warning( + "Couldn't handle packet, cmd: {}, payload: {}".format( + packet.cmd, Utils.Utils.bytes_to_hex(packet.payload))) + + def close(self) -> None: + self._executorService.shutdown() + + class Channel: + _channelManager: ChannelManager + chunkId: int + _q: queue.Queue = queue.Queue() + _file: AudioFile + _chunkIndex: int + _buffer: BytesOutputStream = BytesOutputStream() + _header: bool = True + + def __init__(self, channel_manager: ChannelManager, file: AudioFile, + chunk_index: int): + self._channelManager = channel_manager + self._file = file + self._chunkIndex = chunk_index + with self._channelManager._seqHolderLock: + self.chunkId = self._channelManager._seqHolder + self._channelManager._seqHolder += 1 + + self._channelManager._executorService.submit( + lambda: ChannelManager.Channel.Handler(self)) + + def _handle(self, payload: BytesInputStream) -> bool: + if len(payload.buffer) == 0: + if not self._header: + self._file.write_chunk(bytearray(payload.buffer), + self._chunkIndex, False) + return True + + self._channelManager._LOGGER.debug( + "Received empty chunk, skipping.") + return False + + if self._header: + length: int + while len(payload.buffer) > 0: + length = payload.read_short() + if not length > 0: + break + header_id = payload.read_byte() + header_data = payload.read(length - 1) + self._file.write_header(int.from_bytes(header_id, "big"), + bytearray(header_data), False) + self._header = False + else: + self._buffer.write(payload.read(len(payload.buffer))) + + return False + + def _add_to_queue(self, payload): + self._q.put(payload) + + def stream_error(self, code: int) -> None: + self._file.stream_error(self._chunkIndex, code) + + class Handler(Runnable): + _channel: ChannelManager.Channel = None + + def __init__(self, channel: ChannelManager.Channel): + self._channel = channel + + def run(self) -> None: + self._channel._channelManager._LOGGER.debug( + "ChannelManager.Handler is starting") + + with self._channel._q.all_tasks_done: + self._channel._channelManager._channels.pop( + self._channel.chunkId) + + self._channel._channelManager._LOGGER.debug( + "ChannelManager.Handler is shutting down") diff --git a/src/librespot/audio/storage/__init__.py b/src/librespot/audio/storage/__init__.py new file mode 100644 index 0000000..71135b8 --- /dev/null +++ b/src/librespot/audio/storage/__init__.py @@ -0,0 +1,3 @@ +from librespot.audio.storage.AudioFile import AudioFile +from librespot.audio.storage.AudioFileStreaming import AudioFileStreaming +from librespot.audio.storage.ChannelManager import ChannelManager diff --git a/src/librespot/cache/CacheManager.py b/src/librespot/cache/CacheManager.py new file mode 100644 index 0000000..713a294 --- /dev/null +++ b/src/librespot/cache/CacheManager.py @@ -0,0 +1,13 @@ +from __future__ import annotations +from librespot.core import Session + + +class CacheManager: + CLEAN_UP_THRESHOLD = 604800000 + HEADER_TIMESTAMP = 254 + HEADER_HASH = 253 + + parent: str + + def __init__(self, conf: Session.Configuration): + pass diff --git a/src/librespot/cache/__init__.py b/src/librespot/cache/__init__.py new file mode 100644 index 0000000..e41fdbc --- /dev/null +++ b/src/librespot/cache/__init__.py @@ -0,0 +1 @@ +from librespot.cache.CacheManager import CacheManager diff --git a/src/librespot/common/Base62.py b/src/librespot/common/Base62.py new file mode 100644 index 0000000..9663822 --- /dev/null +++ b/src/librespot/common/Base62.py @@ -0,0 +1,88 @@ +import math + + +class Base62: + standard_base = 256 + target_base = 62 + alphabet: bytes + lookup: bytearray + + def __init__(self, alphabet: bytes): + self.alphabet = alphabet + self.create_lookup_table() + + @staticmethod + def create_instance_with_inverted_character_set(): + return Base62(Base62.CharacterSets.inverted) + + def encode(self, message: bytes, length: int = -1): + indices = self.convert(message, self.standard_base, self.target_base, + length) + return self.translate(indices, self.alphabet) + + def decode(self, encoded: bytes, length: int = -1): + prepared = self.translate(encoded, self.lookup) + return self.convert(prepared, self.target_base, self.standard_base, + length) + + def translate(self, indices: bytes, dictionary: bytes): + translation = bytearray(len(indices)) + for i in range(len(indices)): + translation[i] = dictionary[int.from_bytes(indices[i].encode(), + "big")] + + return translation + + def convert(self, message: bytes, source_base: int, target_base: int, + length: int): + estimated_length = self.estimate_output_length( + len(message), source_base, target_base) if length == -1 else length + out = b"" + source = message + while len(source) > 0: + quotient = b"" + remainder = 0 + for b in source: + accumulator = int(b & 0xff) + remainder * source_base + digit = int( + (accumulator - (accumulator % target_base)) / target_base) + remainder = int(accumulator % target_base) + if len(quotient) > 0 or digit > 0: + quotient += bytes([digit]) + + out += bytes([remainder]) + source = quotient + + if len(out) < estimated_length: + size = len(out) + for i in range(estimated_length - size): + out += bytes([0]) + + return self.reverse(out) + elif len(out) > estimated_length: + return self.reverse(out[:estimated_length]) + else: + return self.reverse(out) + + def estimate_output_length(self, input_length: int, source_base: int, + target_base: int): + return int( + math.ceil((math.log(source_base) / math.log(target_base)) * + input_length)) + + def reverse(self, arr: bytes): + length = len(arr) + reversed_arr = bytearray(length) + for i in range(length): + reversed_arr[length - i - 1] = arr[i] + + return bytes(reversed_arr) + + def create_lookup_table(self): + self.lookup = bytearray(256) + for i in range(len(self.alphabet)): + self.lookup[self.alphabet[i]] = i & 0xff + + class CharacterSets: + gmp = b'0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz' + inverted = b'0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ' diff --git a/src/librespot/common/Utils.py b/src/librespot/common/Utils.py new file mode 100644 index 0000000..40bc3d7 --- /dev/null +++ b/src/librespot/common/Utils.py @@ -0,0 +1,31 @@ +import binascii +import os + + +class Utils: + @staticmethod + def random_hex_string(length: int): + buffer = os.urandom(int(length / 2)) + return Utils.bytes_to_hex(buffer) + + @staticmethod + def split(s: str, c: str): + return s.split(c) + + @staticmethod + def to_byte_array(i: int) -> bytes: + width = i.bit_length() + width += 8 - ((width % 8) or 8) + fmt = '%%0%dx' % (width // 4) + if i == 0: + return bytes([0]) + else: + return binascii.unhexlify(fmt % i) + + @staticmethod + def bytes_to_hex(buffer: bytes) -> str: + return binascii.hexlify(buffer).decode() + + @staticmethod + def hex_to_bytes(s: str) -> bytes: + return binascii.unhexlify(s) diff --git a/src/librespot/common/__init__.py b/src/librespot/common/__init__.py new file mode 100644 index 0000000..0f8b899 --- /dev/null +++ b/src/librespot/common/__init__.py @@ -0,0 +1,2 @@ +from librespot.common.Base62 import Base62 +from librespot.common.Utils import Utils diff --git a/src/librespot/core/ApResolver.py b/src/librespot/core/ApResolver.py new file mode 100644 index 0000000..733eaa1 --- /dev/null +++ b/src/librespot/core/ApResolver.py @@ -0,0 +1,33 @@ +import queue +import random +import requests + + +class ApResolver: + base_url = "http://apresolve.spotify.com/" + + @staticmethod + def request(service_type: str): + response = requests.get("{}?type={}".format(ApResolver.base_url, + service_type)) + return response.json() + + @staticmethod + def get_random_of(service_type: str): + pool = ApResolver.request(service_type) + urls = pool.get(service_type) + if urls is None or len(urls) == 0: + raise RuntimeError() + return random.choice(urls) + + @staticmethod + def get_random_dealer() -> str: + return ApResolver.get_random_of("dealer") + + @staticmethod + def get_random_spclient() -> str: + return ApResolver.get_random_of("spclient") + + @staticmethod + def get_random_accesspoint() -> str: + return ApResolver.get_random_of("accesspoint") diff --git a/src/librespot/core/EventService.py b/src/librespot/core/EventService.py new file mode 100644 index 0000000..6e119ff --- /dev/null +++ b/src/librespot/core/EventService.py @@ -0,0 +1,103 @@ +from __future__ import annotations +import concurrent.futures +import enum +import time +import typing +import logging + +from librespot.core import Session +from librespot.mercury import RawMercuryRequest +from librespot.standard import ByteArrayOutputStream + + +class EventService: + _session: Session + _LOGGER: logging = logging.getLogger(__name__) + _worker: concurrent.futures.ThreadPoolExecutor = concurrent.futures.ThreadPoolExecutor( + ) + + def __init__(self, session: Session): + self._session = session + + def _worker_callback(self, event_builder: EventService.EventBuilder): + try: + body = event_builder.to_array() + resp = self._session.mercury().send_sync(RawMercuryRequest.Builder( + ).set_uri("hm://event-service/v1/events").set_method( + "POST").add_user_field("Accept-Language", "en").add_user_field( + "X-ClientTimeStamp", + int(time.time() * 1000)).add_payload_part(body).build()) + + self._LOGGER.debug("Event sent. body: {}, result: {}".format( + body, resp.status_code)) + except IOError as ex: + self._LOGGER.error("Failed sending event: {} {}".format( + event_builder, ex)) + + def send_event(self, + event_or_builder: typing.Union[EventService.GenericEvent, + EventService.EventBuilder]): + if type(event_or_builder) is EventService.GenericEvent: + builder = event_or_builder.build() + elif type(event_or_builder) is EventService.EventBuilder: + builder = event_or_builder + else: + TypeError() + self._worker.submit(lambda: self._worker_callback(builder)) + + def language(self, lang: str): + event = EventService.EventBuilder(EventService.Type.LANGUAGE) + event.append(s=lang) + + def close(self): + pass + + class Type(enum.Enum): + LANGUAGE = ("812", 1) + FETCHED_FILE_ID = ("274", 3) + NEW_SESSION_ID = ("557", 3) + NEW_PLAYBACK_ID = ("558", 1) + TRACK_PLAYED = ("372", 1) + TRACK_TRANSITION = ("12", 37) + CDN_REQUEST = ("10", 20) + + _eventId: str + _unknown: str + + def __init__(self, event_id: str, unknown: str): + self._eventId = event_id + self._unknown = unknown + + class GenericEvent: + def build(self) -> EventService.EventBuilder: + pass + + class EventBuilder: + body: ByteArrayOutputStream = ByteArrayOutputStream(256) + + def __init__(self, type: EventService.Type): + self.append_no_delimiter(type.value[0]) + self.append(type.value[1]) + + def append_no_delimiter(self, s: str = None) -> None: + if s is None: + s = "" + + self.body.write(buffer=bytearray(s.encode())) + + def append(self, + c: int = None, + s: str = None) -> EventService.EventBuilder: + if c is None and s is None or c is not None and s is not None: + raise TypeError() + if c is not None: + self.body.write(byte=0x09) + self.body.write(byte=c) + return self + elif s is not None: + self.body.write(byte=0x09) + self.append_no_delimiter(s) + return self + + def to_array(self) -> bytearray: + return self.body.to_byte_array() diff --git a/src/librespot/core/PacketsReceiver.py b/src/librespot/core/PacketsReceiver.py new file mode 100644 index 0000000..a4c59c1 --- /dev/null +++ b/src/librespot/core/PacketsReceiver.py @@ -0,0 +1,6 @@ +from librespot.crypto.Packet import Packet + + +class PacketsReceiver: + def dispatch(self, packet: Packet): + pass diff --git a/src/librespot/core/SearchManager.py b/src/librespot/core/SearchManager.py new file mode 100644 index 0000000..706be4d --- /dev/null +++ b/src/librespot/core/SearchManager.py @@ -0,0 +1,10 @@ +from __future__ import annotations +from librespot.core import Session + + +class SearchManager: + _BASE_URL: str = "hm://searchview/km/v4/search/" + _session: Session + + def __init__(self, session: Session): + self._session = session diff --git a/src/librespot/core/Session.py b/src/librespot/core/Session.py new file mode 100644 index 0000000..10c9bf3 --- /dev/null +++ b/src/librespot/core/Session.py @@ -0,0 +1,1048 @@ +from __future__ import annotations +from Crypto.Hash import HMAC, SHA1 +from Crypto.PublicKey import RSA +from Crypto.Signature import PKCS1_v1_5 +from librespot.audio import AudioKeyManager, PlayableContentFeeder +from librespot.audio.cdn import CdnManager +from librespot.audio.storage import ChannelManager +from librespot.cache import CacheManager +from librespot.common.Utils import Utils +from librespot.core import ApResolver, EventService, SearchManager, TokenProvider +from librespot.crypto import CipherPair, DiffieHellman, Packet +from librespot.dealer import ApiClient, DealerClient +from librespot.mercury import MercuryClient, SubListener +from librespot.proto import Authentication, Connect, Keyexchange +from librespot.proto.ExplicitContentPubsub import UserAttributesUpdate +from librespot.standard import BytesInputStream, Closeable, Proxy +from librespot.Version import Version +import base64 +import defusedxml.ElementTree +import json +import logging +import os +import requests +import sched +import socket +import struct +import threading +import time + + +class Session(Closeable, SubListener, DealerClient.MessageListener): + _LOGGER: logging = logging.getLogger(__name__) + _serverKey: bytes = bytes([ + 0xac, 0xe0, 0x46, 0x0b, 0xff, 0xc2, 0x30, 0xaf, 0xf4, 0x6b, 0xfe, 0xc3, + 0xbf, 0xbf, 0x86, 0x3d, 0xa1, 0x91, 0xc6, 0xcc, 0x33, 0x6c, 0x93, 0xa1, + 0x4f, 0xb3, 0xb0, 0x16, 0x12, 0xac, 0xac, 0x6a, 0xf1, 0x80, 0xe7, 0xf6, + 0x14, 0xd9, 0x42, 0x9d, 0xbe, 0x2e, 0x34, 0x66, 0x43, 0xe3, 0x62, 0xd2, + 0x32, 0x7a, 0x1a, 0x0d, 0x92, 0x3b, 0xae, 0xdd, 0x14, 0x02, 0xb1, 0x81, + 0x55, 0x05, 0x61, 0x04, 0xd5, 0x2c, 0x96, 0xa4, 0x4c, 0x1e, 0xcc, 0x02, + 0x4a, 0xd4, 0xb2, 0x0c, 0x00, 0x1f, 0x17, 0xed, 0xc2, 0x2f, 0xc4, 0x35, + 0x21, 0xc8, 0xf0, 0xcb, 0xae, 0xd2, 0xad, 0xd7, 0x2b, 0x0f, 0x9d, 0xb3, + 0xc5, 0x32, 0x1a, 0x2a, 0xfe, 0x59, 0xf3, 0x5a, 0x0d, 0xac, 0x68, 0xf1, + 0xfa, 0x62, 0x1e, 0xfb, 0x2c, 0x8d, 0x0c, 0xb7, 0x39, 0x2d, 0x92, 0x47, + 0xe3, 0xd7, 0x35, 0x1a, 0x6d, 0xbd, 0x24, 0xc2, 0xae, 0x25, 0x5b, 0x88, + 0xff, 0xab, 0x73, 0x29, 0x8a, 0x0b, 0xcc, 0xcd, 0x0c, 0x58, 0x67, 0x31, + 0x89, 0xe8, 0xbd, 0x34, 0x80, 0x78, 0x4a, 0x5f, 0xc9, 0x6b, 0x89, 0x9d, + 0x95, 0x6b, 0xfc, 0x86, 0xd7, 0x4f, 0x33, 0xa6, 0x78, 0x17, 0x96, 0xc9, + 0xc3, 0x2d, 0x0d, 0x32, 0xa5, 0xab, 0xcd, 0x05, 0x27, 0xe2, 0xf7, 0x10, + 0xa3, 0x96, 0x13, 0xc4, 0x2f, 0x99, 0xc0, 0x27, 0xbf, 0xed, 0x04, 0x9c, + 0x3c, 0x27, 0x58, 0x04, 0xb6, 0xb2, 0x19, 0xf9, 0xc1, 0x2f, 0x02, 0xe9, + 0x48, 0x63, 0xec, 0xa1, 0xb6, 0x42, 0xa0, 0x9d, 0x48, 0x25, 0xf8, 0xb3, + 0x9d, 0xd0, 0xe8, 0x6a, 0xf9, 0x48, 0x4d, 0xa1, 0xc2, 0xba, 0x86, 0x30, + 0x42, 0xea, 0x9d, 0xb3, 0x08, 0x6c, 0x19, 0x0e, 0x48, 0xb3, 0x9d, 0x66, + 0xeb, 0x00, 0x06, 0xa2, 0x5a, 0xee, 0xa1, 0x1b, 0x13, 0x87, 0x3c, 0xd7, + 0x19, 0xe6, 0x55, 0xbd + ]) + _keys: DiffieHellman = None + _inner: Session.Inner = None + _scheduler: sched.scheduler = sched.scheduler(time.time) + _authLock: threading.Condition = threading.Condition() + _authLockBool: bool = False + _client: requests.Session = None + _closeListeners: list[Session.CloseListener] = list() + _closeListenersLock: threading.Condition = threading.Condition() + _reconnectionListeners: list[Session.ReconnectionListener] = list() + _reconnectionListenersLock: threading.Condition = threading.Condition() + _userAttributes: dict[str, str] = dict() + _conn: Session.ConnectionHolder = None + _cipherPair: CipherPair = None + _receiver: Session.Receiver = None + _apWelcome: Authentication.APWelcome = None + _mercuryClient: MercuryClient = None + _audioKeyManager: AudioKeyManager = None + _channelManager: ChannelManager = None + _tokenProvider: TokenProvider = None + _cdnManager: CdnManager = None + _cacheManager = None + _dealer: DealerClient = None + _api: ApiClient = None + _search: SearchManager = None + _contentFeeder: PlayableContentFeeder = None + _eventService: EventService = None + _countryCode: str = None + _closed: bool = False + _closing: bool = False + _scheduledReconnect: sched.Event = None + + def __init__(self, inner: Session.Inner, addr: str): + self._inner = inner + self._keys = DiffieHellman() + self._conn = Session.ConnectionHolder.create(addr, inner.conf) + self._client = Session._create_client(self._inner.conf) + + self._LOGGER.info("Created new session! device_id: {}, ap: {}".format( + inner.device_id, addr)) + + @staticmethod + def _create_client(conf: Session.Configuration) -> requests.Session: + client = requests.Session() + if conf.proxyAuth and conf.proxyType is not Proxy.Type.DIRECT: + if conf.proxyAuth: + proxy_setting = [ + conf.proxyUsername, conf.proxyPassword, conf.proxyAddress, + conf.proxyPort + ] + else: + proxy_setting = [conf.proxyAddress, conf.proxyPort] + client.proxies = { + "http": "{}:{}@{}:{}".format(*proxy_setting), + "https": "{}:{}@{}:{}".format(*proxy_setting) + } + + return client + + @staticmethod + def _read_blob_int(buffer: bytearray) -> int: + lo = buffer[0] + if (lo & 0x80) == 0: + return lo + hi = buffer[1] + return lo & 0x7f | hi << 7 + + def client(self) -> requests.Session: + return self._client + + def _connect(self) -> None: + acc = Session.Accumulator() + + # Send ClientHello + + nonce = os.urandom(0x10) + + client_hello = Keyexchange.ClientHello( + build_info=Version.standard_build_info(), + cryptosuites_supported=[ + Keyexchange.Cryptosuite.CRYPTO_SUITE_SHANNON + ], + login_crypto_hello=Keyexchange.LoginCryptoHelloUnion( + diffie_hellman=Keyexchange.LoginCryptoDiffieHellmanHello( + gc=self._keys.public_key_array(), server_keys_known=1), ), + client_nonce=nonce, + padding=bytes([0x1e])) + + client_hello_bytes = client_hello.SerializeToString() + length = 2 + 4 + len(client_hello_bytes) + self._conn.write_byte(0) + self._conn.write_byte(4) + self._conn.write_int(length) + self._conn.write(client_hello_bytes) + self._conn.flush() + + acc.write_byte(0) + acc.write_byte(4) + acc.write_int(length) + acc.write(client_hello_bytes) + + # Read APResponseMessage + + length = self._conn.read_int() + acc.write_int(length) + buffer = self._conn.read(length - 4) + acc.write(buffer) + + ap_response_message = Keyexchange.APResponseMessage() + ap_response_message.ParseFromString(buffer) + shared_key = Utils.to_byte_array( + self._keys.compute_shared_key( + ap_response_message.challenge.login_crypto_challenge. + diffie_hellman.gs)) + + # Check gs_signature + + rsa = RSA.construct((int.from_bytes(self._serverKey, "big"), 65537)) + pkcs1_v1_5 = PKCS1_v1_5.new(rsa) + sha1 = SHA1.new() + sha1.update(ap_response_message.challenge.login_crypto_challenge. + diffie_hellman.gs) + # noinspection PyTypeChecker + if not pkcs1_v1_5.verify( + sha1, ap_response_message.challenge.login_crypto_challenge. + diffie_hellman.gs_signature): + raise RuntimeError("Failed signature check!") + + # Solve challenge + + data = b"" + + for i in range(1, 6): + # noinspection PyTypeChecker + mac = HMAC.new(shared_key, digestmod=SHA1) + mac.update(acc.array()) + mac.update(bytes([i])) + data += mac.digest() + + # noinspection PyTypeChecker + mac = HMAC.new(data[:20], digestmod=SHA1) + mac.update(acc.array()) + + challenge = mac.digest() + client_response_plaintext = Keyexchange.ClientResponsePlaintext( + login_crypto_response=Keyexchange.LoginCryptoResponseUnion( + diffie_hellman=Keyexchange.LoginCryptoDiffieHellmanResponse( + hmac=challenge)), + pow_response=Keyexchange.PoWResponseUnion(), + crypto_response=Keyexchange.CryptoResponseUnion()) + + client_response_plaintext_bytes = client_response_plaintext.SerializeToString( + ) + length = 4 + len(client_response_plaintext_bytes) + self._conn.write_int(length) + self._conn.write(client_response_plaintext_bytes) + self._conn.flush() + + try: + self._conn.set_timeout(1) + scrap = self._conn.read(4) + if 4 == len(scrap): + length = (scrap[0] << 24) | (scrap[1] << 16) | ( + scrap[2] << 8) | (scrap[3] & 0xff) + payload = self._conn.read(length - 4) + failed = Keyexchange.APResponseMessage() + failed.ParseFromString(payload) + raise RuntimeError(failed) + except socket.timeout: + pass + finally: + self._conn.set_timeout(0) + + with self._authLock: + self._cipherPair = CipherPair(data[20:52], data[52:84]) + + self._authLockBool = True + + self._LOGGER.info("Connection successfully!") + + def authenticate(self, + credentials: Authentication.LoginCredentials) -> None: + self._authenticate_partial(credentials, False) + + with self._authLock: + self._mercuryClient = MercuryClient(self) + self._tokenProvider = TokenProvider.TokenProvider(self) + self._audioKeyManager = AudioKeyManager(self) + self._channelManager = ChannelManager(self) + self._api = ApiClient.ApiClient(self) + self._cdnManager = CdnManager.CdnManager(self) + self._contentFeeder = PlayableContentFeeder(self) + self._cacheManager = CacheManager(self) + self._dealer = DealerClient(self) + self._search = SearchManager.SearchManager(self) + self._eventService = EventService.EventService(self) + + self._authLockBool = False + self._authLock.notify_all() + + self._eventService.language(self._inner.preferred_locale) + # TimeProvider.init(self) + self._dealer.connect() + + self._LOGGER.info("Authenticated as {}!".format( + self._apWelcome.canonical_username)) + self.mercury().interested_in("spotify:user:attributes:update", self) + self.dealer().add_message_listener( + self, "hm://connect-state/v1/connect/logout") + + def _authenticate_partial(self, + credentials: Authentication.LoginCredentials, + remove_lock: bool) -> None: + if self._cipherPair is None: + raise RuntimeError("Connection not established!") + + client_response_encrypted = Authentication.ClientResponseEncrypted( + login_credentials=credentials, + system_info=Authentication.SystemInfo( + os=Authentication.Os.OS_UNKNOWN, + cpu_family=Authentication.CpuFamily.CPU_UNKNOWN, + system_information_string=Version.system_info_string(), + device_id=self._inner.device_id), + version_string=Version.version_string()) + + self._send_unchecked(Packet.Type.login, + client_response_encrypted.SerializeToString()) + + packet = self._cipherPair.receive_encoded(self._conn) + if packet.is_cmd(Packet.Type.ap_welcome): + self._apWelcome = Authentication.APWelcome() + self._apWelcome.ParseFromString(packet.payload) + + self._receiver = Session.Receiver(self) + + bytes0x0f = os.urandom(20) + self._send_unchecked(Packet.Type.unknown_0x0f, bytes0x0f) + + preferred_locale = bytes() + preferred_locale += bytes([0x00, 0x00, 0x10, 0x00, 0x02]) + preferred_locale += "preferred-locale".encode() + preferred_locale += self._inner.preferred_locale.encode() + self._send_unchecked(Packet.Type.preferred_locale, + preferred_locale) + + if remove_lock: + with self._authLock: + self._authLockBool = False + self._authLock.notify_all() + + if self._inner.conf.store_credentials: + reusable = self._apWelcome.reusable_auth_credentials + reusable_type = Authentication.AuthenticationType.Name( + self._apWelcome.reusable_auth_credentials_type) + + if self._inner.conf.stored_credentials_file is None: + raise TypeError() + + with open(self._inner.conf.stored_credentials_file, "w") as f: + json.dump( + { + "username": self._apWelcome.canonical_username, + "credentials": base64.b64encode(reusable).decode(), + "type": reusable_type + }, f) + + elif packet.is_cmd(Packet.Type.auth_failure): + ap_login_failed = Keyexchange.APLoginFailed() + ap_login_failed.ParseFromString(packet.payload) + raise Session.SpotifyAuthenticationException(ap_login_failed) + else: + raise RuntimeError("Unknown CMD 0x" + packet.cmd.hex()) + + def close(self) -> None: + self._LOGGER.info("Closing session. device_id: {}".format( + self._inner.device_id)) + + self._closing = True + + if self._dealer is not None: + self._dealer.close() + # noinspection PyTypeChecker + self._dealer = None + + if self._audioKeyManager is not None: + # noinspection PyTypeChecker + self._audioKeyManager = None + + if self._channelManager is not None: + self._channelManager.close() + # noinspection PyTypeChecker + self._channelManager = None + + if self._eventService is not None: + self._eventService.close() + # noinspection PyTypeChecker + self._eventService = None + + if self._mercuryClient is not None: + self._mercuryClient.close() + # noinspection PyTypeChecker + self._mercuryClient = None + + if self._receiver is not None: + self._receiver.stop() + # noinspection PyTypeChecker + self._receiver = None + + if self._client is not None: + # noinspection PyTypeChecker + self._client = None + + if self._conn is not None: + self._conn.sock.close() + # noinspection PyTypeChecker + self._conn = None + + with self._authLock: + self._apWelcome = None + # noinspection PyTypeChecker + self._cipherPair = None + self._closed = True + + with self._closeListenersLock: + for listener in self._closeListeners: + listener.on_closed() + self._closeListeners: list[Session.CloseListener] = list() + + self._reconnectionListeners: list[ + Session.ReconnectionListener] = list() + + self._LOGGER.info("Closed session. device_id: {}".format( + self._inner.device_id)) + + def _send_unchecked(self, cmd: bytes, payload: bytes) -> None: + self._cipherPair.send_encoded(self._conn, cmd, payload) + + def _wait_auth_lock(self) -> None: + if self._closing and self._conn is None: + self._LOGGER.debug("Connection was broken while closing.") + return + + if self._closed: + raise RuntimeError("Session is closed!") + + with self._authLock: + if self._cipherPair is None or self._authLockBool: + self._authLock.wait() + + def send(self, cmd: bytes, payload: bytes): + if self._closing and self._conn is None: + self._LOGGER.debug("Connection was broken while closing.") + return + + if self._closed: + raise RuntimeError("Session is closed!") + + with self._authLock: + if self._cipherPair is None or self._authLockBool: + self._authLock.wait() + + self._send_unchecked(cmd, payload) + + def mercury(self) -> MercuryClient: + self._wait_auth_lock() + if self._mercuryClient is None: + raise RuntimeError("Session isn't authenticated!") + return self._mercuryClient + + def audio_key(self) -> AudioKeyManager: + self._wait_auth_lock() + if self._audioKeyManager is None: + raise RuntimeError("Session isn't authenticated!") + return self._audioKeyManager + + def cache(self) -> CacheManager: + self._wait_auth_lock() + if self._cacheManager is None: + raise RuntimeError("Session isn't authenticated!") + return self._cacheManager + + def cdn(self) -> CdnManager: + self._wait_auth_lock() + if self._cdnManager is None: + raise RuntimeError("Session isn't authenticated!") + return self._cdnManager + + def channel(self) -> ChannelManager: + self._wait_auth_lock() + if self._channelManager is None: + raise RuntimeError("Session isn't authenticated!") + return self._channelManager + + def tokens(self) -> TokenProvider: + self._wait_auth_lock() + if self._tokenProvider is None: + raise RuntimeError("Session isn't authenticated!") + return self._tokenProvider + + def dealer(self) -> DealerClient: + self._wait_auth_lock() + if self._dealer is None: + raise RuntimeError("Session isn't authenticated!") + return self._dealer + + def api(self) -> ApiClient: + self._wait_auth_lock() + if self._api is None: + raise RuntimeError("Session isn't authenticated!") + return self._api + + def content_feeder(self) -> PlayableContentFeeder: + if self._contentFeeder is None: + raise RuntimeError("Session isn't authenticated!") + return self._contentFeeder + + def search(self) -> SearchManager: + self._wait_auth_lock() + if self._search is None: + raise RuntimeError("Session isn't authenticated!") + return self._search + + def event_service(self) -> EventService: + self._wait_auth_lock() + if self._eventService is None: + raise RuntimeError("Session isn't authenticated!") + return self._eventService + + def username(self) -> str: + return self.ap_welcome().canonical_username + + def ap_welcome(self) -> Authentication.APWelcome: + self._wait_auth_lock() + if self._apWelcome is None: + raise RuntimeError("Session isn't authenticated!") + return self._apWelcome + + def is_valid(self) -> bool: + if self._closed: + return False + + self._wait_auth_lock() + return self._apWelcome is not None and self._conn is not None + + def reconnecting(self) -> bool: + return not self._closing and not self._closed and self._conn is None + + def country_code(self) -> str: + return self._countryCode + + def device_id(self) -> str: + return self._inner.device_id + + def preferred_locale(self) -> str: + return self._inner.preferred_locale + + def device_type(self) -> Connect.DeviceType: + return self._inner.device_type + + def device_name(self) -> str: + return self._inner.device_name + + def configuration(self) -> Session.Configuration: + return self._inner.conf + + def _reconnect(self) -> None: + with self._reconnectionListenersLock: + for listener in self._reconnectionListeners: + listener.on_connection_dropped() + + if self._conn is not None: + self._conn.sock.close() + self._receiver.stop() + + self._conn = Session.ConnectionHolder.create( + ApResolver.get_random_accesspoint(), self._inner.conf) + self._connect() + self._authenticate_partial( + Authentication.LoginCredentials( + typ=self._apWelcome.reusable_auth_credentials_type, + username=self._apWelcome.canonical_username, + auth_data=self._apWelcome.reusable_auth_credentials), True) + + self._LOGGER.info("Re-authenticated as {}!".format( + self._apWelcome.canonical_username)) + + with self._reconnectionListenersLock: + for listener in self._reconnectionListeners: + listener.on_connection_established() + + def add_close_listener(self, listener: CloseListener) -> None: + if listener not in self._closeListeners: + self._closeListeners.append(listener) + + def add_reconnection_listener(self, + listener: ReconnectionListener) -> None: + if listener not in self._reconnectionListeners: + self._reconnectionListeners.append(listener) + + def remove_reconnection_listener(self, + listener: ReconnectionListener) -> None: + self._reconnectionListeners.remove(listener) + + def _parse_product_info(self, data) -> None: + doc = defusedxml.ElementTree.fromstring(data) + + products = doc + if products is None: + return + + product = products[0] + if product is None: + return + + for i in range(len(product)): + self._userAttributes[product[i].tag] = product[i].text + + self._LOGGER.debug("Parsed product info: {}".format( + self._userAttributes)) + + def get_user_attribute(self, key: str, fallback: str = None) -> str: + return self._userAttributes.get(key) if self._userAttributes.get( + key) is not None else fallback + + def event(self, resp: MercuryClient.Response) -> None: + if resp.uri == "spotify:user:attributes:update": + attributes_update = UserAttributesUpdate() + attributes_update.ParseFromString(resp.payload) + + for pair in attributes_update.pairs_list: + self._userAttributes[pair.key] = pair.value + self._LOGGER.info("Updated user attribute: {} -> {}".format( + pair.key, pair.value)) + + def on_message(self, uri: str, headers: dict[str, str], + payload: bytes) -> None: + if uri == "hm://connect-state/v1/connect/logout": + self.close() + + class ReconnectionListener: + def on_connection_dropped(self) -> None: + pass + + def on_connection_established(self) -> None: + pass + + class CloseListener: + def on_closed(self) -> None: + pass + + class Inner: + device_type: Connect.DeviceType = None + device_name: str = None + device_id: str = None + conf = None + preferred_locale: str = None + + def __init__(self, + device_type: Connect.DeviceType, + device_name: str, + preferred_locale: str, + conf: Session.Configuration, + device_id: str = None): + self.preferred_locale = preferred_locale + self.conf = conf + self.device_type = device_type + self.device_name = device_name + self.device_id = device_id if device_id is not None else Utils.random_hex_string( + 40) + + class AbsBuilder: + conf = None + device_id = None + device_name = "librespot-python" + device_type = Connect.DeviceType.COMPUTER + preferred_locale = "en" + + def __init__(self, conf: Session.Configuration = None): + if conf is None: + self.conf = Session.Configuration.Builder().build() + else: + self.conf = conf + + def set_preferred_locale(self, locale: str) -> Session.AbsBuilder: + if len(locale) != 2: + raise TypeError("Invalid locale: {}".format(locale)) + + self.preferred_locale = locale + return self + + def set_device_name(self, device_name: str) -> Session.AbsBuilder: + self.device_name = device_name + return self + + def set_device_id(self, device_id: str) -> Session.AbsBuilder: + if self.device_id is not None and len(device_id) != 40: + raise TypeError("Device ID must be 40 chars long.") + + self.device_id = device_id + return self + + def set_device_type( + self, device_type: Connect.DeviceType) -> Session.AbsBuilder: + self.device_type = device_type + return self + + class Builder(AbsBuilder): + login_credentials: Authentication.LoginCredentials = None + + def __init__(self, conf: Session.Configuration = None): + super().__init__(conf) + + def stored(self): + pass + + def stored_file(self, + stored_credentials: str = None) -> Session.Builder: + if stored_credentials is None: + stored_credentials = self.conf.stored_credentials_file + if os.path.isfile(stored_credentials): + try: + with open(stored_credentials) as f: + obj = json.load(f) + except json.JSONDecodeError: + pass + else: + try: + self.login_credentials = Authentication.LoginCredentials( + typ=Authentication.AuthenticationType.Value( + obj["type"]), + username=obj["username"], + auth_data=base64.b64decode(obj["credentials"])) + except KeyError: + pass + + return self + + def user_pass(self, username: str, password: str) -> Session.Builder: + self.login_credentials = Authentication.LoginCredentials( + username=username, + typ=Authentication.AuthenticationType.AUTHENTICATION_USER_PASS, + auth_data=password.encode()) + return self + + def create(self) -> Session: + if self.login_credentials is None: + raise RuntimeError("You must select an authentication method.") + + session = Session( + Session.Inner(self.device_type, self.device_name, + self.preferred_locale, self.conf, + self.device_id), + ApResolver.get_random_accesspoint()) + session._connect() + session.authenticate(self.login_credentials) + return session + + class Configuration: + # Proxy + proxyEnabled: bool + proxyType: Proxy.Type + proxyAddress: str + proxyPort: int + proxyAuth: bool + proxyUsername: str + proxyPassword: str + + # Cache + cache_enabled: bool + cache_dir: str + do_cache_clean_up: bool + + # Stored credentials + store_credentials: bool + stored_credentials_file: str + + # Fetching + retry_on_chunk_error: bool + + def __init__(self, proxy_enabled: bool, proxy_type: Proxy.Type, + proxy_address: str, proxy_port: int, proxy_auth: bool, + proxy_username: str, proxy_password: str, + cache_enabled: bool, cache_dir: str, + do_cache_clean_up: bool, store_credentials: bool, + stored_credentials_file: str, retry_on_chunk_error: bool): + self.proxyEnabled = proxy_enabled + self.proxyType = proxy_type + self.proxyAddress = proxy_address + self.proxyPort = proxy_port + self.proxyAuth = proxy_auth + self.proxyUsername = proxy_username + self.proxyPassword = proxy_password + self.cache_enabled = cache_enabled + self.cache_dir = cache_dir + self.do_cache_clean_up = do_cache_clean_up + self.store_credentials = store_credentials + self.stored_credentials_file = stored_credentials_file + self.retry_on_chunk_error = retry_on_chunk_error + + class Builder: + # Proxy + proxyEnabled: bool = False + proxyType: Proxy.Type = None + proxyAddress: str = None + proxyPort: int = None + proxyAuth: bool = None + proxyUsername: str = None + proxyPassword: str = None + + # Cache + cache_enabled: bool = True + cache_dir: str = os.path.join(os.getcwd(), "cache") + do_cache_clean_up: bool = None + + # Stored credentials + store_credentials: bool = True + stored_credentials_file: str = os.path.join( + os.getcwd(), "credentials.json") + + # Fetching + retry_on_chunk_error: bool = None + + def set_proxy_enabled( + self, + proxy_enabled: bool) -> Session.Configuration.Builder: + self.proxyEnabled = proxy_enabled + return self + + def set_proxy_type( + self, + proxy_type: Proxy.Type) -> Session.Configuration.Builder: + self.proxyType = proxy_type + return self + + def set_proxy_address( + self, proxy_address: str) -> Session.Configuration.Builder: + self.proxyAddress = proxy_address + return self + + def set_proxy_auth( + self, proxy_auth: bool) -> Session.Configuration.Builder: + self.proxyAuth = proxy_auth + return self + + def set_proxy_username( + self, + proxy_username: str) -> Session.Configuration.Builder: + self.proxyUsername = proxy_username + return self + + def set_proxy_password( + self, + proxy_password: str) -> Session.Configuration.Builder: + self.proxyPassword = proxy_password + return self + + def set_cache_enabled( + self, + cache_enabled: bool) -> Session.Configuration.Builder: + self.cache_enabled = cache_enabled + return self + + def set_cache_dir(self, + cache_dir: str) -> Session.Configuration.Builder: + self.cache_dir = cache_dir + return self + + def set_do_cache_clean_up( + self, + do_cache_clean_up: bool) -> Session.Configuration.Builder: + self.do_cache_clean_up = do_cache_clean_up + return self + + def set_store_credentials( + self, + store_credentials: bool) -> Session.Configuration.Builder: + self.store_credentials = store_credentials + return self + + def set_stored_credential_file( + self, stored_credential_file: str + ) -> Session.Configuration.Builder: + self.stored_credentials_file = stored_credential_file + return self + + def set_retry_on_chunk_error( + self, retry_on_chunk_error: bool + ) -> Session.Configuration.Builder: + self.retry_on_chunk_error = retry_on_chunk_error + return self + + def build(self) -> Session.Configuration: + return Session.Configuration( + self.proxyEnabled, self.proxyType, self.proxyAddress, + self.proxyPort, self.proxyAuth, self.proxyUsername, + self.proxyPassword, self.cache_enabled, self.cache_dir, + self.do_cache_clean_up, self.store_credentials, + self.stored_credentials_file, self.retry_on_chunk_error) + + class SpotifyAuthenticationException(Exception): + def __init__(self, login_failed: Keyexchange.APLoginFailed): + super().__init__(login_failed.error_code.name) + + class Accumulator: + buffer: bytes = bytes() + + def array(self) -> bytes: + return self.buffer + + def write(self, data: bytes) -> int: + self.buffer += data + return len(data) + + def write_byte(self, data: int) -> int: + self.buffer += bytes([data]) + return 1 + + def write_int(self, data: int) -> int: + self.buffer += struct.pack(">i", data) + return 4 + + class ConnectionHolder: + buffer: bytes = bytes() + + def __init__(self, sock: socket.socket): + self.sock = sock + + @staticmethod + def create(addr: str, + conf: Session.Configuration) -> Session.ConnectionHolder: + ap_addr = addr.split(":")[0] + ap_port = int(addr.split(":")[1]) + if not conf.proxyEnabled or conf.proxyType is Proxy.Type.DIRECT: + sock = socket.socket() + sock.connect((ap_addr, ap_port)) + return Session.ConnectionHolder(sock) + + if conf.proxyType is Proxy.Type.HTTP: + sock = socket.socket() + sock.connect((conf.proxyAddress, conf.proxyPort)) + + sock.send("CONNECT {}:{} HTTP/1.0\n".format(ap_addr, + ap_port).encode()) + if conf.proxyAuth: + sock.send( + "Proxy-Authorization: {}\n".format(None).encode()) + + sock.send(b"\n") + + elif conf.proxyType is Proxy.Type.SOCKS: + pass + else: + raise RuntimeError() + + def flush(self) -> None: + self.sock.send(self.buffer) + self.buffer = b"" + + def read(self, length: int) -> bytes: + return self.sock.recv(length) + + def read_int(self) -> int: + return struct.unpack(">i", self.sock.recv(4))[0] + + def set_timeout(self, timeout: int) -> None: + if timeout == 0: + self.sock.settimeout(None) + else: + self.sock.settimeout(timeout) + + def write(self, data: bytes) -> int: + self.buffer += data + return len(data) + + def write_byte(self, data: int) -> int: + self.buffer += bytes([data]) + return 1 + + def write_int(self, data: int) -> int: + self.buffer += struct.pack(">i", data) + return 4 + + def write_short(self, data: int) -> int: + self.buffer += struct.pack(">h", data) + return 2 + + class Receiver: + session: Session = None + thread: threading.Thread + running: bool = True + + def __init__(self, session): + self.session = session + self.thread = threading.Thread(target=self.run) + self.thread.setDaemon(True) + self.thread.setName("session-packet-receiver") + self.thread.start() + + def stop(self) -> None: + self.running = False + + def run(self) -> None: + self.session._LOGGER.debug("Session.Receiver started") + + while self.running: + packet: Packet + cmd: bytes + try: + # noinspection PyProtectedMember + packet = self.session._cipherPair.receive_encoded( + self.session._conn) + cmd = Packet.Type.parse(packet.cmd) + if cmd is None: + self.session._LOGGER.info( + "Skipping unknown command cmd: 0x{}, payload: {}". + format(Utils.bytes_to_hex(packet.cmd), + packet.payload)) + continue + except RuntimeError as ex: + if self.running: + self.session._LOGGER.fatal( + "Failed reading packet! {}".format(ex)) + # noinspection PyProtectedMember + self.session._reconnect() + break + + if not self.running: + break + + if cmd == Packet.Type.ping: + # noinspection PyProtectedMember + if self.session._scheduledReconnect is not None: + # noinspection PyProtectedMember + self.session._scheduler.cancel( + self.session._scheduledReconnect) + + def anonymous(): + self._LOGGER.warning( + "Socket timed out. Reconnecting...") + self.session._reconnect() + + # noinspection PyProtectedMember + self.session.scheduled_reconnect = self.session._scheduler.enter( + 2 * 60 + 5, 1, anonymous) + self.session.send(Packet.Type.pong, packet.payload) + continue + elif cmd == Packet.Type.pong_ack: + continue + elif cmd == Packet.Type.country_code: + self.session.country_code = packet.payload.decode() + self.session._LOGGER.info( + "Received country_code: {}".format( + self.session.country_code)) + continue + elif cmd == Packet.Type.license_version: + license_version = BytesInputStream(packet.payload) + license_id = license_version.read_short() + if license_id != 0: + buffer = license_version.read() + self.session._LOGGER.info( + "Received license_version: {}, {}".format( + license_id, buffer.decode())) + else: + self.session._LOGGER.info( + "Received license_version: {}".format(license_id)) + continue + elif cmd == Packet.Type.unknown_0x10: + self.session._LOGGER.debug("Received 0x10: {}".format( + Utils.bytes_to_hex(packet.payload))) + continue + elif cmd == Packet.Type.mercury_sub or \ + cmd == Packet.Type.mercury_unsub or \ + cmd == Packet.Type.mercury_event or \ + cmd == Packet.Type.mercury_req: + self.session.mercury().dispatch(packet) + continue + elif cmd == Packet.Type.aes_key or \ + cmd == Packet.Type.aes_key_error: + self.session.audio_key().dispatch(packet) + continue + elif cmd == Packet.Type.channel_error or \ + cmd == Packet.Type.stream_chunk_res: + self.session.channel().dispatch(packet) + continue + elif cmd == Packet.Type.product_info: + # noinspection PyProtectedMember + self.session._parse_product_info(packet.payload) + continue + else: + self.session._LOGGER.info("Skipping {}".format( + Utils.bytes_to_hex(cmd))) + + self.session._LOGGER.debug("Session.Receiver stopped") diff --git a/src/librespot/core/TimeProvider.py b/src/librespot/core/TimeProvider.py new file mode 100644 index 0000000..34ea289 --- /dev/null +++ b/src/librespot/core/TimeProvider.py @@ -0,0 +1,36 @@ +import math +import time + + +class TimeProvider: + offset = 0 + method = 0x00 + + def init(self, conf=None, session=None): + if conf is None and session is None: + return + if conf is not None: + self.method = conf.time_synchronization_method + if conf.time_synchronization_method == TimeProvider.Method.ntp: + self.update_with_ntp() + if conf.time_synchronization_method == TimeProvider.Method.manual: + self.offset = conf.time_manual_correction + if session is not None: + if self.method != TimeProvider.Method.melody: + return + self.update_melody(session) + + def current_time_millis(self): + return math.floor(time.time() * 1000) + self.offset + + def update_melody(self, session): + pass + + def update_with_ntp(self): + pass + + class Method: + ntp = 0x00 + ping = 0x01 + melody = 0x02 + manual = 0x03 diff --git a/src/librespot/core/TokenProvider.py b/src/librespot/core/TokenProvider.py new file mode 100644 index 0000000..56913cf --- /dev/null +++ b/src/librespot/core/TokenProvider.py @@ -0,0 +1,84 @@ +from __future__ import annotations +from librespot.core import Session, TimeProvider +from librespot.mercury import MercuryRequests +import logging + + +class TokenProvider: + _LOGGER: logging = logging.getLogger(__name__) + _TOKEN_EXPIRE_THRESHOLD = 10 + _session: Session = None + _tokens: list[TokenProvider.StoredToken] = [] + + def __init__(self, session: Session): + self._session = session + + def find_token_with_all_scopes( + self, scopes: list[str]) -> TokenProvider.StoredToken: + for token in self._tokens: + if token.has_scopes(scopes): + return token + + # noinspection PyTypeChecker + return None + + def get_token(self, *scopes) -> TokenProvider.StoredToken: + scopes = list(scopes) + if len(scopes) == 0: + raise RuntimeError() + + token = self.find_token_with_all_scopes(scopes) + if token is not None: + if token.expired(): + self._tokens.remove(token) + else: + return token + + self._LOGGER.debug( + "Token expired or not suitable, requesting again. scopes: {}, old_token: {}" + .format(scopes, token)) + resp = self._session.mercury().send_sync_json( + MercuryRequests.request_token(self._session.device_id(), + ",".join(scopes))) + token = TokenProvider.StoredToken(resp) + + self._LOGGER.debug( + "Updated token successfully! scopes: {}, new_token: {}".format( + scopes, token)) + self._tokens.append(token) + + return token + + def get(self, scope: str) -> str: + return self.get_token(scope).access_token + + class StoredToken: + expires_in: int + access_token: str + scopes: list[str] + timestamp: int + + def __init__(self, obj): + self.timestamp = TimeProvider.TimeProvider().current_time_millis() + self.expires_in = obj["expiresIn"] + self.access_token = obj["accessToken"] + self.scopes = obj["scope"] + + def expired(self) -> bool: + return self.timestamp + ( + self.expires_in - TokenProvider._TOKEN_EXPIRE_THRESHOLD + ) * 1000 < TimeProvider.TimeProvider().current_time_millis() + + def has_scope(self, scope: str) -> bool: + for s in self.scopes: + if s == scope: + return True + + return False + + def has_scopes(self, sc: list[str]) -> bool: + for s in sc: + if not self.has_scope(s): + return False + + return True diff --git a/src/librespot/core/__init__.py b/src/librespot/core/__init__.py new file mode 100644 index 0000000..81e08d5 --- /dev/null +++ b/src/librespot/core/__init__.py @@ -0,0 +1,7 @@ +from librespot.core.ApResolver import ApResolver +from librespot.core.EventService import EventService +from librespot.core.PacketsReceiver import PacketsReceiver +from librespot.core.SearchManager import SearchManager +from librespot.core.Session import Session +from librespot.core.TimeProvider import TimeProvider +from librespot.core.TokenProvider import TokenProvider diff --git a/src/librespot/crypto/CipherPair.py b/src/librespot/crypto/CipherPair.py new file mode 100644 index 0000000..8725101 --- /dev/null +++ b/src/librespot/crypto/CipherPair.py @@ -0,0 +1,62 @@ +from librespot.crypto.Packet import Packet +from librespot.crypto.Shannon import Shannon +import struct + + +class CipherPair: + send_cipher: Shannon + receive_cipher: Shannon + send_nonce = 0 + receive_nonce = 0 + + def __init__(self, send_key: bytes, receive_key: bytes): + # self.send_cipher = Shannon() + # self.send_cipher.key(send_key) + self.send_cipher = Shannon(send_key) + self.send_nonce = 0 + + # self.receive_cipher = Shannon() + # self.receive_cipher.key(receive_key) + self.receive_cipher = Shannon(receive_key) + self.receive_nonce = 0 + + def send_encoded(self, conn, cmd: bytes, payload: bytes): + self.send_cipher.nonce(self.send_nonce) + self.send_nonce += 1 + + buffer = b"" + buffer += cmd + buffer += struct.pack(">H", len(payload)) + buffer += payload + + buffer = self.send_cipher.encrypt(buffer) + + # mac = self.send_cipher.finish(bytes(4)) + mac = self.send_cipher.finish(4) + + conn.write(buffer) + conn.write(mac) + conn.flush() + + def receive_encoded(self, conn) -> Packet: + try: + self.receive_cipher.nonce(self.receive_nonce) + self.receive_nonce += 1 + + header_bytes = self.receive_cipher.decrypt(conn.read(3)) + + cmd = struct.pack(">s", bytes([header_bytes[0]])) + payload_length = (header_bytes[1] << 8) | (header_bytes[2] & 0xff) + + payload_bytes = self.receive_cipher.decrypt( + conn.read(payload_length)) + + mac = conn.read(4) + + expected_mac = self.receive_cipher.finish(4) + if mac != expected_mac: + raise RuntimeError() + + return Packet(cmd, payload_bytes) + except IndexError: + raise RuntimeError() diff --git a/src/librespot/crypto/DiffieHellman.py b/src/librespot/crypto/DiffieHellman.py new file mode 100644 index 0000000..16fe59a --- /dev/null +++ b/src/librespot/crypto/DiffieHellman.py @@ -0,0 +1,38 @@ +from binascii import unhexlify +from librespot.common.Utils import Utils +import os +import struct + + +class DiffieHellman: + prime_bytes: bytearray = bytes([ + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc9, 0x0f, 0xda, 0xa2, + 0x21, 0x68, 0xc2, 0x34, 0xc4, 0xc6, 0x62, 0x8b, 0x80, 0xdc, 0x1c, 0xd1, + 0x29, 0x02, 0x4e, 0x08, 0x8a, 0x67, 0xcc, 0x74, 0x02, 0x0b, 0xbe, 0xa6, + 0x3b, 0x13, 0x9b, 0x22, 0x51, 0x4a, 0x08, 0x79, 0x8e, 0x34, 0x04, 0xdd, + 0xef, 0x95, 0x19, 0xb3, 0xcd, 0x3a, 0x43, 0x1b, 0x30, 0x2b, 0x0a, 0x6d, + 0xf2, 0x5f, 0x14, 0x37, 0x4f, 0xe1, 0x35, 0x6d, 0x6d, 0x51, 0xc2, 0x45, + 0xe4, 0x85, 0xb5, 0x76, 0x62, 0x5e, 0x7e, 0xc6, 0xf4, 0x4c, 0x42, 0xe9, + 0xa6, 0x3a, 0x36, 0x20, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff + ]) + prime: int = int.from_bytes(prime_bytes, "big") + private_key: int + public_key: int + + def __init__(self): + key_data = os.urandom(95) + self.private_key = int.from_bytes(key_data, "big") + self.public_key = pow(2, self.private_key, self.prime) + + def compute_shared_key(self, remote_key_bytes: bytes): + remote_key = int.from_bytes(remote_key_bytes, "big") + return pow(remote_key, self.private_key, self.prime) + + def private_key(self): + return self.private_key + + def public_key(self): + return self.public_key + + def public_key_array(self): + return Utils.to_byte_array(self.public_key) diff --git a/src/librespot/crypto/Packet.py b/src/librespot/crypto/Packet.py new file mode 100644 index 0000000..97d7216 --- /dev/null +++ b/src/librespot/crypto/Packet.py @@ -0,0 +1,66 @@ +import re + + +class Packet: + cmd: bytes + payload: bytes + + def __init__(self, cmd: bytes, payload: bytes): + self.cmd = cmd + self.payload = payload + + def is_cmd(self, cmd: bytes): + return cmd == self.cmd + + class Type: + secret_block = b"\x02" + ping = b"\x04" + stream_chunk = b"\x08" + stream_chunk_res = b"\x09" + channel_error = b"\x0a" + channel_abort = b"\x0b" + request_key = b"\x0c" + aes_key = b"\x0d" + aes_key_error = b"\x0e" + image = b"\x19" + country_code = b"\x1b" + pong = b"\x49" + pong_ack = b"\x4a" + pause = b"\x4b" + product_info = b"\x50" + legacy_welcome = b"\x69" + license_version = b"\x76" + login = b"\xab" + ap_welcome = b"\xac" + auth_failure = b"\xad" + mercury_req = b"\xb2" + mercury_sub = b"\xb3" + mercury_unsub = b"\xb4" + mercury_event = b"\xb5" + track_ended_time = b"\x82" + unknown_data_all_zeros = b"\x1f" + preferred_locale = b"\x74" + unknown_0x4f = b"\x4f" + unknown_0x0f = b"\x0f" + unknown_0x10 = b"\x10" + + @staticmethod + def parse(val: bytes): + for cmd in [ + Packet.Type.__dict__[attr] + for attr in Packet.Type.__dict__.keys() + if re.search("__.+?__", attr) is None + and type(Packet.Type.__dict__[attr]) is bytes + ]: + if cmd == val: + return cmd + + return None + + @staticmethod + def for_method(method: str): + if method == "SUB": + return Packet.Type.mercury_sub + if method == "UNSUB": + return Packet.Type.mercury_unsub + return Packet.Type.mercury_req diff --git a/src/librespot/crypto/Shannon.py b/src/librespot/crypto/Shannon.py new file mode 100644 index 0000000..974bd52 --- /dev/null +++ b/src/librespot/crypto/Shannon.py @@ -0,0 +1,495 @@ +""" + Shannon: Shannon stream cipher and MAC -- reference implementation, ported from C code written by Greg Rose + https://github.com/sashahilton00/spotify-connect-resources/blob/master/Shannon-1.0/ShannonRef.c + + Copyright 2017, Dmitry Borisov + + THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED + WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF + MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE AND AGAINST + INFRINGEMENT ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR + CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +""" + +import struct, \ + copy + +# Constants +N = 16 +INITKONST = 0x6996c53a +KEYP = 13 # where to insert key/MAC/counter words +FOLD = N # how many iterations of folding to do + + +class Shannon: + @staticmethod + def ROTL(w, x): + return ((w << x) | (w >> (32 - x))) & 0xFFFFFFFF + + @staticmethod + def ROTR(w, x): + return ((w >> x) | (w << (32 - x))) & 0xFFFFFFFF + + """ Nonlinear transform (sbox) of a word. + There are two slightly different combinations. """ + + @staticmethod + def sbox1(w): + w ^= Shannon.ROTL(w, 5) | Shannon.ROTL(w, 7) + w ^= Shannon.ROTL(w, 19) | Shannon.ROTL(w, 22) + return w + + """ Nonlinear transform (sbox) of a word. + There are two slightly different combinations. """ + + @staticmethod + def sbox2(w): + w ^= Shannon.ROTL(w, 7) | Shannon.ROTL(w, 22) + w ^= Shannon.ROTL(w, 5) | Shannon.ROTL(w, 19) + return w + + """ initialise to known state """ + + def _initstate(self): + global N, \ + INITKONST + + # Generate fibonacci numbers up to N + self._R = [1, 1] + for x in range(1, N - 1): + self._R.append(self._R[x] + self._R[x - 1]) + + self._konst = INITKONST + + """ cycle the contents of the register and calculate output word in _sbuf. """ + + def _cycle(self): + # nonlinear feedback function + t = self._R[12] ^ self._R[13] ^ self._konst + t = Shannon.sbox1(t) ^ Shannon.ROTL(self._R[0], 1) + + # Shift to the left + self._R = self._R[1:] + [t] + t = Shannon.sbox2(self._R[2] ^ self._R[15]) + self._R[0] ^= t + self._sbuf = t ^ self._R[8] ^ self._R[12] + + """ The Shannon MAC function is modelled after the concepts of Phelix and SHA. + Basically, words to be accumulated in the MAC are incorporated in two + different ways: + 1. They are incorporated into the stream cipher register at a place + where they will immediately have a nonlinear effect on the state + 2. They are incorporated into bit-parallel CRC-16 registers; the + contents of these registers will be used in MAC finalization. """ + """ Accumulate a CRC of input words, later to be fed into MAC. + This is actually 32 parallel CRC-16s, using the IBM CRC-16 + polynomial x^16 + x^15 + x^2 + 1. """ + + def _crcfunc(self, i): + t = self._CRC[0] ^ self._CRC[2] ^ self._CRC[15] ^ i + # Accumulate CRC of input + self._CRC = self._CRC[1:] + [t] + + """ Normal MAC word processing: do both stream register and CRC. """ + + def _macfunc(self, i): + global KEYP + + self._crcfunc(i) + self._R[KEYP] ^= i + + """ extra nonlinear diffusion of register for key and MAC """ + + def _diffuse(self): + global FOLD + + for i in range(FOLD): + self._cycle() + + """ Common actions for loading key material + Allow non-word-multiple key and nonce material. + Note also initializes the CRC register as a side effect. """ + + def _loadkey(self, key): + global KEYP, \ + N + + # Pad key with 00s to align on 4 bytes and add key_len + padding_size = int((len(key) + 3) / 4) * 4 - len(key) + key = key + (b'\x00' * padding_size) + struct.pack("I", nonce)) + + self._R = copy.copy(self._initR) + self._konst = INITKONST + self._loadkey(nonce) + self._konst = self._R[0] + self._nbuf = 0 + self._mbuf = 0 + + """ Encrypt small chunk """ + + def _encrypt_chunk(self, chunk): + result = [] + for c in chunk: + self._mbuf ^= c << (32 - self._nbuf) + result.append(c ^ (self._sbuf >> (32 - self._nbuf)) & 0xFF) + self._nbuf -= 8 + + return result + + """ Combined MAC and encryption. + Note that plaintext is accumulated for MAC. """ + + def encrypt(self, buf): + # handle any previously buffered bytes + result = [] + if self._nbuf != 0: + head = buf[:(self._nbuf >> 3)] + buf = buf[(self._nbuf >> 3):] + result = self._encrypt_chunk(head) + if self._nbuf != 0: + return bytes(result) + + # LFSR already cycled + self._macfunc(self._mbuf) + + # Handle body + i = 0 + while len(buf) >= 4: + self._cycle() + t = struct.unpack("> (32 - self._nbuf)) & 0xFF)) + self._mbuf ^= result[-1] << (32 - self._nbuf) + self._nbuf -= 8 + + return result + + """ Combined MAC and decryption. + Note that plaintext is accumulated for MAC. """ + + def decrypt(self, buf): + # handle any previously buffered bytes + result = [] + if self._nbuf != 0: + head = buf[:(self._nbuf >> 3)] + buf = buf[(self._nbuf >> 3):] + result = self._decrypt_chunk(head) + if self._nbuf != 0: + return bytes(result) + + # LFSR already cycled + self._macfunc(self._mbuf) + + # Handle whole words + i = 0 + while len(buf) >= 4: + self._cycle() + t = struct.unpack(">= 8 + + return bytes(result) + + +if __name__ == '__main__': + TESTSIZE = 23 + TEST_KEY = b"test key 128bits" + TEST_PHRASE = b'\x00' * 20 + + sh = Shannon( + bytes([ + 133, 199, 15, 101, 207, 100, 229, 237, 15, 249, 248, 155, 76, 170, + 62, 189, 239, 251, 147, 213, 22, 186, 157, 47, 218, 198, 235, 14, + 171, 50, 11, 121 + ])) + sh.set_nonce(0) + p1 = sh.decrypt( + bytes([ + 235, + 94, + 210, + 19, + 246, + 203, + 195, + 35, + 22, + 215, + 80, + 69, + 158, + 247, + 110, + 146, + 241, + 101, + 199, + 37, + 67, + 92, + 5, + 197, + 112, + 244, + 77, + 185, + 197, + 118, + 119, + 56, + 164, + 246, + 159, + 242, + 56, + 200, + 39, + 27, + 141, + 191, + 37, + 244, + 244, + 164, + 44, + 250, + 59, + 227, + 245, + 155, + 239, + 155, + 137, + 85, + 244, + 29, + 52, + 233, + 180, + 119, + 166, + 46, + 252, + 24, + 141, + 20, + 135, + 73, + 144, + 10, + 176, + 79, + 88, + 228, + 140, + 62, + 173, + 192, + 117, + 116, + 152, + 182, + 246, + 183, + 88, + 90, + 73, + 51, + 159, + 83, + 227, + 222, + 140, + 48, + 157, + 137, + 185, + 131, + 201, + 202, + 122, + 112, + 207, + 231, + 153, + 155, + 9, + 163, + 225, + 73, + 41, + 252, + 249, + 65, + 33, + 102, + 83, + 100, + 36, + 115, + 174, + 191, + 43, + 250, + 113, + 229, + 146, + 47, + 154, + 175, + 55, + 101, + 73, + 164, + 49, + 234, + 103, + 32, + 53, + 190, + 236, + 47, + 210, + 78, + 141, + 0, + 176, + 255, + 79, + 151, + 159, + 66, + 20, + ])) + print([hex(x) for x in p1]) + print([hex(x) for x in sh.finish(4)]) + sh.set_nonce(1) + print([hex(x) for x in sh.decrypt(bytes([173, 184, 50]))]) + + sh = Shannon(TEST_KEY) + sh.set_nonce(0) + encr = [sh.encrypt(bytes([x])) for x in TEST_PHRASE] + print('Encrypted 1-by-1 (len %d)' % len(encr), [hex(x[0]) for x in encr]) + print(' sbuf %08x' % sh._sbuf) + print(' MAC', [hex(x) for x in sh.finish(4)]) + + sh.set_nonce(0) + encr = sh.encrypt(TEST_PHRASE) + print('Encrypted whole (len %d)' % len(encr), [hex(x) for x in encr]) + print(' sbuf %08x' % sh._sbuf) + print(' MAC', [hex(x) for x in sh.finish(4)]) + + sh.set_nonce(0) + print('Decrypted whole', [hex(x) for x in sh.decrypt(encr)]) + print(' MAC', [hex(x) for x in sh.finish(4)]) + + sh.set_nonce(0) + decr = [sh.decrypt(bytes([x])) for x in encr] + print('Decrypted 1-by-1', [hex(x[0]) for x in decr]) + print(' MAC', [hex(x) for x in sh.finish(4)]) diff --git a/src/librespot/crypto/Shannon_DEV.py b/src/librespot/crypto/Shannon_DEV.py new file mode 100644 index 0000000..c8a80cc --- /dev/null +++ b/src/librespot/crypto/Shannon_DEV.py @@ -0,0 +1,311 @@ +import struct + + +class Shannon: + n = 16 + fold = n + initkonst = 0x6996c53a + keyp = 13 + + r: list + crc: list + initr: list + konst: int + sbuf: int + mbuf: int + nbuf: int + + def __init__(self): + self.r = [0 for _ in range(self.n)] + self.crc = [0 for _ in range(self.n)] + self.initr = [0 for _ in range(self.n)] + + def rotl(self, i: int, distance: int): + return ((i << distance) | (i >> (32 - distance))) & 0xffffffff + + def sbox(self, i: int): + i ^= self.rotl(i, 5) | self.rotl(i, 7) + i ^= self.rotl(i, 19) | self.rotl(i, 22) + + return i + + def sbox2(self, i: int): + i ^= self.rotl(i, 7) | self.rotl(i, 22) + i ^= self.rotl(i, 5) | self.rotl(i, 19) + + return i + + def cycle(self): + t: int + + t = self.r[12] ^ self.r[13] ^ self.konst + t = self.sbox(t) ^ self.rotl(self.r[0], 1) + + for i in range(1, self.n): + self.r[i - 1] = self.r[i] + + self.r[self.n - 1] = t + + t = self.sbox2(self.r[2] ^ self.r[15]) + self.r[0] ^= t + self.sbuf = t ^ self.r[8] ^ self.r[12] + + def crc_func(self, i: int): + t: int + + t = self.crc[0] ^ self.crc[2] ^ self.crc[15] ^ i + + for j in range(1, self.n): + self.crc[j - 1] = self.crc[j] + + self.crc[self.n - 1] = t + + def mac_func(self, i: int): + self.crc_func(i) + + self.r[self.keyp] ^= i + + def init_state(self): + self.r[0] = 1 + self.r[1] = 1 + + for i in range(2, self.n): + self.r[i] = self.r[i - 1] + self.r[i - 2] + + self.konst = self.initkonst + + def save_state(self): + for i in range(self.n): + self.initr[i] = self.r[i] + + def reload_state(self): + for i in range(self.n): + self.r[i] = self.initr[i] + + def gen_konst(self): + self.konst = self.r[0] + + def add_key(self, k: int): + self.r[self.keyp] ^= k + + def diffuse(self): + for i in range(self.fold): + self.cycle() + + def load_key(self, key: bytes): + extra = bytearray(4) + i: int + j: int + t: int + + padding_size = int((len(key) + 3) / 4) * 4 - len(key) + key = key + (b"\x00" * padding_size) + struct.pack("> (32 - self.nbuf)) & 0xff + + i += 1 + + self.nbuf -= 8 + + n -= 1 + + if self.nbuf != 0: + return + + self.mac_func(self.mbuf) + + j = n & ~0x03 + + while i < j: + self.cycle() + + t = ((buffer[i + 3] & 0xFF) << 24) | \ + ((buffer[i + 2] & 0xFF) << 16) | \ + ((buffer[i + 1] & 0xFF) << 8) | \ + (buffer[i] & 0xFF) + + self.mac_func(t) + + t ^= self.sbuf + + buffer[i + 3] = (t >> 24) & 0xFF + buffer[i + 2] = (t >> 16) & 0xFF + buffer[i + 3] = (t >> 8) & 0xFF + buffer[i] = t & 0xFF + + i += 4 + + n &= 0x03 + + if n != 0: + self.cycle() + + self.mbuf = 0 + self.nbuf = 32 + + while self.nbuf != 0 and n != 0: + self.mbuf ^= (buffer[i] & 0xff) << (32 - self.nbuf) + buffer[i] ^= (self.sbuf >> (32 - self.nbuf)) & 0xff + + i += 1 + + self.nbuf -= 8 + + n -= 1 + return bytes(buffer) + + def decrypt(self, buffer: bytes, n: int = None): + if n is None: + return self.decrypt(buffer, len(buffer)) + + buffer = bytearray(buffer) + + i = 0 + j: int + t: int + + if self.nbuf != 0: + while self.nbuf != 0 and n != 0: + buffer[i] ^= (self.sbuf >> (32 - self.nbuf)) & 0xff + self.mbuf ^= (buffer[i] & 0xff) << (32 - self.nbuf) + + i += 1 + + self.nbuf -= 8 + + n -= 1 + + if self.nbuf != 0: + return + + self.mac_func(self.mbuf) + + j = n & ~0x03 + + while i < j: + self.cycle() + + t = ((buffer[i + 3] & 0xFF) << 24) | \ + ((buffer[i + 2] & 0xFF) << 16) | \ + ((buffer[i + 1] & 0xFF) << 8) | \ + (buffer[i] & 0xFF) + + t ^= self.sbuf + + self.mac_func(t) + + buffer[i + 3] = (t >> 24) & 0xFF + buffer[i + 2] = (t >> 16) & 0xFF + buffer[i + 1] = (t >> 8) & 0xFF + buffer[i] = t & 0xFF + + i += 4 + + n &= 0x03 + + if n != 0: + self.cycle() + + self.mbuf = 0 + self.nbuf = 32 + + while self.nbuf != 0 and n != 0: + buffer[i] ^= (self.sbuf >> (32 - self.nbuf)) & 0xff + self.mbuf ^= (buffer[i] & 0xff) << (32 - self.nbuf) + + i += 1 + + self.nbuf -= 8 + + n -= 1 + + return bytes(buffer) + + def finish(self, buffer: bytes, n: int = None): + if n is None: + return self.finish(buffer, len(buffer)) + + buffer = bytearray(buffer) + + i = 0 + j: int + + if self.nbuf != 0: + self.mac_func(self.mbuf) + + self.cycle() + self.add_key(self.initkonst ^ (self.nbuf << 3)) + + self.nbuf = 0 + + for j in range(self.n): + self.r[j] ^= self.crc[j] + + self.diffuse() + + while n > 0: + self.cycle() + + if n >= 4: + buffer[i + 3] = (self.sbuf >> 24) & 0xff + buffer[i + 2] = (self.sbuf >> 16) & 0xff + buffer[i + 1] = (self.sbuf >> 8) & 0xff + buffer[i] = self.sbuf & 0xff + + n -= 4 + i += 4 + else: + for j in range(n): + buffer[i + j] = (self.sbuf >> (i * 8)) & 0xff + break + return bytes(buffer) diff --git a/src/librespot/crypto/__init__.py b/src/librespot/crypto/__init__.py new file mode 100644 index 0000000..3fbf182 --- /dev/null +++ b/src/librespot/crypto/__init__.py @@ -0,0 +1,4 @@ +from librespot.crypto.CipherPair import CipherPair +from librespot.crypto.DiffieHellman import DiffieHellman +from librespot.crypto.Packet import Packet +from librespot.crypto.Shannon import Shannon diff --git a/src/librespot/dealer/ApiClient.py b/src/librespot/dealer/ApiClient.py new file mode 100644 index 0000000..cf5efb6 --- /dev/null +++ b/src/librespot/dealer/ApiClient.py @@ -0,0 +1,129 @@ +from librespot.core.ApResolver import ApResolver +from librespot.metadata import AlbumId, ArtistId, EpisodeId, TrackId, ShowId +from librespot.proto import Connect, Metadata +from librespot.standard import Closeable +from typing import Union +import logging +import requests + + +class ApiClient(Closeable): + _LOGGER: logging = logging.getLogger(__name__) + _session = None + _baseUrl: str = None + + def __init__(self, session): + self._session = session + self._baseUrl = "https://{}".format(ApResolver.get_random_spclient()) + + def build_request(self, method: str, suffix: str, + headers: Union[None, dict[str, str]], + body: Union[None, bytes]) -> requests.PreparedRequest: + request = requests.PreparedRequest() + request.method = method + request.data = body + request.headers = {} + if headers is not None: + request.headers = headers + request.headers["Authorization"] = "Bearer {}".format( + self._session.tokens().get("playlist-read")) + request.url = self._baseUrl + suffix + return request + + def send(self, method: str, suffix: str, headers: Union[None, dict[str, + str]], + body: Union[None, bytes]) -> requests.Response: + resp = self._session.client().send( + self.build_request(method, suffix, headers, body)) + return resp + + def put_connect_state(self, connection_id: str, + proto: Connect.PutStateRequest) -> None: + resp = self.send( + "PUT", + "/connect-state/v1/devices/{}".format(self._session.device_id()), { + "Content-Type": "application/protobuf", + "X-Spotify-Connection-Id": connection_id + }, proto.SerializeToString()) + + if resp.status_code == 413: + self._LOGGER.warning( + "PUT state payload is too large: {} bytes uncompressed.". + format(len(proto.SerializeToString()))) + elif resp.status_code != 200: + self._LOGGER.warning("PUT state returned {}. headers: {}".format( + resp.status_code, resp.headers)) + + def get_metadata_4_track(self, track: TrackId) -> Metadata.Track: + resp = self.send("GET", "/metadata/4/track/{}".format(track.hex_id()), + None, None) + ApiClient.StatusCodeException.check_status(resp) + + body = resp.content + if body is None: + raise RuntimeError() + proto = Metadata.Track() + proto.ParseFromString(body) + return proto + + def get_metadata_4_episode(self, episode: EpisodeId) -> Metadata.Episode: + resp = self.send("GET", + "/metadata/4/episode/{}".format(episode.hex_id()), + None, None) + ApiClient.StatusCodeException.check_status(resp) + + body = resp.content + if body is None: + raise IOError() + proto = Metadata.Episode() + proto.ParseFromString(body) + return proto + + def get_metadata_4_album(self, album: AlbumId) -> Metadata.Album: + resp = self.send("GET", "/metadata/4/album/{}".format(album.hex_id()), + None, None) + ApiClient.StatusCodeException.check_status(resp) + + body = resp.content + if body is None: + raise IOError() + proto = Metadata.Album() + proto.ParseFromString(body) + return proto + + def get_metadata_4_artist(self, artist: ArtistId) -> Metadata.Artist: + resp = self.send("GET", + "/metadata/4/artist/{}".format(artist.hex_id()), None, + None) + ApiClient.StatusCodeException.check_status(resp) + + body = resp.content + if body is None: + raise IOError() + proto = Metadata.Artist() + proto.ParseFromString(body) + return proto + + def get_metadata_4_show(self, show: ShowId) -> Metadata.Show: + resp = self.send("GET", "/metadata/4/show/{}".format(show.hex_id()), + None, None) + ApiClient.StatusCodeException.check_status(resp) + + body = resp.content + if body is None: + raise IOError() + proto = Metadata.Show() + proto.ParseFromString(body) + return proto + + class StatusCodeException(IOError): + code: int + + def __init__(self, resp: requests.Response): + super().__init__(resp.status_code) + self.code = resp.status_code + + @staticmethod + def check_status(resp: requests.Response) -> None: + if resp.status_code != 200: + raise ApiClient.StatusCodeException(resp) diff --git a/src/librespot/dealer/DealerClient.py b/src/librespot/dealer/DealerClient.py new file mode 100644 index 0000000..bfac3ad --- /dev/null +++ b/src/librespot/dealer/DealerClient.py @@ -0,0 +1,19 @@ +from __future__ import annotations +from librespot.standard.Closeable import Closeable + + +class DealerClient(Closeable): + def __init__(self, session): + pass + + def connect(self): + pass + + def add_message_listener(self, listener: DealerClient.MessageListener, + *uris: str): + pass + + class MessageListener: + def on_message(self, uri: str, headers: dict[str, str], + payload: bytes): + pass diff --git a/src/librespot/dealer/__init__.py b/src/librespot/dealer/__init__.py new file mode 100644 index 0000000..93f259c --- /dev/null +++ b/src/librespot/dealer/__init__.py @@ -0,0 +1,2 @@ +from librespot.dealer.ApiClient import ApResolver +from librespot.dealer.DealerClient import DealerClient diff --git a/src/librespot/mercury/JsonMercuryRequest.py b/src/librespot/mercury/JsonMercuryRequest.py new file mode 100644 index 0000000..6eaeb51 --- /dev/null +++ b/src/librespot/mercury/JsonMercuryRequest.py @@ -0,0 +1,5 @@ +class JsonMercuryRequest: + request = None + + def __init__(self, request): + self.request = request diff --git a/src/librespot/mercury/MercuryClient.py b/src/librespot/mercury/MercuryClient.py new file mode 100644 index 0000000..64be030 --- /dev/null +++ b/src/librespot/mercury/MercuryClient.py @@ -0,0 +1,256 @@ +from __future__ import annotations +from librespot.common import Utils +from librespot.core import Session, PacketsReceiver +from librespot.crypto import Packet +from librespot.mercury import JsonMercuryRequest, RawMercuryRequest, SubListener +from librespot.standard import BytesInputStream, BytesOutputStream, Closeable +from librespot.proto import Mercury, Pubsub +import json +import logging +import queue +import threading +import typing + + +class MercuryClient(PacketsReceiver.PacketsReceiver, Closeable): + _LOGGER: logging = logging.getLogger(__name__) + _MERCURY_REQUEST_TIMEOUT: int = 3 + _seqHolder: int = 1 + _seqHolderLock: threading.Condition = threading.Condition() + _callbacks: dict[int, Callback] = dict() + _removeCallbackLock: threading.Condition = threading.Condition() + _subscriptions: list[MercuryClient.InternalSubListener] = list() + _subscriptionsLock: threading.Condition = threading.Condition() + _partials: dict[int, bytes] = dict() + _session: Session = None + + def __init__(self, session: Session): + self._session = session + + def subscribe(self, uri: str, listener: SubListener) -> None: + response = self.send_sync(RawMercuryRequest.sub(uri)) + if response.status_code != 200: + raise RuntimeError(response) + + if len(response.payload) > 0: + for payload in response.payload: + sub = Pubsub.Subscription() + sub.ParseFromString(payload) + self._subscriptions.append( + MercuryClient.InternalSubListener(sub.uri, listener, True)) + else: + self._subscriptions.append( + MercuryClient.InternalSubListener(uri, listener, True)) + + self._LOGGER.debug("Subscribed successfully to {}!".format(uri)) + + def unsubscribe(self, uri) -> None: + response = self.send_sync(RawMercuryRequest.unsub(uri)) + if response.status_code != 200: + raise RuntimeError(response) + + for subscription in self._subscriptions: + if subscription.matches(uri): + self._subscriptions.remove(subscription) + break + self._LOGGER.debug("Unsubscribed successfully from {}!".format(uri)) + + def send_sync(self, request: RawMercuryRequest) -> MercuryClient.Response: + callback = MercuryClient.SyncCallback() + seq = self.send(request, callback) + + try: + resp = callback.wait_response() + if resp is None: + raise IOError( + "Request timeout out, {} passed, yet no response. seq: {}". + format(self._MERCURY_REQUEST_TIMEOUT, seq)) + return resp + except queue.Empty as e: + raise IOError(e) + + def send_sync_json(self, request: JsonMercuryRequest) -> typing.Any: + resp = self.send_sync(request.request) + if 200 <= resp.status_code < 300: + return json.loads(resp.payload[0]) + else: + raise MercuryClient.MercuryException(resp) + + def send(self, request: RawMercuryRequest, callback) -> int: + buffer = BytesOutputStream() + + seq: int + with self._seqHolderLock: + seq = self._seqHolder + self._seqHolder += 1 + + self._LOGGER.debug( + "Send Mercury request, seq: {}, uri: {}, method: {}".format( + seq, request.header.uri, request.header.method)) + + buffer.write_short(4) + buffer.write_int(seq) + + buffer.write_byte(1) + buffer.write_short(1 + len(request.payload)) + + header_bytes = request.header.SerializeToString() + buffer.write_short(len(header_bytes)) + buffer.write(header_bytes) + + for part in request.payload: + buffer.write_short(len(part)) + buffer.write(part) + + cmd = Packet.Type.for_method(request.header.method) + self._session.send(cmd, buffer.buffer) + + self._callbacks[seq] = callback + return seq + + def dispatch(self, packet: Packet) -> None: + payload = BytesInputStream(packet.payload) + seq_length = payload.read_short() + if seq_length == 2: + seq = payload.read_short() + elif seq_length == 4: + seq = payload.read_int() + elif seq_length == 8: + seq = payload.read_long() + else: + raise RuntimeError("Unknown seq length: {}".format(seq_length)) + + flags = payload.read_byte() + parts = payload.read_short() + + partial = self._partials.get(seq) + if partial is None or flags == 0: + partial = [] + self._partials[seq] = partial + + self._LOGGER.debug( + "Handling packet, cmd: 0x{}, seq: {}, flags: {}, parts: {}".format( + Utils.bytes_to_hex(packet.cmd), seq, flags, parts)) + + for i in range(parts): + size = payload.read_short() + buffer = payload.read(size) + partial.append(buffer) + self._partials[seq] = partial + + if flags != b"\x01": + return + + self._partials.pop(seq) + + header = Mercury.Header() + header.ParseFromString(partial[0]) + + resp = MercuryClient.Response(header, partial) + + if packet.is_cmd(Packet.Type.mercury_event): + dispatched = False + with self._subscriptionsLock: + for sub in self._subscriptions: + if sub.matches(header.uri): + sub.dispatch(resp) + dispatched = True + + if not dispatched: + self._LOGGER.debug( + "Couldn't dispatch Mercury event seq: {}, uri: {}, code: {}, payload: {}" + .format(seq, header.uri, header.status_code, resp.payload)) + elif packet.is_cmd(Packet.Type.mercury_req) or \ + packet.is_cmd(Packet.Type.mercury_sub) or \ + packet.is_cmd(Packet.Type.mercury_sub): + callback = self._callbacks.get(seq) + self._callbacks.pop(seq) + if callback is not None: + callback.response(resp) + else: + self._LOGGER.warning( + "Skipped Mercury response, seq: {}, uri: {}, code: {}". + format(seq, resp.uri, resp.status_code)) + + with self._removeCallbackLock: + self._removeCallbackLock.notify_all() + else: + self._LOGGER.warning( + "Couldn't handle packet, seq: {}, uri: {}, code: {}".format( + seq, header.uri, header.status_code)) + + def interested_in(self, uri: str, listener: SubListener) -> None: + self._subscriptions.append( + MercuryClient.InternalSubListener(uri, listener, False)) + + def not_interested_in(self, listener: SubListener) -> None: + try: + # noinspection PyTypeChecker + self._subscriptions.remove(listener) + except ValueError: + pass + + def close(self) -> None: + if len(self._subscriptions) != 0: + for listener in self._subscriptions: + if listener.isSub: + self.unsubscribe(listener.uri) + else: + self.not_interested_in(listener.listener) + + if len(self._callbacks) != 0: + with self._removeCallbackLock: + self._removeCallbackLock.wait(self._MERCURY_REQUEST_TIMEOUT) + + self._callbacks.clear() + + class Callback: + def response(self, response) -> None: + pass + + class SyncCallback(Callback): + _reference = queue.Queue() + + def response(self, response) -> None: + self._reference.put(response) + self._reference.task_done() + + def wait_response(self) -> typing.Any: + return self._reference.get( + timeout=MercuryClient._MERCURY_REQUEST_TIMEOUT) + + # class PubSubException(MercuryClient.MercuryException): + # pass + + class InternalSubListener: + uri: str + listener: SubListener + isSub: bool + + def __init__(self, uri: str, listener: SubListener, is_sub: bool): + self.uri = uri + self.listener = listener + self.isSub = is_sub + + def matches(self, uri: str) -> bool: + return uri.startswith(self.uri) + + def dispatch(self, resp: MercuryClient.Response) -> None: + self.listener.event(resp) + + class MercuryException(Exception): + code: int + + def __init__(self, response): + super("status: {}".format(response.status_code)) + self.code = response.status_code + + class Response: + uri: str + payload: list[bytes] + status_code: int + + def __init__(self, header: Mercury.Header, payload: list[bytes]): + self.uri = header.uri + self.status_code = header.status_code + self.payload = payload[1:] diff --git a/src/librespot/mercury/MercuryRequests.py b/src/librespot/mercury/MercuryRequests.py new file mode 100644 index 0000000..0694a6e --- /dev/null +++ b/src/librespot/mercury/MercuryRequests.py @@ -0,0 +1,18 @@ +from librespot.mercury.JsonMercuryRequest import JsonMercuryRequest +from librespot.mercury.RawMercuryRequest import RawMercuryRequest + + +class MercuryRequests: + keymaster_client_id = "65b708073fc0480ea92a077233ca87bd" + + @staticmethod + def get_root_playlists(username: str): + pass + + @staticmethod + def request_token(device_id, scope): + return JsonMercuryRequest( + RawMercuryRequest.get( + "hm://keymaster/token/authenticated?scope={}&client_id={}&device_id={}" + .format(scope, MercuryRequests.keymaster_client_id, + device_id))) diff --git a/src/librespot/mercury/ProtobufMercuryRequest.py b/src/librespot/mercury/ProtobufMercuryRequest.py new file mode 100644 index 0000000..c94f49f --- /dev/null +++ b/src/librespot/mercury/ProtobufMercuryRequest.py @@ -0,0 +1,7 @@ +class ProtobufMercuryRequest: + request = None + parser = None + + def __init__(self, request, parser): + self.request = request + self.parser = parser diff --git a/src/librespot/mercury/RawMercuryRequest.py b/src/librespot/mercury/RawMercuryRequest.py new file mode 100644 index 0000000..0ddfceb --- /dev/null +++ b/src/librespot/mercury/RawMercuryRequest.py @@ -0,0 +1,87 @@ +from librespot.proto import Mercury + + +class RawMercuryRequest: + header: Mercury.Header + payload: list[bytes] + + def __init__(self, header: Mercury.Header, payload: list[bytes]): + self.header = header + self.payload = payload + + @staticmethod + def sub(uri: str): + return RawMercuryRequest.new_builder().set_uri(uri).set_method( + "SUB").build() + + @staticmethod + def unsub(uri: str): + return RawMercuryRequest.new_builder().set_uri(uri).set_method( + "UNSUB").build() + + @staticmethod + def get(uri: str): + return RawMercuryRequest.new_builder().set_uri(uri).set_method( + "GET").build() + + @staticmethod + def send(uri: str, part: bytes): + return RawMercuryRequest.new_builder().set_uri(uri).add_payload_part( + part).set_method("SEND").build() + + @staticmethod + def post(uri: str, part: bytes): + return RawMercuryRequest.new_builder().set_uri(uri).set_method( + "POST").add_payload_part(part).build() + + @staticmethod + def new_builder(): + return RawMercuryRequest.Builder() + + class Builder: + header_dict: dict + payload: list[bytes] + + def __init__(self): + self.header_dict = {} + self.payload = [] + + def set_uri(self, uri: str): + self.header_dict["uri"] = uri + return self + + def set_content_type(self, content_type: str): + self.header_dict["content_type"] = content_type + return self + + def set_method(self, method: str): + self.header_dict["method"] = method + return self + + def add_user_field(self, + field: Mercury.UserField = None, + key: str = None, + value: str = None): + if field is None and (key is None or value is None): + return self + try: + self.header_dict["user_fields"] + except KeyError: + self.header_dict["user_fields"] = [] + if field is not None: + self.header_dict["user_fields"].append(field) + if key is not None and value is not None: + self.header_dict["user_fields"].append( + Mercury.UserField(key=key, value=value.encode())) + return self + + def add_payload_part(self, part: bytes): + self.payload.append(part) + return self + + def add_protobuf_payload(self, msg): + return self.add_payload_part(msg) + + def build(self): + return RawMercuryRequest(Mercury.Header(**self.header_dict), + self.payload) diff --git a/src/librespot/mercury/SubListener.py b/src/librespot/mercury/SubListener.py new file mode 100644 index 0000000..0aad578 --- /dev/null +++ b/src/librespot/mercury/SubListener.py @@ -0,0 +1,7 @@ +from __future__ import annotations +from librespot.mercury import MercuryClient + + +class SubListener: + def event(self, resp: MercuryClient.Response) -> None: + pass diff --git a/src/librespot/mercury/__init__.py b/src/librespot/mercury/__init__.py new file mode 100644 index 0000000..f58e59b --- /dev/null +++ b/src/librespot/mercury/__init__.py @@ -0,0 +1,6 @@ +from librespot.mercury.JsonMercuryRequest import JsonMercuryRequest +from librespot.mercury.MercuryClient import MercuryClient +from librespot.mercury.MercuryRequests import MercuryRequests +from librespot.mercury.ProtobufMercuryRequest import ProtobufMercuryRequest +from librespot.mercury.RawMercuryRequest import RawMercuryRequest +from librespot.mercury.SubListener import SubListener diff --git a/src/librespot/metadata/AlbumId.py b/src/librespot/metadata/AlbumId.py new file mode 100644 index 0000000..c5b2872 --- /dev/null +++ b/src/librespot/metadata/AlbumId.py @@ -0,0 +1,40 @@ +from __future__ import annotations + +from librespot.common import Base62, Utils +from librespot.metadata import SpotifyId +import re + + +class AlbumId(SpotifyId.SpotifyId): + _PATTERN = re.compile(r"spotify:album:(.{22})") + _BASE62 = Base62.create_instance_with_inverted_character_set() + _hexId: str + + def __init__(self, hex_id: str): + self._hexId = hex_id.lower() + + @staticmethod + def from_uri(uri: str) -> AlbumId: + matcher = AlbumId._PATTERN.search(uri) + if matcher is not None: + album_id = matcher.group(1) + return AlbumId( + Utils.bytes_to_hex(AlbumId._BASE62.decode(album_id, 16))) + else: + raise TypeError("Not a Spotify album ID: {}.f".format(uri)) + + @staticmethod + def from_base62(base62: str) -> AlbumId: + return AlbumId( + Utils.bytes_to_hex(AlbumId._BASE62.decode(base62, 16))) + + @staticmethod + def from_hex(hex_str: str) -> AlbumId: + return AlbumId(hex_str) + + def to_mercury_uri(self) -> str: + return "spotify:album:{}".format( + AlbumId._BASE62.encode(Utils.hex_to_bytes(self._hexId))) + + def hex_id(self) -> str: + return self._hexId diff --git a/src/librespot/metadata/ArtistId.py b/src/librespot/metadata/ArtistId.py new file mode 100644 index 0000000..1c30128 --- /dev/null +++ b/src/librespot/metadata/ArtistId.py @@ -0,0 +1,43 @@ +from __future__ import annotations +from librespot.common import Base62, Utils +from librespot.metadata import SpotifyId +import re + + +class ArtistId(SpotifyId.SpotifyId): + _PATTERN = re.compile("spotify:artist:(.{22})") + _BASE62 = Base62.create_instance_with_inverted_character_set() + _hexId: str + + def __init__(self, hex_id: str): + self._hexId = hex_id + + @staticmethod + def from_uri(uri: str) -> ArtistId: + matcher = ArtistId._PATTERN.search(uri) + if matcher is not None: + artist_id = matcher.group(1) + return ArtistId( + Utils.bytes_to_hex(ArtistId._BASE62.decode( + artist_id, 16))) + else: + raise TypeError("Not a Spotify artist ID: {}".format(uri)) + + @staticmethod + def from_base62(base62: str) -> ArtistId: + return ArtistId( + Utils.bytes_to_hex(ArtistId._BASE62.decode(base62, 16))) + + @staticmethod + def from_hex(hex_str: str) -> ArtistId: + return ArtistId(hex_str) + + def to_mercury_uri(self) -> str: + return "hm://metadata/4/artist/{}".format(self._hexId) + + def to_spotify_uri(self) -> str: + return "spotify:artist:{}".format( + ArtistId._BASE62.encode(Utils.hex_to_bytes(self._hexId))) + + def hex_id(self) -> str: + return self._hexId diff --git a/src/librespot/metadata/EpisodeId.py b/src/librespot/metadata/EpisodeId.py new file mode 100644 index 0000000..c6542ad --- /dev/null +++ b/src/librespot/metadata/EpisodeId.py @@ -0,0 +1,46 @@ +from __future__ import annotations +from librespot.common import Utils +from librespot.metadata import SpotifyId +from librespot.metadata.PlayableId import PlayableId +import re + + +class EpisodeId(SpotifyId.SpotifyId, PlayableId): + _PATTERN = re.compile(r"spotify:episode:(.{22})") + _hexId: str + + def __init__(self, hex_id: str): + self._hexId = hex_id.lower() + + @staticmethod + def from_uri(uri: str) -> EpisodeId: + matcher = EpisodeId._PATTERN.search(uri) + if matcher is not None: + episode_id = matcher.group(1) + return EpisodeId( + Utils.Utils.bytes_to_hex( + PlayableId.BASE62.decode(episode_id, 16))) + else: + TypeError("Not a Spotify episode ID: {}".format(uri)) + + @staticmethod + def from_base62(base62: str) -> EpisodeId: + return EpisodeId( + Utils.Utils.bytes_to_hex(PlayableId.BASE62.decode(base62, 16))) + + @staticmethod + def from_hex(hex_str: str) -> EpisodeId: + return EpisodeId(hex_str) + + def to_mercury_uri(self) -> str: + return "hm://metadata/4/episode/{}".format(self._hexId) + + def to_spotify_uri(self) -> str: + return "Spotify:episode:{}".format( + PlayableId.BASE62.encode(Utils.Utils.hex_to_bytes(self._hexId))) + + def hex_id(self) -> str: + return self._hexId + + def get_gid(self) -> bytes: + return Utils.Utils.hex_to_bytes(self._hexId) diff --git a/src/librespot/metadata/PlayableId.py b/src/librespot/metadata/PlayableId.py new file mode 100644 index 0000000..6361203 --- /dev/null +++ b/src/librespot/metadata/PlayableId.py @@ -0,0 +1,40 @@ +from __future__ import annotations +from librespot.common.Base62 import Base62 +# from librespot.metadata import EpisodeId, TrackId, UnsupportedId +from librespot.proto.context_track_pb2 import ContextTrack + + +class PlayableId: + BASE62 = Base62.create_instance_with_inverted_character_set() + + @staticmethod + def from_uri(uri: str) -> PlayableId: + pass + # if not PlayableId.is_supported(uri): + # return UnsupportedId(uri) + + # if TrackId._PATTERN.search(uri) is not None: + # return TrackId.from_uri(uri) + # elif EpisodeId._PATTERN.search(uri) is not None: + # return EpisodeId.from_uri(uri) + # else: + # raise TypeError("Unknown uri: {}".format(uri)) + + @staticmethod + def is_supported(uri: str): + return not uri.startswith("spotify:local:") and \ + not uri == "spotify:delimiter" and \ + not uri == "spotify:meta:delimiter" + + @staticmethod + def should_play(track: ContextTrack): + return track.metadata_or_default + + def get_gid(self) -> bytes: + pass + + def hex_id(self) -> str: + pass + + def to_spotify_uri(self) -> str: + pass diff --git a/src/librespot/metadata/ShowId.py b/src/librespot/metadata/ShowId.py new file mode 100644 index 0000000..d6c2a7f --- /dev/null +++ b/src/librespot/metadata/ShowId.py @@ -0,0 +1,42 @@ +from __future__ import annotations +from librespot.common import Base62, Utils +from librespot.metadata import SpotifyId +import re + + +class ShowId(SpotifyId.SpotifyId): + _PATTERN = re.compile("spotify:show:(.{22})") + _BASE62 = Base62.create_instance_with_inverted_character_set() + _hexId: str + + def __init__(self, hex_id: str): + self._hexId = hex_id + + @staticmethod + def from_uri(uri: str) -> ShowId: + matcher = ShowId._PATTERN.search(uri) + if matcher is not None: + show_id = matcher.group(1) + return ShowId( + Utils.bytes_to_hex(ShowId._BASE62.decode(show_id, 16))) + else: + raise TypeError("Not a Spotify show ID: {}".format(uri)) + + @staticmethod + def from_base62(base62: str) -> ShowId: + return ShowId( + Utils.bytes_to_hex(ShowId._BASE62.decode(base62, 16))) + + @staticmethod + def from_hex(hex_str: str) -> ShowId: + return ShowId(hex_str) + + def to_mercury_uri(self) -> str: + return "hm://metadata/4/show/{}".format(self._hexId) + + def to_spotify_uri(self) -> str: + return "spotify:show:{}".format( + ShowId._BASE62.encode(Utils.hex_to_bytes(self._hexId))) + + def hex_id(self) -> str: + return self._hexId diff --git a/src/librespot/metadata/SpotifyId.py b/src/librespot/metadata/SpotifyId.py new file mode 100644 index 0000000..951a95a --- /dev/null +++ b/src/librespot/metadata/SpotifyId.py @@ -0,0 +1,23 @@ +class SpotifyId: + STATIC_FROM_URI = "fromUri" + STATIC_FROM_BASE62 = "fromBase62" + STATIC_FROM_HEX = "fromHex" + + @staticmethod + def from_base62(base62: str): + pass + + @staticmethod + def from_hex(hex_str: str): + pass + + @staticmethod + def from_uri(uri: str): + pass + + def to_spotify_uri(self) -> str: + pass + + class SpotifyIdParsingException(Exception): + def __init__(self, cause): + super().__init__(cause) diff --git a/src/librespot/metadata/TrackId.py b/src/librespot/metadata/TrackId.py new file mode 100644 index 0000000..69fb6a2 --- /dev/null +++ b/src/librespot/metadata/TrackId.py @@ -0,0 +1,42 @@ +from __future__ import annotations +from librespot.common import Utils +from librespot.metadata import SpotifyId +from librespot.metadata.PlayableId import PlayableId +import re + + +class TrackId(PlayableId, SpotifyId): + _PATTERN = re.compile("spotify:track:(.{22})") + _hexId: str + + def __init__(self, hex_id: str): + self._hexId = hex_id.lower() + + @staticmethod + def from_uri(uri: str) -> TrackId: + search = TrackId._PATTERN.search(uri) + if search is not None: + track_id = search.group(1) + return TrackId( + Utils.bytes_to_hex(PlayableId.BASE62.decode( + track_id, 16))) + else: + raise RuntimeError("Not a Spotify track ID: {}".format(uri)) + + @staticmethod + def from_base62(base62: str) -> TrackId: + return TrackId( + Utils.bytes_to_hex(PlayableId.BASE62.decode(base62, 16))) + + @staticmethod + def from_hex(hex_str: str) -> TrackId: + return TrackId(hex_str) + + def to_spotify_uri(self) -> str: + return "spotify:track:{}".format(self._hexId) + + def hex_id(self) -> str: + return self._hexId + + def get_gid(self) -> bytes: + return Utils.hex_to_bytes(self._hexId) diff --git a/src/librespot/metadata/UnsupportedId.py b/src/librespot/metadata/UnsupportedId.py new file mode 100644 index 0000000..b0c49aa --- /dev/null +++ b/src/librespot/metadata/UnsupportedId.py @@ -0,0 +1,17 @@ +from librespot.metadata import PlayableId + + +class UnsupportedId(PlayableId): + uri: str + + def __init__(self, uri: str): + self.uri = uri + + def get_gid(self) -> bytes: + raise TypeError() + + def hex_id(self) -> str: + raise TypeError() + + def to_spotify_uri(self) -> str: + return self.uri diff --git a/src/librespot/metadata/__init__.py b/src/librespot/metadata/__init__.py new file mode 100644 index 0000000..dcfb37a --- /dev/null +++ b/src/librespot/metadata/__init__.py @@ -0,0 +1,8 @@ +from librespot.metadata.AlbumId import AlbumId +from librespot.metadata.ArtistId import ArtistId +from librespot.metadata.EpisodeId import EpisodeId +from librespot.metadata.PlayableId import PlayableId +from librespot.metadata.ShowId import SpotifyId +from librespot.metadata.SpotifyId import SpotifyId +from librespot.metadata.TrackId import TrackId +from librespot.metadata.UnsupportedId import UnsupportedId diff --git a/src/librespot/player/Player.py b/src/librespot/player/Player.py new file mode 100644 index 0000000..7e63cfd --- /dev/null +++ b/src/librespot/player/Player.py @@ -0,0 +1,21 @@ +from librespot.core.Session import Session +from librespot.player import PlayerConfiguration, StateWrapper +import sched +import time + + +class Player: + VOLUME_MAX: int = 65536 + _scheduler: sched.scheduler = sched.scheduler(time.time) + _session: Session = None + _conf: PlayerConfiguration + state: StateWrapper + + # _playerSession: + + def __init__(self, conf: PlayerConfiguration, session: Session): + self._conf = conf + self._session = session + + def init_state(self): + self.state = StateWrapper(self._session, self, self._conf) diff --git a/src/librespot/player/PlayerConfiguration.py b/src/librespot/player/PlayerConfiguration.py new file mode 100644 index 0000000..369d72d --- /dev/null +++ b/src/librespot/player/PlayerConfiguration.py @@ -0,0 +1,79 @@ +from __future__ import annotations +from librespot.player.codecs import AudioQuality + + +class PlayerConfiguration: + # Audio + preferred_quality: AudioQuality + enable_normalisation: bool + normalisation_pregain: float + autoplay_enabled: bool + crossfade_duration: int + preload_enabled: bool + + # Volume + initial_volume: int + volume_steps: int + + def __init__(self, preferred_quality: AudioQuality, + enable_normalisation: bool, normalisation_pregain: float, + autoplay_enabled: bool, crossfade_duration: int, + preload_enabled: bool, initial_volume: int, + volume_steps: int): + self.preferred_quality = preferred_quality + self.enable_normalisation = enable_normalisation + self.normalisation_pregain = normalisation_pregain + self.autoplay_enabled = autoplay_enabled + self.crossfade_duration = crossfade_duration + self.preload_enabled = preload_enabled + self.initial_volume = initial_volume + self.volume_steps = volume_steps + + class Builder: + preferred_quality: AudioQuality = AudioQuality.AudioQuality.NORMAL + enable_normalisation: bool = True + normalisation_pregain: float = 3.0 + autoplay_enabled: bool = True + crossfade_duration: int = 0 + preload_enabled: bool = True + + # Volume + initial_volume: int = 65536 + volume_steps: int = 64 + + def __init__(self): + pass + + def set_preferred_quality( + self, preferred_quality: AudioQuality) -> __class__: + self.preferred_quality = preferred_quality + return self + + def set_enable_normalisation(self, + enable_normalisation: bool) -> __class__: + self.enable_normalisation = enable_normalisation + return self + + def set_normalisation_pregain( + self, normalisation_pregain: float) -> __class__: + self.normalisation_pregain = normalisation_pregain + return self + + def set_autoplay_enabled(self, autoplay_enabled: bool) -> __class__: + self.autoplay_enabled = autoplay_enabled + return self + + def set_crossfade_duration(self, crossfade_duration: int) -> __class__: + self.crossfade_duration = crossfade_duration + return self + + def set_preload_enabled(self, preload_enabled: bool) -> __class__: + self.preload_enabled = preload_enabled + return self + + def build(self) -> PlayerConfiguration: + return PlayerConfiguration( + self.preferred_quality, self.enable_normalisation, + self.normalisation_pregain, self.autoplay_enabled, + self.crossfade_duration, self.preload_enabled, + self.initial_volume, self.volume_steps) diff --git a/src/librespot/player/StateWrapper.py b/src/librespot/player/StateWrapper.py new file mode 100644 index 0000000..18e7588 --- /dev/null +++ b/src/librespot/player/StateWrapper.py @@ -0,0 +1,13 @@ +from __future__ import annotations +from librespot.core import Session +from librespot.player import Player, PlayerConfiguration + + +class StateWrapper: + session: Session + player: Player + + def __init__(self, session: Session, player: Player, + conf: PlayerConfiguration): + self.session = session + self.player = player diff --git a/src/librespot/player/__init__.py b/src/librespot/player/__init__.py new file mode 100644 index 0000000..024150b --- /dev/null +++ b/src/librespot/player/__init__.py @@ -0,0 +1,3 @@ +from librespot.player.Player import Player +from librespot.player.PlayerConfiguration import PlayerConfiguration +from librespot.player.StateWrapper import StateWrapper diff --git a/src/librespot/player/codecs/AudioQuality.py b/src/librespot/player/codecs/AudioQuality.py new file mode 100644 index 0000000..495af88 --- /dev/null +++ b/src/librespot/player/codecs/AudioQuality.py @@ -0,0 +1,37 @@ +from __future__ import annotations +from librespot.proto.Metadata import AudioFile +import enum + + +class AudioQuality(enum.Enum): + NORMAL = 0x00 + HIGH = 0x01 + VERY_HIGH = 0x02 + + @staticmethod + def get_quality(audio_format: AudioFile.Format) -> AudioQuality: + if audio_format == AudioFile.MP3_96 or \ + audio_format == AudioFile.OGG_VORBIS_96 or \ + audio_format == AudioFile.AAC_24_NORM: + return AudioQuality.NORMAL + elif audio_format == AudioFile.MP3_160 or \ + audio_format == AudioFile.MP3_160_ENC or \ + audio_format == AudioFile.OGG_VORBIS_160 or \ + audio_format == AudioFile.AAC_24: + return AudioQuality.HIGH + elif audio_format == AudioFile.MP3_320 or \ + audio_format == AudioFile.MP3_256 or \ + audio_format == AudioFile.OGG_VORBIS_320 or \ + audio_format == AudioFile.AAC_48: + return AudioQuality.VERY_HIGH + else: + raise RuntimeError("Unknown format: {}".format(format)) + + def get_matches(self, files: list[AudioFile]) -> list[AudioFile]: + file_list = [] + for file in files: + if hasattr(file, "format") and AudioQuality.get_quality( + file.format) == self: + file_list.append(file) + + return file_list diff --git a/src/librespot/player/codecs/VorbisOnlyAudioQuality.py b/src/librespot/player/codecs/VorbisOnlyAudioQuality.py new file mode 100644 index 0000000..1b80282 --- /dev/null +++ b/src/librespot/player/codecs/VorbisOnlyAudioQuality.py @@ -0,0 +1,42 @@ +from __future__ import annotations + +import logging + +from librespot.audio.format.AudioQualityPicker import AudioQualityPicker +from librespot.audio.format.SuperAudioFormat import SuperAudioFormat +from librespot.player.codecs.AudioQuality import AudioQuality +from librespot.proto import Metadata + + +class VorbisOnlyAudioQuality(AudioQualityPicker): + _LOGGER: logging = logging.getLogger(__name__) + preferred: AudioQuality + + def __init__(self, preferred: AudioQuality): + self.preferred = preferred + + @staticmethod + def get_vorbis_file(files: list[Metadata.AudioFile]): + for file in files: + if hasattr(file, "format") and SuperAudioFormat.get( + file.format) == SuperAudioFormat.VORBIS: + return file + + return None + + def get_file(self, files: list[Metadata.AudioFile]): + matches: list[Metadata.AudioFile] = self.preferred.get_matches(files) + vorbis: Metadata.AudioFile = VorbisOnlyAudioQuality.get_vorbis_file( + matches) + if vorbis is None: + vorbis: Metadata.AudioFile = VorbisOnlyAudioQuality.get_vorbis_file( + files) + if vorbis is not None: + self._LOGGER.warning( + "Using {} because preferred {} couldn't be found.".format( + vorbis.format, self.preferred)) + else: + self._LOGGER.fatal( + "Couldn't find any Vorbis file, available: {}") + + return vorbis diff --git a/src/librespot/player/codecs/__init__.py b/src/librespot/player/codecs/__init__.py new file mode 100644 index 0000000..e380e35 --- /dev/null +++ b/src/librespot/player/codecs/__init__.py @@ -0,0 +1,2 @@ +from librespot.player.codecs.AudioQuality import AudioFile +from librespot.player.codecs.VorbisOnlyAudioQuality import VorbisOnlyAudioQuality diff --git a/src/librespot/player/playback/PlayerSession.py b/src/librespot/player/playback/PlayerSession.py new file mode 100644 index 0000000..2cd1530 --- /dev/null +++ b/src/librespot/player/playback/PlayerSession.py @@ -0,0 +1,6 @@ +from __future__ import annotations +from librespot.standard import Closeable + + +class PlayerSession(Closeable): + pass diff --git a/src/librespot/player/playback/__init__.py b/src/librespot/player/playback/__init__.py new file mode 100644 index 0000000..4b87385 --- /dev/null +++ b/src/librespot/player/playback/__init__.py @@ -0,0 +1 @@ +from librespot.player.playback.PlayerSession import PlayerSession diff --git a/src/librespot/proto/Authentication.py b/src/librespot/proto/Authentication.py new file mode 100644 index 0000000..b38baf1 --- /dev/null +++ b/src/librespot/proto/Authentication.py @@ -0,0 +1,1984 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: authentication.proto +"""Generated protocol buffer code.""" +from google.protobuf.internal import enum_type_wrapper +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='authentication.proto', + package='spotify', + syntax='proto2', + serialized_options=b'\n\013com.spotify', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x14\x61uthentication.proto\x12\x07spotify\"\xa2\x03\n\x17\x43lientResponseEncrypted\x12\x34\n\x11login_credentials\x18\n \x02(\x0b\x32\x19.spotify.LoginCredentials\x12\x32\n\x10\x61\x63\x63ount_creation\x18\x14 \x01(\x0e\x32\x18.spotify.AccountCreation\x12?\n\x14\x66ingerprint_response\x18\x1e \x01(\x0b\x32!.spotify.FingerprintResponseUnion\x12-\n\x0bpeer_ticket\x18( \x01(\x0b\x32\x18.spotify.PeerTicketUnion\x12(\n\x0bsystem_info\x18\x32 \x02(\x0b\x32\x13.spotify.SystemInfo\x12\x16\n\x0eplatform_model\x18< \x01(\t\x12\x16\n\x0eversion_string\x18\x46 \x01(\t\x12)\n\x06\x61ppkey\x18P \x01(\x0b\x32\x19.spotify.LibspotifyAppKey\x12(\n\x0b\x63lient_info\x18Z \x01(\x0b\x32\x13.spotify.ClientInfo\"a\n\x10LoginCredentials\x12\x10\n\x08username\x18\n \x01(\t\x12(\n\x03typ\x18\x14 \x02(\x0e\x32\x1b.spotify.AuthenticationType\x12\x11\n\tauth_data\x18\x1e \x01(\x0c\"\x89\x01\n\x18\x46ingerprintResponseUnion\x12\x30\n\x05grain\x18\n \x01(\x0b\x32!.spotify.FingerprintGrainResponse\x12;\n\x0bhmac_ripemd\x18\x14 \x01(\x0b\x32&.spotify.FingerprintHmacRipemdResponse\"1\n\x18\x46ingerprintGrainResponse\x12\x15\n\rencrypted_key\x18\n \x02(\x0c\"-\n\x1d\x46ingerprintHmacRipemdResponse\x12\x0c\n\x04hmac\x18\n \x02(\x0c\"o\n\x0fPeerTicketUnion\x12\x30\n\npublic_key\x18\n \x01(\x0b\x32\x1c.spotify.PeerTicketPublicKey\x12*\n\nold_ticket\x18\x14 \x01(\x0b\x32\x16.spotify.PeerTicketOld\")\n\x13PeerTicketPublicKey\x12\x12\n\npublic_key\x18\n \x02(\x0c\"C\n\rPeerTicketOld\x12\x13\n\x0bpeer_ticket\x18\n \x02(\x0c\x12\x1d\n\x15peer_ticket_signature\x18\x14 \x02(\x0c\"\x81\x02\n\nSystemInfo\x12&\n\ncpu_family\x18\n \x02(\x0e\x32\x12.spotify.CpuFamily\x12\x13\n\x0b\x63pu_subtype\x18\x14 \x01(\r\x12\x0f\n\x07\x63pu_ext\x18\x1e \x01(\r\x12\x1d\n\x05\x62rand\x18( \x01(\x0e\x32\x0e.spotify.Brand\x12\x13\n\x0b\x62rand_flags\x18\x32 \x01(\r\x12\x17\n\x02os\x18< \x02(\x0e\x32\x0b.spotify.Os\x12\x12\n\nos_version\x18\x46 \x01(\r\x12\x0e\n\x06os_ext\x18P \x01(\r\x12!\n\x19system_information_string\x18Z \x01(\t\x12\x11\n\tdevice_id\x18\x64 \x01(\t\"p\n\x10LibspotifyAppKey\x12\x0f\n\x07version\x18\x01 \x02(\r\x12\x0e\n\x06\x64\x65vkey\x18\x02 \x02(\x0c\x12\x11\n\tsignature\x18\x03 \x02(\x0c\x12\x11\n\tuseragent\x18\x04 \x02(\t\x12\x15\n\rcallback_hash\x18\x05 \x02(\x0c\"X\n\nClientInfo\x12\x0f\n\x07limited\x18\x01 \x01(\x08\x12\'\n\x02\x66\x62\x18\x02 \x01(\x0b\x32\x1b.spotify.ClientInfoFacebook\x12\x10\n\x08language\x18\x03 \x01(\t\"(\n\x12\x43lientInfoFacebook\x12\x12\n\nmachine_id\x18\x01 \x01(\t\"\xe9\x02\n\tAPWelcome\x12\x1a\n\x12\x63\x61nonical_username\x18\n \x02(\t\x12\x34\n\x16\x61\x63\x63ount_type_logged_in\x18\x14 \x02(\x0e\x32\x14.spotify.AccountType\x12\x38\n\x1a\x63redentials_type_logged_in\x18\x19 \x02(\x0e\x32\x14.spotify.AccountType\x12\x43\n\x1ereusable_auth_credentials_type\x18\x1e \x02(\x0e\x32\x1b.spotify.AuthenticationType\x12!\n\x19reusable_auth_credentials\x18( \x02(\x0c\x12\x12\n\nlfs_secret\x18\x32 \x01(\x0c\x12*\n\x0c\x61\x63\x63ount_info\x18< \x01(\x0b\x32\x14.spotify.AccountInfo\x12(\n\x02\x66\x62\x18\x46 \x01(\x0b\x32\x1c.spotify.AccountInfoFacebook\"k\n\x0b\x41\x63\x63ountInfo\x12,\n\x07spotify\x18\x01 \x01(\x0b\x32\x1b.spotify.AccountInfoSpotify\x12.\n\x08\x66\x61\x63\x65\x62ook\x18\x02 \x01(\x0b\x32\x1c.spotify.AccountInfoFacebook\"\x14\n\x12\x41\x63\x63ountInfoSpotify\"?\n\x13\x41\x63\x63ountInfoFacebook\x12\x14\n\x0c\x61\x63\x63\x65ss_token\x18\x01 \x01(\t\x12\x12\n\nmachine_id\x18\x02 \x01(\t*\xd6\x01\n\x12\x41uthenticationType\x12\x1c\n\x18\x41UTHENTICATION_USER_PASS\x10\x00\x12-\n)AUTHENTICATION_STORED_SPOTIFY_CREDENTIALS\x10\x01\x12.\n*AUTHENTICATION_STORED_FACEBOOK_CREDENTIALS\x10\x02\x12 \n\x1c\x41UTHENTICATION_SPOTIFY_TOKEN\x10\x03\x12!\n\x1d\x41UTHENTICATION_FACEBOOK_TOKEN\x10\x04*Y\n\x0f\x41\x63\x63ountCreation\x12\"\n\x1e\x41\x43\x43OUNT_CREATION_ALWAYS_PROMPT\x10\x01\x12\"\n\x1e\x41\x43\x43OUNT_CREATION_ALWAYS_CREATE\x10\x03*\x9d\x01\n\tCpuFamily\x12\x0f\n\x0b\x43PU_UNKNOWN\x10\x00\x12\x0b\n\x07\x43PU_X86\x10\x01\x12\x0e\n\nCPU_X86_64\x10\x02\x12\x0b\n\x07\x43PU_PPC\x10\x03\x12\x0e\n\nCPU_PPC_64\x10\x04\x12\x0b\n\x07\x43PU_ARM\x10\x05\x12\x0c\n\x08\x43PU_IA64\x10\x06\x12\n\n\x06\x43PU_SH\x10\x07\x12\x0c\n\x08\x43PU_MIPS\x10\x08\x12\x10\n\x0c\x43PU_BLACKFIN\x10\t*K\n\x05\x42rand\x12\x13\n\x0f\x42RAND_UNBRANDED\x10\x00\x12\r\n\tBRAND_INQ\x10\x01\x12\r\n\tBRAND_HTC\x10\x02\x12\x0f\n\x0b\x42RAND_NOKIA\x10\x03*\xd1\x02\n\x02Os\x12\x0e\n\nOS_UNKNOWN\x10\x00\x12\x0e\n\nOS_WINDOWS\x10\x01\x12\n\n\x06OS_OSX\x10\x02\x12\r\n\tOS_IPHONE\x10\x03\x12\n\n\x06OS_S60\x10\x04\x12\x0c\n\x08OS_LINUX\x10\x05\x12\x11\n\rOS_WINDOWS_CE\x10\x06\x12\x0e\n\nOS_ANDROID\x10\x07\x12\x0b\n\x07OS_PALM\x10\x08\x12\x0e\n\nOS_FREEBSD\x10\t\x12\x11\n\rOS_BLACKBERRY\x10\n\x12\x0c\n\x08OS_SONOS\x10\x0b\x12\x0f\n\x0bOS_LOGITECH\x10\x0c\x12\n\n\x06OS_WP7\x10\r\x12\x0c\n\x08OS_ONKYO\x10\x0e\x12\x0e\n\nOS_PHILIPS\x10\x0f\x12\t\n\x05OS_WD\x10\x10\x12\x0c\n\x08OS_VOLVO\x10\x11\x12\x0b\n\x07OS_TIVO\x10\x12\x12\x0b\n\x07OS_AWOX\x10\x13\x12\x0c\n\x08OS_MEEGO\x10\x14\x12\r\n\tOS_QNXNTO\x10\x15\x12\n\n\x06OS_BCO\x10\x16*(\n\x0b\x41\x63\x63ountType\x12\x0b\n\x07Spotify\x10\x00\x12\x0c\n\x08\x46\x61\x63\x65\x62ook\x10\x01\x42\r\n\x0b\x63om.spotify' +) + +_AUTHENTICATIONTYPE = _descriptor.EnumDescriptor( + name='AuthenticationType', + full_name='spotify.AuthenticationType', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='AUTHENTICATION_USER_PASS', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AUTHENTICATION_STORED_SPOTIFY_CREDENTIALS', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AUTHENTICATION_STORED_FACEBOOK_CREDENTIALS', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AUTHENTICATION_SPOTIFY_TOKEN', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AUTHENTICATION_FACEBOOK_TOKEN', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2083, + serialized_end=2297, +) +_sym_db.RegisterEnumDescriptor(_AUTHENTICATIONTYPE) + +AuthenticationType = enum_type_wrapper.EnumTypeWrapper(_AUTHENTICATIONTYPE) +_ACCOUNTCREATION = _descriptor.EnumDescriptor( + name='AccountCreation', + full_name='spotify.AccountCreation', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='ACCOUNT_CREATION_ALWAYS_PROMPT', + index=0, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='ACCOUNT_CREATION_ALWAYS_CREATE', + index=1, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2299, + serialized_end=2388, +) +_sym_db.RegisterEnumDescriptor(_ACCOUNTCREATION) + +AccountCreation = enum_type_wrapper.EnumTypeWrapper(_ACCOUNTCREATION) +_CPUFAMILY = _descriptor.EnumDescriptor( + name='CpuFamily', + full_name='spotify.CpuFamily', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='CPU_UNKNOWN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CPU_X86', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CPU_X86_64', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CPU_PPC', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CPU_PPC_64', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CPU_ARM', + index=5, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CPU_IA64', + index=6, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CPU_SH', + index=7, + number=7, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CPU_MIPS', + index=8, + number=8, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CPU_BLACKFIN', + index=9, + number=9, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2391, + serialized_end=2548, +) +_sym_db.RegisterEnumDescriptor(_CPUFAMILY) + +CpuFamily = enum_type_wrapper.EnumTypeWrapper(_CPUFAMILY) +_BRAND = _descriptor.EnumDescriptor( + name='Brand', + full_name='spotify.Brand', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='BRAND_UNBRANDED', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='BRAND_INQ', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='BRAND_HTC', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='BRAND_NOKIA', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2550, + serialized_end=2625, +) +_sym_db.RegisterEnumDescriptor(_BRAND) + +Brand = enum_type_wrapper.EnumTypeWrapper(_BRAND) +_OS = _descriptor.EnumDescriptor( + name='Os', + full_name='spotify.Os', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='OS_UNKNOWN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_WINDOWS', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_OSX', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_IPHONE', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_S60', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_LINUX', + index=5, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_WINDOWS_CE', + index=6, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_ANDROID', + index=7, + number=7, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_PALM', + index=8, + number=8, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_FREEBSD', + index=9, + number=9, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_BLACKBERRY', + index=10, + number=10, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_SONOS', + index=11, + number=11, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_LOGITECH', + index=12, + number=12, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_WP7', + index=13, + number=13, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_ONKYO', + index=14, + number=14, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_PHILIPS', + index=15, + number=15, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_WD', + index=16, + number=16, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_VOLVO', + index=17, + number=17, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_TIVO', + index=18, + number=18, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_AWOX', + index=19, + number=19, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_MEEGO', + index=20, + number=20, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_QNXNTO', + index=21, + number=21, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OS_BCO', + index=22, + number=22, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2628, + serialized_end=2965, +) +_sym_db.RegisterEnumDescriptor(_OS) + +Os = enum_type_wrapper.EnumTypeWrapper(_OS) +_ACCOUNTTYPE = _descriptor.EnumDescriptor( + name='AccountType', + full_name='spotify.AccountType', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='Spotify', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='Facebook', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2967, + serialized_end=3007, +) +_sym_db.RegisterEnumDescriptor(_ACCOUNTTYPE) + +AccountType = enum_type_wrapper.EnumTypeWrapper(_ACCOUNTTYPE) +AUTHENTICATION_USER_PASS = 0 +AUTHENTICATION_STORED_SPOTIFY_CREDENTIALS = 1 +AUTHENTICATION_STORED_FACEBOOK_CREDENTIALS = 2 +AUTHENTICATION_SPOTIFY_TOKEN = 3 +AUTHENTICATION_FACEBOOK_TOKEN = 4 +ACCOUNT_CREATION_ALWAYS_PROMPT = 1 +ACCOUNT_CREATION_ALWAYS_CREATE = 3 +CPU_UNKNOWN = 0 +CPU_X86 = 1 +CPU_X86_64 = 2 +CPU_PPC = 3 +CPU_PPC_64 = 4 +CPU_ARM = 5 +CPU_IA64 = 6 +CPU_SH = 7 +CPU_MIPS = 8 +CPU_BLACKFIN = 9 +BRAND_UNBRANDED = 0 +BRAND_INQ = 1 +BRAND_HTC = 2 +BRAND_NOKIA = 3 +OS_UNKNOWN = 0 +OS_WINDOWS = 1 +OS_OSX = 2 +OS_IPHONE = 3 +OS_S60 = 4 +OS_LINUX = 5 +OS_WINDOWS_CE = 6 +OS_ANDROID = 7 +OS_PALM = 8 +OS_FREEBSD = 9 +OS_BLACKBERRY = 10 +OS_SONOS = 11 +OS_LOGITECH = 12 +OS_WP7 = 13 +OS_ONKYO = 14 +OS_PHILIPS = 15 +OS_WD = 16 +OS_VOLVO = 17 +OS_TIVO = 18 +OS_AWOX = 19 +OS_MEEGO = 20 +OS_QNXNTO = 21 +OS_BCO = 22 +Spotify = 0 +Facebook = 1 + +_CLIENTRESPONSEENCRYPTED = _descriptor.Descriptor( + name='ClientResponseEncrypted', + full_name='spotify.ClientResponseEncrypted', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='login_credentials', + full_name='spotify.ClientResponseEncrypted.login_credentials', + index=0, + number=10, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='account_creation', + full_name='spotify.ClientResponseEncrypted.account_creation', + index=1, + number=20, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=1, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='fingerprint_response', + full_name='spotify.ClientResponseEncrypted.fingerprint_response', + index=2, + number=30, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='peer_ticket', + full_name='spotify.ClientResponseEncrypted.peer_ticket', + index=3, + number=40, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='system_info', + full_name='spotify.ClientResponseEncrypted.system_info', + index=4, + number=50, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='platform_model', + full_name='spotify.ClientResponseEncrypted.platform_model', + index=5, + number=60, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='version_string', + full_name='spotify.ClientResponseEncrypted.version_string', + index=6, + number=70, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='appkey', + full_name='spotify.ClientResponseEncrypted.appkey', + index=7, + number=80, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='client_info', + full_name='spotify.ClientResponseEncrypted.client_info', + index=8, + number=90, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=34, + serialized_end=452, +) + +_LOGINCREDENTIALS = _descriptor.Descriptor( + name='LoginCredentials', + full_name='spotify.LoginCredentials', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='username', + full_name='spotify.LoginCredentials.username', + index=0, + number=10, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='typ', + full_name='spotify.LoginCredentials.typ', + index=1, + number=20, + type=14, + cpp_type=8, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='auth_data', + full_name='spotify.LoginCredentials.auth_data', + index=2, + number=30, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=454, + serialized_end=551, +) + +_FINGERPRINTRESPONSEUNION = _descriptor.Descriptor( + name='FingerprintResponseUnion', + full_name='spotify.FingerprintResponseUnion', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='grain', + full_name='spotify.FingerprintResponseUnion.grain', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='hmac_ripemd', + full_name='spotify.FingerprintResponseUnion.hmac_ripemd', + index=1, + number=20, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=554, + serialized_end=691, +) + +_FINGERPRINTGRAINRESPONSE = _descriptor.Descriptor( + name='FingerprintGrainResponse', + full_name='spotify.FingerprintGrainResponse', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='encrypted_key', + full_name='spotify.FingerprintGrainResponse.encrypted_key', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=693, + serialized_end=742, +) + +_FINGERPRINTHMACRIPEMDRESPONSE = _descriptor.Descriptor( + name='FingerprintHmacRipemdResponse', + full_name='spotify.FingerprintHmacRipemdResponse', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='hmac', + full_name='spotify.FingerprintHmacRipemdResponse.hmac', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=744, + serialized_end=789, +) + +_PEERTICKETUNION = _descriptor.Descriptor( + name='PeerTicketUnion', + full_name='spotify.PeerTicketUnion', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='public_key', + full_name='spotify.PeerTicketUnion.public_key', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='old_ticket', + full_name='spotify.PeerTicketUnion.old_ticket', + index=1, + number=20, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=791, + serialized_end=902, +) + +_PEERTICKETPUBLICKEY = _descriptor.Descriptor( + name='PeerTicketPublicKey', + full_name='spotify.PeerTicketPublicKey', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='public_key', + full_name='spotify.PeerTicketPublicKey.public_key', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=904, + serialized_end=945, +) + +_PEERTICKETOLD = _descriptor.Descriptor( + name='PeerTicketOld', + full_name='spotify.PeerTicketOld', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='peer_ticket', + full_name='spotify.PeerTicketOld.peer_ticket', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='peer_ticket_signature', + full_name='spotify.PeerTicketOld.peer_ticket_signature', + index=1, + number=20, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=947, + serialized_end=1014, +) + +_SYSTEMINFO = _descriptor.Descriptor( + name='SystemInfo', + full_name='spotify.SystemInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='cpu_family', + full_name='spotify.SystemInfo.cpu_family', + index=0, + number=10, + type=14, + cpp_type=8, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='cpu_subtype', + full_name='spotify.SystemInfo.cpu_subtype', + index=1, + number=20, + type=13, + cpp_type=3, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='cpu_ext', + full_name='spotify.SystemInfo.cpu_ext', + index=2, + number=30, + type=13, + cpp_type=3, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='brand', + full_name='spotify.SystemInfo.brand', + index=3, + number=40, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='brand_flags', + full_name='spotify.SystemInfo.brand_flags', + index=4, + number=50, + type=13, + cpp_type=3, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='os', + full_name='spotify.SystemInfo.os', + index=5, + number=60, + type=14, + cpp_type=8, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='os_version', + full_name='spotify.SystemInfo.os_version', + index=6, + number=70, + type=13, + cpp_type=3, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='os_ext', + full_name='spotify.SystemInfo.os_ext', + index=7, + number=80, + type=13, + cpp_type=3, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='system_information_string', + full_name='spotify.SystemInfo.system_information_string', + index=8, + number=90, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='device_id', + full_name='spotify.SystemInfo.device_id', + index=9, + number=100, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1017, + serialized_end=1274, +) + +_LIBSPOTIFYAPPKEY = _descriptor.Descriptor( + name='LibspotifyAppKey', + full_name='spotify.LibspotifyAppKey', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='version', + full_name='spotify.LibspotifyAppKey.version', + index=0, + number=1, + type=13, + cpp_type=3, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='devkey', + full_name='spotify.LibspotifyAppKey.devkey', + index=1, + number=2, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='signature', + full_name='spotify.LibspotifyAppKey.signature', + index=2, + number=3, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='useragent', + full_name='spotify.LibspotifyAppKey.useragent', + index=3, + number=4, + type=9, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='callback_hash', + full_name='spotify.LibspotifyAppKey.callback_hash', + index=4, + number=5, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1276, + serialized_end=1388, +) + +_CLIENTINFO = _descriptor.Descriptor( + name='ClientInfo', + full_name='spotify.ClientInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='limited', + full_name='spotify.ClientInfo.limited', + index=0, + number=1, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='fb', + full_name='spotify.ClientInfo.fb', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='language', + full_name='spotify.ClientInfo.language', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1390, + serialized_end=1478, +) + +_CLIENTINFOFACEBOOK = _descriptor.Descriptor( + name='ClientInfoFacebook', + full_name='spotify.ClientInfoFacebook', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='machine_id', + full_name='spotify.ClientInfoFacebook.machine_id', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1480, + serialized_end=1520, +) + +_APWELCOME = _descriptor.Descriptor( + name='APWelcome', + full_name='spotify.APWelcome', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='canonical_username', + full_name='spotify.APWelcome.canonical_username', + index=0, + number=10, + type=9, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='account_type_logged_in', + full_name='spotify.APWelcome.account_type_logged_in', + index=1, + number=20, + type=14, + cpp_type=8, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='credentials_type_logged_in', + full_name='spotify.APWelcome.credentials_type_logged_in', + index=2, + number=25, + type=14, + cpp_type=8, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='reusable_auth_credentials_type', + full_name='spotify.APWelcome.reusable_auth_credentials_type', + index=3, + number=30, + type=14, + cpp_type=8, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='reusable_auth_credentials', + full_name='spotify.APWelcome.reusable_auth_credentials', + index=4, + number=40, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='lfs_secret', + full_name='spotify.APWelcome.lfs_secret', + index=5, + number=50, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='account_info', + full_name='spotify.APWelcome.account_info', + index=6, + number=60, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='fb', + full_name='spotify.APWelcome.fb', + index=7, + number=70, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1523, + serialized_end=1884, +) + +_ACCOUNTINFO = _descriptor.Descriptor( + name='AccountInfo', + full_name='spotify.AccountInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='spotify', + full_name='spotify.AccountInfo.spotify', + index=0, + number=1, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='facebook', + full_name='spotify.AccountInfo.facebook', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1886, + serialized_end=1993, +) + +_ACCOUNTINFOSPOTIFY = _descriptor.Descriptor( + name='AccountInfoSpotify', + full_name='spotify.AccountInfoSpotify', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1995, + serialized_end=2015, +) + +_ACCOUNTINFOFACEBOOK = _descriptor.Descriptor( + name='AccountInfoFacebook', + full_name='spotify.AccountInfoFacebook', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='access_token', + full_name='spotify.AccountInfoFacebook.access_token', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='machine_id', + full_name='spotify.AccountInfoFacebook.machine_id', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2017, + serialized_end=2080, +) + +_CLIENTRESPONSEENCRYPTED.fields_by_name[ + 'login_credentials'].message_type = _LOGINCREDENTIALS +_CLIENTRESPONSEENCRYPTED.fields_by_name[ + 'account_creation'].enum_type = _ACCOUNTCREATION +_CLIENTRESPONSEENCRYPTED.fields_by_name[ + 'fingerprint_response'].message_type = _FINGERPRINTRESPONSEUNION +_CLIENTRESPONSEENCRYPTED.fields_by_name[ + 'peer_ticket'].message_type = _PEERTICKETUNION +_CLIENTRESPONSEENCRYPTED.fields_by_name[ + 'system_info'].message_type = _SYSTEMINFO +_CLIENTRESPONSEENCRYPTED.fields_by_name[ + 'appkey'].message_type = _LIBSPOTIFYAPPKEY +_CLIENTRESPONSEENCRYPTED.fields_by_name[ + 'client_info'].message_type = _CLIENTINFO +_LOGINCREDENTIALS.fields_by_name['typ'].enum_type = _AUTHENTICATIONTYPE +_FINGERPRINTRESPONSEUNION.fields_by_name[ + 'grain'].message_type = _FINGERPRINTGRAINRESPONSE +_FINGERPRINTRESPONSEUNION.fields_by_name[ + 'hmac_ripemd'].message_type = _FINGERPRINTHMACRIPEMDRESPONSE +_PEERTICKETUNION.fields_by_name[ + 'public_key'].message_type = _PEERTICKETPUBLICKEY +_PEERTICKETUNION.fields_by_name['old_ticket'].message_type = _PEERTICKETOLD +_SYSTEMINFO.fields_by_name['cpu_family'].enum_type = _CPUFAMILY +_SYSTEMINFO.fields_by_name['brand'].enum_type = _BRAND +_SYSTEMINFO.fields_by_name['os'].enum_type = _OS +_CLIENTINFO.fields_by_name['fb'].message_type = _CLIENTINFOFACEBOOK +_APWELCOME.fields_by_name['account_type_logged_in'].enum_type = _ACCOUNTTYPE +_APWELCOME.fields_by_name[ + 'credentials_type_logged_in'].enum_type = _ACCOUNTTYPE +_APWELCOME.fields_by_name[ + 'reusable_auth_credentials_type'].enum_type = _AUTHENTICATIONTYPE +_APWELCOME.fields_by_name['account_info'].message_type = _ACCOUNTINFO +_APWELCOME.fields_by_name['fb'].message_type = _ACCOUNTINFOFACEBOOK +_ACCOUNTINFO.fields_by_name['spotify'].message_type = _ACCOUNTINFOSPOTIFY +_ACCOUNTINFO.fields_by_name['facebook'].message_type = _ACCOUNTINFOFACEBOOK +DESCRIPTOR.message_types_by_name[ + 'ClientResponseEncrypted'] = _CLIENTRESPONSEENCRYPTED +DESCRIPTOR.message_types_by_name['LoginCredentials'] = _LOGINCREDENTIALS +DESCRIPTOR.message_types_by_name[ + 'FingerprintResponseUnion'] = _FINGERPRINTRESPONSEUNION +DESCRIPTOR.message_types_by_name[ + 'FingerprintGrainResponse'] = _FINGERPRINTGRAINRESPONSE +DESCRIPTOR.message_types_by_name[ + 'FingerprintHmacRipemdResponse'] = _FINGERPRINTHMACRIPEMDRESPONSE +DESCRIPTOR.message_types_by_name['PeerTicketUnion'] = _PEERTICKETUNION +DESCRIPTOR.message_types_by_name['PeerTicketPublicKey'] = _PEERTICKETPUBLICKEY +DESCRIPTOR.message_types_by_name['PeerTicketOld'] = _PEERTICKETOLD +DESCRIPTOR.message_types_by_name['SystemInfo'] = _SYSTEMINFO +DESCRIPTOR.message_types_by_name['LibspotifyAppKey'] = _LIBSPOTIFYAPPKEY +DESCRIPTOR.message_types_by_name['ClientInfo'] = _CLIENTINFO +DESCRIPTOR.message_types_by_name['ClientInfoFacebook'] = _CLIENTINFOFACEBOOK +DESCRIPTOR.message_types_by_name['APWelcome'] = _APWELCOME +DESCRIPTOR.message_types_by_name['AccountInfo'] = _ACCOUNTINFO +DESCRIPTOR.message_types_by_name['AccountInfoSpotify'] = _ACCOUNTINFOSPOTIFY +DESCRIPTOR.message_types_by_name['AccountInfoFacebook'] = _ACCOUNTINFOFACEBOOK +DESCRIPTOR.enum_types_by_name['AuthenticationType'] = _AUTHENTICATIONTYPE +DESCRIPTOR.enum_types_by_name['AccountCreation'] = _ACCOUNTCREATION +DESCRIPTOR.enum_types_by_name['CpuFamily'] = _CPUFAMILY +DESCRIPTOR.enum_types_by_name['Brand'] = _BRAND +DESCRIPTOR.enum_types_by_name['Os'] = _OS +DESCRIPTOR.enum_types_by_name['AccountType'] = _ACCOUNTTYPE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +ClientResponseEncrypted = _reflection.GeneratedProtocolMessageType( + 'ClientResponseEncrypted', + (_message.Message, ), + { + 'DESCRIPTOR': _CLIENTRESPONSEENCRYPTED, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.ClientResponseEncrypted) + }) +_sym_db.RegisterMessage(ClientResponseEncrypted) + +LoginCredentials = _reflection.GeneratedProtocolMessageType( + 'LoginCredentials', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGINCREDENTIALS, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.LoginCredentials) + }) +_sym_db.RegisterMessage(LoginCredentials) + +FingerprintResponseUnion = _reflection.GeneratedProtocolMessageType( + 'FingerprintResponseUnion', + (_message.Message, ), + { + 'DESCRIPTOR': _FINGERPRINTRESPONSEUNION, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.FingerprintResponseUnion) + }) +_sym_db.RegisterMessage(FingerprintResponseUnion) + +FingerprintGrainResponse = _reflection.GeneratedProtocolMessageType( + 'FingerprintGrainResponse', + (_message.Message, ), + { + 'DESCRIPTOR': _FINGERPRINTGRAINRESPONSE, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.FingerprintGrainResponse) + }) +_sym_db.RegisterMessage(FingerprintGrainResponse) + +FingerprintHmacRipemdResponse = _reflection.GeneratedProtocolMessageType( + 'FingerprintHmacRipemdResponse', + (_message.Message, ), + { + 'DESCRIPTOR': _FINGERPRINTHMACRIPEMDRESPONSE, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.FingerprintHmacRipemdResponse) + }) +_sym_db.RegisterMessage(FingerprintHmacRipemdResponse) + +PeerTicketUnion = _reflection.GeneratedProtocolMessageType( + 'PeerTicketUnion', + (_message.Message, ), + { + 'DESCRIPTOR': _PEERTICKETUNION, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.PeerTicketUnion) + }) +_sym_db.RegisterMessage(PeerTicketUnion) + +PeerTicketPublicKey = _reflection.GeneratedProtocolMessageType( + 'PeerTicketPublicKey', + (_message.Message, ), + { + 'DESCRIPTOR': _PEERTICKETPUBLICKEY, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.PeerTicketPublicKey) + }) +_sym_db.RegisterMessage(PeerTicketPublicKey) + +PeerTicketOld = _reflection.GeneratedProtocolMessageType( + 'PeerTicketOld', + (_message.Message, ), + { + 'DESCRIPTOR': _PEERTICKETOLD, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.PeerTicketOld) + }) +_sym_db.RegisterMessage(PeerTicketOld) + +SystemInfo = _reflection.GeneratedProtocolMessageType( + 'SystemInfo', + (_message.Message, ), + { + 'DESCRIPTOR': _SYSTEMINFO, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.SystemInfo) + }) +_sym_db.RegisterMessage(SystemInfo) + +LibspotifyAppKey = _reflection.GeneratedProtocolMessageType( + 'LibspotifyAppKey', + (_message.Message, ), + { + 'DESCRIPTOR': _LIBSPOTIFYAPPKEY, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.LibspotifyAppKey) + }) +_sym_db.RegisterMessage(LibspotifyAppKey) + +ClientInfo = _reflection.GeneratedProtocolMessageType( + 'ClientInfo', + (_message.Message, ), + { + 'DESCRIPTOR': _CLIENTINFO, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.ClientInfo) + }) +_sym_db.RegisterMessage(ClientInfo) + +ClientInfoFacebook = _reflection.GeneratedProtocolMessageType( + 'ClientInfoFacebook', + (_message.Message, ), + { + 'DESCRIPTOR': _CLIENTINFOFACEBOOK, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.ClientInfoFacebook) + }) +_sym_db.RegisterMessage(ClientInfoFacebook) + +APWelcome = _reflection.GeneratedProtocolMessageType( + 'APWelcome', + (_message.Message, ), + { + 'DESCRIPTOR': _APWELCOME, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.APWelcome) + }) +_sym_db.RegisterMessage(APWelcome) + +AccountInfo = _reflection.GeneratedProtocolMessageType( + 'AccountInfo', + (_message.Message, ), + { + 'DESCRIPTOR': _ACCOUNTINFO, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.AccountInfo) + }) +_sym_db.RegisterMessage(AccountInfo) + +AccountInfoSpotify = _reflection.GeneratedProtocolMessageType( + 'AccountInfoSpotify', + (_message.Message, ), + { + 'DESCRIPTOR': _ACCOUNTINFOSPOTIFY, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.AccountInfoSpotify) + }) +_sym_db.RegisterMessage(AccountInfoSpotify) + +AccountInfoFacebook = _reflection.GeneratedProtocolMessageType( + 'AccountInfoFacebook', + (_message.Message, ), + { + 'DESCRIPTOR': _ACCOUNTINFOFACEBOOK, + '__module__': 'authentication_pb2' + # @@protoc_insertion_point(class_scope:spotify.AccountInfoFacebook) + }) +_sym_db.RegisterMessage(AccountInfoFacebook) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/Connect.py b/src/librespot/proto/Connect.py new file mode 100644 index 0000000..acb8d43 --- /dev/null +++ b/src/librespot/proto/Connect.py @@ -0,0 +1,2340 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: connect.proto +"""Generated protocol buffer code.""" +from google.protobuf.internal import enum_type_wrapper +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +import librespot.proto.player_pb2 as player__pb2 + +DESCRIPTOR = _descriptor.FileDescriptor( + name='connect.proto', + package='connectstate', + syntax='proto3', + serialized_options=b'\n\030com.spotify.connectstateH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\rconnect.proto\x12\x0c\x63onnectstate\x1a\x0cplayer.proto\"\x9f\x01\n\rClusterUpdate\x12&\n\x07\x63luster\x18\x01 \x01(\x0b\x32\x15.connectstate.Cluster\x12\x38\n\rupdate_reason\x18\x02 \x01(\x0e\x32!.connectstate.ClusterUpdateReason\x12\x0e\n\x06\x61\x63k_id\x18\x03 \x01(\t\x12\x1c\n\x14\x64\x65vices_that_changed\x18\x04 \x03(\t\"\xa6\x01\n\x06\x44\x65vice\x12-\n\x0b\x64\x65vice_info\x18\x01 \x01(\x0b\x32\x18.connectstate.DeviceInfo\x12/\n\x0cplayer_state\x18\x02 \x01(\x0b\x32\x19.connectstate.PlayerState\x12<\n\x13private_device_info\x18\x03 \x01(\x0b\x32\x1f.connectstate.PrivateDeviceInfo\"\xfa\x01\n\x07\x43luster\x12\x11\n\ttimestamp\x18\x01 \x01(\x03\x12\x18\n\x10\x61\x63tive_device_id\x18\x02 \x01(\t\x12/\n\x0cplayer_state\x18\x03 \x01(\x0b\x32\x19.connectstate.PlayerState\x12\x31\n\x06\x64\x65vice\x18\x04 \x03(\x0b\x32!.connectstate.Cluster.DeviceEntry\x12\x15\n\rtransfer_data\x18\x05 \x01(\x0c\x1aG\n\x0b\x44\x65viceEntry\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\'\n\x05value\x18\x02 \x01(\x0b\x32\x18.connectstate.DeviceInfo:\x02\x38\x01\"\xa1\x03\n\x0fPutStateRequest\x12\x14\n\x0c\x63\x61llback_url\x18\x01 \x01(\t\x12$\n\x06\x64\x65vice\x18\x02 \x01(\x0b\x32\x14.connectstate.Device\x12-\n\x0bmember_type\x18\x03 \x01(\x0e\x32\x18.connectstate.MemberType\x12\x11\n\tis_active\x18\x04 \x01(\x08\x12\x36\n\x10put_state_reason\x18\x05 \x01(\x0e\x32\x1c.connectstate.PutStateReason\x12\x12\n\nmessage_id\x18\x06 \x01(\r\x12&\n\x1elast_command_sent_by_device_id\x18\x07 \x01(\t\x12\x1f\n\x17last_command_message_id\x18\x08 \x01(\r\x12\x1a\n\x12started_playing_at\x18\t \x01(\x04\x12\x1f\n\x17has_been_playing_for_ms\x18\x0b \x01(\x04\x12\x1d\n\x15\x63lient_side_timestamp\x18\x0c \x01(\x04\x12\x1f\n\x17only_write_player_state\x18\r \x01(\x08\"%\n\x11PrivateDeviceInfo\x12\x10\n\x08platform\x18\x01 \x01(\t\"(\n\x10SubscribeRequest\x12\x14\n\x0c\x63\x61llback_url\x18\x01 \x01(\t\"\xc5\x03\n\nDeviceInfo\x12\x10\n\x08\x63\x61n_play\x18\x01 \x01(\x08\x12\x0e\n\x06volume\x18\x02 \x01(\r\x12\x0c\n\x04name\x18\x03 \x01(\t\x12\x30\n\x0c\x63\x61pabilities\x18\x04 \x01(\x0b\x32\x1a.connectstate.Capabilities\x12\x1f\n\x17\x64\x65vice_software_version\x18\x06 \x01(\t\x12-\n\x0b\x64\x65vice_type\x18\x07 \x01(\x0e\x32\x18.connectstate.DeviceType\x12\x15\n\rspirc_version\x18\t \x01(\t\x12\x11\n\tdevice_id\x18\n \x01(\t\x12\x1a\n\x12is_private_session\x18\x0b \x01(\x08\x12\x19\n\x11is_social_connect\x18\x0c \x01(\x08\x12\x11\n\tclient_id\x18\r \x01(\t\x12\r\n\x05\x62rand\x18\x0e \x01(\t\x12\r\n\x05model\x18\x0f \x01(\t\x12?\n\x0cmetadata_map\x18\x10 \x03(\x0b\x32).connectstate.DeviceInfo.MetadataMapEntry\x1a\x32\n\x10MetadataMapEntry\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\r\n\x05value\x18\x02 \x01(\t:\x02\x38\x01\"\xcc\x04\n\x0c\x43\x61pabilities\x12\x15\n\rcan_be_player\x18\x02 \x01(\x08\x12\x19\n\x11restrict_to_local\x18\x03 \x01(\x08\x12\x1a\n\x12gaia_eq_connect_id\x18\x05 \x01(\x08\x12\x17\n\x0fsupports_logout\x18\x06 \x01(\x08\x12\x15\n\ris_observable\x18\x07 \x01(\x08\x12\x14\n\x0cvolume_steps\x18\x08 \x01(\x05\x12\x17\n\x0fsupported_types\x18\t \x03(\t\x12\x14\n\x0c\x63ommand_acks\x18\n \x01(\x08\x12\x17\n\x0fsupports_rename\x18\x0b \x01(\x08\x12\x0e\n\x06hidden\x18\x0c \x01(\x08\x12\x16\n\x0e\x64isable_volume\x18\r \x01(\x08\x12\x18\n\x10\x63onnect_disabled\x18\x0e \x01(\x08\x12\x1c\n\x14supports_playlist_v2\x18\x0f \x01(\x08\x12\x17\n\x0fis_controllable\x18\x10 \x01(\x08\x12\"\n\x1asupports_external_episodes\x18\x11 \x01(\x08\x12%\n\x1dsupports_set_backend_metadata\x18\x12 \x01(\x08\x12!\n\x19supports_transfer_command\x18\x13 \x01(\x08\x12 \n\x18supports_command_request\x18\x14 \x01(\x08\x12\x18\n\x10is_voice_enabled\x18\x15 \x01(\x08\x12\x1f\n\x17needs_full_player_state\x18\x16 \x01(\x08\x12\x1c\n\x14supports_gzip_pushes\x18\x17 \x01(\x08\"+\n\x15\x43onnectCommandOptions\x12\x12\n\nmessage_id\x18\x01 \x01(\x05\"M\n\rLogoutCommand\x12<\n\x0f\x63ommand_options\x18\x01 \x01(\x0b\x32#.connectstate.ConnectCommandOptions\"`\n\x10SetVolumeCommand\x12\x0e\n\x06volume\x18\x01 \x01(\x05\x12<\n\x0f\x63ommand_options\x18\x02 \x01(\x0b\x32#.connectstate.ConnectCommandOptions\"`\n\rRenameCommand\x12\x11\n\trename_to\x18\x01 \x01(\t\x12<\n\x0f\x63ommand_options\x18\x02 \x01(\x0b\x32#.connectstate.ConnectCommandOptions\"\x95\x01\n\x19SetBackendMetadataCommand\x12G\n\x08metadata\x18\x01 \x03(\x0b\x32\x35.connectstate.SetBackendMetadataCommand.MetadataEntry\x1a/\n\rMetadataEntry\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\r\n\x05value\x18\x02 \x01(\t:\x02\x38\x01*\xd4\x01\n\x11SendCommandResult\x12\x1f\n\x1bUNKNOWN_SEND_COMMAND_RESULT\x10\x00\x12\x0b\n\x07SUCCESS\x10\x01\x12\x14\n\x10\x44\x45VICE_NOT_FOUND\x10\x02\x12\x18\n\x14\x43ONTEXT_PLAYER_ERROR\x10\x03\x12\x16\n\x12\x44\x45VICE_DISAPPEARED\x10\x04\x12\x12\n\x0eUPSTREAM_ERROR\x10\x05\x12#\n\x1f\x44\x45VICE_DOES_NOT_SUPPORT_COMMAND\x10\x06\x12\x10\n\x0cRATE_LIMITED\x10\x07*\xb7\x01\n\x0ePutStateReason\x12\x1c\n\x18UNKNOWN_PUT_STATE_REASON\x10\x00\x12\x0f\n\x0bSPIRC_HELLO\x10\x01\x12\x10\n\x0cSPIRC_NOTIFY\x10\x02\x12\x0e\n\nNEW_DEVICE\x10\x03\x12\x18\n\x14PLAYER_STATE_CHANGED\x10\x04\x12\x12\n\x0eVOLUME_CHANGED\x10\x05\x12\x11\n\rPICKER_OPENED\x10\x06\x12\x13\n\x0f\x42\x45\x43\x41ME_INACTIVE\x10\x07*;\n\nMemberType\x12\x0c\n\x08SPIRC_V2\x10\x00\x12\x0c\n\x08SPIRC_V3\x10\x01\x12\x11\n\rCONNECT_STATE\x10\x02*\x84\x01\n\x13\x43lusterUpdateReason\x12!\n\x1dUNKNOWN_CLUSTER_UPDATE_REASON\x10\x00\x12\x17\n\x13\x44\x45VICES_DISAPPEARED\x10\x01\x12\x18\n\x14\x44\x45VICE_STATE_CHANGED\x10\x02\x12\x17\n\x13NEW_DEVICE_APPEARED\x10\x03*\xa0\x02\n\nDeviceType\x12\x0b\n\x07UNKNOWN\x10\x00\x12\x0c\n\x08\x43OMPUTER\x10\x01\x12\n\n\x06TABLET\x10\x02\x12\x0e\n\nSMARTPHONE\x10\x03\x12\x0b\n\x07SPEAKER\x10\x04\x12\x06\n\x02TV\x10\x05\x12\x07\n\x03\x41VR\x10\x06\x12\x07\n\x03STB\x10\x07\x12\x10\n\x0c\x41UDIO_DONGLE\x10\x08\x12\x10\n\x0cGAME_CONSOLE\x10\t\x12\x0e\n\nCAST_VIDEO\x10\n\x12\x0e\n\nCAST_AUDIO\x10\x0b\x12\x0e\n\nAUTOMOBILE\x10\x0c\x12\x0e\n\nSMARTWATCH\x10\r\x12\x0e\n\nCHROMEBOOK\x10\x0e\x12\x13\n\x0fUNKNOWN_SPOTIFY\x10\x64\x12\r\n\tCAR_THING\x10\x65\x12\x0c\n\x08OBSERVER\x10\x66\x12\x0e\n\nHOME_THING\x10gB\x1c\n\x18\x63om.spotify.connectstateH\x02\x62\x06proto3', + dependencies=[ + player__pb2.DESCRIPTOR, + ]) + +_SENDCOMMANDRESULT = _descriptor.EnumDescriptor( + name='SendCommandResult', + full_name='connectstate.SendCommandResult', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='UNKNOWN_SEND_COMMAND_RESULT', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SUCCESS', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='DEVICE_NOT_FOUND', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CONTEXT_PLAYER_ERROR', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='DEVICE_DISAPPEARED', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='UPSTREAM_ERROR', + index=5, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='DEVICE_DOES_NOT_SUPPORT_COMMAND', + index=6, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='RATE_LIMITED', + index=7, + number=7, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2650, + serialized_end=2862, +) +_sym_db.RegisterEnumDescriptor(_SENDCOMMANDRESULT) + +SendCommandResult = enum_type_wrapper.EnumTypeWrapper(_SENDCOMMANDRESULT) +_PUTSTATEREASON = _descriptor.EnumDescriptor( + name='PutStateReason', + full_name='connectstate.PutStateReason', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='UNKNOWN_PUT_STATE_REASON', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SPIRC_HELLO', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SPIRC_NOTIFY', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='NEW_DEVICE', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLAYER_STATE_CHANGED', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='VOLUME_CHANGED', + index=5, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PICKER_OPENED', + index=6, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='BECAME_INACTIVE', + index=7, + number=7, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2865, + serialized_end=3048, +) +_sym_db.RegisterEnumDescriptor(_PUTSTATEREASON) + +PutStateReason = enum_type_wrapper.EnumTypeWrapper(_PUTSTATEREASON) +_MEMBERTYPE = _descriptor.EnumDescriptor( + name='MemberType', + full_name='connectstate.MemberType', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='SPIRC_V2', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SPIRC_V3', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CONNECT_STATE', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3050, + serialized_end=3109, +) +_sym_db.RegisterEnumDescriptor(_MEMBERTYPE) + +MemberType = enum_type_wrapper.EnumTypeWrapper(_MEMBERTYPE) +_CLUSTERUPDATEREASON = _descriptor.EnumDescriptor( + name='ClusterUpdateReason', + full_name='connectstate.ClusterUpdateReason', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='UNKNOWN_CLUSTER_UPDATE_REASON', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='DEVICES_DISAPPEARED', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='DEVICE_STATE_CHANGED', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='NEW_DEVICE_APPEARED', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3112, + serialized_end=3244, +) +_sym_db.RegisterEnumDescriptor(_CLUSTERUPDATEREASON) + +ClusterUpdateReason = enum_type_wrapper.EnumTypeWrapper(_CLUSTERUPDATEREASON) +_DEVICETYPE = _descriptor.EnumDescriptor( + name='DeviceType', + full_name='connectstate.DeviceType', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='UNKNOWN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='COMPUTER', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='TABLET', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SMARTPHONE', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SPEAKER', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='TV', + index=5, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AVR', + index=6, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='STB', + index=7, + number=7, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AUDIO_DONGLE', + index=8, + number=8, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='GAME_CONSOLE', + index=9, + number=9, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CAST_VIDEO', + index=10, + number=10, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CAST_AUDIO', + index=11, + number=11, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AUTOMOBILE', + index=12, + number=12, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SMARTWATCH', + index=13, + number=13, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CHROMEBOOK', + index=14, + number=14, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='UNKNOWN_SPOTIFY', + index=15, + number=100, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CAR_THING', + index=16, + number=101, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OBSERVER', + index=17, + number=102, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='HOME_THING', + index=18, + number=103, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3247, + serialized_end=3535, +) +_sym_db.RegisterEnumDescriptor(_DEVICETYPE) + +DeviceType = enum_type_wrapper.EnumTypeWrapper(_DEVICETYPE) +UNKNOWN_SEND_COMMAND_RESULT = 0 +SUCCESS = 1 +DEVICE_NOT_FOUND = 2 +CONTEXT_PLAYER_ERROR = 3 +DEVICE_DISAPPEARED = 4 +UPSTREAM_ERROR = 5 +DEVICE_DOES_NOT_SUPPORT_COMMAND = 6 +RATE_LIMITED = 7 +UNKNOWN_PUT_STATE_REASON = 0 +SPIRC_HELLO = 1 +SPIRC_NOTIFY = 2 +NEW_DEVICE = 3 +PLAYER_STATE_CHANGED = 4 +VOLUME_CHANGED = 5 +PICKER_OPENED = 6 +BECAME_INACTIVE = 7 +SPIRC_V2 = 0 +SPIRC_V3 = 1 +CONNECT_STATE = 2 +UNKNOWN_CLUSTER_UPDATE_REASON = 0 +DEVICES_DISAPPEARED = 1 +DEVICE_STATE_CHANGED = 2 +NEW_DEVICE_APPEARED = 3 +UNKNOWN = 0 +COMPUTER = 1 +TABLET = 2 +SMARTPHONE = 3 +SPEAKER = 4 +TV = 5 +AVR = 6 +STB = 7 +AUDIO_DONGLE = 8 +GAME_CONSOLE = 9 +CAST_VIDEO = 10 +CAST_AUDIO = 11 +AUTOMOBILE = 12 +SMARTWATCH = 13 +CHROMEBOOK = 14 +UNKNOWN_SPOTIFY = 100 +CAR_THING = 101 +OBSERVER = 102 +HOME_THING = 103 + +_CLUSTERUPDATE = _descriptor.Descriptor( + name='ClusterUpdate', + full_name='connectstate.ClusterUpdate', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='cluster', + full_name='connectstate.ClusterUpdate.cluster', + index=0, + number=1, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='update_reason', + full_name='connectstate.ClusterUpdate.update_reason', + index=1, + number=2, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='ack_id', + full_name='connectstate.ClusterUpdate.ack_id', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='devices_that_changed', + full_name='connectstate.ClusterUpdate.devices_that_changed', + index=3, + number=4, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=46, + serialized_end=205, +) + +_DEVICE = _descriptor.Descriptor( + name='Device', + full_name='connectstate.Device', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='device_info', + full_name='connectstate.Device.device_info', + index=0, + number=1, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='player_state', + full_name='connectstate.Device.player_state', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='private_device_info', + full_name='connectstate.Device.private_device_info', + index=2, + number=3, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=208, + serialized_end=374, +) + +_CLUSTER_DEVICEENTRY = _descriptor.Descriptor( + name='DeviceEntry', + full_name='connectstate.Cluster.DeviceEntry', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='connectstate.Cluster.DeviceEntry.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='connectstate.Cluster.DeviceEntry.value', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=b'8\001', + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=556, + serialized_end=627, +) + +_CLUSTER = _descriptor.Descriptor( + name='Cluster', + full_name='connectstate.Cluster', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='timestamp', + full_name='connectstate.Cluster.timestamp', + index=0, + number=1, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='active_device_id', + full_name='connectstate.Cluster.active_device_id', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='player_state', + full_name='connectstate.Cluster.player_state', + index=2, + number=3, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='device', + full_name='connectstate.Cluster.device', + index=3, + number=4, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='transfer_data', + full_name='connectstate.Cluster.transfer_data', + index=4, + number=5, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[ + _CLUSTER_DEVICEENTRY, + ], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=377, + serialized_end=627, +) + +_PUTSTATEREQUEST = _descriptor.Descriptor( + name='PutStateRequest', + full_name='connectstate.PutStateRequest', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='callback_url', + full_name='connectstate.PutStateRequest.callback_url', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='device', + full_name='connectstate.PutStateRequest.device', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='member_type', + full_name='connectstate.PutStateRequest.member_type', + index=2, + number=3, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_active', + full_name='connectstate.PutStateRequest.is_active', + index=3, + number=4, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='put_state_reason', + full_name='connectstate.PutStateRequest.put_state_reason', + index=4, + number=5, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='message_id', + full_name='connectstate.PutStateRequest.message_id', + index=5, + number=6, + type=13, + cpp_type=3, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='last_command_sent_by_device_id', + full_name= + 'connectstate.PutStateRequest.last_command_sent_by_device_id', + index=6, + number=7, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='last_command_message_id', + full_name='connectstate.PutStateRequest.last_command_message_id', + index=7, + number=8, + type=13, + cpp_type=3, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='started_playing_at', + full_name='connectstate.PutStateRequest.started_playing_at', + index=8, + number=9, + type=4, + cpp_type=4, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='has_been_playing_for_ms', + full_name='connectstate.PutStateRequest.has_been_playing_for_ms', + index=9, + number=11, + type=4, + cpp_type=4, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='client_side_timestamp', + full_name='connectstate.PutStateRequest.client_side_timestamp', + index=10, + number=12, + type=4, + cpp_type=4, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='only_write_player_state', + full_name='connectstate.PutStateRequest.only_write_player_state', + index=11, + number=13, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=630, + serialized_end=1047, +) + +_PRIVATEDEVICEINFO = _descriptor.Descriptor( + name='PrivateDeviceInfo', + full_name='connectstate.PrivateDeviceInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='platform', + full_name='connectstate.PrivateDeviceInfo.platform', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1049, + serialized_end=1086, +) + +_SUBSCRIBEREQUEST = _descriptor.Descriptor( + name='SubscribeRequest', + full_name='connectstate.SubscribeRequest', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='callback_url', + full_name='connectstate.SubscribeRequest.callback_url', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1088, + serialized_end=1128, +) + +_DEVICEINFO_METADATAMAPENTRY = _descriptor.Descriptor( + name='MetadataMapEntry', + full_name='connectstate.DeviceInfo.MetadataMapEntry', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='connectstate.DeviceInfo.MetadataMapEntry.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='connectstate.DeviceInfo.MetadataMapEntry.value', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=b'8\001', + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1534, + serialized_end=1584, +) + +_DEVICEINFO = _descriptor.Descriptor( + name='DeviceInfo', + full_name='connectstate.DeviceInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='can_play', + full_name='connectstate.DeviceInfo.can_play', + index=0, + number=1, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='volume', + full_name='connectstate.DeviceInfo.volume', + index=1, + number=2, + type=13, + cpp_type=3, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='name', + full_name='connectstate.DeviceInfo.name', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='capabilities', + full_name='connectstate.DeviceInfo.capabilities', + index=3, + number=4, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='device_software_version', + full_name='connectstate.DeviceInfo.device_software_version', + index=4, + number=6, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='device_type', + full_name='connectstate.DeviceInfo.device_type', + index=5, + number=7, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='spirc_version', + full_name='connectstate.DeviceInfo.spirc_version', + index=6, + number=9, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='device_id', + full_name='connectstate.DeviceInfo.device_id', + index=7, + number=10, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_private_session', + full_name='connectstate.DeviceInfo.is_private_session', + index=8, + number=11, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_social_connect', + full_name='connectstate.DeviceInfo.is_social_connect', + index=9, + number=12, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='client_id', + full_name='connectstate.DeviceInfo.client_id', + index=10, + number=13, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='brand', + full_name='connectstate.DeviceInfo.brand', + index=11, + number=14, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='model', + full_name='connectstate.DeviceInfo.model', + index=12, + number=15, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='metadata_map', + full_name='connectstate.DeviceInfo.metadata_map', + index=13, + number=16, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[ + _DEVICEINFO_METADATAMAPENTRY, + ], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1131, + serialized_end=1584, +) + +_CAPABILITIES = _descriptor.Descriptor( + name='Capabilities', + full_name='connectstate.Capabilities', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='can_be_player', + full_name='connectstate.Capabilities.can_be_player', + index=0, + number=2, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='restrict_to_local', + full_name='connectstate.Capabilities.restrict_to_local', + index=1, + number=3, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='gaia_eq_connect_id', + full_name='connectstate.Capabilities.gaia_eq_connect_id', + index=2, + number=5, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='supports_logout', + full_name='connectstate.Capabilities.supports_logout', + index=3, + number=6, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_observable', + full_name='connectstate.Capabilities.is_observable', + index=4, + number=7, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='volume_steps', + full_name='connectstate.Capabilities.volume_steps', + index=5, + number=8, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='supported_types', + full_name='connectstate.Capabilities.supported_types', + index=6, + number=9, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='command_acks', + full_name='connectstate.Capabilities.command_acks', + index=7, + number=10, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='supports_rename', + full_name='connectstate.Capabilities.supports_rename', + index=8, + number=11, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='hidden', + full_name='connectstate.Capabilities.hidden', + index=9, + number=12, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disable_volume', + full_name='connectstate.Capabilities.disable_volume', + index=10, + number=13, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='connect_disabled', + full_name='connectstate.Capabilities.connect_disabled', + index=11, + number=14, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='supports_playlist_v2', + full_name='connectstate.Capabilities.supports_playlist_v2', + index=12, + number=15, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_controllable', + full_name='connectstate.Capabilities.is_controllable', + index=13, + number=16, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='supports_external_episodes', + full_name='connectstate.Capabilities.supports_external_episodes', + index=14, + number=17, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='supports_set_backend_metadata', + full_name='connectstate.Capabilities.supports_set_backend_metadata', + index=15, + number=18, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='supports_transfer_command', + full_name='connectstate.Capabilities.supports_transfer_command', + index=16, + number=19, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='supports_command_request', + full_name='connectstate.Capabilities.supports_command_request', + index=17, + number=20, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_voice_enabled', + full_name='connectstate.Capabilities.is_voice_enabled', + index=18, + number=21, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='needs_full_player_state', + full_name='connectstate.Capabilities.needs_full_player_state', + index=19, + number=22, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='supports_gzip_pushes', + full_name='connectstate.Capabilities.supports_gzip_pushes', + index=20, + number=23, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1587, + serialized_end=2175, +) + +_CONNECTCOMMANDOPTIONS = _descriptor.Descriptor( + name='ConnectCommandOptions', + full_name='connectstate.ConnectCommandOptions', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='message_id', + full_name='connectstate.ConnectCommandOptions.message_id', + index=0, + number=1, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=2177, + serialized_end=2220, +) + +_LOGOUTCOMMAND = _descriptor.Descriptor( + name='LogoutCommand', + full_name='connectstate.LogoutCommand', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='command_options', + full_name='connectstate.LogoutCommand.command_options', + index=0, + number=1, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=2222, + serialized_end=2299, +) + +_SETVOLUMECOMMAND = _descriptor.Descriptor( + name='SetVolumeCommand', + full_name='connectstate.SetVolumeCommand', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='volume', + full_name='connectstate.SetVolumeCommand.volume', + index=0, + number=1, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='command_options', + full_name='connectstate.SetVolumeCommand.command_options', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=2301, + serialized_end=2397, +) + +_RENAMECOMMAND = _descriptor.Descriptor( + name='RenameCommand', + full_name='connectstate.RenameCommand', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='rename_to', + full_name='connectstate.RenameCommand.rename_to', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='command_options', + full_name='connectstate.RenameCommand.command_options', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=2399, + serialized_end=2495, +) + +_SETBACKENDMETADATACOMMAND_METADATAENTRY = _descriptor.Descriptor( + name='MetadataEntry', + full_name='connectstate.SetBackendMetadataCommand.MetadataEntry', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name= + 'connectstate.SetBackendMetadataCommand.MetadataEntry.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name= + 'connectstate.SetBackendMetadataCommand.MetadataEntry.value', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=b'8\001', + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=2600, + serialized_end=2647, +) + +_SETBACKENDMETADATACOMMAND = _descriptor.Descriptor( + name='SetBackendMetadataCommand', + full_name='connectstate.SetBackendMetadataCommand', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='metadata', + full_name='connectstate.SetBackendMetadataCommand.metadata', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[ + _SETBACKENDMETADATACOMMAND_METADATAENTRY, + ], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=2498, + serialized_end=2647, +) + +_CLUSTERUPDATE.fields_by_name['cluster'].message_type = _CLUSTER +_CLUSTERUPDATE.fields_by_name['update_reason'].enum_type = _CLUSTERUPDATEREASON +_DEVICE.fields_by_name['device_info'].message_type = _DEVICEINFO +_DEVICE.fields_by_name['player_state'].message_type = player__pb2._PLAYERSTATE +_DEVICE.fields_by_name['private_device_info'].message_type = _PRIVATEDEVICEINFO +_CLUSTER_DEVICEENTRY.fields_by_name['value'].message_type = _DEVICEINFO +_CLUSTER_DEVICEENTRY.containing_type = _CLUSTER +_CLUSTER.fields_by_name['player_state'].message_type = player__pb2._PLAYERSTATE +_CLUSTER.fields_by_name['device'].message_type = _CLUSTER_DEVICEENTRY +_PUTSTATEREQUEST.fields_by_name['device'].message_type = _DEVICE +_PUTSTATEREQUEST.fields_by_name['member_type'].enum_type = _MEMBERTYPE +_PUTSTATEREQUEST.fields_by_name['put_state_reason'].enum_type = _PUTSTATEREASON +_DEVICEINFO_METADATAMAPENTRY.containing_type = _DEVICEINFO +_DEVICEINFO.fields_by_name['capabilities'].message_type = _CAPABILITIES +_DEVICEINFO.fields_by_name['device_type'].enum_type = _DEVICETYPE +_DEVICEINFO.fields_by_name[ + 'metadata_map'].message_type = _DEVICEINFO_METADATAMAPENTRY +_LOGOUTCOMMAND.fields_by_name[ + 'command_options'].message_type = _CONNECTCOMMANDOPTIONS +_SETVOLUMECOMMAND.fields_by_name[ + 'command_options'].message_type = _CONNECTCOMMANDOPTIONS +_RENAMECOMMAND.fields_by_name[ + 'command_options'].message_type = _CONNECTCOMMANDOPTIONS +_SETBACKENDMETADATACOMMAND_METADATAENTRY.containing_type = _SETBACKENDMETADATACOMMAND +_SETBACKENDMETADATACOMMAND.fields_by_name[ + 'metadata'].message_type = _SETBACKENDMETADATACOMMAND_METADATAENTRY +DESCRIPTOR.message_types_by_name['ClusterUpdate'] = _CLUSTERUPDATE +DESCRIPTOR.message_types_by_name['Device'] = _DEVICE +DESCRIPTOR.message_types_by_name['Cluster'] = _CLUSTER +DESCRIPTOR.message_types_by_name['PutStateRequest'] = _PUTSTATEREQUEST +DESCRIPTOR.message_types_by_name['PrivateDeviceInfo'] = _PRIVATEDEVICEINFO +DESCRIPTOR.message_types_by_name['SubscribeRequest'] = _SUBSCRIBEREQUEST +DESCRIPTOR.message_types_by_name['DeviceInfo'] = _DEVICEINFO +DESCRIPTOR.message_types_by_name['Capabilities'] = _CAPABILITIES +DESCRIPTOR.message_types_by_name[ + 'ConnectCommandOptions'] = _CONNECTCOMMANDOPTIONS +DESCRIPTOR.message_types_by_name['LogoutCommand'] = _LOGOUTCOMMAND +DESCRIPTOR.message_types_by_name['SetVolumeCommand'] = _SETVOLUMECOMMAND +DESCRIPTOR.message_types_by_name['RenameCommand'] = _RENAMECOMMAND +DESCRIPTOR.message_types_by_name[ + 'SetBackendMetadataCommand'] = _SETBACKENDMETADATACOMMAND +DESCRIPTOR.enum_types_by_name['SendCommandResult'] = _SENDCOMMANDRESULT +DESCRIPTOR.enum_types_by_name['PutStateReason'] = _PUTSTATEREASON +DESCRIPTOR.enum_types_by_name['MemberType'] = _MEMBERTYPE +DESCRIPTOR.enum_types_by_name['ClusterUpdateReason'] = _CLUSTERUPDATEREASON +DESCRIPTOR.enum_types_by_name['DeviceType'] = _DEVICETYPE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +ClusterUpdate = _reflection.GeneratedProtocolMessageType( + 'ClusterUpdate', + (_message.Message, ), + { + 'DESCRIPTOR': _CLUSTERUPDATE, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.ClusterUpdate) + }) +_sym_db.RegisterMessage(ClusterUpdate) + +Device = _reflection.GeneratedProtocolMessageType( + 'Device', + (_message.Message, ), + { + 'DESCRIPTOR': _DEVICE, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.Device) + }) +_sym_db.RegisterMessage(Device) + +Cluster = _reflection.GeneratedProtocolMessageType( + 'Cluster', + (_message.Message, ), + { + 'DeviceEntry': + _reflection.GeneratedProtocolMessageType( + 'DeviceEntry', + (_message.Message, ), + { + 'DESCRIPTOR': _CLUSTER_DEVICEENTRY, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.Cluster.DeviceEntry) + }), + 'DESCRIPTOR': + _CLUSTER, + '__module__': + 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.Cluster) + }) +_sym_db.RegisterMessage(Cluster) +_sym_db.RegisterMessage(Cluster.DeviceEntry) + +PutStateRequest = _reflection.GeneratedProtocolMessageType( + 'PutStateRequest', + (_message.Message, ), + { + 'DESCRIPTOR': _PUTSTATEREQUEST, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.PutStateRequest) + }) +_sym_db.RegisterMessage(PutStateRequest) + +PrivateDeviceInfo = _reflection.GeneratedProtocolMessageType( + 'PrivateDeviceInfo', + (_message.Message, ), + { + 'DESCRIPTOR': _PRIVATEDEVICEINFO, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.PrivateDeviceInfo) + }) +_sym_db.RegisterMessage(PrivateDeviceInfo) + +SubscribeRequest = _reflection.GeneratedProtocolMessageType( + 'SubscribeRequest', + (_message.Message, ), + { + 'DESCRIPTOR': _SUBSCRIBEREQUEST, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.SubscribeRequest) + }) +_sym_db.RegisterMessage(SubscribeRequest) + +DeviceInfo = _reflection.GeneratedProtocolMessageType( + 'DeviceInfo', + (_message.Message, ), + { + 'MetadataMapEntry': + _reflection.GeneratedProtocolMessageType( + 'MetadataMapEntry', + (_message.Message, ), + { + 'DESCRIPTOR': _DEVICEINFO_METADATAMAPENTRY, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.DeviceInfo.MetadataMapEntry) + }), + 'DESCRIPTOR': + _DEVICEINFO, + '__module__': + 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.DeviceInfo) + }) +_sym_db.RegisterMessage(DeviceInfo) +_sym_db.RegisterMessage(DeviceInfo.MetadataMapEntry) + +Capabilities = _reflection.GeneratedProtocolMessageType( + 'Capabilities', + (_message.Message, ), + { + 'DESCRIPTOR': _CAPABILITIES, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.Capabilities) + }) +_sym_db.RegisterMessage(Capabilities) + +ConnectCommandOptions = _reflection.GeneratedProtocolMessageType( + 'ConnectCommandOptions', + (_message.Message, ), + { + 'DESCRIPTOR': _CONNECTCOMMANDOPTIONS, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.ConnectCommandOptions) + }) +_sym_db.RegisterMessage(ConnectCommandOptions) + +LogoutCommand = _reflection.GeneratedProtocolMessageType( + 'LogoutCommand', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGOUTCOMMAND, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.LogoutCommand) + }) +_sym_db.RegisterMessage(LogoutCommand) + +SetVolumeCommand = _reflection.GeneratedProtocolMessageType( + 'SetVolumeCommand', + (_message.Message, ), + { + 'DESCRIPTOR': _SETVOLUMECOMMAND, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.SetVolumeCommand) + }) +_sym_db.RegisterMessage(SetVolumeCommand) + +RenameCommand = _reflection.GeneratedProtocolMessageType( + 'RenameCommand', + (_message.Message, ), + { + 'DESCRIPTOR': _RENAMECOMMAND, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.RenameCommand) + }) +_sym_db.RegisterMessage(RenameCommand) + +SetBackendMetadataCommand = _reflection.GeneratedProtocolMessageType( + 'SetBackendMetadataCommand', + (_message.Message, ), + { + 'MetadataEntry': + _reflection.GeneratedProtocolMessageType( + 'MetadataEntry', + (_message.Message, ), + { + 'DESCRIPTOR': _SETBACKENDMETADATACOMMAND_METADATAENTRY, + '__module__': 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.SetBackendMetadataCommand.MetadataEntry) + }), + 'DESCRIPTOR': + _SETBACKENDMETADATACOMMAND, + '__module__': + 'connect_pb2' + # @@protoc_insertion_point(class_scope:connectstate.SetBackendMetadataCommand) + }) +_sym_db.RegisterMessage(SetBackendMetadataCommand) +_sym_db.RegisterMessage(SetBackendMetadataCommand.MetadataEntry) + +DESCRIPTOR._options = None +_CLUSTER_DEVICEENTRY._options = None +_DEVICEINFO_METADATAMAPENTRY._options = None +_SETBACKENDMETADATACOMMAND_METADATAENTRY._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/ExplicitContentPubsub.py b/src/librespot/proto/ExplicitContentPubsub.py new file mode 100644 index 0000000..26ed33e --- /dev/null +++ b/src/librespot/proto/ExplicitContentPubsub.py @@ -0,0 +1,147 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: explicit_content_pubsub.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='explicit_content_pubsub.proto', + package='spotify.explicit_content.proto', + syntax='proto2', + serialized_options=b'\n\024com.spotify.explicitH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x1d\x65xplicit_content_pubsub.proto\x12\x1espotify.explicit_content.proto\"*\n\x0cKeyValuePair\x12\x0b\n\x03key\x18\x01 \x02(\t\x12\r\n\x05value\x18\x02 \x02(\t\"S\n\x14UserAttributesUpdate\x12;\n\x05pairs\x18\x01 \x03(\x0b\x32,.spotify.explicit_content.proto.KeyValuePairB\x18\n\x14\x63om.spotify.explicitH\x02' +) + +_KEYVALUEPAIR = _descriptor.Descriptor( + name='KeyValuePair', + full_name='spotify.explicit_content.proto.KeyValuePair', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='spotify.explicit_content.proto.KeyValuePair.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='spotify.explicit_content.proto.KeyValuePair.value', + index=1, + number=2, + type=9, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=65, + serialized_end=107, +) + +_USERATTRIBUTESUPDATE = _descriptor.Descriptor( + name='UserAttributesUpdate', + full_name='spotify.explicit_content.proto.UserAttributesUpdate', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='pairs', + full_name= + 'spotify.explicit_content.proto.UserAttributesUpdate.pairs', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=109, + serialized_end=192, +) + +_USERATTRIBUTESUPDATE.fields_by_name['pairs'].message_type = _KEYVALUEPAIR +DESCRIPTOR.message_types_by_name['KeyValuePair'] = _KEYVALUEPAIR +DESCRIPTOR.message_types_by_name[ + 'UserAttributesUpdate'] = _USERATTRIBUTESUPDATE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +KeyValuePair = _reflection.GeneratedProtocolMessageType( + 'KeyValuePair', + (_message.Message, ), + { + 'DESCRIPTOR': _KEYVALUEPAIR, + '__module__': 'explicit_content_pubsub_pb2' + # @@protoc_insertion_point(class_scope:spotify.explicit_content.proto.KeyValuePair) + }) +_sym_db.RegisterMessage(KeyValuePair) + +UserAttributesUpdate = _reflection.GeneratedProtocolMessageType( + 'UserAttributesUpdate', + (_message.Message, ), + { + 'DESCRIPTOR': _USERATTRIBUTESUPDATE, + '__module__': 'explicit_content_pubsub_pb2' + # @@protoc_insertion_point(class_scope:spotify.explicit_content.proto.UserAttributesUpdate) + }) +_sym_db.RegisterMessage(UserAttributesUpdate) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/Keyexchange.py b/src/librespot/proto/Keyexchange.py new file mode 100644 index 0000000..663ee3b --- /dev/null +++ b/src/librespot/proto/Keyexchange.py @@ -0,0 +1,2497 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: keyexchange.proto +"""Generated protocol buffer code.""" +from google.protobuf.internal import enum_type_wrapper +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='keyexchange.proto', + package='spotify', + syntax='proto2', + serialized_options=b'\n\013com.spotify', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x11keyexchange.proto\x12\x07spotify\"\xe0\x02\n\x0b\x43lientHello\x12&\n\nbuild_info\x18\n \x02(\x0b\x32\x12.spotify.BuildInfo\x12\x34\n\x16\x66ingerprints_supported\x18\x14 \x03(\x0e\x32\x14.spotify.Fingerprint\x12\x34\n\x16\x63ryptosuites_supported\x18\x1e \x03(\x0e\x32\x14.spotify.Cryptosuite\x12\x30\n\x14powschemes_supported\x18( \x03(\x0e\x32\x12.spotify.Powscheme\x12:\n\x12login_crypto_hello\x18\x32 \x02(\x0b\x32\x1e.spotify.LoginCryptoHelloUnion\x12\x14\n\x0c\x63lient_nonce\x18< \x02(\x0c\x12\x0f\n\x07padding\x18\x46 \x01(\x0c\x12(\n\x0b\x66\x65\x61ture_set\x18P \x01(\x0b\x32\x13.spotify.FeatureSet\"\x92\x01\n\tBuildInfo\x12!\n\x07product\x18\n \x02(\x0e\x32\x10.spotify.Product\x12,\n\rproduct_flags\x18\x14 \x03(\x0e\x32\x15.spotify.ProductFlags\x12#\n\x08platform\x18\x1e \x02(\x0e\x32\x11.spotify.Platform\x12\x0f\n\x07version\x18( \x02(\x04\"W\n\x15LoginCryptoHelloUnion\x12>\n\x0e\x64iffie_hellman\x18\n \x01(\x0b\x32&.spotify.LoginCryptoDiffieHellmanHello\"F\n\x1dLoginCryptoDiffieHellmanHello\x12\n\n\x02gc\x18\n \x02(\x0c\x12\x19\n\x11server_keys_known\x18\x14 \x02(\r\";\n\nFeatureSet\x12\x13\n\x0b\x61utoupdate2\x18\x01 \x01(\x08\x12\x18\n\x10\x63urrent_location\x18\x02 \x01(\x08\"\x9c\x01\n\x11\x41PResponseMessage\x12\'\n\tchallenge\x18\n \x01(\x0b\x32\x14.spotify.APChallenge\x12\x30\n\x07upgrade\x18\x14 \x01(\x0b\x32\x1f.spotify.UpgradeRequiredMessage\x12,\n\x0clogin_failed\x18\x1e \x01(\x0b\x32\x16.spotify.APLoginFailed\"\xa7\x02\n\x0b\x41PChallenge\x12\x42\n\x16login_crypto_challenge\x18\n \x02(\x0b\x32\".spotify.LoginCryptoChallengeUnion\x12\x41\n\x15\x66ingerprint_challenge\x18\x14 \x02(\x0b\x32\".spotify.FingerprintChallengeUnion\x12\x31\n\rpow_challenge\x18\x1e \x02(\x0b\x32\x1a.spotify.PoWChallengeUnion\x12\x37\n\x10\x63rypto_challenge\x18( \x02(\x0b\x32\x1d.spotify.CryptoChallengeUnion\x12\x14\n\x0cserver_nonce\x18\x32 \x02(\x0c\x12\x0f\n\x07padding\x18< \x01(\x0c\"_\n\x19LoginCryptoChallengeUnion\x12\x42\n\x0e\x64iffie_hellman\x18\n \x01(\x0b\x32*.spotify.LoginCryptoDiffieHellmanChallenge\"c\n!LoginCryptoDiffieHellmanChallenge\x12\n\n\x02gs\x18\n \x02(\x0c\x12\x1c\n\x14server_signature_key\x18\x14 \x02(\x05\x12\x14\n\x0cgs_signature\x18\x1e \x02(\x0c\"\x8c\x01\n\x19\x46ingerprintChallengeUnion\x12\x31\n\x05grain\x18\n \x01(\x0b\x32\".spotify.FingerprintGrainChallenge\x12<\n\x0bhmac_ripemd\x18\x14 \x01(\x0b\x32\'.spotify.FingerprintHmacRipemdChallenge\"(\n\x19\x46ingerprintGrainChallenge\x12\x0b\n\x03kek\x18\n \x02(\x0c\"3\n\x1e\x46ingerprintHmacRipemdChallenge\x12\x11\n\tchallenge\x18\n \x02(\x0c\"E\n\x11PoWChallengeUnion\x12\x30\n\thash_cash\x18\n \x01(\x0b\x32\x1d.spotify.PoWHashCashChallenge\"F\n\x14PoWHashCashChallenge\x12\x0e\n\x06prefix\x18\n \x01(\x0c\x12\x0e\n\x06length\x18\x14 \x01(\x05\x12\x0e\n\x06target\x18\x1e \x01(\x05\"\x84\x01\n\x14\x43ryptoChallengeUnion\x12\x30\n\x07shannon\x18\n \x01(\x0b\x32\x1f.spotify.CryptoShannonChallenge\x12:\n\rrc4_sha1_hmac\x18\x14 \x01(\x0b\x32#.spotify.CryptoRc4Sha1HmacChallenge\"\x18\n\x16\x43ryptoShannonChallenge\"\x1c\n\x1a\x43ryptoRc4Sha1HmacChallenge\"]\n\x16UpgradeRequiredMessage\x12\x1b\n\x13upgrade_signed_part\x18\n \x02(\x0c\x12\x11\n\tsignature\x18\x14 \x02(\x0c\x12\x13\n\x0bhttp_suffix\x18\x1e \x01(\t\"w\n\rAPLoginFailed\x12&\n\nerror_code\x18\n \x02(\x0e\x32\x12.spotify.ErrorCode\x12\x13\n\x0bretry_delay\x18\x14 \x01(\x05\x12\x0e\n\x06\x65xpiry\x18\x1e \x01(\x05\x12\x19\n\x11\x65rror_description\x18( \x01(\t\"\xc3\x01\n\x17\x43lientResponsePlaintext\x12@\n\x15login_crypto_response\x18\n \x02(\x0b\x32!.spotify.LoginCryptoResponseUnion\x12/\n\x0cpow_response\x18\x14 \x02(\x0b\x32\x19.spotify.PoWResponseUnion\x12\x35\n\x0f\x63rypto_response\x18\x1e \x02(\x0b\x32\x1c.spotify.CryptoResponseUnion\"]\n\x18LoginCryptoResponseUnion\x12\x41\n\x0e\x64iffie_hellman\x18\n \x01(\x0b\x32).spotify.LoginCryptoDiffieHellmanResponse\"0\n LoginCryptoDiffieHellmanResponse\x12\x0c\n\x04hmac\x18\n \x02(\x0c\"C\n\x10PoWResponseUnion\x12/\n\thash_cash\x18\n \x01(\x0b\x32\x1c.spotify.PoWHashCashResponse\"*\n\x13PoWHashCashResponse\x12\x13\n\x0bhash_suffix\x18\n \x02(\x0c\"\x81\x01\n\x13\x43ryptoResponseUnion\x12/\n\x07shannon\x18\n \x01(\x0b\x32\x1e.spotify.CryptoShannonResponse\x12\x39\n\rrc4_sha1_hmac\x18\x14 \x01(\x0b\x32\".spotify.CryptoRc4Sha1HmacResponse\"&\n\x15\x43ryptoShannonResponse\x12\r\n\x05\x64ummy\x18\x01 \x01(\x05\"*\n\x19\x43ryptoRc4Sha1HmacResponse\x12\r\n\x05\x64ummy\x18\x01 \x01(\x05*\x7f\n\x07Product\x12\x12\n\x0ePRODUCT_CLIENT\x10\x00\x12\x16\n\x12PRODUCT_LIBSPOTIFY\x10\x01\x12\x12\n\x0ePRODUCT_MOBILE\x10\x02\x12\x13\n\x0fPRODUCT_PARTNER\x10\x03\x12\x1f\n\x1bPRODUCT_LIBSPOTIFY_EMBEDDED\x10\x05*A\n\x0cProductFlags\x12\x15\n\x11PRODUCT_FLAG_NONE\x10\x00\x12\x1a\n\x16PRODUCT_FLAG_DEV_BUILD\x10\x01*\xdc\x04\n\x08Platform\x12\x16\n\x12PLATFORM_WIN32_X86\x10\x00\x12\x14\n\x10PLATFORM_OSX_X86\x10\x01\x12\x16\n\x12PLATFORM_LINUX_X86\x10\x02\x12\x17\n\x13PLATFORM_IPHONE_ARM\x10\x03\x12\x14\n\x10PLATFORM_S60_ARM\x10\x04\x12\x14\n\x10PLATFORM_OSX_PPC\x10\x05\x12\x18\n\x14PLATFORM_ANDROID_ARM\x10\x06\x12\x1b\n\x17PLATFORM_WINDOWS_CE_ARM\x10\x07\x12\x19\n\x15PLATFORM_LINUX_X86_64\x10\x08\x12\x17\n\x13PLATFORM_OSX_X86_64\x10\t\x12\x15\n\x11PLATFORM_PALM_ARM\x10\n\x12\x15\n\x11PLATFORM_LINUX_SH\x10\x0b\x12\x18\n\x14PLATFORM_FREEBSD_X86\x10\x0c\x12\x1b\n\x17PLATFORM_FREEBSD_X86_64\x10\r\x12\x1b\n\x17PLATFORM_BLACKBERRY_ARM\x10\x0e\x12\x12\n\x0ePLATFORM_SONOS\x10\x0f\x12\x17\n\x13PLATFORM_LINUX_MIPS\x10\x10\x12\x16\n\x12PLATFORM_LINUX_ARM\x10\x11\x12\x19\n\x15PLATFORM_LOGITECH_ARM\x10\x12\x12\x1b\n\x17PLATFORM_LINUX_BLACKFIN\x10\x13\x12\x14\n\x10PLATFORM_WP7_ARM\x10\x14\x12\x16\n\x12PLATFORM_ONKYO_ARM\x10\x15\x12\x17\n\x13PLATFORM_QNXNTO_ARM\x10\x16\x12\x14\n\x10PLATFORM_BCO_ARM\x10\x17*A\n\x0b\x46ingerprint\x12\x15\n\x11\x46INGERPRINT_GRAIN\x10\x00\x12\x1b\n\x17\x46INGERPRINT_HMAC_RIPEMD\x10\x01*G\n\x0b\x43ryptosuite\x12\x18\n\x14\x43RYPTO_SUITE_SHANNON\x10\x00\x12\x1e\n\x1a\x43RYPTO_SUITE_RC4_SHA1_HMAC\x10\x01*\x1e\n\tPowscheme\x12\x11\n\rPOW_HASH_CASH\x10\x00*\x89\x02\n\tErrorCode\x12\x11\n\rProtocolError\x10\x00\x12\x10\n\x0cTryAnotherAP\x10\x02\x12\x13\n\x0f\x42\x61\x64\x43onnectionId\x10\x05\x12\x15\n\x11TravelRestriction\x10\t\x12\x1a\n\x16PremiumAccountRequired\x10\x0b\x12\x12\n\x0e\x42\x61\x64\x43redentials\x10\x0c\x12\x1f\n\x1b\x43ouldNotValidateCredentials\x10\r\x12\x11\n\rAccountExists\x10\x0e\x12\x1d\n\x19\x45xtraVerificationRequired\x10\x0f\x12\x11\n\rInvalidAppKey\x10\x10\x12\x15\n\x11\x41pplicationBanned\x10\x11\x42\r\n\x0b\x63om.spotify' +) + +_PRODUCT = _descriptor.EnumDescriptor( + name='Product', + full_name='spotify.Product', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='PRODUCT_CLIENT', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PRODUCT_LIBSPOTIFY', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PRODUCT_MOBILE', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PRODUCT_PARTNER', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PRODUCT_LIBSPOTIFY_EMBEDDED', + index=4, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2871, + serialized_end=2998, +) +_sym_db.RegisterEnumDescriptor(_PRODUCT) + +Product = enum_type_wrapper.EnumTypeWrapper(_PRODUCT) +_PRODUCTFLAGS = _descriptor.EnumDescriptor( + name='ProductFlags', + full_name='spotify.ProductFlags', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='PRODUCT_FLAG_NONE', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PRODUCT_FLAG_DEV_BUILD', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3000, + serialized_end=3065, +) +_sym_db.RegisterEnumDescriptor(_PRODUCTFLAGS) + +ProductFlags = enum_type_wrapper.EnumTypeWrapper(_PRODUCTFLAGS) +_PLATFORM = _descriptor.EnumDescriptor( + name='Platform', + full_name='spotify.Platform', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='PLATFORM_WIN32_X86', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_OSX_X86', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_LINUX_X86', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_IPHONE_ARM', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_S60_ARM', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_OSX_PPC', + index=5, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_ANDROID_ARM', + index=6, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_WINDOWS_CE_ARM', + index=7, + number=7, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_LINUX_X86_64', + index=8, + number=8, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_OSX_X86_64', + index=9, + number=9, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_PALM_ARM', + index=10, + number=10, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_LINUX_SH', + index=11, + number=11, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_FREEBSD_X86', + index=12, + number=12, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_FREEBSD_X86_64', + index=13, + number=13, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_BLACKBERRY_ARM', + index=14, + number=14, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_SONOS', + index=15, + number=15, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_LINUX_MIPS', + index=16, + number=16, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_LINUX_ARM', + index=17, + number=17, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_LOGITECH_ARM', + index=18, + number=18, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_LINUX_BLACKFIN', + index=19, + number=19, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_WP7_ARM', + index=20, + number=20, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_ONKYO_ARM', + index=21, + number=21, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_QNXNTO_ARM', + index=22, + number=22, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PLATFORM_BCO_ARM', + index=23, + number=23, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3068, + serialized_end=3672, +) +_sym_db.RegisterEnumDescriptor(_PLATFORM) + +Platform = enum_type_wrapper.EnumTypeWrapper(_PLATFORM) +_FINGERPRINT = _descriptor.EnumDescriptor( + name='Fingerprint', + full_name='spotify.Fingerprint', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='FINGERPRINT_GRAIN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='FINGERPRINT_HMAC_RIPEMD', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3674, + serialized_end=3739, +) +_sym_db.RegisterEnumDescriptor(_FINGERPRINT) + +Fingerprint = enum_type_wrapper.EnumTypeWrapper(_FINGERPRINT) +_CRYPTOSUITE = _descriptor.EnumDescriptor( + name='Cryptosuite', + full_name='spotify.Cryptosuite', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='CRYPTO_SUITE_SHANNON', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CRYPTO_SUITE_RC4_SHA1_HMAC', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3741, + serialized_end=3812, +) +_sym_db.RegisterEnumDescriptor(_CRYPTOSUITE) + +Cryptosuite = enum_type_wrapper.EnumTypeWrapper(_CRYPTOSUITE) +_POWSCHEME = _descriptor.EnumDescriptor( + name='Powscheme', + full_name='spotify.Powscheme', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='POW_HASH_CASH', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3814, + serialized_end=3844, +) +_sym_db.RegisterEnumDescriptor(_POWSCHEME) + +Powscheme = enum_type_wrapper.EnumTypeWrapper(_POWSCHEME) +_ERRORCODE = _descriptor.EnumDescriptor( + name='ErrorCode', + full_name='spotify.ErrorCode', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='ProtocolError', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='TryAnotherAP', + index=1, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='BadConnectionId', + index=2, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='TravelRestriction', + index=3, + number=9, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PremiumAccountRequired', + index=4, + number=11, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='BadCredentials', + index=5, + number=12, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CouldNotValidateCredentials', + index=6, + number=13, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AccountExists', + index=7, + number=14, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='ExtraVerificationRequired', + index=8, + number=15, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='InvalidAppKey', + index=9, + number=16, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='ApplicationBanned', + index=10, + number=17, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3847, + serialized_end=4112, +) +_sym_db.RegisterEnumDescriptor(_ERRORCODE) + +ErrorCode = enum_type_wrapper.EnumTypeWrapper(_ERRORCODE) +PRODUCT_CLIENT = 0 +PRODUCT_LIBSPOTIFY = 1 +PRODUCT_MOBILE = 2 +PRODUCT_PARTNER = 3 +PRODUCT_LIBSPOTIFY_EMBEDDED = 5 +PRODUCT_FLAG_NONE = 0 +PRODUCT_FLAG_DEV_BUILD = 1 +PLATFORM_WIN32_X86 = 0 +PLATFORM_OSX_X86 = 1 +PLATFORM_LINUX_X86 = 2 +PLATFORM_IPHONE_ARM = 3 +PLATFORM_S60_ARM = 4 +PLATFORM_OSX_PPC = 5 +PLATFORM_ANDROID_ARM = 6 +PLATFORM_WINDOWS_CE_ARM = 7 +PLATFORM_LINUX_X86_64 = 8 +PLATFORM_OSX_X86_64 = 9 +PLATFORM_PALM_ARM = 10 +PLATFORM_LINUX_SH = 11 +PLATFORM_FREEBSD_X86 = 12 +PLATFORM_FREEBSD_X86_64 = 13 +PLATFORM_BLACKBERRY_ARM = 14 +PLATFORM_SONOS = 15 +PLATFORM_LINUX_MIPS = 16 +PLATFORM_LINUX_ARM = 17 +PLATFORM_LOGITECH_ARM = 18 +PLATFORM_LINUX_BLACKFIN = 19 +PLATFORM_WP7_ARM = 20 +PLATFORM_ONKYO_ARM = 21 +PLATFORM_QNXNTO_ARM = 22 +PLATFORM_BCO_ARM = 23 +FINGERPRINT_GRAIN = 0 +FINGERPRINT_HMAC_RIPEMD = 1 +CRYPTO_SUITE_SHANNON = 0 +CRYPTO_SUITE_RC4_SHA1_HMAC = 1 +POW_HASH_CASH = 0 +ProtocolError = 0 +TryAnotherAP = 2 +BadConnectionId = 5 +TravelRestriction = 9 +PremiumAccountRequired = 11 +BadCredentials = 12 +CouldNotValidateCredentials = 13 +AccountExists = 14 +ExtraVerificationRequired = 15 +InvalidAppKey = 16 +ApplicationBanned = 17 + +_CLIENTHELLO = _descriptor.Descriptor( + name='ClientHello', + full_name='spotify.ClientHello', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='build_info', + full_name='spotify.ClientHello.build_info', + index=0, + number=10, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='fingerprints_supported', + full_name='spotify.ClientHello.fingerprints_supported', + index=1, + number=20, + type=14, + cpp_type=8, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='cryptosuites_supported', + full_name='spotify.ClientHello.cryptosuites_supported', + index=2, + number=30, + type=14, + cpp_type=8, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='powschemes_supported', + full_name='spotify.ClientHello.powschemes_supported', + index=3, + number=40, + type=14, + cpp_type=8, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='login_crypto_hello', + full_name='spotify.ClientHello.login_crypto_hello', + index=4, + number=50, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='client_nonce', + full_name='spotify.ClientHello.client_nonce', + index=5, + number=60, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='padding', + full_name='spotify.ClientHello.padding', + index=6, + number=70, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='feature_set', + full_name='spotify.ClientHello.feature_set', + index=7, + number=80, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=31, + serialized_end=383, +) + +_BUILDINFO = _descriptor.Descriptor( + name='BuildInfo', + full_name='spotify.BuildInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='product', + full_name='spotify.BuildInfo.product', + index=0, + number=10, + type=14, + cpp_type=8, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='product_flags', + full_name='spotify.BuildInfo.product_flags', + index=1, + number=20, + type=14, + cpp_type=8, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='platform', + full_name='spotify.BuildInfo.platform', + index=2, + number=30, + type=14, + cpp_type=8, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='version', + full_name='spotify.BuildInfo.version', + index=3, + number=40, + type=4, + cpp_type=4, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=386, + serialized_end=532, +) + +_LOGINCRYPTOHELLOUNION = _descriptor.Descriptor( + name='LoginCryptoHelloUnion', + full_name='spotify.LoginCryptoHelloUnion', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='diffie_hellman', + full_name='spotify.LoginCryptoHelloUnion.diffie_hellman', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=534, + serialized_end=621, +) + +_LOGINCRYPTODIFFIEHELLMANHELLO = _descriptor.Descriptor( + name='LoginCryptoDiffieHellmanHello', + full_name='spotify.LoginCryptoDiffieHellmanHello', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='gc', + full_name='spotify.LoginCryptoDiffieHellmanHello.gc', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='server_keys_known', + full_name='spotify.LoginCryptoDiffieHellmanHello.server_keys_known', + index=1, + number=20, + type=13, + cpp_type=3, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=623, + serialized_end=693, +) + +_FEATURESET = _descriptor.Descriptor( + name='FeatureSet', + full_name='spotify.FeatureSet', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='autoupdate2', + full_name='spotify.FeatureSet.autoupdate2', + index=0, + number=1, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='current_location', + full_name='spotify.FeatureSet.current_location', + index=1, + number=2, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=695, + serialized_end=754, +) + +_APRESPONSEMESSAGE = _descriptor.Descriptor( + name='APResponseMessage', + full_name='spotify.APResponseMessage', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='challenge', + full_name='spotify.APResponseMessage.challenge', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='upgrade', + full_name='spotify.APResponseMessage.upgrade', + index=1, + number=20, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='login_failed', + full_name='spotify.APResponseMessage.login_failed', + index=2, + number=30, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=757, + serialized_end=913, +) + +_APCHALLENGE = _descriptor.Descriptor( + name='APChallenge', + full_name='spotify.APChallenge', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='login_crypto_challenge', + full_name='spotify.APChallenge.login_crypto_challenge', + index=0, + number=10, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='fingerprint_challenge', + full_name='spotify.APChallenge.fingerprint_challenge', + index=1, + number=20, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='pow_challenge', + full_name='spotify.APChallenge.pow_challenge', + index=2, + number=30, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='crypto_challenge', + full_name='spotify.APChallenge.crypto_challenge', + index=3, + number=40, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='server_nonce', + full_name='spotify.APChallenge.server_nonce', + index=4, + number=50, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='padding', + full_name='spotify.APChallenge.padding', + index=5, + number=60, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=916, + serialized_end=1211, +) + +_LOGINCRYPTOCHALLENGEUNION = _descriptor.Descriptor( + name='LoginCryptoChallengeUnion', + full_name='spotify.LoginCryptoChallengeUnion', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='diffie_hellman', + full_name='spotify.LoginCryptoChallengeUnion.diffie_hellman', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1213, + serialized_end=1308, +) + +_LOGINCRYPTODIFFIEHELLMANCHALLENGE = _descriptor.Descriptor( + name='LoginCryptoDiffieHellmanChallenge', + full_name='spotify.LoginCryptoDiffieHellmanChallenge', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='gs', + full_name='spotify.LoginCryptoDiffieHellmanChallenge.gs', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='server_signature_key', + full_name= + 'spotify.LoginCryptoDiffieHellmanChallenge.server_signature_key', + index=1, + number=20, + type=5, + cpp_type=1, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='gs_signature', + full_name='spotify.LoginCryptoDiffieHellmanChallenge.gs_signature', + index=2, + number=30, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1310, + serialized_end=1409, +) + +_FINGERPRINTCHALLENGEUNION = _descriptor.Descriptor( + name='FingerprintChallengeUnion', + full_name='spotify.FingerprintChallengeUnion', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='grain', + full_name='spotify.FingerprintChallengeUnion.grain', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='hmac_ripemd', + full_name='spotify.FingerprintChallengeUnion.hmac_ripemd', + index=1, + number=20, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1412, + serialized_end=1552, +) + +_FINGERPRINTGRAINCHALLENGE = _descriptor.Descriptor( + name='FingerprintGrainChallenge', + full_name='spotify.FingerprintGrainChallenge', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='kek', + full_name='spotify.FingerprintGrainChallenge.kek', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1554, + serialized_end=1594, +) + +_FINGERPRINTHMACRIPEMDCHALLENGE = _descriptor.Descriptor( + name='FingerprintHmacRipemdChallenge', + full_name='spotify.FingerprintHmacRipemdChallenge', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='challenge', + full_name='spotify.FingerprintHmacRipemdChallenge.challenge', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1596, + serialized_end=1647, +) + +_POWCHALLENGEUNION = _descriptor.Descriptor( + name='PoWChallengeUnion', + full_name='spotify.PoWChallengeUnion', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='hash_cash', + full_name='spotify.PoWChallengeUnion.hash_cash', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1649, + serialized_end=1718, +) + +_POWHASHCASHCHALLENGE = _descriptor.Descriptor( + name='PoWHashCashChallenge', + full_name='spotify.PoWHashCashChallenge', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='prefix', + full_name='spotify.PoWHashCashChallenge.prefix', + index=0, + number=10, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='length', + full_name='spotify.PoWHashCashChallenge.length', + index=1, + number=20, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='target', + full_name='spotify.PoWHashCashChallenge.target', + index=2, + number=30, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1720, + serialized_end=1790, +) + +_CRYPTOCHALLENGEUNION = _descriptor.Descriptor( + name='CryptoChallengeUnion', + full_name='spotify.CryptoChallengeUnion', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='shannon', + full_name='spotify.CryptoChallengeUnion.shannon', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='rc4_sha1_hmac', + full_name='spotify.CryptoChallengeUnion.rc4_sha1_hmac', + index=1, + number=20, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1793, + serialized_end=1925, +) + +_CRYPTOSHANNONCHALLENGE = _descriptor.Descriptor( + name='CryptoShannonChallenge', + full_name='spotify.CryptoShannonChallenge', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1927, + serialized_end=1951, +) + +_CRYPTORC4SHA1HMACCHALLENGE = _descriptor.Descriptor( + name='CryptoRc4Sha1HmacChallenge', + full_name='spotify.CryptoRc4Sha1HmacChallenge', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1953, + serialized_end=1981, +) + +_UPGRADEREQUIREDMESSAGE = _descriptor.Descriptor( + name='UpgradeRequiredMessage', + full_name='spotify.UpgradeRequiredMessage', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='upgrade_signed_part', + full_name='spotify.UpgradeRequiredMessage.upgrade_signed_part', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='signature', + full_name='spotify.UpgradeRequiredMessage.signature', + index=1, + number=20, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='http_suffix', + full_name='spotify.UpgradeRequiredMessage.http_suffix', + index=2, + number=30, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1983, + serialized_end=2076, +) + +_APLOGINFAILED = _descriptor.Descriptor( + name='APLoginFailed', + full_name='spotify.APLoginFailed', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='error_code', + full_name='spotify.APLoginFailed.error_code', + index=0, + number=10, + type=14, + cpp_type=8, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='retry_delay', + full_name='spotify.APLoginFailed.retry_delay', + index=1, + number=20, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='expiry', + full_name='spotify.APLoginFailed.expiry', + index=2, + number=30, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='error_description', + full_name='spotify.APLoginFailed.error_description', + index=3, + number=40, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2078, + serialized_end=2197, +) + +_CLIENTRESPONSEPLAINTEXT = _descriptor.Descriptor( + name='ClientResponsePlaintext', + full_name='spotify.ClientResponsePlaintext', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='login_crypto_response', + full_name='spotify.ClientResponsePlaintext.login_crypto_response', + index=0, + number=10, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='pow_response', + full_name='spotify.ClientResponsePlaintext.pow_response', + index=1, + number=20, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='crypto_response', + full_name='spotify.ClientResponsePlaintext.crypto_response', + index=2, + number=30, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2200, + serialized_end=2395, +) + +_LOGINCRYPTORESPONSEUNION = _descriptor.Descriptor( + name='LoginCryptoResponseUnion', + full_name='spotify.LoginCryptoResponseUnion', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='diffie_hellman', + full_name='spotify.LoginCryptoResponseUnion.diffie_hellman', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2397, + serialized_end=2490, +) + +_LOGINCRYPTODIFFIEHELLMANRESPONSE = _descriptor.Descriptor( + name='LoginCryptoDiffieHellmanResponse', + full_name='spotify.LoginCryptoDiffieHellmanResponse', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='hmac', + full_name='spotify.LoginCryptoDiffieHellmanResponse.hmac', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2492, + serialized_end=2540, +) + +_POWRESPONSEUNION = _descriptor.Descriptor( + name='PoWResponseUnion', + full_name='spotify.PoWResponseUnion', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='hash_cash', + full_name='spotify.PoWResponseUnion.hash_cash', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2542, + serialized_end=2609, +) + +_POWHASHCASHRESPONSE = _descriptor.Descriptor( + name='PoWHashCashResponse', + full_name='spotify.PoWHashCashResponse', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='hash_suffix', + full_name='spotify.PoWHashCashResponse.hash_suffix', + index=0, + number=10, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2611, + serialized_end=2653, +) + +_CRYPTORESPONSEUNION = _descriptor.Descriptor( + name='CryptoResponseUnion', + full_name='spotify.CryptoResponseUnion', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='shannon', + full_name='spotify.CryptoResponseUnion.shannon', + index=0, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='rc4_sha1_hmac', + full_name='spotify.CryptoResponseUnion.rc4_sha1_hmac', + index=1, + number=20, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2656, + serialized_end=2785, +) + +_CRYPTOSHANNONRESPONSE = _descriptor.Descriptor( + name='CryptoShannonResponse', + full_name='spotify.CryptoShannonResponse', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='dummy', + full_name='spotify.CryptoShannonResponse.dummy', + index=0, + number=1, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2787, + serialized_end=2825, +) + +_CRYPTORC4SHA1HMACRESPONSE = _descriptor.Descriptor( + name='CryptoRc4Sha1HmacResponse', + full_name='spotify.CryptoRc4Sha1HmacResponse', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='dummy', + full_name='spotify.CryptoRc4Sha1HmacResponse.dummy', + index=0, + number=1, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2827, + serialized_end=2869, +) + +_CLIENTHELLO.fields_by_name['build_info'].message_type = _BUILDINFO +_CLIENTHELLO.fields_by_name['fingerprints_supported'].enum_type = _FINGERPRINT +_CLIENTHELLO.fields_by_name['cryptosuites_supported'].enum_type = _CRYPTOSUITE +_CLIENTHELLO.fields_by_name['powschemes_supported'].enum_type = _POWSCHEME +_CLIENTHELLO.fields_by_name[ + 'login_crypto_hello'].message_type = _LOGINCRYPTOHELLOUNION +_CLIENTHELLO.fields_by_name['feature_set'].message_type = _FEATURESET +_BUILDINFO.fields_by_name['product'].enum_type = _PRODUCT +_BUILDINFO.fields_by_name['product_flags'].enum_type = _PRODUCTFLAGS +_BUILDINFO.fields_by_name['platform'].enum_type = _PLATFORM +_LOGINCRYPTOHELLOUNION.fields_by_name[ + 'diffie_hellman'].message_type = _LOGINCRYPTODIFFIEHELLMANHELLO +_APRESPONSEMESSAGE.fields_by_name['challenge'].message_type = _APCHALLENGE +_APRESPONSEMESSAGE.fields_by_name[ + 'upgrade'].message_type = _UPGRADEREQUIREDMESSAGE +_APRESPONSEMESSAGE.fields_by_name['login_failed'].message_type = _APLOGINFAILED +_APCHALLENGE.fields_by_name[ + 'login_crypto_challenge'].message_type = _LOGINCRYPTOCHALLENGEUNION +_APCHALLENGE.fields_by_name[ + 'fingerprint_challenge'].message_type = _FINGERPRINTCHALLENGEUNION +_APCHALLENGE.fields_by_name['pow_challenge'].message_type = _POWCHALLENGEUNION +_APCHALLENGE.fields_by_name[ + 'crypto_challenge'].message_type = _CRYPTOCHALLENGEUNION +_LOGINCRYPTOCHALLENGEUNION.fields_by_name[ + 'diffie_hellman'].message_type = _LOGINCRYPTODIFFIEHELLMANCHALLENGE +_FINGERPRINTCHALLENGEUNION.fields_by_name[ + 'grain'].message_type = _FINGERPRINTGRAINCHALLENGE +_FINGERPRINTCHALLENGEUNION.fields_by_name[ + 'hmac_ripemd'].message_type = _FINGERPRINTHMACRIPEMDCHALLENGE +_POWCHALLENGEUNION.fields_by_name[ + 'hash_cash'].message_type = _POWHASHCASHCHALLENGE +_CRYPTOCHALLENGEUNION.fields_by_name[ + 'shannon'].message_type = _CRYPTOSHANNONCHALLENGE +_CRYPTOCHALLENGEUNION.fields_by_name[ + 'rc4_sha1_hmac'].message_type = _CRYPTORC4SHA1HMACCHALLENGE +_APLOGINFAILED.fields_by_name['error_code'].enum_type = _ERRORCODE +_CLIENTRESPONSEPLAINTEXT.fields_by_name[ + 'login_crypto_response'].message_type = _LOGINCRYPTORESPONSEUNION +_CLIENTRESPONSEPLAINTEXT.fields_by_name[ + 'pow_response'].message_type = _POWRESPONSEUNION +_CLIENTRESPONSEPLAINTEXT.fields_by_name[ + 'crypto_response'].message_type = _CRYPTORESPONSEUNION +_LOGINCRYPTORESPONSEUNION.fields_by_name[ + 'diffie_hellman'].message_type = _LOGINCRYPTODIFFIEHELLMANRESPONSE +_POWRESPONSEUNION.fields_by_name[ + 'hash_cash'].message_type = _POWHASHCASHRESPONSE +_CRYPTORESPONSEUNION.fields_by_name[ + 'shannon'].message_type = _CRYPTOSHANNONRESPONSE +_CRYPTORESPONSEUNION.fields_by_name[ + 'rc4_sha1_hmac'].message_type = _CRYPTORC4SHA1HMACRESPONSE +DESCRIPTOR.message_types_by_name['ClientHello'] = _CLIENTHELLO +DESCRIPTOR.message_types_by_name['BuildInfo'] = _BUILDINFO +DESCRIPTOR.message_types_by_name[ + 'LoginCryptoHelloUnion'] = _LOGINCRYPTOHELLOUNION +DESCRIPTOR.message_types_by_name[ + 'LoginCryptoDiffieHellmanHello'] = _LOGINCRYPTODIFFIEHELLMANHELLO +DESCRIPTOR.message_types_by_name['FeatureSet'] = _FEATURESET +DESCRIPTOR.message_types_by_name['APResponseMessage'] = _APRESPONSEMESSAGE +DESCRIPTOR.message_types_by_name['APChallenge'] = _APCHALLENGE +DESCRIPTOR.message_types_by_name[ + 'LoginCryptoChallengeUnion'] = _LOGINCRYPTOCHALLENGEUNION +DESCRIPTOR.message_types_by_name[ + 'LoginCryptoDiffieHellmanChallenge'] = _LOGINCRYPTODIFFIEHELLMANCHALLENGE +DESCRIPTOR.message_types_by_name[ + 'FingerprintChallengeUnion'] = _FINGERPRINTCHALLENGEUNION +DESCRIPTOR.message_types_by_name[ + 'FingerprintGrainChallenge'] = _FINGERPRINTGRAINCHALLENGE +DESCRIPTOR.message_types_by_name[ + 'FingerprintHmacRipemdChallenge'] = _FINGERPRINTHMACRIPEMDCHALLENGE +DESCRIPTOR.message_types_by_name['PoWChallengeUnion'] = _POWCHALLENGEUNION +DESCRIPTOR.message_types_by_name[ + 'PoWHashCashChallenge'] = _POWHASHCASHCHALLENGE +DESCRIPTOR.message_types_by_name[ + 'CryptoChallengeUnion'] = _CRYPTOCHALLENGEUNION +DESCRIPTOR.message_types_by_name[ + 'CryptoShannonChallenge'] = _CRYPTOSHANNONCHALLENGE +DESCRIPTOR.message_types_by_name[ + 'CryptoRc4Sha1HmacChallenge'] = _CRYPTORC4SHA1HMACCHALLENGE +DESCRIPTOR.message_types_by_name[ + 'UpgradeRequiredMessage'] = _UPGRADEREQUIREDMESSAGE +DESCRIPTOR.message_types_by_name['APLoginFailed'] = _APLOGINFAILED +DESCRIPTOR.message_types_by_name[ + 'ClientResponsePlaintext'] = _CLIENTRESPONSEPLAINTEXT +DESCRIPTOR.message_types_by_name[ + 'LoginCryptoResponseUnion'] = _LOGINCRYPTORESPONSEUNION +DESCRIPTOR.message_types_by_name[ + 'LoginCryptoDiffieHellmanResponse'] = _LOGINCRYPTODIFFIEHELLMANRESPONSE +DESCRIPTOR.message_types_by_name['PoWResponseUnion'] = _POWRESPONSEUNION +DESCRIPTOR.message_types_by_name['PoWHashCashResponse'] = _POWHASHCASHRESPONSE +DESCRIPTOR.message_types_by_name['CryptoResponseUnion'] = _CRYPTORESPONSEUNION +DESCRIPTOR.message_types_by_name[ + 'CryptoShannonResponse'] = _CRYPTOSHANNONRESPONSE +DESCRIPTOR.message_types_by_name[ + 'CryptoRc4Sha1HmacResponse'] = _CRYPTORC4SHA1HMACRESPONSE +DESCRIPTOR.enum_types_by_name['Product'] = _PRODUCT +DESCRIPTOR.enum_types_by_name['ProductFlags'] = _PRODUCTFLAGS +DESCRIPTOR.enum_types_by_name['Platform'] = _PLATFORM +DESCRIPTOR.enum_types_by_name['Fingerprint'] = _FINGERPRINT +DESCRIPTOR.enum_types_by_name['Cryptosuite'] = _CRYPTOSUITE +DESCRIPTOR.enum_types_by_name['Powscheme'] = _POWSCHEME +DESCRIPTOR.enum_types_by_name['ErrorCode'] = _ERRORCODE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +ClientHello = _reflection.GeneratedProtocolMessageType( + 'ClientHello', + (_message.Message, ), + { + 'DESCRIPTOR': _CLIENTHELLO, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.ClientHello) + }) +_sym_db.RegisterMessage(ClientHello) + +BuildInfo = _reflection.GeneratedProtocolMessageType( + 'BuildInfo', + (_message.Message, ), + { + 'DESCRIPTOR': _BUILDINFO, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.BuildInfo) + }) +_sym_db.RegisterMessage(BuildInfo) + +LoginCryptoHelloUnion = _reflection.GeneratedProtocolMessageType( + 'LoginCryptoHelloUnion', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGINCRYPTOHELLOUNION, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.LoginCryptoHelloUnion) + }) +_sym_db.RegisterMessage(LoginCryptoHelloUnion) + +LoginCryptoDiffieHellmanHello = _reflection.GeneratedProtocolMessageType( + 'LoginCryptoDiffieHellmanHello', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGINCRYPTODIFFIEHELLMANHELLO, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.LoginCryptoDiffieHellmanHello) + }) +_sym_db.RegisterMessage(LoginCryptoDiffieHellmanHello) + +FeatureSet = _reflection.GeneratedProtocolMessageType( + 'FeatureSet', + (_message.Message, ), + { + 'DESCRIPTOR': _FEATURESET, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.FeatureSet) + }) +_sym_db.RegisterMessage(FeatureSet) + +APResponseMessage = _reflection.GeneratedProtocolMessageType( + 'APResponseMessage', + (_message.Message, ), + { + 'DESCRIPTOR': _APRESPONSEMESSAGE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.APResponseMessage) + }) +_sym_db.RegisterMessage(APResponseMessage) + +APChallenge = _reflection.GeneratedProtocolMessageType( + 'APChallenge', + (_message.Message, ), + { + 'DESCRIPTOR': _APCHALLENGE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.APChallenge) + }) +_sym_db.RegisterMessage(APChallenge) + +LoginCryptoChallengeUnion = _reflection.GeneratedProtocolMessageType( + 'LoginCryptoChallengeUnion', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGINCRYPTOCHALLENGEUNION, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.LoginCryptoChallengeUnion) + }) +_sym_db.RegisterMessage(LoginCryptoChallengeUnion) + +LoginCryptoDiffieHellmanChallenge = _reflection.GeneratedProtocolMessageType( + 'LoginCryptoDiffieHellmanChallenge', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGINCRYPTODIFFIEHELLMANCHALLENGE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.LoginCryptoDiffieHellmanChallenge) + }) +_sym_db.RegisterMessage(LoginCryptoDiffieHellmanChallenge) + +FingerprintChallengeUnion = _reflection.GeneratedProtocolMessageType( + 'FingerprintChallengeUnion', + (_message.Message, ), + { + 'DESCRIPTOR': _FINGERPRINTCHALLENGEUNION, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.FingerprintChallengeUnion) + }) +_sym_db.RegisterMessage(FingerprintChallengeUnion) + +FingerprintGrainChallenge = _reflection.GeneratedProtocolMessageType( + 'FingerprintGrainChallenge', + (_message.Message, ), + { + 'DESCRIPTOR': _FINGERPRINTGRAINCHALLENGE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.FingerprintGrainChallenge) + }) +_sym_db.RegisterMessage(FingerprintGrainChallenge) + +FingerprintHmacRipemdChallenge = _reflection.GeneratedProtocolMessageType( + 'FingerprintHmacRipemdChallenge', + (_message.Message, ), + { + 'DESCRIPTOR': _FINGERPRINTHMACRIPEMDCHALLENGE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.FingerprintHmacRipemdChallenge) + }) +_sym_db.RegisterMessage(FingerprintHmacRipemdChallenge) + +PoWChallengeUnion = _reflection.GeneratedProtocolMessageType( + 'PoWChallengeUnion', + (_message.Message, ), + { + 'DESCRIPTOR': _POWCHALLENGEUNION, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.PoWChallengeUnion) + }) +_sym_db.RegisterMessage(PoWChallengeUnion) + +PoWHashCashChallenge = _reflection.GeneratedProtocolMessageType( + 'PoWHashCashChallenge', + (_message.Message, ), + { + 'DESCRIPTOR': _POWHASHCASHCHALLENGE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.PoWHashCashChallenge) + }) +_sym_db.RegisterMessage(PoWHashCashChallenge) + +CryptoChallengeUnion = _reflection.GeneratedProtocolMessageType( + 'CryptoChallengeUnion', + (_message.Message, ), + { + 'DESCRIPTOR': _CRYPTOCHALLENGEUNION, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.CryptoChallengeUnion) + }) +_sym_db.RegisterMessage(CryptoChallengeUnion) + +CryptoShannonChallenge = _reflection.GeneratedProtocolMessageType( + 'CryptoShannonChallenge', + (_message.Message, ), + { + 'DESCRIPTOR': _CRYPTOSHANNONCHALLENGE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.CryptoShannonChallenge) + }) +_sym_db.RegisterMessage(CryptoShannonChallenge) + +CryptoRc4Sha1HmacChallenge = _reflection.GeneratedProtocolMessageType( + 'CryptoRc4Sha1HmacChallenge', + (_message.Message, ), + { + 'DESCRIPTOR': _CRYPTORC4SHA1HMACCHALLENGE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.CryptoRc4Sha1HmacChallenge) + }) +_sym_db.RegisterMessage(CryptoRc4Sha1HmacChallenge) + +UpgradeRequiredMessage = _reflection.GeneratedProtocolMessageType( + 'UpgradeRequiredMessage', + (_message.Message, ), + { + 'DESCRIPTOR': _UPGRADEREQUIREDMESSAGE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.UpgradeRequiredMessage) + }) +_sym_db.RegisterMessage(UpgradeRequiredMessage) + +APLoginFailed = _reflection.GeneratedProtocolMessageType( + 'APLoginFailed', + (_message.Message, ), + { + 'DESCRIPTOR': _APLOGINFAILED, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.APLoginFailed) + }) +_sym_db.RegisterMessage(APLoginFailed) + +ClientResponsePlaintext = _reflection.GeneratedProtocolMessageType( + 'ClientResponsePlaintext', + (_message.Message, ), + { + 'DESCRIPTOR': _CLIENTRESPONSEPLAINTEXT, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.ClientResponsePlaintext) + }) +_sym_db.RegisterMessage(ClientResponsePlaintext) + +LoginCryptoResponseUnion = _reflection.GeneratedProtocolMessageType( + 'LoginCryptoResponseUnion', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGINCRYPTORESPONSEUNION, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.LoginCryptoResponseUnion) + }) +_sym_db.RegisterMessage(LoginCryptoResponseUnion) + +LoginCryptoDiffieHellmanResponse = _reflection.GeneratedProtocolMessageType( + 'LoginCryptoDiffieHellmanResponse', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGINCRYPTODIFFIEHELLMANRESPONSE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.LoginCryptoDiffieHellmanResponse) + }) +_sym_db.RegisterMessage(LoginCryptoDiffieHellmanResponse) + +PoWResponseUnion = _reflection.GeneratedProtocolMessageType( + 'PoWResponseUnion', + (_message.Message, ), + { + 'DESCRIPTOR': _POWRESPONSEUNION, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.PoWResponseUnion) + }) +_sym_db.RegisterMessage(PoWResponseUnion) + +PoWHashCashResponse = _reflection.GeneratedProtocolMessageType( + 'PoWHashCashResponse', + (_message.Message, ), + { + 'DESCRIPTOR': _POWHASHCASHRESPONSE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.PoWHashCashResponse) + }) +_sym_db.RegisterMessage(PoWHashCashResponse) + +CryptoResponseUnion = _reflection.GeneratedProtocolMessageType( + 'CryptoResponseUnion', + (_message.Message, ), + { + 'DESCRIPTOR': _CRYPTORESPONSEUNION, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.CryptoResponseUnion) + }) +_sym_db.RegisterMessage(CryptoResponseUnion) + +CryptoShannonResponse = _reflection.GeneratedProtocolMessageType( + 'CryptoShannonResponse', + (_message.Message, ), + { + 'DESCRIPTOR': _CRYPTOSHANNONRESPONSE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.CryptoShannonResponse) + }) +_sym_db.RegisterMessage(CryptoShannonResponse) + +CryptoRc4Sha1HmacResponse = _reflection.GeneratedProtocolMessageType( + 'CryptoRc4Sha1HmacResponse', + (_message.Message, ), + { + 'DESCRIPTOR': _CRYPTORC4SHA1HMACRESPONSE, + '__module__': 'keyexchange_pb2' + # @@protoc_insertion_point(class_scope:spotify.CryptoRc4Sha1HmacResponse) + }) +_sym_db.RegisterMessage(CryptoRc4Sha1HmacResponse) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/Mercury.py b/src/librespot/proto/Mercury.py new file mode 100644 index 0000000..8109c9f --- /dev/null +++ b/src/librespot/proto/Mercury.py @@ -0,0 +1,625 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: mercury.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='mercury.proto', + package='spotify', + syntax='proto2', + serialized_options=b'\n\013com.spotify', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\rmercury.proto\x12\x07spotify\"B\n\x16MercuryMultiGetRequest\x12(\n\x07request\x18\x01 \x03(\x0b\x32\x17.spotify.MercuryRequest\"<\n\x14MercuryMultiGetReply\x12$\n\x05reply\x18\x01 \x03(\x0b\x32\x15.spotify.MercuryReply\"O\n\x0eMercuryRequest\x12\x0b\n\x03uri\x18\x01 \x01(\t\x12\x14\n\x0c\x63ontent_type\x18\x02 \x01(\t\x12\x0c\n\x04\x62ody\x18\x03 \x01(\x0c\x12\x0c\n\x04\x65tag\x18\x04 \x01(\x0c\"\xf5\x01\n\x0cMercuryReply\x12\x13\n\x0bstatus_code\x18\x01 \x01(\x11\x12\x16\n\x0estatus_message\x18\x02 \x01(\t\x12\x37\n\x0c\x63\x61\x63he_policy\x18\x03 \x01(\x0e\x32!.spotify.MercuryReply.CachePolicy\x12\x0b\n\x03ttl\x18\x04 \x01(\x11\x12\x0c\n\x04\x65tag\x18\x05 \x01(\x0c\x12\x14\n\x0c\x63ontent_type\x18\x06 \x01(\t\x12\x0c\n\x04\x62ody\x18\x07 \x01(\x0c\"@\n\x0b\x43\x61\x63hePolicy\x12\x0c\n\x08\x43\x41\x43HE_NO\x10\x01\x12\x11\n\rCACHE_PRIVATE\x10\x02\x12\x10\n\x0c\x43\x41\x43HE_PUBLIC\x10\x03\"y\n\x06Header\x12\x0b\n\x03uri\x18\x01 \x01(\t\x12\x14\n\x0c\x63ontent_type\x18\x02 \x01(\t\x12\x0e\n\x06method\x18\x03 \x01(\t\x12\x13\n\x0bstatus_code\x18\x04 \x01(\x11\x12\'\n\x0buser_fields\x18\x06 \x03(\x0b\x32\x12.spotify.UserField\"\'\n\tUserField\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\r\n\x05value\x18\x02 \x01(\x0c\x42\r\n\x0b\x63om.spotify' +) + +_MERCURYREPLY_CACHEPOLICY = _descriptor.EnumDescriptor( + name='CachePolicy', + full_name='spotify.MercuryReply.CachePolicy', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='CACHE_NO', + index=0, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CACHE_PRIVATE', + index=1, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CACHE_PUBLIC', + index=2, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=419, + serialized_end=483, +) +_sym_db.RegisterEnumDescriptor(_MERCURYREPLY_CACHEPOLICY) + +_MERCURYMULTIGETREQUEST = _descriptor.Descriptor( + name='MercuryMultiGetRequest', + full_name='spotify.MercuryMultiGetRequest', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='request', + full_name='spotify.MercuryMultiGetRequest.request', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=26, + serialized_end=92, +) + +_MERCURYMULTIGETREPLY = _descriptor.Descriptor( + name='MercuryMultiGetReply', + full_name='spotify.MercuryMultiGetReply', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='reply', + full_name='spotify.MercuryMultiGetReply.reply', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=94, + serialized_end=154, +) + +_MERCURYREQUEST = _descriptor.Descriptor( + name='MercuryRequest', + full_name='spotify.MercuryRequest', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='spotify.MercuryRequest.uri', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='content_type', + full_name='spotify.MercuryRequest.content_type', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='body', + full_name='spotify.MercuryRequest.body', + index=2, + number=3, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='etag', + full_name='spotify.MercuryRequest.etag', + index=3, + number=4, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=156, + serialized_end=235, +) + +_MERCURYREPLY = _descriptor.Descriptor( + name='MercuryReply', + full_name='spotify.MercuryReply', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='status_code', + full_name='spotify.MercuryReply.status_code', + index=0, + number=1, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='status_message', + full_name='spotify.MercuryReply.status_message', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='cache_policy', + full_name='spotify.MercuryReply.cache_policy', + index=2, + number=3, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=1, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='ttl', + full_name='spotify.MercuryReply.ttl', + index=3, + number=4, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='etag', + full_name='spotify.MercuryReply.etag', + index=4, + number=5, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='content_type', + full_name='spotify.MercuryReply.content_type', + index=5, + number=6, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='body', + full_name='spotify.MercuryReply.body', + index=6, + number=7, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _MERCURYREPLY_CACHEPOLICY, + ], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=238, + serialized_end=483, +) + +_HEADER = _descriptor.Descriptor( + name='Header', + full_name='spotify.Header', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='spotify.Header.uri', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='content_type', + full_name='spotify.Header.content_type', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='method', + full_name='spotify.Header.method', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='status_code', + full_name='spotify.Header.status_code', + index=3, + number=4, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='user_fields', + full_name='spotify.Header.user_fields', + index=4, + number=6, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=485, + serialized_end=606, +) + +_USERFIELD = _descriptor.Descriptor( + name='UserField', + full_name='spotify.UserField', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='spotify.UserField.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='spotify.UserField.value', + index=1, + number=2, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=608, + serialized_end=647, +) + +_MERCURYMULTIGETREQUEST.fields_by_name[ + 'request'].message_type = _MERCURYREQUEST +_MERCURYMULTIGETREPLY.fields_by_name['reply'].message_type = _MERCURYREPLY +_MERCURYREPLY.fields_by_name[ + 'cache_policy'].enum_type = _MERCURYREPLY_CACHEPOLICY +_MERCURYREPLY_CACHEPOLICY.containing_type = _MERCURYREPLY +_HEADER.fields_by_name['user_fields'].message_type = _USERFIELD +DESCRIPTOR.message_types_by_name[ + 'MercuryMultiGetRequest'] = _MERCURYMULTIGETREQUEST +DESCRIPTOR.message_types_by_name[ + 'MercuryMultiGetReply'] = _MERCURYMULTIGETREPLY +DESCRIPTOR.message_types_by_name['MercuryRequest'] = _MERCURYREQUEST +DESCRIPTOR.message_types_by_name['MercuryReply'] = _MERCURYREPLY +DESCRIPTOR.message_types_by_name['Header'] = _HEADER +DESCRIPTOR.message_types_by_name['UserField'] = _USERFIELD +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +MercuryMultiGetRequest = _reflection.GeneratedProtocolMessageType( + 'MercuryMultiGetRequest', + (_message.Message, ), + { + 'DESCRIPTOR': _MERCURYMULTIGETREQUEST, + '__module__': 'mercury_pb2' + # @@protoc_insertion_point(class_scope:spotify.MercuryMultiGetRequest) + }) +_sym_db.RegisterMessage(MercuryMultiGetRequest) + +MercuryMultiGetReply = _reflection.GeneratedProtocolMessageType( + 'MercuryMultiGetReply', + (_message.Message, ), + { + 'DESCRIPTOR': _MERCURYMULTIGETREPLY, + '__module__': 'mercury_pb2' + # @@protoc_insertion_point(class_scope:spotify.MercuryMultiGetReply) + }) +_sym_db.RegisterMessage(MercuryMultiGetReply) + +MercuryRequest = _reflection.GeneratedProtocolMessageType( + 'MercuryRequest', + (_message.Message, ), + { + 'DESCRIPTOR': _MERCURYREQUEST, + '__module__': 'mercury_pb2' + # @@protoc_insertion_point(class_scope:spotify.MercuryRequest) + }) +_sym_db.RegisterMessage(MercuryRequest) + +MercuryReply = _reflection.GeneratedProtocolMessageType( + 'MercuryReply', + (_message.Message, ), + { + 'DESCRIPTOR': _MERCURYREPLY, + '__module__': 'mercury_pb2' + # @@protoc_insertion_point(class_scope:spotify.MercuryReply) + }) +_sym_db.RegisterMessage(MercuryReply) + +Header = _reflection.GeneratedProtocolMessageType( + 'Header', + (_message.Message, ), + { + 'DESCRIPTOR': _HEADER, + '__module__': 'mercury_pb2' + # @@protoc_insertion_point(class_scope:spotify.Header) + }) +_sym_db.RegisterMessage(Header) + +UserField = _reflection.GeneratedProtocolMessageType( + 'UserField', + (_message.Message, ), + { + 'DESCRIPTOR': _USERFIELD, + '__module__': 'mercury_pb2' + # @@protoc_insertion_point(class_scope:spotify.UserField) + }) +_sym_db.RegisterMessage(UserField) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/Metadata.py b/src/librespot/proto/Metadata.py new file mode 100644 index 0000000..e8ac38c --- /dev/null +++ b/src/librespot/proto/Metadata.py @@ -0,0 +1,3698 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: metadata.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='metadata.proto', + package='spotify.metadata.proto', + syntax='proto2', + serialized_options=b'\n\024com.spotify.metadataB\010MetadataH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x0emetadata.proto\x12\x16spotify.metadata.proto\"\x8a\x07\n\x06\x41rtist\x12\x0b\n\x03gid\x18\x01 \x01(\x0c\x12\x0c\n\x04name\x18\x02 \x01(\t\x12\x12\n\npopularity\x18\x03 \x01(\x11\x12\x34\n\ttop_track\x18\x04 \x03(\x0b\x32!.spotify.metadata.proto.TopTracks\x12\x37\n\x0b\x61lbum_group\x18\x05 \x03(\x0b\x32\".spotify.metadata.proto.AlbumGroup\x12\x38\n\x0csingle_group\x18\x06 \x03(\x0b\x32\".spotify.metadata.proto.AlbumGroup\x12=\n\x11\x63ompilation_group\x18\x07 \x03(\x0b\x32\".spotify.metadata.proto.AlbumGroup\x12<\n\x10\x61ppears_on_group\x18\x08 \x03(\x0b\x32\".spotify.metadata.proto.AlbumGroup\x12\r\n\x05genre\x18\t \x03(\t\x12\x37\n\x0b\x65xternal_id\x18\n \x03(\x0b\x32\".spotify.metadata.proto.ExternalId\x12/\n\x08portrait\x18\x0b \x03(\x0b\x32\x1d.spotify.metadata.proto.Image\x12\x34\n\tbiography\x18\x0c \x03(\x0b\x32!.spotify.metadata.proto.Biography\x12?\n\x0f\x61\x63tivity_period\x18\r \x03(\x0b\x32&.spotify.metadata.proto.ActivityPeriod\x12\x38\n\x0brestriction\x18\x0e \x03(\x0b\x32#.spotify.metadata.proto.Restriction\x12/\n\x07related\x18\x0f \x03(\x0b\x32\x1e.spotify.metadata.proto.Artist\x12\x1f\n\x17is_portrait_album_cover\x18\x10 \x01(\x08\x12:\n\x0eportrait_group\x18\x11 \x01(\x0b\x32\".spotify.metadata.proto.ImageGroup\x12\x37\n\x0bsale_period\x18\x12 \x03(\x0b\x32\".spotify.metadata.proto.SalePeriod\x12:\n\x0c\x61vailability\x18\x14 \x03(\x0b\x32$.spotify.metadata.proto.Availability\"\xe8\x06\n\x05\x41lbum\x12\x0b\n\x03gid\x18\x01 \x01(\x0c\x12\x0c\n\x04name\x18\x02 \x01(\t\x12.\n\x06\x61rtist\x18\x03 \x03(\x0b\x32\x1e.spotify.metadata.proto.Artist\x12\x30\n\x04type\x18\x04 \x01(\x0e\x32\".spotify.metadata.proto.Album.Type\x12\r\n\x05label\x18\x05 \x01(\t\x12*\n\x04\x64\x61te\x18\x06 \x01(\x0b\x32\x1c.spotify.metadata.proto.Date\x12\x12\n\npopularity\x18\x07 \x01(\x11\x12\r\n\x05genre\x18\x08 \x03(\t\x12,\n\x05\x63over\x18\t \x03(\x0b\x32\x1d.spotify.metadata.proto.Image\x12\x37\n\x0b\x65xternal_id\x18\n \x03(\x0b\x32\".spotify.metadata.proto.ExternalId\x12*\n\x04\x64isc\x18\x0b \x03(\x0b\x32\x1c.spotify.metadata.proto.Disc\x12\x0e\n\x06review\x18\x0c \x03(\t\x12\x34\n\tcopyright\x18\r \x03(\x0b\x32!.spotify.metadata.proto.Copyright\x12\x38\n\x0brestriction\x18\x0e \x03(\x0b\x32#.spotify.metadata.proto.Restriction\x12.\n\x07related\x18\x0f \x03(\x0b\x32\x1d.spotify.metadata.proto.Album\x12\x37\n\x0bsale_period\x18\x10 \x03(\x0b\x32\".spotify.metadata.proto.SalePeriod\x12\x37\n\x0b\x63over_group\x18\x11 \x01(\x0b\x32\".spotify.metadata.proto.ImageGroup\x12\x16\n\x0eoriginal_title\x18\x12 \x01(\t\x12\x15\n\rversion_title\x18\x13 \x01(\t\x12\x10\n\x08type_str\x18\x14 \x01(\t\x12:\n\x0c\x61vailability\x18\x17 \x03(\x0b\x32$.spotify.metadata.proto.Availability\"R\n\x04Type\x12\t\n\x05\x41LBUM\x10\x01\x12\n\n\x06SINGLE\x10\x02\x12\x0f\n\x0b\x43OMPILATION\x10\x03\x12\x06\n\x02\x45P\x10\x04\x12\r\n\tAUDIOBOOK\x10\x05\x12\x0b\n\x07PODCAST\x10\x06\"\xd5\x05\n\x05Track\x12\x0b\n\x03gid\x18\x01 \x01(\x0c\x12\x0c\n\x04name\x18\x02 \x01(\t\x12,\n\x05\x61lbum\x18\x03 \x01(\x0b\x32\x1d.spotify.metadata.proto.Album\x12.\n\x06\x61rtist\x18\x04 \x03(\x0b\x32\x1e.spotify.metadata.proto.Artist\x12\x0e\n\x06number\x18\x05 \x01(\x11\x12\x13\n\x0b\x64isc_number\x18\x06 \x01(\x11\x12\x10\n\x08\x64uration\x18\x07 \x01(\x11\x12\x12\n\npopularity\x18\x08 \x01(\x11\x12\x10\n\x08\x65xplicit\x18\t \x01(\x08\x12\x37\n\x0b\x65xternal_id\x18\n \x03(\x0b\x32\".spotify.metadata.proto.ExternalId\x12\x38\n\x0brestriction\x18\x0b \x03(\x0b\x32#.spotify.metadata.proto.Restriction\x12/\n\x04\x66ile\x18\x0c \x03(\x0b\x32!.spotify.metadata.proto.AudioFile\x12\x32\n\x0b\x61lternative\x18\r \x03(\x0b\x32\x1d.spotify.metadata.proto.Track\x12\x37\n\x0bsale_period\x18\x0e \x03(\x0b\x32\".spotify.metadata.proto.SalePeriod\x12\x32\n\x07preview\x18\x0f \x03(\x0b\x32!.spotify.metadata.proto.AudioFile\x12\x0c\n\x04tags\x18\x10 \x03(\t\x12\x1f\n\x17\x65\x61rliest_live_timestamp\x18\x11 \x01(\x03\x12\x12\n\nhas_lyrics\x18\x12 \x01(\x08\x12:\n\x0c\x61vailability\x18\x13 \x03(\x0b\x32$.spotify.metadata.proto.Availability\x12\x32\n\x08licensor\x18\x15 \x01(\x0b\x32 .spotify.metadata.proto.Licensor\"\xbf\x05\n\x04Show\x12\x0b\n\x03gid\x18\x01 \x01(\x0c\x12\x0c\n\x04name\x18\x02 \x01(\t\x12\x13\n\x0b\x64\x65scription\x18@ \x01(\t\x12!\n\x15\x64\x65precated_popularity\x18\x41 \x01(\x11\x42\x02\x18\x01\x12\x11\n\tpublisher\x18\x42 \x01(\t\x12\x10\n\x08language\x18\x43 \x01(\t\x12\x10\n\x08\x65xplicit\x18\x44 \x01(\x08\x12\x37\n\x0b\x63over_image\x18\x45 \x01(\x0b\x32\".spotify.metadata.proto.ImageGroup\x12\x30\n\x07\x65pisode\x18\x46 \x03(\x0b\x32\x1f.spotify.metadata.proto.Episode\x12\x34\n\tcopyright\x18G \x03(\x0b\x32!.spotify.metadata.proto.Copyright\x12\x38\n\x0brestriction\x18H \x03(\x0b\x32#.spotify.metadata.proto.Restriction\x12\x0f\n\x07keyword\x18I \x03(\t\x12:\n\nmedia_type\x18J \x01(\x0e\x32&.spotify.metadata.proto.Show.MediaType\x12H\n\x11\x63onsumption_order\x18K \x01(\x0e\x32-.spotify.metadata.proto.Show.ConsumptionOrder\x12:\n\x0c\x61vailability\x18N \x03(\x0b\x32$.spotify.metadata.proto.Availability\x12\x13\n\x0btrailer_uri\x18S \x01(\t\",\n\tMediaType\x12\t\n\x05MIXED\x10\x00\x12\t\n\x05\x41UDIO\x10\x01\x12\t\n\x05VIDEO\x10\x02\"<\n\x10\x43onsumptionOrder\x12\x0e\n\nSEQUENTIAL\x10\x01\x12\x0c\n\x08\x45PISODIC\x10\x02\x12\n\n\x06RECENT\x10\x03\"\xf9\x06\n\x07\x45pisode\x12\x0b\n\x03gid\x18\x01 \x01(\x0c\x12\x0c\n\x04name\x18\x02 \x01(\t\x12\x10\n\x08\x64uration\x18\x07 \x01(\x11\x12\x30\n\x05\x61udio\x18\x0c \x03(\x0b\x32!.spotify.metadata.proto.AudioFile\x12\x13\n\x0b\x64\x65scription\x18@ \x01(\t\x12\x0e\n\x06number\x18\x41 \x01(\x11\x12\x32\n\x0cpublish_time\x18\x42 \x01(\x0b\x32\x1c.spotify.metadata.proto.Date\x12!\n\x15\x64\x65precated_popularity\x18\x43 \x01(\x11\x42\x02\x18\x01\x12\x37\n\x0b\x63over_image\x18\x44 \x01(\x0b\x32\".spotify.metadata.proto.ImageGroup\x12\x10\n\x08language\x18\x45 \x01(\t\x12\x10\n\x08\x65xplicit\x18\x46 \x01(\x08\x12*\n\x04show\x18G \x01(\x0b\x32\x1c.spotify.metadata.proto.Show\x12\x30\n\x05video\x18H \x03(\x0b\x32!.spotify.metadata.proto.VideoFile\x12\x38\n\rvideo_preview\x18I \x03(\x0b\x32!.spotify.metadata.proto.VideoFile\x12\x38\n\raudio_preview\x18J \x03(\x0b\x32!.spotify.metadata.proto.AudioFile\x12\x38\n\x0brestriction\x18K \x03(\x0b\x32#.spotify.metadata.proto.Restriction\x12\x38\n\x0c\x66reeze_frame\x18L \x01(\x0b\x32\".spotify.metadata.proto.ImageGroup\x12\x0f\n\x07keyword\x18M \x03(\t\x12!\n\x19\x61llow_background_playback\x18Q \x01(\x08\x12:\n\x0c\x61vailability\x18R \x03(\x0b\x32$.spotify.metadata.proto.Availability\x12\x14\n\x0c\x65xternal_url\x18S \x01(\t\x12\x39\n\x04type\x18W \x01(\x0e\x32+.spotify.metadata.proto.Episode.EpisodeType\"/\n\x0b\x45pisodeType\x12\x08\n\x04\x46ULL\x10\x00\x12\x0b\n\x07TRAILER\x10\x01\x12\t\n\x05\x42ONUS\x10\x02\"\x18\n\x08Licensor\x12\x0c\n\x04uuid\x18\x01 \x01(\x0c\"J\n\tTopTracks\x12\x0f\n\x07\x63ountry\x18\x01 \x01(\t\x12,\n\x05track\x18\x02 \x03(\x0b\x32\x1d.spotify.metadata.proto.Track\"F\n\x0e\x41\x63tivityPeriod\x12\x12\n\nstart_year\x18\x01 \x01(\x11\x12\x10\n\x08\x65nd_year\x18\x02 \x01(\x11\x12\x0e\n\x06\x64\x65\x63\x61\x64\x65\x18\x03 \x01(\x11\":\n\nAlbumGroup\x12,\n\x05\x61lbum\x18\x01 \x03(\x0b\x32\x1d.spotify.metadata.proto.Album\"N\n\x04\x44\x61te\x12\x0c\n\x04year\x18\x01 \x01(\x11\x12\r\n\x05month\x18\x02 \x01(\x11\x12\x0b\n\x03\x64\x61y\x18\x03 \x01(\x11\x12\x0c\n\x04hour\x18\x04 \x01(\x11\x12\x0e\n\x06minute\x18\x05 \x01(\x11\"\xa0\x01\n\x05Image\x12\x0f\n\x07\x66ile_id\x18\x01 \x01(\x0c\x12\x30\n\x04size\x18\x02 \x01(\x0e\x32\".spotify.metadata.proto.Image.Size\x12\r\n\x05width\x18\x03 \x01(\x11\x12\x0e\n\x06height\x18\x04 \x01(\x11\"5\n\x04Size\x12\x0b\n\x07\x44\x45\x46\x41ULT\x10\x00\x12\t\n\x05SMALL\x10\x01\x12\t\n\x05LARGE\x10\x02\x12\n\n\x06XLARGE\x10\x03\":\n\nImageGroup\x12,\n\x05image\x18\x01 \x03(\x0b\x32\x1d.spotify.metadata.proto.Image\"\x86\x01\n\tBiography\x12\x0c\n\x04text\x18\x01 \x01(\t\x12/\n\x08portrait\x18\x02 \x03(\x0b\x32\x1d.spotify.metadata.proto.Image\x12:\n\x0eportrait_group\x18\x03 \x03(\x0b\x32\".spotify.metadata.proto.ImageGroup\"R\n\x04\x44isc\x12\x0e\n\x06number\x18\x01 \x01(\x11\x12\x0c\n\x04name\x18\x02 \x01(\t\x12,\n\x05track\x18\x03 \x03(\x0b\x32\x1d.spotify.metadata.proto.Track\"e\n\tCopyright\x12\x34\n\x04type\x18\x01 \x01(\x0e\x32&.spotify.metadata.proto.Copyright.Type\x12\x0c\n\x04text\x18\x02 \x01(\t\"\x14\n\x04Type\x12\x05\n\x01P\x10\x00\x12\x05\n\x01\x43\x10\x01\"\xdf\x02\n\x0bRestriction\x12@\n\tcatalogue\x18\x01 \x03(\x0e\x32-.spotify.metadata.proto.Restriction.Catalogue\x12\x36\n\x04type\x18\x04 \x01(\x0e\x32(.spotify.metadata.proto.Restriction.Type\x12\x15\n\rcatalogue_str\x18\x05 \x03(\t\x12\x1b\n\x11\x63ountries_allowed\x18\x02 \x01(\tH\x00\x12\x1d\n\x13\x63ountries_forbidden\x18\x03 \x01(\tH\x00\"U\n\tCatalogue\x12\x06\n\x02\x41\x44\x10\x00\x12\x10\n\x0cSUBSCRIPTION\x10\x01\x12\x11\n\rCATALOGUE_ALL\x10\x02\x12\x0b\n\x07SHUFFLE\x10\x03\x12\x0e\n\nCOMMERCIAL\x10\x04\"\x15\n\x04Type\x12\r\n\tSTREAMING\x10\x00\x42\x15\n\x13\x63ountry_restriction\"R\n\x0c\x41vailability\x12\x15\n\rcatalogue_str\x18\x01 \x03(\t\x12+\n\x05start\x18\x02 \x01(\x0b\x32\x1c.spotify.metadata.proto.Date\"\x9e\x01\n\nSalePeriod\x12\x38\n\x0brestriction\x18\x01 \x03(\x0b\x32#.spotify.metadata.proto.Restriction\x12+\n\x05start\x18\x02 \x01(\x0b\x32\x1c.spotify.metadata.proto.Date\x12)\n\x03\x65nd\x18\x03 \x01(\x0b\x32\x1c.spotify.metadata.proto.Date\"&\n\nExternalId\x12\x0c\n\x04type\x18\x01 \x01(\t\x12\n\n\x02id\x18\x02 \x01(\t\"\x89\x02\n\tAudioFile\x12\x0f\n\x07\x66ile_id\x18\x01 \x01(\x0c\x12\x38\n\x06\x66ormat\x18\x02 \x01(\x0e\x32(.spotify.metadata.proto.AudioFile.Format\"\xb0\x01\n\x06\x46ormat\x12\x11\n\rOGG_VORBIS_96\x10\x00\x12\x12\n\x0eOGG_VORBIS_160\x10\x01\x12\x12\n\x0eOGG_VORBIS_320\x10\x02\x12\x0b\n\x07MP3_256\x10\x03\x12\x0b\n\x07MP3_320\x10\x04\x12\x0b\n\x07MP3_160\x10\x05\x12\n\n\x06MP3_96\x10\x06\x12\x0f\n\x0bMP3_160_ENC\x10\x07\x12\n\n\x06\x41\x41\x43_24\x10\x08\x12\n\n\x06\x41\x41\x43_48\x10\t\x12\x0f\n\x0b\x41\x41\x43_24_NORM\x10\x10\"\x1c\n\tVideoFile\x12\x0f\n\x07\x66ile_id\x18\x01 \x01(\x0c\x42\"\n\x14\x63om.spotify.metadataB\x08MetadataH\x02' +) + +_ALBUM_TYPE = _descriptor.EnumDescriptor( + name='Type', + full_name='spotify.metadata.proto.Album.Type', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='ALBUM', + index=0, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SINGLE', + index=1, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='COMPILATION', + index=2, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='EP', + index=3, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AUDIOBOOK', + index=4, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PODCAST', + index=5, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=1742, + serialized_end=1824, +) +_sym_db.RegisterEnumDescriptor(_ALBUM_TYPE) + +_SHOW_MEDIATYPE = _descriptor.EnumDescriptor( + name='MediaType', + full_name='spotify.metadata.proto.Show.MediaType', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='MIXED', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AUDIO', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='VIDEO', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3152, + serialized_end=3196, +) +_sym_db.RegisterEnumDescriptor(_SHOW_MEDIATYPE) + +_SHOW_CONSUMPTIONORDER = _descriptor.EnumDescriptor( + name='ConsumptionOrder', + full_name='spotify.metadata.proto.Show.ConsumptionOrder', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='SEQUENTIAL', + index=0, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='EPISODIC', + index=1, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='RECENT', + index=2, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3198, + serialized_end=3258, +) +_sym_db.RegisterEnumDescriptor(_SHOW_CONSUMPTIONORDER) + +_EPISODE_EPISODETYPE = _descriptor.EnumDescriptor( + name='EpisodeType', + full_name='spotify.metadata.proto.Episode.EpisodeType', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='FULL', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='TRAILER', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='BONUS', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=4103, + serialized_end=4150, +) +_sym_db.RegisterEnumDescriptor(_EPISODE_EPISODETYPE) + +_IMAGE_SIZE = _descriptor.EnumDescriptor( + name='Size', + full_name='spotify.metadata.proto.Image.Size', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='DEFAULT', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SMALL', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LARGE', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='XLARGE', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=4574, + serialized_end=4627, +) +_sym_db.RegisterEnumDescriptor(_IMAGE_SIZE) + +_COPYRIGHT_TYPE = _descriptor.EnumDescriptor( + name='Type', + full_name='spotify.metadata.proto.Copyright.Type', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='P', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='C', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=4991, + serialized_end=5011, +) +_sym_db.RegisterEnumDescriptor(_COPYRIGHT_TYPE) + +_RESTRICTION_CATALOGUE = _descriptor.EnumDescriptor( + name='Catalogue', + full_name='spotify.metadata.proto.Restriction.Catalogue', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='AD', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SUBSCRIPTION', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CATALOGUE_ALL', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SHUFFLE', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='COMMERCIAL', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=5234, + serialized_end=5319, +) +_sym_db.RegisterEnumDescriptor(_RESTRICTION_CATALOGUE) + +_RESTRICTION_TYPE = _descriptor.EnumDescriptor( + name='Type', + full_name='spotify.metadata.proto.Restriction.Type', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='STREAMING', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=5321, + serialized_end=5342, +) +_sym_db.RegisterEnumDescriptor(_RESTRICTION_TYPE) + +_AUDIOFILE_FORMAT = _descriptor.EnumDescriptor( + name='Format', + full_name='spotify.metadata.proto.AudioFile.Format', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='OGG_VORBIS_96', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OGG_VORBIS_160', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='OGG_VORBIS_320', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='MP3_256', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='MP3_320', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='MP3_160', + index=5, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='MP3_96', + index=6, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='MP3_160_ENC', + index=7, + number=7, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AAC_24', + index=8, + number=8, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AAC_48', + index=9, + number=9, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='AAC_24_NORM', + index=10, + number=16, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=5742, + serialized_end=5918, +) +_sym_db.RegisterEnumDescriptor(_AUDIOFILE_FORMAT) + +_ARTIST = _descriptor.Descriptor( + name='Artist', + full_name='spotify.metadata.proto.Artist', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='gid', + full_name='spotify.metadata.proto.Artist.gid', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='name', + full_name='spotify.metadata.proto.Artist.name', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='popularity', + full_name='spotify.metadata.proto.Artist.popularity', + index=2, + number=3, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='top_track', + full_name='spotify.metadata.proto.Artist.top_track', + index=3, + number=4, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='album_group', + full_name='spotify.metadata.proto.Artist.album_group', + index=4, + number=5, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='single_group', + full_name='spotify.metadata.proto.Artist.single_group', + index=5, + number=6, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='compilation_group', + full_name='spotify.metadata.proto.Artist.compilation_group', + index=6, + number=7, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='appears_on_group', + full_name='spotify.metadata.proto.Artist.appears_on_group', + index=7, + number=8, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='genre', + full_name='spotify.metadata.proto.Artist.genre', + index=8, + number=9, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='external_id', + full_name='spotify.metadata.proto.Artist.external_id', + index=9, + number=10, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='portrait', + full_name='spotify.metadata.proto.Artist.portrait', + index=10, + number=11, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='biography', + full_name='spotify.metadata.proto.Artist.biography', + index=11, + number=12, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='activity_period', + full_name='spotify.metadata.proto.Artist.activity_period', + index=12, + number=13, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='restriction', + full_name='spotify.metadata.proto.Artist.restriction', + index=13, + number=14, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='related', + full_name='spotify.metadata.proto.Artist.related', + index=14, + number=15, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_portrait_album_cover', + full_name='spotify.metadata.proto.Artist.is_portrait_album_cover', + index=15, + number=16, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='portrait_group', + full_name='spotify.metadata.proto.Artist.portrait_group', + index=16, + number=17, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='sale_period', + full_name='spotify.metadata.proto.Artist.sale_period', + index=17, + number=18, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='availability', + full_name='spotify.metadata.proto.Artist.availability', + index=18, + number=20, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=43, + serialized_end=949, +) + +_ALBUM = _descriptor.Descriptor( + name='Album', + full_name='spotify.metadata.proto.Album', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='gid', + full_name='spotify.metadata.proto.Album.gid', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='name', + full_name='spotify.metadata.proto.Album.name', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='artist', + full_name='spotify.metadata.proto.Album.artist', + index=2, + number=3, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='type', + full_name='spotify.metadata.proto.Album.type', + index=3, + number=4, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=1, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='label', + full_name='spotify.metadata.proto.Album.label', + index=4, + number=5, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='date', + full_name='spotify.metadata.proto.Album.date', + index=5, + number=6, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='popularity', + full_name='spotify.metadata.proto.Album.popularity', + index=6, + number=7, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='genre', + full_name='spotify.metadata.proto.Album.genre', + index=7, + number=8, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='cover', + full_name='spotify.metadata.proto.Album.cover', + index=8, + number=9, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='external_id', + full_name='spotify.metadata.proto.Album.external_id', + index=9, + number=10, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disc', + full_name='spotify.metadata.proto.Album.disc', + index=10, + number=11, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='review', + full_name='spotify.metadata.proto.Album.review', + index=11, + number=12, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='copyright', + full_name='spotify.metadata.proto.Album.copyright', + index=12, + number=13, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='restriction', + full_name='spotify.metadata.proto.Album.restriction', + index=13, + number=14, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='related', + full_name='spotify.metadata.proto.Album.related', + index=14, + number=15, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='sale_period', + full_name='spotify.metadata.proto.Album.sale_period', + index=15, + number=16, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='cover_group', + full_name='spotify.metadata.proto.Album.cover_group', + index=16, + number=17, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='original_title', + full_name='spotify.metadata.proto.Album.original_title', + index=17, + number=18, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='version_title', + full_name='spotify.metadata.proto.Album.version_title', + index=18, + number=19, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='type_str', + full_name='spotify.metadata.proto.Album.type_str', + index=19, + number=20, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='availability', + full_name='spotify.metadata.proto.Album.availability', + index=20, + number=23, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _ALBUM_TYPE, + ], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=952, + serialized_end=1824, +) + +_TRACK = _descriptor.Descriptor( + name='Track', + full_name='spotify.metadata.proto.Track', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='gid', + full_name='spotify.metadata.proto.Track.gid', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='name', + full_name='spotify.metadata.proto.Track.name', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='album', + full_name='spotify.metadata.proto.Track.album', + index=2, + number=3, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='artist', + full_name='spotify.metadata.proto.Track.artist', + index=3, + number=4, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='number', + full_name='spotify.metadata.proto.Track.number', + index=4, + number=5, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disc_number', + full_name='spotify.metadata.proto.Track.disc_number', + index=5, + number=6, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='duration', + full_name='spotify.metadata.proto.Track.duration', + index=6, + number=7, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='popularity', + full_name='spotify.metadata.proto.Track.popularity', + index=7, + number=8, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='explicit', + full_name='spotify.metadata.proto.Track.explicit', + index=8, + number=9, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='external_id', + full_name='spotify.metadata.proto.Track.external_id', + index=9, + number=10, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='restriction', + full_name='spotify.metadata.proto.Track.restriction', + index=10, + number=11, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='file', + full_name='spotify.metadata.proto.Track.file', + index=11, + number=12, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='alternative', + full_name='spotify.metadata.proto.Track.alternative', + index=12, + number=13, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='sale_period', + full_name='spotify.metadata.proto.Track.sale_period', + index=13, + number=14, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='preview', + full_name='spotify.metadata.proto.Track.preview', + index=14, + number=15, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='tags', + full_name='spotify.metadata.proto.Track.tags', + index=15, + number=16, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='earliest_live_timestamp', + full_name='spotify.metadata.proto.Track.earliest_live_timestamp', + index=16, + number=17, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='has_lyrics', + full_name='spotify.metadata.proto.Track.has_lyrics', + index=17, + number=18, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='availability', + full_name='spotify.metadata.proto.Track.availability', + index=18, + number=19, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='licensor', + full_name='spotify.metadata.proto.Track.licensor', + index=19, + number=21, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1827, + serialized_end=2552, +) + +_SHOW = _descriptor.Descriptor( + name='Show', + full_name='spotify.metadata.proto.Show', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='gid', + full_name='spotify.metadata.proto.Show.gid', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='name', + full_name='spotify.metadata.proto.Show.name', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='description', + full_name='spotify.metadata.proto.Show.description', + index=2, + number=64, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='deprecated_popularity', + full_name='spotify.metadata.proto.Show.deprecated_popularity', + index=3, + number=65, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=b'\030\001', + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='publisher', + full_name='spotify.metadata.proto.Show.publisher', + index=4, + number=66, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='language', + full_name='spotify.metadata.proto.Show.language', + index=5, + number=67, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='explicit', + full_name='spotify.metadata.proto.Show.explicit', + index=6, + number=68, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='cover_image', + full_name='spotify.metadata.proto.Show.cover_image', + index=7, + number=69, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='episode', + full_name='spotify.metadata.proto.Show.episode', + index=8, + number=70, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='copyright', + full_name='spotify.metadata.proto.Show.copyright', + index=9, + number=71, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='restriction', + full_name='spotify.metadata.proto.Show.restriction', + index=10, + number=72, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='keyword', + full_name='spotify.metadata.proto.Show.keyword', + index=11, + number=73, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='media_type', + full_name='spotify.metadata.proto.Show.media_type', + index=12, + number=74, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='consumption_order', + full_name='spotify.metadata.proto.Show.consumption_order', + index=13, + number=75, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=1, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='availability', + full_name='spotify.metadata.proto.Show.availability', + index=14, + number=78, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='trailer_uri', + full_name='spotify.metadata.proto.Show.trailer_uri', + index=15, + number=83, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _SHOW_MEDIATYPE, + _SHOW_CONSUMPTIONORDER, + ], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2555, + serialized_end=3258, +) + +_EPISODE = _descriptor.Descriptor( + name='Episode', + full_name='spotify.metadata.proto.Episode', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='gid', + full_name='spotify.metadata.proto.Episode.gid', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='name', + full_name='spotify.metadata.proto.Episode.name', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='duration', + full_name='spotify.metadata.proto.Episode.duration', + index=2, + number=7, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='audio', + full_name='spotify.metadata.proto.Episode.audio', + index=3, + number=12, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='description', + full_name='spotify.metadata.proto.Episode.description', + index=4, + number=64, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='number', + full_name='spotify.metadata.proto.Episode.number', + index=5, + number=65, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='publish_time', + full_name='spotify.metadata.proto.Episode.publish_time', + index=6, + number=66, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='deprecated_popularity', + full_name='spotify.metadata.proto.Episode.deprecated_popularity', + index=7, + number=67, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=b'\030\001', + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='cover_image', + full_name='spotify.metadata.proto.Episode.cover_image', + index=8, + number=68, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='language', + full_name='spotify.metadata.proto.Episode.language', + index=9, + number=69, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='explicit', + full_name='spotify.metadata.proto.Episode.explicit', + index=10, + number=70, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='show', + full_name='spotify.metadata.proto.Episode.show', + index=11, + number=71, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='video', + full_name='spotify.metadata.proto.Episode.video', + index=12, + number=72, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='video_preview', + full_name='spotify.metadata.proto.Episode.video_preview', + index=13, + number=73, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='audio_preview', + full_name='spotify.metadata.proto.Episode.audio_preview', + index=14, + number=74, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='restriction', + full_name='spotify.metadata.proto.Episode.restriction', + index=15, + number=75, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='freeze_frame', + full_name='spotify.metadata.proto.Episode.freeze_frame', + index=16, + number=76, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='keyword', + full_name='spotify.metadata.proto.Episode.keyword', + index=17, + number=77, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='allow_background_playback', + full_name= + 'spotify.metadata.proto.Episode.allow_background_playback', + index=18, + number=81, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='availability', + full_name='spotify.metadata.proto.Episode.availability', + index=19, + number=82, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='external_url', + full_name='spotify.metadata.proto.Episode.external_url', + index=20, + number=83, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='type', + full_name='spotify.metadata.proto.Episode.type', + index=21, + number=87, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _EPISODE_EPISODETYPE, + ], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=3261, + serialized_end=4150, +) + +_LICENSOR = _descriptor.Descriptor( + name='Licensor', + full_name='spotify.metadata.proto.Licensor', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uuid', + full_name='spotify.metadata.proto.Licensor.uuid', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=4152, + serialized_end=4176, +) + +_TOPTRACKS = _descriptor.Descriptor( + name='TopTracks', + full_name='spotify.metadata.proto.TopTracks', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='country', + full_name='spotify.metadata.proto.TopTracks.country', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='track', + full_name='spotify.metadata.proto.TopTracks.track', + index=1, + number=2, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=4178, + serialized_end=4252, +) + +_ACTIVITYPERIOD = _descriptor.Descriptor( + name='ActivityPeriod', + full_name='spotify.metadata.proto.ActivityPeriod', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='start_year', + full_name='spotify.metadata.proto.ActivityPeriod.start_year', + index=0, + number=1, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='end_year', + full_name='spotify.metadata.proto.ActivityPeriod.end_year', + index=1, + number=2, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='decade', + full_name='spotify.metadata.proto.ActivityPeriod.decade', + index=2, + number=3, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=4254, + serialized_end=4324, +) + +_ALBUMGROUP = _descriptor.Descriptor( + name='AlbumGroup', + full_name='spotify.metadata.proto.AlbumGroup', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='album', + full_name='spotify.metadata.proto.AlbumGroup.album', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=4326, + serialized_end=4384, +) + +_DATE = _descriptor.Descriptor( + name='Date', + full_name='spotify.metadata.proto.Date', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='year', + full_name='spotify.metadata.proto.Date.year', + index=0, + number=1, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='month', + full_name='spotify.metadata.proto.Date.month', + index=1, + number=2, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='day', + full_name='spotify.metadata.proto.Date.day', + index=2, + number=3, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='hour', + full_name='spotify.metadata.proto.Date.hour', + index=3, + number=4, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='minute', + full_name='spotify.metadata.proto.Date.minute', + index=4, + number=5, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=4386, + serialized_end=4464, +) + +_IMAGE = _descriptor.Descriptor( + name='Image', + full_name='spotify.metadata.proto.Image', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='file_id', + full_name='spotify.metadata.proto.Image.file_id', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='size', + full_name='spotify.metadata.proto.Image.size', + index=1, + number=2, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='width', + full_name='spotify.metadata.proto.Image.width', + index=2, + number=3, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='height', + full_name='spotify.metadata.proto.Image.height', + index=3, + number=4, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _IMAGE_SIZE, + ], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=4467, + serialized_end=4627, +) + +_IMAGEGROUP = _descriptor.Descriptor( + name='ImageGroup', + full_name='spotify.metadata.proto.ImageGroup', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='image', + full_name='spotify.metadata.proto.ImageGroup.image', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=4629, + serialized_end=4687, +) + +_BIOGRAPHY = _descriptor.Descriptor( + name='Biography', + full_name='spotify.metadata.proto.Biography', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='text', + full_name='spotify.metadata.proto.Biography.text', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='portrait', + full_name='spotify.metadata.proto.Biography.portrait', + index=1, + number=2, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='portrait_group', + full_name='spotify.metadata.proto.Biography.portrait_group', + index=2, + number=3, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=4690, + serialized_end=4824, +) + +_DISC = _descriptor.Descriptor( + name='Disc', + full_name='spotify.metadata.proto.Disc', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='number', + full_name='spotify.metadata.proto.Disc.number', + index=0, + number=1, + type=17, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='name', + full_name='spotify.metadata.proto.Disc.name', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='track', + full_name='spotify.metadata.proto.Disc.track', + index=2, + number=3, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=4826, + serialized_end=4908, +) + +_COPYRIGHT = _descriptor.Descriptor( + name='Copyright', + full_name='spotify.metadata.proto.Copyright', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='type', + full_name='spotify.metadata.proto.Copyright.type', + index=0, + number=1, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='text', + full_name='spotify.metadata.proto.Copyright.text', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _COPYRIGHT_TYPE, + ], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=4910, + serialized_end=5011, +) + +_RESTRICTION = _descriptor.Descriptor( + name='Restriction', + full_name='spotify.metadata.proto.Restriction', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='catalogue', + full_name='spotify.metadata.proto.Restriction.catalogue', + index=0, + number=1, + type=14, + cpp_type=8, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='type', + full_name='spotify.metadata.proto.Restriction.type', + index=1, + number=4, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='catalogue_str', + full_name='spotify.metadata.proto.Restriction.catalogue_str', + index=2, + number=5, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='countries_allowed', + full_name='spotify.metadata.proto.Restriction.countries_allowed', + index=3, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='countries_forbidden', + full_name='spotify.metadata.proto.Restriction.countries_forbidden', + index=4, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _RESTRICTION_CATALOGUE, + _RESTRICTION_TYPE, + ], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[ + _descriptor.OneofDescriptor( + name='country_restriction', + full_name='spotify.metadata.proto.Restriction.country_restriction', + index=0, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[]), + ], + serialized_start=5014, + serialized_end=5365, +) + +_AVAILABILITY = _descriptor.Descriptor( + name='Availability', + full_name='spotify.metadata.proto.Availability', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='catalogue_str', + full_name='spotify.metadata.proto.Availability.catalogue_str', + index=0, + number=1, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='start', + full_name='spotify.metadata.proto.Availability.start', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=5367, + serialized_end=5449, +) + +_SALEPERIOD = _descriptor.Descriptor( + name='SalePeriod', + full_name='spotify.metadata.proto.SalePeriod', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='restriction', + full_name='spotify.metadata.proto.SalePeriod.restriction', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='start', + full_name='spotify.metadata.proto.SalePeriod.start', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='end', + full_name='spotify.metadata.proto.SalePeriod.end', + index=2, + number=3, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=5452, + serialized_end=5610, +) + +_EXTERNALID = _descriptor.Descriptor( + name='ExternalId', + full_name='spotify.metadata.proto.ExternalId', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='type', + full_name='spotify.metadata.proto.ExternalId.type', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='id', + full_name='spotify.metadata.proto.ExternalId.id', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=5612, + serialized_end=5650, +) + +_AUDIOFILE = _descriptor.Descriptor( + name='AudioFile', + full_name='spotify.metadata.proto.AudioFile', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='file_id', + full_name='spotify.metadata.proto.AudioFile.file_id', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='format', + full_name='spotify.metadata.proto.AudioFile.format', + index=1, + number=2, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _AUDIOFILE_FORMAT, + ], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=5653, + serialized_end=5918, +) + +_VIDEOFILE = _descriptor.Descriptor( + name='VideoFile', + full_name='spotify.metadata.proto.VideoFile', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='file_id', + full_name='spotify.metadata.proto.VideoFile.file_id', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=5920, + serialized_end=5948, +) + +_ARTIST.fields_by_name['top_track'].message_type = _TOPTRACKS +_ARTIST.fields_by_name['album_group'].message_type = _ALBUMGROUP +_ARTIST.fields_by_name['single_group'].message_type = _ALBUMGROUP +_ARTIST.fields_by_name['compilation_group'].message_type = _ALBUMGROUP +_ARTIST.fields_by_name['appears_on_group'].message_type = _ALBUMGROUP +_ARTIST.fields_by_name['external_id'].message_type = _EXTERNALID +_ARTIST.fields_by_name['portrait'].message_type = _IMAGE +_ARTIST.fields_by_name['biography'].message_type = _BIOGRAPHY +_ARTIST.fields_by_name['activity_period'].message_type = _ACTIVITYPERIOD +_ARTIST.fields_by_name['restriction'].message_type = _RESTRICTION +_ARTIST.fields_by_name['related'].message_type = _ARTIST +_ARTIST.fields_by_name['portrait_group'].message_type = _IMAGEGROUP +_ARTIST.fields_by_name['sale_period'].message_type = _SALEPERIOD +_ARTIST.fields_by_name['availability'].message_type = _AVAILABILITY +_ALBUM.fields_by_name['artist'].message_type = _ARTIST +_ALBUM.fields_by_name['type'].enum_type = _ALBUM_TYPE +_ALBUM.fields_by_name['date'].message_type = _DATE +_ALBUM.fields_by_name['cover'].message_type = _IMAGE +_ALBUM.fields_by_name['external_id'].message_type = _EXTERNALID +_ALBUM.fields_by_name['disc'].message_type = _DISC +_ALBUM.fields_by_name['copyright'].message_type = _COPYRIGHT +_ALBUM.fields_by_name['restriction'].message_type = _RESTRICTION +_ALBUM.fields_by_name['related'].message_type = _ALBUM +_ALBUM.fields_by_name['sale_period'].message_type = _SALEPERIOD +_ALBUM.fields_by_name['cover_group'].message_type = _IMAGEGROUP +_ALBUM.fields_by_name['availability'].message_type = _AVAILABILITY +_ALBUM_TYPE.containing_type = _ALBUM +_TRACK.fields_by_name['album'].message_type = _ALBUM +_TRACK.fields_by_name['artist'].message_type = _ARTIST +_TRACK.fields_by_name['external_id'].message_type = _EXTERNALID +_TRACK.fields_by_name['restriction'].message_type = _RESTRICTION +_TRACK.fields_by_name['file'].message_type = _AUDIOFILE +_TRACK.fields_by_name['alternative'].message_type = _TRACK +_TRACK.fields_by_name['sale_period'].message_type = _SALEPERIOD +_TRACK.fields_by_name['preview'].message_type = _AUDIOFILE +_TRACK.fields_by_name['availability'].message_type = _AVAILABILITY +_TRACK.fields_by_name['licensor'].message_type = _LICENSOR +_SHOW.fields_by_name['cover_image'].message_type = _IMAGEGROUP +_SHOW.fields_by_name['episode'].message_type = _EPISODE +_SHOW.fields_by_name['copyright'].message_type = _COPYRIGHT +_SHOW.fields_by_name['restriction'].message_type = _RESTRICTION +_SHOW.fields_by_name['media_type'].enum_type = _SHOW_MEDIATYPE +_SHOW.fields_by_name['consumption_order'].enum_type = _SHOW_CONSUMPTIONORDER +_SHOW.fields_by_name['availability'].message_type = _AVAILABILITY +_SHOW_MEDIATYPE.containing_type = _SHOW +_SHOW_CONSUMPTIONORDER.containing_type = _SHOW +_EPISODE.fields_by_name['audio'].message_type = _AUDIOFILE +_EPISODE.fields_by_name['publish_time'].message_type = _DATE +_EPISODE.fields_by_name['cover_image'].message_type = _IMAGEGROUP +_EPISODE.fields_by_name['show'].message_type = _SHOW +_EPISODE.fields_by_name['video'].message_type = _VIDEOFILE +_EPISODE.fields_by_name['video_preview'].message_type = _VIDEOFILE +_EPISODE.fields_by_name['audio_preview'].message_type = _AUDIOFILE +_EPISODE.fields_by_name['restriction'].message_type = _RESTRICTION +_EPISODE.fields_by_name['freeze_frame'].message_type = _IMAGEGROUP +_EPISODE.fields_by_name['availability'].message_type = _AVAILABILITY +_EPISODE.fields_by_name['type'].enum_type = _EPISODE_EPISODETYPE +_EPISODE_EPISODETYPE.containing_type = _EPISODE +_TOPTRACKS.fields_by_name['track'].message_type = _TRACK +_ALBUMGROUP.fields_by_name['album'].message_type = _ALBUM +_IMAGE.fields_by_name['size'].enum_type = _IMAGE_SIZE +_IMAGE_SIZE.containing_type = _IMAGE +_IMAGEGROUP.fields_by_name['image'].message_type = _IMAGE +_BIOGRAPHY.fields_by_name['portrait'].message_type = _IMAGE +_BIOGRAPHY.fields_by_name['portrait_group'].message_type = _IMAGEGROUP +_DISC.fields_by_name['track'].message_type = _TRACK +_COPYRIGHT.fields_by_name['type'].enum_type = _COPYRIGHT_TYPE +_COPYRIGHT_TYPE.containing_type = _COPYRIGHT +_RESTRICTION.fields_by_name['catalogue'].enum_type = _RESTRICTION_CATALOGUE +_RESTRICTION.fields_by_name['type'].enum_type = _RESTRICTION_TYPE +_RESTRICTION_CATALOGUE.containing_type = _RESTRICTION +_RESTRICTION_TYPE.containing_type = _RESTRICTION +_RESTRICTION.oneofs_by_name['country_restriction'].fields.append( + _RESTRICTION.fields_by_name['countries_allowed']) +_RESTRICTION.fields_by_name[ + 'countries_allowed'].containing_oneof = _RESTRICTION.oneofs_by_name[ + 'country_restriction'] +_RESTRICTION.oneofs_by_name['country_restriction'].fields.append( + _RESTRICTION.fields_by_name['countries_forbidden']) +_RESTRICTION.fields_by_name[ + 'countries_forbidden'].containing_oneof = _RESTRICTION.oneofs_by_name[ + 'country_restriction'] +_AVAILABILITY.fields_by_name['start'].message_type = _DATE +_SALEPERIOD.fields_by_name['restriction'].message_type = _RESTRICTION +_SALEPERIOD.fields_by_name['start'].message_type = _DATE +_SALEPERIOD.fields_by_name['end'].message_type = _DATE +_AUDIOFILE.fields_by_name['format'].enum_type = _AUDIOFILE_FORMAT +_AUDIOFILE_FORMAT.containing_type = _AUDIOFILE +DESCRIPTOR.message_types_by_name['Artist'] = _ARTIST +DESCRIPTOR.message_types_by_name['Album'] = _ALBUM +DESCRIPTOR.message_types_by_name['Track'] = _TRACK +DESCRIPTOR.message_types_by_name['Show'] = _SHOW +DESCRIPTOR.message_types_by_name['Episode'] = _EPISODE +DESCRIPTOR.message_types_by_name['Licensor'] = _LICENSOR +DESCRIPTOR.message_types_by_name['TopTracks'] = _TOPTRACKS +DESCRIPTOR.message_types_by_name['ActivityPeriod'] = _ACTIVITYPERIOD +DESCRIPTOR.message_types_by_name['AlbumGroup'] = _ALBUMGROUP +DESCRIPTOR.message_types_by_name['Date'] = _DATE +DESCRIPTOR.message_types_by_name['Image'] = _IMAGE +DESCRIPTOR.message_types_by_name['ImageGroup'] = _IMAGEGROUP +DESCRIPTOR.message_types_by_name['Biography'] = _BIOGRAPHY +DESCRIPTOR.message_types_by_name['Disc'] = _DISC +DESCRIPTOR.message_types_by_name['Copyright'] = _COPYRIGHT +DESCRIPTOR.message_types_by_name['Restriction'] = _RESTRICTION +DESCRIPTOR.message_types_by_name['Availability'] = _AVAILABILITY +DESCRIPTOR.message_types_by_name['SalePeriod'] = _SALEPERIOD +DESCRIPTOR.message_types_by_name['ExternalId'] = _EXTERNALID +DESCRIPTOR.message_types_by_name['AudioFile'] = _AUDIOFILE +DESCRIPTOR.message_types_by_name['VideoFile'] = _VIDEOFILE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +Artist = _reflection.GeneratedProtocolMessageType( + 'Artist', + (_message.Message, ), + { + 'DESCRIPTOR': _ARTIST, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Artist) + }) +_sym_db.RegisterMessage(Artist) + +Album = _reflection.GeneratedProtocolMessageType( + 'Album', + (_message.Message, ), + { + 'DESCRIPTOR': _ALBUM, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Album) + }) +_sym_db.RegisterMessage(Album) + +Track = _reflection.GeneratedProtocolMessageType( + 'Track', + (_message.Message, ), + { + 'DESCRIPTOR': _TRACK, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Track) + }) +_sym_db.RegisterMessage(Track) + +Show = _reflection.GeneratedProtocolMessageType( + 'Show', + (_message.Message, ), + { + 'DESCRIPTOR': _SHOW, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Show) + }) +_sym_db.RegisterMessage(Show) + +Episode = _reflection.GeneratedProtocolMessageType( + 'Episode', + (_message.Message, ), + { + 'DESCRIPTOR': _EPISODE, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Episode) + }) +_sym_db.RegisterMessage(Episode) + +Licensor = _reflection.GeneratedProtocolMessageType( + 'Licensor', + (_message.Message, ), + { + 'DESCRIPTOR': _LICENSOR, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Licensor) + }) +_sym_db.RegisterMessage(Licensor) + +TopTracks = _reflection.GeneratedProtocolMessageType( + 'TopTracks', + (_message.Message, ), + { + 'DESCRIPTOR': _TOPTRACKS, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.TopTracks) + }) +_sym_db.RegisterMessage(TopTracks) + +ActivityPeriod = _reflection.GeneratedProtocolMessageType( + 'ActivityPeriod', + (_message.Message, ), + { + 'DESCRIPTOR': _ACTIVITYPERIOD, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.ActivityPeriod) + }) +_sym_db.RegisterMessage(ActivityPeriod) + +AlbumGroup = _reflection.GeneratedProtocolMessageType( + 'AlbumGroup', + (_message.Message, ), + { + 'DESCRIPTOR': _ALBUMGROUP, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.AlbumGroup) + }) +_sym_db.RegisterMessage(AlbumGroup) + +Date = _reflection.GeneratedProtocolMessageType( + 'Date', + (_message.Message, ), + { + 'DESCRIPTOR': _DATE, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Date) + }) +_sym_db.RegisterMessage(Date) + +Image = _reflection.GeneratedProtocolMessageType( + 'Image', + (_message.Message, ), + { + 'DESCRIPTOR': _IMAGE, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Image) + }) +_sym_db.RegisterMessage(Image) + +ImageGroup = _reflection.GeneratedProtocolMessageType( + 'ImageGroup', + (_message.Message, ), + { + 'DESCRIPTOR': _IMAGEGROUP, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.ImageGroup) + }) +_sym_db.RegisterMessage(ImageGroup) + +Biography = _reflection.GeneratedProtocolMessageType( + 'Biography', + (_message.Message, ), + { + 'DESCRIPTOR': _BIOGRAPHY, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Biography) + }) +_sym_db.RegisterMessage(Biography) + +Disc = _reflection.GeneratedProtocolMessageType( + 'Disc', + (_message.Message, ), + { + 'DESCRIPTOR': _DISC, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Disc) + }) +_sym_db.RegisterMessage(Disc) + +Copyright = _reflection.GeneratedProtocolMessageType( + 'Copyright', + (_message.Message, ), + { + 'DESCRIPTOR': _COPYRIGHT, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Copyright) + }) +_sym_db.RegisterMessage(Copyright) + +Restriction = _reflection.GeneratedProtocolMessageType( + 'Restriction', + (_message.Message, ), + { + 'DESCRIPTOR': _RESTRICTION, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Restriction) + }) +_sym_db.RegisterMessage(Restriction) + +Availability = _reflection.GeneratedProtocolMessageType( + 'Availability', + (_message.Message, ), + { + 'DESCRIPTOR': _AVAILABILITY, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.Availability) + }) +_sym_db.RegisterMessage(Availability) + +SalePeriod = _reflection.GeneratedProtocolMessageType( + 'SalePeriod', + (_message.Message, ), + { + 'DESCRIPTOR': _SALEPERIOD, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.SalePeriod) + }) +_sym_db.RegisterMessage(SalePeriod) + +ExternalId = _reflection.GeneratedProtocolMessageType( + 'ExternalId', + (_message.Message, ), + { + 'DESCRIPTOR': _EXTERNALID, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.ExternalId) + }) +_sym_db.RegisterMessage(ExternalId) + +AudioFile = _reflection.GeneratedProtocolMessageType( + 'AudioFile', + (_message.Message, ), + { + 'DESCRIPTOR': _AUDIOFILE, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.AudioFile) + }) +_sym_db.RegisterMessage(AudioFile) + +VideoFile = _reflection.GeneratedProtocolMessageType( + 'VideoFile', + (_message.Message, ), + { + 'DESCRIPTOR': _VIDEOFILE, + '__module__': 'metadata_pb2' + # @@protoc_insertion_point(class_scope:spotify.metadata.proto.VideoFile) + }) +_sym_db.RegisterMessage(VideoFile) + +DESCRIPTOR._options = None +_SHOW.fields_by_name['deprecated_popularity']._options = None +_EPISODE.fields_by_name['deprecated_popularity']._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/Pubsub.py b/src/librespot/proto/Pubsub.py new file mode 100644 index 0000000..abe1b3e --- /dev/null +++ b/src/librespot/proto/Pubsub.py @@ -0,0 +1,112 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: pubsub.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='pubsub.proto', + package='spotify', + syntax='proto2', + serialized_options=b'\n\013com.spotify', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x0cpubsub.proto\x12\x07spotify\"@\n\x0cSubscription\x12\x0b\n\x03uri\x18\x01 \x01(\t\x12\x0e\n\x06\x65xpiry\x18\x02 \x01(\x05\x12\x13\n\x0bstatus_code\x18\x03 \x01(\x05\x42\r\n\x0b\x63om.spotify' +) + +_SUBSCRIPTION = _descriptor.Descriptor( + name='Subscription', + full_name='spotify.Subscription', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='spotify.Subscription.uri', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='expiry', + full_name='spotify.Subscription.expiry', + index=1, + number=2, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='status_code', + full_name='spotify.Subscription.status_code', + index=2, + number=3, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=25, + serialized_end=89, +) + +DESCRIPTOR.message_types_by_name['Subscription'] = _SUBSCRIPTION +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +Subscription = _reflection.GeneratedProtocolMessageType( + 'Subscription', + (_message.Message, ), + { + 'DESCRIPTOR': _SUBSCRIPTION, + '__module__': 'pubsub_pb2' + # @@protoc_insertion_point(class_scope:spotify.Subscription) + }) +_sym_db.RegisterMessage(Subscription) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/StorageResolve.py b/src/librespot/proto/StorageResolve.py new file mode 100644 index 0000000..3319832 --- /dev/null +++ b/src/librespot/proto/StorageResolve.py @@ -0,0 +1,154 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: storage-resolve.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='storage-resolve.proto', + package='spotify.download.proto', + syntax='proto3', + serialized_options=b'\n\023com.spotify.storageH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x15storage-resolve.proto\x12\x16spotify.download.proto\"\xaf\x01\n\x16StorageResolveResponse\x12\x45\n\x06result\x18\x01 \x01(\x0e\x32\x35.spotify.download.proto.StorageResolveResponse.Result\x12\x0e\n\x06\x63\x64nurl\x18\x02 \x03(\t\x12\x0e\n\x06\x66ileid\x18\x04 \x01(\x0c\".\n\x06Result\x12\x07\n\x03\x43\x44N\x10\x00\x12\x0b\n\x07STORAGE\x10\x01\x12\x0e\n\nRESTRICTED\x10\x03\x42\x17\n\x13\x63om.spotify.storageH\x02\x62\x06proto3' +) + +_STORAGERESOLVERESPONSE_RESULT = _descriptor.EnumDescriptor( + name='Result', + full_name='spotify.download.proto.StorageResolveResponse.Result', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='CDN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='STORAGE', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='RESTRICTED', + index=2, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=179, + serialized_end=225, +) +_sym_db.RegisterEnumDescriptor(_STORAGERESOLVERESPONSE_RESULT) + +_STORAGERESOLVERESPONSE = _descriptor.Descriptor( + name='StorageResolveResponse', + full_name='spotify.download.proto.StorageResolveResponse', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='result', + full_name='spotify.download.proto.StorageResolveResponse.result', + index=0, + number=1, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='cdnurl', + full_name='spotify.download.proto.StorageResolveResponse.cdnurl', + index=1, + number=2, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='fileid', + full_name='spotify.download.proto.StorageResolveResponse.fileid', + index=2, + number=4, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _STORAGERESOLVERESPONSE_RESULT, + ], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=50, + serialized_end=225, +) + +_STORAGERESOLVERESPONSE.fields_by_name[ + 'result'].enum_type = _STORAGERESOLVERESPONSE_RESULT +_STORAGERESOLVERESPONSE_RESULT.containing_type = _STORAGERESOLVERESPONSE +DESCRIPTOR.message_types_by_name[ + 'StorageResolveResponse'] = _STORAGERESOLVERESPONSE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +StorageResolveResponse = _reflection.GeneratedProtocolMessageType( + 'StorageResolveResponse', + (_message.Message, ), + { + 'DESCRIPTOR': _STORAGERESOLVERESPONSE, + '__module__': 'storage_resolve_pb2' + # @@protoc_insertion_point(class_scope:spotify.download.proto.StorageResolveResponse) + }) +_sym_db.RegisterMessage(StorageResolveResponse) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/__init__.py b/src/librespot/proto/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/src/librespot/proto/canvaz_meta_pb2.py b/src/librespot/proto/canvaz_meta_pb2.py new file mode 100644 index 0000000..5f4576d --- /dev/null +++ b/src/librespot/proto/canvaz_meta_pb2.py @@ -0,0 +1,85 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: canvaz-meta.proto +"""Generated protocol buffer code.""" +from google.protobuf.internal import enum_type_wrapper +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='canvaz-meta.proto', + package='com.spotify.canvaz', + syntax='proto3', + serialized_options=b'\n\022com.spotify.canvazH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x11\x63\x61nvaz-meta.proto\x12\x12\x63om.spotify.canvaz*R\n\x04Type\x12\t\n\x05IMAGE\x10\x00\x12\t\n\x05VIDEO\x10\x01\x12\x11\n\rVIDEO_LOOPING\x10\x02\x12\x18\n\x14VIDEO_LOOPING_RANDOM\x10\x03\x12\x07\n\x03GIF\x10\x04\x42\x16\n\x12\x63om.spotify.canvazH\x02\x62\x06proto3' +) + +_TYPE = _descriptor.EnumDescriptor( + name='Type', + full_name='com.spotify.canvaz.Type', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='IMAGE', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='VIDEO', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='VIDEO_LOOPING', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='VIDEO_LOOPING_RANDOM', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='GIF', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=41, + serialized_end=123, +) +_sym_db.RegisterEnumDescriptor(_TYPE) + +Type = enum_type_wrapper.EnumTypeWrapper(_TYPE) +IMAGE = 0 +VIDEO = 1 +VIDEO_LOOPING = 2 +VIDEO_LOOPING_RANDOM = 3 +GIF = 4 + +DESCRIPTOR.enum_types_by_name['Type'] = _TYPE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/canvaz_pb2.py b/src/librespot/proto/canvaz_pb2.py new file mode 100644 index 0000000..8438ca0 --- /dev/null +++ b/src/librespot/proto/canvaz_pb2.py @@ -0,0 +1,540 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: canvaz.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +import canvaz_meta_pb2 as canvaz__meta__pb2 + +DESCRIPTOR = _descriptor.FileDescriptor( + name='canvaz.proto', + package='com.spotify.canvazcache', + syntax='proto3', + serialized_options=b'\n\022com.spotify.canvazH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x0c\x63\x61nvaz.proto\x12\x17\x63om.spotify.canvazcache\x1a\x11\x63\x61nvaz-meta.proto\"3\n\x06\x41rtist\x12\x0b\n\x03uri\x18\x01 \x01(\t\x12\x0c\n\x04name\x18\x02 \x01(\t\x12\x0e\n\x06\x61vatar\x18\x03 \x01(\t\"\xe1\x02\n\x14\x45ntityCanvazResponse\x12\x46\n\x08\x63\x61nvases\x18\x01 \x03(\x0b\x32\x34.com.spotify.canvazcache.EntityCanvazResponse.Canvaz\x12\x16\n\x0ettl_in_seconds\x18\x02 \x01(\x03\x1a\xe8\x01\n\x06\x43\x61nvaz\x12\n\n\x02id\x18\x01 \x01(\t\x12\x0b\n\x03url\x18\x02 \x01(\t\x12\x0f\n\x07\x66ile_id\x18\x03 \x01(\t\x12&\n\x04type\x18\x04 \x01(\x0e\x32\x18.com.spotify.canvaz.Type\x12\x12\n\nentity_uri\x18\x05 \x01(\t\x12/\n\x06\x61rtist\x18\x06 \x01(\x0b\x32\x1f.com.spotify.canvazcache.Artist\x12\x10\n\x08\x65xplicit\x18\x07 \x01(\x08\x12\x13\n\x0buploaded_by\x18\x08 \x01(\t\x12\x0c\n\x04\x65tag\x18\t \x01(\t\x12\x12\n\ncanvas_uri\x18\x0b \x01(\t\"\x88\x01\n\x13\x45ntityCanvazRequest\x12\x45\n\x08\x65ntities\x18\x01 \x03(\x0b\x32\x33.com.spotify.canvazcache.EntityCanvazRequest.Entity\x1a*\n\x06\x45ntity\x12\x12\n\nentity_uri\x18\x01 \x01(\t\x12\x0c\n\x04\x65tag\x18\x02 \x01(\tB\x16\n\x12\x63om.spotify.canvazH\x02\x62\x06proto3', + dependencies=[ + canvaz__meta__pb2.DESCRIPTOR, + ]) + +_ARTIST = _descriptor.Descriptor( + name='Artist', + full_name='com.spotify.canvazcache.Artist', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='com.spotify.canvazcache.Artist.uri', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='name', + full_name='com.spotify.canvazcache.Artist.name', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='avatar', + full_name='com.spotify.canvazcache.Artist.avatar', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=60, + serialized_end=111, +) + +_ENTITYCANVAZRESPONSE_CANVAZ = _descriptor.Descriptor( + name='Canvaz', + full_name='com.spotify.canvazcache.EntityCanvazResponse.Canvaz', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='id', + full_name='com.spotify.canvazcache.EntityCanvazResponse.Canvaz.id', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='url', + full_name='com.spotify.canvazcache.EntityCanvazResponse.Canvaz.url', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='file_id', + full_name= + 'com.spotify.canvazcache.EntityCanvazResponse.Canvaz.file_id', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='type', + full_name= + 'com.spotify.canvazcache.EntityCanvazResponse.Canvaz.type', + index=3, + number=4, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='entity_uri', + full_name= + 'com.spotify.canvazcache.EntityCanvazResponse.Canvaz.entity_uri', + index=4, + number=5, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='artist', + full_name= + 'com.spotify.canvazcache.EntityCanvazResponse.Canvaz.artist', + index=5, + number=6, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='explicit', + full_name= + 'com.spotify.canvazcache.EntityCanvazResponse.Canvaz.explicit', + index=6, + number=7, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='uploaded_by', + full_name= + 'com.spotify.canvazcache.EntityCanvazResponse.Canvaz.uploaded_by', + index=7, + number=8, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='etag', + full_name= + 'com.spotify.canvazcache.EntityCanvazResponse.Canvaz.etag', + index=8, + number=9, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='canvas_uri', + full_name= + 'com.spotify.canvazcache.EntityCanvazResponse.Canvaz.canvas_uri', + index=9, + number=11, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=235, + serialized_end=467, +) + +_ENTITYCANVAZRESPONSE = _descriptor.Descriptor( + name='EntityCanvazResponse', + full_name='com.spotify.canvazcache.EntityCanvazResponse', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='canvases', + full_name='com.spotify.canvazcache.EntityCanvazResponse.canvases', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='ttl_in_seconds', + full_name= + 'com.spotify.canvazcache.EntityCanvazResponse.ttl_in_seconds', + index=1, + number=2, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[ + _ENTITYCANVAZRESPONSE_CANVAZ, + ], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=114, + serialized_end=467, +) + +_ENTITYCANVAZREQUEST_ENTITY = _descriptor.Descriptor( + name='Entity', + full_name='com.spotify.canvazcache.EntityCanvazRequest.Entity', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='entity_uri', + full_name= + 'com.spotify.canvazcache.EntityCanvazRequest.Entity.entity_uri', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='etag', + full_name='com.spotify.canvazcache.EntityCanvazRequest.Entity.etag', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=564, + serialized_end=606, +) + +_ENTITYCANVAZREQUEST = _descriptor.Descriptor( + name='EntityCanvazRequest', + full_name='com.spotify.canvazcache.EntityCanvazRequest', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='entities', + full_name='com.spotify.canvazcache.EntityCanvazRequest.entities', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[ + _ENTITYCANVAZREQUEST_ENTITY, + ], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=470, + serialized_end=606, +) + +_ENTITYCANVAZRESPONSE_CANVAZ.fields_by_name[ + 'type'].enum_type = canvaz__meta__pb2._TYPE +_ENTITYCANVAZRESPONSE_CANVAZ.fields_by_name['artist'].message_type = _ARTIST +_ENTITYCANVAZRESPONSE_CANVAZ.containing_type = _ENTITYCANVAZRESPONSE +_ENTITYCANVAZRESPONSE.fields_by_name[ + 'canvases'].message_type = _ENTITYCANVAZRESPONSE_CANVAZ +_ENTITYCANVAZREQUEST_ENTITY.containing_type = _ENTITYCANVAZREQUEST +_ENTITYCANVAZREQUEST.fields_by_name[ + 'entities'].message_type = _ENTITYCANVAZREQUEST_ENTITY +DESCRIPTOR.message_types_by_name['Artist'] = _ARTIST +DESCRIPTOR.message_types_by_name[ + 'EntityCanvazResponse'] = _ENTITYCANVAZRESPONSE +DESCRIPTOR.message_types_by_name['EntityCanvazRequest'] = _ENTITYCANVAZREQUEST +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +Artist = _reflection.GeneratedProtocolMessageType( + 'Artist', + (_message.Message, ), + { + 'DESCRIPTOR': _ARTIST, + '__module__': 'canvaz_pb2' + # @@protoc_insertion_point(class_scope:com.spotify.canvazcache.Artist) + }) +_sym_db.RegisterMessage(Artist) + +EntityCanvazResponse = _reflection.GeneratedProtocolMessageType( + 'EntityCanvazResponse', + (_message.Message, ), + { + 'Canvaz': + _reflection.GeneratedProtocolMessageType( + 'Canvaz', + (_message.Message, ), + { + 'DESCRIPTOR': _ENTITYCANVAZRESPONSE_CANVAZ, + '__module__': 'canvaz_pb2' + # @@protoc_insertion_point(class_scope:com.spotify.canvazcache.EntityCanvazResponse.Canvaz) + }), + 'DESCRIPTOR': + _ENTITYCANVAZRESPONSE, + '__module__': + 'canvaz_pb2' + # @@protoc_insertion_point(class_scope:com.spotify.canvazcache.EntityCanvazResponse) + }) +_sym_db.RegisterMessage(EntityCanvazResponse) +_sym_db.RegisterMessage(EntityCanvazResponse.Canvaz) + +EntityCanvazRequest = _reflection.GeneratedProtocolMessageType( + 'EntityCanvazRequest', + (_message.Message, ), + { + 'Entity': + _reflection.GeneratedProtocolMessageType( + 'Entity', + (_message.Message, ), + { + 'DESCRIPTOR': _ENTITYCANVAZREQUEST_ENTITY, + '__module__': 'canvaz_pb2' + # @@protoc_insertion_point(class_scope:com.spotify.canvazcache.EntityCanvazRequest.Entity) + }), + 'DESCRIPTOR': + _ENTITYCANVAZREQUEST, + '__module__': + 'canvaz_pb2' + # @@protoc_insertion_point(class_scope:com.spotify.canvazcache.EntityCanvazRequest) + }) +_sym_db.RegisterMessage(EntityCanvazRequest) +_sym_db.RegisterMessage(EntityCanvazRequest.Entity) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/context_page_pb2.py b/src/librespot/proto/context_page_pb2.py new file mode 100644 index 0000000..e5fa14c --- /dev/null +++ b/src/librespot/proto/context_page_pb2.py @@ -0,0 +1,229 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: context_page.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +import context_track_pb2 as context__track__pb2 + +DESCRIPTOR = _descriptor.FileDescriptor( + name='context_page.proto', + package='spotify.player.proto', + syntax='proto2', + serialized_options=b'\n\023com.spotify.contextH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x12\x63ontext_page.proto\x12\x14spotify.player.proto\x1a\x13\x63ontext_track.proto\"\xef\x01\n\x0b\x43ontextPage\x12\x10\n\x08page_url\x18\x01 \x01(\t\x12\x15\n\rnext_page_url\x18\x02 \x01(\t\x12\x41\n\x08metadata\x18\x03 \x03(\x0b\x32/.spotify.player.proto.ContextPage.MetadataEntry\x12\x32\n\x06tracks\x18\x04 \x03(\x0b\x32\".spotify.player.proto.ContextTrack\x12\x0f\n\x07loading\x18\x05 \x01(\x08\x1a/\n\rMetadataEntry\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\r\n\x05value\x18\x02 \x01(\t:\x02\x38\x01\x42\x17\n\x13\x63om.spotify.contextH\x02', + dependencies=[ + context__track__pb2.DESCRIPTOR, + ]) + +_CONTEXTPAGE_METADATAENTRY = _descriptor.Descriptor( + name='MetadataEntry', + full_name='spotify.player.proto.ContextPage.MetadataEntry', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='spotify.player.proto.ContextPage.MetadataEntry.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='spotify.player.proto.ContextPage.MetadataEntry.value', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=b'8\001', + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=258, + serialized_end=305, +) + +_CONTEXTPAGE = _descriptor.Descriptor( + name='ContextPage', + full_name='spotify.player.proto.ContextPage', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='page_url', + full_name='spotify.player.proto.ContextPage.page_url', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='next_page_url', + full_name='spotify.player.proto.ContextPage.next_page_url', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='metadata', + full_name='spotify.player.proto.ContextPage.metadata', + index=2, + number=3, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='tracks', + full_name='spotify.player.proto.ContextPage.tracks', + index=3, + number=4, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='loading', + full_name='spotify.player.proto.ContextPage.loading', + index=4, + number=5, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[ + _CONTEXTPAGE_METADATAENTRY, + ], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=66, + serialized_end=305, +) + +_CONTEXTPAGE_METADATAENTRY.containing_type = _CONTEXTPAGE +_CONTEXTPAGE.fields_by_name[ + 'metadata'].message_type = _CONTEXTPAGE_METADATAENTRY +_CONTEXTPAGE.fields_by_name[ + 'tracks'].message_type = context__track__pb2._CONTEXTTRACK +DESCRIPTOR.message_types_by_name['ContextPage'] = _CONTEXTPAGE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +ContextPage = _reflection.GeneratedProtocolMessageType( + 'ContextPage', + (_message.Message, ), + { + 'MetadataEntry': + _reflection.GeneratedProtocolMessageType( + 'MetadataEntry', + (_message.Message, ), + { + 'DESCRIPTOR': _CONTEXTPAGE_METADATAENTRY, + '__module__': 'context_page_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.ContextPage.MetadataEntry) + }), + 'DESCRIPTOR': + _CONTEXTPAGE, + '__module__': + 'context_page_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.ContextPage) + }) +_sym_db.RegisterMessage(ContextPage) +_sym_db.RegisterMessage(ContextPage.MetadataEntry) + +DESCRIPTOR._options = None +_CONTEXTPAGE_METADATAENTRY._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/context_pb2.py b/src/librespot/proto/context_pb2.py new file mode 100644 index 0000000..41b91ce --- /dev/null +++ b/src/librespot/proto/context_pb2.py @@ -0,0 +1,249 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: context.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +import context_page_pb2 as context__page__pb2 +import restrictions_pb2 as restrictions__pb2 + +DESCRIPTOR = _descriptor.FileDescriptor( + name='context.proto', + package='spotify.player.proto', + syntax='proto2', + serialized_options=b'\n\023com.spotify.contextH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\rcontext.proto\x12\x14spotify.player.proto\x1a\x12\x63ontext_page.proto\x1a\x12restrictions.proto\"\x90\x02\n\x07\x43ontext\x12\x0b\n\x03uri\x18\x01 \x01(\t\x12\x0b\n\x03url\x18\x02 \x01(\t\x12=\n\x08metadata\x18\x03 \x03(\x0b\x32+.spotify.player.proto.Context.MetadataEntry\x12\x38\n\x0crestrictions\x18\x04 \x01(\x0b\x32\".spotify.player.proto.Restrictions\x12\x30\n\x05pages\x18\x05 \x03(\x0b\x32!.spotify.player.proto.ContextPage\x12\x0f\n\x07loading\x18\x06 \x01(\x08\x1a/\n\rMetadataEntry\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\r\n\x05value\x18\x02 \x01(\t:\x02\x38\x01\x42\x17\n\x13\x63om.spotify.contextH\x02', + dependencies=[ + context__page__pb2.DESCRIPTOR, + restrictions__pb2.DESCRIPTOR, + ]) + +_CONTEXT_METADATAENTRY = _descriptor.Descriptor( + name='MetadataEntry', + full_name='spotify.player.proto.Context.MetadataEntry', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='spotify.player.proto.Context.MetadataEntry.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='spotify.player.proto.Context.MetadataEntry.value', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=b'8\001', + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=305, + serialized_end=352, +) + +_CONTEXT = _descriptor.Descriptor( + name='Context', + full_name='spotify.player.proto.Context', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='spotify.player.proto.Context.uri', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='url', + full_name='spotify.player.proto.Context.url', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='metadata', + full_name='spotify.player.proto.Context.metadata', + index=2, + number=3, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='restrictions', + full_name='spotify.player.proto.Context.restrictions', + index=3, + number=4, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='pages', + full_name='spotify.player.proto.Context.pages', + index=4, + number=5, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='loading', + full_name='spotify.player.proto.Context.loading', + index=5, + number=6, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[ + _CONTEXT_METADATAENTRY, + ], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=80, + serialized_end=352, +) + +_CONTEXT_METADATAENTRY.containing_type = _CONTEXT +_CONTEXT.fields_by_name['metadata'].message_type = _CONTEXT_METADATAENTRY +_CONTEXT.fields_by_name[ + 'restrictions'].message_type = restrictions__pb2._RESTRICTIONS +_CONTEXT.fields_by_name['pages'].message_type = context__page__pb2._CONTEXTPAGE +DESCRIPTOR.message_types_by_name['Context'] = _CONTEXT +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +Context = _reflection.GeneratedProtocolMessageType( + 'Context', + (_message.Message, ), + { + 'MetadataEntry': + _reflection.GeneratedProtocolMessageType( + 'MetadataEntry', + (_message.Message, ), + { + 'DESCRIPTOR': _CONTEXT_METADATAENTRY, + '__module__': 'context_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.Context.MetadataEntry) + }), + 'DESCRIPTOR': + _CONTEXT, + '__module__': + 'context_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.Context) + }) +_sym_db.RegisterMessage(Context) +_sym_db.RegisterMessage(Context.MetadataEntry) + +DESCRIPTOR._options = None +_CONTEXT_METADATAENTRY._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/context_player_options_pb2.py b/src/librespot/proto/context_player_options_pb2.py new file mode 100644 index 0000000..51a4548 --- /dev/null +++ b/src/librespot/proto/context_player_options_pb2.py @@ -0,0 +1,206 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: context_player_options.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='context_player_options.proto', + package='spotify.player.proto', + syntax='proto2', + serialized_options=b'\n\023com.spotify.contextH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x1c\x63ontext_player_options.proto\x12\x14spotify.player.proto\"e\n\x14\x43ontextPlayerOptions\x12\x19\n\x11shuffling_context\x18\x01 \x01(\x08\x12\x19\n\x11repeating_context\x18\x02 \x01(\x08\x12\x17\n\x0frepeating_track\x18\x03 \x01(\x08\"m\n\x1c\x43ontextPlayerOptionOverrides\x12\x19\n\x11shuffling_context\x18\x01 \x01(\x08\x12\x19\n\x11repeating_context\x18\x02 \x01(\x08\x12\x17\n\x0frepeating_track\x18\x03 \x01(\x08\x42\x17\n\x13\x63om.spotify.contextH\x02' +) + +_CONTEXTPLAYEROPTIONS = _descriptor.Descriptor( + name='ContextPlayerOptions', + full_name='spotify.player.proto.ContextPlayerOptions', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='shuffling_context', + full_name= + 'spotify.player.proto.ContextPlayerOptions.shuffling_context', + index=0, + number=1, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='repeating_context', + full_name= + 'spotify.player.proto.ContextPlayerOptions.repeating_context', + index=1, + number=2, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='repeating_track', + full_name= + 'spotify.player.proto.ContextPlayerOptions.repeating_track', + index=2, + number=3, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=54, + serialized_end=155, +) + +_CONTEXTPLAYEROPTIONOVERRIDES = _descriptor.Descriptor( + name='ContextPlayerOptionOverrides', + full_name='spotify.player.proto.ContextPlayerOptionOverrides', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='shuffling_context', + full_name= + 'spotify.player.proto.ContextPlayerOptionOverrides.shuffling_context', + index=0, + number=1, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='repeating_context', + full_name= + 'spotify.player.proto.ContextPlayerOptionOverrides.repeating_context', + index=1, + number=2, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='repeating_track', + full_name= + 'spotify.player.proto.ContextPlayerOptionOverrides.repeating_track', + index=2, + number=3, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=157, + serialized_end=266, +) + +DESCRIPTOR.message_types_by_name[ + 'ContextPlayerOptions'] = _CONTEXTPLAYEROPTIONS +DESCRIPTOR.message_types_by_name[ + 'ContextPlayerOptionOverrides'] = _CONTEXTPLAYEROPTIONOVERRIDES +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +ContextPlayerOptions = _reflection.GeneratedProtocolMessageType( + 'ContextPlayerOptions', + (_message.Message, ), + { + 'DESCRIPTOR': _CONTEXTPLAYEROPTIONS, + '__module__': 'context_player_options_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.ContextPlayerOptions) + }) +_sym_db.RegisterMessage(ContextPlayerOptions) + +ContextPlayerOptionOverrides = _reflection.GeneratedProtocolMessageType( + 'ContextPlayerOptionOverrides', + (_message.Message, ), + { + 'DESCRIPTOR': _CONTEXTPLAYEROPTIONOVERRIDES, + '__module__': 'context_player_options_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.ContextPlayerOptionOverrides) + }) +_sym_db.RegisterMessage(ContextPlayerOptionOverrides) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/context_track_pb2.py b/src/librespot/proto/context_track_pb2.py new file mode 100644 index 0000000..45155a2 --- /dev/null +++ b/src/librespot/proto/context_track_pb2.py @@ -0,0 +1,205 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: context_track.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='context_track.proto', + package='spotify.player.proto', + syntax='proto2', + serialized_options=b'\n\023com.spotify.contextH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x13\x63ontext_track.proto\x12\x14spotify.player.proto\"\xaa\x01\n\x0c\x43ontextTrack\x12\x0b\n\x03uri\x18\x01 \x01(\t\x12\x0b\n\x03uid\x18\x02 \x01(\t\x12\x0b\n\x03gid\x18\x03 \x01(\x0c\x12\x42\n\x08metadata\x18\x04 \x03(\x0b\x32\x30.spotify.player.proto.ContextTrack.MetadataEntry\x1a/\n\rMetadataEntry\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\r\n\x05value\x18\x02 \x01(\t:\x02\x38\x01\x42\x17\n\x13\x63om.spotify.contextH\x02' +) + +_CONTEXTTRACK_METADATAENTRY = _descriptor.Descriptor( + name='MetadataEntry', + full_name='spotify.player.proto.ContextTrack.MetadataEntry', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='spotify.player.proto.ContextTrack.MetadataEntry.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='spotify.player.proto.ContextTrack.MetadataEntry.value', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=b'8\001', + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=169, + serialized_end=216, +) + +_CONTEXTTRACK = _descriptor.Descriptor( + name='ContextTrack', + full_name='spotify.player.proto.ContextTrack', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='spotify.player.proto.ContextTrack.uri', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='uid', + full_name='spotify.player.proto.ContextTrack.uid', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='gid', + full_name='spotify.player.proto.ContextTrack.gid', + index=2, + number=3, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='metadata', + full_name='spotify.player.proto.ContextTrack.metadata', + index=3, + number=4, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[ + _CONTEXTTRACK_METADATAENTRY, + ], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=46, + serialized_end=216, +) + +_CONTEXTTRACK_METADATAENTRY.containing_type = _CONTEXTTRACK +_CONTEXTTRACK.fields_by_name[ + 'metadata'].message_type = _CONTEXTTRACK_METADATAENTRY +DESCRIPTOR.message_types_by_name['ContextTrack'] = _CONTEXTTRACK +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +ContextTrack = _reflection.GeneratedProtocolMessageType( + 'ContextTrack', + (_message.Message, ), + { + 'MetadataEntry': + _reflection.GeneratedProtocolMessageType( + 'MetadataEntry', + (_message.Message, ), + { + 'DESCRIPTOR': _CONTEXTTRACK_METADATAENTRY, + '__module__': 'context_track_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.ContextTrack.MetadataEntry) + }), + 'DESCRIPTOR': + _CONTEXTTRACK, + '__module__': + 'context_track_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.ContextTrack) + }) +_sym_db.RegisterMessage(ContextTrack) +_sym_db.RegisterMessage(ContextTrack.MetadataEntry) + +DESCRIPTOR._options = None +_CONTEXTTRACK_METADATAENTRY._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/play_origin_pb2.py b/src/librespot/proto/play_origin_pb2.py new file mode 100644 index 0000000..e013e4c --- /dev/null +++ b/src/librespot/proto/play_origin_pb2.py @@ -0,0 +1,184 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: play_origin.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='play_origin.proto', + package='spotify.player.proto', + syntax='proto2', + serialized_options=b'\n\023com.spotify.contextH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x11play_origin.proto\x12\x14spotify.player.proto\"\xbf\x01\n\nPlayOrigin\x12\x1a\n\x12\x66\x65\x61ture_identifier\x18\x01 \x01(\t\x12\x17\n\x0f\x66\x65\x61ture_version\x18\x02 \x01(\t\x12\x10\n\x08view_uri\x18\x03 \x01(\t\x12\x19\n\x11\x65xternal_referrer\x18\x04 \x01(\t\x12\x1b\n\x13referrer_identifier\x18\x05 \x01(\t\x12\x19\n\x11\x64\x65vice_identifier\x18\x06 \x01(\t\x12\x17\n\x0f\x66\x65\x61ture_classes\x18\x07 \x03(\tB\x17\n\x13\x63om.spotify.contextH\x02' +) + +_PLAYORIGIN = _descriptor.Descriptor( + name='PlayOrigin', + full_name='spotify.player.proto.PlayOrigin', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='feature_identifier', + full_name='spotify.player.proto.PlayOrigin.feature_identifier', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='feature_version', + full_name='spotify.player.proto.PlayOrigin.feature_version', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='view_uri', + full_name='spotify.player.proto.PlayOrigin.view_uri', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='external_referrer', + full_name='spotify.player.proto.PlayOrigin.external_referrer', + index=3, + number=4, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='referrer_identifier', + full_name='spotify.player.proto.PlayOrigin.referrer_identifier', + index=4, + number=5, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='device_identifier', + full_name='spotify.player.proto.PlayOrigin.device_identifier', + index=5, + number=6, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='feature_classes', + full_name='spotify.player.proto.PlayOrigin.feature_classes', + index=6, + number=7, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=44, + serialized_end=235, +) + +DESCRIPTOR.message_types_by_name['PlayOrigin'] = _PLAYORIGIN +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +PlayOrigin = _reflection.GeneratedProtocolMessageType( + 'PlayOrigin', + (_message.Message, ), + { + 'DESCRIPTOR': _PLAYORIGIN, + '__module__': 'play_origin_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.PlayOrigin) + }) +_sym_db.RegisterMessage(PlayOrigin) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/playback_pb2.py b/src/librespot/proto/playback_pb2.py new file mode 100644 index 0000000..7c40df4 --- /dev/null +++ b/src/librespot/proto/playback_pb2.py @@ -0,0 +1,155 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: playback.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +import context_track_pb2 as context__track__pb2 + +DESCRIPTOR = _descriptor.FileDescriptor( + name='playback.proto', + package='spotify.player.proto.transfer', + syntax='proto2', + serialized_options=b'\n\024com.spotify.transferH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x0eplayback.proto\x12\x1dspotify.player.proto.transfer\x1a\x13\x63ontext_track.proto\"\xa5\x01\n\x08Playback\x12\x11\n\ttimestamp\x18\x01 \x01(\x03\x12 \n\x18position_as_of_timestamp\x18\x02 \x01(\x05\x12\x16\n\x0eplayback_speed\x18\x03 \x01(\x01\x12\x11\n\tis_paused\x18\x04 \x01(\x08\x12\x39\n\rcurrent_track\x18\x05 \x01(\x0b\x32\".spotify.player.proto.ContextTrackB\x18\n\x14\x63om.spotify.transferH\x02', + dependencies=[ + context__track__pb2.DESCRIPTOR, + ]) + +_PLAYBACK = _descriptor.Descriptor( + name='Playback', + full_name='spotify.player.proto.transfer.Playback', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='timestamp', + full_name='spotify.player.proto.transfer.Playback.timestamp', + index=0, + number=1, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='position_as_of_timestamp', + full_name= + 'spotify.player.proto.transfer.Playback.position_as_of_timestamp', + index=1, + number=2, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='playback_speed', + full_name='spotify.player.proto.transfer.Playback.playback_speed', + index=2, + number=3, + type=1, + cpp_type=5, + label=1, + has_default_value=False, + default_value=float(0), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_paused', + full_name='spotify.player.proto.transfer.Playback.is_paused', + index=3, + number=4, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='current_track', + full_name='spotify.player.proto.transfer.Playback.current_track', + index=4, + number=5, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=71, + serialized_end=236, +) + +_PLAYBACK.fields_by_name[ + 'current_track'].message_type = context__track__pb2._CONTEXTTRACK +DESCRIPTOR.message_types_by_name['Playback'] = _PLAYBACK +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +Playback = _reflection.GeneratedProtocolMessageType( + 'Playback', + (_message.Message, ), + { + 'DESCRIPTOR': _PLAYBACK, + '__module__': 'playback_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.transfer.Playback) + }) +_sym_db.RegisterMessage(Playback) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/player_pb2.py b/src/librespot/proto/player_pb2.py new file mode 100644 index 0000000..cd267de --- /dev/null +++ b/src/librespot/proto/player_pb2.py @@ -0,0 +1,1851 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: player.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='player.proto', + package='connectstate', + syntax='proto3', + serialized_options=b'\n\030com.spotify.connectstateH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x0cplayer.proto\x12\x0c\x63onnectstate\"\xea\x08\n\x0bPlayerState\x12\x11\n\ttimestamp\x18\x01 \x01(\x03\x12\x13\n\x0b\x63ontext_uri\x18\x02 \x01(\t\x12\x13\n\x0b\x63ontext_url\x18\x03 \x01(\t\x12\x38\n\x14\x63ontext_restrictions\x18\x04 \x01(\x0b\x32\x1a.connectstate.Restrictions\x12-\n\x0bplay_origin\x18\x05 \x01(\x0b\x32\x18.connectstate.PlayOrigin\x12)\n\x05index\x18\x06 \x01(\x0b\x32\x1a.connectstate.ContextIndex\x12*\n\x05track\x18\x07 \x01(\x0b\x32\x1b.connectstate.ProvidedTrack\x12\x13\n\x0bplayback_id\x18\x08 \x01(\t\x12\x16\n\x0eplayback_speed\x18\t \x01(\x01\x12 \n\x18position_as_of_timestamp\x18\n \x01(\x03\x12\x10\n\x08\x64uration\x18\x0b \x01(\x03\x12\x12\n\nis_playing\x18\x0c \x01(\x08\x12\x11\n\tis_paused\x18\r \x01(\x08\x12\x14\n\x0cis_buffering\x18\x0e \x01(\x08\x12\x1b\n\x13is_system_initiated\x18\x0f \x01(\x08\x12\x33\n\x07options\x18\x10 \x01(\x0b\x32\".connectstate.ContextPlayerOptions\x12\x30\n\x0crestrictions\x18\x11 \x01(\x0b\x32\x1a.connectstate.Restrictions\x12\x30\n\x0csuppressions\x18\x12 \x01(\x0b\x32\x1a.connectstate.Suppressions\x12\x30\n\x0bprev_tracks\x18\x13 \x03(\x0b\x32\x1b.connectstate.ProvidedTrack\x12\x30\n\x0bnext_tracks\x18\x14 \x03(\x0b\x32\x1b.connectstate.ProvidedTrack\x12H\n\x10\x63ontext_metadata\x18\x15 \x03(\x0b\x32..connectstate.PlayerState.ContextMetadataEntry\x12\x42\n\rpage_metadata\x18\x16 \x03(\x0b\x32+.connectstate.PlayerState.PageMetadataEntry\x12\x12\n\nsession_id\x18\x17 \x01(\t\x12\x16\n\x0equeue_revision\x18\x18 \x01(\t\x12\x10\n\x08position\x18\x19 \x01(\x03\x12\x12\n\nentity_uri\x18\x1a \x01(\t\x12,\n\x07reverse\x18\x1b \x03(\x0b\x32\x1b.connectstate.ProvidedTrack\x12+\n\x06\x66uture\x18\x1c \x03(\x0b\x32\x1b.connectstate.ProvidedTrack\x1a\x36\n\x14\x43ontextMetadataEntry\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\r\n\x05value\x18\x02 \x01(\t:\x02\x38\x01\x1a\x33\n\x11PageMetadataEntry\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\r\n\x05value\x18\x02 \x01(\t:\x02\x38\x01\"\xda\x02\n\rProvidedTrack\x12\x0b\n\x03uri\x18\x01 \x01(\t\x12\x0b\n\x03uid\x18\x02 \x01(\t\x12;\n\x08metadata\x18\x03 \x03(\x0b\x32).connectstate.ProvidedTrack.MetadataEntry\x12\x0f\n\x07removed\x18\x04 \x03(\t\x12\x0f\n\x07\x62locked\x18\x05 \x03(\t\x12\x10\n\x08provider\x18\x06 \x01(\t\x12\x30\n\x0crestrictions\x18\x07 \x01(\x0b\x32\x1a.connectstate.Restrictions\x12\x11\n\talbum_uri\x18\x08 \x01(\t\x12\x18\n\x10\x64isallow_reasons\x18\t \x03(\t\x12\x12\n\nartist_uri\x18\n \x01(\t\x12\x1a\n\x12\x64isallow_undecided\x18\x0b \x03(\t\x1a/\n\rMetadataEntry\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\r\n\x05value\x18\x02 \x01(\t:\x02\x38\x01\"+\n\x0c\x43ontextIndex\x12\x0c\n\x04page\x18\x01 \x01(\r\x12\r\n\x05track\x18\x02 \x01(\r\"\x80\x08\n\x0cRestrictions\x12 \n\x18\x64isallow_pausing_reasons\x18\x01 \x03(\t\x12!\n\x19\x64isallow_resuming_reasons\x18\x02 \x03(\t\x12 \n\x18\x64isallow_seeking_reasons\x18\x03 \x03(\t\x12%\n\x1d\x64isallow_peeking_prev_reasons\x18\x04 \x03(\t\x12%\n\x1d\x64isallow_peeking_next_reasons\x18\x05 \x03(\t\x12&\n\x1e\x64isallow_skipping_prev_reasons\x18\x06 \x03(\t\x12&\n\x1e\x64isallow_skipping_next_reasons\x18\x07 \x03(\t\x12\x30\n(disallow_toggling_repeat_context_reasons\x18\x08 \x03(\t\x12.\n&disallow_toggling_repeat_track_reasons\x18\t \x03(\t\x12)\n!disallow_toggling_shuffle_reasons\x18\n \x03(\t\x12\"\n\x1a\x64isallow_set_queue_reasons\x18\x0b \x03(\t\x12.\n&disallow_interrupting_playback_reasons\x18\x0c \x03(\t\x12.\n&disallow_transferring_playback_reasons\x18\r \x03(\t\x12\'\n\x1f\x64isallow_remote_control_reasons\x18\x0e \x03(\t\x12\x33\n+disallow_inserting_into_next_tracks_reasons\x18\x0f \x03(\t\x12\x36\n.disallow_inserting_into_context_tracks_reasons\x18\x10 \x03(\t\x12\x32\n*disallow_reordering_in_next_tracks_reasons\x18\x11 \x03(\t\x12\x35\n-disallow_reordering_in_context_tracks_reasons\x18\x12 \x03(\t\x12\x32\n*disallow_removing_from_next_tracks_reasons\x18\x13 \x03(\t\x12\x35\n-disallow_removing_from_context_tracks_reasons\x18\x14 \x03(\t\x12)\n!disallow_updating_context_reasons\x18\x15 \x03(\t\x12 \n\x18\x64isallow_playing_reasons\x18\x16 \x03(\t\x12!\n\x19\x64isallow_stopping_reasons\x18\x17 \x03(\t\"\xbf\x01\n\nPlayOrigin\x12\x1a\n\x12\x66\x65\x61ture_identifier\x18\x01 \x01(\t\x12\x17\n\x0f\x66\x65\x61ture_version\x18\x02 \x01(\t\x12\x10\n\x08view_uri\x18\x03 \x01(\t\x12\x19\n\x11\x65xternal_referrer\x18\x04 \x01(\t\x12\x1b\n\x13referrer_identifier\x18\x05 \x01(\t\x12\x19\n\x11\x64\x65vice_identifier\x18\x06 \x01(\t\x12\x17\n\x0f\x66\x65\x61ture_classes\x18\x07 \x03(\t\"e\n\x14\x43ontextPlayerOptions\x12\x19\n\x11shuffling_context\x18\x01 \x01(\x08\x12\x19\n\x11repeating_context\x18\x02 \x01(\x08\x12\x17\n\x0frepeating_track\x18\x03 \x01(\x08\"!\n\x0cSuppressions\x12\x11\n\tproviders\x18\x01 \x03(\tB\x1c\n\x18\x63om.spotify.connectstateH\x02\x62\x06proto3' +) + +_PLAYERSTATE_CONTEXTMETADATAENTRY = _descriptor.Descriptor( + name='ContextMetadataEntry', + full_name='connectstate.PlayerState.ContextMetadataEntry', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='connectstate.PlayerState.ContextMetadataEntry.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='connectstate.PlayerState.ContextMetadataEntry.value', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=b'8\001', + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1054, + serialized_end=1108, +) + +_PLAYERSTATE_PAGEMETADATAENTRY = _descriptor.Descriptor( + name='PageMetadataEntry', + full_name='connectstate.PlayerState.PageMetadataEntry', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='connectstate.PlayerState.PageMetadataEntry.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='connectstate.PlayerState.PageMetadataEntry.value', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=b'8\001', + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1110, + serialized_end=1161, +) + +_PLAYERSTATE = _descriptor.Descriptor( + name='PlayerState', + full_name='connectstate.PlayerState', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='timestamp', + full_name='connectstate.PlayerState.timestamp', + index=0, + number=1, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='context_uri', + full_name='connectstate.PlayerState.context_uri', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='context_url', + full_name='connectstate.PlayerState.context_url', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='context_restrictions', + full_name='connectstate.PlayerState.context_restrictions', + index=3, + number=4, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='play_origin', + full_name='connectstate.PlayerState.play_origin', + index=4, + number=5, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='index', + full_name='connectstate.PlayerState.index', + index=5, + number=6, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='track', + full_name='connectstate.PlayerState.track', + index=6, + number=7, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='playback_id', + full_name='connectstate.PlayerState.playback_id', + index=7, + number=8, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='playback_speed', + full_name='connectstate.PlayerState.playback_speed', + index=8, + number=9, + type=1, + cpp_type=5, + label=1, + has_default_value=False, + default_value=float(0), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='position_as_of_timestamp', + full_name='connectstate.PlayerState.position_as_of_timestamp', + index=9, + number=10, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='duration', + full_name='connectstate.PlayerState.duration', + index=10, + number=11, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_playing', + full_name='connectstate.PlayerState.is_playing', + index=11, + number=12, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_paused', + full_name='connectstate.PlayerState.is_paused', + index=12, + number=13, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_buffering', + full_name='connectstate.PlayerState.is_buffering', + index=13, + number=14, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_system_initiated', + full_name='connectstate.PlayerState.is_system_initiated', + index=14, + number=15, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='options', + full_name='connectstate.PlayerState.options', + index=15, + number=16, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='restrictions', + full_name='connectstate.PlayerState.restrictions', + index=16, + number=17, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='suppressions', + full_name='connectstate.PlayerState.suppressions', + index=17, + number=18, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='prev_tracks', + full_name='connectstate.PlayerState.prev_tracks', + index=18, + number=19, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='next_tracks', + full_name='connectstate.PlayerState.next_tracks', + index=19, + number=20, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='context_metadata', + full_name='connectstate.PlayerState.context_metadata', + index=20, + number=21, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='page_metadata', + full_name='connectstate.PlayerState.page_metadata', + index=21, + number=22, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='session_id', + full_name='connectstate.PlayerState.session_id', + index=22, + number=23, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='queue_revision', + full_name='connectstate.PlayerState.queue_revision', + index=23, + number=24, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='position', + full_name='connectstate.PlayerState.position', + index=24, + number=25, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='entity_uri', + full_name='connectstate.PlayerState.entity_uri', + index=25, + number=26, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='reverse', + full_name='connectstate.PlayerState.reverse', + index=26, + number=27, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='future', + full_name='connectstate.PlayerState.future', + index=27, + number=28, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[ + _PLAYERSTATE_CONTEXTMETADATAENTRY, + _PLAYERSTATE_PAGEMETADATAENTRY, + ], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=31, + serialized_end=1161, +) + +_PROVIDEDTRACK_METADATAENTRY = _descriptor.Descriptor( + name='MetadataEntry', + full_name='connectstate.ProvidedTrack.MetadataEntry', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='connectstate.ProvidedTrack.MetadataEntry.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='connectstate.ProvidedTrack.MetadataEntry.value', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=b'8\001', + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1463, + serialized_end=1510, +) + +_PROVIDEDTRACK = _descriptor.Descriptor( + name='ProvidedTrack', + full_name='connectstate.ProvidedTrack', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='connectstate.ProvidedTrack.uri', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='uid', + full_name='connectstate.ProvidedTrack.uid', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='metadata', + full_name='connectstate.ProvidedTrack.metadata', + index=2, + number=3, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='removed', + full_name='connectstate.ProvidedTrack.removed', + index=3, + number=4, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='blocked', + full_name='connectstate.ProvidedTrack.blocked', + index=4, + number=5, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='provider', + full_name='connectstate.ProvidedTrack.provider', + index=5, + number=6, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='restrictions', + full_name='connectstate.ProvidedTrack.restrictions', + index=6, + number=7, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='album_uri', + full_name='connectstate.ProvidedTrack.album_uri', + index=7, + number=8, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_reasons', + full_name='connectstate.ProvidedTrack.disallow_reasons', + index=8, + number=9, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='artist_uri', + full_name='connectstate.ProvidedTrack.artist_uri', + index=9, + number=10, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_undecided', + full_name='connectstate.ProvidedTrack.disallow_undecided', + index=10, + number=11, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[ + _PROVIDEDTRACK_METADATAENTRY, + ], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1164, + serialized_end=1510, +) + +_CONTEXTINDEX = _descriptor.Descriptor( + name='ContextIndex', + full_name='connectstate.ContextIndex', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='page', + full_name='connectstate.ContextIndex.page', + index=0, + number=1, + type=13, + cpp_type=3, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='track', + full_name='connectstate.ContextIndex.track', + index=1, + number=2, + type=13, + cpp_type=3, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1512, + serialized_end=1555, +) + +_RESTRICTIONS = _descriptor.Descriptor( + name='Restrictions', + full_name='connectstate.Restrictions', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='disallow_pausing_reasons', + full_name='connectstate.Restrictions.disallow_pausing_reasons', + index=0, + number=1, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_resuming_reasons', + full_name='connectstate.Restrictions.disallow_resuming_reasons', + index=1, + number=2, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_seeking_reasons', + full_name='connectstate.Restrictions.disallow_seeking_reasons', + index=2, + number=3, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_peeking_prev_reasons', + full_name='connectstate.Restrictions.disallow_peeking_prev_reasons', + index=3, + number=4, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_peeking_next_reasons', + full_name='connectstate.Restrictions.disallow_peeking_next_reasons', + index=4, + number=5, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_skipping_prev_reasons', + full_name= + 'connectstate.Restrictions.disallow_skipping_prev_reasons', + index=5, + number=6, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_skipping_next_reasons', + full_name= + 'connectstate.Restrictions.disallow_skipping_next_reasons', + index=6, + number=7, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_toggling_repeat_context_reasons', + full_name= + 'connectstate.Restrictions.disallow_toggling_repeat_context_reasons', + index=7, + number=8, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_toggling_repeat_track_reasons', + full_name= + 'connectstate.Restrictions.disallow_toggling_repeat_track_reasons', + index=8, + number=9, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_toggling_shuffle_reasons', + full_name= + 'connectstate.Restrictions.disallow_toggling_shuffle_reasons', + index=9, + number=10, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_set_queue_reasons', + full_name='connectstate.Restrictions.disallow_set_queue_reasons', + index=10, + number=11, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_interrupting_playback_reasons', + full_name= + 'connectstate.Restrictions.disallow_interrupting_playback_reasons', + index=11, + number=12, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_transferring_playback_reasons', + full_name= + 'connectstate.Restrictions.disallow_transferring_playback_reasons', + index=12, + number=13, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_remote_control_reasons', + full_name= + 'connectstate.Restrictions.disallow_remote_control_reasons', + index=13, + number=14, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_inserting_into_next_tracks_reasons', + full_name= + 'connectstate.Restrictions.disallow_inserting_into_next_tracks_reasons', + index=14, + number=15, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_inserting_into_context_tracks_reasons', + full_name= + 'connectstate.Restrictions.disallow_inserting_into_context_tracks_reasons', + index=15, + number=16, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_reordering_in_next_tracks_reasons', + full_name= + 'connectstate.Restrictions.disallow_reordering_in_next_tracks_reasons', + index=16, + number=17, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_reordering_in_context_tracks_reasons', + full_name= + 'connectstate.Restrictions.disallow_reordering_in_context_tracks_reasons', + index=17, + number=18, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_removing_from_next_tracks_reasons', + full_name= + 'connectstate.Restrictions.disallow_removing_from_next_tracks_reasons', + index=18, + number=19, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_removing_from_context_tracks_reasons', + full_name= + 'connectstate.Restrictions.disallow_removing_from_context_tracks_reasons', + index=19, + number=20, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_updating_context_reasons', + full_name= + 'connectstate.Restrictions.disallow_updating_context_reasons', + index=20, + number=21, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_playing_reasons', + full_name='connectstate.Restrictions.disallow_playing_reasons', + index=21, + number=22, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_stopping_reasons', + full_name='connectstate.Restrictions.disallow_stopping_reasons', + index=22, + number=23, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1558, + serialized_end=2582, +) + +_PLAYORIGIN = _descriptor.Descriptor( + name='PlayOrigin', + full_name='connectstate.PlayOrigin', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='feature_identifier', + full_name='connectstate.PlayOrigin.feature_identifier', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='feature_version', + full_name='connectstate.PlayOrigin.feature_version', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='view_uri', + full_name='connectstate.PlayOrigin.view_uri', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='external_referrer', + full_name='connectstate.PlayOrigin.external_referrer', + index=3, + number=4, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='referrer_identifier', + full_name='connectstate.PlayOrigin.referrer_identifier', + index=4, + number=5, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='device_identifier', + full_name='connectstate.PlayOrigin.device_identifier', + index=5, + number=6, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='feature_classes', + full_name='connectstate.PlayOrigin.feature_classes', + index=6, + number=7, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=2585, + serialized_end=2776, +) + +_CONTEXTPLAYEROPTIONS = _descriptor.Descriptor( + name='ContextPlayerOptions', + full_name='connectstate.ContextPlayerOptions', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='shuffling_context', + full_name='connectstate.ContextPlayerOptions.shuffling_context', + index=0, + number=1, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='repeating_context', + full_name='connectstate.ContextPlayerOptions.repeating_context', + index=1, + number=2, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='repeating_track', + full_name='connectstate.ContextPlayerOptions.repeating_track', + index=2, + number=3, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=2778, + serialized_end=2879, +) + +_SUPPRESSIONS = _descriptor.Descriptor( + name='Suppressions', + full_name='connectstate.Suppressions', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='providers', + full_name='connectstate.Suppressions.providers', + index=0, + number=1, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=2881, + serialized_end=2914, +) + +_PLAYERSTATE_CONTEXTMETADATAENTRY.containing_type = _PLAYERSTATE +_PLAYERSTATE_PAGEMETADATAENTRY.containing_type = _PLAYERSTATE +_PLAYERSTATE.fields_by_name[ + 'context_restrictions'].message_type = _RESTRICTIONS +_PLAYERSTATE.fields_by_name['play_origin'].message_type = _PLAYORIGIN +_PLAYERSTATE.fields_by_name['index'].message_type = _CONTEXTINDEX +_PLAYERSTATE.fields_by_name['track'].message_type = _PROVIDEDTRACK +_PLAYERSTATE.fields_by_name['options'].message_type = _CONTEXTPLAYEROPTIONS +_PLAYERSTATE.fields_by_name['restrictions'].message_type = _RESTRICTIONS +_PLAYERSTATE.fields_by_name['suppressions'].message_type = _SUPPRESSIONS +_PLAYERSTATE.fields_by_name['prev_tracks'].message_type = _PROVIDEDTRACK +_PLAYERSTATE.fields_by_name['next_tracks'].message_type = _PROVIDEDTRACK +_PLAYERSTATE.fields_by_name[ + 'context_metadata'].message_type = _PLAYERSTATE_CONTEXTMETADATAENTRY +_PLAYERSTATE.fields_by_name[ + 'page_metadata'].message_type = _PLAYERSTATE_PAGEMETADATAENTRY +_PLAYERSTATE.fields_by_name['reverse'].message_type = _PROVIDEDTRACK +_PLAYERSTATE.fields_by_name['future'].message_type = _PROVIDEDTRACK +_PROVIDEDTRACK_METADATAENTRY.containing_type = _PROVIDEDTRACK +_PROVIDEDTRACK.fields_by_name[ + 'metadata'].message_type = _PROVIDEDTRACK_METADATAENTRY +_PROVIDEDTRACK.fields_by_name['restrictions'].message_type = _RESTRICTIONS +DESCRIPTOR.message_types_by_name['PlayerState'] = _PLAYERSTATE +DESCRIPTOR.message_types_by_name['ProvidedTrack'] = _PROVIDEDTRACK +DESCRIPTOR.message_types_by_name['ContextIndex'] = _CONTEXTINDEX +DESCRIPTOR.message_types_by_name['Restrictions'] = _RESTRICTIONS +DESCRIPTOR.message_types_by_name['PlayOrigin'] = _PLAYORIGIN +DESCRIPTOR.message_types_by_name[ + 'ContextPlayerOptions'] = _CONTEXTPLAYEROPTIONS +DESCRIPTOR.message_types_by_name['Suppressions'] = _SUPPRESSIONS +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +PlayerState = _reflection.GeneratedProtocolMessageType( + 'PlayerState', + (_message.Message, ), + { + 'ContextMetadataEntry': + _reflection.GeneratedProtocolMessageType( + 'ContextMetadataEntry', + (_message.Message, ), + { + 'DESCRIPTOR': _PLAYERSTATE_CONTEXTMETADATAENTRY, + '__module__': 'player_pb2' + # @@protoc_insertion_point(class_scope:connectstate.PlayerState.ContextMetadataEntry) + }), + 'PageMetadataEntry': + _reflection.GeneratedProtocolMessageType( + 'PageMetadataEntry', + (_message.Message, ), + { + 'DESCRIPTOR': _PLAYERSTATE_PAGEMETADATAENTRY, + '__module__': 'player_pb2' + # @@protoc_insertion_point(class_scope:connectstate.PlayerState.PageMetadataEntry) + }), + 'DESCRIPTOR': + _PLAYERSTATE, + '__module__': + 'player_pb2' + # @@protoc_insertion_point(class_scope:connectstate.PlayerState) + }) +_sym_db.RegisterMessage(PlayerState) +_sym_db.RegisterMessage(PlayerState.ContextMetadataEntry) +_sym_db.RegisterMessage(PlayerState.PageMetadataEntry) + +ProvidedTrack = _reflection.GeneratedProtocolMessageType( + 'ProvidedTrack', + (_message.Message, ), + { + 'MetadataEntry': + _reflection.GeneratedProtocolMessageType( + 'MetadataEntry', + (_message.Message, ), + { + 'DESCRIPTOR': _PROVIDEDTRACK_METADATAENTRY, + '__module__': 'player_pb2' + # @@protoc_insertion_point(class_scope:connectstate.ProvidedTrack.MetadataEntry) + }), + 'DESCRIPTOR': + _PROVIDEDTRACK, + '__module__': + 'player_pb2' + # @@protoc_insertion_point(class_scope:connectstate.ProvidedTrack) + }) +_sym_db.RegisterMessage(ProvidedTrack) +_sym_db.RegisterMessage(ProvidedTrack.MetadataEntry) + +ContextIndex = _reflection.GeneratedProtocolMessageType( + 'ContextIndex', + (_message.Message, ), + { + 'DESCRIPTOR': _CONTEXTINDEX, + '__module__': 'player_pb2' + # @@protoc_insertion_point(class_scope:connectstate.ContextIndex) + }) +_sym_db.RegisterMessage(ContextIndex) + +Restrictions = _reflection.GeneratedProtocolMessageType( + 'Restrictions', + (_message.Message, ), + { + 'DESCRIPTOR': _RESTRICTIONS, + '__module__': 'player_pb2' + # @@protoc_insertion_point(class_scope:connectstate.Restrictions) + }) +_sym_db.RegisterMessage(Restrictions) + +PlayOrigin = _reflection.GeneratedProtocolMessageType( + 'PlayOrigin', + (_message.Message, ), + { + 'DESCRIPTOR': _PLAYORIGIN, + '__module__': 'player_pb2' + # @@protoc_insertion_point(class_scope:connectstate.PlayOrigin) + }) +_sym_db.RegisterMessage(PlayOrigin) + +ContextPlayerOptions = _reflection.GeneratedProtocolMessageType( + 'ContextPlayerOptions', + (_message.Message, ), + { + 'DESCRIPTOR': _CONTEXTPLAYEROPTIONS, + '__module__': 'player_pb2' + # @@protoc_insertion_point(class_scope:connectstate.ContextPlayerOptions) + }) +_sym_db.RegisterMessage(ContextPlayerOptions) + +Suppressions = _reflection.GeneratedProtocolMessageType( + 'Suppressions', + (_message.Message, ), + { + 'DESCRIPTOR': _SUPPRESSIONS, + '__module__': 'player_pb2' + # @@protoc_insertion_point(class_scope:connectstate.Suppressions) + }) +_sym_db.RegisterMessage(Suppressions) + +DESCRIPTOR._options = None +_PLAYERSTATE_CONTEXTMETADATAENTRY._options = None +_PLAYERSTATE_PAGEMETADATAENTRY._options = None +_PROVIDEDTRACK_METADATAENTRY._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/playlist4_external_pb2.py b/src/librespot/proto/playlist4_external_pb2.py new file mode 100644 index 0000000..72c5896 --- /dev/null +++ b/src/librespot/proto/playlist4_external_pb2.py @@ -0,0 +1,3062 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: playlist4_external.proto +"""Generated protocol buffer code.""" +from google.protobuf.internal import enum_type_wrapper +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='playlist4_external.proto', + package='spotify.playlist4.proto', + syntax='proto2', + serialized_options= + b'\n\025com.spotify.playlist4B\021Playlist4ApiProtoH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x18playlist4_external.proto\x12\x17spotify.playlist4.proto\"P\n\x04Item\x12\x0b\n\x03uri\x18\x01 \x02(\t\x12;\n\nattributes\x18\x02 \x01(\x0b\x32\'.spotify.playlist4.proto.ItemAttributes\"\x94\x01\n\x08MetaItem\x12\x10\n\x08revision\x18\x01 \x01(\x0c\x12;\n\nattributes\x18\x02 \x01(\x0b\x32\'.spotify.playlist4.proto.ListAttributes\x12\x0e\n\x06length\x18\x03 \x01(\x05\x12\x11\n\ttimestamp\x18\x04 \x01(\x03\x12\x16\n\x0eowner_username\x18\x05 \x01(\t\"\x90\x01\n\tListItems\x12\x0b\n\x03pos\x18\x01 \x02(\x05\x12\x11\n\ttruncated\x18\x02 \x02(\x08\x12,\n\x05items\x18\x03 \x03(\x0b\x32\x1d.spotify.playlist4.proto.Item\x12\x35\n\nmeta_items\x18\x04 \x03(\x0b\x32!.spotify.playlist4.proto.MetaItem\"1\n\x13\x46ormatListAttribute\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\r\n\x05value\x18\x02 \x01(\t\"\xf6\x01\n\x0eListAttributes\x12\x0c\n\x04name\x18\x01 \x01(\t\x12\x13\n\x0b\x64\x65scription\x18\x02 \x01(\t\x12\x0f\n\x07picture\x18\x03 \x01(\x0c\x12\x15\n\rcollaborative\x18\x04 \x01(\x08\x12\x13\n\x0bpl3_version\x18\x05 \x01(\t\x12\x18\n\x10\x64\x65leted_by_owner\x18\x06 \x01(\x08\x12\x11\n\tclient_id\x18\n \x01(\t\x12\x0e\n\x06\x66ormat\x18\x0b \x01(\t\x12G\n\x11\x66ormat_attributes\x18\x0c \x03(\x0b\x32,.spotify.playlist4.proto.FormatListAttribute\"\xb0\x01\n\x0eItemAttributes\x12\x10\n\x08\x61\x64\x64\x65\x64_by\x18\x01 \x01(\t\x12\x11\n\ttimestamp\x18\x02 \x01(\x03\x12\x0f\n\x07seen_at\x18\t \x01(\x03\x12\x0e\n\x06public\x18\n \x01(\x08\x12G\n\x11\x66ormat_attributes\x18\x0b \x03(\x0b\x32,.spotify.playlist4.proto.FormatListAttribute\x12\x0f\n\x07item_id\x18\x0c \x01(\x0c\"l\n\x03\x41\x64\x64\x12\x12\n\nfrom_index\x18\x01 \x01(\x05\x12,\n\x05items\x18\x02 \x03(\x0b\x32\x1d.spotify.playlist4.proto.Item\x12\x10\n\x08\x61\x64\x64_last\x18\x04 \x01(\x08\x12\x11\n\tadd_first\x18\x05 \x01(\x08\"m\n\x03Rem\x12\x12\n\nfrom_index\x18\x01 \x01(\x05\x12\x0e\n\x06length\x18\x02 \x01(\x05\x12,\n\x05items\x18\x03 \x03(\x0b\x32\x1d.spotify.playlist4.proto.Item\x12\x14\n\x0citems_as_key\x18\x07 \x01(\x08\";\n\x03Mov\x12\x12\n\nfrom_index\x18\x01 \x02(\x05\x12\x0e\n\x06length\x18\x02 \x02(\x05\x12\x10\n\x08to_index\x18\x03 \x02(\x05\"\x93\x01\n\x1aItemAttributesPartialState\x12\x37\n\x06values\x18\x01 \x02(\x0b\x32\'.spotify.playlist4.proto.ItemAttributes\x12<\n\x08no_value\x18\x02 \x03(\x0e\x32*.spotify.playlist4.proto.ItemAttributeKind\"\x93\x01\n\x1aListAttributesPartialState\x12\x37\n\x06values\x18\x01 \x02(\x0b\x32\'.spotify.playlist4.proto.ListAttributes\x12<\n\x08no_value\x18\x02 \x03(\x0e\x32*.spotify.playlist4.proto.ListAttributeKind\"\xbf\x01\n\x14UpdateItemAttributes\x12\r\n\x05index\x18\x01 \x02(\x05\x12K\n\x0enew_attributes\x18\x02 \x02(\x0b\x32\x33.spotify.playlist4.proto.ItemAttributesPartialState\x12K\n\x0eold_attributes\x18\x03 \x01(\x0b\x32\x33.spotify.playlist4.proto.ItemAttributesPartialState\"\xb0\x01\n\x14UpdateListAttributes\x12K\n\x0enew_attributes\x18\x01 \x02(\x0b\x32\x33.spotify.playlist4.proto.ListAttributesPartialState\x12K\n\x0eold_attributes\x18\x02 \x01(\x0b\x32\x33.spotify.playlist4.proto.ListAttributesPartialState\"\xc0\x03\n\x02Op\x12.\n\x04kind\x18\x01 \x02(\x0e\x32 .spotify.playlist4.proto.Op.Kind\x12)\n\x03\x61\x64\x64\x18\x02 \x01(\x0b\x32\x1c.spotify.playlist4.proto.Add\x12)\n\x03rem\x18\x03 \x01(\x0b\x32\x1c.spotify.playlist4.proto.Rem\x12)\n\x03mov\x18\x04 \x01(\x0b\x32\x1c.spotify.playlist4.proto.Mov\x12M\n\x16update_item_attributes\x18\x05 \x01(\x0b\x32-.spotify.playlist4.proto.UpdateItemAttributes\x12M\n\x16update_list_attributes\x18\x06 \x01(\x0b\x32-.spotify.playlist4.proto.UpdateListAttributes\"k\n\x04Kind\x12\x10\n\x0cKIND_UNKNOWN\x10\x00\x12\x07\n\x03\x41\x44\x44\x10\x02\x12\x07\n\x03REM\x10\x03\x12\x07\n\x03MOV\x10\x04\x12\x1a\n\x16UPDATE_ITEM_ATTRIBUTES\x10\x05\x12\x1a\n\x16UPDATE_LIST_ATTRIBUTES\x10\x06\"2\n\x06OpList\x12(\n\x03ops\x18\x01 \x03(\x0b\x32\x1b.spotify.playlist4.proto.Op\"\xd5\x01\n\nChangeInfo\x12\x0c\n\x04user\x18\x01 \x01(\t\x12\x11\n\ttimestamp\x18\x02 \x01(\x03\x12\r\n\x05\x61\x64min\x18\x03 \x01(\x08\x12\x0c\n\x04undo\x18\x04 \x01(\x08\x12\x0c\n\x04redo\x18\x05 \x01(\x08\x12\r\n\x05merge\x18\x06 \x01(\x08\x12\x12\n\ncompressed\x18\x07 \x01(\x08\x12\x11\n\tmigration\x18\x08 \x01(\x08\x12\x10\n\x08split_id\x18\t \x01(\x05\x12\x33\n\x06source\x18\n \x01(\x0b\x32#.spotify.playlist4.proto.SourceInfo\"\xe8\x01\n\nSourceInfo\x12:\n\x06\x63lient\x18\x01 \x01(\x0e\x32*.spotify.playlist4.proto.SourceInfo.Client\x12\x0b\n\x03\x61pp\x18\x03 \x01(\t\x12\x0e\n\x06source\x18\x04 \x01(\t\x12\x0f\n\x07version\x18\x05 \x01(\t\"p\n\x06\x43lient\x12\x12\n\x0e\x43LIENT_UNKNOWN\x10\x00\x12\x11\n\rNATIVE_HERMES\x10\x01\x12\n\n\x06\x43LIENT\x10\x02\x12\n\n\x06PYTHON\x10\x03\x12\x08\n\x04JAVA\x10\x04\x12\r\n\tWEBPLAYER\x10\x05\x12\x0e\n\nLIBSPOTIFY\x10\x06\"z\n\x05\x44\x65lta\x12\x14\n\x0c\x62\x61se_version\x18\x01 \x01(\x0c\x12(\n\x03ops\x18\x02 \x03(\x0b\x32\x1b.spotify.playlist4.proto.Op\x12\x31\n\x04info\x18\x04 \x01(\x0b\x32#.spotify.playlist4.proto.ChangeInfo\"\\\n\x04\x44iff\x12\x15\n\rfrom_revision\x18\x01 \x02(\x0c\x12(\n\x03ops\x18\x02 \x03(\x0b\x32\x1b.spotify.playlist4.proto.Op\x12\x13\n\x0bto_revision\x18\x03 \x02(\x0c\"\xa0\x01\n\x0bListChanges\x12\x15\n\rbase_revision\x18\x01 \x01(\x0c\x12.\n\x06\x64\x65ltas\x18\x02 \x03(\x0b\x32\x1e.spotify.playlist4.proto.Delta\x12 \n\x18want_resulting_revisions\x18\x03 \x01(\x08\x12\x18\n\x10want_sync_result\x18\x04 \x01(\x08\x12\x0e\n\x06nonces\x18\x06 \x03(\x03\"\x8f\x03\n\x13SelectedListContent\x12\x10\n\x08revision\x18\x01 \x01(\x0c\x12\x0e\n\x06length\x18\x02 \x01(\x05\x12;\n\nattributes\x18\x03 \x01(\x0b\x32\'.spotify.playlist4.proto.ListAttributes\x12\x34\n\x08\x63ontents\x18\x05 \x01(\x0b\x32\".spotify.playlist4.proto.ListItems\x12+\n\x04\x64iff\x18\x06 \x01(\x0b\x32\x1d.spotify.playlist4.proto.Diff\x12\x32\n\x0bsync_result\x18\x07 \x01(\x0b\x32\x1d.spotify.playlist4.proto.Diff\x12\x1b\n\x13resulting_revisions\x18\x08 \x03(\x0c\x12\x16\n\x0emultiple_heads\x18\t \x01(\x08\x12\x12\n\nup_to_date\x18\n \x01(\x08\x12\x0e\n\x06nonces\x18\x0e \x03(\x03\x12\x11\n\ttimestamp\x18\x0f \x01(\x03\x12\x16\n\x0eowner_username\x18\x10 \x01(\t\"0\n\x0f\x43reateListReply\x12\x0b\n\x03uri\x18\x01 \x02(\x0c\x12\x10\n\x08revision\x18\x02 \x01(\x0c\",\n\x0bModifyReply\x12\x0b\n\x03uri\x18\x01 \x02(\x0c\x12\x10\n\x08revision\x18\x02 \x01(\x0c\" \n\x10SubscribeRequest\x12\x0c\n\x04uris\x18\x01 \x03(\x0c\"\"\n\x12UnsubscribeRequest\x12\x0c\n\x04uris\x18\x01 \x03(\x0c\"\x80\x01\n\x18PlaylistModificationInfo\x12\x0b\n\x03uri\x18\x01 \x01(\x0c\x12\x14\n\x0cnew_revision\x18\x02 \x01(\x0c\x12\x17\n\x0fparent_revision\x18\x03 \x01(\x0c\x12(\n\x03ops\x18\x04 \x03(\x0b\x32\x1b.spotify.playlist4.proto.Op*\xe6\x01\n\x11ListAttributeKind\x12\x10\n\x0cLIST_UNKNOWN\x10\x00\x12\r\n\tLIST_NAME\x10\x01\x12\x14\n\x10LIST_DESCRIPTION\x10\x02\x12\x10\n\x0cLIST_PICTURE\x10\x03\x12\x16\n\x12LIST_COLLABORATIVE\x10\x04\x12\x14\n\x10LIST_PL3_VERSION\x10\x05\x12\x19\n\x15LIST_DELETED_BY_OWNER\x10\x06\x12\x12\n\x0eLIST_CLIENT_ID\x10\n\x12\x0f\n\x0bLIST_FORMAT\x10\x0b\x12\x1a\n\x16LIST_FORMAT_ATTRIBUTES\x10\x0c*\x98\x01\n\x11ItemAttributeKind\x12\x10\n\x0cITEM_UNKNOWN\x10\x00\x12\x11\n\rITEM_ADDED_BY\x10\x01\x12\x12\n\x0eITEM_TIMESTAMP\x10\x02\x12\x10\n\x0cITEM_SEEN_AT\x10\t\x12\x0f\n\x0bITEM_PUBLIC\x10\n\x12\x1a\n\x16ITEM_FORMAT_ATTRIBUTES\x10\x0b\x12\x0b\n\x07ITEM_ID\x10\x0c\x42,\n\x15\x63om.spotify.playlist4B\x11Playlist4ApiProtoH\x02' +) + +_LISTATTRIBUTEKIND = _descriptor.EnumDescriptor( + name='ListAttributeKind', + full_name='spotify.playlist4.proto.ListAttributeKind', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='LIST_UNKNOWN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LIST_NAME', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LIST_DESCRIPTION', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LIST_PICTURE', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LIST_COLLABORATIVE', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LIST_PL3_VERSION', + index=5, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LIST_DELETED_BY_OWNER', + index=6, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LIST_CLIENT_ID', + index=7, + number=10, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LIST_FORMAT', + index=8, + number=11, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LIST_FORMAT_ATTRIBUTES', + index=9, + number=12, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=3902, + serialized_end=4132, +) +_sym_db.RegisterEnumDescriptor(_LISTATTRIBUTEKIND) + +ListAttributeKind = enum_type_wrapper.EnumTypeWrapper(_LISTATTRIBUTEKIND) +_ITEMATTRIBUTEKIND = _descriptor.EnumDescriptor( + name='ItemAttributeKind', + full_name='spotify.playlist4.proto.ItemAttributeKind', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='ITEM_UNKNOWN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='ITEM_ADDED_BY', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='ITEM_TIMESTAMP', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='ITEM_SEEN_AT', + index=3, + number=9, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='ITEM_PUBLIC', + index=4, + number=10, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='ITEM_FORMAT_ATTRIBUTES', + index=5, + number=11, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='ITEM_ID', + index=6, + number=12, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=4135, + serialized_end=4287, +) +_sym_db.RegisterEnumDescriptor(_ITEMATTRIBUTEKIND) + +ItemAttributeKind = enum_type_wrapper.EnumTypeWrapper(_ITEMATTRIBUTEKIND) +LIST_UNKNOWN = 0 +LIST_NAME = 1 +LIST_DESCRIPTION = 2 +LIST_PICTURE = 3 +LIST_COLLABORATIVE = 4 +LIST_PL3_VERSION = 5 +LIST_DELETED_BY_OWNER = 6 +LIST_CLIENT_ID = 10 +LIST_FORMAT = 11 +LIST_FORMAT_ATTRIBUTES = 12 +ITEM_UNKNOWN = 0 +ITEM_ADDED_BY = 1 +ITEM_TIMESTAMP = 2 +ITEM_SEEN_AT = 9 +ITEM_PUBLIC = 10 +ITEM_FORMAT_ATTRIBUTES = 11 +ITEM_ID = 12 + +_OP_KIND = _descriptor.EnumDescriptor( + name='Kind', + full_name='spotify.playlist4.proto.Op.Kind', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='KIND_UNKNOWN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='ADD', + index=1, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='REM', + index=2, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='MOV', + index=3, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='UPDATE_ITEM_ATTRIBUTES', + index=4, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='UPDATE_LIST_ATTRIBUTES', + index=5, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2209, + serialized_end=2316, +) +_sym_db.RegisterEnumDescriptor(_OP_KIND) + +_SOURCEINFO_CLIENT = _descriptor.EnumDescriptor( + name='Client', + full_name='spotify.playlist4.proto.SourceInfo.Client', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='CLIENT_UNKNOWN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='NATIVE_HERMES', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='CLIENT', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='PYTHON', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='JAVA', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='WEBPLAYER', + index=5, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='LIBSPOTIFY', + index=6, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=2707, + serialized_end=2819, +) +_sym_db.RegisterEnumDescriptor(_SOURCEINFO_CLIENT) + +_ITEM = _descriptor.Descriptor( + name='Item', + full_name='spotify.playlist4.proto.Item', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='spotify.playlist4.proto.Item.uri', + index=0, + number=1, + type=9, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='attributes', + full_name='spotify.playlist4.proto.Item.attributes', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=53, + serialized_end=133, +) + +_METAITEM = _descriptor.Descriptor( + name='MetaItem', + full_name='spotify.playlist4.proto.MetaItem', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='revision', + full_name='spotify.playlist4.proto.MetaItem.revision', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='attributes', + full_name='spotify.playlist4.proto.MetaItem.attributes', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='length', + full_name='spotify.playlist4.proto.MetaItem.length', + index=2, + number=3, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='timestamp', + full_name='spotify.playlist4.proto.MetaItem.timestamp', + index=3, + number=4, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='owner_username', + full_name='spotify.playlist4.proto.MetaItem.owner_username', + index=4, + number=5, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=136, + serialized_end=284, +) + +_LISTITEMS = _descriptor.Descriptor( + name='ListItems', + full_name='spotify.playlist4.proto.ListItems', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='pos', + full_name='spotify.playlist4.proto.ListItems.pos', + index=0, + number=1, + type=5, + cpp_type=1, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='truncated', + full_name='spotify.playlist4.proto.ListItems.truncated', + index=1, + number=2, + type=8, + cpp_type=7, + label=2, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='items', + full_name='spotify.playlist4.proto.ListItems.items', + index=2, + number=3, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='meta_items', + full_name='spotify.playlist4.proto.ListItems.meta_items', + index=3, + number=4, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=287, + serialized_end=431, +) + +_FORMATLISTATTRIBUTE = _descriptor.Descriptor( + name='FormatListAttribute', + full_name='spotify.playlist4.proto.FormatListAttribute', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='key', + full_name='spotify.playlist4.proto.FormatListAttribute.key', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='value', + full_name='spotify.playlist4.proto.FormatListAttribute.value', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=433, + serialized_end=482, +) + +_LISTATTRIBUTES = _descriptor.Descriptor( + name='ListAttributes', + full_name='spotify.playlist4.proto.ListAttributes', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='name', + full_name='spotify.playlist4.proto.ListAttributes.name', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='description', + full_name='spotify.playlist4.proto.ListAttributes.description', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='picture', + full_name='spotify.playlist4.proto.ListAttributes.picture', + index=2, + number=3, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='collaborative', + full_name='spotify.playlist4.proto.ListAttributes.collaborative', + index=3, + number=4, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='pl3_version', + full_name='spotify.playlist4.proto.ListAttributes.pl3_version', + index=4, + number=5, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='deleted_by_owner', + full_name='spotify.playlist4.proto.ListAttributes.deleted_by_owner', + index=5, + number=6, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='client_id', + full_name='spotify.playlist4.proto.ListAttributes.client_id', + index=6, + number=10, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='format', + full_name='spotify.playlist4.proto.ListAttributes.format', + index=7, + number=11, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='format_attributes', + full_name= + 'spotify.playlist4.proto.ListAttributes.format_attributes', + index=8, + number=12, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=485, + serialized_end=731, +) + +_ITEMATTRIBUTES = _descriptor.Descriptor( + name='ItemAttributes', + full_name='spotify.playlist4.proto.ItemAttributes', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='added_by', + full_name='spotify.playlist4.proto.ItemAttributes.added_by', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='timestamp', + full_name='spotify.playlist4.proto.ItemAttributes.timestamp', + index=1, + number=2, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='seen_at', + full_name='spotify.playlist4.proto.ItemAttributes.seen_at', + index=2, + number=9, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='public', + full_name='spotify.playlist4.proto.ItemAttributes.public', + index=3, + number=10, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='format_attributes', + full_name= + 'spotify.playlist4.proto.ItemAttributes.format_attributes', + index=4, + number=11, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='item_id', + full_name='spotify.playlist4.proto.ItemAttributes.item_id', + index=5, + number=12, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=734, + serialized_end=910, +) + +_ADD = _descriptor.Descriptor( + name='Add', + full_name='spotify.playlist4.proto.Add', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='from_index', + full_name='spotify.playlist4.proto.Add.from_index', + index=0, + number=1, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='items', + full_name='spotify.playlist4.proto.Add.items', + index=1, + number=2, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='add_last', + full_name='spotify.playlist4.proto.Add.add_last', + index=2, + number=4, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='add_first', + full_name='spotify.playlist4.proto.Add.add_first', + index=3, + number=5, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=912, + serialized_end=1020, +) + +_REM = _descriptor.Descriptor( + name='Rem', + full_name='spotify.playlist4.proto.Rem', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='from_index', + full_name='spotify.playlist4.proto.Rem.from_index', + index=0, + number=1, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='length', + full_name='spotify.playlist4.proto.Rem.length', + index=1, + number=2, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='items', + full_name='spotify.playlist4.proto.Rem.items', + index=2, + number=3, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='items_as_key', + full_name='spotify.playlist4.proto.Rem.items_as_key', + index=3, + number=7, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1022, + serialized_end=1131, +) + +_MOV = _descriptor.Descriptor( + name='Mov', + full_name='spotify.playlist4.proto.Mov', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='from_index', + full_name='spotify.playlist4.proto.Mov.from_index', + index=0, + number=1, + type=5, + cpp_type=1, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='length', + full_name='spotify.playlist4.proto.Mov.length', + index=1, + number=2, + type=5, + cpp_type=1, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='to_index', + full_name='spotify.playlist4.proto.Mov.to_index', + index=2, + number=3, + type=5, + cpp_type=1, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1133, + serialized_end=1192, +) + +_ITEMATTRIBUTESPARTIALSTATE = _descriptor.Descriptor( + name='ItemAttributesPartialState', + full_name='spotify.playlist4.proto.ItemAttributesPartialState', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='values', + full_name= + 'spotify.playlist4.proto.ItemAttributesPartialState.values', + index=0, + number=1, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='no_value', + full_name= + 'spotify.playlist4.proto.ItemAttributesPartialState.no_value', + index=1, + number=2, + type=14, + cpp_type=8, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1195, + serialized_end=1342, +) + +_LISTATTRIBUTESPARTIALSTATE = _descriptor.Descriptor( + name='ListAttributesPartialState', + full_name='spotify.playlist4.proto.ListAttributesPartialState', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='values', + full_name= + 'spotify.playlist4.proto.ListAttributesPartialState.values', + index=0, + number=1, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='no_value', + full_name= + 'spotify.playlist4.proto.ListAttributesPartialState.no_value', + index=1, + number=2, + type=14, + cpp_type=8, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1345, + serialized_end=1492, +) + +_UPDATEITEMATTRIBUTES = _descriptor.Descriptor( + name='UpdateItemAttributes', + full_name='spotify.playlist4.proto.UpdateItemAttributes', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='index', + full_name='spotify.playlist4.proto.UpdateItemAttributes.index', + index=0, + number=1, + type=5, + cpp_type=1, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='new_attributes', + full_name= + 'spotify.playlist4.proto.UpdateItemAttributes.new_attributes', + index=1, + number=2, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='old_attributes', + full_name= + 'spotify.playlist4.proto.UpdateItemAttributes.old_attributes', + index=2, + number=3, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1495, + serialized_end=1686, +) + +_UPDATELISTATTRIBUTES = _descriptor.Descriptor( + name='UpdateListAttributes', + full_name='spotify.playlist4.proto.UpdateListAttributes', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='new_attributes', + full_name= + 'spotify.playlist4.proto.UpdateListAttributes.new_attributes', + index=0, + number=1, + type=11, + cpp_type=10, + label=2, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='old_attributes', + full_name= + 'spotify.playlist4.proto.UpdateListAttributes.old_attributes', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1689, + serialized_end=1865, +) + +_OP = _descriptor.Descriptor( + name='Op', + full_name='spotify.playlist4.proto.Op', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='kind', + full_name='spotify.playlist4.proto.Op.kind', + index=0, + number=1, + type=14, + cpp_type=8, + label=2, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='add', + full_name='spotify.playlist4.proto.Op.add', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='rem', + full_name='spotify.playlist4.proto.Op.rem', + index=2, + number=3, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='mov', + full_name='spotify.playlist4.proto.Op.mov', + index=3, + number=4, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='update_item_attributes', + full_name='spotify.playlist4.proto.Op.update_item_attributes', + index=4, + number=5, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='update_list_attributes', + full_name='spotify.playlist4.proto.Op.update_list_attributes', + index=5, + number=6, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _OP_KIND, + ], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=1868, + serialized_end=2316, +) + +_OPLIST = _descriptor.Descriptor( + name='OpList', + full_name='spotify.playlist4.proto.OpList', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='ops', + full_name='spotify.playlist4.proto.OpList.ops', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2318, + serialized_end=2368, +) + +_CHANGEINFO = _descriptor.Descriptor( + name='ChangeInfo', + full_name='spotify.playlist4.proto.ChangeInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='user', + full_name='spotify.playlist4.proto.ChangeInfo.user', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='timestamp', + full_name='spotify.playlist4.proto.ChangeInfo.timestamp', + index=1, + number=2, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='admin', + full_name='spotify.playlist4.proto.ChangeInfo.admin', + index=2, + number=3, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='undo', + full_name='spotify.playlist4.proto.ChangeInfo.undo', + index=3, + number=4, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='redo', + full_name='spotify.playlist4.proto.ChangeInfo.redo', + index=4, + number=5, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='merge', + full_name='spotify.playlist4.proto.ChangeInfo.merge', + index=5, + number=6, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='compressed', + full_name='spotify.playlist4.proto.ChangeInfo.compressed', + index=6, + number=7, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='migration', + full_name='spotify.playlist4.proto.ChangeInfo.migration', + index=7, + number=8, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='split_id', + full_name='spotify.playlist4.proto.ChangeInfo.split_id', + index=8, + number=9, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='source', + full_name='spotify.playlist4.proto.ChangeInfo.source', + index=9, + number=10, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2371, + serialized_end=2584, +) + +_SOURCEINFO = _descriptor.Descriptor( + name='SourceInfo', + full_name='spotify.playlist4.proto.SourceInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='client', + full_name='spotify.playlist4.proto.SourceInfo.client', + index=0, + number=1, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='app', + full_name='spotify.playlist4.proto.SourceInfo.app', + index=1, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='source', + full_name='spotify.playlist4.proto.SourceInfo.source', + index=2, + number=4, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='version', + full_name='spotify.playlist4.proto.SourceInfo.version', + index=3, + number=5, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _SOURCEINFO_CLIENT, + ], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2587, + serialized_end=2819, +) + +_DELTA = _descriptor.Descriptor( + name='Delta', + full_name='spotify.playlist4.proto.Delta', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='base_version', + full_name='spotify.playlist4.proto.Delta.base_version', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='ops', + full_name='spotify.playlist4.proto.Delta.ops', + index=1, + number=2, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='info', + full_name='spotify.playlist4.proto.Delta.info', + index=2, + number=4, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2821, + serialized_end=2943, +) + +_DIFF = _descriptor.Descriptor( + name='Diff', + full_name='spotify.playlist4.proto.Diff', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='from_revision', + full_name='spotify.playlist4.proto.Diff.from_revision', + index=0, + number=1, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='ops', + full_name='spotify.playlist4.proto.Diff.ops', + index=1, + number=2, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='to_revision', + full_name='spotify.playlist4.proto.Diff.to_revision', + index=2, + number=3, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=2945, + serialized_end=3037, +) + +_LISTCHANGES = _descriptor.Descriptor( + name='ListChanges', + full_name='spotify.playlist4.proto.ListChanges', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='base_revision', + full_name='spotify.playlist4.proto.ListChanges.base_revision', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='deltas', + full_name='spotify.playlist4.proto.ListChanges.deltas', + index=1, + number=2, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='want_resulting_revisions', + full_name= + 'spotify.playlist4.proto.ListChanges.want_resulting_revisions', + index=2, + number=3, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='want_sync_result', + full_name='spotify.playlist4.proto.ListChanges.want_sync_result', + index=3, + number=4, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='nonces', + full_name='spotify.playlist4.proto.ListChanges.nonces', + index=4, + number=6, + type=3, + cpp_type=2, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=3040, + serialized_end=3200, +) + +_SELECTEDLISTCONTENT = _descriptor.Descriptor( + name='SelectedListContent', + full_name='spotify.playlist4.proto.SelectedListContent', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='revision', + full_name='spotify.playlist4.proto.SelectedListContent.revision', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='length', + full_name='spotify.playlist4.proto.SelectedListContent.length', + index=1, + number=2, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='attributes', + full_name='spotify.playlist4.proto.SelectedListContent.attributes', + index=2, + number=3, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='contents', + full_name='spotify.playlist4.proto.SelectedListContent.contents', + index=3, + number=5, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='diff', + full_name='spotify.playlist4.proto.SelectedListContent.diff', + index=4, + number=6, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='sync_result', + full_name='spotify.playlist4.proto.SelectedListContent.sync_result', + index=5, + number=7, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='resulting_revisions', + full_name= + 'spotify.playlist4.proto.SelectedListContent.resulting_revisions', + index=6, + number=8, + type=12, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='multiple_heads', + full_name= + 'spotify.playlist4.proto.SelectedListContent.multiple_heads', + index=7, + number=9, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='up_to_date', + full_name='spotify.playlist4.proto.SelectedListContent.up_to_date', + index=8, + number=10, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='nonces', + full_name='spotify.playlist4.proto.SelectedListContent.nonces', + index=9, + number=14, + type=3, + cpp_type=2, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='timestamp', + full_name='spotify.playlist4.proto.SelectedListContent.timestamp', + index=10, + number=15, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='owner_username', + full_name= + 'spotify.playlist4.proto.SelectedListContent.owner_username', + index=11, + number=16, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=3203, + serialized_end=3602, +) + +_CREATELISTREPLY = _descriptor.Descriptor( + name='CreateListReply', + full_name='spotify.playlist4.proto.CreateListReply', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='spotify.playlist4.proto.CreateListReply.uri', + index=0, + number=1, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='revision', + full_name='spotify.playlist4.proto.CreateListReply.revision', + index=1, + number=2, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=3604, + serialized_end=3652, +) + +_MODIFYREPLY = _descriptor.Descriptor( + name='ModifyReply', + full_name='spotify.playlist4.proto.ModifyReply', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='spotify.playlist4.proto.ModifyReply.uri', + index=0, + number=1, + type=12, + cpp_type=9, + label=2, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='revision', + full_name='spotify.playlist4.proto.ModifyReply.revision', + index=1, + number=2, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=3654, + serialized_end=3698, +) + +_SUBSCRIBEREQUEST = _descriptor.Descriptor( + name='SubscribeRequest', + full_name='spotify.playlist4.proto.SubscribeRequest', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uris', + full_name='spotify.playlist4.proto.SubscribeRequest.uris', + index=0, + number=1, + type=12, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=3700, + serialized_end=3732, +) + +_UNSUBSCRIBEREQUEST = _descriptor.Descriptor( + name='UnsubscribeRequest', + full_name='spotify.playlist4.proto.UnsubscribeRequest', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uris', + full_name='spotify.playlist4.proto.UnsubscribeRequest.uris', + index=0, + number=1, + type=12, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=3734, + serialized_end=3768, +) + +_PLAYLISTMODIFICATIONINFO = _descriptor.Descriptor( + name='PlaylistModificationInfo', + full_name='spotify.playlist4.proto.PlaylistModificationInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='uri', + full_name='spotify.playlist4.proto.PlaylistModificationInfo.uri', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='new_revision', + full_name= + 'spotify.playlist4.proto.PlaylistModificationInfo.new_revision', + index=1, + number=2, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='parent_revision', + full_name= + 'spotify.playlist4.proto.PlaylistModificationInfo.parent_revision', + index=2, + number=3, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='ops', + full_name='spotify.playlist4.proto.PlaylistModificationInfo.ops', + index=3, + number=4, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=3771, + serialized_end=3899, +) + +_ITEM.fields_by_name['attributes'].message_type = _ITEMATTRIBUTES +_METAITEM.fields_by_name['attributes'].message_type = _LISTATTRIBUTES +_LISTITEMS.fields_by_name['items'].message_type = _ITEM +_LISTITEMS.fields_by_name['meta_items'].message_type = _METAITEM +_LISTATTRIBUTES.fields_by_name[ + 'format_attributes'].message_type = _FORMATLISTATTRIBUTE +_ITEMATTRIBUTES.fields_by_name[ + 'format_attributes'].message_type = _FORMATLISTATTRIBUTE +_ADD.fields_by_name['items'].message_type = _ITEM +_REM.fields_by_name['items'].message_type = _ITEM +_ITEMATTRIBUTESPARTIALSTATE.fields_by_name[ + 'values'].message_type = _ITEMATTRIBUTES +_ITEMATTRIBUTESPARTIALSTATE.fields_by_name[ + 'no_value'].enum_type = _ITEMATTRIBUTEKIND +_LISTATTRIBUTESPARTIALSTATE.fields_by_name[ + 'values'].message_type = _LISTATTRIBUTES +_LISTATTRIBUTESPARTIALSTATE.fields_by_name[ + 'no_value'].enum_type = _LISTATTRIBUTEKIND +_UPDATEITEMATTRIBUTES.fields_by_name[ + 'new_attributes'].message_type = _ITEMATTRIBUTESPARTIALSTATE +_UPDATEITEMATTRIBUTES.fields_by_name[ + 'old_attributes'].message_type = _ITEMATTRIBUTESPARTIALSTATE +_UPDATELISTATTRIBUTES.fields_by_name[ + 'new_attributes'].message_type = _LISTATTRIBUTESPARTIALSTATE +_UPDATELISTATTRIBUTES.fields_by_name[ + 'old_attributes'].message_type = _LISTATTRIBUTESPARTIALSTATE +_OP.fields_by_name['kind'].enum_type = _OP_KIND +_OP.fields_by_name['add'].message_type = _ADD +_OP.fields_by_name['rem'].message_type = _REM +_OP.fields_by_name['mov'].message_type = _MOV +_OP.fields_by_name[ + 'update_item_attributes'].message_type = _UPDATEITEMATTRIBUTES +_OP.fields_by_name[ + 'update_list_attributes'].message_type = _UPDATELISTATTRIBUTES +_OP_KIND.containing_type = _OP +_OPLIST.fields_by_name['ops'].message_type = _OP +_CHANGEINFO.fields_by_name['source'].message_type = _SOURCEINFO +_SOURCEINFO.fields_by_name['client'].enum_type = _SOURCEINFO_CLIENT +_SOURCEINFO_CLIENT.containing_type = _SOURCEINFO +_DELTA.fields_by_name['ops'].message_type = _OP +_DELTA.fields_by_name['info'].message_type = _CHANGEINFO +_DIFF.fields_by_name['ops'].message_type = _OP +_LISTCHANGES.fields_by_name['deltas'].message_type = _DELTA +_SELECTEDLISTCONTENT.fields_by_name[ + 'attributes'].message_type = _LISTATTRIBUTES +_SELECTEDLISTCONTENT.fields_by_name['contents'].message_type = _LISTITEMS +_SELECTEDLISTCONTENT.fields_by_name['diff'].message_type = _DIFF +_SELECTEDLISTCONTENT.fields_by_name['sync_result'].message_type = _DIFF +_PLAYLISTMODIFICATIONINFO.fields_by_name['ops'].message_type = _OP +DESCRIPTOR.message_types_by_name['Item'] = _ITEM +DESCRIPTOR.message_types_by_name['MetaItem'] = _METAITEM +DESCRIPTOR.message_types_by_name['ListItems'] = _LISTITEMS +DESCRIPTOR.message_types_by_name['FormatListAttribute'] = _FORMATLISTATTRIBUTE +DESCRIPTOR.message_types_by_name['ListAttributes'] = _LISTATTRIBUTES +DESCRIPTOR.message_types_by_name['ItemAttributes'] = _ITEMATTRIBUTES +DESCRIPTOR.message_types_by_name['Add'] = _ADD +DESCRIPTOR.message_types_by_name['Rem'] = _REM +DESCRIPTOR.message_types_by_name['Mov'] = _MOV +DESCRIPTOR.message_types_by_name[ + 'ItemAttributesPartialState'] = _ITEMATTRIBUTESPARTIALSTATE +DESCRIPTOR.message_types_by_name[ + 'ListAttributesPartialState'] = _LISTATTRIBUTESPARTIALSTATE +DESCRIPTOR.message_types_by_name[ + 'UpdateItemAttributes'] = _UPDATEITEMATTRIBUTES +DESCRIPTOR.message_types_by_name[ + 'UpdateListAttributes'] = _UPDATELISTATTRIBUTES +DESCRIPTOR.message_types_by_name['Op'] = _OP +DESCRIPTOR.message_types_by_name['OpList'] = _OPLIST +DESCRIPTOR.message_types_by_name['ChangeInfo'] = _CHANGEINFO +DESCRIPTOR.message_types_by_name['SourceInfo'] = _SOURCEINFO +DESCRIPTOR.message_types_by_name['Delta'] = _DELTA +DESCRIPTOR.message_types_by_name['Diff'] = _DIFF +DESCRIPTOR.message_types_by_name['ListChanges'] = _LISTCHANGES +DESCRIPTOR.message_types_by_name['SelectedListContent'] = _SELECTEDLISTCONTENT +DESCRIPTOR.message_types_by_name['CreateListReply'] = _CREATELISTREPLY +DESCRIPTOR.message_types_by_name['ModifyReply'] = _MODIFYREPLY +DESCRIPTOR.message_types_by_name['SubscribeRequest'] = _SUBSCRIBEREQUEST +DESCRIPTOR.message_types_by_name['UnsubscribeRequest'] = _UNSUBSCRIBEREQUEST +DESCRIPTOR.message_types_by_name[ + 'PlaylistModificationInfo'] = _PLAYLISTMODIFICATIONINFO +DESCRIPTOR.enum_types_by_name['ListAttributeKind'] = _LISTATTRIBUTEKIND +DESCRIPTOR.enum_types_by_name['ItemAttributeKind'] = _ITEMATTRIBUTEKIND +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +Item = _reflection.GeneratedProtocolMessageType( + 'Item', + (_message.Message, ), + { + 'DESCRIPTOR': _ITEM, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.Item) + }) +_sym_db.RegisterMessage(Item) + +MetaItem = _reflection.GeneratedProtocolMessageType( + 'MetaItem', + (_message.Message, ), + { + 'DESCRIPTOR': _METAITEM, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.MetaItem) + }) +_sym_db.RegisterMessage(MetaItem) + +ListItems = _reflection.GeneratedProtocolMessageType( + 'ListItems', + (_message.Message, ), + { + 'DESCRIPTOR': _LISTITEMS, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.ListItems) + }) +_sym_db.RegisterMessage(ListItems) + +FormatListAttribute = _reflection.GeneratedProtocolMessageType( + 'FormatListAttribute', + (_message.Message, ), + { + 'DESCRIPTOR': _FORMATLISTATTRIBUTE, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.FormatListAttribute) + }) +_sym_db.RegisterMessage(FormatListAttribute) + +ListAttributes = _reflection.GeneratedProtocolMessageType( + 'ListAttributes', + (_message.Message, ), + { + 'DESCRIPTOR': _LISTATTRIBUTES, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.ListAttributes) + }) +_sym_db.RegisterMessage(ListAttributes) + +ItemAttributes = _reflection.GeneratedProtocolMessageType( + 'ItemAttributes', + (_message.Message, ), + { + 'DESCRIPTOR': _ITEMATTRIBUTES, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.ItemAttributes) + }) +_sym_db.RegisterMessage(ItemAttributes) + +Add = _reflection.GeneratedProtocolMessageType( + 'Add', + (_message.Message, ), + { + 'DESCRIPTOR': _ADD, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.Add) + }) +_sym_db.RegisterMessage(Add) + +Rem = _reflection.GeneratedProtocolMessageType( + 'Rem', + (_message.Message, ), + { + 'DESCRIPTOR': _REM, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.Rem) + }) +_sym_db.RegisterMessage(Rem) + +Mov = _reflection.GeneratedProtocolMessageType( + 'Mov', + (_message.Message, ), + { + 'DESCRIPTOR': _MOV, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.Mov) + }) +_sym_db.RegisterMessage(Mov) + +ItemAttributesPartialState = _reflection.GeneratedProtocolMessageType( + 'ItemAttributesPartialState', + (_message.Message, ), + { + 'DESCRIPTOR': _ITEMATTRIBUTESPARTIALSTATE, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.ItemAttributesPartialState) + }) +_sym_db.RegisterMessage(ItemAttributesPartialState) + +ListAttributesPartialState = _reflection.GeneratedProtocolMessageType( + 'ListAttributesPartialState', + (_message.Message, ), + { + 'DESCRIPTOR': _LISTATTRIBUTESPARTIALSTATE, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.ListAttributesPartialState) + }) +_sym_db.RegisterMessage(ListAttributesPartialState) + +UpdateItemAttributes = _reflection.GeneratedProtocolMessageType( + 'UpdateItemAttributes', + (_message.Message, ), + { + 'DESCRIPTOR': _UPDATEITEMATTRIBUTES, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.UpdateItemAttributes) + }) +_sym_db.RegisterMessage(UpdateItemAttributes) + +UpdateListAttributes = _reflection.GeneratedProtocolMessageType( + 'UpdateListAttributes', + (_message.Message, ), + { + 'DESCRIPTOR': _UPDATELISTATTRIBUTES, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.UpdateListAttributes) + }) +_sym_db.RegisterMessage(UpdateListAttributes) + +Op = _reflection.GeneratedProtocolMessageType( + 'Op', + (_message.Message, ), + { + 'DESCRIPTOR': _OP, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.Op) + }) +_sym_db.RegisterMessage(Op) + +OpList = _reflection.GeneratedProtocolMessageType( + 'OpList', + (_message.Message, ), + { + 'DESCRIPTOR': _OPLIST, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.OpList) + }) +_sym_db.RegisterMessage(OpList) + +ChangeInfo = _reflection.GeneratedProtocolMessageType( + 'ChangeInfo', + (_message.Message, ), + { + 'DESCRIPTOR': _CHANGEINFO, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.ChangeInfo) + }) +_sym_db.RegisterMessage(ChangeInfo) + +SourceInfo = _reflection.GeneratedProtocolMessageType( + 'SourceInfo', + (_message.Message, ), + { + 'DESCRIPTOR': _SOURCEINFO, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.SourceInfo) + }) +_sym_db.RegisterMessage(SourceInfo) + +Delta = _reflection.GeneratedProtocolMessageType( + 'Delta', + (_message.Message, ), + { + 'DESCRIPTOR': _DELTA, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.Delta) + }) +_sym_db.RegisterMessage(Delta) + +Diff = _reflection.GeneratedProtocolMessageType( + 'Diff', + (_message.Message, ), + { + 'DESCRIPTOR': _DIFF, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.Diff) + }) +_sym_db.RegisterMessage(Diff) + +ListChanges = _reflection.GeneratedProtocolMessageType( + 'ListChanges', + (_message.Message, ), + { + 'DESCRIPTOR': _LISTCHANGES, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.ListChanges) + }) +_sym_db.RegisterMessage(ListChanges) + +SelectedListContent = _reflection.GeneratedProtocolMessageType( + 'SelectedListContent', + (_message.Message, ), + { + 'DESCRIPTOR': _SELECTEDLISTCONTENT, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.SelectedListContent) + }) +_sym_db.RegisterMessage(SelectedListContent) + +CreateListReply = _reflection.GeneratedProtocolMessageType( + 'CreateListReply', + (_message.Message, ), + { + 'DESCRIPTOR': _CREATELISTREPLY, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.CreateListReply) + }) +_sym_db.RegisterMessage(CreateListReply) + +ModifyReply = _reflection.GeneratedProtocolMessageType( + 'ModifyReply', + (_message.Message, ), + { + 'DESCRIPTOR': _MODIFYREPLY, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.ModifyReply) + }) +_sym_db.RegisterMessage(ModifyReply) + +SubscribeRequest = _reflection.GeneratedProtocolMessageType( + 'SubscribeRequest', + (_message.Message, ), + { + 'DESCRIPTOR': _SUBSCRIBEREQUEST, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.SubscribeRequest) + }) +_sym_db.RegisterMessage(SubscribeRequest) + +UnsubscribeRequest = _reflection.GeneratedProtocolMessageType( + 'UnsubscribeRequest', + (_message.Message, ), + { + 'DESCRIPTOR': _UNSUBSCRIBEREQUEST, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.UnsubscribeRequest) + }) +_sym_db.RegisterMessage(UnsubscribeRequest) + +PlaylistModificationInfo = _reflection.GeneratedProtocolMessageType( + 'PlaylistModificationInfo', + (_message.Message, ), + { + 'DESCRIPTOR': _PLAYLISTMODIFICATIONINFO, + '__module__': 'playlist4_external_pb2' + # @@protoc_insertion_point(class_scope:spotify.playlist4.proto.PlaylistModificationInfo) + }) +_sym_db.RegisterMessage(PlaylistModificationInfo) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/playlist_annotate3_pb2.py b/src/librespot/proto/playlist_annotate3_pb2.py new file mode 100644 index 0000000..0ef985a --- /dev/null +++ b/src/librespot/proto/playlist_annotate3_pb2.py @@ -0,0 +1,440 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: playlist_annotate3.proto +"""Generated protocol buffer code.""" +from google.protobuf.internal import enum_type_wrapper +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='playlist_annotate3.proto', + package='spotify_playlist_annotate3.proto', + syntax='proto2', + serialized_options=b'\n\036com.spotify.playlist_annotate3H\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x18playlist_annotate3.proto\x12 spotify_playlist_annotate3.proto\"a\n\x0fTakedownRequest\x12N\n\x12\x61\x62use_report_state\x18\x01 \x01(\x0e\x32\x32.spotify_playlist_annotate3.proto.AbuseReportState\"9\n\x0f\x41nnotateRequest\x12\x13\n\x0b\x64\x65scription\x18\x01 \x01(\t\x12\x11\n\timage_uri\x18\x02 \x01(\t\"5\n\x11TranscodedPicture\x12\x13\n\x0btarget_name\x18\x01 \x01(\t\x12\x0b\n\x03uri\x18\x02 \x01(\t\"\xf4\x02\n\x12PlaylistAnnotation\x12\x13\n\x0b\x64\x65scription\x18\x01 \x01(\t\x12\x0f\n\x07picture\x18\x02 \x01(\t\x12i\n\x1a\x64\x65precated_render_features\x18\x03 \x01(\x0e\x32\x30.spotify_playlist_annotate3.proto.RenderFeatures:\x0fNORMAL_FEATURESB\x02\x18\x01\x12O\n\x12transcoded_picture\x18\x04 \x03(\x0b\x32\x33.spotify_playlist_annotate3.proto.TranscodedPicture\x12(\n\x1ais_abuse_reporting_enabled\x18\x06 \x01(\x08:\x04true\x12R\n\x12\x61\x62use_report_state\x18\x07 \x01(\x0e\x32\x32.spotify_playlist_annotate3.proto.AbuseReportState:\x02OK*<\n\x0eRenderFeatures\x12\x13\n\x0fNORMAL_FEATURES\x10\x01\x12\x15\n\x11\x45XTENDED_FEATURES\x10\x02**\n\x10\x41\x62useReportState\x12\x06\n\x02OK\x10\x00\x12\x0e\n\nTAKEN_DOWN\x10\x01\x42\"\n\x1e\x63om.spotify.playlist_annotate3H\x02' +) + +_RENDERFEATURES = _descriptor.EnumDescriptor( + name='RenderFeatures', + full_name='spotify_playlist_annotate3.proto.RenderFeatures', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='NORMAL_FEATURES', + index=0, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='EXTENDED_FEATURES', + index=1, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=650, + serialized_end=710, +) +_sym_db.RegisterEnumDescriptor(_RENDERFEATURES) + +RenderFeatures = enum_type_wrapper.EnumTypeWrapper(_RENDERFEATURES) +_ABUSEREPORTSTATE = _descriptor.EnumDescriptor( + name='AbuseReportState', + full_name='spotify_playlist_annotate3.proto.AbuseReportState', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='OK', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='TAKEN_DOWN', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=712, + serialized_end=754, +) +_sym_db.RegisterEnumDescriptor(_ABUSEREPORTSTATE) + +AbuseReportState = enum_type_wrapper.EnumTypeWrapper(_ABUSEREPORTSTATE) +NORMAL_FEATURES = 1 +EXTENDED_FEATURES = 2 +OK = 0 +TAKEN_DOWN = 1 + +_TAKEDOWNREQUEST = _descriptor.Descriptor( + name='TakedownRequest', + full_name='spotify_playlist_annotate3.proto.TakedownRequest', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='abuse_report_state', + full_name= + 'spotify_playlist_annotate3.proto.TakedownRequest.abuse_report_state', + index=0, + number=1, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=62, + serialized_end=159, +) + +_ANNOTATEREQUEST = _descriptor.Descriptor( + name='AnnotateRequest', + full_name='spotify_playlist_annotate3.proto.AnnotateRequest', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='description', + full_name= + 'spotify_playlist_annotate3.proto.AnnotateRequest.description', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='image_uri', + full_name= + 'spotify_playlist_annotate3.proto.AnnotateRequest.image_uri', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=161, + serialized_end=218, +) + +_TRANSCODEDPICTURE = _descriptor.Descriptor( + name='TranscodedPicture', + full_name='spotify_playlist_annotate3.proto.TranscodedPicture', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='target_name', + full_name= + 'spotify_playlist_annotate3.proto.TranscodedPicture.target_name', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='uri', + full_name='spotify_playlist_annotate3.proto.TranscodedPicture.uri', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=220, + serialized_end=273, +) + +_PLAYLISTANNOTATION = _descriptor.Descriptor( + name='PlaylistAnnotation', + full_name='spotify_playlist_annotate3.proto.PlaylistAnnotation', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='description', + full_name= + 'spotify_playlist_annotate3.proto.PlaylistAnnotation.description', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='picture', + full_name= + 'spotify_playlist_annotate3.proto.PlaylistAnnotation.picture', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='deprecated_render_features', + full_name= + 'spotify_playlist_annotate3.proto.PlaylistAnnotation.deprecated_render_features', + index=2, + number=3, + type=14, + cpp_type=8, + label=1, + has_default_value=True, + default_value=1, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=b'\030\001', + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='transcoded_picture', + full_name= + 'spotify_playlist_annotate3.proto.PlaylistAnnotation.transcoded_picture', + index=3, + number=4, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_abuse_reporting_enabled', + full_name= + 'spotify_playlist_annotate3.proto.PlaylistAnnotation.is_abuse_reporting_enabled', + index=4, + number=6, + type=8, + cpp_type=7, + label=1, + has_default_value=True, + default_value=True, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='abuse_report_state', + full_name= + 'spotify_playlist_annotate3.proto.PlaylistAnnotation.abuse_report_state', + index=5, + number=7, + type=14, + cpp_type=8, + label=1, + has_default_value=True, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=276, + serialized_end=648, +) + +_TAKEDOWNREQUEST.fields_by_name[ + 'abuse_report_state'].enum_type = _ABUSEREPORTSTATE +_PLAYLISTANNOTATION.fields_by_name[ + 'deprecated_render_features'].enum_type = _RENDERFEATURES +_PLAYLISTANNOTATION.fields_by_name[ + 'transcoded_picture'].message_type = _TRANSCODEDPICTURE +_PLAYLISTANNOTATION.fields_by_name[ + 'abuse_report_state'].enum_type = _ABUSEREPORTSTATE +DESCRIPTOR.message_types_by_name['TakedownRequest'] = _TAKEDOWNREQUEST +DESCRIPTOR.message_types_by_name['AnnotateRequest'] = _ANNOTATEREQUEST +DESCRIPTOR.message_types_by_name['TranscodedPicture'] = _TRANSCODEDPICTURE +DESCRIPTOR.message_types_by_name['PlaylistAnnotation'] = _PLAYLISTANNOTATION +DESCRIPTOR.enum_types_by_name['RenderFeatures'] = _RENDERFEATURES +DESCRIPTOR.enum_types_by_name['AbuseReportState'] = _ABUSEREPORTSTATE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +TakedownRequest = _reflection.GeneratedProtocolMessageType( + 'TakedownRequest', + (_message.Message, ), + { + 'DESCRIPTOR': _TAKEDOWNREQUEST, + '__module__': 'playlist_annotate3_pb2' + # @@protoc_insertion_point(class_scope:spotify_playlist_annotate3.proto.TakedownRequest) + }) +_sym_db.RegisterMessage(TakedownRequest) + +AnnotateRequest = _reflection.GeneratedProtocolMessageType( + 'AnnotateRequest', + (_message.Message, ), + { + 'DESCRIPTOR': _ANNOTATEREQUEST, + '__module__': 'playlist_annotate3_pb2' + # @@protoc_insertion_point(class_scope:spotify_playlist_annotate3.proto.AnnotateRequest) + }) +_sym_db.RegisterMessage(AnnotateRequest) + +TranscodedPicture = _reflection.GeneratedProtocolMessageType( + 'TranscodedPicture', + (_message.Message, ), + { + 'DESCRIPTOR': _TRANSCODEDPICTURE, + '__module__': 'playlist_annotate3_pb2' + # @@protoc_insertion_point(class_scope:spotify_playlist_annotate3.proto.TranscodedPicture) + }) +_sym_db.RegisterMessage(TranscodedPicture) + +PlaylistAnnotation = _reflection.GeneratedProtocolMessageType( + 'PlaylistAnnotation', + (_message.Message, ), + { + 'DESCRIPTOR': _PLAYLISTANNOTATION, + '__module__': 'playlist_annotate3_pb2' + # @@protoc_insertion_point(class_scope:spotify_playlist_annotate3.proto.PlaylistAnnotation) + }) +_sym_db.RegisterMessage(PlaylistAnnotation) + +DESCRIPTOR._options = None +_PLAYLISTANNOTATION.fields_by_name[ + 'deprecated_render_features']._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/queue_pb2.py b/src/librespot/proto/queue_pb2.py new file mode 100644 index 0000000..4e78d14 --- /dev/null +++ b/src/librespot/proto/queue_pb2.py @@ -0,0 +1,100 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: queue.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +import context_track_pb2 as context__track__pb2 + +DESCRIPTOR = _descriptor.FileDescriptor( + name='queue.proto', + package='spotify.player.proto.transfer', + syntax='proto2', + serialized_options=b'\n\024com.spotify.transferH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x0bqueue.proto\x12\x1dspotify.player.proto.transfer\x1a\x13\x63ontext_track.proto\"U\n\x05Queue\x12\x32\n\x06tracks\x18\x01 \x03(\x0b\x32\".spotify.player.proto.ContextTrack\x12\x18\n\x10is_playing_queue\x18\x02 \x01(\x08\x42\x18\n\x14\x63om.spotify.transferH\x02', + dependencies=[ + context__track__pb2.DESCRIPTOR, + ]) + +_QUEUE = _descriptor.Descriptor( + name='Queue', + full_name='spotify.player.proto.transfer.Queue', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='tracks', + full_name='spotify.player.proto.transfer.Queue.tracks', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='is_playing_queue', + full_name='spotify.player.proto.transfer.Queue.is_playing_queue', + index=1, + number=2, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=67, + serialized_end=152, +) + +_QUEUE.fields_by_name[ + 'tracks'].message_type = context__track__pb2._CONTEXTTRACK +DESCRIPTOR.message_types_by_name['Queue'] = _QUEUE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +Queue = _reflection.GeneratedProtocolMessageType( + 'Queue', + (_message.Message, ), + { + 'DESCRIPTOR': _QUEUE, + '__module__': 'queue_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.transfer.Queue) + }) +_sym_db.RegisterMessage(Queue) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/restrictions_pb2.py b/src/librespot/proto/restrictions_pb2.py new file mode 100644 index 0000000..68ba70c --- /dev/null +++ b/src/librespot/proto/restrictions_pb2.py @@ -0,0 +1,457 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: restrictions.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='restrictions.proto', + package='spotify.player.proto', + syntax='proto2', + serialized_options=b'\n\023com.spotify.contextH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x12restrictions.proto\x12\x14spotify.player.proto\"\xbb\x07\n\x0cRestrictions\x12 \n\x18\x64isallow_pausing_reasons\x18\x01 \x03(\t\x12!\n\x19\x64isallow_resuming_reasons\x18\x02 \x03(\t\x12 \n\x18\x64isallow_seeking_reasons\x18\x03 \x03(\t\x12%\n\x1d\x64isallow_peeking_prev_reasons\x18\x04 \x03(\t\x12%\n\x1d\x64isallow_peeking_next_reasons\x18\x05 \x03(\t\x12&\n\x1e\x64isallow_skipping_prev_reasons\x18\x06 \x03(\t\x12&\n\x1e\x64isallow_skipping_next_reasons\x18\x07 \x03(\t\x12\x30\n(disallow_toggling_repeat_context_reasons\x18\x08 \x03(\t\x12.\n&disallow_toggling_repeat_track_reasons\x18\t \x03(\t\x12)\n!disallow_toggling_shuffle_reasons\x18\n \x03(\t\x12\"\n\x1a\x64isallow_set_queue_reasons\x18\x0b \x03(\t\x12.\n&disallow_interrupting_playback_reasons\x18\x0c \x03(\t\x12.\n&disallow_transferring_playback_reasons\x18\r \x03(\t\x12\'\n\x1f\x64isallow_remote_control_reasons\x18\x0e \x03(\t\x12\x33\n+disallow_inserting_into_next_tracks_reasons\x18\x0f \x03(\t\x12\x36\n.disallow_inserting_into_context_tracks_reasons\x18\x10 \x03(\t\x12\x32\n*disallow_reordering_in_next_tracks_reasons\x18\x11 \x03(\t\x12\x35\n-disallow_reordering_in_context_tracks_reasons\x18\x12 \x03(\t\x12\x32\n*disallow_removing_from_next_tracks_reasons\x18\x13 \x03(\t\x12\x35\n-disallow_removing_from_context_tracks_reasons\x18\x14 \x03(\t\x12)\n!disallow_updating_context_reasons\x18\x15 \x03(\tB\x17\n\x13\x63om.spotify.contextH\x02' +) + +_RESTRICTIONS = _descriptor.Descriptor( + name='Restrictions', + full_name='spotify.player.proto.Restrictions', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='disallow_pausing_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_pausing_reasons', + index=0, + number=1, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_resuming_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_resuming_reasons', + index=1, + number=2, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_seeking_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_seeking_reasons', + index=2, + number=3, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_peeking_prev_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_peeking_prev_reasons', + index=3, + number=4, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_peeking_next_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_peeking_next_reasons', + index=4, + number=5, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_skipping_prev_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_skipping_prev_reasons', + index=5, + number=6, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_skipping_next_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_skipping_next_reasons', + index=6, + number=7, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_toggling_repeat_context_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_toggling_repeat_context_reasons', + index=7, + number=8, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_toggling_repeat_track_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_toggling_repeat_track_reasons', + index=8, + number=9, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_toggling_shuffle_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_toggling_shuffle_reasons', + index=9, + number=10, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_set_queue_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_set_queue_reasons', + index=10, + number=11, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_interrupting_playback_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_interrupting_playback_reasons', + index=11, + number=12, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_transferring_playback_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_transferring_playback_reasons', + index=12, + number=13, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_remote_control_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_remote_control_reasons', + index=13, + number=14, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_inserting_into_next_tracks_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_inserting_into_next_tracks_reasons', + index=14, + number=15, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_inserting_into_context_tracks_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_inserting_into_context_tracks_reasons', + index=15, + number=16, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_reordering_in_next_tracks_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_reordering_in_next_tracks_reasons', + index=16, + number=17, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_reordering_in_context_tracks_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_reordering_in_context_tracks_reasons', + index=17, + number=18, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_removing_from_next_tracks_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_removing_from_next_tracks_reasons', + index=18, + number=19, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_removing_from_context_tracks_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_removing_from_context_tracks_reasons', + index=19, + number=20, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='disallow_updating_context_reasons', + full_name= + 'spotify.player.proto.Restrictions.disallow_updating_context_reasons', + index=20, + number=21, + type=9, + cpp_type=9, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=45, + serialized_end=1000, +) + +DESCRIPTOR.message_types_by_name['Restrictions'] = _RESTRICTIONS +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +Restrictions = _reflection.GeneratedProtocolMessageType( + 'Restrictions', + (_message.Message, ), + { + 'DESCRIPTOR': _RESTRICTIONS, + '__module__': 'restrictions_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.Restrictions) + }) +_sym_db.RegisterMessage(Restrictions) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/session_pb2.py b/src/librespot/proto/session_pb2.py new file mode 100644 index 0000000..4b132bc --- /dev/null +++ b/src/librespot/proto/session_pb2.py @@ -0,0 +1,143 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: session.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +import context_pb2 as context__pb2 +import context_player_options_pb2 as context__player__options__pb2 +import play_origin_pb2 as play__origin__pb2 + +DESCRIPTOR = _descriptor.FileDescriptor( + name='session.proto', + package='spotify.player.proto.transfer', + syntax='proto2', + serialized_options=b'\n\024com.spotify.transferH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\rsession.proto\x12\x1dspotify.player.proto.transfer\x1a\rcontext.proto\x1a\x1c\x63ontext_player_options.proto\x1a\x11play_origin.proto\"\xd3\x01\n\x07Session\x12\x35\n\x0bplay_origin\x18\x01 \x01(\x0b\x32 .spotify.player.proto.PlayOrigin\x12.\n\x07\x63ontext\x18\x02 \x01(\x0b\x32\x1d.spotify.player.proto.Context\x12\x13\n\x0b\x63urrent_uid\x18\x03 \x01(\t\x12L\n\x10option_overrides\x18\x04 \x01(\x0b\x32\x32.spotify.player.proto.ContextPlayerOptionOverridesB\x18\n\x14\x63om.spotify.transferH\x02', + dependencies=[ + context__pb2.DESCRIPTOR, + context__player__options__pb2.DESCRIPTOR, + play__origin__pb2.DESCRIPTOR, + ]) + +_SESSION = _descriptor.Descriptor( + name='Session', + full_name='spotify.player.proto.transfer.Session', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='play_origin', + full_name='spotify.player.proto.transfer.Session.play_origin', + index=0, + number=1, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='context', + full_name='spotify.player.proto.transfer.Session.context', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='current_uid', + full_name='spotify.player.proto.transfer.Session.current_uid', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='option_overrides', + full_name='spotify.player.proto.transfer.Session.option_overrides', + index=3, + number=4, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=113, + serialized_end=324, +) + +_SESSION.fields_by_name[ + 'play_origin'].message_type = play__origin__pb2._PLAYORIGIN +_SESSION.fields_by_name['context'].message_type = context__pb2._CONTEXT +_SESSION.fields_by_name[ + 'option_overrides'].message_type = context__player__options__pb2._CONTEXTPLAYEROPTIONOVERRIDES +DESCRIPTOR.message_types_by_name['Session'] = _SESSION +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +Session = _reflection.GeneratedProtocolMessageType( + 'Session', + (_message.Message, ), + { + 'DESCRIPTOR': _SESSION, + '__module__': 'session_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.transfer.Session) + }) +_sym_db.RegisterMessage(Session) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/spotify/__init__.py b/src/librespot/proto/spotify/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/src/librespot/proto/spotify/login5/__init__.py b/src/librespot/proto/spotify/login5/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/src/librespot/proto/spotify/login5/v3/__init__.py b/src/librespot/proto/spotify/login5/v3/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/src/librespot/proto/spotify/login5/v3/challenges/__init__.py b/src/librespot/proto/spotify/login5/v3/challenges/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/src/librespot/proto/spotify/login5/v3/challenges/code_pb2.py b/src/librespot/proto/spotify/login5/v3/challenges/code_pb2.py new file mode 100644 index 0000000..b5db3d2 --- /dev/null +++ b/src/librespot/proto/spotify/login5/v3/challenges/code_pb2.py @@ -0,0 +1,214 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: spotify/login5/v3/challenges/code.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='spotify/login5/v3/challenges/code.proto', + package='spotify.login5.v3.challenges', + syntax='proto3', + serialized_options=b'\n\024com.spotify.login5v3', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\'spotify/login5/v3/challenges/code.proto\x12\x1cspotify.login5.v3.challenges\"\xbc\x01\n\rCodeChallenge\x12\x42\n\x06method\x18\x01 \x01(\x0e\x32\x32.spotify.login5.v3.challenges.CodeChallenge.Method\x12\x13\n\x0b\x63ode_length\x18\x02 \x01(\x05\x12\x12\n\nexpires_in\x18\x03 \x01(\x05\x12\x1e\n\x16\x63\x61nonical_phone_number\x18\x04 \x01(\t\"\x1e\n\x06Method\x12\x0b\n\x07UNKNOWN\x10\x00\x12\x07\n\x03SMS\x10\x01\"\x1c\n\x0c\x43odeSolution\x12\x0c\n\x04\x63ode\x18\x01 \x01(\tB\x16\n\x14\x63om.spotify.login5v3b\x06proto3' +) + +_CODECHALLENGE_METHOD = _descriptor.EnumDescriptor( + name='Method', + full_name='spotify.login5.v3.challenges.CodeChallenge.Method', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='UNKNOWN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='SMS', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=232, + serialized_end=262, +) +_sym_db.RegisterEnumDescriptor(_CODECHALLENGE_METHOD) + +_CODECHALLENGE = _descriptor.Descriptor( + name='CodeChallenge', + full_name='spotify.login5.v3.challenges.CodeChallenge', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='method', + full_name='spotify.login5.v3.challenges.CodeChallenge.method', + index=0, + number=1, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='code_length', + full_name='spotify.login5.v3.challenges.CodeChallenge.code_length', + index=1, + number=2, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='expires_in', + full_name='spotify.login5.v3.challenges.CodeChallenge.expires_in', + index=2, + number=3, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='canonical_phone_number', + full_name= + 'spotify.login5.v3.challenges.CodeChallenge.canonical_phone_number', + index=3, + number=4, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _CODECHALLENGE_METHOD, + ], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=74, + serialized_end=262, +) + +_CODESOLUTION = _descriptor.Descriptor( + name='CodeSolution', + full_name='spotify.login5.v3.challenges.CodeSolution', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='code', + full_name='spotify.login5.v3.challenges.CodeSolution.code', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=264, + serialized_end=292, +) + +_CODECHALLENGE.fields_by_name['method'].enum_type = _CODECHALLENGE_METHOD +_CODECHALLENGE_METHOD.containing_type = _CODECHALLENGE +DESCRIPTOR.message_types_by_name['CodeChallenge'] = _CODECHALLENGE +DESCRIPTOR.message_types_by_name['CodeSolution'] = _CODESOLUTION +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +CodeChallenge = _reflection.GeneratedProtocolMessageType( + 'CodeChallenge', + (_message.Message, ), + { + 'DESCRIPTOR': _CODECHALLENGE, + '__module__': 'spotify.login5.v3.challenges.code_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.challenges.CodeChallenge) + }) +_sym_db.RegisterMessage(CodeChallenge) + +CodeSolution = _reflection.GeneratedProtocolMessageType( + 'CodeSolution', + (_message.Message, ), + { + 'DESCRIPTOR': _CODESOLUTION, + '__module__': 'spotify.login5.v3.challenges.code_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.challenges.CodeSolution) + }) +_sym_db.RegisterMessage(CodeSolution) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/spotify/login5/v3/challenges/hashcash_pb2.py b/src/librespot/proto/spotify/login5/v3/challenges/hashcash_pb2.py new file mode 100644 index 0000000..7b211f7 --- /dev/null +++ b/src/librespot/proto/spotify/login5/v3/challenges/hashcash_pb2.py @@ -0,0 +1,168 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: spotify/login5/v3/challenges/hashcash.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +from google.protobuf import duration_pb2 as google_dot_protobuf_dot_duration__pb2 + +DESCRIPTOR = _descriptor.FileDescriptor( + name='spotify/login5/v3/challenges/hashcash.proto', + package='spotify.login5.v3.challenges', + syntax='proto3', + serialized_options=b'\n\024com.spotify.login5v3', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n+spotify/login5/v3/challenges/hashcash.proto\x12\x1cspotify.login5.v3.challenges\x1a\x1egoogle/protobuf/duration.proto\"3\n\x11HashcashChallenge\x12\x0e\n\x06prefix\x18\x01 \x01(\x0c\x12\x0e\n\x06length\x18\x02 \x01(\x05\"O\n\x10HashcashSolution\x12\x0e\n\x06suffix\x18\x01 \x01(\x0c\x12+\n\x08\x64uration\x18\x02 \x01(\x0b\x32\x19.google.protobuf.DurationB\x16\n\x14\x63om.spotify.login5v3b\x06proto3', + dependencies=[ + google_dot_protobuf_dot_duration__pb2.DESCRIPTOR, + ]) + +_HASHCASHCHALLENGE = _descriptor.Descriptor( + name='HashcashChallenge', + full_name='spotify.login5.v3.challenges.HashcashChallenge', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='prefix', + full_name='spotify.login5.v3.challenges.HashcashChallenge.prefix', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='length', + full_name='spotify.login5.v3.challenges.HashcashChallenge.length', + index=1, + number=2, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=109, + serialized_end=160, +) + +_HASHCASHSOLUTION = _descriptor.Descriptor( + name='HashcashSolution', + full_name='spotify.login5.v3.challenges.HashcashSolution', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='suffix', + full_name='spotify.login5.v3.challenges.HashcashSolution.suffix', + index=0, + number=1, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='duration', + full_name='spotify.login5.v3.challenges.HashcashSolution.duration', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=162, + serialized_end=241, +) + +_HASHCASHSOLUTION.fields_by_name[ + 'duration'].message_type = google_dot_protobuf_dot_duration__pb2._DURATION +DESCRIPTOR.message_types_by_name['HashcashChallenge'] = _HASHCASHCHALLENGE +DESCRIPTOR.message_types_by_name['HashcashSolution'] = _HASHCASHSOLUTION +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +HashcashChallenge = _reflection.GeneratedProtocolMessageType( + 'HashcashChallenge', + (_message.Message, ), + { + 'DESCRIPTOR': _HASHCASHCHALLENGE, + '__module__': 'spotify.login5.v3.challenges.hashcash_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.challenges.HashcashChallenge) + }) +_sym_db.RegisterMessage(HashcashChallenge) + +HashcashSolution = _reflection.GeneratedProtocolMessageType( + 'HashcashSolution', + (_message.Message, ), + { + 'DESCRIPTOR': _HASHCASHSOLUTION, + '__module__': 'spotify.login5.v3.challenges.hashcash_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.challenges.HashcashSolution) + }) +_sym_db.RegisterMessage(HashcashSolution) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/spotify/login5/v3/client_info_pb2.py b/src/librespot/proto/spotify/login5/v3/client_info_pb2.py new file mode 100644 index 0000000..f013e1c --- /dev/null +++ b/src/librespot/proto/spotify/login5/v3/client_info_pb2.py @@ -0,0 +1,94 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: spotify/login5/v3/client_info.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='spotify/login5/v3/client_info.proto', + package='spotify.login5.v3', + syntax='proto3', + serialized_options=b'\n\024com.spotify.login5v3', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n#spotify/login5/v3/client_info.proto\x12\x11spotify.login5.v3\"2\n\nClientInfo\x12\x11\n\tclient_id\x18\x01 \x01(\t\x12\x11\n\tdevice_id\x18\x02 \x01(\tB\x16\n\x14\x63om.spotify.login5v3b\x06proto3' +) + +_CLIENTINFO = _descriptor.Descriptor( + name='ClientInfo', + full_name='spotify.login5.v3.ClientInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='client_id', + full_name='spotify.login5.v3.ClientInfo.client_id', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='device_id', + full_name='spotify.login5.v3.ClientInfo.device_id', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=58, + serialized_end=108, +) + +DESCRIPTOR.message_types_by_name['ClientInfo'] = _CLIENTINFO +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +ClientInfo = _reflection.GeneratedProtocolMessageType( + 'ClientInfo', + (_message.Message, ), + { + 'DESCRIPTOR': _CLIENTINFO, + '__module__': 'spotify.login5.v3.client_info_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.ClientInfo) + }) +_sym_db.RegisterMessage(ClientInfo) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/spotify/login5/v3/credentials/__init__.py b/src/librespot/proto/spotify/login5/v3/credentials/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/src/librespot/proto/spotify/login5/v3/credentials/credentials_pb2.py b/src/librespot/proto/spotify/login5/v3/credentials/credentials_pb2.py new file mode 100644 index 0000000..d4e7d55 --- /dev/null +++ b/src/librespot/proto/spotify/login5/v3/credentials/credentials_pb2.py @@ -0,0 +1,463 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: spotify/login5/v3/credentials/credentials.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='spotify/login5/v3/credentials/credentials.proto', + package='spotify.login5.v3.credentials', + syntax='proto3', + serialized_options=b'\n\024com.spotify.login5v3', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n/spotify/login5/v3/credentials/credentials.proto\x12\x1dspotify.login5.v3.credentials\"2\n\x10StoredCredential\x12\x10\n\x08username\x18\x01 \x01(\t\x12\x0c\n\x04\x64\x61ta\x18\x02 \x01(\x0c\"9\n\x08Password\x12\n\n\x02id\x18\x01 \x01(\t\x12\x10\n\x08password\x18\x02 \x01(\t\x12\x0f\n\x07padding\x18\x03 \x01(\x0c\";\n\x13\x46\x61\x63\x65\x62ookAccessToken\x12\x0e\n\x06\x66\x62_uid\x18\x01 \x01(\t\x12\x14\n\x0c\x61\x63\x63\x65ss_token\x18\x02 \x01(\t\"\x1d\n\x0cOneTimeToken\x12\r\n\x05token\x18\x01 \x01(\t\"|\n\x15ParentChildCredential\x12\x10\n\x08\x63hild_id\x18\x01 \x01(\t\x12Q\n\x18parent_stored_credential\x18\x02 \x01(\x0b\x32/.spotify.login5.v3.credentials.StoredCredential\"S\n\x15\x41ppleSignInCredential\x12\x11\n\tauth_code\x18\x01 \x01(\t\x12\x14\n\x0credirect_uri\x18\x02 \x01(\t\x12\x11\n\tbundle_id\x18\x03 \x01(\tB\x16\n\x14\x63om.spotify.login5v3b\x06proto3' +) + +_STOREDCREDENTIAL = _descriptor.Descriptor( + name='StoredCredential', + full_name='spotify.login5.v3.credentials.StoredCredential', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='username', + full_name='spotify.login5.v3.credentials.StoredCredential.username', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='data', + full_name='spotify.login5.v3.credentials.StoredCredential.data', + index=1, + number=2, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=82, + serialized_end=132, +) + +_PASSWORD = _descriptor.Descriptor( + name='Password', + full_name='spotify.login5.v3.credentials.Password', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='id', + full_name='spotify.login5.v3.credentials.Password.id', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='password', + full_name='spotify.login5.v3.credentials.Password.password', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='padding', + full_name='spotify.login5.v3.credentials.Password.padding', + index=2, + number=3, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=134, + serialized_end=191, +) + +_FACEBOOKACCESSTOKEN = _descriptor.Descriptor( + name='FacebookAccessToken', + full_name='spotify.login5.v3.credentials.FacebookAccessToken', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='fb_uid', + full_name= + 'spotify.login5.v3.credentials.FacebookAccessToken.fb_uid', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='access_token', + full_name= + 'spotify.login5.v3.credentials.FacebookAccessToken.access_token', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=193, + serialized_end=252, +) + +_ONETIMETOKEN = _descriptor.Descriptor( + name='OneTimeToken', + full_name='spotify.login5.v3.credentials.OneTimeToken', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='token', + full_name='spotify.login5.v3.credentials.OneTimeToken.token', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=254, + serialized_end=283, +) + +_PARENTCHILDCREDENTIAL = _descriptor.Descriptor( + name='ParentChildCredential', + full_name='spotify.login5.v3.credentials.ParentChildCredential', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='child_id', + full_name= + 'spotify.login5.v3.credentials.ParentChildCredential.child_id', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='parent_stored_credential', + full_name= + 'spotify.login5.v3.credentials.ParentChildCredential.parent_stored_credential', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=285, + serialized_end=409, +) + +_APPLESIGNINCREDENTIAL = _descriptor.Descriptor( + name='AppleSignInCredential', + full_name='spotify.login5.v3.credentials.AppleSignInCredential', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='auth_code', + full_name= + 'spotify.login5.v3.credentials.AppleSignInCredential.auth_code', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='redirect_uri', + full_name= + 'spotify.login5.v3.credentials.AppleSignInCredential.redirect_uri', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='bundle_id', + full_name= + 'spotify.login5.v3.credentials.AppleSignInCredential.bundle_id', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=411, + serialized_end=494, +) + +_PARENTCHILDCREDENTIAL.fields_by_name[ + 'parent_stored_credential'].message_type = _STOREDCREDENTIAL +DESCRIPTOR.message_types_by_name['StoredCredential'] = _STOREDCREDENTIAL +DESCRIPTOR.message_types_by_name['Password'] = _PASSWORD +DESCRIPTOR.message_types_by_name['FacebookAccessToken'] = _FACEBOOKACCESSTOKEN +DESCRIPTOR.message_types_by_name['OneTimeToken'] = _ONETIMETOKEN +DESCRIPTOR.message_types_by_name[ + 'ParentChildCredential'] = _PARENTCHILDCREDENTIAL +DESCRIPTOR.message_types_by_name[ + 'AppleSignInCredential'] = _APPLESIGNINCREDENTIAL +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +StoredCredential = _reflection.GeneratedProtocolMessageType( + 'StoredCredential', + (_message.Message, ), + { + 'DESCRIPTOR': _STOREDCREDENTIAL, + '__module__': 'spotify.login5.v3.credentials.credentials_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.credentials.StoredCredential) + }) +_sym_db.RegisterMessage(StoredCredential) + +Password = _reflection.GeneratedProtocolMessageType( + 'Password', + (_message.Message, ), + { + 'DESCRIPTOR': _PASSWORD, + '__module__': 'spotify.login5.v3.credentials.credentials_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.credentials.Password) + }) +_sym_db.RegisterMessage(Password) + +FacebookAccessToken = _reflection.GeneratedProtocolMessageType( + 'FacebookAccessToken', + (_message.Message, ), + { + 'DESCRIPTOR': _FACEBOOKACCESSTOKEN, + '__module__': 'spotify.login5.v3.credentials.credentials_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.credentials.FacebookAccessToken) + }) +_sym_db.RegisterMessage(FacebookAccessToken) + +OneTimeToken = _reflection.GeneratedProtocolMessageType( + 'OneTimeToken', + (_message.Message, ), + { + 'DESCRIPTOR': _ONETIMETOKEN, + '__module__': 'spotify.login5.v3.credentials.credentials_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.credentials.OneTimeToken) + }) +_sym_db.RegisterMessage(OneTimeToken) + +ParentChildCredential = _reflection.GeneratedProtocolMessageType( + 'ParentChildCredential', + (_message.Message, ), + { + 'DESCRIPTOR': _PARENTCHILDCREDENTIAL, + '__module__': 'spotify.login5.v3.credentials.credentials_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.credentials.ParentChildCredential) + }) +_sym_db.RegisterMessage(ParentChildCredential) + +AppleSignInCredential = _reflection.GeneratedProtocolMessageType( + 'AppleSignInCredential', + (_message.Message, ), + { + 'DESCRIPTOR': _APPLESIGNINCREDENTIAL, + '__module__': 'spotify.login5.v3.credentials.credentials_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.credentials.AppleSignInCredential) + }) +_sym_db.RegisterMessage(AppleSignInCredential) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/spotify/login5/v3/identifiers/__init__.py b/src/librespot/proto/spotify/login5/v3/identifiers/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/src/librespot/proto/spotify/login5/v3/identifiers/identifiers_pb2.py b/src/librespot/proto/spotify/login5/v3/identifiers/identifiers_pb2.py new file mode 100644 index 0000000..1091d1f --- /dev/null +++ b/src/librespot/proto/spotify/login5/v3/identifiers/identifiers_pb2.py @@ -0,0 +1,114 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: spotify/login5/v3/identifiers/identifiers.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='spotify/login5/v3/identifiers/identifiers.proto', + package='spotify.login5.v3.identifiers', + syntax='proto3', + serialized_options=b'\n\024com.spotify.login5v3', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n/spotify/login5/v3/identifiers/identifiers.proto\x12\x1dspotify.login5.v3.identifiers\"U\n\x0bPhoneNumber\x12\x0e\n\x06number\x18\x01 \x01(\t\x12\x18\n\x10iso_country_code\x18\x02 \x01(\t\x12\x1c\n\x14\x63ountry_calling_code\x18\x03 \x01(\tB\x16\n\x14\x63om.spotify.login5v3b\x06proto3' +) + +_PHONENUMBER = _descriptor.Descriptor( + name='PhoneNumber', + full_name='spotify.login5.v3.identifiers.PhoneNumber', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='number', + full_name='spotify.login5.v3.identifiers.PhoneNumber.number', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='iso_country_code', + full_name= + 'spotify.login5.v3.identifiers.PhoneNumber.iso_country_code', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='country_calling_code', + full_name= + 'spotify.login5.v3.identifiers.PhoneNumber.country_calling_code', + index=2, + number=3, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=82, + serialized_end=167, +) + +DESCRIPTOR.message_types_by_name['PhoneNumber'] = _PHONENUMBER +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +PhoneNumber = _reflection.GeneratedProtocolMessageType( + 'PhoneNumber', + (_message.Message, ), + { + 'DESCRIPTOR': _PHONENUMBER, + '__module__': 'spotify.login5.v3.identifiers.identifiers_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.identifiers.PhoneNumber) + }) +_sym_db.RegisterMessage(PhoneNumber) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/spotify/login5/v3/login5_pb2.py b/src/librespot/proto/spotify/login5/v3/login5_pb2.py new file mode 100644 index 0000000..38f3aac --- /dev/null +++ b/src/librespot/proto/spotify/login5/v3/login5_pb2.py @@ -0,0 +1,910 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: spotify/login5/v3/login5.proto +"""Generated protocol buffer code.""" +from google.protobuf.internal import enum_type_wrapper +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +from spotify.login5.v3 import client_info_pb2 as spotify_dot_login5_dot_v3_dot_client__info__pb2 +from spotify.login5.v3 import user_info_pb2 as spotify_dot_login5_dot_v3_dot_user__info__pb2 +from spotify.login5.v3.challenges import code_pb2 as spotify_dot_login5_dot_v3_dot_challenges_dot_code__pb2 +from spotify.login5.v3.challenges import hashcash_pb2 as spotify_dot_login5_dot_v3_dot_challenges_dot_hashcash__pb2 +from spotify.login5.v3.credentials import credentials_pb2 as spotify_dot_login5_dot_v3_dot_credentials_dot_credentials__pb2 +from spotify.login5.v3.identifiers import identifiers_pb2 as spotify_dot_login5_dot_v3_dot_identifiers_dot_identifiers__pb2 + +DESCRIPTOR = _descriptor.FileDescriptor( + name='spotify/login5/v3/login5.proto', + package='spotify.login5.v3', + syntax='proto3', + serialized_options=b'\n\024com.spotify.login5v3', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x1espotify/login5/v3/login5.proto\x12\x11spotify.login5.v3\x1a#spotify/login5/v3/client_info.proto\x1a!spotify/login5/v3/user_info.proto\x1a\'spotify/login5/v3/challenges/code.proto\x1a+spotify/login5/v3/challenges/hashcash.proto\x1a/spotify/login5/v3/credentials/credentials.proto\x1a/spotify/login5/v3/identifiers/identifiers.proto\">\n\nChallenges\x12\x30\n\nchallenges\x18\x01 \x03(\x0b\x32\x1c.spotify.login5.v3.Challenge\"\x89\x01\n\tChallenge\x12\x41\n\x08hashcash\x18\x01 \x01(\x0b\x32/.spotify.login5.v3.challenges.HashcashChallenge\x12\x39\n\x04\x63ode\x18\x02 \x01(\x0b\x32+.spotify.login5.v3.challenges.CodeChallenge\"M\n\x12\x43hallengeSolutions\x12\x37\n\tsolutions\x18\x01 \x03(\x0b\x32$.spotify.login5.v3.ChallengeSolution\"\x8f\x01\n\x11\x43hallengeSolution\x12@\n\x08hashcash\x18\x01 \x01(\x0b\x32..spotify.login5.v3.challenges.HashcashSolution\x12\x38\n\x04\x63ode\x18\x02 \x01(\x0b\x32*.spotify.login5.v3.challenges.CodeSolution\"\xad\x05\n\x0cLoginRequest\x12\x32\n\x0b\x63lient_info\x18\x01 \x01(\x0b\x32\x1d.spotify.login5.v3.ClientInfo\x12\x15\n\rlogin_context\x18\x02 \x01(\x0c\x12\x42\n\x13\x63hallenge_solutions\x18\x03 \x01(\x0b\x32%.spotify.login5.v3.ChallengeSolutions\x12J\n\x11stored_credential\x18\x64 \x01(\x0b\x32/.spotify.login5.v3.credentials.StoredCredential\x12\x39\n\x08password\x18\x65 \x01(\x0b\x32\'.spotify.login5.v3.credentials.Password\x12Q\n\x15\x66\x61\x63\x65\x62ook_access_token\x18\x66 \x01(\x0b\x32\x32.spotify.login5.v3.credentials.FacebookAccessToken\x12@\n\x0cphone_number\x18g \x01(\x0b\x32*.spotify.login5.v3.identifiers.PhoneNumber\x12\x43\n\x0eone_time_token\x18h \x01(\x0b\x32+.spotify.login5.v3.credentials.OneTimeToken\x12U\n\x17parent_child_credential\x18i \x01(\x0b\x32\x34.spotify.login5.v3.credentials.ParentChildCredential\x12V\n\x18\x61pple_sign_in_credential\x18j \x01(\x0b\x32\x34.spotify.login5.v3.credentials.AppleSignInCredential\"m\n\x07LoginOk\x12\x10\n\x08username\x18\x01 \x01(\t\x12\x14\n\x0c\x61\x63\x63\x65ss_token\x18\x02 \x01(\t\x12\x19\n\x11stored_credential\x18\x03 \x01(\x0c\x12\x1f\n\x17\x61\x63\x63\x65ss_token_expires_in\x18\x04 \x01(\x05\"\xf8\x02\n\rLoginResponse\x12&\n\x02ok\x18\x01 \x01(\x0b\x32\x1a.spotify.login5.v3.LoginOk\x12,\n\x05\x65rror\x18\x02 \x01(\x0e\x32\x1d.spotify.login5.v3.LoginError\x12\x31\n\nchallenges\x18\x03 \x01(\x0b\x32\x1d.spotify.login5.v3.Challenges\x12;\n\x08warnings\x18\x04 \x03(\x0e\x32).spotify.login5.v3.LoginResponse.Warnings\x12\x15\n\rlogin_context\x18\x05 \x01(\x0c\x12\x18\n\x10identifier_token\x18\x06 \x01(\t\x12.\n\tuser_info\x18\x07 \x01(\x0b\x32\x1b.spotify.login5.v3.UserInfo\"@\n\x08Warnings\x12\x13\n\x0fUNKNOWN_WARNING\x10\x00\x12\x1f\n\x1b\x44\x45PRECATED_PROTOCOL_VERSION\x10\x01*\xd3\x01\n\nLoginError\x12\x11\n\rUNKNOWN_ERROR\x10\x00\x12\x17\n\x13INVALID_CREDENTIALS\x10\x01\x12\x0f\n\x0b\x42\x41\x44_REQUEST\x10\x02\x12\x1e\n\x1aUNSUPPORTED_LOGIN_PROTOCOL\x10\x03\x12\x0b\n\x07TIMEOUT\x10\x04\x12\x16\n\x12UNKNOWN_IDENTIFIER\x10\x05\x12\x15\n\x11TOO_MANY_ATTEMPTS\x10\x06\x12\x17\n\x13INVALID_PHONENUMBER\x10\x07\x12\x13\n\x0fTRY_AGAIN_LATER\x10\x08\x42\x16\n\x14\x63om.spotify.login5v3b\x06proto3', + dependencies=[ + spotify_dot_login5_dot_v3_dot_client__info__pb2.DESCRIPTOR, + spotify_dot_login5_dot_v3_dot_user__info__pb2.DESCRIPTOR, + spotify_dot_login5_dot_v3_dot_challenges_dot_code__pb2.DESCRIPTOR, + spotify_dot_login5_dot_v3_dot_challenges_dot_hashcash__pb2.DESCRIPTOR, + spotify_dot_login5_dot_v3_dot_credentials_dot_credentials__pb2. + DESCRIPTOR, + spotify_dot_login5_dot_v3_dot_identifiers_dot_identifiers__pb2. + DESCRIPTOR, + ]) + +_LOGINERROR = _descriptor.EnumDescriptor( + name='LoginError', + full_name='spotify.login5.v3.LoginError', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='UNKNOWN_ERROR', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='INVALID_CREDENTIALS', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='BAD_REQUEST', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='UNSUPPORTED_LOGIN_PROTOCOL', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='TIMEOUT', + index=4, + number=4, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='UNKNOWN_IDENTIFIER', + index=5, + number=5, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='TOO_MANY_ATTEMPTS', + index=6, + number=6, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='INVALID_PHONENUMBER', + index=7, + number=7, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='TRY_AGAIN_LATER', + index=8, + number=8, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=1917, + serialized_end=2128, +) +_sym_db.RegisterEnumDescriptor(_LOGINERROR) + +LoginError = enum_type_wrapper.EnumTypeWrapper(_LOGINERROR) +UNKNOWN_ERROR = 0 +INVALID_CREDENTIALS = 1 +BAD_REQUEST = 2 +UNSUPPORTED_LOGIN_PROTOCOL = 3 +TIMEOUT = 4 +UNKNOWN_IDENTIFIER = 5 +TOO_MANY_ATTEMPTS = 6 +INVALID_PHONENUMBER = 7 +TRY_AGAIN_LATER = 8 + +_LOGINRESPONSE_WARNINGS = _descriptor.EnumDescriptor( + name='Warnings', + full_name='spotify.login5.v3.LoginResponse.Warnings', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='UNKNOWN_WARNING', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='DEPRECATED_PROTOCOL_VERSION', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=1850, + serialized_end=1914, +) +_sym_db.RegisterEnumDescriptor(_LOGINRESPONSE_WARNINGS) + +_CHALLENGES = _descriptor.Descriptor( + name='Challenges', + full_name='spotify.login5.v3.Challenges', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='challenges', + full_name='spotify.login5.v3.Challenges.challenges', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=309, + serialized_end=371, +) + +_CHALLENGE = _descriptor.Descriptor( + name='Challenge', + full_name='spotify.login5.v3.Challenge', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='hashcash', + full_name='spotify.login5.v3.Challenge.hashcash', + index=0, + number=1, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='code', + full_name='spotify.login5.v3.Challenge.code', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=374, + serialized_end=511, +) + +_CHALLENGESOLUTIONS = _descriptor.Descriptor( + name='ChallengeSolutions', + full_name='spotify.login5.v3.ChallengeSolutions', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='solutions', + full_name='spotify.login5.v3.ChallengeSolutions.solutions', + index=0, + number=1, + type=11, + cpp_type=10, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=513, + serialized_end=590, +) + +_CHALLENGESOLUTION = _descriptor.Descriptor( + name='ChallengeSolution', + full_name='spotify.login5.v3.ChallengeSolution', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='hashcash', + full_name='spotify.login5.v3.ChallengeSolution.hashcash', + index=0, + number=1, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='code', + full_name='spotify.login5.v3.ChallengeSolution.code', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=593, + serialized_end=736, +) + +_LOGINREQUEST = _descriptor.Descriptor( + name='LoginRequest', + full_name='spotify.login5.v3.LoginRequest', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='client_info', + full_name='spotify.login5.v3.LoginRequest.client_info', + index=0, + number=1, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='login_context', + full_name='spotify.login5.v3.LoginRequest.login_context', + index=1, + number=2, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='challenge_solutions', + full_name='spotify.login5.v3.LoginRequest.challenge_solutions', + index=2, + number=3, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='stored_credential', + full_name='spotify.login5.v3.LoginRequest.stored_credential', + index=3, + number=100, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='password', + full_name='spotify.login5.v3.LoginRequest.password', + index=4, + number=101, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='facebook_access_token', + full_name='spotify.login5.v3.LoginRequest.facebook_access_token', + index=5, + number=102, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='phone_number', + full_name='spotify.login5.v3.LoginRequest.phone_number', + index=6, + number=103, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='one_time_token', + full_name='spotify.login5.v3.LoginRequest.one_time_token', + index=7, + number=104, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='parent_child_credential', + full_name='spotify.login5.v3.LoginRequest.parent_child_credential', + index=8, + number=105, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='apple_sign_in_credential', + full_name='spotify.login5.v3.LoginRequest.apple_sign_in_credential', + index=9, + number=106, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=739, + serialized_end=1424, +) + +_LOGINOK = _descriptor.Descriptor( + name='LoginOk', + full_name='spotify.login5.v3.LoginOk', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='username', + full_name='spotify.login5.v3.LoginOk.username', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='access_token', + full_name='spotify.login5.v3.LoginOk.access_token', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='stored_credential', + full_name='spotify.login5.v3.LoginOk.stored_credential', + index=2, + number=3, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='access_token_expires_in', + full_name='spotify.login5.v3.LoginOk.access_token_expires_in', + index=3, + number=4, + type=5, + cpp_type=1, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1426, + serialized_end=1535, +) + +_LOGINRESPONSE = _descriptor.Descriptor( + name='LoginResponse', + full_name='spotify.login5.v3.LoginResponse', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='ok', + full_name='spotify.login5.v3.LoginResponse.ok', + index=0, + number=1, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='error', + full_name='spotify.login5.v3.LoginResponse.error', + index=1, + number=2, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='challenges', + full_name='spotify.login5.v3.LoginResponse.challenges', + index=2, + number=3, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='warnings', + full_name='spotify.login5.v3.LoginResponse.warnings', + index=3, + number=4, + type=14, + cpp_type=8, + label=3, + has_default_value=False, + default_value=[], + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='login_context', + full_name='spotify.login5.v3.LoginResponse.login_context', + index=4, + number=5, + type=12, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"", + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='identifier_token', + full_name='spotify.login5.v3.LoginResponse.identifier_token', + index=5, + number=6, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='user_info', + full_name='spotify.login5.v3.LoginResponse.user_info', + index=6, + number=7, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _LOGINRESPONSE_WARNINGS, + ], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=1538, + serialized_end=1914, +) + +_CHALLENGES.fields_by_name['challenges'].message_type = _CHALLENGE +_CHALLENGE.fields_by_name[ + 'hashcash'].message_type = spotify_dot_login5_dot_v3_dot_challenges_dot_hashcash__pb2._HASHCASHCHALLENGE +_CHALLENGE.fields_by_name[ + 'code'].message_type = spotify_dot_login5_dot_v3_dot_challenges_dot_code__pb2._CODECHALLENGE +_CHALLENGESOLUTIONS.fields_by_name[ + 'solutions'].message_type = _CHALLENGESOLUTION +_CHALLENGESOLUTION.fields_by_name[ + 'hashcash'].message_type = spotify_dot_login5_dot_v3_dot_challenges_dot_hashcash__pb2._HASHCASHSOLUTION +_CHALLENGESOLUTION.fields_by_name[ + 'code'].message_type = spotify_dot_login5_dot_v3_dot_challenges_dot_code__pb2._CODESOLUTION +_LOGINREQUEST.fields_by_name[ + 'client_info'].message_type = spotify_dot_login5_dot_v3_dot_client__info__pb2._CLIENTINFO +_LOGINREQUEST.fields_by_name[ + 'challenge_solutions'].message_type = _CHALLENGESOLUTIONS +_LOGINREQUEST.fields_by_name[ + 'stored_credential'].message_type = spotify_dot_login5_dot_v3_dot_credentials_dot_credentials__pb2._STOREDCREDENTIAL +_LOGINREQUEST.fields_by_name[ + 'password'].message_type = spotify_dot_login5_dot_v3_dot_credentials_dot_credentials__pb2._PASSWORD +_LOGINREQUEST.fields_by_name[ + 'facebook_access_token'].message_type = spotify_dot_login5_dot_v3_dot_credentials_dot_credentials__pb2._FACEBOOKACCESSTOKEN +_LOGINREQUEST.fields_by_name[ + 'phone_number'].message_type = spotify_dot_login5_dot_v3_dot_identifiers_dot_identifiers__pb2._PHONENUMBER +_LOGINREQUEST.fields_by_name[ + 'one_time_token'].message_type = spotify_dot_login5_dot_v3_dot_credentials_dot_credentials__pb2._ONETIMETOKEN +_LOGINREQUEST.fields_by_name[ + 'parent_child_credential'].message_type = spotify_dot_login5_dot_v3_dot_credentials_dot_credentials__pb2._PARENTCHILDCREDENTIAL +_LOGINREQUEST.fields_by_name[ + 'apple_sign_in_credential'].message_type = spotify_dot_login5_dot_v3_dot_credentials_dot_credentials__pb2._APPLESIGNINCREDENTIAL +_LOGINRESPONSE.fields_by_name['ok'].message_type = _LOGINOK +_LOGINRESPONSE.fields_by_name['error'].enum_type = _LOGINERROR +_LOGINRESPONSE.fields_by_name['challenges'].message_type = _CHALLENGES +_LOGINRESPONSE.fields_by_name['warnings'].enum_type = _LOGINRESPONSE_WARNINGS +_LOGINRESPONSE.fields_by_name[ + 'user_info'].message_type = spotify_dot_login5_dot_v3_dot_user__info__pb2._USERINFO +_LOGINRESPONSE_WARNINGS.containing_type = _LOGINRESPONSE +DESCRIPTOR.message_types_by_name['Challenges'] = _CHALLENGES +DESCRIPTOR.message_types_by_name['Challenge'] = _CHALLENGE +DESCRIPTOR.message_types_by_name['ChallengeSolutions'] = _CHALLENGESOLUTIONS +DESCRIPTOR.message_types_by_name['ChallengeSolution'] = _CHALLENGESOLUTION +DESCRIPTOR.message_types_by_name['LoginRequest'] = _LOGINREQUEST +DESCRIPTOR.message_types_by_name['LoginOk'] = _LOGINOK +DESCRIPTOR.message_types_by_name['LoginResponse'] = _LOGINRESPONSE +DESCRIPTOR.enum_types_by_name['LoginError'] = _LOGINERROR +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +Challenges = _reflection.GeneratedProtocolMessageType( + 'Challenges', + (_message.Message, ), + { + 'DESCRIPTOR': _CHALLENGES, + '__module__': 'spotify.login5.v3.login5_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.Challenges) + }) +_sym_db.RegisterMessage(Challenges) + +Challenge = _reflection.GeneratedProtocolMessageType( + 'Challenge', + (_message.Message, ), + { + 'DESCRIPTOR': _CHALLENGE, + '__module__': 'spotify.login5.v3.login5_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.Challenge) + }) +_sym_db.RegisterMessage(Challenge) + +ChallengeSolutions = _reflection.GeneratedProtocolMessageType( + 'ChallengeSolutions', + (_message.Message, ), + { + 'DESCRIPTOR': _CHALLENGESOLUTIONS, + '__module__': 'spotify.login5.v3.login5_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.ChallengeSolutions) + }) +_sym_db.RegisterMessage(ChallengeSolutions) + +ChallengeSolution = _reflection.GeneratedProtocolMessageType( + 'ChallengeSolution', + (_message.Message, ), + { + 'DESCRIPTOR': _CHALLENGESOLUTION, + '__module__': 'spotify.login5.v3.login5_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.ChallengeSolution) + }) +_sym_db.RegisterMessage(ChallengeSolution) + +LoginRequest = _reflection.GeneratedProtocolMessageType( + 'LoginRequest', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGINREQUEST, + '__module__': 'spotify.login5.v3.login5_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.LoginRequest) + }) +_sym_db.RegisterMessage(LoginRequest) + +LoginOk = _reflection.GeneratedProtocolMessageType( + 'LoginOk', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGINOK, + '__module__': 'spotify.login5.v3.login5_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.LoginOk) + }) +_sym_db.RegisterMessage(LoginOk) + +LoginResponse = _reflection.GeneratedProtocolMessageType( + 'LoginResponse', + (_message.Message, ), + { + 'DESCRIPTOR': _LOGINRESPONSE, + '__module__': 'spotify.login5.v3.login5_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.LoginResponse) + }) +_sym_db.RegisterMessage(LoginResponse) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/spotify/login5/v3/user_info_pb2.py b/src/librespot/proto/spotify/login5/v3/user_info_pb2.py new file mode 100644 index 0000000..85ee0d9 --- /dev/null +++ b/src/librespot/proto/spotify/login5/v3/user_info_pb2.py @@ -0,0 +1,249 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: spotify/login5/v3/user_info.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +DESCRIPTOR = _descriptor.FileDescriptor( + name='spotify/login5/v3/user_info.proto', + package='spotify.login5.v3', + syntax='proto3', + serialized_options=b'\n\024com.spotify.login5v3', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n!spotify/login5/v3/user_info.proto\x12\x11spotify.login5.v3\"\x97\x02\n\x08UserInfo\x12\x0c\n\x04name\x18\x01 \x01(\t\x12\r\n\x05\x65mail\x18\x02 \x01(\t\x12\x16\n\x0e\x65mail_verified\x18\x03 \x01(\x08\x12\x11\n\tbirthdate\x18\x04 \x01(\t\x12\x32\n\x06gender\x18\x05 \x01(\x0e\x32\".spotify.login5.v3.UserInfo.Gender\x12\x14\n\x0cphone_number\x18\x06 \x01(\t\x12\x1d\n\x15phone_number_verified\x18\x07 \x01(\x08\x12 \n\x18\x65mail_already_registered\x18\x08 \x01(\x08\"8\n\x06Gender\x12\x0b\n\x07UNKNOWN\x10\x00\x12\x08\n\x04MALE\x10\x01\x12\n\n\x06\x46\x45MALE\x10\x02\x12\x0b\n\x07NEUTRAL\x10\x03\x42\x16\n\x14\x63om.spotify.login5v3b\x06proto3' +) + +_USERINFO_GENDER = _descriptor.EnumDescriptor( + name='Gender', + full_name='spotify.login5.v3.UserInfo.Gender', + filename=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key, + values=[ + _descriptor.EnumValueDescriptor( + name='UNKNOWN', + index=0, + number=0, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='MALE', + index=1, + number=1, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='FEMALE', + index=2, + number=2, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + _descriptor.EnumValueDescriptor( + name='NEUTRAL', + index=3, + number=3, + serialized_options=None, + type=None, + create_key=_descriptor._internal_create_key), + ], + containing_type=None, + serialized_options=None, + serialized_start=280, + serialized_end=336, +) +_sym_db.RegisterEnumDescriptor(_USERINFO_GENDER) + +_USERINFO = _descriptor.Descriptor( + name='UserInfo', + full_name='spotify.login5.v3.UserInfo', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='name', + full_name='spotify.login5.v3.UserInfo.name', + index=0, + number=1, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='email', + full_name='spotify.login5.v3.UserInfo.email', + index=1, + number=2, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='email_verified', + full_name='spotify.login5.v3.UserInfo.email_verified', + index=2, + number=3, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='birthdate', + full_name='spotify.login5.v3.UserInfo.birthdate', + index=3, + number=4, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='gender', + full_name='spotify.login5.v3.UserInfo.gender', + index=4, + number=5, + type=14, + cpp_type=8, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='phone_number', + full_name='spotify.login5.v3.UserInfo.phone_number', + index=5, + number=6, + type=9, + cpp_type=9, + label=1, + has_default_value=False, + default_value=b"".decode('utf-8'), + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='phone_number_verified', + full_name='spotify.login5.v3.UserInfo.phone_number_verified', + index=6, + number=7, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='email_already_registered', + full_name='spotify.login5.v3.UserInfo.email_already_registered', + index=7, + number=8, + type=8, + cpp_type=7, + label=1, + has_default_value=False, + default_value=False, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[ + _USERINFO_GENDER, + ], + serialized_options=None, + is_extendable=False, + syntax='proto3', + extension_ranges=[], + oneofs=[], + serialized_start=57, + serialized_end=336, +) + +_USERINFO.fields_by_name['gender'].enum_type = _USERINFO_GENDER +_USERINFO_GENDER.containing_type = _USERINFO +DESCRIPTOR.message_types_by_name['UserInfo'] = _USERINFO +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +UserInfo = _reflection.GeneratedProtocolMessageType( + 'UserInfo', + (_message.Message, ), + { + 'DESCRIPTOR': _USERINFO, + '__module__': 'spotify.login5.v3.user_info_pb2' + # @@protoc_insertion_point(class_scope:spotify.login5.v3.UserInfo) + }) +_sym_db.RegisterMessage(UserInfo) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/proto/transfer_state_pb2.py b/src/librespot/proto/transfer_state_pb2.py new file mode 100644 index 0000000..b78d407 --- /dev/null +++ b/src/librespot/proto/transfer_state_pb2.py @@ -0,0 +1,167 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: transfer_state.proto +"""Generated protocol buffer code.""" +from google.protobuf import descriptor as _descriptor +from google.protobuf import message as _message +from google.protobuf import reflection as _reflection +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + +import context_player_options_pb2 as context__player__options__pb2 +import playback_pb2 as playback__pb2 +import session_pb2 as session__pb2 +import queue_pb2 as queue__pb2 + +DESCRIPTOR = _descriptor.FileDescriptor( + name='transfer_state.proto', + package='spotify.player.proto.transfer', + syntax='proto2', + serialized_options=b'\n\024com.spotify.transferH\002', + create_key=_descriptor._internal_create_key, + serialized_pb= + b'\n\x14transfer_state.proto\x12\x1dspotify.player.proto.transfer\x1a\x1c\x63ontext_player_options.proto\x1a\x0eplayback.proto\x1a\rsession.proto\x1a\x0bqueue.proto\"\x99\x02\n\rTransferState\x12;\n\x07options\x18\x01 \x01(\x0b\x32*.spotify.player.proto.ContextPlayerOptions\x12\x39\n\x08playback\x18\x02 \x01(\x0b\x32\'.spotify.player.proto.transfer.Playback\x12?\n\x0f\x63urrent_session\x18\x03 \x01(\x0b\x32&.spotify.player.proto.transfer.Session\x12\x33\n\x05queue\x18\x04 \x01(\x0b\x32$.spotify.player.proto.transfer.Queue\x12\x1a\n\x12\x63reation_timestamp\x18\x05 \x01(\x03\x42\x18\n\x14\x63om.spotify.transferH\x02', + dependencies=[ + context__player__options__pb2.DESCRIPTOR, + playback__pb2.DESCRIPTOR, + session__pb2.DESCRIPTOR, + queue__pb2.DESCRIPTOR, + ]) + +_TRANSFERSTATE = _descriptor.Descriptor( + name='TransferState', + full_name='spotify.player.proto.transfer.TransferState', + filename=None, + file=DESCRIPTOR, + containing_type=None, + create_key=_descriptor._internal_create_key, + fields=[ + _descriptor.FieldDescriptor( + name='options', + full_name='spotify.player.proto.transfer.TransferState.options', + index=0, + number=1, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='playback', + full_name='spotify.player.proto.transfer.TransferState.playback', + index=1, + number=2, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='current_session', + full_name= + 'spotify.player.proto.transfer.TransferState.current_session', + index=2, + number=3, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='queue', + full_name='spotify.player.proto.transfer.TransferState.queue', + index=3, + number=4, + type=11, + cpp_type=10, + label=1, + has_default_value=False, + default_value=None, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + _descriptor.FieldDescriptor( + name='creation_timestamp', + full_name= + 'spotify.player.proto.transfer.TransferState.creation_timestamp', + index=4, + number=5, + type=3, + cpp_type=2, + label=1, + has_default_value=False, + default_value=0, + message_type=None, + enum_type=None, + containing_type=None, + is_extension=False, + extension_scope=None, + serialized_options=None, + file=DESCRIPTOR, + create_key=_descriptor._internal_create_key), + ], + extensions=[], + nested_types=[], + enum_types=[], + serialized_options=None, + is_extendable=False, + syntax='proto2', + extension_ranges=[], + oneofs=[], + serialized_start=130, + serialized_end=411, +) + +_TRANSFERSTATE.fields_by_name[ + 'options'].message_type = context__player__options__pb2._CONTEXTPLAYEROPTIONS +_TRANSFERSTATE.fields_by_name[ + 'playback'].message_type = playback__pb2._PLAYBACK +_TRANSFERSTATE.fields_by_name[ + 'current_session'].message_type = session__pb2._SESSION +_TRANSFERSTATE.fields_by_name['queue'].message_type = queue__pb2._QUEUE +DESCRIPTOR.message_types_by_name['TransferState'] = _TRANSFERSTATE +_sym_db.RegisterFileDescriptor(DESCRIPTOR) + +TransferState = _reflection.GeneratedProtocolMessageType( + 'TransferState', + (_message.Message, ), + { + 'DESCRIPTOR': _TRANSFERSTATE, + '__module__': 'transfer_state_pb2' + # @@protoc_insertion_point(class_scope:spotify.player.proto.transfer.TransferState) + }) +_sym_db.RegisterMessage(TransferState) + +DESCRIPTOR._options = None +# @@protoc_insertion_point(module_scope) diff --git a/src/librespot/standard/AutoCloseable.py b/src/librespot/standard/AutoCloseable.py new file mode 100644 index 0000000..7707ac1 --- /dev/null +++ b/src/librespot/standard/AutoCloseable.py @@ -0,0 +1,3 @@ +class AutoCloseable: + def close(self) -> None: + pass diff --git a/src/librespot/standard/ByteArrayOutputStream.py b/src/librespot/standard/ByteArrayOutputStream.py new file mode 100644 index 0000000..0b290ff --- /dev/null +++ b/src/librespot/standard/ByteArrayOutputStream.py @@ -0,0 +1,68 @@ +from librespot.standard.OutputStream import OutputStream + + +class ByteArrayOutputStream(OutputStream): + buf: bytearray + count: int = 0 + + def __init__(self, size: int = 32): + if size < 0: + raise RuntimeError("Negative initial size: {}".format(self)) + self.buf = bytearray(size) + + def ensure_capacity(self, min_capacity: int) -> None: + old_capacity = len(self.buf) + min_growth = min_capacity - old_capacity + if min_growth > 0: + new_buf = bytearray(min_capacity) + new_buf[0:len(self.buf)] = self.buf + self.buf = new_buf + + def internal_write(self, byte: int) -> None: + self.ensure_capacity(self.count + 1) + self.buf[self.count] = byte + self.count += 1 + + def write(self, + byte: int = None, + buffer: bytearray = None, + offset: int = None, + length: int = None) -> None: + if byte is not None and buffer is None and offset is None and length is None: + self.internal_write(byte) + return + elif byte is None and buffer is not None and offset is None and length is None: + offset = 0 + length = len(buffer) + elif not (byte is None and buffer is not None and offset is not None + and length is not None): + raise TypeError() + + if len(buffer) < (offset + length): + raise IndexError() + + self.ensure_capacity(self.count + length) + self.buf[self.count:self.count + length] = buffer[offset:offset + + length] + self.count += length + + def write_bytes(self, b: bytearray): + self.write(buffer=b, offset=0, length=len(b)) + + def write_to(self, out: OutputStream) -> None: + out.write(buffer=self.buf, offset=0, length=self.count) + + def reset(self) -> None: + self.count = 0 + + def to_byte_array(self) -> bytearray: + return self.buf + + def to_bytes(self) -> bytes: + return bytes(self.buf) + + def size(self) -> int: + return self.count + + def close(self) -> None: + pass diff --git a/src/librespot/standard/BytesInputStream.py b/src/librespot/standard/BytesInputStream.py new file mode 100644 index 0000000..4e1d8d9 --- /dev/null +++ b/src/librespot/standard/BytesInputStream.py @@ -0,0 +1,42 @@ +import struct + + +class BytesInputStream: + buffer: bytes + endian: str + + def __init__(self, buffer: bytes, endian: str = ">"): + self.buffer = buffer + self.endian = endian + + def read(self, length: int = None) -> bytes: + if length is None: + length = len(self.buffer) + buffer = self.buffer[:length] + self.buffer = self.buffer[length:] + return buffer + + def read_byte(self) -> bytes: + buffer = struct.unpack("s", self.buffer[:1])[0] + self.buffer = self.buffer[1:] + return buffer + + def read_int(self) -> int: + buffer = struct.unpack("{}i".format(self.endian), self.buffer[:4])[0] + self.buffer = self.buffer[4:] + return buffer + + def read_short(self) -> int: + buffer = struct.unpack("{}h".format(self.endian), self.buffer[:2])[0] + self.buffer = self.buffer[2:] + return buffer + + def read_long(self) -> int: + buffer = struct.unpack("{}q".format(self.endian), self.buffer[:8])[0] + self.buffer = self.buffer[8:] + return buffer + + def read_float(self) -> float: + buffer = struct.unpack("{}f".format(self.endian), self.buffer[:4])[0] + self.buffer = self.buffer[4:] + return buffer diff --git a/src/librespot/standard/BytesOutputStream.py b/src/librespot/standard/BytesOutputStream.py new file mode 100644 index 0000000..e6438d6 --- /dev/null +++ b/src/librespot/standard/BytesOutputStream.py @@ -0,0 +1,24 @@ +import struct + + +class BytesOutputStream: + buffer: bytes + + def __init__(self): + self.buffer = b"" + + def write(self, data: bytes): + self.buffer += data + return len(data) + + def write_byte(self, data: int): + self.buffer += bytes([data]) + return 1 + + def write_int(self, data: int): + self.buffer += struct.pack(">i", data) + return 4 + + def write_short(self, data: int): + self.buffer += struct.pack(">h", data) + return 2 diff --git a/src/librespot/standard/Closeable.py b/src/librespot/standard/Closeable.py new file mode 100644 index 0000000..8810afb --- /dev/null +++ b/src/librespot/standard/Closeable.py @@ -0,0 +1,6 @@ +from librespot.standard.AutoCloseable import AutoCloseable + + +class Closeable(AutoCloseable): + def close(self) -> None: + pass diff --git a/src/librespot/standard/DataInput.py b/src/librespot/standard/DataInput.py new file mode 100644 index 0000000..caef152 --- /dev/null +++ b/src/librespot/standard/DataInput.py @@ -0,0 +1,48 @@ +class DataInput: + def internal_read_fully(self, b: bytearray) -> None: + pass + + def read_fully(self, + b: bytearray = None, + offset: int = None, + length: int = None) -> None: + pass + + def skip_bytes(self, n: int) -> int: + pass + + def read_boolean(self) -> bool: + pass + + def read_byte(self) -> bytes: + pass + + def read_unsigned_byte(self) -> int: + pass + + def read_short(self) -> int: + pass + + def read_unsigned_short(self) -> int: + pass + + def read_char(self) -> str: + pass + + def read_int(self) -> int: + pass + + def read_long(self) -> int: + pass + + def read_float(self) -> float: + pass + + def read_double(self) -> float: + pass + + def read_line(self) -> str: + pass + + def read_utf(self) -> str: + pass diff --git a/src/librespot/standard/DataInputStream.py b/src/librespot/standard/DataInputStream.py new file mode 100644 index 0000000..9267c35 --- /dev/null +++ b/src/librespot/standard/DataInputStream.py @@ -0,0 +1,118 @@ +from librespot.standard.DataInput import DataInput +from librespot.standard.FilterInputStream import FilterInputStream +from librespot.standard.InputStream import InputStream + + +class DataInputStream(FilterInputStream, DataInput): + def __init__(self, input_stream: InputStream): + super().__init__(input_stream) + + def read(self, + b: bytearray = None, + offset: int = None, + length: int = None) -> int: + if b is not None and offset is None and length is None: + return self.input_stream.read(b, 0, len(b)) + elif b is not None and offset is not None and length is not None: + return self.input_stream.read(b, offset, length) + else: + raise TypeError() + + def read_fully(self, + b: bytearray = None, + offset: int = None, + length: int = None) -> None: + if b is not None and offset is None and length is None: + offset = 0 + length = len(b) + elif not (b is not None and offset is not None and length is not None): + raise TypeError() + if length < 0: + raise IndexError() + n = 0 + while n < length: + count = self.input_stream.read(b, offset + n, length - n) + if count < 0: + raise EOFError() + n += count + + def skip_bytes(self, n: int) -> int: + total = 0 + cur = 0 + while True: + cur = self.input_stream.skip(n - total) + if not (total < n and cur > 0): + break + total += cur + + return total + + def read_boolean(self) -> bool: + ch = self.input_stream.read() + if ch < 0: + raise EOFError() + return ch != 0 + + def read_byte(self) -> bytes: + ch = self.input_stream.read() + if ch < 0: + raise EOFError() + return bytes([ch]) + + def read_unsigned_byte(self) -> int: + ch = self.input_stream.read() + if ch < 0: + raise EOFError() + return ch + + def read_short(self) -> int: + ch1 = self.input_stream.read() + ch2 = self.input_stream.read() + if (ch1 | ch2) < 0: + raise EOFError() + return (ch1 << 8) + (ch2 << 0) + + def read_unsigned_short(self) -> int: + ch1 = self.input_stream.read() + ch2 = self.input_stream.read() + if (ch1 | ch2) < 0: + raise EOFError() + return (ch1 << 8) + (ch2 << 0) + + def read_char(self) -> str: + ch1 = self.input_stream.read() + ch2 = self.input_stream.read() + if (ch1 | ch2) < 0: + raise EOFError() + return chr((ch1 << 8) + (ch2 << 0)) + + def read_int(self) -> int: + ch1 = self.input_stream.read() + ch2 = self.input_stream.read() + ch3 = self.input_stream.read() + ch4 = self.input_stream.read() + if (ch1 | ch2 | ch3 | ch4) < 0: + raise EOFError() + return (ch1 << 24) + (ch2 << 16) + (ch3 << 8) + (ch4 << 0) + + read_buffer = bytearray(8) + + def read_long(self) -> int: + self.read_fully(self.read_buffer, 0, 8) + return (self.read_buffer[0] << 56) + \ + ((self.read_buffer[1] & 255) << 48) + \ + ((self.read_buffer[2] & 255) << 40) + \ + ((self.read_buffer[3] & 255) << 32) + \ + ((self.read_buffer[4] & 255) << 24) + \ + ((self.read_buffer[5] & 255) << 16) + \ + ((self.read_buffer[6] & 255) << 8) + \ + ((self.read_buffer[7] & 255) << 0) + + def read_float(self) -> float: + pass + + def read_double(self) -> float: + pass + + def read_line(self) -> str: + pass diff --git a/src/librespot/standard/DataOutput.py b/src/librespot/standard/DataOutput.py new file mode 100644 index 0000000..0b295a9 --- /dev/null +++ b/src/librespot/standard/DataOutput.py @@ -0,0 +1,43 @@ +class DataOutput: + def internal_write(self, byte: int) -> None: + pass + + def write(self, + byte: int = None, + buffer: bytearray = None, + offset: int = None, + length: int = None) -> None: + pass + + def write_boolean(self, v: bytes) -> None: + pass + + def write_byte(self, v: int) -> None: + pass + + def write_short(self, v: int) -> None: + pass + + def write_char(self, v: int) -> None: + pass + + def write_int(self, v: int) -> None: + pass + + def write_long(self, v: int) -> None: + pass + + def write_float(self, v: float) -> None: + pass + + def write_double(self, v: float) -> None: + pass + + def write_bytes(self, s: str) -> None: + pass + + def write_chars(self, s: str) -> None: + pass + + def write_utf(self, s: str) -> None: + pass diff --git a/src/librespot/standard/FilterInputStream.py b/src/librespot/standard/FilterInputStream.py new file mode 100644 index 0000000..9409cd9 --- /dev/null +++ b/src/librespot/standard/FilterInputStream.py @@ -0,0 +1,41 @@ +from librespot.standard.InputStream import InputStream + + +class FilterInputStream(InputStream): + input_stream: InputStream + + def __init__(self, input_stream: InputStream): + self.input_stream = input_stream + + def internal_read(self): + return self.input_stream.read() + + def read(self, + b: bytearray = None, + offset: int = None, + length: int = None) -> int: + if b is not None and offset is None and length is None: + offset = 0 + length = len(b) + elif not (b is not None and offset is not None and length is not None): + raise TypeError() + + return self.input_stream.read(b, offset, length) + + def skip(self, n: int) -> int: + return self.input_stream.skip(n) + + def available(self) -> int: + return self.input_stream.available() + + def close(self) -> None: + self.input_stream.close() + + def mark(self, read_limit: int) -> None: + self.input_stream.mark(read_limit) + + def reset(self) -> None: + self.input_stream.reset() + + def mark_supported(self) -> bool: + return self.input_stream.mark_supported() diff --git a/src/librespot/standard/Flushable.py b/src/librespot/standard/Flushable.py new file mode 100644 index 0000000..148a0d0 --- /dev/null +++ b/src/librespot/standard/Flushable.py @@ -0,0 +1,3 @@ +class Flushable: + def flush(self) -> None: + pass diff --git a/src/librespot/standard/InputStream.py b/src/librespot/standard/InputStream.py new file mode 100644 index 0000000..ed265cd --- /dev/null +++ b/src/librespot/standard/InputStream.py @@ -0,0 +1,240 @@ +from __future__ import annotations +from librespot.standard.Closeable import Closeable +import sys +import typing + +if typing.TYPE_CHECKING: + from librespot.standard.OutputStream import OutputStream + + +class InputStream(Closeable): + max_skip_buffer_size: typing.Final[int] = 2048 + default_buffer_size: typing.Final[int] = 8192 + + @staticmethod + def null_input_stream(): + class Anonymous(InputStream): + closed: bool + + def ensure_open(self) -> None: + if self.closed: + raise IOError("Stream closed") + + def available(self) -> int: + self.ensure_open() + return 0 + + def read(self, + b: bytearray = None, + offset: int = None, + length: int = None) -> int: + if b is not None and offset is not None and length is not None: + if len(b) < (offset + length): + raise IndexError() + if length == 0: + return 0 + self.ensure_open() + return -1 + elif b is None and offset is None and length is None: + self.ensure_open() + return -1 + else: + raise TypeError() + + def read_all_bytes(self): + self.ensure_open() + return bytearray(0) + + def read_n_bytes(self, + b: bytearray = None, + offset: int = None, + length: int = None) -> bytearray: + if length < 0: + raise TypeError("length < 0") + self.ensure_open() + return bytearray(0) + + def skip(self, n) -> int: + self.ensure_open() + return 0 + + def skip_n_bytes(self, n: int) -> None: + self.ensure_open() + if n > 0: + raise EOFError() + + def transfer_to(self, out) -> int: + if out is None: + raise TypeError() + self.ensure_open() + return 0 + + def close(self): + self.closed = True + + return Anonymous() + + def internal_read(self): + raise NotImplementedError() + + def read(self, + b: bytearray = None, + offset: int = None, + length: int = None) -> int: + if b is None and offset is None and length is None: + return self.internal_read() + elif b is not None and offset is None and length is None: + offset = 0 + length = len(b) + elif not (b is not None and offset is not None and length is not None): + raise TypeError() + if len(b) < (offset + length): + raise IndexError() + if length == 0: + return 0 + + c = self.read() + if c == -1: + return -1 + + b[offset] = c + + i = 1 + for i in range(i, length): + c = self.read() + if c == -1: + break + b[offset + i] = c + return i + + max_buffer_size: typing.Final[int] = sys.maxsize - 8 + + def read_all_bytes(self) -> bytearray: + return self.read_n_bytes(length=sys.maxsize) + + def read_n_bytes(self, + b: bytearray = None, + offset: int = None, + length: int = None) -> typing.Union[bytearray, int]: + if b is None and offset is None and len is not None: + if length < 0: + raise TypeError("length < 0") + + bufs = None + result = None + total = 0 + remaining = length + n: int + while True: + buf = bytearray(min(remaining, self.default_buffer_size)) + nread = 0 + + while True: + n = self.read(buf, nread, min(len(buf) - nread, remaining)) + if not n > 0: + break + nread += n + remaining -= n + + if nread > 0: + if self.max_buffer_size - total < nread: + raise MemoryError("Required array size too large") + total += nread + if result is None: + result = buf + else: + if bufs is None: + bufs = [result] + bufs.append(buf) + if n >= 0 and remaining > 0: + break + + if bufs is None: + if result is None: + return bytearray(0) + return result if len(result) == total else result[:total] + + result = bytearray(total) + offset = 0 + remaining = total + for b in bufs: + count = min(len(b), remaining) + for i in range(offset, offset + count): + result.insert(i, b[i]) + offset += count + remaining -= count + + return result + elif b is not None and offset is not None and length is not None: + if len(b) < (offset + length): + raise IndexError() + + n = 0 + while n < length: + count = self.read(b, offset + n, length - n) + if count < 0: + break + n += count + return n + else: + raise TypeError() + + def skip(self, n: int) -> int: + remaining = n + nr: int + + if n <= 0: + return 0 + + size = min(self.max_skip_buffer_size, remaining) + skip_buffer = bytearray(size) + while remaining > 0: + nr = self.read(skip_buffer, 0, min(size, remaining)) + if nr < 0: + break + remaining -= nr + + return n - remaining + + def skip_n_bytes(self, n: int) -> None: + if n > 0: + ns = self.skip(n) + if ns >= 0 and ns < n: + n -= ns + + while n > 0 and self.read() != -1: + n -= 1 + + if n != 0: + raise EOFError() + elif ns != n: + raise IOError("Unable to skip exactly") + + def available(self) -> int: + return 0 + + def close(self) -> None: + pass + + def mark(self, read_limit: int) -> None: + pass + + def reset(self) -> None: + raise IOError("mark/reset not supported") + + def mark_supported(self) -> bool: + return False + + def transfer_to(self, out: OutputStream) -> int: + if out is None: + raise TypeError() + transferred = 0 + buffer = bytearray(self.default_buffer_size) + read: int + while True: + read = self.read(buffer, 0, self.default_buffer_size) + if not read: + break + out.write(buffer=buffer, offset=0, length=read) + transferred += read + return transferred diff --git a/src/librespot/standard/OutputStream.py b/src/librespot/standard/OutputStream.py new file mode 100644 index 0000000..aa7cf68 --- /dev/null +++ b/src/librespot/standard/OutputStream.py @@ -0,0 +1,61 @@ +from librespot.standard.Closeable import Closeable +from librespot.standard.Flushable import Flushable + + +class OutputStream(Closeable, Flushable): + def null_output_stream(self): + class Annonymous(OutputStream): + closed: bool + + def ensure_open(self) -> None: + if self.closed: + raise IOError("Stream closed") + + def internal_write(self, byte: int): + self.ensure_open() + + def write(self, + byte: int = None, + buffer: bytearray = None, + offset: int = None, + length: int = None): + if byte is not None and buffer is None and offset is None and length is None: + self.internal_write(byte) + elif not (byte is None and buffer is not None + and offset is not None and length is not None): + raise TypeError() + if len(bytearray) < (offset + length): + raise IndexError() + self.ensure_open() + + def close(self) -> None: + self.closed = True + + def internal_write(self, byte: int): + raise NotImplementedError() + + def write(self, + byte: int = None, + buffer: bytearray = None, + offset: int = None, + length: int = None): + if byte is not None and buffer is None and offset is None and length is None: + self.internal_write(byte) + elif byte is None and buffer is not None and offset is None and length is None: + offset = 0 + length = len(buffer) + elif not (byte is None and buffer is not None and offset is not None + and length is not None): + raise TypeError() + + if len(bytearray) < (offset + length): + raise IndexError() + + for i in range(length): + self.write(buffer[offset + i]) + + def flush(self) -> None: + pass + + def close(self) -> None: + pass diff --git a/src/librespot/standard/Proxy.py b/src/librespot/standard/Proxy.py new file mode 100644 index 0000000..9baaeef --- /dev/null +++ b/src/librespot/standard/Proxy.py @@ -0,0 +1,9 @@ +from __future__ import annotations +import enum + + +class Proxy: + class Type(enum.Enum): + DIRECT = enum.auto() + HTTP = enum.auto() + SOCKS = enum.auto() diff --git a/src/librespot/standard/Runnable.py b/src/librespot/standard/Runnable.py new file mode 100644 index 0000000..f12139f --- /dev/null +++ b/src/librespot/standard/Runnable.py @@ -0,0 +1,3 @@ +class Runnable: + def run(self) -> None: + raise NotImplementedError() diff --git a/src/librespot/standard/__init__.py b/src/librespot/standard/__init__.py new file mode 100644 index 0000000..7af7efe --- /dev/null +++ b/src/librespot/standard/__init__.py @@ -0,0 +1,14 @@ +from librespot.standard.AutoCloseable import AutoCloseable +from librespot.standard.ByteArrayOutputStream import ByteArrayOutputStream +from librespot.standard.BytesInputStream import BytesInputStream +from librespot.standard.BytesOutputStream import BytesOutputStream +from librespot.standard.Closeable import Closeable +from librespot.standard.DataInput import DataInput +from librespot.standard.DataInputStream import DataInputStream +from librespot.standard.DataOutput import DataOutput +from librespot.standard.FilterInputStream import FilterInputStream +from librespot.standard.Flushable import Flushable +from librespot.standard.InputStream import InputStream +from librespot.standard.OutputStream import OutputStream +from librespot.standard.Proxy import Proxy +from librespot.standard.Runnable import Runnable