From c4cb47df6c390c85f9bf0c4129aa3a585a522a30 Mon Sep 17 00:00:00 2001 From: Stein Magnus Jodal Date: Mon, 8 Feb 2010 12:11:34 +0100 Subject: [PATCH] Move Backend API docs from docs/ to docstrings --- docs/api/backends.rst | 317 +----------------------------------- mopidy/backends/__init__.py | 237 +++++++++++++++++++++++++-- 2 files changed, 224 insertions(+), 330 deletions(-) diff --git a/docs/api/backends.rst b/docs/api/backends.rst index fe5a96e7..56d6f059 100644 --- a/docs/api/backends.rst +++ b/docs/api/backends.rst @@ -2,318 +2,7 @@ :mod:`mopidy.backends` -- Backend API ************************************* -.. warning:: - This is our *planned* backend API, and not the current API. - -.. module:: mopidy.backends +.. automodule:: mopidy.backends :synopsis: Interface between Mopidy and its various backends. - -.. class:: BaseBackend() - - .. attribute:: current_playlist - - The current playlist controller. An instance of - :class:`BaseCurrentPlaylistController`. - - .. attribute:: library - - The library controller. An instance of :class:`BaseLibraryController`. - - .. attribute:: playback - - The playback controller. An instance of :class:`BasePlaybackController`. - - .. attribute:: stored_playlists - - The stored playlists controller. An instance of - :class:`BaseStoredPlaylistsController`. - - .. attribute:: uri_handlers - - List of URI prefixes this backend can handle. - - -.. class:: BaseCurrentPlaylistController(backend) - - :param backend: backend the controller is a part of - :type backend: :class:`BaseBackend` - - .. method:: add(track, at_position=None) - - Add the track to the end of, or at the given position in the current - playlist. - - :param track: track to add - :type track: :class:`mopidy.models.Track` - :param at_position: position in current playlist to add track - :type at_position: int or :class:`None` - - .. method:: clear() - - Clear the current playlist. - - .. method:: get_by_id(id) - - Get track by ID. Raises :class:`KeyError` if not found. - - :param id: track ID - :type id: int - - .. method:: get_by_uri(uri) - - Get track by URI. Raises :class:`KeyError` if not found. - - :param uri: track URI - :type uri: string - - .. method:: load(playlist) - - Replace the current playlist with the given playlist. - - :param playlist: playlist to load - :type playlist: :class:`mopidy.models.Playlist` - - .. method:: move(start, end, to_position) - - Move the tracks in the slice ``[start:end]`` to ``to_position``. - - :param start: position of first track to move - :type start: int - :param end: position after last track to move - :type end: int - :param to_position: new position for the tracks - :type to_position: int - - .. attribute:: playlist - - The currently loaded :class:`mopidy.models.Playlist`. - - .. method:: remove(track) - - Remove the track from the current playlist. - - :param track: track to remove - :type track: :class:`mopidy.models.Track` - - .. method:: shuffle(start=None, end=None) - - Shuffles the entire playlist. If ``start`` and ``end`` is given only - shuffles the slice ``[start:end]``. - - :param start: position of first track to shuffle - :type start: int or :class:`None` - :param end: position after last track to shuffle - :type end: int or :class:`None` - - .. attribute:: version - - The current playlist version. Integer which is increased every time the - current playlist is changed. - - -.. class:: BasePlaybackController(backend) - - :param backend: backend the controller is a part of - :type backend: :class:`BaseBackend` - - .. attribute:: consume - - :class:`True` - Tracks are removed from the playlist when they have been played. - :class:`False` - Tracks are not removed from the playlist. - - .. attribute:: current_track - - The currently playing or selected :class:`mopidy.models.Track`. - - .. method:: new_playlist_loaded_callback() - - Tell the playback controller that a new playlist has been loaded. - - .. method:: next() - - Play the next track. - - .. method:: pause() - - Pause playblack. - - .. attribute:: PAUSED - - Constant representing the paused state. - - .. method:: play(track=None) - - Play the given track or the currently active track. - - :param track: track to play - :type track: :class:`mopidy.models.Track` or :class:`None` - - .. attribute:: PLAYING - - Constant representing the playing state. - - .. attribute:: playlist_position - - The position in the current playlist. - - .. method:: previous() - - Play the previous track. - - .. attribute:: random - - :class:`True` - Tracks are selected at random from the playlist. - :class:`False` - Tracks are played in the order of the playlist. - - .. attribute:: repeat - - :class:`True` - The current track is played repeatedly. - :class:`False` - The current track is played once. - - .. method:: resume() - - If paused, resume playing the current track. - - .. method:: seek(time_position) - - Seeks to time position given in milliseconds. - - :param time_position: time position in milliseconds - :type time_position: int - - .. attribute:: state - - The playback state. Must be :attr:`PLAYING`, :attr:`PAUSED`, or - :attr:`STOPPED`. - - .. method:: stop() - - Stop playing. - - .. attribute:: STOPPED - - Constant representing the stopped state. - - .. attribute:: time_position - - Time position in milliseconds. - - .. attribute:: volume - - The audio volume as an int in the range [0, 100]. :class:`None` if - unknown. - - -.. class:: BaseLibraryController(backend) - - :param backend: backend the controller is a part of - :type backend: :class:`BaseBackend` - - .. method:: find_exact(type, query) - - Find tracks in the library where ``type`` matches ``query`` exactly. - - :param type: 'title', 'artist', or 'album' - :type type: string - :param query: the search query - :type query: string - :rtype: list of :class:`mopidy.models.Track` - - .. method:: lookup(uri) - - Lookup track with given URI. - - :param uri: track URI - :type uri: string - :rtype: :class:`mopidy.models.Track` - - .. method:: refresh(uri=None) - - Refresh library. Limit to URI and below if an URI is given. - - :param uri: directory or track URI - :type uri: string - - .. method:: search(type, query) - - Search the library for tracks where ``type`` contains ``query``. - - :param type: 'title', 'artist', 'album', or 'uri' - :type type: string - :param query: the search query - :type query: string - :rtype: list of :class:`mopidy.models.Track` - - -.. class:: BaseStoredPlaylistsController(backend) - - :param backend: backend the controller is a part of - :type backend: :class:`BaseBackend` - - .. method:: add(uri) - - Add existing playlist with the given URI. - - :param uri: URI of existing playlist - :type uri: string - - .. method:: create(name) - - Create a new playlist. - - :param name: name of the new playlist - :type name: string - :rtype: :class:`mopidy.models.Playlist` - - .. attribute:: playlists - - List of :class:`mopidy.models.Playlist`. - - .. method:: delete(playlist) - - Delete playlist. - - :param playlist: the playlist to delete - :type playlist: :class:`mopidy.models.Playlist` - - .. method:: lookup(uri) - - Lookup playlist with given URI. - - :param uri: playlist URI - :type uri: string - :rtype: :class:`mopidy.models.Playlist` - - .. method:: refresh() - - Refresh stored playlists. - - .. method:: rename(playlist, new_name) - - Rename playlist. - - :param playlist: the playlist - :type playlist: :class:`mopidy.models.Playlist` - :param new_name: the new name - :type new_name: string - - .. method:: save(playlist) - - Save the playlist. - - :param playlist: the playlist - :type playlist: :class:`mopidy.models.Playlist` - - .. method:: search(query) - - Search for playlists whose name contains ``query``. - - :param query: query to search for - :type query: string - :rtype: list of :class:`mopidy.models.Playlist` + :members: + :undoc-members: diff --git a/mopidy/backends/__init__.py b/mopidy/backends/__init__.py index 6f1ddd69..92e79000 100644 --- a/mopidy/backends/__init__.py +++ b/mopidy/backends/__init__.py @@ -8,21 +8,41 @@ from mopidy.models import Playlist logger = logging.getLogger('backends.base') class BaseBackend(object): + #: The current playlist controller. An instance of + #: :class:`BaseCurrentPlaylistController`. current_playlist = None + + #: The library controller. An instance of :class:`BaseLibraryController`. library = None + + #: The playback controller. An instance of :class:`BasePlaybackController`. playback = None + + #: The stored playlists controller. An instance of + #: :class:`BaseStoredPlaylistsController`. stored_playlists = None + + #: List of URI prefixes this backend can handle. uri_handlers = [] class BaseCurrentPlaylistController(object): + """ + :param backend: backend the controller is a part of + :type backend: :class:`BaseBackend` + """ + + #: The current playlist version. Integer which is increased every time the + #: current playlist is changed. + version = 0 + def __init__(self, backend): self.backend = backend - self.version = 0 self.playlist = Playlist() @property def playlist(self): + """The currently loaded :class:`mopidy.models.Playlist`.""" return copy(self._playlist) @playlist.setter @@ -30,14 +50,30 @@ class BaseCurrentPlaylistController(object): self._playlist = new_playlist self.version += 1 - def add(self, uri, at_position=None): + def add(self, track, at_position=None): + """ + Add the track to the end of, or at the given position in the current + playlist. + + :param track: track to add + :type track: :class:`mopidy.models.Track` + :param at_position: position in current playlist to add track + :type at_position: int or :class:`None` + """ raise NotImplementedError def clear(self): + """Clear the current playlist.""" self.backend.playback.stop() self.playlist = Playlist() def get_by_id(self, id): + """ + Get track by ID. Raises :class:`KeyError` if not found. + + :param id: track ID + :type id: int + """ matches = filter(lambda t: t.id == id, self._playlist.tracks) if matches: return matches[0] @@ -45,6 +81,12 @@ class BaseCurrentPlaylistController(object): raise KeyError('Track with ID "%s" not found' % id) def get_by_uri(self, uri): + """ + Get track by URI. Raises :class:`KeyError` if not found. + + :param uri: track URI + :type uri: string + """ matches = filter(lambda t: t.uri == uri, self._playlist.tracks) if matches: return matches[0] @@ -52,70 +94,164 @@ class BaseCurrentPlaylistController(object): raise KeyError('Track with URI "%s" not found' % uri) def load(self, playlist): + """ + Replace the current playlist with the given playlist. + + :param playlist: playlist to load + :type playlist: :class:`mopidy.models.Playlist` + """ self.playlist = playlist self.version = 0 def move(self, start, end, to_position): + """ + Move the tracks in the slice ``[start:end]`` to ``to_position``. + + :param start: position of first track to move + :type start: int + :param end: position after last track to move + :type end: int + :param to_position: new position for the tracks + :type to_position: int + """ tracks = self.playlist.tracks new_tracks = tracks[:start] + tracks[end:] - for track in tracks[start:end]: new_tracks.insert(to_position, track) to_position += 1 - self.playlist = self.playlist.with_(tracks=new_tracks) - def remove(self, position): + def remove(self, track): + """ + Remove the track from the current playlist. + + :param track: track to remove + :type track: :class:`mopidy.models.Track` + """ tracks = self.playlist.tracks + position = tracks.index(track) del tracks[position] self.playlist = self.playlist.with_(tracks=tracks) def shuffle(self, start=None, end=None): - tracks = self.playlist.tracks + """ + Shuffles the entire playlist. If ``start`` and ``end`` is given only + shuffles the slice ``[start:end]``. + :param start: position of first track to shuffle + :type start: int or :class:`None` + :param end: position after last track to shuffle + :type end: int or :class:`None` + """ + tracks = self.playlist.tracks before = tracks[:start or 0] shuffled = tracks[start:end] after = tracks[end or len(tracks):] - random.shuffle(shuffled) - self.playlist = self.playlist.with_(tracks=before+shuffled+after) class BaseLibraryController(object): + """ + :param backend: backend the controller is a part of + :type backend: :class:`BaseBackend` + """ + def __init__(self, backend): self.backend = backend def find_exact(self, type, query): + """ + Find tracks in the library where ``type`` matches ``query`` exactly. + + :param type: 'title', 'artist', or 'album' + :type type: string + :param query: the search query + :type query: string + :rtype: list of :class:`mopidy.models.Track` + """ raise NotImplementedError def lookup(self, uri): + """ + Lookup track with given URI. + + :param uri: track URI + :type uri: string + :rtype: :class:`mopidy.models.Track` + """ raise NotImplementedError def refresh(self, uri=None): + """ + Refresh library. Limit to URI and below if an URI is given. + + :param uri: directory or track URI + :type uri: string + """ raise NotImplementedError def search(self, type, query): + """ + Search the library for tracks where ``type`` contains ``query``. + + :param type: 'title', 'artist', 'album', or 'uri' + :type type: string + :param query: the search query + :type query: string + :rtype: list of :class:`mopidy.models.Track` + """ raise NotImplementedError class BasePlaybackController(object): + """ + :param backend: backend the controller is a part of + :type backend: :class:`BaseBackend` + """ + + #: Constant representing the paused state. PAUSED = u'paused' + + #: Constant representing the playing state. PLAYING = u'playing' + + #: Constant representing the stopped state. STOPPED = u'stopped' + #: :class:`True` + #: Tracks are removed from the playlist when they have been played. + #: :class:`False` + #: Tracks are not removed from the playlist. + consume = False + + #: The currently playing or selected :class:`mopidy.models.Track`. + current_track = None + + #: :class:`True` + #: Tracks are selected at random from the playlist. + #: :class:`False` + #: Tracks are played in the order of the playlist. + random = False + + #: :class:`True` + #: The current track is played repeatedly. + #: :class:`False` + #: The current track is played once. + repeat = False + + #: The audio volume as an int in the range [0, 100]. :class:`None` if + #: unknown. + volume = None + def __init__(self, backend): self.backend = backend self._state = self.STOPPED - self.consume = False - self.current_track = None - self.random = False - self.repeat = False self.state = self.STOPPED - self.volume = None @property def playlist_position(self): + """The position in the current playlist.""" if self.current_track is None: return None try: @@ -126,6 +262,10 @@ class BasePlaybackController(object): @property def state(self): + """ + The playback state. Must be :attr:`PLAYING`, :attr:`PAUSED`, or + :attr:`STOPPED`. + """ return self._state @state.setter @@ -142,6 +282,7 @@ class BasePlaybackController(object): @property def time_position(self): + """Time position in milliseconds.""" if self.state == self.PLAYING: time_since_started = int(time.time()) - self._play_time_started return self._play_time_accumulated + time_since_started @@ -162,6 +303,7 @@ class BasePlaybackController(object): self._play_time_started = int(time.time()) def new_playlist_loaded_callback(self): + """Tell the playback controller that a new playlist has been loaded.""" self.current_track = None if self.state == self.PLAYING: if self.backend.current_playlist.playlist.length > 0: @@ -170,6 +312,7 @@ class BasePlaybackController(object): self.stop() def next(self): + """Play the next track.""" self.stop() if self._next(): self.state = self.PLAYING @@ -178,6 +321,7 @@ class BasePlaybackController(object): raise NotImplementedError def pause(self): + """Pause playback.""" if self.state == self.PLAYING and self._pause(): self.state = self.PAUSED @@ -185,6 +329,12 @@ class BasePlaybackController(object): raise NotImplementedError def play(self, track=None): + """ + Play the given track or the currently active track. + + :param track: track to play + :type track: :class:`mopidy.models.Track` or :class:`None` + """ if self.state == self.PAUSED and track is None: return self.resume() if track is not None: @@ -197,6 +347,7 @@ class BasePlaybackController(object): raise NotImplementedError def previous(self): + """Play the previous track.""" self.stop() if self._previous(): self.state = self.PLAYING @@ -205,6 +356,7 @@ class BasePlaybackController(object): raise NotImplementedError def resume(self): + """If paused, resume playing the current track.""" if self.state == self.PAUSED and self._resume(): self.state = self.PLAYING @@ -212,9 +364,16 @@ class BasePlaybackController(object): raise NotImplementedError def seek(self, time_position): + """ + Seeks to time position given in milliseconds. + + :param time_position: time position in milliseconds + :type time_position: int + """ raise NotImplementedError def stop(self): + """Stop playing.""" if self.state != self.STOPPED and self._stop(): self.state = self.STOPPED @@ -223,34 +382,80 @@ class BasePlaybackController(object): class BaseStoredPlaylistsController(object): + """ + :param backend: backend the controller is a part of + :type backend: :class:`BaseBackend` + """ + def __init__(self, backend): self.backend = backend self._playlists = [] @property def playlists(self): + """List of :class:`mopidy.models.Playlist`.""" return copy(self._playlists) - def add(self, uri): - raise NotImplementedError - def create(self, name): + """ + Create a new playlist. + + :param name: name of the new playlist + :type name: string + :rtype: :class:`mopidy.models.Playlist` + """ raise NotImplementedError def delete(self, playlist): + """ + Delete playlist. + + :param playlist: the playlist to delete + :type playlist: :class:`mopidy.models.Playlist` + """ raise NotImplementedError def lookup(self, uri): + """ + Lookup playlist with given URI in both the set of stored playlists and + in any other playlist sources. + + :param uri: playlist URI + :type uri: string + :rtype: :class:`mopidy.models.Playlist` + """ raise NotImplementedError def refresh(self): + """Refresh stored playlists.""" raise NotImplementedError def rename(self, playlist, new_name): + """ + Rename playlist. + + :param playlist: the playlist + :type playlist: :class:`mopidy.models.Playlist` + :param new_name: the new name + :type new_name: string + """ raise NotImplementedError def save(self, playlist): + """ + Save the playlist to the set of stored playlists. + + :param playlist: the playlist + :type playlist: :class:`mopidy.models.Playlist` + """ raise NotImplementedError def search(self, query): + """ + Search for playlists whose name contains ``query``. + + :param query: query to search for + :type query: string + :rtype: list of :class:`mopidy.models.Playlist` + """ return filter(lambda p: query in p.name, self._playlists)