Exemple #1
0
def Tags(path, fileformat=None):
    """
    Loader for file metadata tags. Tag reading and writing for various
    file formats is implemented by tag formatter classes in module
    soundforest.tags.formats, initialized automatically by this class.
    """
    if not os.path.isfile(path):
        raise TagError('No such file: %s' % path)

    path = normalized(os.path.realpath(path))

    if fileformat is None:
        fileformat = AudioFileFormat(path)

    if not isinstance(fileformat, AudioFileFormat):
        raise TagError('File format must be AudioFileFormat instance')

    fileformat = fileformat
    if fileformat.is_metadata:
        raise TagError('Attempting to load audio tags from metadata file')

    if fileformat.codec is None:
        raise TagError('Unsupported audio file: %s' % path)

    tag_parser = fileformat.get_tag_parser()
    if tag_parser is None:
        return None

    return tag_parser(fileformat.codec, path)
Exemple #2
0
def Tags(path, fileformat=None):
    """
    Loader for file metadata tags. Tag reading and writing for various
    file formats is implemented by tag formatter classes in module
    soundforest.tags.formats, initialized automatically by this class.
    """
    if not os.path.isfile(path):
        raise TagError('No such file: {0}'.format(path))

    path = normalized(os.path.realpath(path))

    if fileformat is None:
        fileformat = AudioFileFormat(path)

    if not isinstance(fileformat, AudioFileFormat):
        raise TagError('File format must be AudioFileFormat instance')

    fileformat = fileformat
    if fileformat.is_metadata:
        raise TagError('Attempting to load audio tags from metadata file')

    if fileformat.codec is None:
        raise TagError('Unsupported audio file: {0}'.format(path))

    tag_parser = fileformat.get_tag_parser()
    if tag_parser is None:
        return None

    return tag_parser(fileformat.codec, path)
Exemple #3
0
    def append(self, path, position=None, recursive=False):
        path = normalized(os.path.realpath(path))
        if os.path.isfile(path):
            self.__insert(path, position)

        elif os.path.isdir(path):
            for f in ['%s' % os.path.join(path, x) for x in os.listdir(path)]:
                f = normalized(os.path.realpath(f))

                if not recursive and os.path.isdir(f):
                    continue

                self.append(f, position)

        else:
            raise PlaylistError('Not a file or directory: %s' % path)

        self.modified = True
Exemple #4
0
    def __init__(self, codec, path, tag_map=None):
        self.codec = codec
        self.path = normalized(os.path.realpath(path))
        self.tag_map = tag_map is not None and tag_map or {}
        self.entry = None
        self.modified = False

        self.albumart_obj = None
        self.supports_albumart = False
Exemple #5
0
    def append(self, path, position=None, recursive=False):
        path = normalized(os.path.realpath(path))
        if os.path.isfile(path):
            self.__insert(path, position)

        elif os.path.isdir(path):
            for f in ['%s' % os.path.join(path, x) for x in os.listdir(path)]:
                f = normalized(os.path.realpath(f))

                if not recursive and os.path.isdir(f):
                    continue

                self.append(f, position)

        else:
            raise PlaylistError('Not a file or directory: %s' % path)

        self.modified = True
Exemple #6
0
    def __init__(self, codec, path, tag_map=None):
        dict.__init__(self)
        self.codec = codec
        self.path = normalized(os.path.realpath(path))
        self.tag_map = tag_map is not None and tag_map or {}
        self.entry = None
        self.modified = False

        self.albumart_obj = None
        self.supports_albumart = False
Exemple #7
0
    def __init__(self, name, config=None, folder=None, unique=True):
        Playlist.__init__(self, name, unique)

        if os.path.isfile(name):
            path = os.path.realpath(name)

        else:
            if folder is not None:
                path = os.path.join(folder, '%s.m3u' % self.name)
            else:
                path = os.path.join('%s.m3u' % self.name)

        self.path = normalized(os.path.realpath(path))
        self.filename = os.path.basename(self.path)
        self.folder = os.path.dirname(self.path)
Exemple #8
0
    def __init__(self, name, config=None, folder=None, unique=True):
        Playlist.__init__(self, name, unique)

        if os.path.isfile(name):
            path = os.path.realpath(name)

        else:
            if folder is not None:
                path = os.path.join(folder, '%s.m3u' % self.name)
            else:
                path = os.path.join('%s.m3u' % self.name)

        self.path = normalized(os.path.realpath(path))
        self.filename = os.path.basename(self.path)
        self.folder = os.path.dirname(self.path)
