mirror of
https://github.com/Sonarr/Sonarr.git
synced 2024-11-28 08:58:41 +02:00
Added basic episode support
This commit is contained in:
parent
606140832d
commit
81e155ae42
@ -26,7 +26,7 @@ public void Overwrite_existing_value()
|
||||
var repo = new Mock<IRepository>();
|
||||
var config = new Config { Key = key, Value = value };
|
||||
repo.Setup(r => r.Single<Config>(key)).Returns(config);
|
||||
var target = new ConfigProvider(new Mock<ILog>().Object, repo.Object);
|
||||
var target = new ConfigProvider(repo.Object);
|
||||
|
||||
//Act
|
||||
target.SetValue(key, value);
|
||||
@ -45,7 +45,7 @@ public void Add_new_value()
|
||||
//Arrange
|
||||
var repo = new Mock<IRepository>();
|
||||
repo.Setup(r => r.Single<Config>(It.IsAny<string>())).Returns<Config>(null).Verifiable();
|
||||
var target = new ConfigProvider(new Mock<ILog>().Object, repo.Object);
|
||||
var target = new ConfigProvider(repo.Object);
|
||||
|
||||
//Act
|
||||
target.SetValue(key, value);
|
||||
|
15
NzbDrone.Core.Test/EpisodeProviderTest.cs
Normal file
15
NzbDrone.Core.Test/EpisodeProviderTest.cs
Normal file
@ -0,0 +1,15 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using Gallio.Framework;
|
||||
using MbUnit.Framework;
|
||||
using MbUnit.Framework.ContractVerifiers;
|
||||
|
||||
namespace NzbDrone.Core.Test
|
||||
{
|
||||
[TestFixture]
|
||||
public class EpisodeProviderTest
|
||||
{
|
||||
|
||||
}
|
||||
}
|
@ -27,7 +27,7 @@ public void TearDown()
|
||||
[SetUp]
|
||||
public void Setup()
|
||||
{
|
||||
Main.ConfigureNlog();
|
||||
CentralDispatch.ConfigureNlog();
|
||||
}
|
||||
}
|
||||
}
|
@ -7,6 +7,7 @@
|
||||
using NzbDrone.Core.Providers;
|
||||
using SubSonic.DataProviders;
|
||||
using SubSonic.Repository;
|
||||
using TvdbLib;
|
||||
|
||||
namespace NzbDrone.Core.Test
|
||||
{
|
||||
@ -17,12 +18,9 @@ static class MockLib
|
||||
{
|
||||
public static string[] StandardSeries
|
||||
{
|
||||
get { return new string[] { "C:\\TV\\The Simpsons", "C:\\TV\\Family Guy" }; }
|
||||
get { return new string[] { "c:\\tv\\the simpsons", "c:\\tv\\family guy", "c:\\tv\\southpark", "c:\\tv\\24" }; }
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
public static IRepository GetEmptyRepository()
|
||||
{
|
||||
var provider = ProviderFactory.GetProvider("Data Source=" + Guid.NewGuid() + ".testdb;Version=3;New=True", "System.Data.SQLite");
|
||||
@ -39,15 +37,12 @@ public static IConfigProvider StandardConfig
|
||||
}
|
||||
}
|
||||
|
||||
public static IDiskProvider StandardDisk
|
||||
public static IDiskProvider GetStandardDisk()
|
||||
{
|
||||
get
|
||||
{
|
||||
var mock = new Mock<IDiskProvider>();
|
||||
mock.Setup(c => c.GetDirectories(It.IsAny<String>())).Returns(StandardSeries);
|
||||
mock.Setup(c => c.Exists(It.Is<String>(d => StandardSeries.Contains(d)))).Returns(true);
|
||||
return mock.Object;
|
||||
}
|
||||
var mock = new Mock<IDiskProvider>();
|
||||
mock.Setup(c => c.GetDirectories(It.IsAny<String>())).Returns(StandardSeries);
|
||||
mock.Setup(c => c.Exists(It.Is<String>(d => StandardSeries.Contains(d)))).Returns(true);
|
||||
return mock.Object;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -41,7 +41,6 @@
|
||||
<HintPath>..\NzbDrone.Core\Libraries\log4net.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="MbUnit, Version=3.2.0.0, Culture=neutral, PublicKeyToken=eb9cfa67ee6ab36e, processorArchitecture=MSIL" />
|
||||
<Reference Include="MbUnit35, Version=3.2.0.0, Culture=neutral, PublicKeyToken=eb9cfa67ee6ab36e, processorArchitecture=MSIL" />
|
||||
<Reference Include="Moq, Version=4.0.10827.0, Culture=neutral, PublicKeyToken=69f491c39445e920, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>Moq\Moq.dll</HintPath>
|
||||
@ -55,13 +54,11 @@
|
||||
<HintPath>..\NzbDrone.Core\Libraries\SubSonic.Core.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="System" />
|
||||
<Reference Include="System.Data.SQLite">
|
||||
<HintPath>Libs\System.Data.SQLite.DLL</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="System.Xml.Linq" />
|
||||
<Reference Include="System.Data.DataSetExtensions" />
|
||||
<Reference Include="Microsoft.CSharp" />
|
||||
<Reference Include="System.Data" />
|
||||
<Reference Include="System.Data.SQLite, Version=1.0.66.0, Culture=neutral, PublicKeyToken=db937bc2d44ff139, processorArchitecture=AMD64">
|
||||
<HintPath>Libs\System.Data.SQLite.DLL</HintPath>
|
||||
<Private>True</Private>
|
||||
</Reference>
|
||||
<Reference Include="System.Xml" />
|
||||
<Reference Include="TvdbLib">
|
||||
<HintPath>..\NzbDrone.Core\Libraries\TvdbLib.dll</HintPath>
|
||||
@ -69,6 +66,7 @@
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="DbConfigControllerTest.cs" />
|
||||
<Compile Include="EpisodeProviderTest.cs" />
|
||||
<Compile Include="Fixtures.cs" />
|
||||
<Compile Include="MockLib.cs" />
|
||||
<Compile Include="Ninject.Moq\ExtensionsForBindingSyntax.cs" />
|
||||
@ -77,7 +75,7 @@
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
<Compile Include="QualityProfileTest.cs" />
|
||||
<Compile Include="SabControllerTest.cs" />
|
||||
<Compile Include="SeriesTest.cs" />
|
||||
<Compile Include="SeriesProviderTest.cs" />
|
||||
<Compile Include="TvDbControllerTest.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
@ -99,7 +97,9 @@
|
||||
<Content Include="Files\QueueError.xml">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</Content>
|
||||
<Content Include="Libs\System.Data.SQLite.DLL" />
|
||||
<Content Include="Libs\System.Data.SQLite.DLL">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
</Content>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="App.config">
|
||||
|
@ -36,7 +36,7 @@ public void AddByUrlSuccess()
|
||||
var http = new Mock<IHttpProvider>();
|
||||
http.Setup(s => s.DownloadString("http://192.168.5.55:2222/sabnzbd/api?mode=addurl&name=http://www.nzbclub.com/nzb_download.aspx?mid=1950232&priority=0&cat=tv&nzbname=This+is+an+Nzb&apikey=5c770e3197e4fe763423ee7c392c25d1&ma_username=admin&ma_password=pass")).Returns("ok");
|
||||
|
||||
var target = new SabProvider(config.Object, new Mock<ILog>().Object, http.Object);
|
||||
var target = new SabProvider(config.Object, http.Object);
|
||||
|
||||
//Act
|
||||
bool result = target.AddByUrl("http://www.nzbclub.com/nzb_download.aspx?mid=1950232", "This is an Nzb");
|
||||
@ -65,7 +65,7 @@ public void AddByUrlError()
|
||||
var http = new Mock<IHttpProvider>();
|
||||
http.Setup(s => s.DownloadString("http://192.168.5.55:2222/sabnzbd/api?mode=addurl&name=http://www.nzbclub.com/nzb_download.aspx?mid=1950232&priority=0&cat=tv&nzbname=This+is+an+Nzb&apikey=5c770e3197e4fe763423ee7c392c25d1&ma_username=admin&ma_password=pass")).Returns("error");
|
||||
|
||||
var target = new SabProvider(config.Object, new Mock<ILog>().Object, http.Object);
|
||||
var target = new SabProvider(config.Object, http.Object);
|
||||
|
||||
//Act
|
||||
bool result = target.AddByUrl("http://www.nzbclub.com/nzb_download.aspx?mid=1950232", "This is an Nzb");
|
||||
@ -98,7 +98,7 @@ public void IsInQueue_True()
|
||||
"http://192.168.5.55:2222/sabnzbd/api?mode=queue&output=xml&apikey=5c770e3197e4fe763423ee7c392c25d1&ma_username=admin&ma_password=pass"))
|
||||
.Returns(new StreamReader(@".\Files\Queue.xml").ReadToEnd());
|
||||
|
||||
var target = new SabProvider(config.Object, new Mock<ILog>().Object, http.Object);
|
||||
var target = new SabProvider(config.Object, http.Object);
|
||||
|
||||
//Act
|
||||
bool result = target.IsInQueue("Ubuntu Test");
|
||||
@ -131,7 +131,7 @@ public void IsInQueue_False_Empty()
|
||||
"http://192.168.5.55:2222/sabnzbd/api?mode=queue&output=xml&apikey=5c770e3197e4fe763423ee7c392c25d1&ma_username=admin&ma_password=pass"))
|
||||
.Returns(new StreamReader(@".\Files\QueueEmpty.xml").ReadToEnd());
|
||||
|
||||
var target = new SabProvider(config.Object, new Mock<ILog>().Object, http.Object);
|
||||
var target = new SabProvider(config.Object, http.Object);
|
||||
|
||||
//Act
|
||||
bool result = target.IsInQueue(String.Empty);
|
||||
@ -164,7 +164,7 @@ public void IsInQueue_False_Error()
|
||||
"http://192.168.5.55:2222/sabnzbd/api?mode=queue&output=xml&apikey=5c770e3197e4fe763423ee7c392c25d1&ma_username=admin&ma_password=pass"))
|
||||
.Returns(new StreamReader(@".\Files\QueueError.xml").ReadToEnd());
|
||||
|
||||
var target = new SabProvider(config.Object, new Mock<ILog>().Object, http.Object);
|
||||
var target = new SabProvider(config.Object, http.Object);
|
||||
|
||||
//Act
|
||||
bool result = target.IsInQueue(String.Empty);
|
||||
|
@ -12,6 +12,7 @@
|
||||
using Ninject.Moq;
|
||||
using NzbDrone.Core.Providers;
|
||||
using NzbDrone.Core.Repository;
|
||||
using NzbDrone.Core.Repository.Episode;
|
||||
using SubSonic.Repository;
|
||||
using TvdbLib.Data;
|
||||
using System.Linq;
|
||||
@ -20,7 +21,7 @@
|
||||
namespace NzbDrone.Core.Test
|
||||
{
|
||||
[TestFixture]
|
||||
public class SeriesTest
|
||||
public class SeriesProviderTest
|
||||
{
|
||||
[Test]
|
||||
public void Map_path_to_series()
|
||||
@ -34,10 +35,10 @@ public void Map_path_to_series()
|
||||
var moqData = new Mock<IRepository>();
|
||||
var moqTvdb = new Mock<ITvDbProvider>();
|
||||
|
||||
moqData.Setup(f => f.Exists<Series>(c => c.TvdbId == It.IsAny<long>())).Returns(false);
|
||||
moqData.Setup(f => f.Exists<Series>(c => c.SeriesId == It.IsAny<int>())).Returns(false);
|
||||
|
||||
moqTvdb.Setup(f => f.GetSeries(It.IsAny<String>())).Returns(fakeSearch);
|
||||
moqTvdb.Setup(f => f.GetSeries(fakeSeries.Id, It.IsAny<TvdbLanguage>())).Returns(fakeSeries);
|
||||
moqTvdb.Setup(f => f.GetSeries(fakeSeries.Id, false)).Returns(fakeSeries).Verifiable();
|
||||
|
||||
var kernel = new MockingKernel();
|
||||
kernel.Bind<IRepository>().ToConstant(moqData.Object);
|
||||
@ -49,6 +50,7 @@ public void Map_path_to_series()
|
||||
var mappedSeries = seriesController.MapPathToSeries(@"D:\TV Shows\The Simpsons");
|
||||
|
||||
//Assert
|
||||
moqTvdb.VerifyAll();
|
||||
Assert.AreEqual(fakeSeries, mappedSeries);
|
||||
}
|
||||
|
||||
@ -71,7 +73,7 @@ public void tvdbid_is_preserved([RandomNumbers(Minimum = 100, Maximum = 999, Cou
|
||||
{
|
||||
//Arrange
|
||||
var sonicRepo = MockLib.GetEmptyRepository();
|
||||
var series = Builder<Series>.CreateNew().With(c => c.TvdbId = tvdbId).Build();
|
||||
var series = Builder<Series>.CreateNew().With(c => c.SeriesId = tvdbId).Build();
|
||||
|
||||
//Act
|
||||
var addId = sonicRepo.Add(series);
|
||||
@ -80,28 +82,43 @@ public void tvdbid_is_preserved([RandomNumbers(Minimum = 100, Maximum = 999, Cou
|
||||
Assert.AreEqual(tvdbId, addId);
|
||||
var allSeries = sonicRepo.All<Series>();
|
||||
Assert.IsNotEmpty(allSeries);
|
||||
Assert.AreEqual(tvdbId, allSeries.First().TvdbId);
|
||||
Assert.AreEqual(tvdbId, allSeries.First().SeriesId);
|
||||
}
|
||||
|
||||
[Test]
|
||||
[Row(new object[] { "CAPITAL", "capital", true })]
|
||||
[Row(new object[] { "Something!!", "Something", true })]
|
||||
[Row(new object[] { "Simpsons 2000", "Simpsons", true })]
|
||||
[Row(new object[] { "Simp222sons", "Simpsons", true })]
|
||||
[Row(new object[] { "Simpsons", "The Simpsons", true })]
|
||||
[Row(new object[] { "Law and order", "Law & order", true })]
|
||||
[Row(new object[] { "xxAndxx", "xxxx", false })]
|
||||
[Row(new object[] { "Andxx", "xx", false })]
|
||||
[Row(new object[] { "xxAnd", "xx", false })]
|
||||
[Row(new object[] { "Thexx", "xx", false })]
|
||||
[Row(new object[] { "Thexx", "xx", false })]
|
||||
[Row(new object[] { "xxThexx", "xxxxx", false })]
|
||||
[Row(new object[] { "Simpsons The", "Simpsons", true })]
|
||||
public void Name_match_test(string a, string b, bool match)
|
||||
public void get_unmapped()
|
||||
{
|
||||
bool result = TvDbProvider.IsTitleMatch(a, b);
|
||||
//Setup
|
||||
var kernel = new MockingKernel();
|
||||
|
||||
Assert.AreEqual(match, result, "{0} , {1}", a, b);
|
||||
|
||||
kernel.Bind<ISeriesProvider>().To<SeriesProvider>();
|
||||
kernel.Bind<IDiskProvider>().ToConstant(MockLib.GetStandardDisk());
|
||||
|
||||
var seriesController = kernel.Get<ISeriesProvider>();
|
||||
|
||||
//Act
|
||||
var unmappedFolder = seriesController.GetUnmappedFolders();
|
||||
|
||||
//Assert
|
||||
Assert.AreElementsEqualIgnoringOrder(MockLib.StandardSeries, unmappedFolder);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void get_episode_test()
|
||||
{
|
||||
var fakeSeries = Builder<Series>.CreateNew().Build();
|
||||
var fakeEpisode = Builder<EpisodeInfo>.CreateNew().With(c => c.SeriesId).Build();
|
||||
|
||||
Console.WriteLine("test");
|
||||
|
||||
var repo = MockLib.GetEmptyRepository();
|
||||
repo.Add(fakeSeries);
|
||||
repo.Add(fakeEpisode);
|
||||
|
||||
var fetchedSeries = repo.Single<Series>(fakeSeries.SeriesId);
|
||||
|
||||
Assert.IsNotEmpty(fetchedSeries.Episodes);
|
||||
}
|
||||
}
|
||||
}
|
@ -15,14 +15,77 @@ public class TvDbControllerTest
|
||||
[Row("The Simpsons")]
|
||||
[Row("Family Guy")]
|
||||
[Row("South Park")]
|
||||
[Ignore("Have to find a way to mock app path for tests.")]
|
||||
public void TestSearch(string title)
|
||||
[Row("clone high, usa")]
|
||||
public void successful_search(string title)
|
||||
{
|
||||
var tvCont =new TvDbProvider();
|
||||
var tvCont = new TvDbProvider();
|
||||
var result = tvCont.SearchSeries(title);
|
||||
|
||||
Assert.AreNotEqual(0, result.Count);
|
||||
Assert.IsNotEmpty(result);
|
||||
Assert.AreEqual(title, result[0].SeriesName, StringComparison.InvariantCultureIgnoreCase);
|
||||
}
|
||||
|
||||
[Test]
|
||||
[Row("The Simpsons")]
|
||||
[Row("Family Guy")]
|
||||
[Row("South Park")]
|
||||
public void successful_title_lookup(string title)
|
||||
{
|
||||
var tvCont = new TvDbProvider();
|
||||
var result = tvCont.GetSeries(title);
|
||||
|
||||
Assert.AreEqual(title, result.SeriesName, StringComparison.InvariantCultureIgnoreCase);
|
||||
}
|
||||
|
||||
|
||||
[Test]
|
||||
[Row(new object[] { "CAPITAL", "capital", true })]
|
||||
[Row(new object[] { "Something!!", "Something", true })]
|
||||
[Row(new object[] { "Simpsons 2000", "Simpsons", true })]
|
||||
[Row(new object[] { "Simp222sons", "Simpsons", true })]
|
||||
[Row(new object[] { "Simpsons", "The Simpsons", true })]
|
||||
[Row(new object[] { "Law and order", "Law & order", true })]
|
||||
[Row(new object[] { "xxAndxx", "xxxx", false })]
|
||||
[Row(new object[] { "Andxx", "xx", false })]
|
||||
[Row(new object[] { "xxAnd", "xx", false })]
|
||||
[Row(new object[] { "Thexx", "xx", false })]
|
||||
[Row(new object[] { "Thexx", "xx", false })]
|
||||
[Row(new object[] { "xxThexx", "xxxxx", false })]
|
||||
[Row(new object[] { "Simpsons The", "Simpsons", true })]
|
||||
public void Name_match_test(string a, string b, bool match)
|
||||
{
|
||||
bool result = TvDbProvider.IsTitleMatch(a, b);
|
||||
|
||||
Assert.AreEqual(match, result, "{0} , {1}", a, b);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void no_search_result()
|
||||
{
|
||||
//setup
|
||||
var tvdbProvider = new TvDbProvider();
|
||||
|
||||
//act
|
||||
var result = tvdbProvider.SearchSeries("clone high");
|
||||
|
||||
//assert
|
||||
Assert.IsEmpty(result);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void no_result_title_lookup()
|
||||
{
|
||||
//setup
|
||||
var tvdbProvider = new TvDbProvider();
|
||||
|
||||
//act
|
||||
var result = tvdbProvider.GetSeries("clone high");
|
||||
|
||||
//assert
|
||||
Assert.IsNull(result);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
@ -5,13 +5,15 @@
|
||||
using NLog.Config;
|
||||
using NLog.Targets;
|
||||
using NzbDrone.Core.Providers;
|
||||
using NzbDrone.Core.Repository;
|
||||
using NzbDrone.Core.Repository.Episode;
|
||||
using SubSonic.DataProviders;
|
||||
using SubSonic.Repository;
|
||||
using NLog;
|
||||
|
||||
namespace NzbDrone.Core
|
||||
{
|
||||
public static class Main
|
||||
public static class CentralDispatch
|
||||
{
|
||||
public static void BindKernel(IKernel kernel)
|
||||
{
|
||||
@ -19,16 +21,27 @@ public static void BindKernel(IKernel kernel)
|
||||
var provider = ProviderFactory.GetProvider(connectionString, "System.Data.SQLite");
|
||||
|
||||
kernel.Bind<ISeriesProvider>().To<SeriesProvider>();
|
||||
kernel.Bind<ISeasonProvider>().To<SeasonProvider>();
|
||||
kernel.Bind<IEpisodeProvider>().To<EpisodeProvider>();
|
||||
kernel.Bind<IDiskProvider>().To<DiskProvider>();
|
||||
kernel.Bind<ITvDbProvider>().To<TvDbProvider>();
|
||||
kernel.Bind<IConfigProvider>().To<ConfigProvider>();
|
||||
kernel.Bind<log4net.ILog>().ToMethod(c => log4net.LogManager.GetLogger("logger-name"));
|
||||
kernel.Bind<IRepository>().ToMethod(c => new SimpleRepository(provider, SimpleRepositoryOptions.RunMigrations));
|
||||
kernel.Bind<IConfigProvider>().To<ConfigProvider>().InSingletonScope();
|
||||
kernel.Bind<IRepository>().ToMethod(c => new SimpleRepository(provider, SimpleRepositoryOptions.RunMigrations)).InSingletonScope();
|
||||
|
||||
ForceMigration(kernel.Get<IRepository>());
|
||||
}
|
||||
|
||||
public static String AppPath
|
||||
{
|
||||
get { return new DirectoryInfo(HttpContext.Current.Server.MapPath("\\")).FullName; }
|
||||
get
|
||||
{
|
||||
if (HttpContext.Current != null)
|
||||
{
|
||||
return new DirectoryInfo(HttpContext.Current.Server.MapPath("\\")).FullName;
|
||||
}
|
||||
return Directory.GetCurrentDirectory();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -67,5 +80,12 @@ public static void ConfigureNlog()
|
||||
logger.Error("error log message");
|
||||
logger.Fatal("fatal log message");
|
||||
}
|
||||
|
||||
private static void ForceMigration(IRepository repository)
|
||||
{
|
||||
repository.GetPaged<Series>(0, 1);
|
||||
repository.GetPaged<EpisodeInfo>(0, 1);
|
||||
repository.GetPaged<Series>(0, 1);
|
||||
}
|
||||
}
|
||||
}
|
@ -125,7 +125,6 @@
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>Libraries\Castle.Core.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="log4net, Version=1.2.10.0, Culture=neutral, PublicKeyToken=1b44e1d426115821, processorArchitecture=MSIL" />
|
||||
<Reference Include="Ninject, Version=2.0.0.0, Culture=neutral, PublicKeyToken=c7192dc5380945e7, processorArchitecture=MSIL" />
|
||||
<Reference Include="NLog, Version=2.0.0.0, Culture=neutral, PublicKeyToken=5120e14c03d0593c, processorArchitecture=MSIL" />
|
||||
<Reference Include="NLog.Extended, Version=2.0.0.0, Culture=neutral, PublicKeyToken=5120e14c03d0593c, processorArchitecture=MSIL">
|
||||
@ -157,16 +156,17 @@
|
||||
<Compile Include="Providers\ISeriesProvider.cs" />
|
||||
<Compile Include="Providers\ITvDbProvider.cs" />
|
||||
<Compile Include="Providers\SabProvider.cs" />
|
||||
<Compile Include="Providers\SeasonProvider.cs" />
|
||||
<Compile Include="Repository\Episode\RemoteEpisode.cs" />
|
||||
<Compile Include="Repository\Episode\EpisodeInfo.cs" />
|
||||
<Compile Include="Repository\Quality\AllowedQuality.cs" />
|
||||
<Compile Include="Repository\Config.cs" />
|
||||
<Compile Include="Repository\Quality\QualityProfile.cs" />
|
||||
<Compile Include="Repository\Season.cs" />
|
||||
<Compile Include="Repository\RemoteEpisode.cs" />
|
||||
<Compile Include="Repository\LocalEpisode.cs" />
|
||||
<Compile Include="Repository\Episode.cs" />
|
||||
<Compile Include="Repository\Episode\Episode.cs" />
|
||||
<Compile Include="Repository\Quality\QualityTypes.cs" />
|
||||
<Compile Include="Repository\Series.cs" />
|
||||
<Compile Include="Main.cs" />
|
||||
<Compile Include="CentralDispatch.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
<Compile Include="Providers\DiskProvider.cs" />
|
||||
<Compile Include="Providers\IConfigProvider.cs" />
|
||||
|
@ -1,5 +1,5 @@
|
||||
using System;
|
||||
using log4net;
|
||||
using NLog;
|
||||
using NzbDrone.Core.Repository;
|
||||
using SubSonic.Repository;
|
||||
|
||||
@ -8,13 +8,11 @@ namespace NzbDrone.Core.Providers
|
||||
public class ConfigProvider : IConfigProvider
|
||||
{
|
||||
private const string SERIES_ROOTS = "SeriesRoots";
|
||||
private readonly ILog _logger;
|
||||
private static readonly Logger Logger = LogManager.GetCurrentClassLogger();
|
||||
private readonly IRepository _sonicRepo;
|
||||
|
||||
public ConfigProvider(ILog logger, IRepository dataRepository)
|
||||
public ConfigProvider(IRepository dataRepository)
|
||||
{
|
||||
_logger = logger;
|
||||
|
||||
_sonicRepo = dataRepository;
|
||||
}
|
||||
|
||||
@ -39,7 +37,7 @@ public string GetValue(string key, object defaultValue, bool makePermanent)
|
||||
if (dbValue != null && !String.IsNullOrEmpty(dbValue.Value))
|
||||
return dbValue.Value;
|
||||
|
||||
_logger.WarnFormat("Unable to find config key '{0}' defaultValue:'{1}'", key, defaultValue);
|
||||
Logger.Debug("Unable to find config key '{0}' defaultValue:'{1}'", key, defaultValue);
|
||||
if (makePermanent)
|
||||
SetValue(key, defaultValue.ToString());
|
||||
value = defaultValue.ToString();
|
||||
@ -54,16 +52,17 @@ public void SetValue(string key, string value)
|
||||
if (value == null)
|
||||
throw new ArgumentNullException("key");
|
||||
|
||||
_logger.DebugFormat("Writing Setting to file. Key:'{0}' Value:'{1}'", key, value);
|
||||
Logger.Debug("Writing Setting to file. Key:'{0}' Value:'{1}'", key, value);
|
||||
|
||||
var dbValue = _sonicRepo.Single<Config>(key);
|
||||
|
||||
if (dbValue == null)
|
||||
{
|
||||
_sonicRepo.Add(new Config {
|
||||
Key = key,
|
||||
Value = value
|
||||
});
|
||||
_sonicRepo.Add(new Config
|
||||
{
|
||||
Key = key,
|
||||
Value = value
|
||||
});
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1,7 +1,9 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text.RegularExpressions;
|
||||
using NLog;
|
||||
using NzbDrone.Core.Repository;
|
||||
using NzbDrone.Core.Repository.Episode;
|
||||
using NzbDrone.Core.Repository.Quality;
|
||||
using SubSonic.Repository;
|
||||
|
||||
@ -27,12 +29,19 @@ public class EpisodeProvider : IEpisodeProvider
|
||||
|
||||
|
||||
private readonly IRepository _sonicRepo;
|
||||
private readonly ISeriesProvider _seriesProvider;
|
||||
private readonly ISeriesProvider _series;
|
||||
private readonly ISeasonProvider _seasons;
|
||||
private readonly ITvDbProvider _tvDb;
|
||||
private static readonly Logger Logger = NLog.LogManager.GetCurrentClassLogger();
|
||||
|
||||
public EpisodeProvider(IRepository sonicRepo, ISeriesProvider seriesProvider)
|
||||
|
||||
public EpisodeProvider(IRepository sonicRepo, ISeriesProvider seriesProvider, ISeasonProvider seasonProvider, ITvDbProvider tvDbProvider)
|
||||
{
|
||||
_sonicRepo = sonicRepo;
|
||||
_seriesProvider = seriesProvider;
|
||||
_series = seriesProvider;
|
||||
_tvDb = tvDbProvider;
|
||||
_seasons = seasonProvider;
|
||||
|
||||
}
|
||||
|
||||
public Episode GetEpisode(long id)
|
||||
@ -40,7 +49,7 @@ public Episode GetEpisode(long id)
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public Episode SaveEpisode(Episode episode)
|
||||
public Episode UpdateEpisode(Episode episode)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
@ -57,7 +66,7 @@ public IList<Episode> GetEpisodeBySeries(long seriesId)
|
||||
|
||||
public String GetSabTitle(Episode episode)
|
||||
{
|
||||
var series = _seriesProvider.GetSeries(episode.SeriesId);
|
||||
var series = _series.GetSeries(episode.SeriesId);
|
||||
if (series == null) throw new ArgumentException("Unknown series. ID: " + episode.SeriesId);
|
||||
|
||||
//TODO: This method should return a standard title for the sab episode.
|
||||
@ -75,6 +84,44 @@ public bool IsNeeded(Episode episode)
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public void RefreshSeries(int seriesId)
|
||||
{
|
||||
Logger.Info("Starting episode info refresh for series:{0}", seriesId);
|
||||
int successCount = 0;
|
||||
int failCount = 0;
|
||||
var targetSeries = _tvDb.GetSeries(seriesId, true);
|
||||
foreach (var episode in targetSeries.Episodes)
|
||||
{
|
||||
try
|
||||
{
|
||||
_seasons.EnsureSeason(seriesId, episode.SeasonId, episode.SeasonNumber);
|
||||
var newEpisode = new EpisodeInfo()
|
||||
{
|
||||
AirDate = episode.FirstAired,
|
||||
EpisodeId = episode.Id,
|
||||
EpisodeNumber = episode.EpisodeNumber,
|
||||
Language = episode.Language.Abbriviation,
|
||||
Overview = episode.Overview,
|
||||
SeasonId = episode.SeasonId,
|
||||
SeasonNumber = episode.SeasonNumber,
|
||||
SeriesId = episode.SeriesId,
|
||||
Title = episode.EpisodeName
|
||||
};
|
||||
|
||||
_sonicRepo.Add<EpisodeInfo>(newEpisode);
|
||||
successCount++;
|
||||
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
Logger.FatalException(String.Format("An error has occured while updating episode info for series {0}", seriesId), e);
|
||||
failCount++;
|
||||
}
|
||||
}
|
||||
|
||||
Logger.Info("Finished episode refresh for series:{0}. Success:{1} - Fail:{2} ", seriesId, successCount, failCount);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
@ -82,27 +129,25 @@ public bool IsNeeded(Episode episode)
|
||||
/// </summary>
|
||||
/// <param name="title">Title of the report</param>
|
||||
/// <returns>List of episodes relating to the post</returns>
|
||||
public static List<Episode> Parse(string title)
|
||||
public static List<RemoteEpisode> Parse(string title)
|
||||
{
|
||||
var match = ParseRegex.Match(title);
|
||||
|
||||
if (!match.Success)
|
||||
throw new ArgumentException(String.Format("Title doesn't match any know patterns. [{0}]", title));
|
||||
|
||||
var result = new List<Episode>();
|
||||
var result = new List<RemoteEpisode>();
|
||||
|
||||
result.Add(new Episode() { EpisodeNumber = Convert.ToInt32(match.Groups["episodeNumber"].Value) });
|
||||
result.Add(new RemoteEpisode { EpisodeNumber = Convert.ToInt32(match.Groups["episodeNumber"].Value) });
|
||||
|
||||
if (match.Groups["episodeNumber2"].Success)
|
||||
{
|
||||
result.Add(new Episode() { EpisodeNumber = Convert.ToInt32(match.Groups["episodeNumber2"].Value) });
|
||||
result.Add(new RemoteEpisode { EpisodeNumber = Convert.ToInt32(match.Groups["episodeNumber2"].Value) });
|
||||
}
|
||||
|
||||
foreach (var ep in result)
|
||||
{
|
||||
//TODO: Get TVDB episode Title, Series name and the rest of the details
|
||||
ep.SeasonNumber = Convert.ToInt32(match.Groups["seasonNumber"].Value);
|
||||
ep.Title = ReplaceSeparatorChars(match.Groups["episodeName"].Value);
|
||||
ep.Proper = title.Contains("PROPER");
|
||||
ep.Quality = QualityTypes.Unknown;
|
||||
}
|
||||
@ -110,13 +155,5 @@ public static List<Episode> Parse(string title)
|
||||
return result;
|
||||
}
|
||||
|
||||
private static string ReplaceSeparatorChars(string text)
|
||||
{
|
||||
if (text == null)
|
||||
throw new ArgumentNullException("text");
|
||||
|
||||
return text.Replace('.', ' ').Replace('-', ' ').Replace('_', ' ').Trim();
|
||||
}
|
||||
|
||||
}
|
||||
}
|
@ -1,13 +1,14 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using NzbDrone.Core.Repository;
|
||||
using NzbDrone.Core.Repository.Episode;
|
||||
|
||||
namespace NzbDrone.Core.Providers
|
||||
{
|
||||
public interface IEpisodeProvider
|
||||
{
|
||||
Episode GetEpisode(long id);
|
||||
Episode SaveEpisode(Episode episode);
|
||||
Episode UpdateEpisode(Episode episode);
|
||||
IList<Episode> GetEpisodesBySeason(long seasonId);
|
||||
IList<Episode> GetEpisodeBySeries(long seriesId);
|
||||
String GetSabTitle(Episode episode);
|
||||
@ -18,5 +19,7 @@ public interface IEpisodeProvider
|
||||
/// <param name="episode">Episode that needs to be checked</param>
|
||||
/// <returns></returns>
|
||||
bool IsNeeded(Episode episode);
|
||||
|
||||
void RefreshSeries(int seriesId);
|
||||
}
|
||||
}
|
@ -5,10 +5,9 @@ namespace NzbDrone.Core.Providers
|
||||
{
|
||||
public interface ISeasonProvider
|
||||
{
|
||||
Season GetSeason(long seasonId);
|
||||
List<Season> GetSeasongs(long seriesId);
|
||||
|
||||
Season GetSeason(int seasonId);
|
||||
List<Season> GetSeasongs(int seriesId);
|
||||
void EnsureSeason(int seriesId, int seasonId, int seasonNumber);
|
||||
int SaveSeason(Season season);
|
||||
}
|
||||
|
||||
}
|
@ -9,7 +9,7 @@ namespace NzbDrone.Core.Providers
|
||||
public interface ISeriesProvider
|
||||
{
|
||||
IQueryable<Series> GetSeries();
|
||||
Series GetSeries(long tvdbId);
|
||||
Series GetSeries(int seriesId);
|
||||
void SyncSeriesWithDisk();
|
||||
|
||||
/// <summary>
|
||||
|
@ -6,7 +6,7 @@ namespace NzbDrone.Core.Providers
|
||||
public interface ITvDbProvider
|
||||
{
|
||||
IList<TvdbSearchResult> SearchSeries(string name);
|
||||
TvdbSeries GetSeries(int id, TvdbLanguage language);
|
||||
TvdbSearchResult GetSeries(string title);
|
||||
TvdbSeries GetSeries(int id, bool loadEpisodes);
|
||||
}
|
||||
}
|
@ -2,20 +2,20 @@
|
||||
using System.Linq;
|
||||
using System.Web;
|
||||
using System.Xml.Linq;
|
||||
using log4net;
|
||||
using NLog;
|
||||
|
||||
namespace NzbDrone.Core.Providers
|
||||
{
|
||||
public class SabProvider : IDownloadProvider
|
||||
{
|
||||
private readonly IConfigProvider _config;
|
||||
private readonly ILog _logger;
|
||||
private readonly IHttpProvider _http;
|
||||
|
||||
public SabProvider(IConfigProvider config, ILog logger, IHttpProvider http)
|
||||
private static readonly Logger Logger = LogManager.GetCurrentClassLogger();
|
||||
|
||||
public SabProvider(IConfigProvider config, IHttpProvider http)
|
||||
{
|
||||
_config = config;
|
||||
_logger = logger;
|
||||
_http = http;
|
||||
}
|
||||
|
||||
@ -32,10 +32,10 @@ public bool AddByUrl(string url, string title)
|
||||
string action = string.Format("mode={0}&name={1}&priority={2}&cat={3}&nzbname={4}", mode, name, priority, cat, nzbName);
|
||||
string request = GetSabRequest(action);
|
||||
|
||||
_logger.DebugFormat("Adding report [{0}] to the queue.", nzbName);
|
||||
Logger.Debug("Adding report [{0}] to the queue.", nzbName);
|
||||
|
||||
string response = _http.DownloadString(request).Replace("\n", String.Empty);
|
||||
_logger.DebugFormat("Queue Repsonse: [{0}]", response);
|
||||
Logger.Debug("Queue Repsonse: [{0}]", response);
|
||||
|
||||
if (response == "ok")
|
||||
return true;
|
||||
@ -61,7 +61,7 @@ public bool IsInQueue(string title)
|
||||
//Get the Count of Items in Queue where 'filename' is Equal to goodName, if not zero, return true (isInQueue)))
|
||||
if ((xDoc.Descendants("slot").Where(s => s.Element("filename").Value.Equals(title, StringComparison.InvariantCultureIgnoreCase))).Count() != 0)
|
||||
{
|
||||
_logger.DebugFormat("Episode in queue - '{0}'", title);
|
||||
Logger.Debug("Episode in queue - '{0}'", title);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
54
NzbDrone.Core/Providers/SeasonProvider.cs
Normal file
54
NzbDrone.Core/Providers/SeasonProvider.cs
Normal file
@ -0,0 +1,54 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using NLog;
|
||||
using NzbDrone.Core.Repository;
|
||||
using SubSonic.Repository;
|
||||
|
||||
namespace NzbDrone.Core.Providers
|
||||
{
|
||||
class SeasonProvider : ISeasonProvider
|
||||
{
|
||||
private readonly IRepository _sonicRepo;
|
||||
private static readonly Logger Logger = NLog.LogManager.GetCurrentClassLogger();
|
||||
|
||||
public SeasonProvider(IRepository dataRepository)
|
||||
{
|
||||
_sonicRepo = dataRepository;
|
||||
}
|
||||
|
||||
public Season GetSeason(int seasonId)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public List<Season> GetSeasongs(int seriesId)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public void EnsureSeason(int seriesId, int seasonId, int seasonNumber)
|
||||
{
|
||||
if (_sonicRepo.Exists<Season>(s => s.SeasonId == seasonId))
|
||||
return;
|
||||
//TODO: Calculate Season Folder
|
||||
Logger.Debug("Creating Season. SeriesID:{0} SeasonID:{1} SeasonNumber:{2} Folder:{3}", seriesId, seasonId, seasonNumber, string.Empty);
|
||||
|
||||
var newSeason = new Season()
|
||||
{
|
||||
Folder = String.Empty,
|
||||
Monitored = true,
|
||||
SeasonId = seasonId,
|
||||
SeasonNumber = seasonNumber,
|
||||
SeriesId = seriesId
|
||||
};
|
||||
_sonicRepo.Add<Season>(newSeason);
|
||||
}
|
||||
|
||||
|
||||
|
||||
public int SaveSeason(Season season)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
}
|
@ -3,7 +3,6 @@
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Text.RegularExpressions;
|
||||
using log4net;
|
||||
using NLog;
|
||||
using NzbDrone.Core.Repository;
|
||||
using SubSonic.Repository;
|
||||
@ -38,7 +37,7 @@ public class SeriesProvider : ISeriesProvider
|
||||
private readonly IDiskProvider _diskProvider;
|
||||
private readonly IRepository _sonioRepo;
|
||||
private readonly ITvDbProvider _tvDb;
|
||||
private static readonly Logger Logger = NLog.LogManager.GetCurrentClassLogger();
|
||||
private static readonly Logger Logger = LogManager.GetCurrentClassLogger();
|
||||
private static readonly Regex CleanUpRegex = new Regex(@"((\s|^)the(\s|$))|((\s|^)and(\s|$))|[^a-z]", RegexOptions.IgnoreCase | RegexOptions.Compiled);
|
||||
|
||||
public SeriesProvider(IDiskProvider diskProvider, IConfigProvider configProvider, IRepository dataRepository, ITvDbProvider tvDbProvider)
|
||||
@ -56,9 +55,9 @@ public IQueryable<Series> GetSeries()
|
||||
return _sonioRepo.All<Series>();
|
||||
}
|
||||
|
||||
public Series GetSeries(long tvdbId)
|
||||
public Series GetSeries(int seriesId)
|
||||
{
|
||||
return _sonioRepo.Single<Series>(s => s.TvdbId == tvdbId);
|
||||
return _sonioRepo.Single<Series>(s => s.SeriesId == seriesId);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@ -68,7 +67,7 @@ public Series GetSeries(long tvdbId)
|
||||
/// <returns>Whether or not the show is monitored</returns>
|
||||
public bool IsMonitored(long id)
|
||||
{
|
||||
return _sonioRepo.Exists<Series>(c => c.TvdbId == id && c.Monitored);
|
||||
return _sonioRepo.Exists<Series>(c => c.SeriesId == id && c.Monitored);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@ -99,16 +98,18 @@ public void SyncSeriesWithDisk()
|
||||
if (mappedSeries == null)
|
||||
{
|
||||
Logger.Warn("Unable to find a matching series for '{0}'", seriesFolder);
|
||||
break;
|
||||
}
|
||||
|
||||
if (!_sonioRepo.Exists<Series>(s => s.TvdbId == mappedSeries.Id))
|
||||
{
|
||||
RegisterSeries(seriesFolder, mappedSeries);
|
||||
}
|
||||
else
|
||||
{
|
||||
Logger.Warn("Folder '{0}' mapped to '{1}' which is already another folder assigned to it.'", seriesFolder, mappedSeries.SeriesName);
|
||||
|
||||
if (!_sonioRepo.Exists<Series>(s => s.SeriesId == mappedSeries.Id))
|
||||
{
|
||||
RegisterSeries(seriesFolder, mappedSeries);
|
||||
}
|
||||
else
|
||||
{
|
||||
Logger.Warn("Folder '{0}' mapped to '{1}' which is already another folder assigned to it.'", seriesFolder, mappedSeries.SeriesName);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@ -137,7 +138,7 @@ public TvdbSeries MapPathToSeries(string path)
|
||||
if (searchResults == null)
|
||||
return null;
|
||||
|
||||
return _tvDb.GetSeries(searchResults.Id, searchResults.Language);
|
||||
return _tvDb.GetSeries(searchResults.Id, false);
|
||||
}
|
||||
|
||||
|
||||
@ -145,7 +146,7 @@ public void RegisterSeries(string path, TvdbSeries series)
|
||||
{
|
||||
Logger.Info("registering '{0}' with [{1}]-{2}", path, series.Id, series.SeriesName);
|
||||
var repoSeries = new Series();
|
||||
repoSeries.TvdbId = series.Id;
|
||||
repoSeries.SeriesId = series.Id;
|
||||
repoSeries.Title = series.SeriesName;
|
||||
repoSeries.AirTimes = series.AirsTime;
|
||||
repoSeries.AirsDayOfWeek = series.AirsDayOfWeek;
|
||||
|
@ -19,7 +19,7 @@ public class TvDbProvider : ITvDbProvider
|
||||
|
||||
public TvDbProvider()
|
||||
{
|
||||
_handler = new TvdbHandler(new XmlCacheProvider(Path.Combine(Main.AppPath, @"cache\tvdbcache.xml")), TVDB_APIKEY);
|
||||
_handler = new TvdbHandler(new XmlCacheProvider(CentralDispatch.AppPath + @"\cache\tvdb"), TVDB_APIKEY);
|
||||
}
|
||||
|
||||
#region ITvDbProvider Members
|
||||
@ -44,13 +44,17 @@ public IList<TvdbSearchResult> SearchSeries(string title)
|
||||
|
||||
public TvdbSearchResult GetSeries(string title)
|
||||
{
|
||||
return SearchSeries(title)[0];
|
||||
var searchResults = SearchSeries(title);
|
||||
if (searchResults.Count == 0)
|
||||
return null;
|
||||
|
||||
return searchResults[0];
|
||||
}
|
||||
|
||||
public TvdbSeries GetSeries(int id, TvdbLanguage language)
|
||||
public TvdbSeries GetSeries(int id, bool loadEpisodes)
|
||||
{
|
||||
Logger.Debug("Fetching seriesId'{0}' - '{1}' from tvdb", id, language);
|
||||
return _handler.GetSeries(id, language, true, false, false);
|
||||
Logger.Debug("Fetching SeriesId'{0}' from tvdb", id);
|
||||
return _handler.GetSeries(id, TvdbLanguage.DefaultLanguage, loadEpisodes, false, false);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -2,6 +2,7 @@
|
||||
|
||||
namespace NzbDrone.Core.Repository
|
||||
{
|
||||
[SubSonicTableNameOverride("Config")]
|
||||
public class Config
|
||||
{
|
||||
[SubSonicPrimaryKey]
|
||||
|
@ -1,27 +0,0 @@
|
||||
using System;
|
||||
using NzbDrone.Core.Repository.Quality;
|
||||
using SubSonic.SqlGeneration.Schema;
|
||||
|
||||
namespace NzbDrone.Core.Repository
|
||||
{
|
||||
public class Episode
|
||||
{
|
||||
[SubSonicPrimaryKey(false)]
|
||||
public long EpisodeId { get; set; }
|
||||
|
||||
public long SeriesId { get; set; }
|
||||
public string Title { get; set; }
|
||||
public long SeasonId { get; set; }
|
||||
public int SeasonNumber { get; set; }
|
||||
public int EpisodeNumber { get; set; }
|
||||
public DateTime AirDate { get; set; }
|
||||
public QualityTypes Quality { get; set; }
|
||||
public bool Proper { get; set; }
|
||||
|
||||
[SubSonicToOneRelation(ThisClassContainsJoinKey = true)]
|
||||
public virtual Season Season { get; private set; }
|
||||
|
||||
[SubSonicToOneRelation(ThisClassContainsJoinKey = true)]
|
||||
public virtual Series Series { get; private set; }
|
||||
}
|
||||
}
|
16
NzbDrone.Core/Repository/Episode/Episode.cs
Normal file
16
NzbDrone.Core/Repository/Episode/Episode.cs
Normal file
@ -0,0 +1,16 @@
|
||||
using System;
|
||||
using NzbDrone.Core.Repository.Quality;
|
||||
using SubSonic.SqlGeneration.Schema;
|
||||
|
||||
namespace NzbDrone.Core.Repository.Episode
|
||||
{
|
||||
public class Episode
|
||||
{
|
||||
public virtual int SeriesId { get; set; }
|
||||
public int SeasonNumber { get; set; }
|
||||
public int EpisodeNumber { get; set; }
|
||||
|
||||
[SubSonicToOneRelation(ThisClassContainsJoinKey = true)]
|
||||
public virtual Series Series { get; private set; }
|
||||
}
|
||||
}
|
24
NzbDrone.Core/Repository/Episode/EpisodeInfo.cs
Normal file
24
NzbDrone.Core/Repository/Episode/EpisodeInfo.cs
Normal file
@ -0,0 +1,24 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using SubSonic.SqlGeneration.Schema;
|
||||
|
||||
namespace NzbDrone.Core.Repository.Episode
|
||||
{
|
||||
[SubSonicTableNameOverride("EpisodeInfo")]
|
||||
public class EpisodeInfo : Episode
|
||||
{
|
||||
[SubSonicPrimaryKey(false)]
|
||||
public virtual int EpisodeId { get; set; }
|
||||
public int SeasonId { get; set; }
|
||||
public string Title { get; set; }
|
||||
public DateTime AirDate { get; set; }
|
||||
[SubSonicLongString]
|
||||
public string Overview { get; set; }
|
||||
public string Language { get; set; }
|
||||
|
||||
[SubSonicToOneRelation(ThisClassContainsJoinKey = true)]
|
||||
public virtual Season Season { get; set; }
|
||||
}
|
||||
}
|
17
NzbDrone.Core/Repository/Episode/RemoteEpisode.cs
Normal file
17
NzbDrone.Core/Repository/Episode/RemoteEpisode.cs
Normal file
@ -0,0 +1,17 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.ServiceModel.Syndication;
|
||||
using System.Text;
|
||||
using NzbDrone.Core.Repository.Quality;
|
||||
using SubSonic.SqlGeneration.Schema;
|
||||
|
||||
namespace NzbDrone.Core.Repository.Episode
|
||||
{
|
||||
public class RemoteEpisode : Episode
|
||||
{
|
||||
public QualityTypes Quality { get; set; }
|
||||
public SyndicationItem Feed { get; set; }
|
||||
public bool Proper { get; set; }
|
||||
}
|
||||
}
|
@ -1,11 +0,0 @@
|
||||
using System;
|
||||
using System.ServiceModel.Syndication;
|
||||
using SubSonic.SqlGeneration.Schema;
|
||||
|
||||
namespace NzbDrone.Core.Repository
|
||||
{
|
||||
public class LocalEpisode : Episode
|
||||
{
|
||||
public String Path { get; set; }
|
||||
}
|
||||
}
|
@ -1,12 +0,0 @@
|
||||
using System;
|
||||
using System.ServiceModel.Syndication;
|
||||
using SubSonic.SqlGeneration.Schema;
|
||||
|
||||
namespace NzbDrone.Core.Repository
|
||||
{
|
||||
public class RemoteEpisode : Episode
|
||||
{
|
||||
[SubSonicIgnore]
|
||||
public SyndicationItem Feed { get; set; }
|
||||
}
|
||||
}
|
@ -8,16 +8,16 @@ namespace NzbDrone.Core.Repository
|
||||
public class Season
|
||||
{
|
||||
[SubSonicPrimaryKey(false)]
|
||||
public long SeasonId { get; set; }
|
||||
public virtual long SeasonId { get; set; }
|
||||
public long SeriesId { get; set; }
|
||||
public int SeasonNumber { get; set; }
|
||||
public bool Monitored { get; set; }
|
||||
public string Folder { get; set; }
|
||||
|
||||
[SubSonicToManyRelation]
|
||||
public virtual List<Episode> Episodes { get; set; }
|
||||
public virtual List<Episode.Episode> Episodes { get; private set; }
|
||||
|
||||
[SubSonicToOneRelation(ThisClassContainsJoinKey = true)]
|
||||
public virtual Series Series { get; set; }
|
||||
public virtual Series Series { get; private set; }
|
||||
}
|
||||
}
|
@ -1,5 +1,6 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using NzbDrone.Core.Repository.Episode;
|
||||
using SubSonic.SqlGeneration.Schema;
|
||||
|
||||
namespace NzbDrone.Core.Repository
|
||||
@ -7,7 +8,7 @@ namespace NzbDrone.Core.Repository
|
||||
public class Series
|
||||
{
|
||||
[SubSonicPrimaryKey(false)]
|
||||
public int TvdbId { get; set; }
|
||||
public virtual int SeriesId { get; set; }
|
||||
|
||||
public string Title { get; set; }
|
||||
|
||||
@ -32,8 +33,8 @@ public class Series
|
||||
public virtual List<Season> Seasons { get; private set; }
|
||||
|
||||
[SubSonicToManyRelation]
|
||||
public virtual List<Episode> Episodes { get; private set; }
|
||||
public virtual List<EpisodeInfo> Episodes { get; private set; }
|
||||
|
||||
|
||||
|
||||
}
|
||||
}
|
@ -10,12 +10,14 @@ namespace NzbDrone.Web.Controllers
|
||||
public class SeriesController : Controller
|
||||
{
|
||||
private readonly ISeriesProvider _seriesProvider;
|
||||
private readonly IEpisodeProvider _episodeProvider;
|
||||
//
|
||||
// GET: /Series/
|
||||
|
||||
public SeriesController(ISeriesProvider seriesProvider)
|
||||
public SeriesController(ISeriesProvider seriesProvider, IEpisodeProvider episodeProvider)
|
||||
{
|
||||
_seriesProvider = seriesProvider;
|
||||
_episodeProvider = episodeProvider;
|
||||
}
|
||||
|
||||
public ActionResult Index()
|
||||
@ -39,90 +41,23 @@ public ActionResult UnMapped()
|
||||
}
|
||||
|
||||
|
||||
public ActionResult LoadEpisodes(int seriesId)
|
||||
{
|
||||
_episodeProvider.RefreshSeries(seriesId);
|
||||
return RedirectToAction("Details", new
|
||||
{
|
||||
seriesId = seriesId
|
||||
});
|
||||
}
|
||||
|
||||
//
|
||||
// GET: /Series/Details/5
|
||||
|
||||
public ActionResult Details(int tvdbId)
|
||||
public ActionResult Details(int seriesId)
|
||||
{
|
||||
return View(_seriesProvider.GetSeries(tvdbId));
|
||||
return View(_seriesProvider.GetSeries(seriesId));
|
||||
}
|
||||
|
||||
//
|
||||
// GET: /Series/Create
|
||||
|
||||
public ActionResult Create()
|
||||
{
|
||||
return View();
|
||||
}
|
||||
|
||||
//
|
||||
// POST: /Series/Create
|
||||
|
||||
[HttpPost]
|
||||
public ActionResult Create(FormCollection collection)
|
||||
{
|
||||
try
|
||||
{
|
||||
// TODO: Add insert logic here
|
||||
|
||||
return RedirectToAction("Index");
|
||||
}
|
||||
catch
|
||||
{
|
||||
return View();
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// GET: /Series/Edit/5
|
||||
|
||||
public ActionResult Edit(int id)
|
||||
{
|
||||
return View();
|
||||
}
|
||||
|
||||
//
|
||||
// POST: /Series/Edit/5
|
||||
|
||||
[HttpPost]
|
||||
public ActionResult Edit(int id, FormCollection collection)
|
||||
{
|
||||
try
|
||||
{
|
||||
// TODO: Add update logic here
|
||||
|
||||
return RedirectToAction("Index");
|
||||
}
|
||||
catch
|
||||
{
|
||||
return View();
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// GET: /Series/Delete/5
|
||||
|
||||
public ActionResult Delete(int id)
|
||||
{
|
||||
return View();
|
||||
}
|
||||
|
||||
//
|
||||
// POST: /Series/Delete/5
|
||||
|
||||
[HttpPost]
|
||||
public ActionResult Delete(int id, FormCollection collection)
|
||||
{
|
||||
try
|
||||
{
|
||||
// TODO: Add delete logic here
|
||||
|
||||
return RedirectToAction("Index");
|
||||
}
|
||||
catch
|
||||
{
|
||||
return View();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -27,7 +27,7 @@ public static void RegisterRoutes(RouteCollection routes)
|
||||
|
||||
protected override void OnApplicationStarted()
|
||||
{
|
||||
Main.ConfigureNlog();
|
||||
CentralDispatch.ConfigureNlog();
|
||||
AreaRegistration.RegisterAllAreas();
|
||||
RegisterRoutes(RouteTable.Routes);
|
||||
base.OnApplicationStarted();
|
||||
@ -36,7 +36,7 @@ protected override void OnApplicationStarted()
|
||||
protected override IKernel CreateKernel()
|
||||
{
|
||||
_kernel = new StandardKernel();
|
||||
Main.BindKernel(_kernel);
|
||||
CentralDispatch.BindKernel(_kernel);
|
||||
return _kernel;
|
||||
}
|
||||
|
||||
|
@ -1,35 +1,52 @@
|
||||
<%@ Page Title="" Language="C#" MasterPageFile="~/Views/Shared/Site.Master" Inherits="System.Web.Mvc.ViewPage<NzbDrone.Core.Repository.Series>" %>
|
||||
|
||||
<%@ Import Namespace="Telerik.Web.Mvc.UI" %>
|
||||
<asp:Content ID="Content1" ContentPlaceHolderID="TitleContent" runat="server">
|
||||
<%: Model.Title %>
|
||||
<%: Model.Title %>
|
||||
</asp:Content>
|
||||
|
||||
<asp:Content ID="Content2" ContentPlaceHolderID="MainContent" runat="server">
|
||||
<fieldset>
|
||||
|
||||
<div class="display-label">ID</div>
|
||||
<div class="display-field"><%: Model.TvdbId %></div>
|
||||
|
||||
<div class="display-label">Overview</div>
|
||||
<div class="display-field"><%: Model.Overview %></div>
|
||||
|
||||
<div class="display-label">Status</div>
|
||||
<div class="display-field"><%: Model.Status %></div>
|
||||
|
||||
<div class="display-label">AirTimes</div>
|
||||
<div class="display-field"><%: Model.AirTimes %></div>
|
||||
|
||||
<div class="display-label">Language</div>
|
||||
<div class="display-field"><%: Model.Language.ToUpper() %></div>
|
||||
|
||||
<div class="display-label">Location</div>
|
||||
<div class="display-field"><%: Model.Path %></div>
|
||||
|
||||
<div class="display-label">
|
||||
ID</div>
|
||||
<div class="display-field">
|
||||
<%: Model.SeriesId %></div>
|
||||
<div class="display-label">
|
||||
Overview</div>
|
||||
<div class="display-field">
|
||||
<%: Model.Overview %></div>
|
||||
<div class="display-label">
|
||||
Status</div>
|
||||
<div class="display-field">
|
||||
<%: Model.Status %></div>
|
||||
<div class="display-label">
|
||||
AirTimes</div>
|
||||
<div class="display-field">
|
||||
<%: Model.AirTimes %></div>
|
||||
<div class="display-label">
|
||||
Language</div>
|
||||
<div class="display-field">
|
||||
<%: Model.Language.ToUpper() %></div>
|
||||
<div class="display-label">
|
||||
Location</div>
|
||||
<div class="display-field">
|
||||
<%: Model.Path %></div>
|
||||
</fieldset>
|
||||
<%= Html.Telerik().Grid(Model.Episodes)
|
||||
.Name("Episodes")
|
||||
.Columns(columns =>
|
||||
{
|
||||
columns.Bound(c => c.EpisodeNumber).Width(10);
|
||||
columns.Bound(c => c.Title);
|
||||
columns.Bound(c => c.AirDate).Format("{0:d}").Width(150);
|
||||
})
|
||||
.Groupable(grouping => grouping.Groups(groups => groups.Add(c => c.SeasonNumber)))
|
||||
.Sortable(rows=>rows
|
||||
.OrderBy(epSort => epSort.Add(c => c.EpisodeNumber)))
|
||||
|
||||
%>
|
||||
<p>
|
||||
<%-- <%: Html.ActionLink("Edit", "Edit", new { /* id=Model.PrimaryKey */ }) %> |--%>
|
||||
<%-- <%: Html.ActionLink("Edit", "Edit", new { /* id=Model.PrimaryKey */ }) %> |--%>
|
||||
<%: Html.ActionLink("Back to List", "Index") %>
|
||||
<%: Html.ActionLink("Load Episodes", "LoadEpisodes", new{seriesId= Model.SeriesId}) %>
|
||||
</p>
|
||||
|
||||
</asp:Content>
|
||||
|
||||
|
@ -20,11 +20,11 @@
|
||||
.Name("Grid")
|
||||
.Columns(columns =>
|
||||
{
|
||||
columns.Bound(o => o.TvdbId).Width(100);
|
||||
columns.Bound(o => o.SeriesId).Width(100);
|
||||
columns.Template(c =>
|
||||
{
|
||||
%>
|
||||
<%:Html.ActionLink(c.Title, "Details", new {tvdbId =c.TvdbId}) %>
|
||||
<%:Html.ActionLink(c.Title, "Details", new {seriesId =c.SeriesId}) %>
|
||||
<%
|
||||
}).Title("Title");
|
||||
columns.Bound(o => o.Status);
|
||||
|
Loading…
Reference in New Issue
Block a user