示例#1
0
    def infer_album_fields(self):
        """Make the some album fields equal across `self.items`
        """
        changes = {}

        if self.choice_flag == action.ASIS:
            # Taking metadata "as-is". Guess whether this album is VA.
            plur_albumartist, freq = util.plurality([i.albumartist or i.artist for i in self.items])
            if freq == len(self.items) or (freq > 1 and float(freq) / len(self.items) >= SINGLE_ARTIST_THRESH):
                # Single-artist album.
                changes["albumartist"] = plur_albumartist
                changes["comp"] = False
            else:
                # VA.
                changes["albumartist"] = VARIOUS_ARTISTS
                changes["comp"] = True

        elif self.choice_flag == action.APPLY:
            # Applying autotagged metadata. Just get AA from the first
            # item.
            if not self.items[0].albumartist:
                changes["albumartist"] = self.items[0].artist
            if not self.items[0].mb_albumartistid:
                changes["mb_albumartistid"] = self.items[0].mb_artistid

        # Apply new metadata.
        for item in self.items:
            item.update(changes)
示例#2
0
    def align_album_level_fields(self):
        """Make the some album fields equal across `self.items`
        """
        changes = {}

        if self.choice_flag == action.ASIS:
            # Taking metadata "as-is". Guess whether this album is VA.
            plur_albumartist, freq = util.plurality(
                [i.albumartist or i.artist for i in self.items])
            if freq == len(self.items) or \
                (freq > 1 and
                    float(freq) / len(self.items) >= SINGLE_ARTIST_THRESH):
                # Single-artist album.
                changes['albumartist'] = plur_albumartist
                changes['comp'] = False
            else:
                # VA.
                changes['albumartist'] = VARIOUS_ARTISTS
                changes['comp'] = True

        elif self.choice_flag == action.APPLY:
            # Applying autotagged metadata. Just get AA from the first
            # item.
            if not self.items[0].albumartist:
                changes['albumartist'] = self.items[0].artist
            if not self.items[0].mb_albumartistid:
                changes['mb_albumartistid'] = self.items[0].mb_artistid

        # Apply new metadata.
        for item in self.items:
            item.update(changes)
示例#3
0
def current_metadata(items):
    """Extract the likely current metadata for an album given a list of its
    items. Return two dictionaries:
     - The most common value for each field.
     - Whether each field's value was unanimous (values are booleans).
    """
    assert items  # Must be nonempty.

    likelies = {}
    consensus = {}
    fields = [
        "artist",
        "album",
        "albumartist",
        "year",
        "disctotal",
        "mb_albumid",
        "label",
        "catalognum",
        "country",
        "media",
        "albumdisambig",
    ]
    for field in fields:
        values = [item[field] for item in items if item]
        likelies[field], freq = plurality(values)
        consensus[field] = freq == len(values)

    # If there's an album artist consensus, use this for the artist.
    if consensus["albumartist"] and likelies["albumartist"]:
        likelies["artist"] = likelies["albumartist"]

    return likelies, consensus
示例#4
0
def _infer_album_fields(task):
    """Given an album and an associated import task, massage the
    album-level metadata. This ensures that the album artist is set
    and that the "compilation" flag is set automatically.
    """
    assert task.is_album
    assert task.items

    changes = {}

    if task.choice_flag == action.ASIS:
        # Taking metadata "as-is". Guess whether this album is VA.

        # Check for albumartist field:
        for item in task.items:
            if item is not None:
                first_item = item
                break
            else:
                assert False, "all items are None"
        if first_item.mb_albumartistid:
            changes['mb_albumartistid'] = first_item.mb_albumartistid
        if first_item.albumartist:
            changes['albumartist'] = first_item.albumartist
        else:
            # Guess if the album is not VA:
            plur_artist, freq = plurality([i.artist for i in task.items])
            if freq == len(task.items) or (freq > 1 and
                    float(freq) / len(task.items) >= SINGLE_ARTIST_THRESH):
                # Single-artist album.
                changes['albumartist'] = plur_artist
                changes['comp'] = False
            else:
                # VA.
                changes['albumartist'] = VARIOUS_ARTISTS
                changes['comp'] = True

    elif task.choice_flag == action.APPLY:
        # Applying autotagged metadata. Just get AA from the first
        # item.
        for item in task.items:
            if item is not None:
                first_item = item
                break
            else:
                assert False, "all items are None"
        if not first_item.albumartist:
            changes['albumartist'] = first_item.artist
        if not first_item.mb_albumartistid:
            changes['mb_albumartistid'] = first_item.mb_artistid

    else:
        assert False

    # Apply new metadata.
    for item in task.items:
        if item is not None:
            for k, v in changes.iteritems():
                setattr(item, k, v)
