From 713c4225c0c60e6579745fdb6ad9629c6152c9a0 Mon Sep 17 00:00:00 2001 From: Mark McDowall Date: Tue, 18 Sep 2012 18:30:30 -0700 Subject: [PATCH 1/8] Added EpisodeAiredAfter to server side --- NzbDrone.Core.Test/NzbDrone.Core.Test.csproj | 1 + ...odeAiredAfterCutoffSpecificationFixture.cs | 145 ++++++++++++++++++ .../Datastore/Migrations/Migration20120918.cs | 17 ++ NzbDrone.Core/Model/ReportRejectionType.cs | 3 +- NzbDrone.Core/NzbDrone.Core.csproj | 2 + .../AllowedDownloadSpecification.cs | 5 +- .../EpisodeAiredAfterCutoffSpecification.cs | 44 ++++++ NzbDrone.Core/Repository/Series.cs | 2 + 8 files changed, 217 insertions(+), 2 deletions(-) create mode 100644 NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/EpisodeAiredAfterCutoffSpecificationFixture.cs create mode 100644 NzbDrone.Core/Datastore/Migrations/Migration20120918.cs create mode 100644 NzbDrone.Core/Providers/DecisionEngine/EpisodeAiredAfterCutoffSpecification.cs diff --git a/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj b/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj index 6af68d08a..bb8f27d12 100644 --- a/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj +++ b/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj @@ -128,6 +128,7 @@ + diff --git a/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/EpisodeAiredAfterCutoffSpecificationFixture.cs b/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/EpisodeAiredAfterCutoffSpecificationFixture.cs new file mode 100644 index 000000000..2041fba02 --- /dev/null +++ b/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/EpisodeAiredAfterCutoffSpecificationFixture.cs @@ -0,0 +1,145 @@ +// ReSharper disable RedundantUsingDirective + +using System.Linq; +using System; +using System.Collections.Generic; +using FizzWare.NBuilder; +using FluentAssertions; +using Moq; +using NUnit.Framework; +using NzbDrone.Core.Model; +using NzbDrone.Core.Providers; +using NzbDrone.Core.Providers.DecisionEngine; +using NzbDrone.Core.Repository; +using NzbDrone.Core.Test.Framework; + +namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests +{ + [TestFixture] + // ReSharper disable InconsistentNaming + public class EpisodeAiredAfterCutoffSpecificationFixture : CoreTest + { + private EpisodeAiredAfterCutoffSpecification episodeAiredAfterCutoffSpecification; + + private EpisodeParseResult parseResultMulti; + private EpisodeParseResult parseResultSingle; + private Series fakeSeries; + private Episode firstEpisode; + private Episode secondEpisode; + + [SetUp] + public void Setup() + { + episodeAiredAfterCutoffSpecification = Mocker.Resolve(); + + fakeSeries = Builder.CreateNew() + .With(c => c.Monitored = true) + .With(c => c.DownloadEpisodesAiredAfter = null) + .Build(); + + parseResultMulti = new EpisodeParseResult + { + SeriesTitle = "Title", + Series = fakeSeries, + EpisodeNumbers = new List { 3, 4 }, + SeasonNumber = 12, + }; + + parseResultSingle = new EpisodeParseResult + { + SeriesTitle = "Title", + Series = fakeSeries, + EpisodeNumbers = new List { 3 }, + SeasonNumber = 12, + }; + + firstEpisode = new Episode { AirDate = DateTime.Today }; + secondEpisode = new Episode { AirDate = DateTime.Today }; + + var singleEpisodeList = new List { firstEpisode }; + var doubleEpisodeList = new List { firstEpisode, secondEpisode }; + + Mocker.GetMock().Setup(c => c.GetEpisodesByParseResult(parseResultSingle)).Returns(singleEpisodeList); + Mocker.GetMock().Setup(c => c.GetEpisodesByParseResult(parseResultMulti)).Returns(doubleEpisodeList); + } + + private void WithFirstEpisodeLastYear() + { + firstEpisode.AirDate = DateTime.Today.AddYears(-1); + } + + private void WithSecondEpisodeYear() + { + secondEpisode.AirDate = DateTime.Today.AddYears(-1); + } + + private void WithAiredAfterYesterday() + { + fakeSeries.DownloadEpisodesAiredAfter = DateTime.Today.AddDays(-1); + } + + private void WithAiredAfterLastWeek() + { + fakeSeries.DownloadEpisodesAiredAfter = DateTime.Today.AddDays(-7); + } + + [Test] + public void should_return_true_when_downloadEpisodesAiredAfter_is_null_for_single_episode() + { + episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultSingle).Should().BeTrue(); + } + + [Test] + public void should_return_true_when_downloadEpisodesAiredAfter_is_null_for_multiple_episodes() + { + episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); + } + + [Test] + public void should_return_true_if_both_episodes_air_after_cutoff() + { + WithAiredAfterLastWeek(); + episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); + } + + [Test] + public void should_return_true_if_episode_airs_after_cutoff() + { + WithAiredAfterLastWeek(); + episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultSingle).Should().BeTrue(); + } + + [Test] + public void should_return_true_if_first_episode_aired_after_cutoff() + { + WithAiredAfterLastWeek(); + WithSecondEpisodeYear(); + episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); + } + + [Test] + public void should_return_true_if_second_episode_aired_after_cutoff() + { + WithAiredAfterLastWeek(); + WithFirstEpisodeLastYear(); + episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); + } + + [Test] + public void should_return_false_if_both_episodes_aired_before_cutoff() + { + WithAiredAfterLastWeek(); + WithFirstEpisodeLastYear(); + WithSecondEpisodeYear(); + episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultMulti).Should().BeFalse(); + } + + [Test] + public void should_return_false_if_episode_aired_before_cutoff() + { + WithAiredAfterLastWeek(); + WithFirstEpisodeLastYear(); + episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultSingle).Should().BeFalse(); + } + } +} \ No newline at end of file diff --git a/NzbDrone.Core/Datastore/Migrations/Migration20120918.cs b/NzbDrone.Core/Datastore/Migrations/Migration20120918.cs new file mode 100644 index 000000000..f5cf8a93e --- /dev/null +++ b/NzbDrone.Core/Datastore/Migrations/Migration20120918.cs @@ -0,0 +1,17 @@ +using System; +using System.Data; +using Migrator.Framework; +using NzbDrone.Common; + +namespace NzbDrone.Core.Datastore.Migrations +{ + + [Migration(20120918)] + public class Migration20120918 : NzbDroneMigration + { + protected override void MainDbUpgrade() + { + Database.AddColumn("Series", new Column("DownloadEpisodesAiredAfter", DbType.DateTime, ColumnProperty.Null)); + } + } +} \ No newline at end of file diff --git a/NzbDrone.Core/Model/ReportRejectionType.cs b/NzbDrone.Core/Model/ReportRejectionType.cs index b4cf7336f..ad695a577 100644 --- a/NzbDrone.Core/Model/ReportRejectionType.cs +++ b/NzbDrone.Core/Model/ReportRejectionType.cs @@ -17,6 +17,7 @@ namespace NzbDrone.Core.Model DownloadClientFailure = 10, Skipped = 11, Failure = 12, - ReleaseGroupNotWanted = 13 + ReleaseGroupNotWanted = 13, + EpisodeAiredBeforeCutoff = 14 } } diff --git a/NzbDrone.Core/NzbDrone.Core.csproj b/NzbDrone.Core/NzbDrone.Core.csproj index 69532ee79..4b6c2cdf7 100644 --- a/NzbDrone.Core/NzbDrone.Core.csproj +++ b/NzbDrone.Core/NzbDrone.Core.csproj @@ -227,6 +227,7 @@ + @@ -291,6 +292,7 @@ + diff --git a/NzbDrone.Core/Providers/DecisionEngine/AllowedDownloadSpecification.cs b/NzbDrone.Core/Providers/DecisionEngine/AllowedDownloadSpecification.cs index df58a271f..3ef8408aa 100644 --- a/NzbDrone.Core/Providers/DecisionEngine/AllowedDownloadSpecification.cs +++ b/NzbDrone.Core/Providers/DecisionEngine/AllowedDownloadSpecification.cs @@ -14,13 +14,14 @@ namespace NzbDrone.Core.Providers.DecisionEngine private readonly AlreadyInQueueSpecification _alreadyInQueueSpecification; private readonly RetentionSpecification _retentionSpecification; private readonly AllowedReleaseGroupSpecification _allowedReleaseGroupSpecification; + private readonly EpisodeAiredAfterCutoffSpecification _episodeAiredAfterCutoffSpecification; private static readonly Logger logger = LogManager.GetCurrentClassLogger(); [Inject] public AllowedDownloadSpecification(QualityAllowedByProfileSpecification qualityAllowedByProfileSpecification, UpgradeDiskSpecification upgradeDiskSpecification, AcceptableSizeSpecification acceptableSizeSpecification, AlreadyInQueueSpecification alreadyInQueueSpecification, RetentionSpecification retentionSpecification, - AllowedReleaseGroupSpecification allowedReleaseGroupSpecification) + AllowedReleaseGroupSpecification allowedReleaseGroupSpecification, EpisodeAiredAfterCutoffSpecification episodeAiredAfterCutoffSpecification) { _qualityAllowedByProfileSpecification = qualityAllowedByProfileSpecification; _upgradeDiskSpecification = upgradeDiskSpecification; @@ -28,6 +29,7 @@ namespace NzbDrone.Core.Providers.DecisionEngine _alreadyInQueueSpecification = alreadyInQueueSpecification; _retentionSpecification = retentionSpecification; _allowedReleaseGroupSpecification = allowedReleaseGroupSpecification; + _episodeAiredAfterCutoffSpecification = episodeAiredAfterCutoffSpecification; } public AllowedDownloadSpecification() @@ -37,6 +39,7 @@ namespace NzbDrone.Core.Providers.DecisionEngine public virtual ReportRejectionType IsSatisfiedBy(EpisodeParseResult subject) { if (!_qualityAllowedByProfileSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.QualityNotWanted; + if (!_episodeAiredAfterCutoffSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.EpisodeAiredBeforeCutoff; if (!_upgradeDiskSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.ExistingQualityIsEqualOrBetter; if (!_retentionSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.Retention; if (!_acceptableSizeSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.Size; diff --git a/NzbDrone.Core/Providers/DecisionEngine/EpisodeAiredAfterCutoffSpecification.cs b/NzbDrone.Core/Providers/DecisionEngine/EpisodeAiredAfterCutoffSpecification.cs new file mode 100644 index 000000000..f6778816f --- /dev/null +++ b/NzbDrone.Core/Providers/DecisionEngine/EpisodeAiredAfterCutoffSpecification.cs @@ -0,0 +1,44 @@ +using System.Linq; +using NLog; +using Ninject; +using NzbDrone.Core.Model; + +namespace NzbDrone.Core.Providers.DecisionEngine +{ + public class EpisodeAiredAfterCutoffSpecification + { + private readonly EpisodeProvider _episodeProvider; + private static readonly Logger logger = LogManager.GetCurrentClassLogger(); + + [Inject] + public EpisodeAiredAfterCutoffSpecification(EpisodeProvider episodeProvider) + { + _episodeProvider = episodeProvider; + } + + public EpisodeAiredAfterCutoffSpecification() + { + + } + + public virtual bool IsSatisfiedBy(EpisodeParseResult subject) + { + if (!subject.Series.DownloadEpisodesAiredAfter.HasValue) + { + logger.Debug("{0} does not restrict downloads before date.", subject.Series.Title); + return true; + } + + var episodes = _episodeProvider.GetEpisodesByParseResult(subject); + + if (episodes.Any(episode => episode.AirDate > subject.Series.DownloadEpisodesAiredAfter.Value)) + { + logger.Debug("One or more episodes aired after cutoff, downloading."); + return true; + } + + logger.Debug("Episodes aired before cutoff date: {0}", subject.Series.DownloadEpisodesAiredAfter); + return false; + } + } +} diff --git a/NzbDrone.Core/Repository/Series.cs b/NzbDrone.Core/Repository/Series.cs index 13fce0064..acb0c25b8 100644 --- a/NzbDrone.Core/Repository/Series.cs +++ b/NzbDrone.Core/Repository/Series.cs @@ -48,6 +48,8 @@ namespace NzbDrone.Core.Repository public string Network { get; set; } + public DateTime? DownloadEpisodesAiredAfter { get; set; } + /// /// Gets or sets a value indicating whether this is hidden. /// From 6c78187601a464c4f173b43c8bfdbeb23b31f650 Mon Sep 17 00:00:00 2001 From: Mark McDowall Date: Tue, 18 Sep 2012 23:06:09 -0700 Subject: [PATCH 2/8] EpisodeAiredAfter added to AddSeries UI New: Ability to skip episodes that aired before a certain date, per series. --- .../ProviderTests/EpisodeProviderTest.cs | 2 +- .../ProviderTests/SeriesProviderTest.cs | 4 ++-- NzbDrone.Core/Providers/SeriesProvider.cs | 5 ++++- NzbDrone.Web/Content/NzbDrone.css | 2 +- NzbDrone.Web/Controllers/AddSeriesController.cs | 16 +++++++++++----- NzbDrone.Web/Scripts/NzbDrone/AutoBind.js | 6 ++++++ NzbDrone.Web/Scripts/NzbDrone/addSeries.js | 14 ++++++++++++-- NzbDrone.Web/Views/AddSeries/AddNew.cshtml | 1 + .../Views/AddSeries/ExistingSeries.cshtml | 5 ++++- NzbDrone.Web/Views/AddSeries/Index.cshtml | 9 +++++++++ 10 files changed, 51 insertions(+), 13 deletions(-) diff --git a/NzbDrone.Core.Test/ProviderTests/EpisodeProviderTest.cs b/NzbDrone.Core.Test/ProviderTests/EpisodeProviderTest.cs index 28229bb67..66db8435f 100644 --- a/NzbDrone.Core.Test/ProviderTests/EpisodeProviderTest.cs +++ b/NzbDrone.Core.Test/ProviderTests/EpisodeProviderTest.cs @@ -729,7 +729,7 @@ namespace NzbDrone.Core.Test.ProviderTests //act var seriesProvider = Mocker.Resolve(); - seriesProvider.AddSeries("Test Series","c:\\test\\", tvDbSeriesId, 1); + seriesProvider.AddSeries("Test Series","c:\\test\\", tvDbSeriesId, 1, null); var episodeProvider = Mocker.Resolve(); episodeProvider.RefreshEpisodeInfo(seriesProvider.GetSeries(tvDbSeriesId)); diff --git a/NzbDrone.Core.Test/ProviderTests/SeriesProviderTest.cs b/NzbDrone.Core.Test/ProviderTests/SeriesProviderTest.cs index a003c773e..2d765676e 100644 --- a/NzbDrone.Core.Test/ProviderTests/SeriesProviderTest.cs +++ b/NzbDrone.Core.Test/ProviderTests/SeriesProviderTest.cs @@ -36,7 +36,7 @@ namespace NzbDrone.Core.Test.ProviderTests //Act var seriesProvider = Mocker.Resolve(); - seriesProvider.AddSeries(title, path, tvDbId, qualityProfileId); + seriesProvider.AddSeries(title, path, tvDbId, qualityProfileId, null); //Assert var series = seriesProvider.GetAllSeries(); @@ -54,7 +54,7 @@ namespace NzbDrone.Core.Test.ProviderTests public void add_series_should_fail_if_series_is_less_than_zero(int seriesId) { WithRealDb(); - Assert.Throws(() => Mocker.Resolve().AddSeries("Title", "C:\\Test", seriesId, 1)); + Assert.Throws(() => Mocker.Resolve().AddSeries("Title", "C:\\Test", seriesId, 1, null)); } [Test] diff --git a/NzbDrone.Core/Providers/SeriesProvider.cs b/NzbDrone.Core/Providers/SeriesProvider.cs index aee5b150d..2f223dfa8 100644 --- a/NzbDrone.Core/Providers/SeriesProvider.cs +++ b/NzbDrone.Core/Providers/SeriesProvider.cs @@ -110,7 +110,7 @@ namespace NzbDrone.Core.Providers return series; } - public virtual void AddSeries(string title, string path, int tvDbSeriesId, int qualityProfileId) + public virtual void AddSeries(string title, string path, int tvDbSeriesId, int qualityProfileId, DateTime? airedAfter) { Logger.Info("Adding Series [{0}] Path: [{1}]", tvDbSeriesId, path); @@ -131,6 +131,9 @@ namespace NzbDrone.Core.Providers repoSeries.SeasonFolder = _configProvider.UseSeasonFolder; repoSeries.BacklogSetting = BacklogSettingType.Inherit; + if (airedAfter.HasValue) + repoSeries.DownloadEpisodesAiredAfter = airedAfter; + _database.Insert(repoSeries); } diff --git a/NzbDrone.Web/Content/NzbDrone.css b/NzbDrone.Web/Content/NzbDrone.css index 1e80b38d8..3badb5c64 100644 --- a/NzbDrone.Web/Content/NzbDrone.css +++ b/NzbDrone.Web/Content/NzbDrone.css @@ -115,7 +115,7 @@ hr } -input[type=text], select +input[type=text], input[type=date], select { font-size: small; padding: 2px 2px; diff --git a/NzbDrone.Web/Controllers/AddSeriesController.cs b/NzbDrone.Web/Controllers/AddSeriesController.cs index 4b164671c..04dff1a5a 100644 --- a/NzbDrone.Web/Controllers/AddSeriesController.cs +++ b/NzbDrone.Web/Controllers/AddSeriesController.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Globalization; using System.IO; using System.Linq; using System.Web.Mvc; @@ -116,7 +117,7 @@ namespace NzbDrone.Web.Controllers } [HttpPost] - public JsonResult AddNewSeries(string path, string seriesName, int seriesId, int qualityProfileId) + public JsonResult AddNewSeries(string path, string seriesName, int seriesId, int qualityProfileId, string airedAfter) { if (string.IsNullOrWhiteSpace(path) || String.Equals(path,"null",StringComparison.InvariantCultureIgnoreCase)) return JsonNotificationResult.Error("Couldn't add " + seriesName, "You need a valid root folder"); @@ -127,17 +128,22 @@ namespace NzbDrone.Web.Controllers //Use the created folder name when adding the series path = _diskProvider.CreateDirectory(path); - return AddExistingSeries(path, seriesName, seriesId, qualityProfileId); + return AddExistingSeries(path, seriesName, seriesId, qualityProfileId, airedAfter); } [HttpPost] [JsonErrorFilter] - public JsonResult AddExistingSeries(string path, string seriesName, int seriesId, int qualityProfileId) + public JsonResult AddExistingSeries(string path, string seriesName, int seriesId, int qualityProfileId, string airedAfter) { if (seriesId == 0 || String.IsNullOrWhiteSpace(seriesName)) return JsonNotificationResult.Error("Add Existing series failed.", "Invalid Series information"); - _seriesProvider.AddSeries(seriesName,path, seriesId, qualityProfileId); + DateTime? date = null; + + if (!String.IsNullOrWhiteSpace(airedAfter)) + date = DateTime.Parse(airedAfter, null, DateTimeStyles.RoundtripKind); + + _seriesProvider.AddSeries(seriesName,path, seriesId, qualityProfileId, date); ScanNewSeries(); return JsonNotificationResult.Info(seriesName, "Was added successfully"); @@ -153,7 +159,7 @@ namespace NzbDrone.Web.Controllers //Use the created folder name when adding the series path = _diskProvider.CreateDirectory(path); - return AddExistingSeries(path, seriesName, seriesId, qualityProfileId); + return AddExistingSeries(path, seriesName, seriesId, qualityProfileId, null); } [ChildActionOnly] diff --git a/NzbDrone.Web/Scripts/NzbDrone/AutoBind.js b/NzbDrone.Web/Scripts/NzbDrone/AutoBind.js index 702fa43b2..5c9947995 100644 --- a/NzbDrone.Web/Scripts/NzbDrone/AutoBind.js +++ b/NzbDrone.Web/Scripts/NzbDrone/AutoBind.js @@ -44,4 +44,10 @@ } }); }); + + $('.jQuery-dateTime').livequery(function () { + $(this).datepicker({ + dateFormat: "yy-mm-dd" + }); + }); }); \ No newline at end of file diff --git a/NzbDrone.Web/Scripts/NzbDrone/addSeries.js b/NzbDrone.Web/Scripts/NzbDrone/addSeries.js index 2455de01f..b52489cf3 100644 --- a/NzbDrone.Web/Scripts/NzbDrone/addSeries.js +++ b/NzbDrone.Web/Scripts/NzbDrone/addSeries.js @@ -24,6 +24,7 @@ $(".addExistingButton").live('click', function() { var title = $(this).siblings(".seriesLookup").val(); var seriesId = $(this).siblings(".seriesId").val(); var qualityId = $(this).siblings(".qualitySelector").val(); + var date = $(this).siblings('.aired-after').val(); var path = root.find(".seriesPathValue Label").text(); @@ -41,7 +42,7 @@ $(".addExistingButton").live('click', function() { $.ajax({ type: "POST", url: addSeriesUrl, - data: jQuery.param({ path: path, seriesName: title, seriesId: seriesId, qualityProfileId: qualityId }), + data: jQuery.param({ path: path, seriesName: title, seriesId: seriesId, qualityProfileId: qualityId, airedAfter: date }), error: function(req, status, error) { alert("Sorry! We could not add " + path + " at this time. " + error); }, @@ -64,6 +65,14 @@ function reloadExistingSeries() { }); } +$(".aired-after-master").live('change', function () { + + var date = $(this).val(); + $("#existingSeries").find(".aired-after").each(function () { + $(this).val(date); + }); +}); + //RootDir //Delete RootDir $('#rootDirs .actionButton img').live('click', function (image) { @@ -116,11 +125,12 @@ $('#saveNewSeries').live('click', function () { var seriesId = $("#newSeriesId").val(); var qualityId = $("#qualityList").val(); var path = $('#newSeriesPath').val(); + var date = $('#newAiredAfter').val(); $.ajax({ type: "POST", url: addNewSeriesUrl, - data: jQuery.param({ path: path, seriesName: seriesTitle, seriesId: seriesId, qualityProfileId: qualityId }), + data: jQuery.param({ path: path, seriesName: seriesTitle, seriesId: seriesId, qualityProfileId: qualityId, airedAfter: date }), error: function (req, status, error) { alert("Sorry! We could not add " + path + " at this time. " + error); }, diff --git a/NzbDrone.Web/Views/AddSeries/AddNew.cshtml b/NzbDrone.Web/Views/AddSeries/AddNew.cshtml index ebd84fb33..1d4be560d 100644 --- a/NzbDrone.Web/Views/AddSeries/AddNew.cshtml +++ b/NzbDrone.Web/Views/AddSeries/AddNew.cshtml @@ -7,6 +7,7 @@ @Html.DropDownList("newSeriesPath", new SelectList((IList)ViewData["RootDirs"]), new { style = "width: 406px; margin-left: 0px;" }) @Html.DropDownList("qualityList", (SelectList)ViewData["QualityProfiles"], new { @class = "qualitySelector" }) + @Html.TextBox("newAiredAfter", "", new { type = "date", @class = "jQuery-dateTime aired-after", title = "Only download episodes that aired after the choosen date" }) \ No newline at end of file diff --git a/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml b/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml index 1e95d2ddd..dfb807ffb 100644 --- a/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml +++ b/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml @@ -23,6 +23,8 @@ else { @Html.DropDownList(Guid.NewGuid().ToString(), Model.Quality, new { @class = "qualitySelector masterQualitySelector" }) + @Html.TextBox(Guid.NewGuid().ToString(), "", new { type="date", @class = "jQuery-dateTime aired-after-master", title = "Skip episodes that aired before the choosen date" }) + foreach (var series in Model.ExistingSeries) {
@@ -30,9 +32,10 @@ else
- + @Html.Hidden("seriesId", series.Item3, new { @class = "seriesId" }) @Html.DropDownList(Guid.NewGuid().ToString(), Model.Quality, new { @class = "qualitySelector" }) + @Html.TextBox(Guid.NewGuid().ToString(), "", new { type="date", @class = "jQuery-dateTime aired-after", title = "Only download episodes that aired after the choosen date" })
diff --git a/NzbDrone.Web/Views/AddSeries/Index.cshtml b/NzbDrone.Web/Views/AddSeries/Index.cshtml index fa8b5f638..14746e52a 100644 --- a/NzbDrone.Web/Views/AddSeries/Index.cshtml +++ b/NzbDrone.Web/Views/AddSeries/Index.cshtml @@ -19,6 +19,11 @@ left: 415px; position: relative; } + + .aired-after-master { + left: 430px; + position: relative; + } .seriesPathValue { @@ -45,6 +50,10 @@ cursor: pointer; text-decoration: underline; } + + input[type=date].aired-after { + margin-left: 10px; + } } From 3061219367319573de6f6829a39c72ec927df84e Mon Sep 17 00:00:00 2001 From: Mark McDowall Date: Wed, 19 Sep 2012 00:07:19 -0700 Subject: [PATCH 3/8] EpisodeAiredAfter added to edit/editor --- NzbDrone.Core/Providers/SeriesProvider.cs | 1 + NzbDrone.Web/Content/SeriesEditor.css | 17 +++++++- NzbDrone.Web/Content/Settings.css | 42 +++++++------------ NzbDrone.Web/Controllers/SeriesController.cs | 13 ++++-- NzbDrone.Web/Models/SeriesModel.cs | 6 ++- NzbDrone.Web/NzbDrone.Web.csproj | 2 +- NzbDrone.Web/Scripts/NzbDrone/AutoBind.js | 2 +- NzbDrone.Web/Scripts/NzbDrone/series.js | 4 +- NzbDrone.Web/Views/AddSeries/AddNew.cshtml | 2 +- .../Views/AddSeries/ExistingSeries.cshtml | 4 +- ...{SingleSeriesEditor.cshtml => Edit.cshtml} | 7 +++- NzbDrone.Web/Views/Series/Editor.cshtml | 26 +++++++++--- NzbDrone.Web/Views/Series/EditorItem.cshtml | 1 + 13 files changed, 78 insertions(+), 49 deletions(-) rename NzbDrone.Web/Views/Series/{SingleSeriesEditor.cshtml => Edit.cshtml} (77%) diff --git a/NzbDrone.Core/Providers/SeriesProvider.cs b/NzbDrone.Core/Providers/SeriesProvider.cs index 2f223dfa8..08e129def 100644 --- a/NzbDrone.Core/Providers/SeriesProvider.cs +++ b/NzbDrone.Core/Providers/SeriesProvider.cs @@ -232,6 +232,7 @@ namespace NzbDrone.Core.Providers series.SeasonFolder = edited.SeasonFolder; series.BacklogSetting = edited.BacklogSetting; series.Path = edited.Path; + series.DownloadEpisodesAiredAfter = edited.DownloadEpisodesAiredAfter; } _database.UpdateMany(allSeries); diff --git a/NzbDrone.Web/Content/SeriesEditor.css b/NzbDrone.Web/Content/SeriesEditor.css index be5178250..f41e13fcf 100644 --- a/NzbDrone.Web/Content/SeriesEditor.css +++ b/NzbDrone.Web/Content/SeriesEditor.css @@ -4,7 +4,7 @@ } .checkboxColumn { - width: 110px; + width: 50px; text-align: center; } @@ -13,7 +13,7 @@ text-align: center; } -table input[type="text"], table select { +table input[type="text"], table input[type="date"], table select { margin: 2px 2px; } @@ -37,6 +37,19 @@ th .footer-control-quality { width: 120px; } +td .aired-after { + width: 80px; +} + +th .footer-control-boolean { + width: 90px; +} + +th .footer-control-aired-after { + width: 80px; +} + + #stylized, .settingsForm { overflow: hidden; } diff --git a/NzbDrone.Web/Content/Settings.css b/NzbDrone.Web/Content/Settings.css index 3fdbdff45..59d5d25ea 100644 --- a/NzbDrone.Web/Content/Settings.css +++ b/NzbDrone.Web/Content/Settings.css @@ -1,5 +1,4 @@ -p, h1, form, button -{ +p, h1, form, button { border: 0; margin: 0; padding: 0; @@ -9,21 +8,18 @@ display: none; } -.spacer -{ +.spacer { clear: both; height: 1px; } -.settingsForm -{ +.settingsForm { width: 620px; padding: 14px; } -#stylized p -{ +#stylized p { font-size: 11px; color: #666666; margin-bottom: 20px; @@ -31,8 +27,7 @@ padding-bottom: 10px; } -#stylized .labelClass -{ +#stylized .labelClass { display: block; font-weight: bold; text-align: right; @@ -41,8 +36,7 @@ margin-bottom: -10px; } -#stylized .small -{ +#stylized .small { color: #666666; display: block; font-size: 11px; @@ -51,8 +45,7 @@ width: 340px; } -#stylized .inputClass -{ +#stylized .inputClass { float: left; padding: 2px 2px; border: solid 1px #aacfe4; @@ -60,19 +53,16 @@ margin: 4px 0 20px 10px; } -#stylized .selectClass -{ +#stylized .selectClass { width: 206px; } -#stylized .checkClass -{ +#stylized .checkClass { margin: 12px 0px 20px 10px; border: none; } -#stylized button -{ +#stylized button { clear: both; margin-left: 220px; margin-bottom: 10px; @@ -85,8 +75,7 @@ } -#saveAjax -{ +#saveAjax { padding-left: 6px; margin-bottom: -7px; width: 20px; @@ -94,24 +83,21 @@ display: none; } -#save_button[disabled="disabled"] -{ +#save_button[disabled="disabled"] { padding: 0px 6px 0px 6px; border: 2px outset ButtonFace; color: lightgrey; cursor: progress; } -.ui-dialog-buttonset .ui-delete-button -{ +.ui-dialog-buttonset .ui-delete-button { background: url("jQueryUI/images/ui-bg_flat_30_b40404_40x100.png") repeat-x scroll 50% 50% #B40404; border: 1px solid #FFFFFF; color: #FFFFFF; font-weight: normal; } -.ui-dialog-buttonset .ui-delete-button:active -{ +.ui-dialog-buttonset .ui-delete-button:active { background: url("jQueryUI/images/ui-bg_flat_30_616161_40x100.png") repeat-x scroll 50% 50% #616161; border: 1px solid #FFFFFF; color: #FFFFFF; diff --git a/NzbDrone.Web/Controllers/SeriesController.cs b/NzbDrone.Web/Controllers/SeriesController.cs index e18e7ef4d..a1f637f2c 100644 --- a/NzbDrone.Web/Controllers/SeriesController.cs +++ b/NzbDrone.Web/Controllers/SeriesController.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Globalization; using System.IO; using System.Linq; using System.Web.Mvc; @@ -44,7 +45,7 @@ namespace NzbDrone.Web.Controllers return View((object)serialized); } - public ActionResult SingleSeriesEditor(int seriesId) + public ActionResult Edit(int seriesId) { var profiles = _qualityProvider.All(); ViewData["SelectList"] = new SelectList(profiles, "QualityProfileId", "Name"); @@ -63,7 +64,7 @@ namespace NzbDrone.Web.Controllers } [HttpPost] - public EmptyResult SaveSingleSeriesEditor(SeriesModel seriesModel) + public EmptyResult Edit(SeriesModel seriesModel) { var series = _seriesProvider.GetSeries(seriesModel.SeriesId); series.Monitored = seriesModel.Monitored; @@ -72,6 +73,9 @@ namespace NzbDrone.Web.Controllers series.Path = seriesModel.Path; series.BacklogSetting = (BacklogSettingType)seriesModel.BacklogSetting; + if (!String.IsNullOrWhiteSpace(seriesModel.DownloadEpisodesAiredAfter)) + series.DownloadEpisodesAiredAfter = DateTime.Parse(seriesModel.DownloadEpisodesAiredAfter, null, DateTimeStyles.RoundtripKind); + _seriesProvider.UpdateSeries(series); return new EmptyResult(); @@ -172,7 +176,7 @@ namespace NzbDrone.Web.Controllers } [HttpPost] - public JsonResult SaveEditor(List series) + public JsonResult Editor(List series) { //Save edits if (series == null || series.Count == 0) @@ -204,7 +208,8 @@ namespace NzbDrone.Web.Controllers EpisodeFileCount = s.EpisodeFileCount, NextAiring = s.NextAiring == null ? String.Empty : s.NextAiring.Value.ToBestDateString(), NextAiringSorter = s.NextAiring == null ? "12/31/9999" : s.NextAiring.Value.ToString("MM/dd/yyyy"), - AirTime = s.AirTimes + AirTime = s.AirTimes, + DownloadEpisodesAiredAfter = s.DownloadEpisodesAiredAfter.HasValue ? s.DownloadEpisodesAiredAfter.Value.ToString("yyyy-MM-dd") : String.Empty }).ToList(); return series; diff --git a/NzbDrone.Web/Models/SeriesModel.cs b/NzbDrone.Web/Models/SeriesModel.cs index 652d1b9f8..b61204248 100644 --- a/NzbDrone.Web/Models/SeriesModel.cs +++ b/NzbDrone.Web/Models/SeriesModel.cs @@ -28,7 +28,7 @@ namespace NzbDrone.Web.Models public string Details { get; set; } public string Network { get; set; } public string AirTime { get; set; } - + public IList Seasons { get; set; } //View & Edit @@ -52,5 +52,9 @@ namespace NzbDrone.Web.Models [DisplayName("Backlog Setting")] [Description("Should NzbDrone search for missing episodes every 30 days?")] public int BacklogSetting { get; set; } + + [DisplayName("Download Episodes Aired After")] + [Description("Should NzbDrone only download episodes a certain date?")] + public string DownloadEpisodesAiredAfter { get; set; } } } \ No newline at end of file diff --git a/NzbDrone.Web/NzbDrone.Web.csproj b/NzbDrone.Web/NzbDrone.Web.csproj index 1aaeb81f9..c906c085a 100644 --- a/NzbDrone.Web/NzbDrone.Web.csproj +++ b/NzbDrone.Web/NzbDrone.Web.csproj @@ -534,7 +534,7 @@ - + diff --git a/NzbDrone.Web/Scripts/NzbDrone/AutoBind.js b/NzbDrone.Web/Scripts/NzbDrone/AutoBind.js index 5c9947995..2c31f28ad 100644 --- a/NzbDrone.Web/Scripts/NzbDrone/AutoBind.js +++ b/NzbDrone.Web/Scripts/NzbDrone/AutoBind.js @@ -45,7 +45,7 @@ }); }); - $('.jQuery-dateTime').livequery(function () { + $('.jQuery-datepicker').livequery(function () { $(this).datepicker({ dateFormat: "yy-mm-dd" }); diff --git a/NzbDrone.Web/Scripts/NzbDrone/series.js b/NzbDrone.Web/Scripts/NzbDrone/series.js index c630adf50..7dc54f64c 100644 --- a/NzbDrone.Web/Scripts/NzbDrone/series.js +++ b/NzbDrone.Web/Scripts/NzbDrone/series.js @@ -1,5 +1,5 @@ -var seriesEditorUrl = '../Series/SingleSeriesEditor'; -var saveSeriesEditorUrl = '../Series/SaveSingleSeriesEditor'; +var seriesEditorUrl = '../Series/Edit'; +var saveSeriesEditorUrl = '../Series/Edit'; var seriesDeleteUrl = '../Series/DeleteSeries'; $("#seriesEditor").dialog({ diff --git a/NzbDrone.Web/Views/AddSeries/AddNew.cshtml b/NzbDrone.Web/Views/AddSeries/AddNew.cshtml index 1d4be560d..5c46dfeaa 100644 --- a/NzbDrone.Web/Views/AddSeries/AddNew.cshtml +++ b/NzbDrone.Web/Views/AddSeries/AddNew.cshtml @@ -7,7 +7,7 @@
@Html.DropDownList("newSeriesPath", new SelectList((IList)ViewData["RootDirs"]), new { style = "width: 406px; margin-left: 0px;" }) @Html.DropDownList("qualityList", (SelectList)ViewData["QualityProfiles"], new { @class = "qualitySelector" }) - @Html.TextBox("newAiredAfter", "", new { type = "date", @class = "jQuery-dateTime aired-after", title = "Only download episodes that aired after the choosen date" }) + @Html.TextBox("newAiredAfter", "", new { type = "date", @class = "jQuery-datepicker aired-after", title = "Only download episodes that aired after the choosen date" }) \ No newline at end of file diff --git a/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml b/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml index dfb807ffb..fe0a51a40 100644 --- a/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml +++ b/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml @@ -23,7 +23,7 @@ else { @Html.DropDownList(Guid.NewGuid().ToString(), Model.Quality, new { @class = "qualitySelector masterQualitySelector" }) - @Html.TextBox(Guid.NewGuid().ToString(), "", new { type="date", @class = "jQuery-dateTime aired-after-master", title = "Skip episodes that aired before the choosen date" }) + @Html.TextBox(Guid.NewGuid().ToString(), "", new { type="date", @class = "jQuery-datepicker aired-after-master", title = "Skip episodes that aired before the choosen date" }) foreach (var series in Model.ExistingSeries) { @@ -35,7 +35,7 @@ else @Html.Hidden("seriesId", series.Item3, new { @class = "seriesId" }) @Html.DropDownList(Guid.NewGuid().ToString(), Model.Quality, new { @class = "qualitySelector" }) - @Html.TextBox(Guid.NewGuid().ToString(), "", new { type="date", @class = "jQuery-dateTime aired-after", title = "Only download episodes that aired after the choosen date" }) + @Html.TextBox(Guid.NewGuid().ToString(), "", new { type="date", @class = "jQuery-datepicker aired-after", title = "Only download episodes that aired after the choosen date" }) diff --git a/NzbDrone.Web/Views/Series/SingleSeriesEditor.cshtml b/NzbDrone.Web/Views/Series/Edit.cshtml similarity index 77% rename from NzbDrone.Web/Views/Series/SingleSeriesEditor.cshtml rename to NzbDrone.Web/Views/Series/Edit.cshtml index 8f6e29cc3..a2bf391e2 100644 --- a/NzbDrone.Web/Views/Series/SingleSeriesEditor.cshtml +++ b/NzbDrone.Web/Views/Series/Edit.cshtml @@ -12,7 +12,7 @@
- @using (Html.BeginForm("SaveSingleSeriesEditor", "Series", FormMethod.Post, new { id = "SeriesEditorForm", name = "SeriesEditorForm", @class = "settingsForm" })) + @using (Html.BeginForm("Edit", "Series", FormMethod.Post, new { id = "SeriesEditorForm", name = "SeriesEditorForm", @class = "settingsForm" })) { @Html.HiddenFor(m => m.SeriesId) @Html.HiddenFor(m => m.Status) @@ -36,5 +36,10 @@ @Html.DescriptionFor(m => m.BacklogSetting) @Html.DropDownListFor(m => m.BacklogSetting, (SelectList)ViewData["BacklogSettingSelectList"], new { @class = "inputClass" }) + + + @Html.TextBoxFor(m => m.DownloadEpisodesAiredAfter, new { type = "date", @class = "inputClass jQuery-datepicker" }) }
\ No newline at end of file diff --git a/NzbDrone.Web/Views/Series/Editor.cshtml b/NzbDrone.Web/Views/Series/Editor.cshtml index 3b58995b0..93ec6bbba 100644 --- a/NzbDrone.Web/Views/Series/Editor.cshtml +++ b/NzbDrone.Web/Views/Series/Editor.cshtml @@ -16,7 +16,7 @@ } -@using (Html.BeginForm("SaveEditor", "Series", FormMethod.Post, new { id = "SeriesEditor", name = "SeriesEditor" })) +@using (Html.BeginForm("Editor", "Series", FormMethod.Post, new { id = "SeriesEditor", name = "SeriesEditor" })) { @@ -24,9 +24,10 @@ - - - + + + + @@ -46,14 +47,17 @@ @Html.DropDownList("masterQualitySelector", (SelectList)ViewData["MasterProfileSelectList"], new { @class = "footer-control-quality masterSelector master-quality", disabled = true }) + + } \ No newline at end of file From d9d902702298198d9f135fb26906706d1876374f Mon Sep 17 00:00:00 2001 From: Mark McDowall Date: Wed, 19 Sep 2012 00:32:34 -0700 Subject: [PATCH 4/8] Series Editor backend cleanup --- NzbDrone.Web/Controllers/SeriesController.cs | 17 ++++++++++++++--- NzbDrone.Web/Views/Series/Editor.cshtml | 2 +- NzbDrone.Web/Views/Series/EditorItem.cshtml | 2 +- 3 files changed, 16 insertions(+), 5 deletions(-) diff --git a/NzbDrone.Web/Controllers/SeriesController.cs b/NzbDrone.Web/Controllers/SeriesController.cs index a1f637f2c..8691827ad 100644 --- a/NzbDrone.Web/Controllers/SeriesController.cs +++ b/NzbDrone.Web/Controllers/SeriesController.cs @@ -170,19 +170,30 @@ namespace NzbDrone.Web.Controllers masterBacklogList.Insert(0, new KeyValuePair(-10, "Select...")); ViewData["MasterBacklogSettingSelectList"] = new SelectList(masterBacklogList, "Key", "Value"); - var series = _seriesProvider.GetAllSeries().OrderBy(o => SortHelper.SkipArticles(o.Title)); + var series = GetSeriesModels(_seriesProvider.GetAllSeries()).OrderBy(o => SortHelper.SkipArticles(o.Title)); return View(series); } [HttpPost] - public JsonResult Editor(List series) + public JsonResult Editor(List series) { //Save edits if (series == null || series.Count == 0) return JsonNotificationResult.Oops("Invalid post data"); - _seriesProvider.UpdateFromSeriesEditor(series); + _seriesProvider.UpdateFromSeriesEditor(series.Select(s => new Series + { + SeriesId = s.SeriesId, + QualityProfileId = s.QualityProfileId, + Monitored = s.Monitored, + SeasonFolder = s.SeasonFolder, + BacklogSetting = (BacklogSettingType)s.BacklogSetting, + Path = s.Path, + DownloadEpisodesAiredAfter = String.IsNullOrWhiteSpace(s.DownloadEpisodesAiredAfter) ? (DateTime?)null + : DateTime.Parse(s.DownloadEpisodesAiredAfter, null, DateTimeStyles.RoundtripKind) + } + ).ToList()); return JsonNotificationResult.Info("Series Mass Edit Saved"); } diff --git a/NzbDrone.Web/Views/Series/Editor.cshtml b/NzbDrone.Web/Views/Series/Editor.cshtml index 93ec6bbba..499a082a6 100644 --- a/NzbDrone.Web/Views/Series/Editor.cshtml +++ b/NzbDrone.Web/Views/Series/Editor.cshtml @@ -1,5 +1,5 @@ @using NzbDrone.Web.Helpers -@model IEnumerable +@model IEnumerable @{ViewBag.Title = "Series Editor";} @section HeaderContent diff --git a/NzbDrone.Web/Views/Series/EditorItem.cshtml b/NzbDrone.Web/Views/Series/EditorItem.cshtml index 6efda18b8..a34dc8ea6 100644 --- a/NzbDrone.Web/Views/Series/EditorItem.cshtml +++ b/NzbDrone.Web/Views/Series/EditorItem.cshtml @@ -1,4 +1,4 @@ -@model NzbDrone.Core.Repository.Series +@model NzbDrone.Web.Models.SeriesModel @using NzbDrone.Core.Model @using NzbDrone.Core.Repository.Quality @using NzbDrone.Web.Helpers From bd5ced1540deef0fbb21068ad54d848254ea3fbc Mon Sep 17 00:00:00 2001 From: Mark McDowall Date: Wed, 19 Sep 2012 08:13:26 -0700 Subject: [PATCH 5/8] Fixed broken tests. --- .../AllowedDownloadSpecificationFixture.cs | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/AllowedDownloadSpecificationFixture.cs b/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/AllowedDownloadSpecificationFixture.cs index 620eece0b..0feeeeca4 100644 --- a/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/AllowedDownloadSpecificationFixture.cs +++ b/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/AllowedDownloadSpecificationFixture.cs @@ -52,6 +52,10 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests Mocker.GetMock() .Setup(c => c.IsSatisfiedBy(It.IsAny())) .Returns(true); + + Mocker.GetMock() + .Setup(c => c.IsSatisfiedBy(It.IsAny())) + .Returns(true); } private void WithProfileNotAllowed() @@ -89,6 +93,13 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests .Returns(false); } + private void WithAiredBeforeCutoff() + { + Mocker.GetMock() + .Setup(c => c.IsSatisfiedBy(It.IsAny())) + .Returns(false); + } + [Test] public void should_be_allowed_if_all_conditions_are_met() { @@ -130,6 +141,13 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests spec.IsSatisfiedBy(parseResult).Should().Be(ReportRejectionType.Retention); } + [Test] + public void should_not_be_allowed_if_episode_aired_before_cutoff() + { + WithAiredBeforeCutoff(); + spec.IsSatisfiedBy(parseResult).Should().Be(ReportRejectionType.EpisodeAiredBeforeCutoff); + } + [Test] public void should_not_be_allowed_if_none_of_conditions_are_met() { From 15e4a286d1e0b173225863107dfd645d5b00e5c6 Mon Sep 17 00:00:00 2001 From: Mark McDowall Date: Wed, 19 Sep 2012 09:18:03 -0700 Subject: [PATCH 6/8] Fixed debugging issues. Add Series tweaks. Add series buttons are disabled on click to prevent multiple clicks. --- NzbDrone.App.Test/NzbDrone.App.Test.csproj | 18 +++++ .../NzbDrone.Common.Test.csproj | 18 +++++ NzbDrone.Common/NzbDrone.Common.csproj | 18 +++++ NzbDrone.Core.Test/NzbDrone.Core.Test.csproj | 18 +++++ .../NzbDrone.Services.Service.csproj | 18 +++++ .../NzbDrone.Services.Tests.csproj | 18 +++++ .../NzbDrone.Test.Common.csproj | 18 +++++ .../NzbDrone.Web.UI.Automation.csproj | 18 +++++ NzbDrone.Web/Content/NzbDrone.css | 10 --- .../Controllers/AddSeriesController.cs | 66 ++++------------- NzbDrone.Web/NzbDrone.Web.csproj | 24 +++++-- NzbDrone.Web/Scripts/NzbDrone/addSeries.js | 36 +++------- NzbDrone.Web/Views/Shared/QuickAdd.cshtml | 15 ---- .../_MINIPROFILER UPDATED Layout.cshtml | 45 ------------ NzbDrone.sln | 70 ++++++++++--------- 15 files changed, 225 insertions(+), 185 deletions(-) delete mode 100644 NzbDrone.Web/Views/Shared/QuickAdd.cshtml delete mode 100644 NzbDrone.Web/Views/Shared/_MINIPROFILER UPDATED Layout.cshtml diff --git a/NzbDrone.App.Test/NzbDrone.App.Test.csproj b/NzbDrone.App.Test/NzbDrone.App.Test.csproj index 8dfd6f64a..41c6b72c8 100644 --- a/NzbDrone.App.Test/NzbDrone.App.Test.csproj +++ b/NzbDrone.App.Test/NzbDrone.App.Test.csproj @@ -34,6 +34,24 @@ 4 x86 + + true + bin\x86\Debug\ + DEBUG;TRACE + full + x86 + prompt + MinimumRecommendedRules.ruleset + + + bin\x86\Release\ + TRACE + true + pdbonly + x86 + prompt + MinimumRecommendedRules.ruleset + ..\packages\NBuilder.3.0.1.1\lib\FizzWare.NBuilder.dll diff --git a/NzbDrone.Common.Test/NzbDrone.Common.Test.csproj b/NzbDrone.Common.Test/NzbDrone.Common.Test.csproj index a0c96e899..6e333950b 100644 --- a/NzbDrone.Common.Test/NzbDrone.Common.Test.csproj +++ b/NzbDrone.Common.Test/NzbDrone.Common.Test.csproj @@ -34,6 +34,24 @@ 4 x86 + + true + bin\x86\Debug\ + DEBUG;TRACE + full + x86 + prompt + MinimumRecommendedRules.ruleset + + + bin\x86\Release\ + TRACE + true + pdbonly + x86 + prompt + MinimumRecommendedRules.ruleset + False diff --git a/NzbDrone.Common/NzbDrone.Common.csproj b/NzbDrone.Common/NzbDrone.Common.csproj index 7aa2c9795..9a8e02d72 100644 --- a/NzbDrone.Common/NzbDrone.Common.csproj +++ b/NzbDrone.Common/NzbDrone.Common.csproj @@ -34,6 +34,24 @@ 4 x86 + + true + bin\x86\Debug\ + DEBUG;TRACE + full + x86 + prompt + MinimumRecommendedRules.ruleset + + + bin\x86\Release\ + TRACE + true + pdbonly + x86 + prompt + MinimumRecommendedRules.ruleset + ..\Libraries\Exceptioneer.WindowsFormsClient.dll diff --git a/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj b/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj index bb8f27d12..540e2f486 100644 --- a/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj +++ b/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj @@ -34,6 +34,24 @@ 4 x86 + + true + bin\x86\Debug\ + DEBUG;TRACE + full + x86 + prompt + MinimumRecommendedRules.ruleset + + + bin\x86\Release\ + TRACE + true + pdbonly + x86 + prompt + MinimumRecommendedRules.ruleset + True diff --git a/NzbDrone.Services/NzbDrone.Services.Service/NzbDrone.Services.Service.csproj b/NzbDrone.Services/NzbDrone.Services.Service/NzbDrone.Services.Service.csproj index 7ad30f6f5..5e178474b 100644 --- a/NzbDrone.Services/NzbDrone.Services.Service/NzbDrone.Services.Service.csproj +++ b/NzbDrone.Services/NzbDrone.Services.Service/NzbDrone.Services.Service.csproj @@ -335,6 +335,24 @@ 10.0 $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + + true + bin\ + DEBUG;TRACE + full + x86 + prompt + MinimumRecommendedRules.ruleset + + + bin\ + TRACE + true + pdbonly + x86 + prompt + MinimumRecommendedRules.ruleset + diff --git a/NzbDrone.Services/NzbDrone.Services.Tests/NzbDrone.Services.Tests.csproj b/NzbDrone.Services/NzbDrone.Services.Tests/NzbDrone.Services.Tests.csproj index f7b2c815f..2e71b9bd6 100644 --- a/NzbDrone.Services/NzbDrone.Services.Tests/NzbDrone.Services.Tests.csproj +++ b/NzbDrone.Services/NzbDrone.Services.Tests/NzbDrone.Services.Tests.csproj @@ -33,6 +33,24 @@ prompt 4 + + true + bin\x86\Debug\ + DEBUG;TRACE + full + x86 + prompt + MinimumRecommendedRules.ruleset + + + bin\x86\Release\ + TRACE + true + pdbonly + x86 + prompt + MinimumRecommendedRules.ruleset + ..\..\packages\NBuilder.3.0.1.1\lib\FizzWare.NBuilder.dll diff --git a/NzbDrone.Test.Common/NzbDrone.Test.Common.csproj b/NzbDrone.Test.Common/NzbDrone.Test.Common.csproj index 48a1913ba..75821406a 100644 --- a/NzbDrone.Test.Common/NzbDrone.Test.Common.csproj +++ b/NzbDrone.Test.Common/NzbDrone.Test.Common.csproj @@ -34,6 +34,24 @@ 4 x86 + + true + bin\x86\Debug\ + DEBUG;TRACE + full + x86 + prompt + MinimumRecommendedRules.ruleset + + + bin\x86\Release\ + TRACE + true + pdbonly + x86 + prompt + MinimumRecommendedRules.ruleset + ..\packages\CommonServiceLocator.1.0\lib\NET35\Microsoft.Practices.ServiceLocation.dll diff --git a/NzbDrone.Web.UI.Test/NzbDrone.Web.UI.Automation.csproj b/NzbDrone.Web.UI.Test/NzbDrone.Web.UI.Automation.csproj index 8d37a0e5c..872c609e1 100644 --- a/NzbDrone.Web.UI.Test/NzbDrone.Web.UI.Automation.csproj +++ b/NzbDrone.Web.UI.Test/NzbDrone.Web.UI.Automation.csproj @@ -34,6 +34,24 @@ 4 x86 + + true + bin\x86\Debug\ + DEBUG;TRACE + full + x86 + prompt + MinimumRecommendedRules.ruleset + + + bin\x86\Release\ + TRACE + true + pdbonly + x86 + prompt + MinimumRecommendedRules.ruleset + ..\packages\FluentAssertions.1.7.0\Lib\net40\FluentAssertions.dll diff --git a/NzbDrone.Web/Content/NzbDrone.css b/NzbDrone.Web/Content/NzbDrone.css index 3badb5c64..fe69fb11c 100644 --- a/NzbDrone.Web/Content/NzbDrone.css +++ b/NzbDrone.Web/Content/NzbDrone.css @@ -181,28 +181,18 @@ button span, input[type="button"] span, input[type="submit"] span, input[type="r height: 25px; } - .dialog { margin-left: auto; margin-right: auto; } - .qualitySelector { min-width: 60px; width: auto; } -#quickAdd -{ - position: fixed; - top: 30px; - right: 15px; -} - - #localSeriesLookup { width: 220px; diff --git a/NzbDrone.Web/Controllers/AddSeriesController.cs b/NzbDrone.Web/Controllers/AddSeriesController.cs index 04dff1a5a..9d8d93b36 100644 --- a/NzbDrone.Web/Controllers/AddSeriesController.cs +++ b/NzbDrone.Web/Controllers/AddSeriesController.cs @@ -44,11 +44,9 @@ namespace NzbDrone.Web.Controllers _diskProvider = diskProvider; } - [HttpPost] - public EmptyResult ScanNewSeries() + public ActionResult Index() { - _jobProvider.QueueJob(typeof(ImportNewSeriesJob)); - return new EmptyResult(); + return View(); } public ActionResult AddNew() @@ -67,11 +65,6 @@ namespace NzbDrone.Web.Controllers return View(); } - public ActionResult Index() - { - return View(); - } - public ActionResult ExistingSeries() { var result = new ExistingSeriesModel(); @@ -144,52 +137,11 @@ namespace NzbDrone.Web.Controllers date = DateTime.Parse(airedAfter, null, DateTimeStyles.RoundtripKind); _seriesProvider.AddSeries(seriesName,path, seriesId, qualityProfileId, date); - ScanNewSeries(); + _jobProvider.QueueJob(typeof(ImportNewSeriesJob)); return JsonNotificationResult.Info(seriesName, "Was added successfully"); } - [HttpPost] - public JsonResult QuickAddNewSeries(string seriesName, int seriesId, int qualityProfileId) - { - var path = _rootFolderProvider.GetMostFreeRootDir(); - path = Path.Combine(path, MediaFileProvider.CleanFilename(seriesName)); - - //Create the folder for the new series - //Use the created folder name when adding the series - path = _diskProvider.CreateDirectory(path); - - return AddExistingSeries(path, seriesName, seriesId, qualityProfileId, null); - } - - [ChildActionOnly] - public ActionResult QuickAdd() - { - var defaultQuality = _configProvider.DefaultQualityProfile; - var qualityProfiles = _qualityProvider.All(); - - ViewData["qualityProfiles"] = new SelectList( - qualityProfiles, - "QualityProfileId", - "Name", - defaultQuality); - - return PartialView(); - } - - - [HttpPost] - [JsonErrorFilter] - public JsonResult SaveRootDir(string path) - { - if (String.IsNullOrWhiteSpace(path)) - JsonNotificationResult.Error("Can't add root folder", "Path can not be empty"); - - _rootFolderProvider.Add(new RootDir { Path = path }); - - return JsonNotificationResult.Info("Root Folder saved", "Root folder saved successfully."); - } - [HttpGet] public JsonResult LookupSeries(string term) { @@ -234,6 +186,18 @@ namespace NzbDrone.Web.Controllers return PartialView("RootDir"); } + [HttpPost] + [JsonErrorFilter] + public JsonResult SaveRootDir(string path) + { + if (String.IsNullOrWhiteSpace(path)) + JsonNotificationResult.Error("Can't add root folder", "Path can not be empty"); + + _rootFolderProvider.Add(new RootDir { Path = path }); + + return JsonNotificationResult.Info("Root Folder saved", "Root folder saved successfully."); + } + [JsonErrorFilter] public JsonResult DeleteRootDir(string path) { diff --git a/NzbDrone.Web/NzbDrone.Web.csproj b/NzbDrone.Web/NzbDrone.Web.csproj index c906c085a..5b8c486da 100644 --- a/NzbDrone.Web/NzbDrone.Web.csproj +++ b/NzbDrone.Web/NzbDrone.Web.csproj @@ -476,9 +476,6 @@ - - - @@ -559,9 +556,6 @@ - - - @@ -569,6 +563,24 @@ 10.0 $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + + true + bin\ + DEBUG;TRACE + full + x86 + prompt + BasicCorrectnessRules.ruleset + + + bin\ + TRACE + true + pdbonly + x86 + prompt + MinimumRecommendedRules.ruleset + diff --git a/NzbDrone.Web/Scripts/NzbDrone/addSeries.js b/NzbDrone.Web/Scripts/NzbDrone/addSeries.js index b52489cf3..219d87eef 100644 --- a/NzbDrone.Web/Scripts/NzbDrone/addSeries.js +++ b/NzbDrone.Web/Scripts/NzbDrone/addSeries.js @@ -1,7 +1,6 @@ //URLs var addSeriesUrl = '../AddSeries/AddExistingSeries'; var addNewSeriesUrl = '../AddSeries/AddNewSeries'; -var quickAddNewSeriesUrl = '../AddSeries/QuickAddNewSeries'; var existingSeriesUrl = '../AddSeries/ExistingSeries'; var addNewUrl = '../AddSeries/AddNew'; @@ -19,7 +18,9 @@ $(".masterQualitySelector").live('change', function () { }); }); -$(".addExistingButton").live('click', function() { +$(".addExistingButton").live('click', function () { + var button = $(this); + $(button).attr('disabled', 'disabled'); var root = $(this).parents(".existingSeries"); var title = $(this).siblings(".seriesLookup").val(); var seriesId = $(this).siblings(".seriesId").val(); @@ -43,7 +44,8 @@ $(".addExistingButton").live('click', function() { type: "POST", url: addSeriesUrl, data: jQuery.param({ path: path, seriesName: title, seriesId: seriesId, qualityProfileId: qualityId, airedAfter: date }), - error: function(req, status, error) { + error: function (req, status, error) { + $(button).removeAttr('disabled'); alert("Sorry! We could not add " + path + " at this time. " + error); }, success: function() { @@ -121,6 +123,8 @@ function refreshRoot() { //AddNew $('#saveNewSeries').live('click', function () { + $('#saveNewSeries').attr('disabled', 'disabled'); + var seriesTitle = $("#newSeriesLookup").val(); var seriesId = $("#newSeriesId").val(); var qualityId = $("#qualityList").val(); @@ -132,10 +136,13 @@ $('#saveNewSeries').live('click', function () { url: addNewSeriesUrl, data: jQuery.param({ path: path, seriesName: seriesTitle, seriesId: seriesId, qualityProfileId: qualityId, airedAfter: date }), error: function (req, status, error) { + $('#saveNewSeries').removeAttr('disabled'); alert("Sorry! We could not add " + path + " at this time. " + error); }, success: function () { - $("#newSeriesLookup").val(""); + $('#saveNewSeries').removeAttr('disabled'); + $("#newSeriesLookup").val(''); + $('#newAiredAfter').val(''); } }); }); @@ -150,27 +157,6 @@ function reloadAddNew() { } -//QuickAddNew -$('#quickAddNew').live('click', function () { - var seriesTitle = $("#newSeriesLookup").val(); - var seriesId = $("#newSeriesId").val(); - var qualityId = $("#qualityList").val(); - - $.ajax({ - type: "POST", - url: quickAddNewSeriesUrl, - data: jQuery.param({ seriesName: seriesTitle, seriesId: seriesId, qualityProfileId: qualityId }), - error: function (req, status, error) { - alert("Sorry! We could not add " + path + " at this time. " + error); - }, - success: function () { - $("#newSeriesLookup").val(""); - $('#newSeriesPath').val(""); - } - }); -}); - - //Watermark $('#rootDirInput').livequery(function () { $(this).watermark('Enter your new root folder path...'); diff --git a/NzbDrone.Web/Views/Shared/QuickAdd.cshtml b/NzbDrone.Web/Views/Shared/QuickAdd.cshtml deleted file mode 100644 index fe420a935..000000000 --- a/NzbDrone.Web/Views/Shared/QuickAdd.cshtml +++ /dev/null @@ -1,15 +0,0 @@ -@using System.Collections -@using NzbDrone.Core -
- - @Html.Hidden("newSeriesId", 0, new { @class = "seriesId" }) - @Html.DropDownList("qualityList", (SelectList)ViewData["QualityProfiles"], new { @class = "qualitySelector" }) - -
- - \ No newline at end of file diff --git a/NzbDrone.Web/Views/Shared/_MINIPROFILER UPDATED Layout.cshtml b/NzbDrone.Web/Views/Shared/_MINIPROFILER UPDATED Layout.cshtml deleted file mode 100644 index 87b393155..000000000 --- a/NzbDrone.Web/Views/Shared/_MINIPROFILER UPDATED Layout.cshtml +++ /dev/null @@ -1,45 +0,0 @@ -@* Required so you have extention methods for client timings *@ -@using StackExchange.Profiling; - - - - @* optional (enable client timing framework) *@ - @this.InitClientTimings() - - @ViewBag.Title - - @* optional time scripts in the header *@ - @this.TimeScript("Content Site.css", - @) - @this.TimeScript("jQuery 1.5.1", - @) - @this.TimeScript("modernizr", - @) - - - -
-
-
-

My MVC Application

-
-
- @Html.Partial("_LogOnPartial") -
- -
-
- @RenderBody() -
-
-
-
- @* Make sure you've added this one line to your LAYOUT or MASTER PAGE *@ - @MiniProfiler.RenderIncludes() - - diff --git a/NzbDrone.sln b/NzbDrone.sln index 07eeff8e8..9ef8e2c68 100644 --- a/NzbDrone.sln +++ b/NzbDrone.sln @@ -9,6 +9,10 @@ EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Services", "Services", "{5853FEE1-D6C1-49AB-B1E3-12216491DA69}" EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "NzbDrone", "NzbDrone\NzbDrone.csproj", "{D12F7F2F-8A3C-415F-88FA-6DD061A84869}" + ProjectSection(ProjectDependencies) = postProject + {FF5EE3B6-913B-47CE-9CEB-11C51B4E1205} = {FF5EE3B6-913B-47CE-9CEB-11C51B4E1205} + {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD} = {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD} + EndProjectSection EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "NzbDrone.Core", "NzbDrone.Core\NzbDrone.Core.csproj", "{FF5EE3B6-913B-47CE-9CEB-11C51B4E1205}" EndProject @@ -103,7 +107,7 @@ Global {FF5EE3B6-913B-47CE-9CEB-11C51B4E1205}.Pilot|Mixed Platforms.ActiveCfg = Release|Any CPU {FF5EE3B6-913B-47CE-9CEB-11C51B4E1205}.Pilot|Mixed Platforms.Build.0 = Release|Any CPU {FF5EE3B6-913B-47CE-9CEB-11C51B4E1205}.Pilot|x64.ActiveCfg = Release|Any CPU - {FF5EE3B6-913B-47CE-9CEB-11C51B4E1205}.Pilot|x86.ActiveCfg = Release|Any CPU + {FF5EE3B6-913B-47CE-9CEB-11C51B4E1205}.Pilot|x86.ActiveCfg = Release|x86 {FF5EE3B6-913B-47CE-9CEB-11C51B4E1205}.Release|Any CPU.ActiveCfg = Release|Any CPU {FF5EE3B6-913B-47CE-9CEB-11C51B4E1205}.Release|Any CPU.Build.0 = Release|Any CPU {FF5EE3B6-913B-47CE-9CEB-11C51B4E1205}.Release|Mixed Platforms.ActiveCfg = Release|x86 @@ -125,14 +129,14 @@ Global {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Debug|x64.ActiveCfg = Debug|Any CPU - {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Debug|x86.ActiveCfg = Debug|Any CPU - {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Debug|x86.Build.0 = Debug|Any CPU + {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Debug|x86.ActiveCfg = Debug|x86 + {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Debug|x86.Build.0 = Debug|x86 {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Pilot|Any CPU.ActiveCfg = Release|Any CPU {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Pilot|Any CPU.Build.0 = Release|Any CPU - {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Pilot|Mixed Platforms.ActiveCfg = Release|Any CPU - {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Pilot|Mixed Platforms.Build.0 = Release|Any CPU + {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Pilot|Mixed Platforms.ActiveCfg = Release|x86 + {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Pilot|Mixed Platforms.Build.0 = Release|x86 {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Pilot|x64.ActiveCfg = Release|Any CPU - {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Pilot|x86.ActiveCfg = Release|Any CPU + {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Pilot|x86.ActiveCfg = Release|x86 {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Release|Any CPU.ActiveCfg = Release|Any CPU {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Release|Any CPU.Build.0 = Release|Any CPU {43BD3BBD-1531-4D8F-9C08-E1CD544AB2CD}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU @@ -150,14 +154,14 @@ Global {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Debug|x64.ActiveCfg = Debug|Any CPU - {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Debug|x86.ActiveCfg = Debug|Any CPU - {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Debug|x86.Build.0 = Debug|Any CPU + {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Debug|x86.ActiveCfg = Debug|x86 + {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Debug|x86.Build.0 = Debug|x86 {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Pilot|Any CPU.ActiveCfg = Release|Any CPU {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Pilot|Any CPU.Build.0 = Release|Any CPU {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Pilot|Mixed Platforms.ActiveCfg = Release|Any CPU {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Pilot|Mixed Platforms.Build.0 = Release|Any CPU {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Pilot|x64.ActiveCfg = Release|Any CPU - {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Pilot|x86.ActiveCfg = Release|Any CPU + {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Pilot|x86.ActiveCfg = Release|x86 {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Release|Any CPU.ActiveCfg = Release|Any CPU {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Release|Any CPU.Build.0 = Release|Any CPU {193ADD3B-792B-4173-8E4C-5A3F8F0237F0}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU @@ -175,14 +179,14 @@ Global {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Debug|x64.ActiveCfg = Debug|Any CPU - {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Debug|x86.ActiveCfg = Debug|Any CPU - {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Debug|x86.Build.0 = Debug|Any CPU + {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Debug|x86.ActiveCfg = Debug|x86 + {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Debug|x86.Build.0 = Debug|x86 {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Pilot|Any CPU.ActiveCfg = Release|Any CPU {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Pilot|Any CPU.Build.0 = Release|Any CPU - {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Pilot|Mixed Platforms.ActiveCfg = Release|Any CPU - {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Pilot|Mixed Platforms.Build.0 = Release|Any CPU + {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Pilot|Mixed Platforms.ActiveCfg = Release|x86 + {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Pilot|Mixed Platforms.Build.0 = Release|x86 {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Pilot|x64.ActiveCfg = Release|Any CPU - {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Pilot|x86.ActiveCfg = Release|Any CPU + {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Pilot|x86.ActiveCfg = Release|x86 {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Release|Any CPU.ActiveCfg = Release|Any CPU {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Release|Any CPU.Build.0 = Release|Any CPU {C0EA1A40-91AD-4EEB-BD16-2DDDEBD20AE5}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU @@ -272,14 +276,14 @@ Global {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Debug|x64.ActiveCfg = Debug|Any CPU - {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Debug|x86.ActiveCfg = Debug|Any CPU - {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Debug|x86.Build.0 = Debug|Any CPU + {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Debug|x86.ActiveCfg = Debug|x86 + {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Debug|x86.Build.0 = Debug|x86 {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Pilot|Any CPU.ActiveCfg = Release|Any CPU {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Pilot|Any CPU.Build.0 = Release|Any CPU - {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Pilot|Mixed Platforms.ActiveCfg = Release|Any CPU - {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Pilot|Mixed Platforms.Build.0 = Release|Any CPU + {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Pilot|Mixed Platforms.ActiveCfg = Release|x86 + {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Pilot|Mixed Platforms.Build.0 = Release|x86 {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Pilot|x64.ActiveCfg = Release|Any CPU - {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Pilot|x86.ActiveCfg = Release|Any CPU + {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Pilot|x86.ActiveCfg = Release|x86 {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Release|Any CPU.ActiveCfg = Release|Any CPU {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Release|Any CPU.Build.0 = Release|Any CPU {F2BE0FDF-6E47-4827-A420-DD4EF82407F8}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU @@ -297,14 +301,14 @@ Global {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Debug|x64.ActiveCfg = Debug|Any CPU - {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Debug|x86.ActiveCfg = Debug|Any CPU - {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Debug|x86.Build.0 = Debug|Any CPU + {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Debug|x86.ActiveCfg = Debug|x86 + {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Debug|x86.Build.0 = Debug|x86 {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Pilot|Any CPU.ActiveCfg = Release|Any CPU {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Pilot|Any CPU.Build.0 = Release|Any CPU {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Pilot|Mixed Platforms.ActiveCfg = Release|Any CPU {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Pilot|Mixed Platforms.Build.0 = Release|Any CPU {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Pilot|x64.ActiveCfg = Release|Any CPU - {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Pilot|x86.ActiveCfg = Release|Any CPU + {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Pilot|x86.ActiveCfg = Release|x86 {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Release|Any CPU.ActiveCfg = Release|Any CPU {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Release|Any CPU.Build.0 = Release|Any CPU {BEC74619-DDBB-4FBA-B517-D3E20AFC9997}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU @@ -322,14 +326,14 @@ Global {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Debug|x64.ActiveCfg = Debug|Any CPU - {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Debug|x86.ActiveCfg = Debug|Any CPU - {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Debug|x86.Build.0 = Debug|Any CPU + {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Debug|x86.ActiveCfg = Debug|x86 + {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Debug|x86.Build.0 = Debug|x86 {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Pilot|Any CPU.ActiveCfg = Release|Any CPU {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Pilot|Any CPU.Build.0 = Release|Any CPU {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Pilot|Mixed Platforms.ActiveCfg = Release|Any CPU {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Pilot|Mixed Platforms.Build.0 = Release|Any CPU {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Pilot|x64.ActiveCfg = Release|Any CPU - {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Pilot|x86.ActiveCfg = Release|Any CPU + {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Pilot|x86.ActiveCfg = Release|x86 {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Release|Any CPU.ActiveCfg = Release|Any CPU {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Release|Any CPU.Build.0 = Release|Any CPU {CADDFCE0-7509-4430-8364-2074E1EEFCA2}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU @@ -347,13 +351,13 @@ Global {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Debug|x64.ActiveCfg = Debug|Any CPU - {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Debug|x86.ActiveCfg = Debug|Any CPU + {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Debug|x86.ActiveCfg = Debug|x86 {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Pilot|Any CPU.ActiveCfg = Release|Any CPU {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Pilot|Any CPU.Build.0 = Release|Any CPU {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Pilot|Mixed Platforms.ActiveCfg = Release|Any CPU {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Pilot|Mixed Platforms.Build.0 = Release|Any CPU {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Pilot|x64.ActiveCfg = Release|Any CPU - {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Pilot|x86.ActiveCfg = Release|Any CPU + {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Pilot|x86.ActiveCfg = Release|x86 {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Release|Any CPU.ActiveCfg = Release|Any CPU {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Release|Any CPU.Build.0 = Release|Any CPU {3CCD64E1-84DA-4853-B7EF-98B02FD4E39E}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU @@ -419,14 +423,14 @@ Global {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Debug|x64.ActiveCfg = Debug|Any CPU - {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Debug|x86.ActiveCfg = Debug|Any CPU - {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Debug|x86.Build.0 = Debug|Any CPU + {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Debug|x86.ActiveCfg = Debug|x86 + {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Debug|x86.Build.0 = Debug|x86 {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Pilot|Any CPU.ActiveCfg = Release|Any CPU {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Pilot|Any CPU.Build.0 = Release|Any CPU {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Pilot|Mixed Platforms.ActiveCfg = Release|Any CPU {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Pilot|Mixed Platforms.Build.0 = Release|Any CPU {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Pilot|x64.ActiveCfg = Release|Any CPU - {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Pilot|x86.ActiveCfg = Release|Any CPU + {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Pilot|x86.ActiveCfg = Release|x86 {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Release|Any CPU.ActiveCfg = Release|Any CPU {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Release|Any CPU.Build.0 = Release|Any CPU {63B155D7-AE78-4FEB-88BB-2F025ADD1F15}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU @@ -444,14 +448,14 @@ Global {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Debug|x64.ActiveCfg = Debug|Any CPU - {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Debug|x86.ActiveCfg = Debug|Any CPU - {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Debug|x86.Build.0 = Debug|Any CPU + {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Debug|x86.ActiveCfg = Debug|x86 + {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Debug|x86.Build.0 = Debug|x86 {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Pilot|Any CPU.ActiveCfg = Release|Any CPU {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Pilot|Any CPU.Build.0 = Release|Any CPU {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Pilot|Mixed Platforms.ActiveCfg = Release|Any CPU {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Pilot|Mixed Platforms.Build.0 = Release|Any CPU {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Pilot|x64.ActiveCfg = Release|Any CPU - {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Pilot|x86.ActiveCfg = Release|Any CPU + {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Pilot|x86.ActiveCfg = Release|x86 {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Release|Any CPU.ActiveCfg = Release|Any CPU {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Release|Any CPU.Build.0 = Release|Any CPU {12261AE5-BCC4-4DC7-A218-0764B9C30230}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU From a7a0a2502944b02ee1c0586b5f133be1f42fb011 Mon Sep 17 00:00:00 2001 From: Mark McDowall Date: Thu, 20 Sep 2012 08:37:40 -0700 Subject: [PATCH 7/8] Renamed AiredAfter to CustomStartDate --- NzbDrone.Core.Test/NzbDrone.Core.Test.csproj | 2 +- .../AllowedDownloadSpecificationFixture.cs | 10 +++---- ...=> CustomStartDateSpecificationFixture.cs} | 28 +++++++++---------- .../Datastore/Migrations/Migration20120919.cs | 21 ++++++++++++++ NzbDrone.Core/Model/ReportRejectionType.cs | 2 +- NzbDrone.Core/NzbDrone.Core.csproj | 3 +- .../AllowedDownloadSpecification.cs | 8 +++--- ...ion.cs => CustomStartDateSpecification.cs} | 12 ++++---- NzbDrone.Core/Providers/SeriesProvider.cs | 4 +-- NzbDrone.Core/Repository/Series.cs | 2 +- NzbDrone.Web/Content/SeriesEditor.css | 4 +-- .../Controllers/AddSeriesController.cs | 10 +++---- NzbDrone.Web/Controllers/SeriesController.cs | 10 +++---- NzbDrone.Web/Models/SeriesModel.cs | 6 ++-- NzbDrone.Web/Scripts/NzbDrone/addSeries.js | 14 +++++----- NzbDrone.Web/Views/AddSeries/AddNew.cshtml | 2 +- .../Views/AddSeries/ExistingSeries.cshtml | 4 +-- NzbDrone.Web/Views/AddSeries/Index.cshtml | 4 +-- NzbDrone.Web/Views/Series/Edit.cshtml | 6 ++-- NzbDrone.Web/Views/Series/Editor.cshtml | 10 +++---- NzbDrone.Web/Views/Series/EditorItem.cshtml | 2 +- 21 files changed, 93 insertions(+), 71 deletions(-) rename NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/{EpisodeAiredAfterCutoffSpecificationFixture.cs => CustomStartDateSpecificationFixture.cs} (74%) create mode 100644 NzbDrone.Core/Datastore/Migrations/Migration20120919.cs rename NzbDrone.Core/Providers/DecisionEngine/{EpisodeAiredAfterCutoffSpecification.cs => CustomStartDateSpecification.cs} (74%) diff --git a/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj b/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj index 540e2f486..5c0d764d7 100644 --- a/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj +++ b/NzbDrone.Core.Test/NzbDrone.Core.Test.csproj @@ -146,7 +146,7 @@ - + diff --git a/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/AllowedDownloadSpecificationFixture.cs b/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/AllowedDownloadSpecificationFixture.cs index 0feeeeca4..a5e79c2a1 100644 --- a/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/AllowedDownloadSpecificationFixture.cs +++ b/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/AllowedDownloadSpecificationFixture.cs @@ -53,7 +53,7 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests .Setup(c => c.IsSatisfiedBy(It.IsAny())) .Returns(true); - Mocker.GetMock() + Mocker.GetMock() .Setup(c => c.IsSatisfiedBy(It.IsAny())) .Returns(true); } @@ -93,9 +93,9 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests .Returns(false); } - private void WithAiredBeforeCutoff() + private void WithAiredBeforeCustomStartDateCutoff() { - Mocker.GetMock() + Mocker.GetMock() .Setup(c => c.IsSatisfiedBy(It.IsAny())) .Returns(false); } @@ -144,8 +144,8 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests [Test] public void should_not_be_allowed_if_episode_aired_before_cutoff() { - WithAiredBeforeCutoff(); - spec.IsSatisfiedBy(parseResult).Should().Be(ReportRejectionType.EpisodeAiredBeforeCutoff); + WithAiredBeforeCustomStartDateCutoff(); + spec.IsSatisfiedBy(parseResult).Should().Be(ReportRejectionType.AiredAfterCustomStartDate); } [Test] diff --git a/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/EpisodeAiredAfterCutoffSpecificationFixture.cs b/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/CustomStartDateSpecificationFixture.cs similarity index 74% rename from NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/EpisodeAiredAfterCutoffSpecificationFixture.cs rename to NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/CustomStartDateSpecificationFixture.cs index 2041fba02..6e5b5d0da 100644 --- a/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/EpisodeAiredAfterCutoffSpecificationFixture.cs +++ b/NzbDrone.Core.Test/ProviderTests/DecisionEngineTests/CustomStartDateSpecificationFixture.cs @@ -17,9 +17,9 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests { [TestFixture] // ReSharper disable InconsistentNaming - public class EpisodeAiredAfterCutoffSpecificationFixture : CoreTest + public class CustomStartDateSpecificationFixture : CoreTest { - private EpisodeAiredAfterCutoffSpecification episodeAiredAfterCutoffSpecification; + private CustomStartDateSpecification _customStartDateSpecification; private EpisodeParseResult parseResultMulti; private EpisodeParseResult parseResultSingle; @@ -30,11 +30,11 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests [SetUp] public void Setup() { - episodeAiredAfterCutoffSpecification = Mocker.Resolve(); + _customStartDateSpecification = Mocker.Resolve(); fakeSeries = Builder.CreateNew() .With(c => c.Monitored = true) - .With(c => c.DownloadEpisodesAiredAfter = null) + .With(c => c.CustomStartDate = null) .Build(); parseResultMulti = new EpisodeParseResult @@ -75,38 +75,38 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests private void WithAiredAfterYesterday() { - fakeSeries.DownloadEpisodesAiredAfter = DateTime.Today.AddDays(-1); + fakeSeries.CustomStartDate = DateTime.Today.AddDays(-1); } private void WithAiredAfterLastWeek() { - fakeSeries.DownloadEpisodesAiredAfter = DateTime.Today.AddDays(-7); + fakeSeries.CustomStartDate = DateTime.Today.AddDays(-7); } [Test] public void should_return_true_when_downloadEpisodesAiredAfter_is_null_for_single_episode() { - episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultSingle).Should().BeTrue(); + _customStartDateSpecification.IsSatisfiedBy(parseResultSingle).Should().BeTrue(); } [Test] public void should_return_true_when_downloadEpisodesAiredAfter_is_null_for_multiple_episodes() { - episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); + _customStartDateSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); } [Test] public void should_return_true_if_both_episodes_air_after_cutoff() { WithAiredAfterLastWeek(); - episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); + _customStartDateSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); } [Test] public void should_return_true_if_episode_airs_after_cutoff() { WithAiredAfterLastWeek(); - episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultSingle).Should().BeTrue(); + _customStartDateSpecification.IsSatisfiedBy(parseResultSingle).Should().BeTrue(); } [Test] @@ -114,7 +114,7 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests { WithAiredAfterLastWeek(); WithSecondEpisodeYear(); - episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); + _customStartDateSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); } [Test] @@ -122,7 +122,7 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests { WithAiredAfterLastWeek(); WithFirstEpisodeLastYear(); - episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); + _customStartDateSpecification.IsSatisfiedBy(parseResultMulti).Should().BeTrue(); } [Test] @@ -131,7 +131,7 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests WithAiredAfterLastWeek(); WithFirstEpisodeLastYear(); WithSecondEpisodeYear(); - episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultMulti).Should().BeFalse(); + _customStartDateSpecification.IsSatisfiedBy(parseResultMulti).Should().BeFalse(); } [Test] @@ -139,7 +139,7 @@ namespace NzbDrone.Core.Test.ProviderTests.DecisionEngineTests { WithAiredAfterLastWeek(); WithFirstEpisodeLastYear(); - episodeAiredAfterCutoffSpecification.IsSatisfiedBy(parseResultSingle).Should().BeFalse(); + _customStartDateSpecification.IsSatisfiedBy(parseResultSingle).Should().BeFalse(); } } } \ No newline at end of file diff --git a/NzbDrone.Core/Datastore/Migrations/Migration20120919.cs b/NzbDrone.Core/Datastore/Migrations/Migration20120919.cs new file mode 100644 index 000000000..5790ef024 --- /dev/null +++ b/NzbDrone.Core/Datastore/Migrations/Migration20120919.cs @@ -0,0 +1,21 @@ +using System; +using System.Data; +using Migrator.Framework; +using NzbDrone.Common; + +namespace NzbDrone.Core.Datastore.Migrations +{ + + [Migration(20120919)] + public class Migration20120919 : NzbDroneMigration + { + protected override void MainDbUpgrade() + { + Database.AddColumn("Series", new Column("CustomStartDate", DbType.DateTime, ColumnProperty.Null)); + + Database.ExecuteNonQuery("UPDATE Series SET CustomStartDate = DownloadEpisodesAiredAfter"); + + Database.RemoveColumn("Series", "DownloadEpisodesAiredAfter"); + } + } +} \ No newline at end of file diff --git a/NzbDrone.Core/Model/ReportRejectionType.cs b/NzbDrone.Core/Model/ReportRejectionType.cs index ad695a577..9e2b6900d 100644 --- a/NzbDrone.Core/Model/ReportRejectionType.cs +++ b/NzbDrone.Core/Model/ReportRejectionType.cs @@ -18,6 +18,6 @@ namespace NzbDrone.Core.Model Skipped = 11, Failure = 12, ReleaseGroupNotWanted = 13, - EpisodeAiredBeforeCutoff = 14 + AiredAfterCustomStartDate = 14 } } diff --git a/NzbDrone.Core/NzbDrone.Core.csproj b/NzbDrone.Core/NzbDrone.Core.csproj index 4b6c2cdf7..8cc7feb5b 100644 --- a/NzbDrone.Core/NzbDrone.Core.csproj +++ b/NzbDrone.Core/NzbDrone.Core.csproj @@ -227,6 +227,7 @@ + @@ -292,7 +293,7 @@ - + diff --git a/NzbDrone.Core/Providers/DecisionEngine/AllowedDownloadSpecification.cs b/NzbDrone.Core/Providers/DecisionEngine/AllowedDownloadSpecification.cs index 3ef8408aa..5e29fce41 100644 --- a/NzbDrone.Core/Providers/DecisionEngine/AllowedDownloadSpecification.cs +++ b/NzbDrone.Core/Providers/DecisionEngine/AllowedDownloadSpecification.cs @@ -14,14 +14,14 @@ namespace NzbDrone.Core.Providers.DecisionEngine private readonly AlreadyInQueueSpecification _alreadyInQueueSpecification; private readonly RetentionSpecification _retentionSpecification; private readonly AllowedReleaseGroupSpecification _allowedReleaseGroupSpecification; - private readonly EpisodeAiredAfterCutoffSpecification _episodeAiredAfterCutoffSpecification; + private readonly CustomStartDateSpecification _customStartDateSpecification; private static readonly Logger logger = LogManager.GetCurrentClassLogger(); [Inject] public AllowedDownloadSpecification(QualityAllowedByProfileSpecification qualityAllowedByProfileSpecification, UpgradeDiskSpecification upgradeDiskSpecification, AcceptableSizeSpecification acceptableSizeSpecification, AlreadyInQueueSpecification alreadyInQueueSpecification, RetentionSpecification retentionSpecification, - AllowedReleaseGroupSpecification allowedReleaseGroupSpecification, EpisodeAiredAfterCutoffSpecification episodeAiredAfterCutoffSpecification) + AllowedReleaseGroupSpecification allowedReleaseGroupSpecification, CustomStartDateSpecification customStartDateSpecification) { _qualityAllowedByProfileSpecification = qualityAllowedByProfileSpecification; _upgradeDiskSpecification = upgradeDiskSpecification; @@ -29,7 +29,7 @@ namespace NzbDrone.Core.Providers.DecisionEngine _alreadyInQueueSpecification = alreadyInQueueSpecification; _retentionSpecification = retentionSpecification; _allowedReleaseGroupSpecification = allowedReleaseGroupSpecification; - _episodeAiredAfterCutoffSpecification = episodeAiredAfterCutoffSpecification; + _customStartDateSpecification = customStartDateSpecification; } public AllowedDownloadSpecification() @@ -39,7 +39,7 @@ namespace NzbDrone.Core.Providers.DecisionEngine public virtual ReportRejectionType IsSatisfiedBy(EpisodeParseResult subject) { if (!_qualityAllowedByProfileSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.QualityNotWanted; - if (!_episodeAiredAfterCutoffSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.EpisodeAiredBeforeCutoff; + if (!_customStartDateSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.AiredAfterCustomStartDate; if (!_upgradeDiskSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.ExistingQualityIsEqualOrBetter; if (!_retentionSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.Retention; if (!_acceptableSizeSpecification.IsSatisfiedBy(subject)) return ReportRejectionType.Size; diff --git a/NzbDrone.Core/Providers/DecisionEngine/EpisodeAiredAfterCutoffSpecification.cs b/NzbDrone.Core/Providers/DecisionEngine/CustomStartDateSpecification.cs similarity index 74% rename from NzbDrone.Core/Providers/DecisionEngine/EpisodeAiredAfterCutoffSpecification.cs rename to NzbDrone.Core/Providers/DecisionEngine/CustomStartDateSpecification.cs index f6778816f..53db72ff1 100644 --- a/NzbDrone.Core/Providers/DecisionEngine/EpisodeAiredAfterCutoffSpecification.cs +++ b/NzbDrone.Core/Providers/DecisionEngine/CustomStartDateSpecification.cs @@ -5,25 +5,25 @@ using NzbDrone.Core.Model; namespace NzbDrone.Core.Providers.DecisionEngine { - public class EpisodeAiredAfterCutoffSpecification + public class CustomStartDateSpecification { private readonly EpisodeProvider _episodeProvider; private static readonly Logger logger = LogManager.GetCurrentClassLogger(); [Inject] - public EpisodeAiredAfterCutoffSpecification(EpisodeProvider episodeProvider) + public CustomStartDateSpecification(EpisodeProvider episodeProvider) { _episodeProvider = episodeProvider; } - public EpisodeAiredAfterCutoffSpecification() + public CustomStartDateSpecification() { } public virtual bool IsSatisfiedBy(EpisodeParseResult subject) { - if (!subject.Series.DownloadEpisodesAiredAfter.HasValue) + if (!subject.Series.CustomStartDate.HasValue) { logger.Debug("{0} does not restrict downloads before date.", subject.Series.Title); return true; @@ -31,13 +31,13 @@ namespace NzbDrone.Core.Providers.DecisionEngine var episodes = _episodeProvider.GetEpisodesByParseResult(subject); - if (episodes.Any(episode => episode.AirDate > subject.Series.DownloadEpisodesAiredAfter.Value)) + if (episodes.Any(episode => episode.AirDate > subject.Series.CustomStartDate.Value)) { logger.Debug("One or more episodes aired after cutoff, downloading."); return true; } - logger.Debug("Episodes aired before cutoff date: {0}", subject.Series.DownloadEpisodesAiredAfter); + logger.Debug("Episodes aired before cutoff date: {0}", subject.Series.CustomStartDate); return false; } } diff --git a/NzbDrone.Core/Providers/SeriesProvider.cs b/NzbDrone.Core/Providers/SeriesProvider.cs index 08e129def..ecbded829 100644 --- a/NzbDrone.Core/Providers/SeriesProvider.cs +++ b/NzbDrone.Core/Providers/SeriesProvider.cs @@ -132,7 +132,7 @@ namespace NzbDrone.Core.Providers repoSeries.BacklogSetting = BacklogSettingType.Inherit; if (airedAfter.HasValue) - repoSeries.DownloadEpisodesAiredAfter = airedAfter; + repoSeries.CustomStartDate = airedAfter; _database.Insert(repoSeries); } @@ -232,7 +232,7 @@ namespace NzbDrone.Core.Providers series.SeasonFolder = edited.SeasonFolder; series.BacklogSetting = edited.BacklogSetting; series.Path = edited.Path; - series.DownloadEpisodesAiredAfter = edited.DownloadEpisodesAiredAfter; + series.CustomStartDate = edited.CustomStartDate; } _database.UpdateMany(allSeries); diff --git a/NzbDrone.Core/Repository/Series.cs b/NzbDrone.Core/Repository/Series.cs index acb0c25b8..70d19cead 100644 --- a/NzbDrone.Core/Repository/Series.cs +++ b/NzbDrone.Core/Repository/Series.cs @@ -48,7 +48,7 @@ namespace NzbDrone.Core.Repository public string Network { get; set; } - public DateTime? DownloadEpisodesAiredAfter { get; set; } + public DateTime? CustomStartDate { get; set; } /// /// Gets or sets a value indicating whether this is hidden. diff --git a/NzbDrone.Web/Content/SeriesEditor.css b/NzbDrone.Web/Content/SeriesEditor.css index f41e13fcf..0bd01b82a 100644 --- a/NzbDrone.Web/Content/SeriesEditor.css +++ b/NzbDrone.Web/Content/SeriesEditor.css @@ -37,7 +37,7 @@ th .footer-control-quality { width: 120px; } -td .aired-after { +td .start-date { width: 80px; } @@ -45,7 +45,7 @@ th .footer-control-boolean { width: 90px; } -th .footer-control-aired-after { +th .footer-control-start-date { width: 80px; } diff --git a/NzbDrone.Web/Controllers/AddSeriesController.cs b/NzbDrone.Web/Controllers/AddSeriesController.cs index 9d8d93b36..cdb50d6ad 100644 --- a/NzbDrone.Web/Controllers/AddSeriesController.cs +++ b/NzbDrone.Web/Controllers/AddSeriesController.cs @@ -110,7 +110,7 @@ namespace NzbDrone.Web.Controllers } [HttpPost] - public JsonResult AddNewSeries(string path, string seriesName, int seriesId, int qualityProfileId, string airedAfter) + public JsonResult AddNewSeries(string path, string seriesName, int seriesId, int qualityProfileId, string startDate) { if (string.IsNullOrWhiteSpace(path) || String.Equals(path,"null",StringComparison.InvariantCultureIgnoreCase)) return JsonNotificationResult.Error("Couldn't add " + seriesName, "You need a valid root folder"); @@ -121,20 +121,20 @@ namespace NzbDrone.Web.Controllers //Use the created folder name when adding the series path = _diskProvider.CreateDirectory(path); - return AddExistingSeries(path, seriesName, seriesId, qualityProfileId, airedAfter); + return AddExistingSeries(path, seriesName, seriesId, qualityProfileId, startDate); } [HttpPost] [JsonErrorFilter] - public JsonResult AddExistingSeries(string path, string seriesName, int seriesId, int qualityProfileId, string airedAfter) + public JsonResult AddExistingSeries(string path, string seriesName, int seriesId, int qualityProfileId, string startDate) { if (seriesId == 0 || String.IsNullOrWhiteSpace(seriesName)) return JsonNotificationResult.Error("Add Existing series failed.", "Invalid Series information"); DateTime? date = null; - if (!String.IsNullOrWhiteSpace(airedAfter)) - date = DateTime.Parse(airedAfter, null, DateTimeStyles.RoundtripKind); + if (!String.IsNullOrWhiteSpace(startDate)) + date = DateTime.Parse(startDate, null, DateTimeStyles.RoundtripKind); _seriesProvider.AddSeries(seriesName,path, seriesId, qualityProfileId, date); _jobProvider.QueueJob(typeof(ImportNewSeriesJob)); diff --git a/NzbDrone.Web/Controllers/SeriesController.cs b/NzbDrone.Web/Controllers/SeriesController.cs index 8691827ad..d82d7898f 100644 --- a/NzbDrone.Web/Controllers/SeriesController.cs +++ b/NzbDrone.Web/Controllers/SeriesController.cs @@ -73,8 +73,8 @@ namespace NzbDrone.Web.Controllers series.Path = seriesModel.Path; series.BacklogSetting = (BacklogSettingType)seriesModel.BacklogSetting; - if (!String.IsNullOrWhiteSpace(seriesModel.DownloadEpisodesAiredAfter)) - series.DownloadEpisodesAiredAfter = DateTime.Parse(seriesModel.DownloadEpisodesAiredAfter, null, DateTimeStyles.RoundtripKind); + if (!String.IsNullOrWhiteSpace(seriesModel.CustomStartDate)) + series.CustomStartDate = DateTime.Parse(seriesModel.CustomStartDate, null, DateTimeStyles.RoundtripKind); _seriesProvider.UpdateSeries(series); @@ -190,8 +190,8 @@ namespace NzbDrone.Web.Controllers SeasonFolder = s.SeasonFolder, BacklogSetting = (BacklogSettingType)s.BacklogSetting, Path = s.Path, - DownloadEpisodesAiredAfter = String.IsNullOrWhiteSpace(s.DownloadEpisodesAiredAfter) ? (DateTime?)null - : DateTime.Parse(s.DownloadEpisodesAiredAfter, null, DateTimeStyles.RoundtripKind) + CustomStartDate = String.IsNullOrWhiteSpace(s.CustomStartDate) ? (DateTime?)null + : DateTime.Parse(s.CustomStartDate, null, DateTimeStyles.RoundtripKind) } ).ToList()); return JsonNotificationResult.Info("Series Mass Edit Saved"); @@ -220,7 +220,7 @@ namespace NzbDrone.Web.Controllers NextAiring = s.NextAiring == null ? String.Empty : s.NextAiring.Value.ToBestDateString(), NextAiringSorter = s.NextAiring == null ? "12/31/9999" : s.NextAiring.Value.ToString("MM/dd/yyyy"), AirTime = s.AirTimes, - DownloadEpisodesAiredAfter = s.DownloadEpisodesAiredAfter.HasValue ? s.DownloadEpisodesAiredAfter.Value.ToString("yyyy-MM-dd") : String.Empty + CustomStartDate = s.CustomStartDate.HasValue ? s.CustomStartDate.Value.ToString("yyyy-MM-dd") : String.Empty }).ToList(); return series; diff --git a/NzbDrone.Web/Models/SeriesModel.cs b/NzbDrone.Web/Models/SeriesModel.cs index b61204248..a99617155 100644 --- a/NzbDrone.Web/Models/SeriesModel.cs +++ b/NzbDrone.Web/Models/SeriesModel.cs @@ -53,8 +53,8 @@ namespace NzbDrone.Web.Models [Description("Should NzbDrone search for missing episodes every 30 days?")] public int BacklogSetting { get; set; } - [DisplayName("Download Episodes Aired After")] - [Description("Should NzbDrone only download episodes a certain date?")] - public string DownloadEpisodesAiredAfter { get; set; } + [DisplayName("Custom Start Date")] + [Description("Should NzbDrone only download episodes after your preferred start date?")] + public string CustomStartDate { get; set; } } } \ No newline at end of file diff --git a/NzbDrone.Web/Scripts/NzbDrone/addSeries.js b/NzbDrone.Web/Scripts/NzbDrone/addSeries.js index 219d87eef..6f1c8fa71 100644 --- a/NzbDrone.Web/Scripts/NzbDrone/addSeries.js +++ b/NzbDrone.Web/Scripts/NzbDrone/addSeries.js @@ -25,7 +25,7 @@ $(".addExistingButton").live('click', function () { var title = $(this).siblings(".seriesLookup").val(); var seriesId = $(this).siblings(".seriesId").val(); var qualityId = $(this).siblings(".qualitySelector").val(); - var date = $(this).siblings('.aired-after').val(); + var date = $(this).siblings('.start-date').val(); var path = root.find(".seriesPathValue Label").text(); @@ -43,7 +43,7 @@ $(".addExistingButton").live('click', function () { $.ajax({ type: "POST", url: addSeriesUrl, - data: jQuery.param({ path: path, seriesName: title, seriesId: seriesId, qualityProfileId: qualityId, airedAfter: date }), + data: jQuery.param({ path: path, seriesName: title, seriesId: seriesId, qualityProfileId: qualityId, startDate: date }), error: function (req, status, error) { $(button).removeAttr('disabled'); alert("Sorry! We could not add " + path + " at this time. " + error); @@ -67,10 +67,10 @@ function reloadExistingSeries() { }); } -$(".aired-after-master").live('change', function () { +$(".start-date-master").live('change', function () { var date = $(this).val(); - $("#existingSeries").find(".aired-after").each(function () { + $("#existingSeries").find(".start-date").each(function () { $(this).val(date); }); }); @@ -129,12 +129,12 @@ $('#saveNewSeries').live('click', function () { var seriesId = $("#newSeriesId").val(); var qualityId = $("#qualityList").val(); var path = $('#newSeriesPath').val(); - var date = $('#newAiredAfter').val(); + var date = $('#newStartDate').val(); $.ajax({ type: "POST", url: addNewSeriesUrl, - data: jQuery.param({ path: path, seriesName: seriesTitle, seriesId: seriesId, qualityProfileId: qualityId, airedAfter: date }), + data: jQuery.param({ path: path, seriesName: seriesTitle, seriesId: seriesId, qualityProfileId: qualityId, startDate: date }), error: function (req, status, error) { $('#saveNewSeries').removeAttr('disabled'); alert("Sorry! We could not add " + path + " at this time. " + error); @@ -142,7 +142,7 @@ $('#saveNewSeries').live('click', function () { success: function () { $('#saveNewSeries').removeAttr('disabled'); $("#newSeriesLookup").val(''); - $('#newAiredAfter').val(''); + $('#newStartDate').val(''); } }); }); diff --git a/NzbDrone.Web/Views/AddSeries/AddNew.cshtml b/NzbDrone.Web/Views/AddSeries/AddNew.cshtml index 5c46dfeaa..9b86fb816 100644 --- a/NzbDrone.Web/Views/AddSeries/AddNew.cshtml +++ b/NzbDrone.Web/Views/AddSeries/AddNew.cshtml @@ -7,7 +7,7 @@ @Html.DropDownList("newSeriesPath", new SelectList((IList)ViewData["RootDirs"]), new { style = "width: 406px; margin-left: 0px;" }) @Html.DropDownList("qualityList", (SelectList)ViewData["QualityProfiles"], new { @class = "qualitySelector" }) - @Html.TextBox("newAiredAfter", "", new { type = "date", @class = "jQuery-datepicker aired-after", title = "Only download episodes that aired after the choosen date" }) + @Html.TextBox("newStartDate", "", new { type = "date", @class = "jQuery-datepicker start-date", placeholder = "Custom Start Date", title = "Only download episodes that aired after the specified date" }) \ No newline at end of file diff --git a/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml b/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml index fe0a51a40..9f84db2e2 100644 --- a/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml +++ b/NzbDrone.Web/Views/AddSeries/ExistingSeries.cshtml @@ -23,7 +23,7 @@ else { @Html.DropDownList(Guid.NewGuid().ToString(), Model.Quality, new { @class = "qualitySelector masterQualitySelector" }) - @Html.TextBox(Guid.NewGuid().ToString(), "", new { type="date", @class = "jQuery-datepicker aired-after-master", title = "Skip episodes that aired before the choosen date" }) + @Html.TextBox(Guid.NewGuid().ToString(), "", new { type="date", @class = "jQuery-datepicker start-date-master", placeholder = "Custom Start Date", title = "Only download episodes that aired after the specified date" }) foreach (var series in Model.ExistingSeries) { @@ -35,7 +35,7 @@ else @Html.Hidden("seriesId", series.Item3, new { @class = "seriesId" }) @Html.DropDownList(Guid.NewGuid().ToString(), Model.Quality, new { @class = "qualitySelector" }) - @Html.TextBox(Guid.NewGuid().ToString(), "", new { type="date", @class = "jQuery-datepicker aired-after", title = "Only download episodes that aired after the choosen date" }) + @Html.TextBox(Guid.NewGuid().ToString(), "", new { type="date", @class = "jQuery-datepicker start-date", placeholder = "Custom Start Date", title = "Only download episodes that aired after the specified date" }) diff --git a/NzbDrone.Web/Views/AddSeries/Index.cshtml b/NzbDrone.Web/Views/AddSeries/Index.cshtml index 14746e52a..d629009b6 100644 --- a/NzbDrone.Web/Views/AddSeries/Index.cshtml +++ b/NzbDrone.Web/Views/AddSeries/Index.cshtml @@ -20,7 +20,7 @@ position: relative; } - .aired-after-master { + .start-date-master { left: 430px; position: relative; } @@ -51,7 +51,7 @@ text-decoration: underline; } - input[type=date].aired-after { + input[type=date].start-date { margin-left: 10px; } diff --git a/NzbDrone.Web/Views/Series/Edit.cshtml b/NzbDrone.Web/Views/Series/Edit.cshtml index a2bf391e2..c7770a995 100644 --- a/NzbDrone.Web/Views/Series/Edit.cshtml +++ b/NzbDrone.Web/Views/Series/Edit.cshtml @@ -37,9 +37,9 @@ @Html.DropDownListFor(m => m.BacklogSetting, (SelectList)ViewData["BacklogSettingSelectList"], new { @class = "inputClass" }) -
- + @@ -56,7 +56,7 @@ @Html.DropDownList("masterBacklogSetting", (SelectList)ViewData["MasterBacklogSettingSelectList"], new { @class = "footer-control masterSelector master-backlog-setting", disabled = true }) - + } \ No newline at end of file From 61d03a69b7f9a96e8d955154c1cadfc9ac5ebb63 Mon Sep 17 00:00:00 2001 From: Mark McDowall Date: Sat, 22 Sep 2012 22:21:20 -0700 Subject: [PATCH 8/8] Status and Sorting added to Series Editor --- NzbDrone.Web/Content/Grid.css | 5 +- NzbDrone.Web/Content/SeriesEditor.css | 2 +- NzbDrone.Web/Views/Series/Editor.cshtml | 73 ++++++++++++++++++--- NzbDrone.Web/Views/Series/EditorItem.cshtml | 13 +++- 4 files changed, 79 insertions(+), 14 deletions(-) diff --git a/NzbDrone.Web/Content/Grid.css b/NzbDrone.Web/Content/Grid.css index b30f86be1..26963de2c 100644 --- a/NzbDrone.Web/Content/Grid.css +++ b/NzbDrone.Web/Content/Grid.css @@ -68,10 +68,7 @@ opacity: 0.7; } - - -.episodeMissing -{ +.episodeMissing, table.dataTable tr.series-ended { background-color: #f5d6d6; } diff --git a/NzbDrone.Web/Content/SeriesEditor.css b/NzbDrone.Web/Content/SeriesEditor.css index 0bd01b82a..22366b2ce 100644 --- a/NzbDrone.Web/Content/SeriesEditor.css +++ b/NzbDrone.Web/Content/SeriesEditor.css @@ -18,7 +18,7 @@ table input[type="text"], table input[type="date"], table select { } td .path { - width: 300px; + width: 290px; } td .backlogSetting { diff --git a/NzbDrone.Web/Views/Series/Editor.cshtml b/NzbDrone.Web/Views/Series/Editor.cshtml index f1032b114..0db6ff1f6 100644 --- a/NzbDrone.Web/Views/Series/Editor.cshtml +++ b/NzbDrone.Web/Views/Series/Editor.cshtml @@ -28,7 +28,8 @@ - + + @@ -62,10 +63,15 @@ + + -
@Html.CheckBox("editToggleMaster", false, new { @class = "editToggleMaster" }) Title QualityMonitoredSeason FolderBacklog StatusMonitoredSeason FolderBacklog StatusAired After Path
- @Html.DropDownList("masterMonitored", (SelectList)ViewData["BoolSelectList"], new { @class = "footer-control masterSelector master-monitored", disabled = true }) + @Html.DropDownList("masterMonitored", (SelectList)ViewData["BoolSelectList"], new { @class = "footer-control-boolean masterSelector master-monitored", disabled = true }) - @Html.DropDownList("masterSeasonFolder", (SelectList)ViewData["BoolSelectList"], new { @class = "footer-control masterSelector master-season-folder", disabled = true }) + @Html.DropDownList("masterSeasonFolder", (SelectList)ViewData["BoolSelectList"], new { @class = "footer-control-boolean masterSelector master-season-folder", disabled = true }) @Html.DropDownList("masterBacklogSetting", (SelectList)ViewData["MasterBacklogSettingSelectList"], new { @class = "footer-control masterSelector master-backlog-setting", disabled = true }) + @Html.TextBox("masterAiredAfter", "" , new { type = "date", @class = "footer-control-aired-after masterSelector master-aired-after jQuery-datepicker", disabled = true }) + @Html.CheckBoxFor(m => m.Monitored, new {@class = "seriesCheckbox monitored"}) @Html.CheckBoxFor(m => m.SeasonFolder, new {@class = "seriesCheckbox seasonFolder"}) @Html.DropDownListFor(m => m.BacklogSetting, new SelectList((List>)ViewData["BacklogSettingTypes"], "Key", "Value", (int)Model.BacklogSetting), new { @class = "backlogSetting" })@Html.TextBoxFor(m => m.DownloadEpisodesAiredAfter, new { type = "date", @class = "aired-after jQuery-datepicker" }) @Html.TextBoxFor(m => m.Path, new { @class = "path" })
Monitored Season Folder Backlog StatusAired AfterStart Date Path
- @Html.TextBox("masterAiredAfter", "" , new { type = "date", @class = "footer-control-aired-after masterSelector master-aired-after jQuery-datepicker", disabled = true }) + @Html.TextBox("masterStartDate", "" , new { type = "date", @class = "footer-control-start-date masterSelector master-start-date jQuery-datepicker", disabled = true }) @Html.CheckBoxFor(m => m.Monitored, new {@class = "seriesCheckbox monitored"}) @Html.CheckBoxFor(m => m.SeasonFolder, new {@class = "seriesCheckbox seasonFolder"}) @Html.DropDownListFor(m => m.BacklogSetting, new SelectList((List>)ViewData["BacklogSettingTypes"], "Key", "Value", (int)Model.BacklogSetting), new { @class = "backlogSetting" })@Html.TextBoxFor(m => m.DownloadEpisodesAiredAfter, new { type = "date", @class = "aired-after jQuery-datepicker" })@Html.TextBoxFor(m => m.CustomStartDate, new { type = "date", @class = "start-date jQuery-datepicker" }) @Html.TextBoxFor(m => m.Path, new { @class = "path" })
Season Folder Backlog Status Start DatePathPath
+ + +@Html.CheckBox("highlightEnded", true) + } @section Scripts @@ -79,19 +85,70 @@ "bPaginate": false, "bLengthChange": false, "bFilter": false, - "bSort": false, + "bSort": true, "bInfo": false, - "bAutoWidth": false + "bAutoWidth": false, + "aaSorting": [[1, 'asc']], + "aoColumns": [ + { "bSortable": false }, + { "bSortable": true }, + { "bSortable": false }, + { "bSortable": false }, + { "bSortable": false }, + { "bSortable": false }, + { "bSortable": false }, + { "bSortable": false }, + { "bSortable": true } + ] }); new FixedHeader(oTable, { "top": true, "left": false, "right": false, "bottom": true }); $('.editToggle').enableCheckboxRangeSelection(); - //$('.master-quality option[value=-10]').text('Quality...'); - //$('.master-monitored option[value=-10]').text('Monitored...'); - //$('.master-season-folder option[value=-10]').text('Season Folder...'); - //$('.master-backlog-setting option[value=-10]').text('Backlog Setting...'); + $(document).ready(function () { + var cookieValue = $.cookie("highlightEnded"); + + if (cookieValue == "true") { + $('#highlightEnded').attr('checked', true); + toggleHighlightEnded(true); + } + + else { + $('#highlightEnded').attr('checked', false); + toggleHighlightEnded(false); + } + + $('#highlightEnded').button(); + }); + + $('#highlightEnded').on('change', function () { + var checked = $(this).attr('checked'); + toggleHighlightEnded(checked); + toggleHighlightEndedCookie(checked); + }); + + function toggleHighlightEnded(highlight) { + var ended = $('tr[data-status="Ended"]'); + + ended.each(function () { + if (highlight) { + $(this).addClass('series-ended'); + } + + else { + $(this).removeClass('series-ended'); + } + }); + } + + function toggleHighlightEndedCookie(highlight) { + if (highlight) + $.cookie("highlightEnded", true, { expires: 365 }); + + else + $.cookie("highlightEnded", false, { expires: 365 }); + } }); $(document).on('change', '.editToggleMaster', function () { diff --git a/NzbDrone.Web/Views/Series/EditorItem.cshtml b/NzbDrone.Web/Views/Series/EditorItem.cshtml index 6fa425195..0101f9424 100644 --- a/NzbDrone.Web/Views/Series/EditorItem.cshtml +++ b/NzbDrone.Web/Views/Series/EditorItem.cshtml @@ -9,7 +9,7 @@ @*SeriesId, Title, Quality, Monitored, Use Season Folder, Root Directory/Path*, Backlog Toggle*@ - + @using (Html.BeginCollectionItem("series")) { var idClean = ViewData.TemplateInfo.HtmlFieldPrefix.Replace('[', '_').Replace(']', '_'); @@ -23,5 +23,16 @@ @Html.DropDownListFor(m => m.BacklogSetting, new SelectList((List>)ViewData["BacklogSettingTypes"], "Key", "Value", (int)Model.BacklogSetting), new { @class = "backlogSetting" }) @Html.TextBoxFor(m => m.CustomStartDate, new { type = "date", @class = "start-date jQuery-datepicker" }) @Html.TextBoxFor(m => m.Path, new { @class = "path" }) + + @if (Model.Status == "Ended") + { + Ended + } + + else + { + Active + } + } \ No newline at end of file