1
0
mirror of https://github.com/Sonarr/Sonarr.git synced 2024-12-14 11:23:42 +02:00

added release results to episode detail tab

This commit is contained in:
kay.one 2013-06-06 17:17:57 -07:00
parent a5be71fd8c
commit 890d1f2398
14 changed files with 191 additions and 48 deletions

View File

@ -1,10 +1,8 @@
using System;
using System.Collections.Generic;
using System.Collections.Generic;
using NzbDrone.Api.Mapping;
using NzbDrone.Api.REST;
using NzbDrone.Core.DecisionEngine;
using NzbDrone.Core.IndexerSearch;
using NzbDrone.Core.Indexers;
using NzbDrone.Core.Parser;
using Omu.ValueInjecter;
using System.Linq;
@ -13,13 +11,32 @@ namespace NzbDrone.Api.Indexers
public class ReleaseModule : NzbDroneRestModule<ReleaseResource>
{
private readonly IFetchAndParseRss _rssFetcherAndParser;
private readonly ISearchForNzb _nzbSearchService;
private readonly IMakeDownloadDecision _downloadDecisionMaker;
public ReleaseModule(IFetchAndParseRss rssFetcherAndParser, IMakeDownloadDecision downloadDecisionMaker)
public ReleaseModule(IFetchAndParseRss rssFetcherAndParser, ISearchForNzb nzbSearchService, IMakeDownloadDecision downloadDecisionMaker)
{
_rssFetcherAndParser = rssFetcherAndParser;
_nzbSearchService = nzbSearchService;
_downloadDecisionMaker = downloadDecisionMaker;
GetResourceAll = GetRss;
GetResourceAll = GetReleases;
}
private List<ReleaseResource> GetReleases()
{
if (Request.Query.episodeId != null)
{
return GetEpisodeReleases(Request.Query.episodeId);
}
return GetRss();
}
private List<ReleaseResource> GetEpisodeReleases(int episodeId)
{
var decisions = _nzbSearchService.EpisodeSearch(episodeId);
return MapDecisions(decisions);
}
private List<ReleaseResource> GetRss()
@ -27,6 +44,11 @@ private List<ReleaseResource> GetRss()
var reports = _rssFetcherAndParser.Fetch();
var decisions = _downloadDecisionMaker.GetRssDecision(reports);
return MapDecisions(decisions);
}
private static List<ReleaseResource> MapDecisions(IEnumerable<DownloadDecision> decisions)
{
var result = new List<ReleaseResource>();
foreach (var downloadDecision in decisions)
@ -44,24 +66,4 @@ private List<ReleaseResource> GetRss()
return result;
}
}
public class ReleaseResource : RestResource
{
public Int32 Age { get; set; }
public Int64 Size { get; set; }
public String Indexer { get; set; }
public String NzbInfoUrl { get; set; }
public String NzbUrl { get; set; }
public String ReleaseGroup { get; set; }
public String Title { get; set; }
public Boolean FullSeason { get; set; }
public Boolean SceneSource { get; set; }
public Int32 SeasonNumber { get; set; }
public Language Language { get; set; }
public DateTime? AirDate { get; set; }
public String SeriesTitle { get; set; }
public int[] EpisodeNumbers { get; set; }
public Boolean Approved { get; set; }
public List<string> Rejections { get; set; }
}
}

View File

@ -0,0 +1,27 @@
using System;
using System.Collections.Generic;
using NzbDrone.Api.REST;
using NzbDrone.Core.Parser;
namespace NzbDrone.Api.Indexers
{
public class ReleaseResource : RestResource
{
public Int32 Age { get; set; }
public Int64 Size { get; set; }
public String Indexer { get; set; }
public String NzbInfoUrl { get; set; }
public String NzbUrl { get; set; }
public String ReleaseGroup { get; set; }
public String Title { get; set; }
public Boolean FullSeason { get; set; }
public Boolean SceneSource { get; set; }
public Int32 SeasonNumber { get; set; }
public Language Language { get; set; }
public DateTime? AirDate { get; set; }
public String SeriesTitle { get; set; }
public int[] EpisodeNumbers { get; set; }
public Boolean Approved { get; set; }
public List<string> Rejections { get; set; }
}
}

