From 9b238ba712677a18aa9c407a383f707264b0c77a Mon Sep 17 00:00:00 2001 From: Jason Mehring Date: Thu, 22 Aug 2013 02:47:41 -0400 Subject: [PATCH] Added Seasons. Show is the parent to Seasons and Episodes are the children if Season --- couchpotato/core/media/show/_base/main.py | 64 +++-- .../core/media/show/library/episode/main.py | 22 +- couchpotato/core/media/show/library/season/main.py | 56 ++--- couchpotato/core/media/show/library/show/main.py | 12 +- couchpotato/core/providers/show/thetvdb/main.py | 270 ++++++++++++++------- couchpotato/core/settings/model.py | 6 +- 6 files changed, 281 insertions(+), 149 deletions(-) diff --git a/couchpotato/core/media/show/_base/main.py b/couchpotato/core/media/show/_base/main.py index f9fb52a..d7e0985 100644 --- a/couchpotato/core/media/show/_base/main.py +++ b/couchpotato/core/media/show/_base/main.py @@ -50,7 +50,7 @@ class ShowBase(MediaBase): 'title': {'desc': 'Movie title to use for searches. Has to be one of the titles returned by movie.search.'}, } }) - + addEvent('show.add', self.add) def search(self, q = '', **kwargs): @@ -82,8 +82,8 @@ class ShowBase(MediaBase): 'added': True if movie_dict else False, 'movie': movie_dict, } - - def debug(self): + + def debug(self, identifier): """ XXX: This is only a hook for a breakpoint so we can test database stuff easily REMOVE when finished @@ -99,21 +99,21 @@ class ShowBase(MediaBase): import traceback db = get_session() - #parent = db.query(Library).filter_by(identifier = attrs.get('')).first() + parent = db.query(Library).filter_by(identifier = identifier).first() return - + def add(self, params = {}, force_readd = True, search_after = True, update_library = False, status_id = None): """ 1. Add Show 2. Add All Episodes 3. Add All Seasons - + Notes, not to forget: - relate parent and children, possible grandparent to grandchild so episodes know it belong to show, etc - looks like we dont send info to library; it comes later - change references to plot to description - change Model to Media - + params {'category_id': u'-1', 'identifier': u'tt1519931', @@ -122,27 +122,45 @@ class ShowBase(MediaBase): 'title': u'Haven'} """ log.debug("show.add") - + # Add show parent to db first parent = self.addToDatabase(params = params, type = 'show') - - skip = False # XXX: For debugging + identifier = params.get('id') - episodes = fireEvent('show.episodes', identifier = identifier) - - # XXX: Fix so we dont have a nested list - if episodes is not None and skip is False: - for episode in episodes[0]: - episode['title'] = episode.get('titles', None)[0] - episode['identifier'] = episode.get('id', None) - episode['parent_identifier'] = identifier - self.addToDatabase(params=episode, type = "episode") - + + # XXX: add seasons + # XXX: Fix so we dont have a nested list [0] (fireEvent) + try: + seasons = fireEvent('season.info', identifier = identifier)[0] + except: return None + if seasons is not None: + for season in seasons: + season['title'] = season.get('title', None) + season_id = season.get('id', None) + if season_id is None: continue + season['identifier'] = season_id + season['parent_identifier'] = identifier + self.addToDatabase(params=season, type = "season") + + # XXX: Fix so we dont have a nested list [0] (fireEvent) + try: + episodes = fireEvent('episode.info', identifier = identifier, season_identifier = season_id)[0] + except: continue + if episodes is not None: + for episode in episodes: + episode['title'] = episode.get('titles', None)[0] # XXX. [0] will create exception. FIX! + episode_id = episode.get('id', None) + if episode_id is None: continue + episode['identifier'] = episode_id + episode['parent_identifier'] = season['identifier'] + self.addToDatabase(params=episode, type = "episode") + + self.debug(str(identifier)) # XXX: Remove TODO: Add Show(extend Library) convience options for db seasching return parent def addToDatabase(self, params = {}, type="show", force_readd = True, search_after = True, update_library = False, status_id = None): log.debug("show.addToDatabase") - + if not params.get('identifier'): msg = 'Can\'t add show without imdb identifier.' log.error(msg) @@ -176,7 +194,7 @@ class ShowBase(MediaBase): do_search = False if not m: m = Movie( - type = type, + type = type, library_id = library.get('id'), profile_id = params.get('profile_id', default_profile.get('id')), status_id = status_id if status_id else status_active.get('id'), @@ -242,7 +260,7 @@ class ShowBase(MediaBase): db.expire_all() return onComplete - + def createNotifyFront(self, show_id): def notifyFront(): diff --git a/couchpotato/core/media/show/library/episode/main.py b/couchpotato/core/media/show/library/episode/main.py index 99a21f6..3d2323d 100644 --- a/couchpotato/core/media/show/library/episode/main.py +++ b/couchpotato/core/media/show/library/episode/main.py @@ -23,10 +23,10 @@ class EpisodeLibraryPlugin(LibraryBase): def add(self, attrs = {}, update_after = True): type = attrs.get('type', 'episode') primary_provider = attrs.get('primary_provider', 'thetvdb') - + db = get_session() parent_identifier = attrs.get('parent_identifier', None) - + parent = None if parent_identifier: parent = db.query(Library).filter_by(primary_provider = primary_provider, identifier = attrs.get('parent_identifier')).first() @@ -35,15 +35,15 @@ class EpisodeLibraryPlugin(LibraryBase): if not l: status = fireEvent('status.get', 'needs_update', single = True) l = Library( - type = type, - primary_provider = primary_provider, + type = type, + primary_provider = primary_provider, year = attrs.get('year'), identifier = attrs.get('identifier'), plot = toUnicode(attrs.get('plot')), tagline = toUnicode(attrs.get('tagline')), status_id = status.get('id'), info = {}, - parent = parent, + parent = parent, ) title = LibraryTitle( @@ -84,12 +84,16 @@ class EpisodeLibraryPlugin(LibraryBase): parent_identifier = None if library.parent: parent_identifier = library.parent.identifier - + if library.status_id == done_status.get('id') and not force: do_update = False - - info = fireEvent('episode.info', merge = True, identifier = identifier, \ - parent_identifier = parent_identifier) + + #info = fireEvent('episode.info', merge = True, identifier = identifier, \ + # parent_identifier = parent_identifier) + #info = fireEvent('episode.info', merge = True, identifier = parent_identifier, \ + # episode_identifier = identifier) + info = fireEvent('episode.info', merge = True, season_identifier = parent_identifier, \ + episode_identifier = identifier) # Don't need those here try: del info['in_wanted'] diff --git a/couchpotato/core/media/show/library/season/main.py b/couchpotato/core/media/show/library/season/main.py index 65bfbb5..331adaf 100644 --- a/couchpotato/core/media/show/library/season/main.py +++ b/couchpotato/core/media/show/library/season/main.py @@ -23,10 +23,10 @@ class SeasonLibraryPlugin(LibraryBase): def add(self, attrs = {}, update_after = True): type = attrs.get('type', 'season') primary_provider = attrs.get('primary_provider', 'thetvdb') - + db = get_session() parent_identifier = attrs.get('parent_identifier', None) - + parent = None if parent_identifier: parent = db.query(Library).filter_by(primary_provider = primary_provider, identifier = attrs.get('parent_identifier')).first() @@ -35,15 +35,15 @@ class SeasonLibraryPlugin(LibraryBase): if not l: status = fireEvent('status.get', 'needs_update', single = True) l = Library( - type = type, - primary_provider = primary_provider, + type = type, + primary_provider = primary_provider, year = attrs.get('year'), identifier = attrs.get('identifier'), plot = toUnicode(attrs.get('plot')), tagline = toUnicode(attrs.get('tagline')), status_id = status.get('id'), info = {}, - parent = parent, + parent = parent, ) title = LibraryTitle( @@ -84,12 +84,12 @@ class SeasonLibraryPlugin(LibraryBase): parent_identifier = None if library.parent: parent_identifier = library.parent.identifier - + if library.status_id == done_status.get('id') and not force: do_update = False - - info = fireEvent('season.info', merge = True, identifier = identifier, \ - parent_identifier = parent_identifier) + + info = fireEvent('season.info', merge = True, identifier = parent_identifier, \ + season_identifier = identifier) # Don't need those here try: del info['in_wanted'] @@ -124,7 +124,9 @@ class SeasonLibraryPlugin(LibraryBase): t = LibraryTitle( title = title, simple_title = self.simplifyTitle(title), - default = (len(default_title) == 0 and counter == 0) or len(titles) == 1 or title.lower() == toUnicode(default_title.lower()) or (toUnicode(default_title) == u'' and toUnicode(titles[0]) == title) + # XXX: default was None; so added a quick hack since we don't really need titiles for seasons anyway + #default = (len(default_title) == 0 and counter == 0) or len(titles) == 1 or title.lower() == toUnicode(default_title.lower()) or (toUnicode(default_title) == u'' and toUnicode(titles[0]) == title) + default = True, ) library.titles.append(t) counter += 1 @@ -132,23 +134,23 @@ class SeasonLibraryPlugin(LibraryBase): db.commit() # Files - images = info.get('images', []) - for image_type in ['poster']: - for image in images.get(image_type, []): - if not isinstance(image, (str, unicode)): - continue - - file_path = fireEvent('file.download', url = image, single = True) - if file_path: - file_obj = fireEvent('file.add', path = file_path, type_tuple = ('image', image_type), single = True) - try: - file_obj = db.query(File).filter_by(id = file_obj.get('id')).one() - library.files.append(file_obj) - db.commit() - - break - except: - log.debug('Failed to attach to library: %s', traceback.format_exc()) + #images = info.get('images', []) + #for image_type in ['poster']: + #for image in images.get(image_type, []): + #if not isinstance(image, (str, unicode)): + #continue + + #file_path = fireEvent('file.download', url = image, single = True) + #if file_path: + #file_obj = fireEvent('file.add', path = file_path, type_tuple = ('image', image_type), single = True) + #try: + #file_obj = db.query(File).filter_by(id = file_obj.get('id')).one() + #library.files.append(file_obj) + #db.commit() + + #break + #except: + #log.debug('Failed to attach to library: %s', traceback.format_exc()) library_dict = library.to_dict(self.default_dict) diff --git a/couchpotato/core/media/show/library/show/main.py b/couchpotato/core/media/show/library/show/main.py index b8db80c..df39ff8 100644 --- a/couchpotato/core/media/show/library/show/main.py +++ b/couchpotato/core/media/show/library/show/main.py @@ -23,22 +23,22 @@ class ShowLibraryPlugin(LibraryBase): def add(self, attrs = {}, update_after = True): type = attrs.get('type', 'show') primary_provider = attrs.get('primary_provider', 'thetvdb') - + db = get_session() - + l = db.query(Library).filter_by(type = type, identifier = attrs.get('identifier')).first() if not l: status = fireEvent('status.get', 'needs_update', single = True) l = Library( - type = type, - primary_provider = primary_provider, + type = type, + primary_provider = primary_provider, year = attrs.get('year'), identifier = attrs.get('identifier'), plot = toUnicode(attrs.get('plot')), tagline = toUnicode(attrs.get('tagline')), status_id = status.get('id'), info = {}, - parent = None, + parent = None, ) title = LibraryTitle( @@ -75,7 +75,7 @@ class ShowLibraryPlugin(LibraryBase): do_update = True - info = fireEvent('show.info' % library.type, merge = True, identifier = identifier) + info = fireEvent('show.info', merge = True, identifier = identifier) # Don't need those here try: del info['in_wanted'] diff --git a/couchpotato/core/providers/show/thetvdb/main.py b/couchpotato/core/providers/show/thetvdb/main.py index fa19580..61ecd6b 100644 --- a/couchpotato/core/providers/show/thetvdb/main.py +++ b/couchpotato/core/providers/show/thetvdb/main.py @@ -3,22 +3,26 @@ from couchpotato.core.helpers.encoding import simplifyString, toUnicode from couchpotato.core.logger import CPLog from couchpotato.core.providers.show.base import ShowProvider from tvdb_api import tvdb_api, tvdb_exceptions -from datetime import datetime +from datetime import datetime import traceback log = CPLog(__name__) # XXX: I return None in alot of functions when there is error or no value; check if I -# should be returning an empty list or dictionary +# should be returning an empty list or dictionary # XXX: Consider grabbing zips to put less strain on tvdb # XXX: Consider a cache; not implenented everywhere yet or at all +# XXX: Search by language; now ists defualt of "en" +# XXX: alternate titles do exist for show and episodes; add them +# XXX: Unicode stuff +# XXX: we have a getShow function but it it being used? class TheTVDb(ShowProvider): - + def __init__(self): #addEvent('show.by_hash', self.byHash) addEvent('show.search', self.search, priority = 1) addEvent('show.info', self.getShowInfo, priority = 1) - addEvent('show.episodes', self.getEpisodes, priority = 1) + addEvent('season.info', self.getSeasonInfo, priority = 1) addEvent('episode.info', self.getEpisodeInfo, priority = 1) #addEvent('show.info_by_thetvdb', self.getInfoByTheTVDBId) @@ -27,7 +31,7 @@ class TheTVDb(ShowProvider): 'apikey':"7966C02F860586D2", 'banners':True } - + self.tvdb = tvdb_api.Tvdb(**tvdb_api_parms) #def byHash(self, file): @@ -62,7 +66,7 @@ class TheTVDb(ShowProvider): #return results def search(self, q, limit = 12): - ''' Find show by name + ''' Find show by name show = { 'id': 74713, 'language': 'en', 'lid': 7, @@ -76,6 +80,7 @@ class TheTVDb(ShowProvider): search_string = simplifyString(q) cache_key = 'thetvdb.cache.%s.%s' % (search_string, limit) results = self.getCache(cache_key) + # TODO: cache is not returned if not results: log.debug('Searching for show: %s', q) @@ -83,7 +88,6 @@ class TheTVDb(ShowProvider): raw = None try: raw = self.tvdb.search(search_string) - except (tvdb_exceptions.tvdb_error, IOError), e: log.error('Failed searching TheTVDB for "%s": %s', (search_string, traceback.format_exc())) return None @@ -114,51 +118,107 @@ class TheTVDb(ShowProvider): return results - def getEpisodes(self, identifier=None, episode_identifier=None): - """Either return a list of all episodes or a single episode. - If episode_identifer contains an episode to search for it will be returned if found + def getShow(self, identifier = None): + show = None + try: + log.debug('Getting show: %s', identifier) + show = self.tvdb[int(identifier)] + except (tvdb_exceptions.tvdb_error, IOError), e: + log.error('Failed to getShowInfo for show id "%s": %s', (identifier, traceback.format_exc())) + return None + + return show + + def getSeasonInfo(self, identifier=None, season_identifier=None): + """Either return a list of all seasons or a single season by number. + identifier is the show 'id' """ if not identifier: return None - + + # season_identifier must contain the 'show id : season number' since there is no tvdb id + # for season and we need a reference to both the show id and season number + if season_identifier: + try: season_identifier = int(season_identifier.split(':')[1]) + except: return None + + cache_key = 'thetvdb.cache.%s.%s' % (identifier, season_identifier) + log.debug('Getting SeasonInfo: %s', cache_key) + result = self.getCache(cache_key) or {} + if result: + return result + try: show = self.tvdb[int(identifier)] except (tvdb_exceptions.tvdb_error, IOError), e: - log.error('Failed parsing TheTVDB for "%s" id "%s": %s', (show, identifier, traceback.format_exc())) + log.error('Failed parsing TheTVDB SeasonInfo for "%s" id "%s": %s', (show, identifier, traceback.format_exc())) return None - + result = [] - for season in show.values(): - for episode in season.values(): - if episode_identifier: - if episode['id'] == toUnicode(episode_identifier): - return episode - else: - result.append(self.parseEpisode(show, episode)) - + for number, season in show.items(): + if season_identifier is not None and number == season_identifier: + result = self.parseSeason(show, (number, season)) + self.setCache(cache_key, result) + return result + else: + result.append(self.parseSeason(show, (number, season))) + + self.setCache(cache_key, result) return result - - def getShow(self, identifier = None): - show = None + + def getEpisodeInfo(self, identifier=None, season_identifier=None, episode_identifier=None): + """Either return a list of all episodes or a single episode. + If episode_identifer contains an episode number to search for + """ + if not identifier and season_identifier is None: + return None + + # season_identifier must contain the 'show id : season number' since there is no tvdb id + # for season and we need a reference to both the show id and season number + if season_identifier: + try: + identifier, season_identifier = season_identifier.split(':') + season_identifier = int(season_identifier) + except: return None + + cache_key = 'thetvdb.cache.%s.%s.%s' % (identifier, episode_identifier, season_identifier) + log.debug('Getting EpisodeInfo: %s', cache_key) + result = self.getCache(cache_key) or {} + if result: + return result + try: - log.debug('Getting show: %s', identifier) show = self.tvdb[int(identifier)] except (tvdb_exceptions.tvdb_error, IOError), e: - log.error('Failed to getShowInfo for show id "%s": %s', (identifier, traceback.format_exc())) + log.error('Failed parsing TheTVDB EpisodeInfo for "%s" id "%s": %s', (show, identifier, traceback.format_exc())) return None - - return show - + + result = [] + for number, season in show.items(): + if season_identifier is not None and number != season_identifier: + continue + + for episode in season.values(): + if episode_identifier is not None and episode['id'] == toUnicode(episode_identifier): + result = self.parseEpisode(show, episode) + self.setCache(cache_key, result) + return result + else: + result.append(self.parseEpisode(show, episode)) + + self.setCache(cache_key, result) + return result + def getShowInfo(self, identifier = None): if not identifier: return None - + cache_key = 'thetvdb.cache.%s' % identifier log.debug('Getting showInfo: %s', cache_key) result = self.getCache(cache_key) or {} if result: return result - + show = self.getShow(identifier=identifier) if show: result = self.parseShow(show) @@ -166,26 +226,6 @@ class TheTVDb(ShowProvider): return result - def getEpisodeInfo(self, identifier = None, parent_identifier = None): - if not identifier or not parent_identifier: - return None - - cache_key = 'thetvdb.cache.%s.%s' % (parent_identifier, identifier) - log.debug('Getting EpisodeInfo: %s', cache_key) - result = self.getCache(cache_key) or {} - if result: - return result - - show = self.getShow(identifier = parent_identifier) - if show: - episode = self.getEpisodes(identifier=parent_identifier, episode_identifier=identifier) - - if episode: - result = self.parseEpisode(show, episode) - self.setCache(cache_key, result) - - return result - #def getInfoByTheTVDBId(self, id = None): #cache_key = 'thetvdb.cache.%s' % id @@ -208,7 +248,7 @@ class TheTVDb(ShowProvider): #return result def parseShow(self, show): - """ + """ show[74713] = { 'actors': u'|Bryan Cranston|Aaron Paul|Dean Norris|RJ Mitte|Betsy Brandt|Anna Gunn|Laura Fraser|Jesse Plemons|Christopher Cousins|Steven Michael Quezada|Jonathan Banks|Giancarlo Esposito|Bob Odenkirk|', 'added': None, @@ -234,25 +274,23 @@ class TheTVDb(ShowProvider): 'seriesid': u'74713', 'seriesname': u'Breaking Bad', 'status': u'Continuing', - 'zap2it_id': u'SH01009396'} + 'zap2it_id': u'SH01009396'} """ - + # Make sure we have a valid show id, not '' or None #if len (show['id']) is 0: # return None - + ## Images poster = self.getImage(show, type = 'poster', size = 'cover') backdrop = self.getImage(show, type = 'fanart', size = 'w1280') #poster_original = self.getImage(show, type = 'poster', size = 'original') #backdrop_original = self.getImage(show, type = 'backdrop', size = 'original') - - ## Genres - genres = [] if show['genre'] is None else show['genre'].strip('|').split('|') - ## Year - if show['firstaired']: - year = datetime.strptime(show['firstaired'], '%Y-%m-%d').year + genres = [] if show['genre'] is None else show['genre'].strip('|').split('|') + if show['firstaired'] is not None: + try: year = datetime.strptime(show['firstaired'], '%Y-%m-%d').year + except: year = None else: year = None @@ -268,26 +306,71 @@ class TheTVDb(ShowProvider): 'poster_original': [], 'backdrop_original': [], }, - 'imdb': show['imdb_id'], - 'runtime': show['runtime'], - 'released': show['firstaired'], 'year': year, - 'plot': show['overview'], 'genres': genres, + 'imdb': show['imdb_id'], + 'zap2it_id': show['zap2it_id'], + 'seriesid': show['seriesid'], + 'network': show['network'], + 'networkid': show['networkid'], + 'airs_dayofweek': show['airs_dayofweek'], + 'airs_time': show['airs_time'], + 'firstaired': show['firstaired'], + 'released': show['firstaired'], + 'runtime': show['runtime'], + 'contentrating': show['contentrating'], + 'rating': show['rating'], + 'ratingcount': show['ratingcount'], + 'actors': show['actors'], + 'lastupdated': show['lastupdated'], + 'status': show['status'], + 'language': show['language'], } show_data = dict((k, v) for k, v in show_data.iteritems() if v) ## Add alternative names #for alt in ['original_name', 'alternative_name']: - #alt_name = toUnicode(show.get(alt)) + #alt_name = toUnicode(show['alt)) #if alt_name and not alt_name in show_data['titles'] and alt_name.lower() != 'none' and alt_name != None: #show_data['titles'].append(alt_name) return show_data - + + def parseSeason(self, show, season_tuple): + """ + contains no data + """ + + number, season = season_tuple + title = toUnicode('%s - Season %s' % (show['seriesname'], str(number))) + + # XXX: work on title; added defualt_title to fix an error + season_data = { + 'id': (show['id'] + ':' + str(number)), + 'type': 'season', + 'primary_provider': 'thetvdb', + 'titles': [title, ], + 'original_title': title, + 'via_thetvdb': True, + 'parent_identifier': show['id'], + 'seasonnumber': str(number), + 'images': { + 'poster': [], + 'backdrop': [], + 'poster_original': [], + 'backdrop_original': [], + }, + 'year': None, + 'genres': None, + 'imdb': None, + } + + season_data = dict((k, v) for k, v in season_data.iteritems() if v) + return season_data + def parseEpisode(self, show, episode): - """ + """ ('episodenumber', u'1'), ('thumb_added', None), ('rating', u'7.7'), @@ -321,23 +404,23 @@ class TheTVDb(ShowProvider): ('firstaired', u'2011-09-19'), ('episodename', u'Pilot')] """ - + ## Images #poster = self.getImage(episode, type = 'poster', size = 'cover') #backdrop = self.getImage(episode, type = 'fanart', size = 'w1280') ##poster_original = self.getImage(episode, type = 'poster', size = 'original') ##backdrop_original = self.getImage(episode, type = 'backdrop', size = 'original') + poster = episode['filename'] or [] backdrop = [] - - ## Genres genres = [] - - plot = "%s - %sx%s - %s" % (show['seriesname'], episode['seasonnumber'], episode['episodenumber'], episode['overview']) - - ## Year - if episode['firstaired']: - year = datetime.strptime(episode['firstaired'], '%Y-%m-%d').year + plot = "%s - %sx%s - %s" % (show['seriesname'], + episode['seasonnumber'], + episode['episodenumber'], + episode['overview']) + if episode['firstaired'] is not None: + try: year = datetime.strptime(episode['firstaired'], '%Y-%m-%d').year + except: year = None else: year = None @@ -348,7 +431,7 @@ class TheTVDb(ShowProvider): 'via_thetvdb': True, 'thetvdb_id': int(episode['id']), 'titles': [episode['episodename'], ], - 'original_title': episode['episodename'], + 'original_title': episode['episodename'] , 'images': { 'poster': [poster] if poster else [], 'backdrop': [backdrop] if backdrop else [], @@ -362,13 +445,38 @@ class TheTVDb(ShowProvider): 'plot': plot, 'genres': genres, 'parent_identifier': show['id'], + 'seasonnumber': episode['seasonnumber'], + 'episodenumber': episode['episodenumber'], + 'combined_episodenumber': episode['combined_episodenumber'], + 'absolute_number': episode['absolute_number'], + 'combined_season': episode['combined_season'], + 'productioncode': episode['productioncode'], + 'seriesid': episode['seriesid'], + 'seasonid': episode['seasonid'], + 'firstaired': episode['firstaired'], + 'thumb_added': episode['thumb_added'], + 'thumb_height': episode['thumb_height'], + 'thumb_width': episode['thumb_width'], + 'rating': episode['rating'], + 'ratingcount': episode['ratingcount'], + 'epimgflag': episode['epimgflag'], + 'dvd_episodenumber': episode['dvd_episodenumber'], + 'dvd_discid': episode['dvd_discid'], + 'dvd_chapter': episode['dvd_chapter'], + 'dvd_season': episode['dvd_season'], + 'tms_export': episode['tms_export'], + 'writer': episode['writer'], + 'director': episode['director'], + 'gueststars': episode['gueststars'], + 'lastupdated': episode['lastupdated'], + 'language': episode['language'], } episode_data = dict((k, v) for k, v in episode_data.iteritems() if v) ## Add alternative names #for alt in ['original_name', 'alternative_name']: - #alt_name = toUnicode(episode.get(alt)) + #alt_name = toUnicode(episode['alt)) #if alt_name and not alt_name in episode_data['titles'] and alt_name.lower() != 'none' and alt_name != None: #episode_data['titles'].append(alt_name) @@ -378,11 +486,11 @@ class TheTVDb(ShowProvider): """""" # XXX: Need to implement size image_url = '' - + for res, res_data in show['_banners'].get(type, {}).items(): for bid, banner_info in res_data.items(): image_url = banner_info.get('_bannerpath', '') - break + break return image_url diff --git a/couchpotato/core/settings/model.py b/couchpotato/core/settings/model.py index 5013d3a..16c0190 100644 --- a/couchpotato/core/settings/model.py +++ b/couchpotato/core/settings/model.py @@ -94,7 +94,7 @@ class Library(Entity): type = Field(String(10), default="movie", index=True) primary_provider = Field(String(10), default="imdb", index=True) year = Field(Integer) - identifier = Field(String(20), index = True) + identifier = Field(String(40), index = True) plot = Field(UnicodeText) tagline = Field(UnicodeText(255)) @@ -104,7 +104,7 @@ class Library(Entity): movies = OneToMany('Movie', cascade = 'all, delete-orphan') titles = OneToMany('LibraryTitle', cascade = 'all, delete-orphan') files = ManyToMany('File', cascade = 'all, delete-orphan', single_parent = True) - + parent = ManyToOne('Library') children = OneToMany('Library') @@ -120,7 +120,7 @@ class LibraryTitle(Entity): language = OneToMany('Language') libraries = ManyToOne('Library') - + class Language(Entity): """"""