diff --git a/src/NzbDrone.Core.Test/DecisionEngineTests/DownloadDecisionMakerFixture.cs b/src/NzbDrone.Core.Test/DecisionEngineTests/DownloadDecisionMakerFixture.cs index 2d501ca2a..90b251ace 100644 --- a/src/NzbDrone.Core.Test/DecisionEngineTests/DownloadDecisionMakerFixture.cs +++ b/src/NzbDrone.Core.Test/DecisionEngineTests/DownloadDecisionMakerFixture.cs @@ -239,11 +239,16 @@ namespace NzbDrone.Core.Test.DecisionEngineTests Episodes = episodes.Where(v => v.SceneEpisodeNumber == p.EpisodeNumbers.First()).ToList() }); - Mocker.SetConstant>(new List()); + Mocker.SetConstant>(new List + { + Mocker.Resolve() + }); var decisions = Subject.GetSearchDecision(reports, criteria); - Assert.AreEqual(1, decisions.Count); + var approvedDecisions = decisions.Where(v => v.Approved).ToList(); + + approvedDecisions.Count.Should().Be(1); } } } \ No newline at end of file diff --git a/src/NzbDrone.Core.Test/IndexerSearchTests/NzbSearchServiceFixture.cs b/src/NzbDrone.Core.Test/IndexerSearchTests/NzbSearchServiceFixture.cs index 2ccfa51ea..d6780b56f 100644 --- a/src/NzbDrone.Core.Test/IndexerSearchTests/NzbSearchServiceFixture.cs +++ b/src/NzbDrone.Core.Test/IndexerSearchTests/NzbSearchServiceFixture.cs @@ -5,6 +5,7 @@ using System; using System.Collections.Generic; using System.Linq; using System.Text; +using FluentAssertions; using Moq; using NUnit.Framework; using NzbDrone.Core.Tv; @@ -26,12 +27,12 @@ namespace NzbDrone.Core.Test.IndexerSearchTests Mocker.GetMock() .Setup(s => s.GetAvailableProviders()) - .Returns(new List{indexer.Object}); + .Returns(new List { indexer.Object }); Mocker.GetMock() .Setup(s => s.GetSearchDecision(It.IsAny>(), It.IsAny())) .Returns(new List()); - + _xemSeries = Builder.CreateNew() .With(v => v.UseSceneNumbering = true) .Build(); @@ -81,12 +82,16 @@ namespace NzbDrone.Core.Test.IndexerSearchTests WithEpisode(4, 2, 5, 14); WithEpisode(4, 3, 6, 11); WithEpisode(5, 1, 6, 12); + + // Season 7+ maps normally, so no mapping specified. + WithEpisode(7, 1, 0, 0); + WithEpisode(7, 2, 0, 0); } private List WatchForSearchCriteria() { List result = new List(); - + Mocker.GetMock() .Setup(v => v.Fetch(It.IsAny(), It.IsAny())) .Callback((i, s) => result.Add(s)) @@ -94,7 +99,7 @@ namespace NzbDrone.Core.Test.IndexerSearchTests Mocker.GetMock() .Setup(v => v.Fetch(It.IsAny(), It.IsAny())) - .Callback((i,s) => result.Add(s)) + .Callback((i, s) => result.Add(s)) .Returns(new List()); return result; @@ -111,9 +116,9 @@ namespace NzbDrone.Core.Test.IndexerSearchTests var criteria = allCriteria.OfType().ToList(); - Assert.AreEqual(1, criteria.Count); - Assert.AreEqual(2, criteria[0].SeasonNumber); - Assert.AreEqual(3, criteria[0].EpisodeNumber); + criteria.Count.Should().Be(1); + criteria[0].SeasonNumber.Should().Be(2); + criteria[0].EpisodeNumber.Should().Be(3); } [Test] @@ -127,8 +132,8 @@ namespace NzbDrone.Core.Test.IndexerSearchTests var criteria = allCriteria.OfType().ToList(); - Assert.AreEqual(1, criteria.Count); - Assert.AreEqual(2, criteria[0].SeasonNumber); + criteria.Count.Should().Be(1); + criteria[0].SeasonNumber.Should().Be(2); } [Test] @@ -142,9 +147,9 @@ namespace NzbDrone.Core.Test.IndexerSearchTests var criteria = allCriteria.OfType().ToList(); - Assert.AreEqual(2, criteria.Count); - Assert.AreEqual(3, criteria[0].SeasonNumber); - Assert.AreEqual(4, criteria[1].SeasonNumber); + criteria.Count.Should().Be(2); + criteria[0].SeasonNumber.Should().Be(3); + criteria[1].SeasonNumber.Should().Be(4); } [Test] @@ -159,12 +164,27 @@ namespace NzbDrone.Core.Test.IndexerSearchTests var criteria1 = allCriteria.OfType().ToList(); var criteria2 = allCriteria.OfType().ToList(); - Assert.AreEqual(1, criteria1.Count); - Assert.AreEqual(5, criteria1[0].SeasonNumber); + criteria1.Count.Should().Be(1); + criteria1[0].SeasonNumber.Should().Be(5); + + criteria2.Count.Should().Be(1); + criteria2[0].SeasonNumber.Should().Be(6); + criteria2[0].EpisodeNumber.Should().Be(11); + } + + [Test] + public void scene_seasonsearch_should_use_seasonnumber_if_no_scene_number_is_available() + { + WithEpisodes(); + + var allCriteria = WatchForSearchCriteria(); + + Subject.SeasonSearch(_xemSeries.Id, 7); + + var criteria = allCriteria.OfType().ToList(); - Assert.AreEqual(1, criteria2.Count); - Assert.AreEqual(6, criteria2[0].SeasonNumber); - Assert.AreEqual(11, criteria2[0].EpisodeNumber); + criteria.Count.Should().Be(1); + criteria[0].SeasonNumber.Should().Be(7); } } } diff --git a/src/NzbDrone.Core/DecisionEngine/DownloadDecisionMaker.cs b/src/NzbDrone.Core/DecisionEngine/DownloadDecisionMaker.cs index b5b13d9a7..cfed22a5c 100644 --- a/src/NzbDrone.Core/DecisionEngine/DownloadDecisionMaker.cs +++ b/src/NzbDrone.Core/DecisionEngine/DownloadDecisionMaker.cs @@ -97,17 +97,6 @@ namespace NzbDrone.Core.DecisionEngine if (decision != null) { - if (searchCriteria != null) - { - var criteriaEpisodes = searchCriteria.Episodes.Select(v => v.Id).ToList(); - var remoteEpisodes = decision.RemoteEpisode.Episodes.Select(v => v.Id).ToList(); - if (!criteriaEpisodes.Intersect(remoteEpisodes).Any()) - { - _logger.Debug("Release rejected since the episode wasn't requested: {0}", decision.RemoteEpisode.ParsedEpisodeInfo); - continue; - } - } - if (decision.Rejections.Any()) { _logger.Debug("Release rejected for the following reasons: {0}", String.Join(", ", decision.Rejections)); diff --git a/src/NzbDrone.Core/DecisionEngine/Specifications/Search/EpisodeRequestedSpecification.cs b/src/NzbDrone.Core/DecisionEngine/Specifications/Search/EpisodeRequestedSpecification.cs new file mode 100644 index 000000000..6df94a6fc --- /dev/null +++ b/src/NzbDrone.Core/DecisionEngine/Specifications/Search/EpisodeRequestedSpecification.cs @@ -0,0 +1,43 @@ +using System.Linq; +using NLog; +using NzbDrone.Core.IndexerSearch.Definitions; +using NzbDrone.Core.Parser.Model; + + +namespace NzbDrone.Core.DecisionEngine.Specifications.Search +{ + public class EpisodeRequestedSpecification : IDecisionEngineSpecification + { + private readonly Logger _logger; + + public EpisodeRequestedSpecification(Logger logger) + { + _logger = logger; + } + + public string RejectionReason + { + get + { + return "Episode wasn't requested"; + } + } + + public bool IsSatisfiedBy(RemoteEpisode remoteEpisode, SearchCriteriaBase searchCriteria) + { + if (searchCriteria == null) + { + return true; + } + var criteriaEpisodes = searchCriteria.Episodes.Select(v => v.Id).ToList(); + var remoteEpisodes = remoteEpisode.Episodes.Select(v => v.Id).ToList(); + if (!criteriaEpisodes.Intersect(remoteEpisodes).Any()) + { + _logger.Debug("Release rejected since the episode wasn't requested: {0}", remoteEpisode.ParsedEpisodeInfo); + return false; + } + + return true; + } + } +} diff --git a/src/NzbDrone.Core/IndexerSearch/NzbSearchService.cs b/src/NzbDrone.Core/IndexerSearch/NzbSearchService.cs index a5b140beb..1b71323e6 100644 --- a/src/NzbDrone.Core/IndexerSearch/NzbSearchService.cs +++ b/src/NzbDrone.Core/IndexerSearch/NzbSearchService.cs @@ -142,15 +142,25 @@ namespace NzbDrone.Core.IndexerSearch if (series.UseSceneNumbering) { - var sceneSeasonGroups = episodes.GroupBy(v => v.SceneSeasonNumber).Distinct(); + var sceneSeasonGroups = episodes.GroupBy(v => + { + if (v.SceneSeasonNumber == 0 && v.SceneEpisodeNumber == 0) + return v.SeasonNumber; + else + return v.SceneSeasonNumber; + }).Distinct(); foreach (var sceneSeasonEpisodes in sceneSeasonGroups) { if (sceneSeasonEpisodes.Count() == 1) { + var episode = sceneSeasonEpisodes.First(); var searchSpec = Get(series, sceneSeasonEpisodes.ToList()); searchSpec.SeasonNumber = sceneSeasonEpisodes.Key; - searchSpec.EpisodeNumber = sceneSeasonEpisodes.First().SceneEpisodeNumber; + if (episode.SceneSeasonNumber == 0 && episode.SceneEpisodeNumber == 0) + searchSpec.EpisodeNumber = episode.EpisodeNumber; + else + searchSpec.EpisodeNumber = episode.SceneEpisodeNumber; var decisions = Dispatch(indexer => _feedFetcher.Fetch(indexer, searchSpec), searchSpec); downloadDecisions.AddRange(decisions); diff --git a/src/NzbDrone.Core/NzbDrone.Core.csproj b/src/NzbDrone.Core/NzbDrone.Core.csproj index 0e3b6e8b7..c331efd94 100644 --- a/src/NzbDrone.Core/NzbDrone.Core.csproj +++ b/src/NzbDrone.Core/NzbDrone.Core.csproj @@ -217,6 +217,7 @@ +