Merge pull request #110 from jodal/feature/spotify-playlist-loading
feature/spotify-playlist-loading
This commit is contained in:
commit
0dc50bd048
@ -1,16 +1,46 @@
|
||||
import logging
|
||||
|
||||
from spotify.manager import SpotifyContainerManager as PyspotifyContainerManager
|
||||
from spotify.manager import SpotifyContainerManager as \
|
||||
PyspotifyContainerManager
|
||||
|
||||
logger = logging.getLogger('mopidy.backends.spotify.container_manager')
|
||||
|
||||
class SpotifyContainerManager(PyspotifyContainerManager):
|
||||
|
||||
def __init__(self, session_manager):
|
||||
PyspotifyContainerManager.__init__(self)
|
||||
self.session_manager = session_manager
|
||||
|
||||
def container_loaded(self, container, userdata):
|
||||
"""Callback used by pyspotify."""
|
||||
logger.debug(u'Container loaded')
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(u'Callback called: playlist container loaded')
|
||||
self.session_manager.refresh_stored_playlists()
|
||||
|
||||
playlist_container = self.session_manager.session.playlist_container()
|
||||
for playlist in playlist_container:
|
||||
self.session_manager.playlist_manager.watch(playlist)
|
||||
logger.debug(u'Watching %d playlist(s) for changes',
|
||||
len(playlist_container))
|
||||
|
||||
def playlist_added(self, container, playlist, position, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(u'Callback called: playlist added at position %d',
|
||||
position)
|
||||
# container_loaded() is called after this callback, so we do not need
|
||||
# to handle this callback.
|
||||
|
||||
def playlist_moved(self, container, playlist, old_position, new_position,
|
||||
userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(
|
||||
u'Callback called: playlist "%s" moved from position %d to %d',
|
||||
playlist.name(), old_position, new_position)
|
||||
# container_loaded() is called after this callback, so we do not need
|
||||
# to handle this callback.
|
||||
|
||||
def playlist_removed(self, container, playlist, position, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(
|
||||
u'Callback called: playlist "%s" removed from position %d',
|
||||
playlist.name(), position)
|
||||
# container_loaded() is called after this callback, so we do not need
|
||||
# to handle this callback.
|
||||
|
||||
93
mopidy/backends/spotify/playlist_manager.py
Normal file
93
mopidy/backends/spotify/playlist_manager.py
Normal file
@ -0,0 +1,93 @@
|
||||
import datetime
|
||||
import logging
|
||||
|
||||
from spotify.manager import SpotifyPlaylistManager as PyspotifyPlaylistManager
|
||||
|
||||
logger = logging.getLogger('mopidy.backends.spotify.playlist_manager')
|
||||
|
||||
class SpotifyPlaylistManager(PyspotifyPlaylistManager):
|
||||
def __init__(self, session_manager):
|
||||
PyspotifyPlaylistManager.__init__(self)
|
||||
self.session_manager = session_manager
|
||||
|
||||
def tracks_added(self, playlist, tracks, position, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(u'Callback called: '
|
||||
u'%d track(s) added to position %d in playlist "%s"',
|
||||
len(tracks), position, playlist.name())
|
||||
self.session_manager.refresh_stored_playlists()
|
||||
|
||||
def tracks_moved(self, playlist, tracks, new_position, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(u'Callback called: '
|
||||
u'%d track(s) moved to position %d in playlist "%s"',
|
||||
len(tracks), new_position, playlist.name())
|
||||
self.session_manager.refresh_stored_playlists()
|
||||
|
||||
def tracks_removed(self, playlist, tracks, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(u'Callback called: '
|
||||
u'%d track(s) removed from playlist "%s"', len(tracks), playlist.name())
|
||||
self.session_manager.refresh_stored_playlists()
|
||||
|
||||
def playlist_renamed(self, playlist, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(u'Callback called: Playlist renamed to "%s"',
|
||||
playlist.name())
|
||||
self.session_manager.refresh_stored_playlists()
|
||||
|
||||
def playlist_state_changed(self, playlist, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(u'Callback called: The state of playlist "%s" changed',
|
||||
playlist.name())
|
||||
|
||||
def playlist_update_in_progress(self, playlist, done, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
if done:
|
||||
logger.debug(u'Callback called: '
|
||||
u'Update of playlist "%s" done', playlist.name())
|
||||
else:
|
||||
logger.debug(u'Callback called: '
|
||||
u'Update of playlist "%s" in progress', playlist.name())
|
||||
|
||||
def playlist_metadata_updated(self, playlist, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(u'Callback called: Metadata updated for playlist "%s"',
|
||||
playlist.name())
|
||||
|
||||
def track_created_changed(self, playlist, position, user, when, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
when = datetime.datetime.fromtimestamp(when)
|
||||
logger.debug(
|
||||
u'Callback called: Created by/when for track %d in playlist '
|
||||
u'"%s" changed to user "N/A" and time "%s"',
|
||||
position, playlist.name(), when)
|
||||
|
||||
def track_message_changed(self, playlist, position, message, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(
|
||||
u'Callback called: Message for track %d in playlist '
|
||||
u'"%s" changed to "%s"', position, playlist.name(), message)
|
||||
|
||||
def track_seen_changed(self, playlist, position, seen, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(
|
||||
u'Callback called: Seen attribute for track %d in playlist '
|
||||
u'"%s" changed to "%s"', position, playlist.name(), seen)
|
||||
|
||||
def description_changed(self, playlist, description, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(
|
||||
u'Callback called: Description changed for playlist "%s" to "%s"',
|
||||
playlist.name(), description)
|
||||
|
||||
def subscribers_changed(self, playlist, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(
|
||||
u'Callback called: Subscribers changed for playlist "%s"',
|
||||
playlist.name())
|
||||
|
||||
def image_changed(self, playlist, image, userdata):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(u'Callback called: Image changed for playlist "%s"',
|
||||
playlist.name())
|
||||
@ -9,11 +9,12 @@ from pykka.registry import ActorRegistry
|
||||
from mopidy import get_version, settings
|
||||
from mopidy.backends.base import Backend
|
||||
from mopidy.backends.spotify import BITRATES
|
||||
from mopidy.backends.spotify.container_manager import SpotifyContainerManager
|
||||
from mopidy.backends.spotify.playlist_manager import SpotifyPlaylistManager
|
||||
from mopidy.backends.spotify.translator import SpotifyTranslator
|
||||
from mopidy.models import Playlist
|
||||
from mopidy.gstreamer import GStreamer
|
||||
from mopidy.utils.process import BaseThread
|
||||
from mopidy.backends.spotify.container_manager import SpotifyContainerManager
|
||||
|
||||
logger = logging.getLogger('mopidy.backends.spotify.session_manager')
|
||||
|
||||
@ -29,7 +30,7 @@ class SpotifySessionManager(BaseThread, PyspotifySessionManager):
|
||||
def __init__(self, username, password):
|
||||
PyspotifySessionManager.__init__(self, username, password)
|
||||
BaseThread.__init__(self)
|
||||
self.name = 'SpotifySMThread'
|
||||
self.name = 'SpotifyThread'
|
||||
|
||||
self.gstreamer = None
|
||||
self.backend = None
|
||||
@ -38,6 +39,7 @@ class SpotifySessionManager(BaseThread, PyspotifySessionManager):
|
||||
self.session = None
|
||||
|
||||
self.container_manager = None
|
||||
self.playlist_manager = None
|
||||
|
||||
def run_inside_try(self):
|
||||
self.setup()
|
||||
@ -45,7 +47,8 @@ class SpotifySessionManager(BaseThread, PyspotifySessionManager):
|
||||
|
||||
def setup(self):
|
||||
gstreamer_refs = ActorRegistry.get_by_class(GStreamer)
|
||||
assert len(gstreamer_refs) == 1, 'Expected exactly one running gstreamer.'
|
||||
assert len(gstreamer_refs) == 1, \
|
||||
'Expected exactly one running gstreamer.'
|
||||
self.gstreamer = gstreamer_refs[0].proxy()
|
||||
|
||||
backend_refs = ActorRegistry.get_by_class(Backend)
|
||||
@ -57,14 +60,19 @@ class SpotifySessionManager(BaseThread, PyspotifySessionManager):
|
||||
if error:
|
||||
logger.error(u'Spotify login error: %s', error)
|
||||
return
|
||||
|
||||
logger.info(u'Connected to Spotify')
|
||||
self.session = session
|
||||
|
||||
logger.debug(u'Preferred Spotify bitrate is %s kbps.', settings.SPOTIFY_BITRATE)
|
||||
logger.debug(u'Preferred Spotify bitrate is %s kbps',
|
||||
settings.SPOTIFY_BITRATE)
|
||||
self.session.set_preferred_bitrate(BITRATES[settings.SPOTIFY_BITRATE])
|
||||
|
||||
self.container_manager = SpotifyContainerManager(self)
|
||||
self.playlist_manager = SpotifyPlaylistManager(self)
|
||||
|
||||
self.container_manager.watch(self.session.playlist_container())
|
||||
|
||||
self.connected.set()
|
||||
|
||||
def logged_out(self, session):
|
||||
@ -73,13 +81,12 @@ class SpotifySessionManager(BaseThread, PyspotifySessionManager):
|
||||
|
||||
def metadata_updated(self, session):
|
||||
"""Callback used by pyspotify"""
|
||||
logger.debug(u'Metadata updated')
|
||||
self.refresh_stored_playlists()
|
||||
logger.debug(u'Callback called: Metadata updated')
|
||||
|
||||
def connection_error(self, session, error):
|
||||
"""Callback used by pyspotify"""
|
||||
if error is None:
|
||||
logger.info(u'Spotify connection error resolved')
|
||||
logger.info(u'Spotify connection OK')
|
||||
else:
|
||||
logger.error(u'Spotify connection error: %s', error)
|
||||
self.backend.playback.pause()
|
||||
|
||||
Loading…
Reference in New Issue
Block a user