示例#5
0
文件: lastid.py 项目: navinpai/beets
def get_cur_artist(items):
    """Given a sequence of items, returns the current artist and
    artist ID that is most popular among the fingerprinted metadata
    for the tracks.
    """
    # Get "fingerprinted" artists for each track.
    artists = []
    artist_ids = []
    for item in items:
        last_data = match(item.path)
        if last_data:
            artists.append(last_data["artist"])
            if last_data["artist_mbid"]:
                artist_ids.append(last_data["artist_mbid"])

    # Vote on the most popular artist.
    artist, _ = plurality(artists)
    artist_id, _ = plurality(artist_ids)

    return artist, artist_id
示例#6
0
def get_cur_artist(items):
    """Given a sequence of items, returns the current artist and
    artist ID that is most popular among the fingerprinted metadata
    for the tracks.
    """
    # Get "fingerprinted" artists for each track.
    artists = []
    artist_ids = []
    for item in items:
        last_data = last_match(item.path)
        if last_data:
            artists.append(last_data['artist'])
            if last_data['artist_mbid']:
                artist_ids.append(last_data['artist_mbid'])

    # Vote on the most popular artist.
    artist, _ = plurality(artists)
    artist_id, _ = plurality(artist_ids)

    return artist, artist_id
示例#7
0
def current_metadata(items):
    """Returns the most likely artist and album for a set of Items.
    Each is determined by tag reflected by the plurality of the Items.
    """
    keys = 'artist', 'album'
    likelies = {}
    consensus = {}
    for key in keys:
        values = [getattr(item, key) for item in items if item]
        likelies[key], freq = plurality(values)
        consensus[key] = (freq == len(values))
    return likelies['artist'], likelies['album'], consensus['artist']
示例#8
0
文件: match.py 项目: nateroling/beets
def current_metadata(items):
    """Returns the most likely artist and album for a set of Items.
    Each is determined by tag reflected by the plurality of the Items.
    """
    keys = 'artist', 'album'
    likelies = {}
    consensus = {}
    for key in keys:
        values = [getattr(item, key) for item in items if item]
        likelies[key], freq = plurality(values)
        consensus[key] = (freq == len(values))
    return likelies['artist'], likelies['album'], consensus['artist']
示例#9
0
def _infer_album_fields(task):
    """Given an album and an associated import task, massage the
    album-level metadata. This ensures that the album artist is set
    and that the "compilation" flag is set automatically.
    """
    assert task.is_album
    assert task.items

    changes = {}

    if task.choice_flag == action.ASIS:
        # Taking metadata "as-is". Guess whether this album is VA.
        plur_albumartist, freq = util.plurality(
            [i.albumartist or i.artist for i in task.items])
        if freq == len(task.items) or (
                freq > 1
                and float(freq) / len(task.items) >= SINGLE_ARTIST_THRESH):
            # Single-artist album.
            changes['albumartist'] = plur_albumartist
            changes['comp'] = False
        else:
            # VA.
            changes['albumartist'] = VARIOUS_ARTISTS
            changes['comp'] = True

    elif task.choice_flag == action.APPLY:
        # Applying autotagged metadata. Just get AA from the first
        # item.
        for item in task.items:
            if item is not None:
                first_item = item
                break
        else:
            assert False, "all items are None"
        if not first_item.albumartist:
            changes['albumartist'] = first_item.artist
        if not first_item.mb_albumartistid:
            changes['mb_albumartistid'] = first_item.mb_artistid

    else:
        assert False

    # Apply new metadata.
    for item in task.items:
        if item is not None:
            for k, v in changes.iteritems():
                setattr(item, k, v)
