created wiki module. added some new methods in Track class. some minor debugging.

master
Abhinav Sarkar 2008-09-16 19:44:14 +00:00
parent 2b02a84b87
commit 7d25f64788
6 changed files with 178 additions and 80 deletions

View File

@ -169,8 +169,7 @@ class Album(LastfmBase):
name = data.findtext('artist'),
),
)
if a.id is None:
a._fillInfo()
a._fillInfo()
return a
@staticmethod

View File

@ -144,15 +144,10 @@ class Api(object):
limit = None):
return Tasteometer.compare(self, type1, type2, value1, value2, limit)
def getTrack(self, track, artist):
def getTrack(self, track, artist = None, mbid = None):
if isinstance(artist, Artist):
artist = artist.name
result = Track.search(self, track, artist)
try:
result[0]
except IndexError:
raise LastfmInvalidResourceError("'%s' by %s: no such track found" % (track, artist))
return result[0]
return Track.getInfo(self, artist, track, mbid)
def searchTrack(self,
track,
@ -209,6 +204,8 @@ class Api(object):
def _GetOpener(self, url):
opener = self._urllib.build_opener()
if self._urllib._opener is not None:
opener = self._urllib.build_opener(*self._urllib._opener.handlers)
opener.addheaders = self._request_headers.items()
return opener
@ -233,7 +230,9 @@ class Api(object):
if parameters is None:
return None
else:
return urllib.urlencode(dict([(k, self._Encode(v)) for k, v in parameters.items() if v is not None]))
keys = parameters.keys()
keys.sort()
return urllib.urlencode([(k, self._Encode(parameters[k])) for k in keys if parameters[k] is not None])
def _ReadUrlData(self, opener, url, data = None):
now = datetime.now()

View File

@ -37,8 +37,8 @@ class Artist(LastfmBase):
)
self.__similar = similar
self.__topTags = topTags
self.__bio = bio and Artist.Bio(
artist = self,
self.__bio = bio and Wiki(
subject = self,
published = bio.published,
summary = bio.summary,
content = bio.content
@ -324,7 +324,7 @@ class Artist(LastfmBase):
)
for t in data.findall('tags/tag')
]
self.__bio = Artist.Bio(
self.__bio = Wiki(
self,
published = datetime(*(time.strptime(
data.findtext('bio/published').strip(),
@ -341,8 +341,7 @@ class Artist(LastfmBase):
data = Artist._fetchData(api, artist, mbid)
a = Artist(api, name = data.findtext('name'))
if a.bio is None:
a._fillInfo()
a._fillInfo()
return a
@staticmethod
@ -371,41 +370,6 @@ class Artist(LastfmBase):
def __repr__(self):
return "<lastfm.Artist: %s>" % self.__name
class Bio(object):
"""A class representing the biography of an artist."""
def __init__(self,
artist,
published = None,
summary = None,
content = None):
self.__artist = artist
self.__published = published
self.__summary = summary
self.__content = content
@property
def artist(self):
"""artist for which the biography is"""
return self.__artist
@property
def published(self):
"""publication time of the biography"""
return self.__published
@property
def summary(self):
"""summary of the biography"""
return self.__summary
@property
def content(self):
"""content of the biography"""
return self.__content
def __repr__(self):
return "<lastfm.artist.Bio: for artist '%s'>" % self.__artist.name
from datetime import datetime
import time
@ -417,3 +381,4 @@ from stats import Stats
from tag import Tag
from track import Track
from user import User
from wiki import Wiki

View File

@ -74,7 +74,11 @@ class LastfmBase(object):
if cacheAttribute is None:
cacheAttribute = func(ob)
setattr(ob, attributeName, cacheAttribute)
return copy.copy(cacheAttribute)
try:
cp = copy.copy(cacheAttribute)
return cp
except LastfmError:
return cacheAttribute
return property(fget = wrapper, doc = func.__doc__)
@ -91,4 +95,5 @@ class LastfmBase(object):
return not self.__gt__(other)
import sys
import copy
import copy
from error import LastfmError

View File

@ -14,23 +14,30 @@ class Track(LastfmBase):
name = None,
mbid = None,
url = None,
duration = None,
streamable = None,
fullTrack = None,
artist = None,
album = None,
position = None,
image = None,
stats = None,
fullTrack = None,
playedOn = None,
lovedOn = None):
lovedOn = None,
wiki = None):
if not isinstance(api, Api):
raise LastfmInvalidParametersError("api reference must be supplied as an argument")
self.__api = api
self.__id = id
self.__name = name
self.__mbid = mbid
self.__url = url
self.__duration = duration
self.__streamable = streamable
self.__fullTrack = fullTrack
self.__artist = artist
self.__album = album
self.__position = position
self.__image = image
self.__stats = stats and Stats(
subject = self,
@ -39,10 +46,19 @@ class Track(LastfmBase):
rank = stats.rank,
listeners = stats.listeners,
)
self.__fullTrack = fullTrack
self.__playedOn = playedOn
self.__lovedOn = lovedOn
self.__tags = None
self.__wiki = wiki and Wiki(
subject = self,
published = wiki.published,
summary = wiki.summary,
content = wiki.content
)
@property
def id(self):
"""id of the track"""
return self.__id
@property
def name(self):
@ -58,12 +74,26 @@ class Track(LastfmBase):
def url(self):
"""url of the tracks's page"""
return self.__url
@property
def duration(self):
"""duration of the tracks's page"""
return self.__duration
@property
def streamable(self):
"""is the track streamable"""
if self.__streamable is None:
self._fillInfo()
return self.__streamable
@property
def fullTrack(self):
"""is the full track streamable"""
if self.__fullTrack is None:
self._fillInfo()
return self.__fullTrack
@property
def artist(self):
"""artist of the track"""
@ -72,8 +102,17 @@ class Track(LastfmBase):
@property
def album(self):
"""artist of the track"""
if self.__album is None:
self._fillInfo()
return self.__album
@property
def position(self):
"""position of the track"""
if self.__position is None:
self._fillInfo()
return self.__position
@property
def image(self):
"""image of the track's album cover"""
@ -84,11 +123,6 @@ class Track(LastfmBase):
"""stats of the track"""
return self.__stats
@property
def fullTrack(self):
"""is the full track streamable"""
return self.__fullTrack
@property
def playedOn(self):
"""datetime the track was last played"""
@ -98,6 +132,15 @@ class Track(LastfmBase):
def lovedOn(self):
"""datetime the track was marked 'loved'"""
return self.__lovedOn
@property
def wiki(self):
"""wiki of the track"""
if self.__wiki == "na":
return None
if self.__wiki is None:
self._fillInfo()
return self.__wiki
def __checkParams(self,
params,
@ -213,21 +256,19 @@ class Track(LastfmBase):
@LastfmBase.cachedProperty
def tags(self):
if self.__tags is None:
if not (self.artist and self.name):
raise LastfmInvalidParametersError("artist and track name have to be provided.")
params = {'method': 'track.getTags', 'artist': self.artist.name, 'track': self.name}
data = self.__api._fetchData(params, sign = True, session = True, no_cache = True).find('tags')
self.__tags = SafeList([
Tag(
self.__api,
name = t.findtext('name'),
url = t.findtext('url')
)
for t in data.findall('tag')
],
self.addTags, self.removeTag)
return self.__tags
if not (self.artist and self.name):
raise LastfmInvalidParametersError("artist and track name have to be provided.")
params = {'method': 'track.getTags', 'artist': self.artist.name, 'track': self.name}
data = self.__api._fetchData(params, sign = True, session = True, no_cache = True).find('tags')
return SafeList([
Tag(
self.__api,
name = t.findtext('name'),
url = t.findtext('url')
)
for t in data.findall('tag')
],
self.addTags, self.removeTag)
def addTags(self, tags):
while(len(tags) > 10):
@ -335,6 +376,80 @@ class Track(LastfmBase):
for t in gen2(data):
yield t
return gen()
@staticmethod
def _fetchData(api,
artist = None,
track = None,
mbid = None):
params = {'method': 'track.getInfo'}
if not ((artist and track) or mbid):
raise LastfmInvalidParametersError("either (artist and track) or mbid has to be given as argument.")
if artist and track:
params.update({'artist': artist, 'track': track})
elif mbid:
params.update({'mbid': mbid})
return api._fetchData(params).find('track')
def _fillInfo(self):
data = Track._fetchData(self.__api, self.artist.name, self.name)
self.__id = int(data.findtext('id'))
self.__mbid = data.findtext('mbid')
self.__url = data.findtext('url')
self.__duration = int(data.findtext('duration'))
self.__streamable = (data.findtext('streamable') == '1'),
self.__fullTrack = (data.find('streamable').attrib['fulltrack'] == '1'),
self.__image = dict([(i.get('size'), i.text) for i in data.findall('image')])
self.__stats = Stats(
subject = self,
listeners = int(data.findtext('listeners')),
playcount = int(data.findtext('playcount')),
)
self.__artist = Artist(
self.__api,
name = data.findtext('artist/name'),
mbid = data.findtext('artist/mbid'),
url = data.findtext('artist/url')
)
self.__album = Album(
self.__api,
artist = self.__artist,
name = data.findtext('album/title'),
mbid = data.findtext('album/mbid'),
url = data.findtext('album/url'),
image = dict([(i.get('size'), i.text) for i in data.findall('album/image')])
)
self.__position = int(data.find('album').attrib['position'])
if data.find('wiki') is not None:
self.__wiki = Wiki(
self,
published = datetime(*(time.strptime(
data.findtext('wiki/published').strip(),
'%a, %d %b %Y %H:%M:%S +0000'
)[0:6])),
summary = data.findtext('wiki/summary'),
content = data.findtext('wiki/content')
)
else:
self.__wiki = 'na'
@staticmethod
def getInfo(api,
artist = None,
track = None,
mbid = None):
data = Track._fetchData(api, artist, track, mbid)
t = Track(
api,
name = data.findtext('name'),
artist = Artist(
api,
name = data.findtext('artist/name'),
),
)
t._fillInfo()
return t
@staticmethod
def hashFunc(*args, **kwds):
@ -361,10 +476,15 @@ class Track(LastfmBase):
def __repr__(self):
return "<lastfm.Track: '%s' by %s>" % (self.name, self.artist.name)
import time
from datetime import datetime
from api import Api
from artist import Artist
from album import Album
from error import LastfmInvalidParametersError
from safelist import SafeList
from stats import Stats
from tag import Tag
from user import User
from user import User
from wiki import Wiki

View File

@ -590,7 +590,10 @@ class User(LastfmBase):
for page in xrange(2, totalPages+1):
params.update({'page': page})
data = self.__api._fetchData(params).find('albums')
try:
data = self.__api._fetchData(params).find('albums')
except LastfmError:
continue
for a in gen2(data):
yield a
return gen()
@ -633,7 +636,10 @@ class User(LastfmBase):
for page in xrange(2, totalPages+1):
params.update({'page': page})
data = self.__api._fetchData(params).find('artists')
try:
data = self.__api._fetchData(params).find('artists')
except LastfmError:
continue
for a in gen2(data):
yield a
return gen()
@ -683,7 +689,11 @@ class User(LastfmBase):
for page in xrange(2, totalPages+1):
params.update({'page': page})
data = self.__api._fetchData(params).find('tracks')
data = None
try:
data = self.__api._fetchData(params).find('tracks')
except LastfmError:
continue
for t in gen2(data):
yield t
return gen()