Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

New: Indexer condition Custom Format #9417

Open
wants to merge 3 commits into
base: develop
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
using FizzWare.NBuilder;
using FluentAssertions;
using NUnit.Framework;
using NzbDrone.Core.CustomFormats;
using NzbDrone.Core.Movies;
using NzbDrone.Core.Test.Framework;

namespace NzbDrone.Core.Test.CustomFormats
{
[TestFixture]
public class IndexerSpecificationFixture : CoreTest<IndexerSpecification>
{
private CustomFormatInput _movieInput;

[SetUp]
public void Setup()
{
_movieInput = new CustomFormatInput
{
Movie = Builder<Movie>.CreateNew().Build()
};
}

private void GivenCustomFormatIndexer(int indexerId)
{
Subject.Value = indexerId;
}

private void GivenMovieReleaseIndexer(int indexerId)
{
_movieInput.IndexerId = indexerId;
}

[Test]
public void should_return_false_if_indexer_id_not_captured()
{
GivenCustomFormatIndexer(4);
GivenMovieReleaseIndexer(-1);

Subject.IsSatisfiedBy(_movieInput).Should().BeFalse();
}

[Test]
public void should_return_false_if_indexer_id_does_not_match_custom_format()
{
GivenCustomFormatIndexer(4);
GivenMovieReleaseIndexer(3);

Subject.IsSatisfiedBy(_movieInput).Should().BeFalse();
}

[Test]
public void should_return_true_if_indexer_id_matches_custom_format()
{
GivenCustomFormatIndexer(4);
GivenMovieReleaseIndexer(4);

Subject.IsSatisfiedBy(_movieInput).Should().BeTrue();
}
}
}
1 change: 1 addition & 0 deletions src/NzbDrone.Core/Blocklisting/Blocklist.cs
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ public class Blocklist : ModelBase
public DownloadProtocol Protocol { get; set; }
public string Indexer { get; set; }
public IndexerFlags IndexerFlags { get; set; }
public int IndexerId { get; set; }
public string Message { get; set; }
public string TorrentInfoHash { get; set; }
public List<Language> Languages { get; set; }
Expand Down
7 changes: 7 additions & 0 deletions src/NzbDrone.Core/Blocklisting/BlocklistService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,8 @@ public void Block(RemoteMovie remoteMovie, string message)
PublishedDate = remoteMovie.Release.PublishDate,
Size = remoteMovie.Release.Size,
Indexer = remoteMovie.Release.Indexer,
IndexerFlags = remoteMovie.Release.IndexerFlags,
IndexerId = remoteMovie.Release.IndexerId,
Protocol = remoteMovie.Release.DownloadProtocol,
Message = message,
Languages = remoteMovie.ParsedMovieInfo.Languages
Expand Down Expand Up @@ -194,6 +196,11 @@ public void Handle(DownloadFailedEvent message)
blocklist.IndexerFlags = flags;
}

if (int.TryParse(message.Data.GetValueOrDefault("indexerId"), out var indexerId))
{
blocklist.IndexerId = indexerId;
}

_blocklistRepository.Insert(blocklist);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,8 @@ public List<CustomFormat> ParseCustomFormat(RemoteMovie remoteMovie, long size)
Movie = remoteMovie.Movie,
Size = size,
Languages = remoteMovie.Languages,
IndexerFlags = remoteMovie.Release?.IndexerFlags ?? 0
IndexerFlags = remoteMovie.Release?.IndexerFlags ?? 0,
IndexerId = remoteMovie.Release?.IndexerId ?? -1
};

return ParseCustomFormat(input);
Expand Down Expand Up @@ -76,6 +77,7 @@ public List<CustomFormat> ParseCustomFormat(Blocklist blocklist, Movie movie)
Movie = movie,
Size = blocklist.Size ?? 0,
IndexerFlags = blocklist.IndexerFlags,
IndexerId = blocklist.IndexerId,
Languages = blocklist.Languages
};

Expand Down Expand Up @@ -106,6 +108,7 @@ public List<CustomFormat> ParseCustomFormat(MovieHistory history, Movie movie)
Movie = movie,
Size = size,
IndexerFlags = flags,
IndexerId = int.TryParse(history.Data.GetValueOrDefault("indexerId"), out var indexerId) ? indexerId : -1,
Languages = history.Languages
};