Exemple #9
0
    def read(self):
        if not self.exists:
            return

        try:
            with open(self.path, 'r') as lines:
                self.__delslice__(0, list.__len__(self))
                for l in lines:
                    l = l.strip()
                    if l.startswith('#'):
                        continue

                    filepath = normalized(os.path.realpath(l))
                    if not os.path.isfile(filepath):
                        continue

                    if self.unique and self.count(filepath)>0:
                        continue

                    self.append(filepath)
        except IOError, (ecode, emsg):
            raise PlaylistError('Error reading %s: %s' % (self.path, emsg))
Exemple #10
0
    def read(self):
        if not self.exists:
            return

        try:
            with open(self.path, 'r') as lines:
                self.__delslice__(0, list.__len__(self))
                for l in lines:
                    l = l.strip()
                    if l.startswith('#'):
                        continue

                    filepath = normalized(os.path.realpath(l))
                    if not os.path.isfile(filepath):
                        continue

                    if self.unique and self.count(filepath) > 0:
                        continue

                    self.append(filepath)
        except IOError, (ecode, emsg):
            raise PlaylistError('Error reading %s: %s' % (self.path, emsg))
Exemple #11
0
 def realpaths(self):
     return dict((normalized(os.path.realpath(v)), True) for v in self.paths.keys())
Exemple #12
0
 def directories(self):
     return set(normalized(os.path.dirname(x)) for x in self.paths.keys())
Exemple #13
0
 def __init__(self, path):
     if isinstance(path, unicode):
         unicode.__init__(self, normalized(path).encode('utf-8'))
     else:
         unicode.__init__(self, normalized(path))
Exemple #14
0
    def songinfo(self, track=None, xml_output=False, export_albumart=False):
        """Current playing track info

        Return current playing track information as XML or None if no
        track was selected.
        """

        try:
            if self.client.status in ('stopped', 'paused'):
                return None

            if not track:
                track = self.client.current_track

            started = time.mktime(time.localtime()) - self.client.player_position()
            info = {
                'path': track.path,
                'started': time.strftime('%Y-%m-%d %H:%M:%S', time.localtime(started)),
                'album_artist':  track.album_artist,
                'artist':  track.artist,
                'album': track.album,
                'name': track.name,
                'comment': track.comment,
                'genre': track.genre,
                'length': track.time,
                'track_number': track.track_number,
                'track_count': track.track_count,
            }

            if track.year != 0:
                info['year'] = track.year

            albumart = os.path.join(os.path.dirname(normalized(track.path)), 'artwork.jpg')
            if os.path.isfile(albumart):
                info['artwork'] = os.path.realpath(albumart)

            if not self.xml_output and not xml_output:
                return info

            xml = E(
                'itunes',
                persistent_ID=track.persistent_ID,
                started=info['started']
            )

            for k in INFO_KEY_ORDER:
                # Skip node attributes
                if k in ['started']:
                    continue

                # Optional fields
                if k not in info:
                    continue

                # Don't export empty fields
                if info[k] is '':
                    continue

                v = info[k]
                try:
                    if isinstance(v, int):
                        if v == 0:
                            continue
                        xml.append(E(k, '{0:d}'.format(v)))
                    elif isinstance(v, float):
                        if v == 0:
                            continue
                        xml.append(E(k, '{0:3.2f}'.format(v)))
                    elif v != '':
                        xml.append(E(k, v))

                except ValueError:
                    print('ERROR encoding key {0} type {1}: {2}'.format(k, type(v), v))

            for k in sorted(track.keys()):
                v = track[k]
                if k in INFO_KEY_ORDER or k in IGNORE_TRACK_FIELDS:
                    continue

                try:
                    if isinstance(v, int):
                        if v == 0:
                            continue
                        xml.append(E(k, '{0:d}'.format(v)))
                    elif isinstance(v, float):
                        if v == 0:
                            continue
                        xml.append(E(k, '{0:3.2f}'.format(v)))
                    else:
                        if v == '':
                            continue
                        xml.append(E(k, v))

                except TypeError:
                    print('ERROR encoding key {0} type {1}: {2}'.format(k, type(v), v))

                except ValueError:
                    print('ERROR encoding key {0} type {1}: {2}'.format(k, type(v), v))

            if (self.export_albumart or export_albumart) and albumart:
                xml.append(E(
                    'albumart',
                    base64.b64encode(open(albumart, 'r').read()),
                    filename=os.path.basename(albumart)
                ))

            return xml

        except iTunesError:
            self.client = None
            return None