further refactoring: abstract source from matching logic

--HG--
rename : beets/autotag/model.py => beets/autotag/hooks.py
This commit is contained in:
Adrian Sampson 2011-10-10 21:31:47 -07:00
parent ee78391f4f
commit 064a0432f1
4 changed files with 34 additions and 20 deletions

View file

@ -18,15 +18,16 @@ import os
from beets import library, mediafile
from beets.util import sorted_walk
from . import mb
# Parts of external interface.
from .model import AlbumInfo, TrackInfo
from .hooks import AlbumInfo, TrackInfo
from .match import tag_item, tag_album
from .match import RECOMMEND_STRONG, RECOMMEND_MEDIUM, RECOMMEND_NONE
from .match import STRONG_REC_THRESH, MEDIUM_REC_THRESH, REC_GAP_THRESH
# Main interface.
# Additional utilities for the main interface.
def albums_in_dir(path):
"""Recursively searches the given directory and returns an iterable

View file

@ -12,7 +12,11 @@
# The above copyright notice and this permission notice shall be
# included in all copies or substantial portions of the Software.
"""Classes used by metadata sources and the matching logic."""
"""Glue between metadata sources and the matching logic."""
from . import mb
# Classes used to represent candidate options.
class AlbumInfo(object):
"""Describes a canonical release that may be used to match a release
@ -68,3 +72,18 @@ class TrackInfo(object):
self.artist = artist
self.artist_id = artist
self.length = length
# Aggregation of sources.
def _album_for_id(album_id):
return mb.album_for_id(album_id)
def _match_album(artist, album, tracks):
return mb.match_album(artist, album, tracks)
def _track_for_id(track_id):
return mb.track_for_id(track_id)
def _match_track(artist, title):
return mb.match_track(artist, title)

View file

@ -20,9 +20,9 @@ import re
from munkres import Munkres
from unidecode import unidecode
from beets.autotag import mb
from beets import plugins
from beets.util import levenshtein, plurality
from beets.autotag import hooks
# Distance parameters.
# Text distance weights: proportions on the normalized intuitive edit
@ -64,12 +64,6 @@ SD_REPLACE = [
(r'&', 'and'),
]
# Try 5 releases. In the future, this should be more dynamic: let the
# probability of continuing to the next release be inversely
# proportional to how good our current best is and how long we've
# already taken.
MAX_CANDIDATES = 5
# Recommendation constants.
RECOMMEND_STRONG = 'RECOMMEND_STRONG'
RECOMMEND_MEDIUM = 'RECOMMEND_MEDIUM'
@ -304,7 +298,7 @@ def match_by_id(items):
if bool(reduce(lambda x,y: x if x==y else (), albumids)):
albumid = albumids[0]
log.debug('Searching for discovered album ID: ' + albumid)
return mb.album_for_id(albumid)
return hooks._album_for_id(albumid)
else:
log.debug('No album ID consensus.')
return None
@ -398,7 +392,7 @@ def tag_album(items, timid=False, search_artist=None, search_album=None,
# Try to find album indicated by MusicBrainz IDs.
if search_id:
log.debug('Searching for album ID: ' + search_id)
id_info = mb.album_for_id(search_id)
id_info = hooks._album_for_id(search_id)
else:
id_info = match_by_id(items)
if id_info:
@ -428,8 +422,8 @@ def tag_album(items, timid=False, search_artist=None, search_album=None,
# Get candidate metadata from search.
if search_artist and search_album:
candidates = mb.match_album(search_artist, search_album,
len(items), MAX_CANDIDATES)
candidates = hooks._match_album(search_artist, search_album,
len(items))
candidates = list(candidates)
else:
candidates = []
@ -439,8 +433,7 @@ def tag_album(items, timid=False, search_artist=None, search_album=None,
(search_artist.lower() in VA_ARTISTS) or \
any(item.comp for item in items)):
log.debug(u'Possibly Various Artists; adding matches.')
candidates.extend(mb.match_album(None, search_album, len(items),
MAX_CANDIDATES))
candidates.extend(hooks._match_album(None, search_album, len(items)))
# Get candidates from plugins.
candidates.extend(plugins.candidates(items))
@ -471,7 +464,7 @@ def tag_item(item, timid=False, search_artist=None, search_title=None,
trackid = search_id or item.mb_trackid
if trackid:
log.debug('Searching for track ID: ' + trackid)
track_info = mb.track_for_id(trackid)
track_info = hooks._track_for_id(trackid)
if track_info:
dist = track_distance(item, track_info, incl_artist=True)
candidates.append((dist, track_info))
@ -494,7 +487,7 @@ def tag_item(item, timid=False, search_artist=None, search_title=None,
log.debug(u'Item search terms: %s - %s' % (search_artist, search_title))
# Candidate metadata from search.
for track_info in mb.match_track(search_artist, search_title):
for track_info in hooks._match_track(search_artist, search_title):
dist = track_distance(item, track_info, incl_artist=True)
candidates.append((dist, track_info))

View file

@ -30,9 +30,10 @@ from musicbrainz2.model import Release
from threading import Lock
from musicbrainz2.model import VARIOUS_ARTISTS_ID
SEARCH_LIMIT = 10
SEARCH_LIMIT = 5
VARIOUS_ARTISTS_ID = VARIOUS_ARTISTS_ID.rsplit('/', 1)[1]
class ServerBusyError(Exception): pass
class BadResponseError(Exception): pass
@ -298,7 +299,7 @@ def match_album(artist, album, tracks=None, limit=SEARCH_LIMIT):
criteria['tracks'] = str(tracks)
# Search for the release.
return find_releases(criteria)
return find_releases(criteria, limit)
def match_track(artist, title):
"""Searches for a single track and returns an iterable of track