Expand Down Expand Up @@ -198,6 +201,7 @@ private static List<CustomFormat> ParseCustomFormat(MovieFile movieFile, Movie m
Movie = movie,
Size = movieFile.Size,
IndexerFlags = movieFile.IndexerFlags,
IndexerId = movieFile.IndexerId,
Languages = movieFile.Languages,
Filename = Path.GetFileName(movieFile.RelativePath)
};
Expand Down
1 change: 1 addition & 0 deletions src/NzbDrone.Core/CustomFormats/CustomFormatInput.cs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ public class CustomFormatInput
public Movie Movie { get; set; }
public long Size { get; set; }
public IndexerFlags IndexerFlags { get; set; }
public int? IndexerId { get; set; }
public List<Language> Languages { get; set; }
public string Filename { get; set; }

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
using FluentValidation;
using NzbDrone.Core.Annotations;
using NzbDrone.Core.Validation;

namespace NzbDrone.Core.CustomFormats
{
public class IndexerSpecificationValidator : AbstractValidator<IndexerSpecification>
{
public IndexerSpecificationValidator()
{
RuleFor(c => c.Value).GreaterThan(0);
}
}

public class IndexerSpecification : CustomFormatSpecificationBase
{
private static readonly IndexerSpecificationValidator Validator = new IndexerSpecificationValidator();

public override int Order => 4;
public override string ImplementationName => "Indexer";

[FieldDefinition(1, Label = "Indexer", Type = FieldType.Select, SelectOptionsProviderAction = "indexers")]
public int Value { get; set; }

protected override bool IsSatisfiedByWithoutNegate(CustomFormatInput input)
{
return input.IndexerId == Value;
}

public override NzbDroneValidationResult Validate()
{
return new NzbDroneValidationResult(Validator.Validate(this));
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
using FluentMigrator;
using NzbDrone.Core.Datastore.Migration.Framework;

namespace NzbDrone.Core.Datastore.Migration
{
[Migration(234)]
public class add_indexer_id_columns : NzbDroneMigrationBase
{
protected override void MainDbUpgrade()
{
Alter.Table("Blocklist").AddColumn("IndexerId").AsInt32().WithDefaultValue(-1);
Alter.Table("MovieFiles").AddColumn("IndexerId").AsInt32().WithDefaultValue(-1);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -161,6 +161,13 @@ public TrackedDownload TrackDownload(DownloadClientDefinition downloadClient, Do
trackedDownload.RemoteMovie.Release ??= new ReleaseInfo();
trackedDownload.RemoteMovie.Release.IndexerFlags = flags;
}

if (trackedDownload.RemoteMovie != null &&
int.TryParse(grabbedEvent?.Data?.GetValueOrDefault("indexerId"), out var indexerId))
{
trackedDownload.RemoteMovie.Release ??= new ReleaseInfo();
trackedDownload.RemoteMovie.Release.IndexerId = indexerId;
}
}

// Calculate custom formats
Expand Down
3 changes: 3 additions & 0 deletions src/NzbDrone.Core/History/HistoryService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -204,6 +204,7 @@ public void Handle(MovieFileImportedEvent message)
history.Data.Add("ReleaseGroup", message.MovieInfo.ReleaseGroup);
history.Data.Add("CustomFormatScore", message.MovieInfo.CustomFormatScore.ToString());
history.Data.Add("IndexerFlags", message.ImportedMovie.IndexerFlags.ToString());
history.Data.Add("IndexerId", message.ImportedMovie.IndexerId.ToString());

_historyRepository.Insert(history);
}
Expand All @@ -229,6 +230,7 @@ public void Handle(MovieFileDeletedEvent message)
history.Data.Add("Reason", message.Reason.ToString());
history.Data.Add("ReleaseGroup", message.MovieFile.ReleaseGroup);
history.Data.Add("IndexerFlags", message.MovieFile.IndexerFlags.ToString());
history.Data.Add("IndexerId", message.MovieFile.IndexerId.ToString());

_historyRepository.Insert(history);
}
Expand Down Expand Up @@ -256,6 +258,7 @@ public void Handle(MovieFileRenamedEvent message)
history.Data.Add("RelativePath", relativePath);
history.Data.Add("ReleaseGroup", message.MovieFile.ReleaseGroup);
history.Data.Add("IndexerFlags", message.MovieFile.IndexerFlags.ToString());
history.Data.Add("IndexerId", message.MovieFile.IndexerId.ToString());

_historyRepository.Insert(history);
}
Expand Down
1 change: 1 addition & 0 deletions src/NzbDrone.Core/MediaFiles/MovieFile.cs
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ public class MovieFile : ModelBase
public string SceneName { get; set; }
public string ReleaseGroup { get; set; }
public IndexerFlags IndexerFlags { get; set; }
public int IndexerId { get; set; } = -1;
public QualityModel Quality { get; set; }
public List<Language> Languages { get; set; }
public MediaInfoModel MediaInfo { get; set; }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,11 @@ public List<ImportResult> Import(List<ImportDecision> decisions, bool newDownloa
{
movieFile.IndexerFlags = flags;
}

if (int.TryParse(grabHistory?.Data.GetValueOrDefault("indexerId"), out var indexerId))
{
movieFile.IndexerId = indexerId;
}
}

bool copyOnly;
Expand Down
6 changes: 6 additions & 0 deletions src/Radarr.Api.V3/MovieFiles/MovieFileController.cs
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,7 @@ public ActionResult<MovieFileResource> SetMovieFile(MovieFileResource movieFileR
{
var movieFile = _mediaFileService.GetMovie(movieFileResource.Id);
movieFile.IndexerFlags = (IndexerFlags)movieFileResource.IndexerFlags;
movieFile.IndexerId = movieFileResource.IndexerId;
movieFile.Quality = movieFileResource.Quality;
movieFile.Languages = movieFileResource.Languages;
movieFile.Edition = movieFileResource.Edition;
Expand Down Expand Up @@ -135,6 +136,11 @@ public object SetMovieFile([FromBody] MovieFileListResource resource)
movieFile.IndexerFlags = (IndexerFlags)resource.IndexerFlags.Value;
}

if (resource.IndexerId != null)
{
movieFile.IndexerId = resource.IndexerId.Value;
}

if (resource.Edition != null)
{
movieFile.Edition = resource.Edition;
Expand Down
1 change: 1 addition & 0 deletions src/Radarr.Api.V3/MovieFiles/MovieFileListResource.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,5 +13,6 @@ public class MovieFileListResource
public string ReleaseGroup { get; set; }
public string SceneName { get; set; }
public int? IndexerFlags { get; set; }
public int? IndexerId { get; set; }
}
}
3 changes: 3 additions & 0 deletions src/Radarr.Api.V3/MovieFiles/MovieFileResource.cs
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ public class MovieFileResource : RestResource
public DateTime DateAdded { get; set; }
public string SceneName { get; set; }
public int IndexerFlags { get; set; }
public int IndexerId { get; set; }
public QualityModel Quality { get; set; }
public List<CustomFormatResource> CustomFormats { get; set; }
public int CustomFormatScore { get; set; }
Expand Down Expand Up @@ -52,6 +53,7 @@ private static MovieFileResource ToResource(this MovieFile model)
DateAdded = model.DateAdded,
SceneName = model.SceneName,
IndexerFlags = (int)model.IndexerFlags,
IndexerId = model.IndexerId,
Quality = model.Quality,
Languages = model.Languages,
ReleaseGroup = model.ReleaseGroup,
Expand Down Expand Up @@ -79,6 +81,7 @@ public static MovieFileResource ToResource(this MovieFile model, NzbDrone.Core.M
DateAdded = model.DateAdded,
SceneName = model.SceneName,
IndexerFlags = (int)model.IndexerFlags,
IndexerId = model.IndexerId,
Quality = model.Quality,
Languages = model.Languages,
Edition = model.Edition,
Expand Down
28 changes: 28 additions & 0 deletions src/Radarr.Api.V3/Specifications/SpecificationsController.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
using System.Linq;
using Microsoft.AspNetCore.Mvc;
using NzbDrone.Core.Annotations;
using NzbDrone.Core.Indexers;
using Radarr.Http;

namespace Radarr.Api.V3.Specifications
{
[V3ApiController]
public class SpecificationsController : Controller
{
private readonly IIndexerFactory _indexerFactory;

public SpecificationsController(IIndexerFactory indexerFactory)
{
_indexerFactory = indexerFactory;
}

[HttpPost("action/indexers")]
public object GetIndexers()
{
return new
{
options = _indexerFactory.All().Select(o => new FieldSelectOption { Value = o.Id, Name = o.Name }).ToList()
};
}
}
}