def refresh(self): playlists = [] for playlist in self.backend.session.get_all_playlist_contents(): tracks = [] for track in playlist['tracks']: if not track['deleted']: tracks += self.backend.library.lookup('gmusic:track:' + track['trackId']) playlist = Playlist(uri='gmusic:playlist:' + playlist['id'], name=playlist['name'], tracks=tracks) playlists.append(playlist) for playlist in self.backend.session.get_all_playlists(): if playlist.get('type') == 'SHARED': tracks = [] tracklist = self.backend.session.get_shared_playlist_contents( playlist['shareToken']) for track in tracklist: tracks += self.backend.library.lookup('gmusic:track:' + track['trackId']) playlist = Playlist(uri='gmusic:playlist:' + playlist['id'], name=playlist['name'], tracks=tracks) playlists.append(playlist) self.playlists = playlists listener.BackendListener.send('playlists_loaded')
def test_with_new_name(self): tracks = [Track()] last_modified = datetime.datetime.utcnow() playlist = Playlist(uri="an uri", name="a name", tracks=tracks, last_modified=last_modified) new_playlist = playlist.copy(name="another name") self.assertEqual(new_playlist.uri, "an uri") self.assertEqual(new_playlist.name, "another name") self.assertEqual(list(new_playlist.tracks), tracks) self.assertEqual(new_playlist.last_modified, last_modified)
def test_with_new_uri(self): tracks = [Track()] last_modified = dt.datetime.now() playlist = Playlist(uri=u"an uri", name=u"a name", tracks=tracks, last_modified=last_modified) new_playlist = playlist.copy(uri=u"another uri") self.assertEqual(new_playlist.uri, u"another uri") self.assertEqual(new_playlist.name, u"a name") self.assertEqual(list(new_playlist.tracks), tracks) self.assertEqual(new_playlist.last_modified, last_modified)
def test_with_new_last_modified(self): tracks = [Track()] last_modified = datetime.datetime.utcnow() new_last_modified = last_modified + datetime.timedelta(1) playlist = Playlist(uri="an uri", name="a name", tracks=tracks, last_modified=last_modified) new_playlist = playlist.copy(last_modified=new_last_modified) self.assertEqual(new_playlist.uri, "an uri") self.assertEqual(new_playlist.name, "a name") self.assertEqual(list(new_playlist.tracks), tracks) self.assertEqual(new_playlist.last_modified, new_last_modified)
def test_with_new_uri(self): tracks = [Track()] last_modified = datetime.datetime.utcnow() playlist = Playlist( uri='an uri', name='a name', tracks=tracks, last_modified=last_modified) new_playlist = playlist.copy(uri='another uri') self.assertEqual(new_playlist.uri, 'another uri') self.assertEqual(new_playlist.name, 'a name') self.assertEqual(list(new_playlist.tracks), tracks) self.assertEqual(new_playlist.last_modified, last_modified)
def test_with_new_name(self): tracks = [Track()] last_modified = 1390942873000 playlist = Playlist( uri='an uri', name='a name', tracks=tracks, last_modified=last_modified) new_playlist = playlist.replace(name='another name') self.assertEqual(new_playlist.uri, 'an uri') self.assertEqual(new_playlist.name, 'another name') self.assertEqual(list(new_playlist.tracks), tracks) self.assertEqual(new_playlist.last_modified, last_modified)
def test_with_new_last_modified(self): tracks = [Track()] last_modified = 1390942873000 new_last_modified = last_modified + 1000 playlist = Playlist( uri='an uri', name='a name', tracks=tracks, last_modified=last_modified) new_playlist = playlist.copy(last_modified=new_last_modified) self.assertEqual(new_playlist.uri, 'an uri') self.assertEqual(new_playlist.name, 'a name') self.assertEqual(list(new_playlist.tracks), tracks) self.assertEqual(new_playlist.last_modified, new_last_modified)
def __init__(self, config, backend): super(InternetArchivePlaylistsProvider, self).__init__(backend) self._bookmarks = [] self._username = config[Extension.ext_name]['username'] self._playlist = Playlist( uri='%s://%s/bookmarks' % (Extension.ext_name, self._username), name='Internet Archive Bookmarks' ) self.playlists = [self._playlist]
def test_create_without_uri_scheme_uses_first_backend(self): playlist = Playlist() self.sp1.create.return_value.get.return_value = playlist result = self.core.playlists.create('foo') self.assertEqual(playlist, result) self.sp1.create.assert_called_once_with('foo') self.assertFalse(self.sp2.create.called)
def test_save_selects_the_dummy2_backend(self): playlist = Playlist(uri='dummy2:a') self.sp2.save.return_value.get.return_value = playlist result = self.core.playlists.save(playlist) self.assertEqual(playlist, result) self.assertFalse(self.sp1.save.called) self.sp2.save.assert_called_once_with(playlist)
def test_listplaylists_ignores_playlists_without_name(self): last_modified = 1390942873222 self.backend.playlists.set_dummy_playlists( [Playlist(name='', uri='dummy:', last_modified=last_modified)]) self.send_request('listplaylists') self.assertNotInResponse('playlist: ') self.assertInResponse('OK')
def test_listplaylists_replaces_newline_with_space(self): self.backend.playlists.set_dummy_playlists( [Playlist(name='a\n', uri='dummy:')]) self.send_request('listplaylists') self.assertInResponse('playlist: a ') self.assertNotInResponse('playlist: a\n') self.assertInResponse('OK')
def test_create_with_uri_scheme_selects_the_matching_backend(self): playlist = Playlist() self.sp2.create.return_value.get.return_value = playlist result = self.core.playlists.create('foo', uri_scheme='dummy2') self.assertEqual(playlist, result) self.assertFalse(self.sp1.create.called) self.sp2.create.assert_called_once_with('foo')
def setUp(self): # noqa: N802 self.plr1a = Ref.playlist(name="A", uri="dummy1:pl:a") self.plr1b = Ref.playlist(name="B", uri="dummy1:pl:b") self.plr2a = Ref.playlist(name="A", uri="dummy2:pl:a") self.plr2b = Ref.playlist(name="B", uri="dummy2:pl:b") self.pl1a = Playlist(name="A", tracks=[Track(uri="dummy1:t:a")]) self.pl1b = Playlist(name="B", tracks=[Track(uri="dummy1:t:b")]) self.pl2a = Playlist(name="A", tracks=[Track(uri="dummy2:t:a")]) self.pl2b = Playlist(name="B", tracks=[Track(uri="dummy2:t:b")]) self.sp1 = mock.Mock(spec=backend.PlaylistsProvider) self.sp1.as_list.return_value.get.return_value = [ self.plr1a, self.plr1b, ] self.sp1.lookup.return_value.get.side_effect = [self.pl1a, self.pl1b] self.sp2 = mock.Mock(spec=backend.PlaylistsProvider) self.sp2.as_list.return_value.get.return_value = [ self.plr2a, self.plr2b, ] self.sp2.lookup.return_value.get.side_effect = [self.pl2a, self.pl2b] self.backend1 = mock.Mock() self.backend1.actor_ref.actor_class.__name__ = "Backend1" self.backend1.uri_schemes.get.return_value = ["dummy1"] self.backend1.playlists = self.sp1 self.backend2 = mock.Mock() self.backend2.actor_ref.actor_class.__name__ = "Backend2" self.backend2.uri_schemes.get.return_value = ["dummy2"] self.backend2.playlists = self.sp2 # A backend without the optional playlists provider self.backend3 = mock.Mock() self.backend3.uri_schemes.get.return_value = ["dummy3"] self.backend3.has_playlists().get.return_value = False self.backend3.playlists = None self.core = core.Core( mixer=None, backends=[self.backend3, self.backend1, self.backend2])
def test_create_without_uri_scheme_ignores_exception(self): playlist = Playlist() self.sp1.create.return_value.get.side_effect = Exception self.sp2.create.return_value.get.return_value = playlist result = self.core.playlists.create("foo") assert playlist == result self.sp1.create.assert_called_once_with("foo") self.sp2.create.assert_called_once_with("foo")
def create(self, name): ''' Creates a new playlist, adds to the local cache ''' playlist = self.backend.remote.create_playlist(name) self.refresh() return Playlist(uri='jellyfin:playlist:{}'.format(playlist.get('Id')), name=name, tracks=[])
def test_rename(self): self.backend.playlists.set_dummy_playlists([ Playlist(name="old_name", uri="dummy:a1", tracks=[Track(uri="b")]) ]) self.send_request('rename "old_name" "new_namé"') self.assertInResponse("OK") assert self.backend.playlists.lookup( "dummy:new_namé").get() is not None
def test_rename_save_fails(self): self.backend.playlists.set_dummy_playlists([ Playlist(name="old_name", uri="dummy:a1", tracks=[Track(uri="b")]) ]) self.backend.playlists.set_allow_save(False) self.send_request('rename "old_name" "new_name"') self.assertInResponse("ACK [0@0] {rename} Backend with " 'scheme "dummy" failed to save playlist')
def test_listplaylist(self): self.backend.playlists.playlists = [ Playlist(name='name', uri='dummy:name', tracks=[Track(uri='dummy:a')]) ] self.sendRequest('listplaylist "name"') self.assertInResponse('file: dummy:a') self.assertInResponse('OK')
def test_listplaylists(self, last_modified_mock): last_modified_mock.return_value = '2015-08-05T22:51:06Z' self.backend.playlists.set_dummy_playlists([ Playlist(name='a', uri='dummy:a')]) self.send_request('listplaylists') self.assertInResponse('playlist: a') # Date without milliseconds and with time zone information self.assertInResponse('Last-Modified: 2015-08-05T22:51:06Z') self.assertInResponse('OK')
def test_listplaylist_without_quotes(self): self.backend.playlists.set_dummy_playlists([ Playlist(name='name', uri='dummy:name', tracks=[Track(uri='dummy:a')]) ]) self.send_request('listplaylist name') self.assertInResponse('file: dummy:a') self.assertInResponse('OK')
def test_mpd_format(self): playlist = Playlist( tracks=[ Track(uri="foo", track_no=1), Track(uri="bàr", track_no=2), Track(uri="baz", track_no=3), ] ) result = translator.playlist_to_mpd_format(playlist) assert len(result) == 3
def test_create_without_uri_scheme_ignores_none_result(self): playlist = Playlist() self.sp1.create.return_value.get.return_value = None self.sp2.create.return_value.get.return_value = playlist result = self.core.playlists.create('foo') self.assertEqual(playlist, result) self.sp1.create.assert_called_once_with('foo') self.sp2.create.assert_called_once_with('foo')
def test_listplaylistinfo(self): self.backend.playlists.set_dummy_playlists([ Playlist( name='name', uri='dummy:name', tracks=[Track(uri='dummy:a')])]) self.send_request('listplaylistinfo "name"') self.assertInResponse('file: dummy:a') self.assertNotInResponse('Track: 0') self.assertNotInResponse('Pos: 0') self.assertInResponse('OK')
def test_create_without_uri_scheme_ignores_none_result(self): playlist = Playlist() self.sp1.create.return_value.get.return_value = None self.sp2.create.return_value.get.return_value = playlist result = self.core.playlists.create("foo") assert playlist == result self.sp1.create.assert_called_once_with("foo") self.sp2.create.assert_called_once_with("foo")
def get_playlists(self): con = sqlite3.connect(self.database_file) con.row_factory = sqlite3.Row q = """SELECT PlaylistID, Name FROM CorePlaylists""" playlists = [ Playlist(uri='banshee:playlist:%d' % int(row[b'PlaylistID']), name=row[b'Name']) for row in con.execute(q) ] con.close() return playlists
def test_lsinfo_for_root_includes_playlists(self): last_modified = 1390942873222 self.backend.playlists.set_dummy_playlists( [Playlist(name='a', uri='dummy:/a', last_modified=last_modified)]) self.send_request('lsinfo "/"') self.assertInResponse('playlist: a') # Date without milliseconds and with time zone information self.assertInResponse('Last-Modified: 2014-01-28T21:01:13Z') self.assertInResponse('OK')
def test_listplaylistinfo(self): self.backend.stored_playlists.playlists = [ Playlist(name='name', tracks=[Track(uri='file:///dev/urandom')]) ] self.sendRequest(u'listplaylistinfo "name"') self.assertInResponse(u'file: file:///dev/urandom') self.assertInResponse(u'Track: 0') self.assertNotInResponse(u'Pos: 0') self.assertInResponse(u'OK')
def test_serialize_with_tracks(self): track = Track(name='foo') self.assertDictEqual( { '__model__': 'Playlist', 'uri': 'uri', 'name': 'name', 'tracks': [track.serialize()] }, Playlist(uri='uri', name='name', tracks=[track]).serialize())
def test_create_with_unsupported_uri_scheme_uses_first_backend(self): playlist = Playlist() self.sp1.create().get.return_value = playlist self.sp1.reset_mock() result = self.core.playlists.create('foo', uri_scheme='dummy3') self.assertEqual(playlist, result) self.sp1.create.assert_called_once_with('foo') self.assertFalse(self.sp2.create.called)
def test_lsinfo_for_root_includes_playlists(self, last_modified_mock): last_modified_mock.return_value = "2015-08-05T22:51:06Z" self.backend.playlists.set_dummy_playlists( [Playlist(name="a", uri="dummy:/a")] ) self.send_request('lsinfo "/"') self.assertInResponse("playlist: a") self.assertInResponse("Last-Modified: 2015-08-05T22:51:06Z") self.assertInResponse("OK")
def test_listplaylists(self): last_modified = 1390942873222 self.backend.playlists.playlists = [ Playlist(name='a', uri='dummy:a', last_modified=last_modified)] self.sendRequest('listplaylists') self.assertInResponse('playlist: a') # Date without milliseconds and with time zone information self.assertInResponse('Last-Modified: 2014-01-28T21:01:13Z') self.assertInResponse('OK')
def test_listplaylistinfo_without_quotes(self): self.backend.playlists.playlists = [ Playlist( name='name', uri='dummy:name', tracks=[Track(uri='dummy:a')])] self.sendRequest('listplaylistinfo name') self.assertInResponse('file: dummy:a') self.assertInResponse('Track: 0') self.assertNotInResponse('Pos: 0') self.assertInResponse('OK')
def test_rename(self): self.backend.playlists.set_dummy_playlists([ Playlist(name='old_name', uri='dummy:a1', tracks=[Track(uri='b')]) ]) self.send_request('rename "old_name" "new_name"') self.assertInResponse('OK') self.assertIsNotNone( self.backend.playlists.lookup('dummy:new_name').get())
def to_mopidy_playlist(spotify_playlist): if spotify_playlist is None or spotify_playlist.type() != 'playlist': return uri = str(Link.from_playlist(spotify_playlist)) if not spotify_playlist.is_loaded(): return Playlist(uri=uri, name='[loading...]') name = spotify_playlist.name() if not name: # Other user's "starred" playlists isn't handled properly by pyspotify # See https://github.com/mopidy/pyspotify/issues/81 return if spotify_playlist.owner().canonical_name() != settings.SPOTIFY_USERNAME: name += ' by ' + spotify_playlist.owner().canonical_name() return Playlist( uri=uri, name=name, tracks=[ to_mopidy_track(spotify_track) for spotify_track in spotify_playlist if not spotify_track.is_local()])
def to_mopidy_playlist(cls, spotify_playlist): if not spotify_playlist.is_loaded(): return Playlist(name=u'[loading...]') # FIXME Replace this try-except with a check on the playlist type, # which is currently not supported by pyspotify, to avoid handling # playlist folder boundaries like normal playlists. try: return Playlist( uri=str(Link.from_playlist(spotify_playlist)), name=spotify_playlist.name(), # FIXME if check on link is a hackish workaround for is_local tracks=[ cls.to_mopidy_track(t) for t in spotify_playlist if str(Link.from_track(t, 0)) ], ) except SpotifyError, e: logger.info( u'Failed translating Spotify playlist ' '(probably a playlist folder boundary): %s', e)
def test_listplaylists(self): last_modified = datetime.datetime(2001, 3, 17, 13, 41, 17, 12345) self.backend.stored_playlists.playlists = [ Playlist(name='a', last_modified=last_modified) ] self.sendRequest(u'listplaylists') self.assertInResponse(u'playlist: a') # Date without microseconds and with time zone information self.assertInResponse(u'Last-Modified: 2001-03-17T13:41:17Z') self.assertInResponse(u'OK')
def test_lsinfo_with_empty_path_returns_same_as_for_root( self, last_modified_mock ): last_modified_mock.return_value = "2015-08-05T22:51:06Z" self.backend.playlists.set_dummy_playlists( [Playlist(name="a", uri="dummy:/a")] ) response1 = self.send_request('lsinfo ""') response2 = self.send_request('lsinfo "/"') assert response1 == response2
class InternetArchivePlaylistsProvider(backend.PlaylistsProvider): def __init__(self, config, backend): super(InternetArchivePlaylistsProvider, self).__init__(backend) self._bookmarks = [] self._username = config[Extension.ext_name]['username'] self._playlist = Playlist( uri='%s://%s/bookmarks' % (Extension.ext_name, self._username), name='Internet Archive Bookmarks' ) self.playlists = [self._playlist] def create(self, name): pass # TODO def delete(self, uri): pass # TODO def lookup(self, uri): for playlist in self.playlists: if playlist.uri == uri: return playlist return None def refresh(self): try: bookmarks = self.backend.client.bookmarks(self._username) logger.info('Loaded %d Internet Archive bookmarks', len(bookmarks)) if bookmarks == self._bookmarks: return # unchanged # FIXME: this can probably be removed when playlists return refs... tracks = self._tracks(bookmarks) logger.info('Loaded %d Internet Archive tracks', len(tracks)) self.playlists = [self._playlist.copy(tracks=tracks)] backend.BackendListener.send('playlists_loaded') self._bookmarks = bookmarks except Exception as e: logger.error('Error loading Internet Archive bookmarks: %s', e) def save(self, playlist): pass # TODO def _tracks(self, bookmarks): tracks = [] for doc in bookmarks: tracks.extend(self.backend.library._lookup(doc['identifier'])) return tracks
def test_copying_playlist(self): playlist = Playlist() self.compare(playlist, playlist.copy())
def test_uri(self): uri = 'an_uri' playlist = Playlist(uri=uri) self.assertEqual(playlist.uri, uri) with self.assertRaises(AttributeError): playlist.uri = None
def test_tracks(self): tracks = [Track(), Track(), Track()] playlist = Playlist(tracks=tracks) self.assertEqual(list(playlist.tracks), tracks) with self.assertRaises(AttributeError): playlist.tracks = None
def test_replace_playlist(self): playlist = Playlist() self.compare(playlist, playlist.replace())
def test_name(self): name = 'a name' playlist = Playlist(name=name) self.assertEqual(playlist.name, name) with self.assertRaises(AttributeError): playlist.name = None
def test_last_modified(self): last_modified = 1390942873000 playlist = Playlist(last_modified=last_modified) self.assertEqual(playlist.last_modified, last_modified) with self.assertRaises(AttributeError): playlist.last_modified = None