diff --git a/SickBeard.py b/SickBeard.py index ae44059e17fedc6f6eb35a0f99ff7b8d85e486c2..4be6a58524ab4539ed0f3bdd592dd6da26558266 100644 --- a/SickBeard.py +++ b/SickBeard.py @@ -166,10 +166,6 @@ def main(): logger.log(u"Loading initial show list") loadShowsFromDB() - # set up the lists - sickbeard.updateAiringList() - sickbeard.updateComingList() - # fire up all our threads sickbeard.start() diff --git a/data/interfaces/default/comingEpisodes.tmpl b/data/interfaces/default/comingEpisodes.tmpl index 341921f1a4a7012cd1fc1c8be152de4b57b5b2f9..abef3db78b44e353e2a57fa47c28a1c61a67c2be 100644 --- a/data/interfaces/default/comingEpisodes.tmpl +++ b/data/interfaces/default/comingEpisodes.tmpl @@ -1,7 +1,6 @@ #import sickbeard #import datetime #from sickbeard.common import * -#set $oneWeek = datetime.timedelta(days=7) #set global $title="Coming Episodes" #set global $sbPath=".." @@ -12,59 +11,66 @@ <div id="outerWrapper"> <div id="listingWrapper"> - #set $curDay = None - #set $missed = False - #for $curEp in $epList - #if $sort == "date" - #if $curEp.show.paused: - #continue - #end if - #if $curEp.airdate < datetime.date.today() and $curDay == None: - #if $missed == False - <br /><h1 class="day">Missing</h1> - #set $missed = True - #end if - #elif $curDay == None or ($curEp.airdate > $curDay and $curEp.airdate - datetime.date.today() < $oneWeek): - #set $curDay = curEp.airdate - <br /><h1 class="day">$curEp.airdate.strftime("%A")</h1> - #elif $curEp.airdate > $curDay and $curEp.airdate - datetime.date.today() >= $oneWeek: - #set $curDay = datetime.date(datetime.MAXYEAR, 1, 1) - <br /><h1 class="day">More than one week</h1> - #end if - - #if $curEp.airdate == datetime.date.today() - #set $showDiv = "listing_current" - #elif $curEp.airdate < datetime.date.today() - #set $showDiv = "listing_overdue" - #elif $curEp.airdate - datetime.date.today() >= $oneWeek - #set $showDiv = "listing_toofar" - #else - #set $showDiv = "" - #end if - #else - #set $showDiv = "" - #end if - <div class="$showDiv"> - <div class="listing" id="listing_$curEp.show.tvdbid"> - <a name="$curEp.show.name"></a> - <a href="$sbRoot/home/displayShow?show=$curEp.show.tvdbid"><img alt="" src="$sbRoot/showPoster/?show=$curEp.show.tvdbid" class="listingThumb" /></a> - <div id="info_$curEp.show.tvdbid"> + + #set $cur_segment = None + #set $too_late_header = False + #set $missed_header = False + #set $show_div = "" + + #for $cur_result in $sql_results: + #if int($cur_result["paused"]): + #continue + #end if + + #if $sort == "network": + #if $cur_result["network"] and $cur_segment != $cur_result["network"]: + <br /><h1 class="day">$cur_result["network"]</h1> + #set $cur_segment = $cur_result["network"] + #end if + #elif $sort == "date": + #set $cur_ep_airdate = int($cur_result["airdate"]) + #if $cur_segment != $cur_ep_airdate: + #if $cur_ep_airdate < $today and not $missed_header: + <br /><h1 class="day">Missed</h1> + #set $missed_header = True + #set $show_div = "listing_overdue" + #elif $cur_ep_airdate >= $next_week and not $too_late_header: + <br /><h1 class="day">Later</h1> + #set $show_div = "listing_toofar" + #set $too_late_header = True + #elif $cur_ep_airdate >= $today and $cur_ep_airdate < $next_week: + <br /><h1 class="day">$datetime.date.fromordinal($cur_ep_airdate).strftime("%A")</h1> + #if $cur_ep_airdate == $today: + #set $show_div = "listing_current" + #else: + #set $show_div = "" + #end if + #end if + #set $cur_segment = $cur_ep_airdate + #end if + #end if + + <div class="$show_div"> + <div class="listing" id="listing_${cur_result["showid"]}"> + <a name="$cur_result["show_name"]"></a> + <a href="$sbRoot/home/displayShow?show=${cur_result["showid"]}"><img alt="" src="$sbRoot/showPoster/?show=${cur_result["showid"]}" class="listingThumb" /></a> + <div id="info_${cur_result["showid"]}"> <h1> <div class="icons"> - <a href="http://www.thetvdb.com/?tab=series&id=$curEp.show.tvdbid" target="_blank" title="http://www.thetvdb.com/?tab=series&id=$curEp.show.tvdbid"><img alt="" src="$sbRoot/images/info.png" /></a> - <a href="$sbRoot/home/searchEpisode?show=$curEp.show.tvdbid&season=$curEp.season&episode=$curEp.episode" title="Force Update" id="forceUpdate|$curEp.show.tvdbid|$curEp.show.name" class="forceUpdate"><img alt="" src="$sbRoot/images/forceUpdate.png" id="forceUpdateImage|$curEp.show.tvdbid" /></a> + <a href="http://www.thetvdb.com/?tab=series&id=${cur_result["showid"]}" target="_blank" title="http://www.thetvdb.com/?tab=series&id=${cur_result["showid"]}"><img alt="" src="$sbRoot/images/info.png" /></a> + <a href="$sbRoot/home/searchEpisode?show=${cur_result["showid"]}&season=$cur_result["season"]&episode=$cur_result["episode"]" title="Force Update" id="forceUpdate|${cur_result["showid"]}|$cur_result["show_name"]" class="forceUpdate"><img alt="" src="$sbRoot/images/forceUpdate.png" id="forceUpdateImage|${cur_result["showid"]}" /></a> </div> - <a href="$sbRoot/home/displayShow?show=$curEp.show.tvdbid">$curEp.show.name</a> + <a href="$sbRoot/home/displayShow?show=${cur_result["showid"]}">$cur_result["show_name"]</a> </h1> <p class="next"> - <span class="title">Next Episode:</span> <span class="info "><%=str(curEp.season)+"x"+"%02i" % int(curEp.episode) %> - $curEp.name airs $curEp.airdate</span> + <span class="title">Next Episode:</span> <span class="info "><%=str(cur_result["season"])+"x"+"%02i" % int(cur_result["episode"]) %> - $cur_result["name"] airs $datetime.date.fromordinal(int($cur_result["airdate"]))</span> </p> <p class="noMargin"> - <span class="title">Status:</span> <span class="info ">$curEp.show.status</span><br /> - <span class="title">Airs:</span> <span class="info ">$curEp.show.airs on $curEp.show.network</span><br /> + <span class="title">Status:</span> <span class="info ">$cur_result["show_status"]</span><br /> + <span class="title">Airs:</span> <span class="info ">$cur_result["airs"] on $cur_result["network"]</span><br /> <span class="title">Format:</span> <span class="info "> -#if $curEp.show.quality in $qualityPresets: -$qualityPresetStrings[$curEp.show.quality] +#if int($cur_result["quality"]) in $qualityPresets: +$qualityPresetStrings[int($cur_result["quality"])] #else: Custom #end if diff --git a/data/interfaces/default/displayShow.tmpl b/data/interfaces/default/displayShow.tmpl index abf55244f17e30517e5db40f0d2ce685289a6148..00104dfd74865201131c6ea86917cb3abd20eda7 100644 --- a/data/interfaces/default/displayShow.tmpl +++ b/data/interfaces/default/displayShow.tmpl @@ -82,13 +82,15 @@ All other statuses will automatically update to the appropriate "Downloaded ..." <span class="good">Downloaded: <b>$epCounts[$Overview.GOOD]</b> <input type="checkbox" id="good" CHECKED></span> <span class="skipped">Skipped: <b>$epCounts[$Overview.SKIPPED]</b> <input type="checkbox" id="skipped" CHECKED></span> <br /> +<span class="selectAll"><a href="#" onClick="return false" class="seriesCheck">Select Filtered Episodes</a> </span> +<span class="clearAll"><a href="#" onClick="return false" class="clearAll">Clear All</a></span> <br /> </div> -Jump To: +Jump to Season: #for $seasonNum in $seasonResults: <a href="#season-$seasonNum["season"]"> - #if int($seasonNum["season"]) == 0 then "Specials</a>" else "Season "+str($seasonNum["season"])+"</a> |" + #if int($seasonNum["season"]) == 0 then "Specials</a>" else str($seasonNum["season"])+"</a> |" #end for <table class="sickbeardTable"> diff --git a/data/interfaces/default/history.tmpl b/data/interfaces/default/history.tmpl index b7eb4487f0dffd7ea11f80ce50d3f95925d11ea0..728b6e4a9a4b3da77d22723631a5e5fcf7ecfe89 100644 --- a/data/interfaces/default/history.tmpl +++ b/data/interfaces/default/history.tmpl @@ -30,7 +30,7 @@ #set $curStatus, $curQuality = $Quality.splitCompositeStatus(int($hItem["action"])) <tr class="evenLine"> <td>$datetime.datetime.strptime(str($hItem["date"]), $history.dateFormat)</td> - <td><a href="$sbRoot/home/displayShow?show=$hItem["showid"]">$hItem["show_name"] - <%=str(hItem["season"]) +"x"+ "%02i" % int(hItem["episode"]) %></a></td> + <td><a href="$sbRoot/home/displayShow?show=$hItem["showid"]#season-$hItem["season"]">$hItem["show_name"] - <%=str(hItem["season"]) +"x"+ "%02i" % int(hItem["episode"]) %></a></td> <td align="center">$statusStrings[$curStatus]</td> <td align="center"> #if $curStatus == DOWNLOADED: diff --git a/data/js/displayShow.js b/data/js/displayShow.js index a6f2216a722d4b39defd72f03cbf4ecd83740fec..9cbc14ff7490bcf4b2384f54cfdfa8fc2d4e995f 100644 --- a/data/js/displayShow.js +++ b/data/js/displayShow.js @@ -35,7 +35,27 @@ $(document).ready(function(){ } }); }); - + + // selects all visible episode checkboxes. + $('.seriesCheck').click(function(){ + $('.epCheck:visible').each(function(){ + this.checked = true + }); + $('.seasonCheck:visible').each(function(){ + this.checked = true + }) + }); + + // clears all visible episode checkboxes and the season selectors + $('.clearAll').click(function(){ + $('.epCheck:visible').each(function(){ + this.checked = false + }); + $('.seasonCheck:visible').each(function(){ + this.checked = false + }); + }); + // handle the show selection dropbox $('#pickShow').change(function(){ var sbRoot = $('#sbRoot').val() diff --git a/sickbeard/__init__.py b/sickbeard/__init__.py index f87dfdcf0630f8142dcb7e6ac171f6013180fd35..d05ccfa7fd2653e8b520fa3f11e3e63d6fb4f6c0 100644 --- a/sickbeard/__init__.py +++ b/sickbeard/__init__.py @@ -64,9 +64,6 @@ autoPostProcesserScheduler = None showList = None loadingShowList = None -airingList = None -comingList = None - providerList = [] newznabProviderList = [] metadata_generator = None @@ -289,7 +286,7 @@ def initialize(consoleLogging=True): XBMC_NOTIFY_ONSNATCH, XBMC_NOTIFY_ONDOWNLOAD, XBMC_UPDATE_FULL, \ XBMC_UPDATE_LIBRARY, XBMC_HOST, XBMC_USERNAME, XBMC_PASSWORD, currentSearchScheduler, backlogSearchScheduler, \ showUpdateScheduler, __INITIALIZED__, LAUNCH_BROWSER, showList, \ - airingList, comingList, loadingShowList, SOCKET_TIMEOUT, \ + loadingShowList, SOCKET_TIMEOUT, \ NZBS, NZBS_UID, NZBS_HASH, EZRSS, TORRENT_DIR, USENET_RETENTION, \ SEARCH_FREQUENCY, DEFAULT_SEARCH_FREQUENCY, BACKLOG_SEARCH_FREQUENCY, \ DEFAULT_BACKLOG_SEARCH_FREQUENCY, QUALITY_DEFAULT, SEASON_FOLDERS_FORMAT, SEASON_FOLDERS_DEFAULT, \ @@ -537,9 +534,6 @@ def initialize(consoleLogging=True): showList = [] loadingShowList = {} - airingList = [] - comingList = [] - __INITIALIZED__ = True return True @@ -842,64 +836,6 @@ def launchBrowser(startPort=None): except: logger.log(u"Unable to launch a browser", logger.ERROR) - -def updateAiringList(): - - logger.log(u"Searching DB and building list of airing episodes") - - curDate = datetime.date.today().toordinal() - - myDB = db.DBConnection() - sqlResults = myDB.select("SELECT * FROM tv_episodes WHERE status == ? AND airdate <= ?", [UNAIRED, curDate]) - - epList = [] - - for sqlEp in sqlResults: - - try: - show = helpers.findCertainShow (sickbeard.showList, int(sqlEp["showid"])) - except exceptions.MultipleShowObjectsException: - logger.log(u"ERROR: expected to find a single show matching " + sqlEp["showid"]) - return None - except exceptions.SickBeardException, e: - logger.log(u"Unexpected exception: "+str(e).decode('utf-8'), logger.ERROR) - continue - - # we aren't ever downloading specials - if int(sqlEp["season"]) == 0: - continue - - if show == None: - continue - - ep = show.getEpisode(sqlEp["season"], sqlEp["episode"]) - - if ep == None: - logger.log(u"Somehow "+show.name+" - "+str(sqlEp["season"])+"x"+str(sqlEp["episode"])+" is None", logger.ERROR) - else: - epList.append(ep) - - sickbeard.airingList = epList - -def updateComingList(): - - epList = [] - - for curShow in sickbeard.showList: - - curEps = None - - try: - curEps = curShow.nextEpisode() - except exceptions.NoNFOException, e: - logger.log(u"Unable to retrieve episode from show: "+str(e).decode('utf-8'), logger.ERROR) - - for myEp in curEps: - if myEp.season != 0: - epList.append(myEp) - - sickbeard.comingList = epList - def getEpList(epIDs, showid=None): if epIDs == None or len(epIDs) == 0: diff --git a/sickbeard/name_parser/parser.py b/sickbeard/name_parser/parser.py index d934976163c334f1c5dce9038b0513ba27c90c21..24b4b01a179a2d7e3455aeeecf3fe2676dd0e92f 100644 --- a/sickbeard/name_parser/parser.py +++ b/sickbeard/name_parser/parser.py @@ -142,6 +142,12 @@ class NameParser(object): else: return b + def _unicodify(self, obj, encoding = "utf-8"): + if isinstance(obj, basestring): + if not isinstance(obj, unicode): + obj = unicode(obj, encoding) + return obj + def _convert_number(self, number): if type(number) == int: return number @@ -167,6 +173,8 @@ class NameParser(object): def parse(self, name): + name = self._unicodify(name) + # break it into parts if there are any (dirname, file name, extension) dir_name, file_name = os.path.split(name) ext_match = re.match('(.*)\.\w{3,4}$', file_name) @@ -225,6 +233,7 @@ class ParseResult(object): release_group=None, air_date=None ): + self.original_name = original_name self.series_name = series_name @@ -276,7 +285,7 @@ class ParseResult(object): if self.release_group: to_return += ' (' + self.release_group + ')' - return to_return + return to_return.encode('utf-8') def _is_air_by_date(self): if self.season_number == None and len(self.episode_numbers) == 0 and self.air_date: diff --git a/sickbeard/name_parser/regexes.py b/sickbeard/name_parser/regexes.py index df61199089059a4e543ef1cfce071693c86bfdd4..d0727fd1cde5dc9ad058710b8f7cbc5f2c3a6522 100644 --- a/sickbeard/name_parser/regexes.py +++ b/sickbeard/name_parser/regexes.py @@ -82,9 +82,9 @@ ep_regexes = [ ^(?P<series_name>.+?)[\. _-]+ # Show_Name and separator (?P<air_year>\d{4})[\. _-]+ # 2010 and separator (?P<air_month>\d{2})[\. _-]+ # 11 and separator - (?P<air_day>\d{2})[\. _-]+ # 23 and separator - (?P<extra_info>.+?) # Source.Quality.Etc - (-(?P<release_group>.+))?$ # Group + (?P<air_day>\d{2}) # 23 and separator + ([\. _-]+(?P<extra_info>.+?) # Source.Quality.Etc + (-(?P<release_group>.+))?)?$ # Group '''), ('stupid', diff --git a/sickbeard/postProcessor.py b/sickbeard/postProcessor.py index 41c95e6836b7f0e85fddf290407e9e2deeb69dc1..db31804288fe35b8be82b6d43b6fbb1053c99ee3 100644 --- a/sickbeard/postProcessor.py +++ b/sickbeard/postProcessor.py @@ -313,7 +313,7 @@ class PostProcessor(object): # parse the name to break it into show name, season, and episode np = NameParser(file) parse_result = np.parse(name) - self._log("Parsed "+name+" into "+str(parse_result), logger.DEBUG) + self._log("Parsed "+name+" into "+str(parse_result).decode('utf-8'), logger.DEBUG) if parse_result.air_by_date: season = -1 @@ -536,8 +536,9 @@ class PostProcessor(object): return True # if the user downloaded it manually and it appears to be a PROPER/REPACK then it's priority - if self.is_proper and new_ep_quality <= ep_obj.quality: - self._log(u"This was manually downloaded but it appears to a proper so I'm marking it as priority", logger.DEBUG) + old_ep_status, old_ep_quality = common.Quality.splitCompositeStatus(ep_obj.status) + if self.is_proper and new_ep_quality >= old_ep_quality: + self._log(u"This was manually downloaded but it appears to be a proper so I'm marking it as priority", logger.DEBUG) return True return False diff --git a/sickbeard/providers/nzbmatrix.py b/sickbeard/providers/nzbmatrix.py index 02740df12568b14e5764b586a217ccbc1483d462..ab622c093ad64b5ff0826cd8f8a2c2a846683684 100644 --- a/sickbeard/providers/nzbmatrix.py +++ b/sickbeard/providers/nzbmatrix.py @@ -49,7 +49,7 @@ class NZBMatrixProvider(generic.NZBProvider): sceneSearchStrings = set(sceneHelpers.makeSceneSeasonSearchString(show, season, "nzbmatrix")) # search for all show names and episode numbers like ("a","b","c") in a single search - return ['("' + '","'.join(sceneSearchStrings) + '")'] + return [' '.join(sceneSearchStrings)] def _get_episode_search_strings(self, ep_obj): @@ -162,4 +162,4 @@ class NZBMatrixCache(tvcache.TVCache): return data -provider = NZBMatrixProvider() \ No newline at end of file +provider = NZBMatrixProvider() diff --git a/sickbeard/queue.py b/sickbeard/queue.py index 8fa878f3f4eb9bfa41e33f5efb6715a54098bdef..a7c12b612dd98565991b429b0aa6f89315cbdb19 100644 --- a/sickbeard/queue.py +++ b/sickbeard/queue.py @@ -280,10 +280,6 @@ class QueueItemAdd(QueueItem): self.finish() - sickbeard.updateAiringList() - sickbeard.updateComingList() - - def _finishEarly(self): if self.show != None: self.show.deleteShow() diff --git a/sickbeard/sceneHelpers.py b/sickbeard/sceneHelpers.py index 3f9c04a712f81744bb22c9acafc2b9ccabfe9831..72f4f76fb1df503aa49f7606bcb2012ef28bcffa 100644 --- a/sickbeard/sceneHelpers.py +++ b/sickbeard/sceneHelpers.py @@ -119,6 +119,7 @@ def makeSceneSeasonSearchString (show, segment, extraSearchType=None): showNames = set(makeSceneShowSearchStrings(show)) toReturn = [] + term_list = [] # search each show name for curShow in showNames: @@ -135,7 +136,7 @@ def makeSceneSeasonSearchString (show, segment, extraSearchType=None): # nzbmatrix is special, we build a search string just for them elif extraSearchType == "nzbmatrix": if numseasons == 1: - toReturn.append('+"'+curShow+'"') + toReturn.append('"'+curShow+'"') elif numseasons == 0: toReturn.append('"'+curShow+' '+str(segment).replace('-',' ')+'"') else: @@ -143,8 +144,12 @@ def makeSceneSeasonSearchString (show, segment, extraSearchType=None): if show.is_air_by_date: term_list = ['"'+x+'"' for x in term_list] - toReturn.append('+"'+curShow+'" +('+','.join(term_list)+')') - + toReturn.append('"'+curShow+'"') + + if extraSearchType == "nzbmatrix": + toReturn = ['+('+','.join(toReturn)+')'] + if term_list: + toReturn.append('+('+','.join(term_list)+')') return toReturn diff --git a/sickbeard/search.py b/sickbeard/search.py index 58c47f9d4ddf8ad44c412b3e82ddf497fccfcb2a..760ef1e968a4435b1a9b39beef77598ac57ed1f4 100644 --- a/sickbeard/search.py +++ b/sickbeard/search.py @@ -98,10 +98,6 @@ def snatchEpisode(result, endStatus=SNATCHED): if curEpObj.status not in Quality.DOWNLOADED: notifiers.notify(NOTIFY_SNATCH, curEpObj.prettyName(True)) - - sickbeard.updateAiringList() - sickbeard.updateComingList() - return True def searchForNeededEpisodes(): @@ -159,21 +155,26 @@ def searchForNeededEpisodes(): return foundResults.values() -def pickBestResult(results): +def pickBestResult(results, quality_list=None): logger.log(u"Picking the best result out of "+str([x.name for x in results]), logger.DEBUG) # find the best result for the current episode bestResult = None - for curResult in results: - logger.log("Quality of "+curResult.name+" is "+str(curResult.quality)) - if not bestResult or bestResult.quality < curResult.quality and curResult.quality != Quality.UNKNOWN: - bestResult = curResult - elif bestResult.quality == curResult.quality: - if "proper" in curResult.name.lower() or "repack" in curResult.name.lower(): - bestResult = curResult - elif "internal" in bestResult.name.lower() and "internal" not in curResult.name.lower(): - bestResult = curResult + for cur_result in results: + logger.log("Quality of "+cur_result.name+" is "+str(cur_result.quality)) + + if quality_list and cur_result.quality not in quality_list: + logger.log(cur_result.name+" is a quality we know we don't want, rejecting it", logger.DEBUG) + continue + + if not bestResult or bestResult.quality < cur_result.quality and cur_result.quality != Quality.UNKNOWN: + bestResult = cur_result + elif bestResult.quality == cur_result.quality: + if "proper" in cur_result.name.lower() or "repack" in cur_result.name.lower(): + bestResult = cur_result + elif "internal" in bestResult.name.lower() and "internal" not in cur_result.name.lower(): + bestResult = cur_result if bestResult: logger.log(u"Picked "+bestResult.name+" as the best", logger.DEBUG) @@ -262,10 +263,12 @@ def findSeason(show, season): finalResults = [] + anyQualities, bestQualities = Quality.splitQuality(show.quality) + # pick the best season NZB bestSeasonNZB = None if SEASON_RESULT in foundResults: - bestSeasonNZB = pickBestResult(foundResults[SEASON_RESULT]) + bestSeasonNZB = pickBestResult(foundResults[SEASON_RESULT], anyQualities+bestQualities) highest_quality_overall = 0 for cur_season in foundResults: diff --git a/sickbeard/searchCurrent.py b/sickbeard/searchCurrent.py index 0e51693fbb9e1220403e3774fe0d987fdc6fae3b..e7289ad1ee765d7b6dbf07fc1670ab8902f2c32e 100644 --- a/sickbeard/searchCurrent.py +++ b/sickbeard/searchCurrent.py @@ -51,10 +51,6 @@ class CurrentSearcher(): self._changeMissingEpisodes() - # make sure our lists are up to date - sickbeard.updateAiringList() - sickbeard.updateComingList() - with self.lock: logger.log(u"Beginning search for new episodes on RSS") @@ -68,10 +64,6 @@ class CurrentSearcher(): search.snatchEpisode(curResult) time.sleep(2) - # update our lists to reflect any changes we just made - sickbeard.updateAiringList() - sickbeard.updateComingList() - if not backlogPaused: logger.log(u"Search is done, resuming backlog", logger.DEBUG) sickbeard.backlogSearchScheduler.action.amPaused = False diff --git a/sickbeard/tv.py b/sickbeard/tv.py index fe373bf858da80082e6ff588f99435eea71b8707..ad381dff6b8072334b4e15ea57a88fd44526e812 100644 --- a/sickbeard/tv.py +++ b/sickbeard/tv.py @@ -110,10 +110,8 @@ class TVShow(object): for curSeason in self.episodes: for curEp in self.episodes[curSeason]: myEp = self.episodes[curSeason][curEp] - if myEp not in sickbeard.comingList and \ - myEp not in sickbeard.airingList: - self.episodes[curSeason][curEp] = None - del myEp + self.episodes[curSeason][curEp] = None + del myEp def getEpisode(self, season, episode, file=None, noCreate=False): @@ -416,7 +414,7 @@ class TVShow(object): else: # if there is a new file associated with this ep then re-check the quality - if ek.ek(os.path.normpath, curEp.location) != ek.ek(os.path.normpath, file): + if curEp.location and ek.ek(os.path.normpath, curEp.location) != ek.ek(os.path.normpath, file): logger.log(u"The old episode had a different file associated with it, I will re-check the quality based on the new filename "+file, logger.DEBUG) checkQualityAgain = True @@ -1276,14 +1274,6 @@ class TVEpisode: logger.log(u"Removing myself from my show's list", logger.DEBUG) del self.show.episodes[self.season][self.episode] - # make sure it's not in any ep lists - if self in sickbeard.airingList: - logger.log(u"Removing myself from the airing list", logger.DEBUG) - sickbeard.airingList.remove(self) - if self in sickbeard.comingList: - logger.log(u"Removing myself from the coming list", logger.DEBUG) - sickbeard.comingList.remove(self) - # delete myself from the DB logger.log(u"Deleting myself from the database", logger.DEBUG) myDB = db.DBConnection() diff --git a/sickbeard/webserve.py b/sickbeard/webserve.py index feb6027f7fdb74a96e0234becb0b552f34c1ad64..51e56b4d434641035490e2533971096ecea4b3b9 100644 --- a/sickbeard/webserve.py +++ b/sickbeard/webserve.py @@ -1756,10 +1756,6 @@ class Home: #TODO: check if the download was successful - # update our lists to reflect the result if this search - sickbeard.updateAiringList() - sickbeard.updateComingList() - redirect("/home/displayShow?show=" + str(epObj.show.tvdbid)) @@ -1803,17 +1799,35 @@ class WebInterface: @cherrypy.expose def comingEpisodes(self, sort="date"): - epList = sickbeard.comingList + myDB = db.DBConnection() + + today = datetime.date.today().toordinal() + next_week = (datetime.date.today() + datetime.timedelta(days=7)).toordinal() + recently = (datetime.date.today() - datetime.timedelta(days=3)).toordinal() + + done_show_list = [] + sql_results = myDB.select("SELECT *, tv_shows.status as show_status FROM tv_episodes, tv_shows WHERE airdate >= ? AND airdate < ? AND tv_shows.tvdb_id = tv_episodes.showid AND tv_episodes.status NOT IN ("+','.join(['?']*len(Quality.DOWNLOADED+Quality.SNATCHED))+")", [today, next_week] + Quality.DOWNLOADED + Quality.SNATCHED) + for cur_result in sql_results: + done_show_list.append(int(cur_result["showid"])) + + more_sql_results = myDB.select("SELECT *, tv_shows.status as show_status FROM tv_episodes outer_eps, tv_shows WHERE showid NOT IN ("+','.join(['?']*len(done_show_list))+") AND tv_shows.tvdb_id = outer_eps.showid AND airdate = (SELECT airdate FROM tv_episodes inner_eps WHERE inner_eps.showid = outer_eps.showid AND inner_eps.airdate >= ? ORDER BY inner_eps.airdate ASC LIMIT 1) AND outer_eps.status NOT IN ("+','.join(['?']*len(Quality.DOWNLOADED+Quality.SNATCHED))+")", done_show_list + [next_week] + Quality.DOWNLOADED + Quality.SNATCHED) + sql_results += more_sql_results + + more_sql_results = myDB.select("SELECT *, tv_shows.status as show_status FROM tv_episodes, tv_shows WHERE tv_shows.tvdb_id = tv_episodes.showid AND airdate < ? AND airdate >= ? AND tv_episodes.status = ? AND tv_episodes.status NOT IN ("+','.join(['?']*len(Quality.DOWNLOADED+Quality.SNATCHED))+")", [today, recently, WANTED] + Quality.DOWNLOADED + Quality.SNATCHED) + sql_results += more_sql_results + + #epList = sickbeard.comingList # sort by air date sorts = { - 'date': (lambda x, y: cmp(x.airdate.toordinal(), y.airdate.toordinal())), - 'show': (lambda a, b: cmp(a.name, b.name)), - 'network': (lambda a, b: cmp(a.show.network, b.show.network)), + 'date': (lambda x, y: cmp(int(x["airdate"]), int(y["airdate"]))), + 'show': (lambda a, b: cmp(a["show_name"], b["show_name"])), + 'network': (lambda a, b: cmp(a["network"], b["network"])), } if sort not in sorts: sort = 'date' - epList.sort(sorts[sort]) + #epList.sort(sorts[sort]) + sql_results.sort(sorts[sort]) t = PageTemplate(file="comingEpisodes.tmpl") t.submenu = [ @@ -1822,7 +1836,11 @@ class WebInterface: { 'title': 'Sort by Network', 'path': 'comingEpisodes/?sort=network' }, ] t.sort = sort - t.epList = epList + #t.epList = epList + + t.next_week = next_week + t.today = today + t.sql_results = sql_results return _munge(t) diff --git a/tests/name_parser_tests.py b/tests/name_parser_tests.py index 5d6ec038a67c27622607e1e144ec17572a70ac8e..eb667757b2ec77db1ef0e93ec54ce04f7ae4f78c 100644 --- a/tests/name_parser_tests.py +++ b/tests/name_parser_tests.py @@ -75,6 +75,7 @@ simple_test_cases = { 'scene_date_format': { 'Show.Name.2010.11.23.Source.Quality.Etc-Group': parser.ParseResult(None, 'Show Name', None, [], 'Source.Quality.Etc', 'Group', datetime.date(2010,11,23)), + 'Show Name - 2010.11.23': parser.ParseResult(None, 'Show Name', air_date = datetime.date(2010,11,23)), 'Show.Name.2010.23.11.Source.Quality.Etc-Group': parser.ParseResult(None, 'Show Name', None, [], 'Source.Quality.Etc', 'Group', datetime.date(2010,11,23)), 'Show Name - 2010-11-23 - Ep Name': parser.ParseResult(None, 'Show Name', extra_info = 'Ep Name', air_date = datetime.date(2010,11,23)), } @@ -99,6 +100,27 @@ combination_test_cases = [ ] +unicode_test_cases = [ + (u'The.Big.Bang.Theory.2x07.The.Panty.Pi\xf1ata.Polarization.720p.HDTV.x264.AC3-SHELDON.mkv', + parser.ParseResult(None, 'The.Big.Bang.Theory', 2, [7], '720p.HDTV.x264.AC3', 'SHELDON') + ), + ('The.Big.Bang.Theory.2x07.The.Panty.Pi\xc3\xb1ata.Polarization.720p.HDTV.x264.AC3-SHELDON.mkv', + parser.ParseResult(None, 'The.Big.Bang.Theory', 2, [7], '720p.HDTV.x264.AC3', 'SHELDON') + ), + ] + +class UnicodeTests(unittest.TestCase): + + def _test_unicode(self, name, result): + np = parser.NameParser(True) + parse_result = np.parse(name) + # this shouldn't raise an exception + a = repr(str(parse_result)) + + def test_unicode(self): + for (name, result) in unicode_test_cases: + self._test_unicode(name, result) + class ComboTests(unittest.TestCase): def _test_combo(self, name, result, which_regexes): @@ -236,3 +258,6 @@ if __name__ == '__main__': suite = unittest.TestLoader().loadTestsFromTestCase(ComboTests) unittest.TextTestRunner(verbosity=2).run(suite) + + suite = unittest.TestLoader().loadTestsFromTestCase(UnicodeTests) + unittest.TextTestRunner(verbosity=2).run(suite)