mirror of
https://github.com/Radarr/Radarr.git
synced 2024-09-11 12:02:35 +02:00
New: Use MediaInfo to Augment Languages
This commit is contained in:
parent
10322a1867
commit
88bda6bcb6
@ -1,9 +1,14 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using FizzWare.NBuilder;
|
||||
using FluentAssertions;
|
||||
using FluentAssertions.Common;
|
||||
using Moq;
|
||||
using NUnit.Framework;
|
||||
using NzbDrone.Core.Languages;
|
||||
using NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators;
|
||||
using NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators.Augmenters.Language;
|
||||
using NzbDrone.Core.Movies;
|
||||
using NzbDrone.Core.Parser.Model;
|
||||
using NzbDrone.Core.Test.Framework;
|
||||
|
||||
@ -13,17 +18,47 @@ namespace NzbDrone.Core.Test.MediaFiles.MovieImport.Aggregation.Aggregators
|
||||
public class AggregateLanguageFixture : CoreTest<AggregateLanguage>
|
||||
{
|
||||
private LocalMovie _localMovie;
|
||||
private Movie _movie;
|
||||
|
||||
[SetUp]
|
||||
public void Setup()
|
||||
{
|
||||
_movie = Builder<Movie>.CreateNew()
|
||||
.With(m => m.OriginalLanguage = Language.English)
|
||||
.Build();
|
||||
|
||||
_localMovie = Builder<LocalMovie>.CreateNew()
|
||||
.With(l => l.DownloadClientMovieInfo = null)
|
||||
.With(l => l.FolderMovieInfo = null)
|
||||
.With(l => l.FileMovieInfo = null)
|
||||
.With(l => l.Movie = _movie)
|
||||
.Build();
|
||||
}
|
||||
|
||||
private void GivenAugmenters(List<Language> fileNameLanguages, List<Language> folderNameLanguages, List<Language> clientLanguages, List<Language> mediaInfoLanguages)
|
||||
{
|
||||
var fileNameAugmenter = new Mock<IAugmentLanguage>();
|
||||
var folderNameAugmenter = new Mock<IAugmentLanguage>();
|
||||
var clientInfoAugmenter = new Mock<IAugmentLanguage>();
|
||||
var mediaInfoAugmenter = new Mock<IAugmentLanguage>();
|
||||
|
||||
fileNameAugmenter.Setup(s => s.AugmentLanguage(It.IsAny<LocalMovie>()))
|
||||
.Returns(new AugmentLanguageResult(fileNameLanguages, Confidence.Filename));
|
||||
|
||||
folderNameAugmenter.Setup(s => s.AugmentLanguage(It.IsAny<LocalMovie>()))
|
||||
.Returns(new AugmentLanguageResult(folderNameLanguages, Confidence.Foldername));
|
||||
|
||||
clientInfoAugmenter.Setup(s => s.AugmentLanguage(It.IsAny<LocalMovie>()))
|
||||
.Returns(new AugmentLanguageResult(clientLanguages, Confidence.DownloadClientItem));
|
||||
|
||||
mediaInfoAugmenter.Setup(s => s.AugmentLanguage(It.IsAny<LocalMovie>()))
|
||||
.Returns(new AugmentLanguageResult(mediaInfoLanguages, Confidence.MediaInfo));
|
||||
|
||||
var mocks = new List<Mock<IAugmentLanguage>> { fileNameAugmenter, folderNameAugmenter, clientInfoAugmenter, mediaInfoAugmenter };
|
||||
|
||||
Mocker.SetConstant<IEnumerable<IAugmentLanguage>>(mocks.Select(c => c.Object));
|
||||
}
|
||||
|
||||
private ParsedMovieInfo GetParsedMovieInfo(List<Language> languages)
|
||||
{
|
||||
return new ParsedMovieInfo
|
||||
@ -35,56 +70,77 @@ private ParsedMovieInfo GetParsedMovieInfo(List<Language> languages)
|
||||
[Test]
|
||||
public void should_return_default_if_no_info_is_known()
|
||||
{
|
||||
Subject.Aggregate(_localMovie, false).Languages.Should().Contain(Language.Unknown);
|
||||
var result = Subject.Aggregate(_localMovie, false);
|
||||
|
||||
result.Languages.Should().Contain(_movie.OriginalLanguage);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void should_return_file_language_when_only_file_info_is_known()
|
||||
{
|
||||
_localMovie.FileMovieInfo = GetParsedMovieInfo(new List<Language> { Language.English });
|
||||
GivenAugmenters(new List<Language> { Language.French },
|
||||
null,
|
||||
null,
|
||||
null);
|
||||
|
||||
Subject.Aggregate(_localMovie, false).Languages.Should().Equal(_localMovie.FileMovieInfo.Languages);
|
||||
Subject.Aggregate(_localMovie, false).Languages.Should().Equal(new List<Language> { Language.French });
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void should_return_folder_language_when_folder_info_is_known()
|
||||
{
|
||||
_localMovie.FolderMovieInfo = GetParsedMovieInfo(new List<Language> { Language.English });
|
||||
_localMovie.FileMovieInfo = GetParsedMovieInfo(new List<Language> { Language.English });
|
||||
GivenAugmenters(new List<Language> { Language.French },
|
||||
new List<Language> { Language.German },
|
||||
null,
|
||||
null);
|
||||
|
||||
var aggregation = Subject.Aggregate(_localMovie, false);
|
||||
|
||||
aggregation.Languages.Should().Equal(_localMovie.FolderMovieInfo.Languages);
|
||||
aggregation.Languages.Should().Equal(new List<Language> { Language.German });
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void should_return_download_client_item_language_when_download_client_item_info_is_known()
|
||||
{
|
||||
_localMovie.DownloadClientMovieInfo = GetParsedMovieInfo(new List<Language> { Language.English });
|
||||
_localMovie.FolderMovieInfo = GetParsedMovieInfo(new List<Language> { Language.English });
|
||||
_localMovie.FileMovieInfo = GetParsedMovieInfo(new List<Language> { Language.English });
|
||||
GivenAugmenters(new List<Language> { Language.French },
|
||||
new List<Language> { Language.German },
|
||||
new List<Language> { Language.Spanish },
|
||||
null);
|
||||
|
||||
Subject.Aggregate(_localMovie, false).Languages.Should().Equal(_localMovie.DownloadClientMovieInfo.Languages);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void should_return_file_language_when_file_language_is_higher_than_others()
|
||||
{
|
||||
_localMovie.DownloadClientMovieInfo = GetParsedMovieInfo(new List<Language> { Language.Unknown });
|
||||
_localMovie.FolderMovieInfo = GetParsedMovieInfo(new List<Language> { Language.Unknown });
|
||||
_localMovie.FileMovieInfo = GetParsedMovieInfo(new List<Language> { Language.French });
|
||||
|
||||
Subject.Aggregate(_localMovie, false).Languages.Should().Equal(_localMovie.FileMovieInfo.Languages);
|
||||
Subject.Aggregate(_localMovie, false).Languages.Should().Equal(new List<Language> { Language.Spanish });
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void should_return_multi_language()
|
||||
{
|
||||
_localMovie.DownloadClientMovieInfo = GetParsedMovieInfo(new List<Language> { Language.Unknown });
|
||||
_localMovie.FolderMovieInfo = GetParsedMovieInfo(new List<Language> { Language.English, Language.German });
|
||||
_localMovie.FileMovieInfo = GetParsedMovieInfo(new List<Language> { Language.Unknown });
|
||||
GivenAugmenters(new List<Language> { Language.Unknown },
|
||||
new List<Language> { Language.French, Language.German },
|
||||
new List<Language> { Language.Unknown },
|
||||
null);
|
||||
|
||||
Subject.Aggregate(_localMovie, false).Languages.Should().Equal(_localMovie.FolderMovieInfo.Languages);
|
||||
Subject.Aggregate(_localMovie, false).Languages.Should().Equal(new List<Language> { Language.French, Language.German });
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void should_use_mediainfo_over_others()
|
||||
{
|
||||
GivenAugmenters(new List<Language> { Language.Unknown },
|
||||
new List<Language> { Language.French, Language.German },
|
||||
new List<Language> { Language.Unknown },
|
||||
new List<Language> { Language.Japanese, Language.English });
|
||||
|
||||
Subject.Aggregate(_localMovie, false).Languages.Should().Equal(new List<Language> { Language.Japanese, Language.English });
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void should_not_use_mediainfo_if_unknown()
|
||||
{
|
||||
GivenAugmenters(new List<Language> { Language.Unknown },
|
||||
new List<Language> { Language.French, Language.German },
|
||||
new List<Language> { Language.Unknown },
|
||||
new List<Language> { Language.Unknown });
|
||||
|
||||
Subject.Aggregate(_localMovie, false).Languages.Should().Equal(new List<Language> { Language.French, Language.German });
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,53 +1,43 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using NLog;
|
||||
using NzbDrone.Common.Extensions;
|
||||
using NzbDrone.Core.Languages;
|
||||
using NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators.Augmenters.Language;
|
||||
using NzbDrone.Core.Parser.Model;
|
||||
|
||||
namespace NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators
|
||||
{
|
||||
public class AggregateLanguage : IAggregateLocalMovie
|
||||
{
|
||||
private readonly IEnumerable<IAugmentLanguage> _augmentQualities;
|
||||
private readonly Logger _logger;
|
||||
|
||||
public AggregateLanguage(Logger logger)
|
||||
public AggregateLanguage(IEnumerable<IAugmentLanguage> augmentQualities,
|
||||
Logger logger)
|
||||
{
|
||||
_augmentQualities = augmentQualities;
|
||||
_logger = logger;
|
||||
}
|
||||
|
||||
public LocalMovie Aggregate(LocalMovie localMovie, bool otherFiles)
|
||||
{
|
||||
// Get languages in preferred order, download client item, folder and finally file.
|
||||
// Non-English languages will be preferred later, in the event there is a conflict
|
||||
// between parsed languages the more preferred item will be used.
|
||||
var languages = new List<Language>();
|
||||
var augmentedLanguages = _augmentQualities.Select(a => a.AugmentLanguage(localMovie))
|
||||
.Where(a => a != null)
|
||||
.OrderBy(a => a.Confidence);
|
||||
|
||||
languages.AddRange(localMovie.DownloadClientMovieInfo?.Languages ?? new List<Language>());
|
||||
var languages = new List<Language> { localMovie.Movie.OriginalLanguage ?? Language.Unknown };
|
||||
var languagesConfidence = Confidence.Default;
|
||||
|
||||
if (!languages.Any(l => l != Language.Unknown))
|
||||
foreach (var augmentedLanguage in augmentedLanguages)
|
||||
{
|
||||
languages = localMovie.FolderMovieInfo?.Languages ?? new List<Language>();
|
||||
if (augmentedLanguage?.Languages != null && augmentedLanguage.Languages.Count > 0 && !(augmentedLanguage.Languages.Count == 1 && augmentedLanguage.Languages.Contains(Language.Unknown)))
|
||||
{
|
||||
languages = augmentedLanguage.Languages;
|
||||
languagesConfidence = augmentedLanguage.Confidence;
|
||||
}
|
||||
}
|
||||
|
||||
if (!languages.Any(l => l != Language.Unknown))
|
||||
{
|
||||
languages = localMovie.FileMovieInfo?.Languages ?? new List<Language>();
|
||||
}
|
||||
|
||||
if (!languages.Any())
|
||||
{
|
||||
languages.Add(Language.Unknown);
|
||||
}
|
||||
|
||||
languages = languages.Distinct().ToList();
|
||||
|
||||
if (languages.Count == 1 && languages.Contains(Language.Unknown))
|
||||
{
|
||||
languages = new List<Language> { localMovie.Movie.OriginalLanguage };
|
||||
}
|
||||
|
||||
_logger.Debug("Using languages: {0}", languages.Select(l => l.Name).ToList().Join(","));
|
||||
_logger.Debug("Using languages: {0}", languages);
|
||||
|
||||
localMovie.Languages = languages;
|
||||
|
||||
|
@ -0,0 +1,19 @@
|
||||
using NzbDrone.Core.Parser.Model;
|
||||
|
||||
namespace NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators.Augmenters.Language
|
||||
{
|
||||
public class AugmentLanguageFromDownloadClientItem : IAugmentLanguage
|
||||
{
|
||||
public AugmentLanguageResult AugmentLanguage(LocalMovie localMovie)
|
||||
{
|
||||
var languages = localMovie.DownloadClientMovieInfo?.Languages;
|
||||
|
||||
if (languages == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return new AugmentLanguageResult(languages, Confidence.DownloadClientItem);
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,19 @@
|
||||
using NzbDrone.Core.Parser.Model;
|
||||
|
||||
namespace NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators.Augmenters.Language
|
||||
{
|
||||
public class AugmentLanguageFromFileName : IAugmentLanguage
|
||||
{
|
||||
public AugmentLanguageResult AugmentLanguage(LocalMovie localMovie)
|
||||
{
|
||||
var languages = localMovie.FileMovieInfo?.Languages;
|
||||
|
||||
if (languages == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return new AugmentLanguageResult(languages, Confidence.Filename);
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,19 @@
|
||||
using NzbDrone.Core.Parser.Model;
|
||||
|
||||
namespace NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators.Augmenters.Language
|
||||
{
|
||||
public class AugmentLanguageFromFolder : IAugmentLanguage
|
||||
{
|
||||
public AugmentLanguageResult AugmentLanguage(LocalMovie localMovie)
|
||||
{
|
||||
var languages = localMovie.FolderMovieInfo?.Languages;
|
||||
|
||||
if (languages == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return new AugmentLanguageResult(languages, Confidence.Foldername);
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,36 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using NzbDrone.Common.Extensions;
|
||||
using NzbDrone.Core.Parser;
|
||||
using NzbDrone.Core.Parser.Model;
|
||||
|
||||
namespace NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators.Augmenters.Language
|
||||
{
|
||||
public class AugmentLanguageFromMediaInfo : IAugmentLanguage
|
||||
{
|
||||
public AugmentLanguageResult AugmentLanguage(LocalMovie localMovie)
|
||||
{
|
||||
if (localMovie.MediaInfo == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
var audioLanguages = localMovie.MediaInfo.AudioLanguages.Split('/').Distinct().ToList();
|
||||
|
||||
var languages = new List<Languages.Language>();
|
||||
|
||||
foreach (var audioLanguage in audioLanguages)
|
||||
{
|
||||
var language = IsoLanguages.FindByName(audioLanguage)?.Language;
|
||||
languages.AddIfNotNull(language);
|
||||
}
|
||||
|
||||
if (languages.Count == 0)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return new AugmentLanguageResult(languages, Confidence.MediaInfo);
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,17 @@
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators.Augmenters.Language
|
||||
{
|
||||
public class AugmentLanguageResult
|
||||
{
|
||||
public List<Languages.Language> Languages { get; set; }
|
||||
public Confidence Confidence { get; set; }
|
||||
|
||||
public AugmentLanguageResult(List<Languages.Language> languages,
|
||||
Confidence confidence)
|
||||
{
|
||||
Languages = languages;
|
||||
Confidence = confidence;
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,11 @@
|
||||
namespace NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators.Augmenters.Language
|
||||
{
|
||||
public enum Confidence
|
||||
{
|
||||
Default,
|
||||
Filename,
|
||||
Foldername,
|
||||
DownloadClientItem,
|
||||
MediaInfo
|
||||
}
|
||||
}
|
@ -0,0 +1,9 @@
|
||||
using NzbDrone.Core.Parser.Model;
|
||||
|
||||
namespace NzbDrone.Core.MediaFiles.MovieImport.Aggregation.Aggregators.Augmenters.Language
|
||||
{
|
||||
public interface IAugmentLanguage
|
||||
{
|
||||
AugmentLanguageResult AugmentLanguage(LocalMovie localMovie);
|
||||
}
|
||||
}
|
@ -7,13 +7,15 @@ public class IsoLanguage
|
||||
public string TwoLetterCode { get; set; }
|
||||
public string ThreeLetterCode { get; set; }
|
||||
public string CountryCode { get; set; }
|
||||
public string EnglishName { get; set; }
|
||||
public Language Language { get; set; }
|
||||
|
||||
public IsoLanguage(string twoLetterCode, string countryCode, string threeLetterCode, Language language)
|
||||
public IsoLanguage(string twoLetterCode, string countryCode, string threeLetterCode, string englishName, Language language)
|
||||
{
|
||||
TwoLetterCode = twoLetterCode;
|
||||
ThreeLetterCode = threeLetterCode;
|
||||
CountryCode = countryCode;
|
||||
EnglishName = englishName;
|
||||
Language = language;
|
||||
}
|
||||
}
|
||||
|
@ -8,30 +8,30 @@ public static class IsoLanguages
|
||||
{
|
||||
private static readonly HashSet<IsoLanguage> All = new HashSet<IsoLanguage>
|
||||
{
|
||||
new IsoLanguage("en", "", "eng", Language.English),
|
||||
new IsoLanguage("fr", "", "fra", Language.French),
|
||||
new IsoLanguage("es", "", "spa", Language.Spanish),
|
||||
new IsoLanguage("de", "", "deu", Language.German),
|
||||
new IsoLanguage("it", "", "ita", Language.Italian),
|
||||
new IsoLanguage("da", "", "dan", Language.Danish),
|
||||
new IsoLanguage("nl", "", "nld", Language.Dutch),
|
||||
new IsoLanguage("ja", "", "jpn", Language.Japanese),
|
||||
new IsoLanguage("is", "", "isl", Language.Icelandic),
|
||||
new IsoLanguage("zh", "", "zho", Language.Chinese),
|
||||
new IsoLanguage("ru", "", "rus", Language.Russian),
|
||||
new IsoLanguage("pl", "", "pol", Language.Polish),
|
||||
new IsoLanguage("vi", "", "vie", Language.Vietnamese),
|
||||
new IsoLanguage("sv", "", "swe", Language.Swedish),
|
||||
new IsoLanguage("no", "", "nor", Language.Norwegian),
|
||||
new IsoLanguage("nb", "", "nob", Language.Norwegian),
|
||||
new IsoLanguage("fi", "", "fin", Language.Finnish),
|
||||
new IsoLanguage("tr", "", "tur", Language.Turkish),
|
||||
new IsoLanguage("pt", "", "por", Language.Portuguese),
|
||||
new IsoLanguage("el", "", "ell", Language.Greek),
|
||||
new IsoLanguage("ko", "", "kor", Language.Korean),
|
||||
new IsoLanguage("hu", "", "hun", Language.Hungarian),
|
||||
new IsoLanguage("he", "", "heb", Language.Hebrew),
|
||||
new IsoLanguage("cs", "", "ces", Language.Czech)
|
||||
new IsoLanguage("en", "", "eng", "English", Language.English),
|
||||
new IsoLanguage("fr", "", "fra", "French", Language.French),
|
||||
new IsoLanguage("es", "", "spa", "Spanish", Language.Spanish),
|
||||
new IsoLanguage("de", "", "deu", "German", Language.German),
|
||||
new IsoLanguage("it", "", "ita", "Italian", Language.Italian),
|
||||
new IsoLanguage("da", "", "dan", "Danish", Language.Danish),
|
||||
new IsoLanguage("nl", "", "nld", "Dutch", Language.Dutch),
|
||||
new IsoLanguage("ja", "", "jpn", "Japanese", Language.Japanese),
|
||||
new IsoLanguage("is", "", "isl", "Icelandic", Language.Icelandic),
|
||||
new IsoLanguage("zh", "", "zho", "Chinese", Language.Chinese),
|
||||
new IsoLanguage("ru", "", "rus", "Russian", Language.Russian),
|
||||
new IsoLanguage("pl", "", "pol", "Polish", Language.Polish),
|
||||
new IsoLanguage("vi", "", "vie", "Vietnamese", Language.Vietnamese),
|
||||
new IsoLanguage("sv", "", "swe", "Swedish", Language.Swedish),
|
||||
new IsoLanguage("no", "", "nor", "Norwegian", Language.Norwegian),
|
||||
new IsoLanguage("nb", "", "nob", "Norwegian Bokmal", Language.Norwegian),
|
||||
new IsoLanguage("fi", "", "fin", "Finnish", Language.Finnish),
|
||||
new IsoLanguage("tr", "", "tur", "Turkish", Language.Turkish),
|
||||
new IsoLanguage("pt", "", "por", "Portuguese", Language.Portuguese),
|
||||
new IsoLanguage("el", "", "ell", "Greek", Language.Greek),
|
||||
new IsoLanguage("ko", "", "kor", "Korean", Language.Korean),
|
||||
new IsoLanguage("hu", "", "hun", "Hungarian", Language.Hungarian),
|
||||
new IsoLanguage("he", "", "heb", "Hebrew", Language.Hebrew),
|
||||
new IsoLanguage("cs", "", "ces", "Czech", Language.Czech)
|
||||
};
|
||||
|
||||
public static IsoLanguage Find(string isoCode)
|
||||
@ -62,6 +62,11 @@ public static IsoLanguage Find(string isoCode)
|
||||
return null;
|
||||
}
|
||||
|
||||
public static IsoLanguage FindByName(string name)
|
||||
{
|
||||
return All.FirstOrDefault(l => l.EnglishName == name.Trim());
|
||||
}
|
||||
|
||||
public static IsoLanguage Get(Language language)
|
||||
{
|
||||
return All.FirstOrDefault(l => l.Language == language);
|
||||
|
Loading…
Reference in New Issue
Block a user