View File

@ -115,6 +115,7 @@
<Compile Include="Indexers\IndexerResource.cs" />
<Compile Include="Indexers\ReleaseModule.cs" />
<Compile Include="Extensions\LazyExtensions.cs" />
<Compile Include="Indexers\ReleaseResource.cs" />
<Compile Include="Logs\LogModule.cs" />
<Compile Include="Logs\LogResource.cs" />
<Compile Include="Mapping\CloneInjection.cs" />

View File

@ -26,5 +26,11 @@
<RegexTestSelector>
<RegularExpression>NzbDrone\.Common\.Test\.EventingTests\.ServiceNameFixture\..*</RegularExpression>
</RegexTestSelector>
<RegexTestSelector>
<RegularExpression>NzbDrone\.Common\.Test\.ProcessProviderTests\..*</RegularExpression>
</RegexTestSelector>
<RegexTestSelector>
<RegularExpression>NzbDrone\.Common\.Test\.ServiceFactoryFixture\..*</RegularExpression>
</RegexTestSelector>
</IgnoredTests>
</ProjectConfiguration>

View File

@ -1,5 +1,6 @@
using System;
using System.Text.RegularExpressions;
using NzbDrone.Common.EnsureThat;
namespace NzbDrone.Core.IndexerSearch.Definitions
{
@ -21,6 +22,8 @@ public string QueryTitle
private static string GetQueryTitle(string title)
{
Ensure.That(() => title).IsNotNullOrWhiteSpace();
var cleanTitle = BeginningThe.Replace(title, String.Empty);
cleanTitle = cleanTitle

View File

@ -14,9 +14,8 @@ namespace NzbDrone.Core.IndexerSearch
{
public interface ISearchForNzb
{
List<DownloadDecision> SearchSingle(int seriesId, int seasonNumber, int episodeNumber);
List<DownloadDecision> SearchDaily(int seriesId, DateTime airDate);
List<DownloadDecision> SearchSeason(int seriesId, int seasonNumber);
List<DownloadDecision> EpisodeSearch(int episodeId);
List<DownloadDecision> SeasonSearch(int seriesId, int seasonNumber);
}
public class NzbSearchService : ISearchForNzb
@ -40,7 +39,23 @@ public NzbSearchService(IIndexerService indexerService, IFetchFeedFromIndexers f
_logger = logger;
}
public List<DownloadDecision> SearchSingle(int seriesId, int seasonNumber, int episodeNumber)
public List<DownloadDecision> EpisodeSearch(int episodeId)
{
var episode = _episodeService.GetEpisode(episodeId);
var series = _seriesService.GetSeries(episode.SeriesId);
if (series.SeriesType == SeriesTypes.Daily)
{
return SearchDaily(episode.SeriesId, episode.AirDate.Value.Date);
}
return SearchSingle(episode.SeriesId, episode.SeasonNumber, episode.EpisodeNumber);
}
private List<DownloadDecision> SearchSingle(int seriesId, int seasonNumber, int episodeNumber)
{
var searchSpec = Get<SingleEpisodeSearchCriteria>(seriesId, seasonNumber);
@ -59,7 +74,7 @@ public List<DownloadDecision> SearchSingle(int seriesId, int seasonNumber, int e
return Dispatch(indexer => _feedFetcher.Fetch(indexer, searchSpec), searchSpec);
}
public List<DownloadDecision> SearchDaily(int seriesId, DateTime airDate)
private List<DownloadDecision> SearchDaily(int seriesId, DateTime airDate)
{
var searchSpec = Get<DailyEpisodeSearchCriteria>(seriesId);
searchSpec.Airtime = airDate;
@ -67,7 +82,7 @@ public List<DownloadDecision> SearchDaily(int seriesId, DateTime airDate)
return Dispatch(indexer => _feedFetcher.Fetch(indexer, searchSpec), searchSpec);
}
public List<DownloadDecision> SearchSeason(int seriesId, int seasonNumber)
public List<DownloadDecision> SeasonSearch(int seriesId, int seasonNumber)
{
var searchSpec = Get<SeasonSearchCriteria>(seriesId, seasonNumber);
searchSpec.SeasonNumber = seasonNumber;
@ -99,10 +114,15 @@ private List<DownloadDecision> PartialSeasonSearch(SeasonSearchCriteria search)
{
var spec = new TSpec();
var tvdbId = _seriesService.GetSeries(seriesId).TvdbId;
var series = _seriesService.GetSeries(seriesId);
spec.SeriesId = seriesId;
spec.SceneTitle = _sceneMapping.GetSceneName(tvdbId, seasonNumber);
spec.SceneTitle = _sceneMapping.GetSceneName(series.TvdbId, seasonNumber);
if (string.IsNullOrWhiteSpace(spec.SceneTitle))
{
spec.SceneTitle = series.Title;
}
return spec;
}

View File

@ -12,7 +12,7 @@ interface ISearchAndDownload
void SearchSeason(int seriesId, int seasonNumber);
}
public class SearchAndDownloadService : ISearchAndDownload
/* public class SearchAndDownloadService : ISearchAndDownload
{
private readonly ISearchForNzb _searchService;
private readonly IMakeDownloadDecision _downloadDecisionMaker;
@ -23,7 +23,7 @@ public SearchAndDownloadService(ISearchForNzb searchService, IMakeDownloadDecisi
_downloadDecisionMaker = downloadDecisionMaker;
}
public void SearchSingle(int seriesId, int seasonNumber, int episodeNumber)
public void FetchSearchSingle(int seriesId, int seasonNumber, int episodeNumber)
{
var result = _searchService.SearchSingle(seriesId, seasonNumber, episodeNumber);
}
@ -37,5 +37,5 @@ public void SearchSeason(int seriesId, int seasonNumber)
{
throw new NotImplementedException();
}
}
}*/
}

View File

@ -48,7 +48,7 @@ public IList<ReportInfo> Fetch(IIndexer indexer, SeasonSearchCriteria searchCrit
{
_logger.Debug("Searching for {0}", searchCriteria);
var searchUrls = indexer.GetSeasonSearchUrls(searchCriteria.SceneTitle, searchCriteria.SeasonNumber);
var searchUrls = indexer.GetSeasonSearchUrls(searchCriteria.QueryTitle, searchCriteria.SeasonNumber);
var result = Fetch(indexer, searchUrls);
@ -60,7 +60,7 @@ public IList<ReportInfo> Fetch(IIndexer indexer, SingleEpisodeSearchCriteria sea
{
_logger.Debug("Searching for {0}", searchCriteria);
var searchUrls = indexer.GetEpisodeSearchUrls(searchCriteria.SceneTitle, searchCriteria.SeasonNumber, searchCriteria.EpisodeNumber);
var searchUrls = indexer.GetEpisodeSearchUrls(searchCriteria.QueryTitle, searchCriteria.SeasonNumber, searchCriteria.EpisodeNumber);
var result = Fetch(indexer, searchUrls);
@ -73,7 +73,7 @@ public IList<ReportInfo> Fetch(IIndexer indexer, PartialSeasonSearchCriteria sea
{
_logger.Debug("Searching for {0}", searchCriteria);
var searchUrls = indexer.GetSeasonSearchUrls(searchCriteria.SceneTitle, searchCriteria.SeasonNumber);
var searchUrls = indexer.GetSeasonSearchUrls(searchCriteria.QueryTitle, searchCriteria.SeasonNumber);
var result = Fetch(indexer, searchUrls);
@ -85,7 +85,7 @@ public IList<ReportInfo> Fetch(IIndexer indexer, DailyEpisodeSearchCriteria sear
{
_logger.Debug("Searching for {0}", searchCriteria);
var searchUrls = indexer.GetDailyEpisodeSearchUrls(searchCriteria.SceneTitle, searchCriteria.Airtime);
var searchUrls = indexer.GetDailyEpisodeSearchUrls(searchCriteria.QueryTitle, searchCriteria.Airtime);
var result = Fetch(indexer, searchUrls);
_logger.Info("Finished searching {0} on {1}. Found {2}", indexer.Name, searchCriteria, result.Count);

View File

@ -1,6 +1,6 @@
<SolutionConfiguration>
<FileVersion>1</FileVersion>
<AutoEnableOnStartup>False</AutoEnableOnStartup>
<AutoEnableOnStartup>True</AutoEnableOnStartup>
<AllowParallelTestExecution>true</AllowParallelTestExecution>
<AllowTestsToRunInParallelWithThemselves>true</AllowTestsToRunInParallelWithThemselves>
<FrameworkUtilisationTypeForNUnit>UseDynamicAnalysis</FrameworkUtilisationTypeForNUnit>

View File

@ -1,5 +1,5 @@
"use strict";
define(['app', 'Episode/Summary/View'], function () {
define(['app', 'Shared/SpinnerView', 'Episode/Summary/View', 'Episode/Search/Layout', 'Release/Collection'], function () {
NzbDrone.Episode.Layout = Backbone.Marionette.Layout.extend({
template: 'Episode/LayoutTemplate',
@ -27,6 +27,7 @@ define(['app', 'Episode/Summary/View'], function () {
onShow: function () {
this.showSummary();
this._releaseSearchActivated = false;
},
@ -53,7 +54,21 @@ define(['app', 'Episode/Summary/View'], function () {
e.preventDefault();
}
if (this._releaseSearchActivated) {
return;
}
var self = this;
this.ui.search.tab('show');
this.search.show(new NzbDrone.Shared.SpinnerView());
var releases = new NzbDrone.Release.Collection();
var promise = releases.fetchEpisodeReleases(this.model.id);
promise.done(function () {
self.search.show(new NzbDrone.Episode.Search.Layout({collection: releases}));
});
}
});

View File

@ -2,9 +2,65 @@
define(['app'], function () {
NzbDrone.Episode.Search.Layout = Backbone.Marionette.Layout.extend({
template: 'Episode/Search/LayoutTemplate'
template: 'Episode/Search/LayoutTemplate',
regions: {
grid: '#episode-release-grid'
},
columns: [
{
name : 'age',
label : 'Age',
sortable: true,
cell : Backgrid.IntegerCell
},
{
name : 'size',
label : 'Size',
sortable: true,
cell : Backgrid.IntegerCell
},
{
name : 'title',
label : 'Title',
sortable: true,
cell : Backgrid.StringCell
},
{
name : 'seasonNumber',
label: 'season',
cell : Backgrid.IntegerCell
},
{
name : 'episodeNumber',
label: 'episode',
cell : Backgrid.StringCell
},
{
name : 'approved',
label: 'Approved',
cell : Backgrid.BooleanCell
}
],
initialize: function () {
},
onShow :function(){
if (!this.isClosed) {
this.grid.show(new Backgrid.Grid(
{
row : Backgrid.Row,
columns : this.columns,
collection: this.collection,
className : 'table table-hover'
}));
}
}
});
});

View File

@ -1 +1 @@

<div id="episode-release-grid"/>

View File

@ -4,6 +4,10 @@ define(['app', 'Release/Model'], function () {
url : NzbDrone.Constants.ApiRoot + '/release',
model: NzbDrone.Release.Model,
mode : 'client'
mode: 'client',
fetchEpisodeReleases: function (episodeId) {
return this.fetch({ data: { episodeId: episodeId }});
}
});
});

View File

@ -10,9 +10,18 @@ define(['app'], function () {
$(document).on('click', 'a[href]', this._handleClick);
},
_isInTab: function (element) {
return;
},
_handleClick: function (event) {
var $target = $(event.target);
//check if tab nav
if ($target.parents('.nav-tabs').length) {
return;
}
if ($target.hasClass('no-router')) {
return;
}