Cover Art Archive support (GC-71)

This commit is contained in:
Adrian Sampson 2012-06-24 16:57:04 -07:00
parent d97f13a899
commit d807b3fbf1
4 changed files with 44 additions and 6 deletions

View file

@ -50,13 +50,25 @@ def _fetch_image(url):
log.debug('Not an image.')
# Cover Art Archive.
CAA_URL = 'http://coverartarchive.org/release/{mbid}/front-500'
def caa_art(release_id):
"""Fetch album art from the Cover Art Archive given a MusicBrainz
release ID.
"""
url = CAA_URL.format(mbid=release_id)
return _fetch_image(url)
# Art from Amazon.
AMAZON_URL = 'http://images.amazon.com/images/P/%s.%02i.LZZZZZZZ.jpg'
AMAZON_INDICES = (1, 2)
def art_for_asin(asin):
"""Fetches art for an Amazon ID (ASIN) string."""
"""Fetch art for an Amazon ID (ASIN) string."""
for index in AMAZON_INDICES:
# Fetch the image.
url = AMAZON_URL % (asin, index)
@ -71,6 +83,7 @@ AAO_URL = 'http://www.albumart.org/index_detail.php'
AAO_PAT = r'href\s*=\s*"([^>"]*)"[^>]*title\s*=\s*"View larger image"'
def aao_art(asin):
"""Fetch art from AlbumArt.org."""
# Get the page from albumart.org.
url = '%s?%s' % (AAO_URL, urllib.urlencode({'asin': asin}))
try:
@ -119,14 +132,20 @@ def art_in_path(path):
# Try each source in turn.
def art_for_album(album, path):
"""Given an album info dictionary from MusicBrainz, returns a path
to downloaded art for the album (or None if no art is found).
"""Given an AlbumInfo object, returns a path to downloaded art for
the album (or None if no art is found).
"""
if isinstance(path, basestring):
out = art_in_path(path)
if out:
return out
if album.album_id:
log.debug('Fetching album art for MBID {0}.'.format(album.album_id))
out = caa_art(album.album_id)
if out:
return out
if album.asin:
log.debug('Fetching album art for ASIN %s.' % album.asin)
out = art_for_asin(album.asin)

View file

@ -16,6 +16,11 @@ art for your music, enable this plugin after upgrading to beets 1.0b15.
Thanks to Fabrice Laporte.
* Album cover art fetching is now encapsulated in the :doc:`/plugins/fetchart`.
Be sure to enable this plugin if you're using this functionality.
* :doc:`/plugins/fetchart`: Cover art can now be fetched from the `Cover Art
Archive`_, a new image repository from MusicBrainz and the Internet Archive.
While its coverage is currently spotty, CAA is growing and its images are
generally higher-quality than those from Amazon. You can help out by
`submitting new images to the archive`_.
* Errors when communicating with MusicBrainz now log an error message instead of
halting the importer.
* Similarly, filesystem manipulation errors now print helpful error messages
@ -70,7 +75,10 @@ art for your music, enable this plugin after upgrading to beets 1.0b15.
already at its destination.
* Use a nicer error message when input requested but stdin is closed.
.. _submitting new images to the archive:
http://musicbrainz.org/doc/How_to_Add_Cover_Art
.. _artist credits: http://wiki.musicbrainz.org/Artist_Credit
.. _Cover Art Archive: http://coverartarchive.org/
1.0b14 (May 12, 2012)
---------------------

View file

@ -18,10 +18,12 @@ the :ref:`art-filename` config option.
Album Art Sources
-----------------
Currently, this plugin searches for art in the local filesystem, on Amazon.com,
and on AlbumArt.org (in that order).
Currently, this plugin searches for art in the local filesystem, on the `Cover
Art Archive`_, on Amazon, and on AlbumArt.org (in that order).
When looking for local album art, beets looks for image files located in the
.. _Cover Art Archive: http://coverartarchive.org/
When looking for local album art, beets checks for image files located in the
same folder as the music files you're importing. If you have an image file
called "cover," "front," "art," "album," for "folder" alongside your music,
beets will treat it as album art and skip searching any online databases.

View file

@ -85,6 +85,7 @@ class CombinedTest(unittest.TestCase):
def _urlopen(self, url):
self.urlopen_called = True
self.fetched_url = url
return StringIO.StringIO(self.page_text)
def test_main_interface_returns_amazon_art(self):
@ -130,6 +131,14 @@ class CombinedTest(unittest.TestCase):
fetchart.art_for_album(album, self.dpath)
self.assertTrue(self.urlopen_called)
def test_main_interface_uses_caa_when_mbid_available(self):
mock_retrieve = MockUrlRetrieve('anotherpath', 'image/jpeg')
fetchart.urllib.urlretrieve = mock_retrieve
album = AlbumInfo(None, 'releaseid', None, None, None, asin='xxxx')
artpath = fetchart.art_for_album(album, None)
self.assertEqual(artpath, 'anotherpath')
self.assertTrue('coverartarchive.org' in mock_retrieve.fetched)
class AAOTest(unittest.TestCase):
def setUp(self):
self.old_urlopen = fetchart.urllib.urlopen