1
0
mirror of https://github.com/Radarr/Radarr.git synced 2024-11-04 10:02:40 +01:00

basic RSS fetch seems to be working.

download might still not work.
This commit is contained in:
kay.one 2013-04-27 17:25:28 -07:00
parent 182192e0ba
commit a1783a53a9
20 changed files with 186 additions and 22 deletions

View File

@ -5,6 +5,7 @@
using NzbDrone.Api.Mapping; using NzbDrone.Api.Mapping;
using NzbDrone.Api.RootFolders; using NzbDrone.Api.RootFolders;
using NzbDrone.Api.Series; using NzbDrone.Api.Series;
using NzbDrone.Core.Indexers;
using NzbDrone.Core.Organizer; using NzbDrone.Core.Organizer;
using NzbDrone.Core.RootFolders; using NzbDrone.Core.RootFolders;
using NzbDrone.Test.Common; using NzbDrone.Test.Common;
@ -18,6 +19,7 @@ public class ResourceMappingFixture : TestBase
[TestCase(typeof(Core.Tv.Episode), typeof(EpisodeResource))] [TestCase(typeof(Core.Tv.Episode), typeof(EpisodeResource))]
[TestCase(typeof(RootFolder), typeof(RootFolderResource))] [TestCase(typeof(RootFolder), typeof(RootFolderResource))]
[TestCase(typeof(NamingConfig), typeof(NamingConfigResource))] [TestCase(typeof(NamingConfig), typeof(NamingConfigResource))]
[TestCase(typeof(IndexerDefinition), typeof(IndexerRepository))]
public void matching_fields(Type modelType, Type resourceType) public void matching_fields(Type modelType, Type resourceType)
{ {
MappingValidation.ValidateMapping(modelType, resourceType); MappingValidation.ValidateMapping(modelType, resourceType);

View File

@ -0,0 +1,21 @@
using System.Collections.Generic;
using NzbDrone.Core.Indexers;
namespace NzbDrone.Api.Indexers
{
public class IndexerModule : NzbDroneRestModule<IndexerResource>
{
private readonly IIndexerService _indexerService;
public IndexerModule(IIndexerService indexerService)
{
_indexerService = indexerService;
GetResourceAll = GetAll;
}
private List<IndexerResource> GetAll()
{
return ApplyToList(_indexerService.All);
}
}
}

View File

@ -0,0 +1,12 @@
using System;
using NzbDrone.Api.REST;
namespace NzbDrone.Api.Indexers
{
public class IndexerResource : RestResource
{
public Boolean Enable { get; set; }
public String Name { get; set; }
public String Settings { get; set; }
}
}

View File

@ -94,6 +94,8 @@
<Compile Include="Frontend\IndexModule.cs" /> <Compile Include="Frontend\IndexModule.cs" />
<Compile Include="Frontend\StaticResourceProvider.cs" /> <Compile Include="Frontend\StaticResourceProvider.cs" />
<Compile Include="Frontend\StaticResourceMapper.cs" /> <Compile Include="Frontend\StaticResourceMapper.cs" />
<Compile Include="Indexers\IndexerModule.cs" />
<Compile Include="Indexers\IndexerResource.cs" />
<Compile Include="Mapping\MappingValidation.cs" /> <Compile Include="Mapping\MappingValidation.cs" />
<Compile Include="Mapping\ResourceMappingException.cs" /> <Compile Include="Mapping\ResourceMappingException.cs" />
<Compile Include="Mapping\ValueInjectorExtensions.cs" /> <Compile Include="Mapping\ValueInjectorExtensions.cs" />
@ -103,6 +105,7 @@
<Compile Include="Resolvers\EndTimeResolver.cs" /> <Compile Include="Resolvers\EndTimeResolver.cs" />
<Compile Include="Resolvers\NextAiringResolver.cs" /> <Compile Include="Resolvers\NextAiringResolver.cs" />
<Compile Include="Resolvers\NullableDatetimeToString.cs" /> <Compile Include="Resolvers\NullableDatetimeToString.cs" />
<Compile Include="REST\BadRequestException.cs" />
<Compile Include="REST\ResourceValidator.cs" /> <Compile Include="REST\ResourceValidator.cs" />
<Compile Include="REST\RestModule.cs" /> <Compile Include="REST\RestModule.cs" />
<Compile Include="REST\RestResource.cs" /> <Compile Include="REST\RestResource.cs" />

View File

@ -0,0 +1,14 @@
using System;
using Nancy;
using NzbDrone.Api.ErrorManagement;
namespace NzbDrone.Api.REST
{
public class BadRequestException : ApiException
{
public BadRequestException(object content = null)
: base(HttpStatusCode.BadRequest, content)
{
}
}
}

View File

@ -25,6 +25,15 @@ public abstract class RestModule<TResource> : NancyModule
protected ResourceValidator<TResource> SharedValidator { get; private set; } protected ResourceValidator<TResource> SharedValidator { get; private set; }
protected void ValidateId(int id)
{
if (id <= 0)
{
throw new BadRequestException(id + " is not a valid ID");
}
}
protected RestModule(string modulePath) protected RestModule(string modulePath)
: base(modulePath) : base(modulePath)
{ {
@ -42,6 +51,7 @@ protected Action<int> DeleteResource
_deleteResource = value; _deleteResource = value;
Delete[ID_ROUTE] = options => Delete[ID_ROUTE] = options =>
{ {
ValidateId(options.Id);
DeleteResource((int)options.Id); DeleteResource((int)options.Id);
return new Response { StatusCode = HttpStatusCode.OK }; return new Response { StatusCode = HttpStatusCode.OK };
}; };
@ -56,12 +66,7 @@ protected Func<int, TResource> GetResourceById
_getResourceById = value; _getResourceById = value;
Get[ID_ROUTE] = options => Get[ID_ROUTE] = options =>
{ {
int id; ValidateId(options.Id);
if (!Int32.TryParse(options.Id, out id))
{
throw new NotImplementedException();
}
var resource = GetResourceById((int)options.Id); var resource = GetResourceById((int)options.Id);
return resource.AsResponse(); return resource.AsResponse();
}; };

View File

@ -43,7 +43,7 @@ public void Setup()
_fail2.Setup(c => c.IsSatisfiedBy(It.IsAny<RemoteEpisode>())).Returns(false); _fail2.Setup(c => c.IsSatisfiedBy(It.IsAny<RemoteEpisode>())).Returns(false);
_fail3.Setup(c => c.IsSatisfiedBy(It.IsAny<RemoteEpisode>())).Returns(false); _fail3.Setup(c => c.IsSatisfiedBy(It.IsAny<RemoteEpisode>())).Returns(false);
_reports = new List<ReportInfo> {new ReportInfo()}; _reports = new List<ReportInfo> { new ReportInfo() };
_remoteEpisode = new RemoteEpisode(); _remoteEpisode = new RemoteEpisode();
Mocker.GetMock<IParsingService>().Setup(c => c.Map(It.IsAny<ReportInfo>())) Mocker.GetMock<IParsingService>().Setup(c => c.Map(It.IsAny<ReportInfo>()))
@ -101,6 +101,25 @@ public void should_have_same_number_of_rejections_as_specs_that_failed()
} }
[Test]
public void should_not_attempt_to_make_decision_if_remote_episode_is_null()
{
GivenSpecifications(_pass1, _pass2, _pass3);
Mocker.GetMock<IParsingService>().Setup(c => c.Map(It.IsAny<ReportInfo>()))
.Returns<RemoteEpisode>(null);
var results = Subject.GetRssDecision(_reports).ToList();
_pass1.Verify(c => c.IsSatisfiedBy(It.IsAny<RemoteEpisode>()), Times.Never());
_pass2.Verify(c => c.IsSatisfiedBy(It.IsAny<RemoteEpisode>()), Times.Never());
_pass3.Verify(c => c.IsSatisfiedBy(It.IsAny<RemoteEpisode>()), Times.Never());
results.Should().BeEmpty();
}
} }
} }

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -0,0 +1,22 @@
using NzbDrone.Core.Indexers;
using NzbDrone.Core.Indexers.Nzbx;
using NzbDrone.Core.Test.Framework;
using NUnit.Framework;
namespace NzbDrone.Core.Test.IndexerTests.IntegerationTests
{
public class NzbxIntegerationTests : CoreTest<FetchFeedService>
{
[Test]
public void should_be_able_to_fetch_rss()
{
UseRealHttp();
var indexer = new Nzbx();
Subject.FetchRss(indexer);
}
}
}