示例#10
0
文件: match.py 项目: Lugoues/beets
def current_metadata(items):
    """Returns the most likely artist and album for a set of Items.
    Each is determined by tag reflected by the plurality of the Items.
    """
    likelies = {}
    consensus = {}
    for key in "artist", "album", "albumartist":
        values = [getattr(item, key) for item in items if item]
        likelies[key], freq = plurality(values)
        consensus[key] = freq == len(values)

    if consensus["albumartist"] and likelies["albumartist"]:
        artist = likelies["albumartist"]
    else:
        artist = likelies["artist"]

    return artist, likelies["album"], consensus["artist"]
示例#11
0
def current_metadata(items):
    """Extract the likely current metadata for an album given a list of its
    items. Return two dictionaries:
     - The most common value for each field.
     - Whether each field's value was unanimous (values are booleans).
    """
    assert items  # Must be nonempty.

    likelies = {}
    consensus = {}
    fields = ['artist', 'album', 'albumartist', 'year', 'disctotal',
              'mb_albumid', 'label', 'catalognum', 'country', 'media',
              'albumdisambig']
    for key in fields:
        values = [getattr(item, key) for item in items if item]
        likelies[key], freq = plurality(values)
        consensus[key] = (freq == len(values))

    # If there's an album artist consensus, use this for the artist.
    if consensus['albumartist'] and likelies['albumartist']:
        likelies['artist'] = likelies['albumartist']

    return likelies, consensus
示例#12
0
def current_metadata(items):
    """Extract the likely current metadata for an album given a list of its
    items. Return two dictionaries:
     - The most common value for each field.
     - Whether each field's value was unanimous (values are booleans).
    """
    assert items  # Must be nonempty.

    likelies = {}
    consensus = {}
    fields = ['artist', 'album', 'albumartist', 'year', 'disctotal',
              'mb_albumid', 'label', 'catalognum', 'country', 'media',
              'albumdisambig']
    for key in fields:
        values = [getattr(item, key) for item in items if item]
        likelies[key], freq = plurality(values)
        consensus[key] = (freq == len(values))

    # If there's an album artist consensus, use this for the artist.
    if consensus['albumartist'] and likelies['albumartist']:
        likelies['artist'] = likelies['albumartist']

    return likelies, consensus
示例#13
0
 def test_plurality_near_consensus(self):
     objs = [1, 1, 2, 1]
     obj, freq = plurality(objs)
     self.assertEqual(obj, 1)
     self.assertEqual(freq, 3)
示例#14
0
    def _get_genre(self, obj):
        """Get the genre string for an Album or Item object based on
        self.sources. Return a `(genre, source)` pair. The
        prioritization order is:
            - track (for Items only)
            - album
            - artist
            - original
            - fallback
            - None
        """

        # Shortcut to existing genre if not forcing.
        if not self.config['force'] and self._is_allowed(obj.genre):
            return obj.genre, 'keep'

        # Track genre (for Items only).
        if isinstance(obj, library.Item):
            if 'track' in self.sources:
                result = self.fetch_track_genre(obj)
                if result:
                    return result, 'track'

        # Album genre.
        if 'album' in self.sources:
            result = self.fetch_album_genre(obj)
            if result:
                return result, 'album'

        # Artist (or album artist) genre.
        if 'artist' in self.sources:
            result = None
            if isinstance(obj, library.Item):
                result = self.fetch_artist_genre(obj)
            elif obj.albumartist != 'Various Artists':
                result = self.fetch_album_artist_genre(obj)
            else:
                # For "Various Artists", pick the most popular track genre.
                item_genres = []
                for item in obj.items():
                    item_genre = None
                    if 'track' in self.sources:
                        item_genre = self.fetch_track_genre(item)
                    if not item_genre:
                        item_genre = self.fetch_artist_genre(item)
                    if item_genre:
                        item_genres.append(item_genre)
                if item_genres:
                    result, _ = plurality(item_genres)

            if result:
                return result, 'artist'

        # Filter the existing genre.
        if obj.genre:
            result = self._resolve_genres([obj.genre])
            if result:
                return result, 'original'

        # Fallback string.
        fallback = self.config['fallback'].get()
        if fallback:
            return fallback, 'fallback'

        return None, None