View File

@ -0,0 +1,21 @@
using NzbDrone.Core.Indexers.Nzbx;
using NzbDrone.Core.Test.Framework;
using NUnit.Framework;
using System.Linq;
using FluentAssertions;
namespace NzbDrone.Core.Test.IndexerTests.ParserTests
{
public class NzbxParserFixture : CoreTest<NzbxParser>
{
[Test]
public void should_be_able_to_parse_json()
{
var stream = OpenRead("Files", "Indexers", "Nzbx", "nzbx_recent.json");
var result = Subject.Process(stream).ToList();
result.Should().NotBeEmpty();
}
}
}

View File

@ -132,6 +132,8 @@
<Compile Include="Framework\NBuilderExtensions.cs" /> <Compile Include="Framework\NBuilderExtensions.cs" />
<Compile Include="IndexerSearchTests\SearchDefinitionFixture.cs" /> <Compile Include="IndexerSearchTests\SearchDefinitionFixture.cs" />
<Compile Include="IndexerTests\BasicRssParserFixture.cs" /> <Compile Include="IndexerTests\BasicRssParserFixture.cs" />
<Compile Include="IndexerTests\IntegerationTests\NzbxIntegerationTests.cs" />
<Compile Include="IndexerTests\ParserTests\NzbxParserFixture.cs" />
<Compile Include="JobTests\JobRepositoryFixture.cs" /> <Compile Include="JobTests\JobRepositoryFixture.cs" />
<Compile Include="JobTests\RenameSeasonJobFixture.cs" /> <Compile Include="JobTests\RenameSeasonJobFixture.cs" />
<Compile Include="DecisionEngineTests\LanguageSpecificationFixture.cs" /> <Compile Include="DecisionEngineTests\LanguageSpecificationFixture.cs" />
@ -261,10 +263,10 @@
<None Include="..\NzbDrone.Test.Common\App.config"> <None Include="..\NzbDrone.Test.Common\App.config">
<Link>App.config</Link> <Link>App.config</Link>
</None> </None>
<None Include="Files\RSS\nzbx_search.json"> <None Include="Files\Indexers\Nzbx\nzbx_search.json">
<CopyToOutputDirectory>Always</CopyToOutputDirectory> <CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None> </None>
<None Include="Files\RSS\nzbx_recent.json"> <None Include="Files\Indexers\Nzbx\nzbx_recent.json">
<CopyToOutputDirectory>Always</CopyToOutputDirectory> <CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None> </None>
<Content Include="Files\RSS\omgwtfnzbs.xml"> <Content Include="Files\RSS\omgwtfnzbs.xml">

View File

@ -29,9 +29,12 @@ public IEnumerable<DownloadDecision> GetRssDecision(IEnumerable<ReportInfo> repo
foreach (var report in reports) foreach (var report in reports)
{ {
var parseResult = _parsingService.Map(report); var parseResult = _parsingService.Map(report);
yield return new DownloadDecision(parseResult, GetGeneralRejectionReasons(parseResult).ToArray()); if (parseResult != null)
} {
yield return new DownloadDecision(parseResult, GetGeneralRejectionReasons(parseResult).ToArray());
}
}
} }
public IEnumerable<DownloadDecision> GetSearchDecision(IEnumerable<ReportInfo> reports, SearchDefinitionBase searchDefinitionBase) public IEnumerable<DownloadDecision> GetSearchDecision(IEnumerable<ReportInfo> reports, SearchDefinitionBase searchDefinitionBase)

View File

@ -14,7 +14,7 @@ public virtual bool EnabledByDefault
{ {
get get
{ {
return false; return true;
} }
} }

View File

@ -17,7 +17,15 @@ public override bool IsConfigured
get { return Settings.IsValid; } get { return Settings.IsValid; }
} }
protected TSetting Settings { get; private set; } public override bool EnabledByDefault
{
get
{
return false;
}
}
public TSetting Settings { get; private set; }
public void Handle(IndexerSettingUpdatedEvent message) public void Handle(IndexerSettingUpdatedEvent message)
{ {

View File

@ -5,6 +5,14 @@ namespace NzbDrone.Core.Indexers.Nzbx
{ {
public class Nzbx : Indexer public class Nzbx : Indexer
{ {
public override IParseFeed Parser
{
get
{
return new NzbxParser();
}
}
public override string Name public override string Name
{ {
get { return "nzbx"; } get { return "nzbx"; }

View File

@ -3,8 +3,6 @@
using System.IO; using System.IO;
using NLog; using NLog;
using Newtonsoft.Json; using Newtonsoft.Json;
using NzbDrone.Core.Model;
using NzbDrone.Core.Parser;
using NzbDrone.Core.Parser.Model; using NzbDrone.Core.Parser.Model;
namespace NzbDrone.Core.Indexers.Nzbx namespace NzbDrone.Core.Indexers.Nzbx
@ -14,9 +12,9 @@ public class NzbxParser : IParseFeed
private readonly Logger _logger; private readonly Logger _logger;
private readonly JsonSerializer _serializer; private readonly JsonSerializer _serializer;
public NzbxParser(Logger logger) public NzbxParser()
{ {
_logger = logger; _logger = LogManager.GetCurrentClassLogger();
_serializer = new JsonSerializer(); _serializer = new JsonSerializer();
} }

View File

@ -11,7 +11,7 @@ public interface IParsingService
{ {
LocalEpisode GetEpisodes(string fileName, Series series); LocalEpisode GetEpisodes(string fileName, Series series);
Series GetSeries(string title); Series GetSeries(string title);
RemoteEpisode Map(ReportInfo indexerParseResult); RemoteEpisode Map(ReportInfo reportInfo);
} }
public class ParsingService : IParsingService public class ParsingService : IParsingService
@ -65,9 +65,34 @@ public Series GetSeries(string title)
return _seriesService.FindByTitle(searchTitle); return _seriesService.FindByTitle(searchTitle);
} }
public RemoteEpisode Map(ReportInfo indexerParseResult) public RemoteEpisode Map(ReportInfo reportInfo)
{ {
throw new NotImplementedException(); var parsedInfo = Parser.ParseTitle(reportInfo.Title);
if (parsedInfo == null)
{
return null;
}
var series = _seriesService.FindByTitle(parsedInfo.SeriesTitle);
if (series == null)
{
_logger.Trace("No matching series {0}", parsedInfo.SeriesTitle);
return null;
}
var remoteEpisode = new RemoteEpisode
{
Series = series,
Episodes = GetEpisodes(parsedInfo, series),
FullSeason = parsedInfo.FullSeason,
Language = parsedInfo.Language,
Quality = parsedInfo.Quality,
Report = reportInfo
};
return remoteEpisode;
} }
private List<Episode> GetEpisodes(ParsedEpisodeInfo parsedEpisodeInfo, Series series) private List<Episode> GetEpisodes(ParsedEpisodeInfo parsedEpisodeInfo, Series series)

View File

@ -41,8 +41,9 @@ public void should_be_able_to_add_and_delete_series()
var rootFolder = RootFolders.Post(new RootFolderResource { Path = Directory.GetCurrentDirectory() }); var rootFolder = RootFolders.Post(new RootFolderResource { Path = Directory.GetCurrentDirectory() });
series.RootFolderId = rootFolder.Id; series.RootFolderId = rootFolder.Id;
series.QualityProfileId = 1;
Series.Post(series); series = Series.Post(series);
Series.All().Should().HaveCount(1); Series.All().Should().HaveCount(1);