示例#15
0
    def _get_genre(self, obj):
        """Get the genre string for an Album or Item object based on
        self.sources. Return a `(genre, source)` pair. The
        prioritization order is:
            - track (for Items only)
            - album
            - artist
            - original
            - fallback
            - None
        """

        # Shortcut to existing genre if not forcing.
        if not self.config["force"] and self._is_allowed(obj.genre):
            return obj.genre, "keep"

        # Track genre (for Items only).
        if isinstance(obj, library.Item):
            if "track" in self.sources:
                result = self.fetch_track_genre(obj)
                if result:
                    return result, "track"

        # Album genre.
        if "album" in self.sources:
            result = self.fetch_album_genre(obj)
            if result:
                return result, "album"

        # Artist (or album artist) genre.
        if "artist" in self.sources:
            result = None
            if isinstance(obj, library.Item):
                result = self.fetch_artist_genre(obj)
            elif obj.albumartist != config["va_name"].as_str():
                result = self.fetch_album_artist_genre(obj)
            else:
                # For "Various Artists", pick the most popular track genre.
                item_genres = []
                for item in obj.items():
                    item_genre = None
                    if "track" in self.sources:
                        item_genre = self.fetch_track_genre(item)
                    if not item_genre:
                        item_genre = self.fetch_artist_genre(item)
                    if item_genre:
                        item_genres.append(item_genre)
                if item_genres:
                    result, _ = plurality(item_genres)

            if result:
                return result, "artist"

        # Filter the existing genre.
        if obj.genre:
            result = self._resolve_genres([obj.genre])
            if result:
                return result, "original"

        # Fallback string.
        fallback = self.config["fallback"].get()
        if fallback:
            return fallback, "fallback"

        return None, None
示例#16
0
 def test_plurality_conflict(self):
     objs = [1, 1, 2, 2, 3]
     obj, freq = plurality(objs)
     self.assertTrue(obj in (1, 2))
     self.assertEqual(freq, 2)
示例#17
0
 def test_plurality_empty_sequence_raises_error(self):
     with self.assertRaises(ValueError):
         plurality([])
示例#18
0
    def _get_genre(self, obj):
        """Get the genre string for an Album or Item object based on
        self.sources. Return a `(genre, source)` pair. The
        prioritization order is:
            - track (for Items only)
            - album
            - artist
            - original
            - fallback
            - None
        """
        # Shortcut to existing genre if not forcing.
        if not self.config['force'] and _is_allowed(obj.genre):
            return obj.genre, 'keep'

        # Track genre (for Items only).
        if isinstance(obj, library.Item):
            if 'track' in self.sources:
                result = fetch_track_genre(obj)
                if result:
                    return result, 'track'

        # Album genre.
        if 'album' in self.sources:
            result = fetch_album_genre(obj)
            if result:
                return result, 'album'

        # Artist (or album artist) genre.
        if 'artist' in self.sources:
            result = None
            if isinstance(obj, library.Item):
                result = fetch_artist_genre(obj)
            elif obj.albumartist != 'Various Artists':
                result = fetch_album_artist_genre(obj)
            else:
                # For "Various Artists", pick the most popular track genre.
                item_genres = []
                for item in obj.items():
                    item_genre = None
                    if 'track' in self.sources:
                        item_genre = fetch_track_genre(item)
                    if not item_genre:
                        item_genre = fetch_artist_genre(item)
                    if item_genre:
                        item_genres.append(item_genre)
                if item_genres:
                    result, _ = plurality(item_genres)

            if result:
                return result, 'artist'

        # Filter the existing genre.
        if obj.genre:
            result = _strings_to_genre([obj.genre])
            if result:
                return result, 'original'

        # Fallback string.
        fallback = self.config['fallback'].get()
        if fallback:
            return fallback, 'fallback'

        return None, None