From 896cc599367894ff15405412ca824c447b6ed814 Mon Sep 17 00:00:00 2001 From: softworkz Date: Sat, 14 May 2016 03:55:46 +0200 Subject: [PATCH 1/9] Prioritize metadata merging by preferred language --- .../Providers/MetadataResult.cs | 3 +- .../Manager/MetadataService.cs | 36 ++++++++++++++++++- .../TV/TheMovieDb/MovieDbEpisodeProvider.cs | 6 ++++ .../TV/TheMovieDb/MovieDbSeriesProvider.cs | 19 +++++++--- .../TV/TheTVDB/TvdbEpisodeProvider.cs | 11 ++++++ .../TV/TheTVDB/TvdbSeriesProvider.cs | 20 +++++++---- 6 files changed, 82 insertions(+), 13 deletions(-) diff --git a/MediaBrowser.Controller/Providers/MetadataResult.cs b/MediaBrowser.Controller/Providers/MetadataResult.cs index 17175f91cf..f6ca9405a0 100644 --- a/MediaBrowser.Controller/Providers/MetadataResult.cs +++ b/MediaBrowser.Controller/Providers/MetadataResult.cs @@ -13,13 +13,14 @@ namespace MediaBrowser.Controller.Providers public MetadataResult() { Images = new List(); + ResultLanguage = "en"; } public List People { get; set; } public bool HasMetadata { get; set; } public T Item { get; set; } - + public string ResultLanguage { get; set; } public void AddPerson(PersonInfo p) { if (People == null) diff --git a/MediaBrowser.Providers/Manager/MetadataService.cs b/MediaBrowser.Providers/Manager/MetadataService.cs index 85e25d2b6b..fa9a725a72 100644 --- a/MediaBrowser.Providers/Manager/MetadataService.cs +++ b/MediaBrowser.Providers/Manager/MetadataService.cs @@ -646,6 +646,8 @@ namespace MediaBrowser.Providers.Manager { var refreshResult = new RefreshResult(); + var results = new List>(); + foreach (var provider in providers) { var providerName = provider.GetType().Name; @@ -662,7 +664,7 @@ namespace MediaBrowser.Providers.Manager if (result.HasMetadata) { - MergeData(result, temp, new List(), false, false); + results.Add(result); refreshResult.UpdateType = refreshResult.UpdateType | ItemUpdateType.MetadataDownload; } @@ -683,6 +685,38 @@ namespace MediaBrowser.Providers.Manager } } + var orderedResults = new List>(); + + if (string.IsNullOrEmpty(id.MetadataLanguage)) + { + orderedResults.AddRange(results); + } + else + { + // prioritize results with matching ResultLanguage + foreach (var result in results) + { + if (!string.IsNullOrEmpty(result.ResultLanguage) && result.ResultLanguage == id.MetadataLanguage) + { + orderedResults.Add(result); + } + } + + // add all other results + foreach (var result in results) + { + if (!orderedResults.Contains(result)) + { + orderedResults.Add(result); + } + } + } + + foreach (var result in results) + { + MergeData(result, temp, new List(), false, false); + } + return refreshResult; } diff --git a/MediaBrowser.Providers/TV/TheMovieDb/MovieDbEpisodeProvider.cs b/MediaBrowser.Providers/TV/TheMovieDb/MovieDbEpisodeProvider.cs index bc9842b736..db49ef075e 100644 --- a/MediaBrowser.Providers/TV/TheMovieDb/MovieDbEpisodeProvider.cs +++ b/MediaBrowser.Providers/TV/TheMovieDb/MovieDbEpisodeProvider.cs @@ -92,6 +92,12 @@ namespace MediaBrowser.Providers.TV result.HasMetadata = true; + if (!string.IsNullOrEmpty(response.overview)) + { + // if overview is non-empty, we can assume that localized data was returned + result.ResultLanguage = info.MetadataLanguage; + } + var item = new Episode(); result.Item = item; diff --git a/MediaBrowser.Providers/TV/TheMovieDb/MovieDbSeriesProvider.cs b/MediaBrowser.Providers/TV/TheMovieDb/MovieDbSeriesProvider.cs index 3245a2c85a..13a637be84 100644 --- a/MediaBrowser.Providers/TV/TheMovieDb/MovieDbSeriesProvider.cs +++ b/MediaBrowser.Providers/TV/TheMovieDb/MovieDbSeriesProvider.cs @@ -168,7 +168,7 @@ namespace MediaBrowser.Providers.TV { cancellationToken.ThrowIfCancellationRequested(); - result.Item = await FetchSeriesData(tmdbId, info.MetadataLanguage, info.MetadataCountryCode, cancellationToken).ConfigureAwait(false); + result = await FetchMovieData(tmdbId, info.MetadataLanguage, info.MetadataCountryCode, cancellationToken).ConfigureAwait(false); result.HasMetadata = result.Item != null; } @@ -176,7 +176,7 @@ namespace MediaBrowser.Providers.TV return result; } - private async Task FetchSeriesData(string tmdbId, string language, string preferredCountryCode, CancellationToken cancellationToken) + private async Task> FetchMovieData(string tmdbId, string language, string preferredCountryCode, CancellationToken cancellationToken) { string dataFilePath = null; RootObject seriesInfo = null; @@ -199,11 +199,13 @@ namespace MediaBrowser.Providers.TV await EnsureSeriesInfo(tmdbId, language, cancellationToken).ConfigureAwait(false); - var item = new Series(); + var result = new MetadataResult(); + result.Item = new Series(); + result.ResultLanguage = seriesInfo.ResultLanguage; - ProcessMainInfo(item, seriesInfo, preferredCountryCode); + ProcessMainInfo(result.Item, seriesInfo, preferredCountryCode); - return item; + return result; } private void ProcessMainInfo(Series series, RootObject seriesInfo, string preferredCountryCode) @@ -354,6 +356,11 @@ namespace MediaBrowser.Providers.TV }).ConfigureAwait(false)) { mainResult = _jsonSerializer.DeserializeFromStream(json); + + if (!string.IsNullOrEmpty(language)) + { + mainResult.ResultLanguage = language; + } } cancellationToken.ThrowIfCancellationRequested(); @@ -385,6 +392,7 @@ namespace MediaBrowser.Providers.TV var englishResult = _jsonSerializer.DeserializeFromStream(json); mainResult.overview = englishResult.overview; + mainResult.ResultLanguage = "en"; } } @@ -627,6 +635,7 @@ namespace MediaBrowser.Providers.TV public ExternalIds external_ids { get; set; } public Videos videos { get; set; } public ContentRatings content_ratings { get; set; } + public string ResultLanguage { get; set; } } public int Order diff --git a/MediaBrowser.Providers/TV/TheTVDB/TvdbEpisodeProvider.cs b/MediaBrowser.Providers/TV/TheTVDB/TvdbEpisodeProvider.cs index a41a95c126..807db61808 100644 --- a/MediaBrowser.Providers/TV/TheTVDB/TvdbEpisodeProvider.cs +++ b/MediaBrowser.Providers/TV/TheTVDB/TvdbEpisodeProvider.cs @@ -713,6 +713,17 @@ namespace MediaBrowser.Providers.TV } } + break; + } + case "Language": + { + var val = reader.ReadElementContentAsString(); + + if (!string.IsNullOrWhiteSpace(val)) + { + result.ResultLanguage = val; + } + break; } diff --git a/MediaBrowser.Providers/TV/TheTVDB/TvdbSeriesProvider.cs b/MediaBrowser.Providers/TV/TheTVDB/TvdbSeriesProvider.cs index 66a02eba21..3d532b2fcf 100644 --- a/MediaBrowser.Providers/TV/TheTVDB/TvdbSeriesProvider.cs +++ b/MediaBrowser.Providers/TV/TheTVDB/TvdbSeriesProvider.cs @@ -159,7 +159,7 @@ namespace MediaBrowser.Providers.TV var seriesXmlPath = GetSeriesXmlPath(seriesProviderIds, metadataLanguage); var actorsXmlPath = Path.Combine(seriesDataPath, "actors.xml"); - FetchSeriesInfo(series, seriesXmlPath, cancellationToken); + FetchSeriesInfo(result, seriesXmlPath, cancellationToken); cancellationToken.ThrowIfCancellationRequested(); @@ -607,7 +607,7 @@ namespace MediaBrowser.Providers.TV return name.Trim(); } - private void FetchSeriesInfo(Series item, string seriesXmlPath, CancellationToken cancellationToken) + private void FetchSeriesInfo(MetadataResult result, string seriesXmlPath, CancellationToken cancellationToken) { var settings = new XmlReaderSettings { @@ -639,7 +639,7 @@ namespace MediaBrowser.Providers.TV { using (var subtree = reader.ReadSubtree()) { - FetchDataFromSeriesNode(item, subtree, cancellationToken); + FetchDataFromSeriesNode(result, subtree, cancellationToken); } break; } @@ -667,9 +667,9 @@ namespace MediaBrowser.Providers.TV } } - if (item.Status.HasValue && item.Status.Value == SeriesStatus.Ended && episiodeAirDates.Count > 0) + if (result.Item.Status.HasValue && result.Item.Status.Value == SeriesStatus.Ended && episiodeAirDates.Count > 0) { - item.EndDate = episiodeAirDates.Max(); + result.Item.EndDate = episiodeAirDates.Max(); } } @@ -861,8 +861,10 @@ namespace MediaBrowser.Providers.TV } } - private void FetchDataFromSeriesNode(Series item, XmlReader reader, CancellationToken cancellationToken) + private void FetchDataFromSeriesNode(MetadataResult result, XmlReader reader, CancellationToken cancellationToken) { + Series item = result.Item; + reader.MoveToContent(); // Loop through each element @@ -886,6 +888,12 @@ namespace MediaBrowser.Providers.TV break; } + case "Language": + { + result.ResultLanguage = (reader.ReadElementContentAsString() ?? string.Empty).Trim(); + break; + } + case "Airs_DayOfWeek": { var val = reader.ReadElementContentAsString(); From 9f5cf9de0c60310f1f15f777ecadc3fa39696f60 Mon Sep 17 00:00:00 2001 From: softworkz Date: Sun, 18 Sep 2016 06:27:17 +0200 Subject: [PATCH 2/9] Added MetadataResult.QueriedById property --- MediaBrowser.Controller/Providers/MetadataResult.cs | 1 + MediaBrowser.Providers/Manager/MetadataService.cs | 2 +- MediaBrowser.Providers/Omdb/OmdbItemProvider.cs | 8 ++++++-- MediaBrowser.Providers/TV/Omdb/OmdbEpisodeProvider.cs | 3 ++- .../TV/TheMovieDb/MovieDbEpisodeProvider.cs | 1 + .../TV/TheMovieDb/MovieDbSeriesProvider.cs | 6 ++++-- MediaBrowser.Providers/TV/TheTVDB/TvdbEpisodeProvider.cs | 1 + MediaBrowser.Providers/TV/TheTVDB/TvdbSeriesProvider.cs | 2 ++ 8 files changed, 18 insertions(+), 6 deletions(-) diff --git a/MediaBrowser.Controller/Providers/MetadataResult.cs b/MediaBrowser.Controller/Providers/MetadataResult.cs index f6ca9405a0..99402a9694 100644 --- a/MediaBrowser.Controller/Providers/MetadataResult.cs +++ b/MediaBrowser.Controller/Providers/MetadataResult.cs @@ -21,6 +21,7 @@ namespace MediaBrowser.Controller.Providers public bool HasMetadata { get; set; } public T Item { get; set; } public string ResultLanguage { get; set; } + public bool QueriedById { get; set; } public void AddPerson(PersonInfo p) { if (People == null) diff --git a/MediaBrowser.Providers/Manager/MetadataService.cs b/MediaBrowser.Providers/Manager/MetadataService.cs index fa9a725a72..9c9cf5520e 100644 --- a/MediaBrowser.Providers/Manager/MetadataService.cs +++ b/MediaBrowser.Providers/Manager/MetadataService.cs @@ -696,7 +696,7 @@ namespace MediaBrowser.Providers.Manager // prioritize results with matching ResultLanguage foreach (var result in results) { - if (!string.IsNullOrEmpty(result.ResultLanguage) && result.ResultLanguage == id.MetadataLanguage) + if (!string.IsNullOrEmpty(result.ResultLanguage) && result.ResultLanguage == id.MetadataLanguage && result.QueriedById) { orderedResults.Add(result); } diff --git a/MediaBrowser.Providers/Omdb/OmdbItemProvider.cs b/MediaBrowser.Providers/Omdb/OmdbItemProvider.cs index 914b775af7..428bde2f28 100644 --- a/MediaBrowser.Providers/Omdb/OmdbItemProvider.cs +++ b/MediaBrowser.Providers/Omdb/OmdbItemProvider.cs @@ -212,13 +212,15 @@ namespace MediaBrowser.Providers.Omdb { var result = new MetadataResult { - Item = new Series() + Item = new Series(), + QueriedById = true }; var imdbId = info.GetProviderId(MetadataProviders.Imdb); if (string.IsNullOrWhiteSpace(imdbId)) { imdbId = await GetSeriesImdbId(info, cancellationToken).ConfigureAwait(false); + result.QueriedById = false; } if (!string.IsNullOrEmpty(imdbId)) @@ -251,13 +253,15 @@ namespace MediaBrowser.Providers.Omdb { var result = new MetadataResult { - Item = new T() + Item = new T(), + QueriedById = true }; var imdbId = info.GetProviderId(MetadataProviders.Imdb); if (string.IsNullOrWhiteSpace(imdbId)) { imdbId = await GetMovieImdbId(info, cancellationToken).ConfigureAwait(false); + result.QueriedById = false; } if (!string.IsNullOrEmpty(imdbId)) diff --git a/MediaBrowser.Providers/TV/Omdb/OmdbEpisodeProvider.cs b/MediaBrowser.Providers/TV/Omdb/OmdbEpisodeProvider.cs index 621f665146..78bce241f4 100644 --- a/MediaBrowser.Providers/TV/Omdb/OmdbEpisodeProvider.cs +++ b/MediaBrowser.Providers/TV/Omdb/OmdbEpisodeProvider.cs @@ -43,7 +43,8 @@ namespace MediaBrowser.Providers.TV { var result = new MetadataResult() { - Item = new Episode() + Item = new Episode(), + QueriedById = true }; // Allowing this will dramatically increase scan times diff --git a/MediaBrowser.Providers/TV/TheMovieDb/MovieDbEpisodeProvider.cs b/MediaBrowser.Providers/TV/TheMovieDb/MovieDbEpisodeProvider.cs index db49ef075e..748124c033 100644 --- a/MediaBrowser.Providers/TV/TheMovieDb/MovieDbEpisodeProvider.cs +++ b/MediaBrowser.Providers/TV/TheMovieDb/MovieDbEpisodeProvider.cs @@ -91,6 +91,7 @@ namespace MediaBrowser.Providers.TV var response = await GetEpisodeInfo(seriesTmdbId, seasonNumber.Value, episodeNumber.Value, info.MetadataLanguage, cancellationToken).ConfigureAwait(false); result.HasMetadata = true; + result.QueriedById = true; if (!string.IsNullOrEmpty(response.overview)) { diff --git a/MediaBrowser.Providers/TV/TheMovieDb/MovieDbSeriesProvider.cs b/MediaBrowser.Providers/TV/TheMovieDb/MovieDbSeriesProvider.cs index 13a637be84..fb06780293 100644 --- a/MediaBrowser.Providers/TV/TheMovieDb/MovieDbSeriesProvider.cs +++ b/MediaBrowser.Providers/TV/TheMovieDb/MovieDbSeriesProvider.cs @@ -119,6 +119,7 @@ namespace MediaBrowser.Providers.TV public async Task> GetMetadata(SeriesInfo info, CancellationToken cancellationToken) { var result = new MetadataResult(); + result.QueriedById = true; var tmdbId = info.GetProviderId(MetadataProviders.Tmdb); @@ -154,6 +155,7 @@ namespace MediaBrowser.Providers.TV if (string.IsNullOrEmpty(tmdbId)) { + result.QueriedById = false; var searchResults = await new MovieDbSearch(_logger, _jsonSerializer, _libraryManager).GetSearchResults(info, cancellationToken).ConfigureAwait(false); var searchResult = searchResults.FirstOrDefault(); @@ -194,7 +196,7 @@ namespace MediaBrowser.Providers.TV tmdbId = seriesInfo.id.ToString(_usCulture); dataFilePath = GetDataFilePath(tmdbId, language); - _fileSystem.CreateDirectory(Path.GetDirectoryName(dataFilePath)); + _fileSystem.CreateDirectory(Path.GetDirectoryName(dataFilePath)); _jsonSerializer.SerializeToFile(seriesInfo, dataFilePath); await EnsureSeriesInfo(tmdbId, language, cancellationToken).ConfigureAwait(false); @@ -326,7 +328,7 @@ namespace MediaBrowser.Providers.TV var dataFilePath = GetDataFilePath(id, preferredMetadataLanguage); - _fileSystem.CreateDirectory(Path.GetDirectoryName(dataFilePath)); + _fileSystem.CreateDirectory(Path.GetDirectoryName(dataFilePath)); _jsonSerializer.SerializeToFile(mainResult, dataFilePath); } diff --git a/MediaBrowser.Providers/TV/TheTVDB/TvdbEpisodeProvider.cs b/MediaBrowser.Providers/TV/TheTVDB/TvdbEpisodeProvider.cs index 807db61808..41a2282d80 100644 --- a/MediaBrowser.Providers/TV/TheTVDB/TvdbEpisodeProvider.cs +++ b/MediaBrowser.Providers/TV/TheTVDB/TvdbEpisodeProvider.cs @@ -108,6 +108,7 @@ namespace MediaBrowser.Providers.TV public async Task> GetMetadata(EpisodeInfo searchInfo, CancellationToken cancellationToken) { var result = new MetadataResult(); + result.QueriedById = true; if (TvdbSeriesProvider.IsValidSeries(searchInfo.SeriesProviderIds) && (searchInfo.IndexNumber.HasValue || searchInfo.PremiereDate.HasValue)) diff --git a/MediaBrowser.Providers/TV/TheTVDB/TvdbSeriesProvider.cs b/MediaBrowser.Providers/TV/TheTVDB/TvdbSeriesProvider.cs index 3d532b2fcf..4ac9e68361 100644 --- a/MediaBrowser.Providers/TV/TheTVDB/TvdbSeriesProvider.cs +++ b/MediaBrowser.Providers/TV/TheTVDB/TvdbSeriesProvider.cs @@ -93,9 +93,11 @@ namespace MediaBrowser.Providers.TV public async Task> GetMetadata(SeriesInfo itemId, CancellationToken cancellationToken) { var result = new MetadataResult(); + result.QueriedById = true; if (!IsValidSeries(itemId.ProviderIds)) { + result.QueriedById = false; await Identify(itemId).ConfigureAwait(false); } From 35acc01e03d6cef73483c2065345e4ac2a4ebdba Mon Sep 17 00:00:00 2001 From: Luke Pulverenti Date: Thu, 22 Sep 2016 18:04:48 -0400 Subject: [PATCH 3/9] update language normalization --- .../Manager/MetadataService.cs | 42 +++++++++++-------- 1 file changed, 25 insertions(+), 17 deletions(-) diff --git a/MediaBrowser.Providers/Manager/MetadataService.cs b/MediaBrowser.Providers/Manager/MetadataService.cs index 48f8ebb049..4bd2971f3e 100644 --- a/MediaBrowser.Providers/Manager/MetadataService.cs +++ b/MediaBrowser.Providers/Manager/MetadataService.cs @@ -691,29 +691,28 @@ namespace MediaBrowser.Providers.Manager } var orderedResults = new List>(); + var preferredLanguage = NormalizeLanguage(id.MetadataLanguage); - if (string.IsNullOrEmpty(id.MetadataLanguage)) - { - orderedResults.AddRange(results); - } - else + // prioritize results with matching ResultLanguage + foreach (var result in results) { - // prioritize results with matching ResultLanguage - foreach (var result in results) + if (!result.QueriedById) { - if (!string.IsNullOrEmpty(result.ResultLanguage) && result.ResultLanguage == id.MetadataLanguage && result.QueriedById) - { - orderedResults.Add(result); - } + break; } - // add all other results - foreach (var result in results) + if (string.Equals(NormalizeLanguage(result.ResultLanguage), preferredLanguage, StringComparison.OrdinalIgnoreCase) && result.QueriedById) { - if (!orderedResults.Contains(result)) - { - orderedResults.Add(result); - } + orderedResults.Add(result); + } + } + + // add all other results + foreach (var result in results) + { + if (!orderedResults.Contains(result)) + { + orderedResults.Add(result); } } @@ -725,6 +724,15 @@ namespace MediaBrowser.Providers.Manager return refreshResult; } + private string NormalizeLanguage(string language) + { + if (string.IsNullOrWhiteSpace(language)) + { + return "en-us"; + } + return language; + } + private void MergeNewData(TItemType source, TIdType lookupInfo) { // Copy new provider id's that may have been obtained From b4bc4037471dea55a679e1be24a202906b1e8f4d Mon Sep 17 00:00:00 2001 From: Luke Pulverenti Date: Fri, 23 Sep 2016 01:45:14 -0400 Subject: [PATCH 4/9] fix EnableThrottling override --- MediaBrowser.Api/Playback/BaseStreamingService.cs | 2 +- MediaBrowser.Api/Playback/Hls/DynamicHlsService.cs | 5 ----- 2 files changed, 1 insertion(+), 6 deletions(-) diff --git a/MediaBrowser.Api/Playback/BaseStreamingService.cs b/MediaBrowser.Api/Playback/BaseStreamingService.cs index 7ef9a1d5ba..371247ecd8 100644 --- a/MediaBrowser.Api/Playback/BaseStreamingService.cs +++ b/MediaBrowser.Api/Playback/BaseStreamingService.cs @@ -1241,7 +1241,7 @@ namespace MediaBrowser.Api.Playback } } - protected virtual bool EnableThrottling(StreamState state) + private bool EnableThrottling(StreamState state) { // do not use throttling with hardware encoders return state.InputProtocol == MediaProtocol.File && diff --git a/MediaBrowser.Api/Playback/Hls/DynamicHlsService.cs b/MediaBrowser.Api/Playback/Hls/DynamicHlsService.cs index 7de3096997..9cd55528d3 100644 --- a/MediaBrowser.Api/Playback/Hls/DynamicHlsService.cs +++ b/MediaBrowser.Api/Playback/Hls/DynamicHlsService.cs @@ -922,11 +922,6 @@ namespace MediaBrowser.Api.Playback.Hls ).Trim(); } - protected override bool EnableThrottling(StreamState state) - { - return true; - } - /// /// Gets the segment file extension. /// From bb117d6b9894c9d6572af1dc348bed6574ddc8ea Mon Sep 17 00:00:00 2001 From: Luke Pulverenti Date: Fri, 23 Sep 2016 01:45:39 -0400 Subject: [PATCH 5/9] update SocketHttpListener --- .../MediaBrowser.Server.Implementations.csproj | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/MediaBrowser.Server.Implementations/MediaBrowser.Server.Implementations.csproj b/MediaBrowser.Server.Implementations/MediaBrowser.Server.Implementations.csproj index b25c07fe31..eb3da1a12e 100644 --- a/MediaBrowser.Server.Implementations/MediaBrowser.Server.Implementations.csproj +++ b/MediaBrowser.Server.Implementations/MediaBrowser.Server.Implementations.csproj @@ -73,8 +73,8 @@ ..\packages\SimpleInjector.3.2.2\lib\net45\SimpleInjector.dll True - - ..\packages\SocketHttpListener.1.0.0.39\lib\net45\SocketHttpListener.dll + + ..\packages\SocketHttpListener.1.0.0.40\lib\net45\SocketHttpListener.dll True From bfb2f64ea480a35c973362f014e1caee7918b713 Mon Sep 17 00:00:00 2001 From: Luke Pulverenti Date: Fri, 23 Sep 2016 02:20:56 -0400 Subject: [PATCH 6/9] check against repeat programs --- .../Connect/ConnectManager.cs | 22 ++++++++++++------- .../LiveTv/EmbyTV/EncodedRecorder.cs | 2 +- .../LiveTv/Listings/SchedulesDirect.cs | 4 ++-- .../LiveTv/LiveTvManager.cs | 14 ++++++++++++ .../packages.config | 2 +- .../Api/PackageCreator.cs | 2 +- 6 files changed, 33 insertions(+), 13 deletions(-) diff --git a/MediaBrowser.Server.Implementations/Connect/ConnectManager.cs b/MediaBrowser.Server.Implementations/Connect/ConnectManager.cs index e7e52a8878..b2dd8ec865 100644 --- a/MediaBrowser.Server.Implementations/Connect/ConnectManager.cs +++ b/MediaBrowser.Server.Implementations/Connect/ConnectManager.cs @@ -403,6 +403,14 @@ namespace MediaBrowser.Server.Implementations.Connect public async Task LinkUser(string userId, string connectUsername) { + if (string.IsNullOrWhiteSpace(userId)) + { + throw new ArgumentNullException("userId"); + } + if (string.IsNullOrWhiteSpace(connectUsername)) + { + throw new ArgumentNullException("connectUsername"); + } if (string.IsNullOrWhiteSpace(ConnectServerId)) { await UpdateConnectInfo().ConfigureAwait(false); @@ -422,14 +430,6 @@ namespace MediaBrowser.Server.Implementations.Connect private async Task LinkUserInternal(string userId, string connectUsername) { - if (string.IsNullOrWhiteSpace(userId)) - { - throw new ArgumentNullException("userId"); - } - if (string.IsNullOrWhiteSpace(connectUsername)) - { - throw new ArgumentNullException("connectUsername"); - } if (string.IsNullOrWhiteSpace(ConnectServerId)) { throw new ArgumentNullException("ConnectServerId"); @@ -446,6 +446,12 @@ namespace MediaBrowser.Server.Implementations.Connect throw new ArgumentException("The Emby account has been disabled."); } + var existingUser = _userManager.Users.FirstOrDefault(i => string.Equals(i.ConnectUserId, connectUser.Id) && !string.IsNullOrWhiteSpace(i.ConnectAccessKey)); + if (existingUser != null) + { + throw new InvalidOperationException("This connect user is already linked to local user " + existingUser.Name); + } + var user = GetUser(userId); if (!string.IsNullOrWhiteSpace(user.ConnectUserId)) diff --git a/MediaBrowser.Server.Implementations/LiveTv/EmbyTV/EncodedRecorder.cs b/MediaBrowser.Server.Implementations/LiveTv/EmbyTV/EncodedRecorder.cs index 560b0d5b4d..4e7f637b11 100644 --- a/MediaBrowser.Server.Implementations/LiveTv/EmbyTV/EncodedRecorder.cs +++ b/MediaBrowser.Server.Implementations/LiveTv/EmbyTV/EncodedRecorder.cs @@ -253,7 +253,7 @@ namespace MediaBrowser.Server.Implementations.LiveTv.EmbyTV } var durationParam = " -t " + _mediaEncoder.GetTimeParameter(duration.Ticks); - var commandLineArgs = "-fflags +genpts -async 1 -vsync -1 -re -i \"{0}\"{4} -sn {2} -map_metadata -1 -threads 0 {3} -y \"{1}\""; + var commandLineArgs = "-fflags +genpts -async 1 -vsync -1 -i \"{0}\"{4} -sn {2} -map_metadata -1 -threads 0 {3} -y \"{1}\""; if (mediaSource.ReadAtNativeFramerate) { diff --git a/MediaBrowser.Server.Implementations/LiveTv/Listings/SchedulesDirect.cs b/MediaBrowser.Server.Implementations/LiveTv/Listings/SchedulesDirect.cs index c3907c0454..b98919282a 100644 --- a/MediaBrowser.Server.Implementations/LiveTv/Listings/SchedulesDirect.cs +++ b/MediaBrowser.Server.Implementations/LiveTv/Listings/SchedulesDirect.cs @@ -171,7 +171,7 @@ namespace MediaBrowser.Server.Implementations.LiveTv.Listings var data = images[imageIndex].data ?? new List(); data = data.OrderByDescending(GetSizeOrder).ToList(); - programEntry.primaryImage = GetProgramImage(ApiUrl, data, "Logo", true, 800); + programEntry.primaryImage = GetProgramImage(ApiUrl, data, "Logo", true, 600); //programEntry.thumbImage = GetProgramImage(ApiUrl, data, "Iconic", false); //programEntry.bannerImage = GetProgramImage(ApiUrl, data, "Banner", false) ?? // GetProgramImage(ApiUrl, data, "Banner-L1", false) ?? @@ -485,7 +485,7 @@ namespace MediaBrowser.Server.Implementations.LiveTv.Listings } } - if (!string.IsNullOrWhiteSpace(details.originalAirDate)) + if (!string.IsNullOrWhiteSpace(details.originalAirDate) && (!info.IsSeries || info.IsRepeat)) { info.OriginalAirDate = DateTime.Parse(details.originalAirDate); } diff --git a/MediaBrowser.Server.Implementations/LiveTv/LiveTvManager.cs b/MediaBrowser.Server.Implementations/LiveTv/LiveTvManager.cs index df1ef39624..dcef6e84a2 100644 --- a/MediaBrowser.Server.Implementations/LiveTv/LiveTvManager.cs +++ b/MediaBrowser.Server.Implementations/LiveTv/LiveTvManager.cs @@ -2837,6 +2837,20 @@ namespace MediaBrowser.Server.Implementations.LiveTv feature = "embytvseriesrecordings"; } + if (string.Equals(feature, "dvr-l", StringComparison.OrdinalIgnoreCase)) + { + var config = GetConfiguration(); + if (config.TunerHosts.Count(i => i.IsEnabled) > 0 && + config.ListingProviders.Count(i => (i.EnableAllTuners || i.EnabledTuners.Length > 0) && string.Equals(i.Type, SchedulesDirect.TypeName, StringComparison.OrdinalIgnoreCase)) > 0) + { + return Task.FromResult(new MBRegistrationRecord + { + IsRegistered = true, + IsValid = true + }); + } + } + if (string.Equals(feature, "dvr", StringComparison.OrdinalIgnoreCase)) { var config = GetConfiguration(); diff --git a/MediaBrowser.Server.Implementations/packages.config b/MediaBrowser.Server.Implementations/packages.config index 5d58aea191..043257fc8a 100644 --- a/MediaBrowser.Server.Implementations/packages.config +++ b/MediaBrowser.Server.Implementations/packages.config @@ -8,5 +8,5 @@ - + \ No newline at end of file diff --git a/MediaBrowser.WebDashboard/Api/PackageCreator.cs b/MediaBrowser.WebDashboard/Api/PackageCreator.cs index 02e8ad6f22..eaac3e2a0e 100644 --- a/MediaBrowser.WebDashboard/Api/PackageCreator.cs +++ b/MediaBrowser.WebDashboard/Api/PackageCreator.cs @@ -346,7 +346,7 @@ namespace MediaBrowser.WebDashboard.Api if (string.Equals(mode, "cordova", StringComparison.OrdinalIgnoreCase)) { - sb.Append(""); + sb.Append(""); } else { From 8b096ccc0e87883655bcf9ea1f9e22e9961450d3 Mon Sep 17 00:00:00 2001 From: Luke Pulverenti Date: Fri, 23 Sep 2016 02:21:54 -0400 Subject: [PATCH 7/9] stub out storage for new path substitution --- .../Library/LibraryStructureService.cs | 20 ++- .../Entities/Audio/Audio.cs | 2 +- MediaBrowser.Controller/Entities/BaseItem.cs | 4 +- .../Entities/CollectionFolder.cs | 31 ++-- MediaBrowser.Controller/Entities/Video.cs | 2 +- .../Library/ILibraryManager.cs | 6 +- .../Configuration/LibraryOptions.cs | 8 + .../Dto/DtoService.cs | 4 +- .../Library/CoreResolutionIgnoreRule.cs | 3 +- .../Library/LibraryManager.cs | 140 ++++++++++++------ .../LiveTv/EmbyTV/EmbyTV.cs | 8 +- 11 files changed, 160 insertions(+), 68 deletions(-) diff --git a/MediaBrowser.Api/Library/LibraryStructureService.cs b/MediaBrowser.Api/Library/LibraryStructureService.cs index 72966a7cdc..0ed4ee2a2d 100644 --- a/MediaBrowser.Api/Library/LibraryStructureService.cs +++ b/MediaBrowser.Api/Library/LibraryStructureService.cs @@ -112,6 +112,8 @@ namespace MediaBrowser.Api.Library /// The name. public string Path { get; set; } + public MediaPathInfo PathInfo { get; set; } + /// /// Gets or sets a value indicating whether [refresh library]. /// @@ -212,7 +214,12 @@ namespace MediaBrowser.Api.Library { var libraryOptions = request.LibraryOptions ?? new LibraryOptions(); - _libraryManager.AddVirtualFolder(request.Name, request.CollectionType, request.Paths, libraryOptions, request.RefreshLibrary); + if (request.Paths != null && request.Paths.Length > 0) + { + libraryOptions.PathInfos = request.Paths.Select(i => new MediaPathInfo { Path = i }).ToArray(); + } + + _libraryManager.AddVirtualFolder(request.Name, request.CollectionType, libraryOptions, request.RefreshLibrary); } /// @@ -308,7 +315,16 @@ namespace MediaBrowser.Api.Library try { - _libraryManager.AddMediaPath(request.Name, request.Path); + var mediaPath = request.PathInfo; + + if (mediaPath == null) + { + mediaPath = new MediaPathInfo + { + Path = request.Path + }; + } + _libraryManager.AddMediaPath(request.Name, mediaPath); } finally { diff --git a/MediaBrowser.Controller/Entities/Audio/Audio.cs b/MediaBrowser.Controller/Entities/Audio/Audio.cs index 1af55a389f..599e72314d 100644 --- a/MediaBrowser.Controller/Entities/Audio/Audio.cs +++ b/MediaBrowser.Controller/Entities/Audio/Audio.cs @@ -262,7 +262,7 @@ namespace MediaBrowser.Controller.Entities.Audio Protocol = locationType == LocationType.Remote ? MediaProtocol.Http : MediaProtocol.File, MediaStreams = MediaSourceManager.GetMediaStreams(i.Id).ToList(), Name = i.Name, - Path = enablePathSubstituion ? GetMappedPath(i.Path, locationType) : i.Path, + Path = enablePathSubstituion ? GetMappedPath(i, i.Path, locationType) : i.Path, RunTimeTicks = i.RunTimeTicks, Container = i.Container, Size = i.Size diff --git a/MediaBrowser.Controller/Entities/BaseItem.cs b/MediaBrowser.Controller/Entities/BaseItem.cs index 6e0a336207..30e0f3ee72 100644 --- a/MediaBrowser.Controller/Entities/BaseItem.cs +++ b/MediaBrowser.Controller/Entities/BaseItem.cs @@ -2121,11 +2121,11 @@ namespace MediaBrowser.Controller.Entities return hasChanges; } - protected static string GetMappedPath(string path, LocationType locationType) + protected static string GetMappedPath(BaseItem item, string path, LocationType locationType) { if (locationType == LocationType.FileSystem || locationType == LocationType.Offline) { - return LibraryManager.GetPathAfterNetworkSubstitution(path); + return LibraryManager.GetPathAfterNetworkSubstitution(path, item); } return path; diff --git a/MediaBrowser.Controller/Entities/CollectionFolder.cs b/MediaBrowser.Controller/Entities/CollectionFolder.cs index 30ea26eb66..77d7ca7f20 100644 --- a/MediaBrowser.Controller/Entities/CollectionFolder.cs +++ b/MediaBrowser.Controller/Entities/CollectionFolder.cs @@ -48,24 +48,14 @@ namespace MediaBrowser.Controller.Entities private static readonly Dictionary LibraryOptions = new Dictionary(); public LibraryOptions GetLibraryOptions() { - lock (LibraryOptions) - { - LibraryOptions options; - if (!LibraryOptions.TryGetValue(Path, out options)) - { - options = LoadLibraryOptions(); - LibraryOptions[Path] = options; - } - - return options; - } + return GetLibraryOptions(Path); } - private LibraryOptions LoadLibraryOptions() + private static LibraryOptions LoadLibraryOptions(string path) { try { - var result = XmlSerializer.DeserializeFromFile(typeof(LibraryOptions), GetLibraryOptionsPath(Path)) as LibraryOptions; + var result = XmlSerializer.DeserializeFromFile(typeof(LibraryOptions), GetLibraryOptionsPath(path)) as LibraryOptions; if (result == null) { @@ -100,6 +90,21 @@ namespace MediaBrowser.Controller.Entities SaveLibraryOptions(Path, options); } + public static LibraryOptions GetLibraryOptions(string path) + { + lock (LibraryOptions) + { + LibraryOptions options; + if (!LibraryOptions.TryGetValue(path, out options)) + { + options = LoadLibraryOptions(path); + LibraryOptions[path] = options; + } + + return options; + } + } + public static void SaveLibraryOptions(string path, LibraryOptions options) { lock (LibraryOptions) diff --git a/MediaBrowser.Controller/Entities/Video.cs b/MediaBrowser.Controller/Entities/Video.cs index 8809f155c3..1406a05cef 100644 --- a/MediaBrowser.Controller/Entities/Video.cs +++ b/MediaBrowser.Controller/Entities/Video.cs @@ -600,7 +600,7 @@ namespace MediaBrowser.Controller.Entities Protocol = locationType == LocationType.Remote ? MediaProtocol.Http : MediaProtocol.File, MediaStreams = mediaStreams, Name = GetMediaSourceName(i, mediaStreams), - Path = enablePathSubstitution ? GetMappedPath(i.Path, locationType) : i.Path, + Path = enablePathSubstitution ? GetMappedPath(i, i.Path, locationType) : i.Path, RunTimeTicks = i.RunTimeTicks, Video3DFormat = i.Video3DFormat, VideoType = i.VideoType, diff --git a/MediaBrowser.Controller/Library/ILibraryManager.cs b/MediaBrowser.Controller/Library/ILibraryManager.cs index d5c2fcd20c..184a245c14 100644 --- a/MediaBrowser.Controller/Library/ILibraryManager.cs +++ b/MediaBrowser.Controller/Library/ILibraryManager.cs @@ -506,7 +506,7 @@ namespace MediaBrowser.Controller.Library /// QueryResult<BaseItem>. QueryResult QueryItems(InternalItemsQuery query); - string GetPathAfterNetworkSubstitution(string path); + string GetPathAfterNetworkSubstitution(string path, BaseItem ownerItem = null); /// /// Substitutes the path. @@ -556,9 +556,9 @@ namespace MediaBrowser.Controller.Library /// true if XXXX, false otherwise. bool IgnoreFile(FileSystemMetadata file, BaseItem parent); - void AddVirtualFolder(string name, string collectionType, string[] mediaPaths, LibraryOptions options, bool refreshLibrary); + void AddVirtualFolder(string name, string collectionType, LibraryOptions options, bool refreshLibrary); void RemoveVirtualFolder(string name, bool refreshLibrary); - void AddMediaPath(string virtualFolderName, string path); + void AddMediaPath(string virtualFolderName, MediaPathInfo path); void RemoveMediaPath(string virtualFolderName, string path); QueryResult> GetGenres(InternalItemsQuery query); diff --git a/MediaBrowser.Model/Configuration/LibraryOptions.cs b/MediaBrowser.Model/Configuration/LibraryOptions.cs index 770ad433d6..460ee0918f 100644 --- a/MediaBrowser.Model/Configuration/LibraryOptions.cs +++ b/MediaBrowser.Model/Configuration/LibraryOptions.cs @@ -9,11 +9,19 @@ public bool EnableChapterImageExtraction { get; set; } public bool ExtractChapterImagesDuringLibraryScan { get; set; } public bool DownloadImagesInAdvance { get; set; } + public MediaPathInfo[] PathInfos { get; set; } public LibraryOptions() { EnablePhotos = true; EnableRealtimeMonitor = true; + PathInfos = new MediaPathInfo[] { }; } } + + public class MediaPathInfo + { + public string Path { get; set; } + public string NetworkPath { get; set; } + } } diff --git a/MediaBrowser.Server.Implementations/Dto/DtoService.cs b/MediaBrowser.Server.Implementations/Dto/DtoService.cs index ae676626db..e4f1460c66 100644 --- a/MediaBrowser.Server.Implementations/Dto/DtoService.cs +++ b/MediaBrowser.Server.Implementations/Dto/DtoService.cs @@ -1509,7 +1509,7 @@ namespace MediaBrowser.Server.Implementations.Dto } } - private string GetMappedPath(IHasMetadata item) + private string GetMappedPath(BaseItem item) { var path = item.Path; @@ -1517,7 +1517,7 @@ namespace MediaBrowser.Server.Implementations.Dto if (locationType == LocationType.FileSystem || locationType == LocationType.Offline) { - path = _libraryManager.GetPathAfterNetworkSubstitution(path); + path = _libraryManager.GetPathAfterNetworkSubstitution(path, item); } return path; diff --git a/MediaBrowser.Server.Implementations/Library/CoreResolutionIgnoreRule.cs b/MediaBrowser.Server.Implementations/Library/CoreResolutionIgnoreRule.cs index ba7e33890a..b550d1dda2 100644 --- a/MediaBrowser.Server.Implementations/Library/CoreResolutionIgnoreRule.cs +++ b/MediaBrowser.Server.Implementations/Library/CoreResolutionIgnoreRule.cs @@ -33,7 +33,8 @@ namespace MediaBrowser.Server.Implementations.Library // Synology "@eaDir", - "eaDir" + "eaDir", + "#recycle" }; diff --git a/MediaBrowser.Server.Implementations/Library/LibraryManager.cs b/MediaBrowser.Server.Implementations/Library/LibraryManager.cs index 1f8c779539..cef0022cfc 100644 --- a/MediaBrowser.Server.Implementations/Library/LibraryManager.cs +++ b/MediaBrowser.Server.Implementations/Library/LibraryManager.cs @@ -2527,8 +2527,29 @@ namespace MediaBrowser.Server.Implementations.Library }).OrderBy(i => i.Path).ToList(); } - public string GetPathAfterNetworkSubstitution(string path) + public string GetPathAfterNetworkSubstitution(string path, BaseItem ownerItem) { + if (ownerItem != null) + { + var libraryOptions = GetLibraryOptions(ownerItem); + if (libraryOptions != null) + { + foreach (var pathInfo in libraryOptions.PathInfos) + { + if (string.IsNullOrWhiteSpace(pathInfo.NetworkPath)) + { + continue; + } + + var substitutionResult = SubstitutePathInternal(path, pathInfo.Path, pathInfo.NetworkPath); + if (substitutionResult.Item2) + { + return substitutionResult.Item1; + } + } + } + } + foreach (var map in ConfigurationManager.Configuration.PathSubstitutions) { path = SubstitutePath(path, map.From, map.To); @@ -2538,6 +2559,11 @@ namespace MediaBrowser.Server.Implementations.Library } public string SubstitutePath(string path, string from, string to) + { + return SubstitutePathInternal(path, from, to).Item1; + } + + private Tuple SubstitutePathInternal(string path, string from, string to) { if (string.IsNullOrWhiteSpace(path)) { @@ -2552,7 +2578,11 @@ namespace MediaBrowser.Server.Implementations.Library throw new ArgumentNullException("to"); } - var newPath = path.Replace(from.Trim(), to.Trim(), StringComparison.OrdinalIgnoreCase); + from = from.Trim(); + to = to.Trim(); + + var newPath = path.Replace(from, to, StringComparison.OrdinalIgnoreCase); + var changed = false; if (!string.Equals(newPath, path)) { @@ -2564,9 +2594,11 @@ namespace MediaBrowser.Server.Implementations.Library { newPath = newPath.Replace('/', '\\'); } + + changed = true; } - return newPath; + return new Tuple(newPath, changed); } private void SetExtraTypeFromFilename(Video item) @@ -2695,7 +2727,7 @@ namespace MediaBrowser.Server.Implementations.Library throw new InvalidOperationException(); } - public void AddVirtualFolder(string name, string collectionType, string[] mediaPaths, LibraryOptions options, bool refreshLibrary) + public void AddVirtualFolder(string name, string collectionType, LibraryOptions options, bool refreshLibrary) { if (string.IsNullOrWhiteSpace(name)) { @@ -2713,12 +2745,13 @@ namespace MediaBrowser.Server.Implementations.Library virtualFolderPath = Path.Combine(rootFolderPath, name); } - if (mediaPaths != null) + var mediaPathInfos = options.PathInfos; + if (mediaPathInfos != null) { - var invalidpath = mediaPaths.FirstOrDefault(i => !_fileSystem.DirectoryExists(i)); + var invalidpath = mediaPathInfos.FirstOrDefault(i => !_fileSystem.DirectoryExists(i.Path)); if (invalidpath != null) { - throw new ArgumentException("The specified path does not exist: " + invalidpath + "."); + throw new ArgumentException("The specified path does not exist: " + invalidpath.Path + "."); } } @@ -2740,11 +2773,11 @@ namespace MediaBrowser.Server.Implementations.Library CollectionFolder.SaveLibraryOptions(virtualFolderPath, options); - if (mediaPaths != null) + if (mediaPathInfos != null) { - foreach (var path in mediaPaths) + foreach (var path in mediaPathInfos) { - AddMediaPath(name, path); + AddMediaPathInternal(name, path, false); } } } @@ -2770,6 +2803,61 @@ namespace MediaBrowser.Server.Implementations.Library } } + private const string ShortcutFileExtension = ".mblink"; + private const string ShortcutFileSearch = "*" + ShortcutFileExtension; + public void AddMediaPath(string virtualFolderName, MediaPathInfo pathInfo) + { + AddMediaPathInternal(virtualFolderName, pathInfo, true); + } + + private void AddMediaPathInternal(string virtualFolderName, MediaPathInfo pathInfo, bool saveLibraryOptions) + { + if (pathInfo == null) + { + throw new ArgumentNullException("path"); + } + + var path = pathInfo.Path; + + if (string.IsNullOrWhiteSpace(path)) + { + throw new ArgumentNullException("path"); + } + + if (!_fileSystem.DirectoryExists(path)) + { + throw new DirectoryNotFoundException("The path does not exist."); + } + + var rootFolderPath = ConfigurationManager.ApplicationPaths.DefaultUserViewsPath; + var virtualFolderPath = Path.Combine(rootFolderPath, virtualFolderName); + + var shortcutFilename = _fileSystem.GetFileNameWithoutExtension(path); + + var lnk = Path.Combine(virtualFolderPath, shortcutFilename + ShortcutFileExtension); + + while (_fileSystem.FileExists(lnk)) + { + shortcutFilename += "1"; + lnk = Path.Combine(virtualFolderPath, shortcutFilename + ShortcutFileExtension); + } + + _fileSystem.CreateShortcut(lnk, path); + + RemoveContentTypeOverrides(path); + + if (saveLibraryOptions) + { + var libraryOptions = CollectionFolder.GetLibraryOptions(virtualFolderPath); + + var list = libraryOptions.PathInfos.ToList(); + list.Add(pathInfo); + libraryOptions.PathInfos = list.ToArray(); + + CollectionFolder.SaveLibraryOptions(virtualFolderPath, libraryOptions); + } + } + public void RemoveVirtualFolder(string name, bool refreshLibrary) { if (string.IsNullOrWhiteSpace(name)) @@ -2814,38 +2902,6 @@ namespace MediaBrowser.Server.Implementations.Library } } - private const string ShortcutFileExtension = ".mblink"; - private const string ShortcutFileSearch = "*" + ShortcutFileExtension; - public void AddMediaPath(string virtualFolderName, string path) - { - if (string.IsNullOrWhiteSpace(path)) - { - throw new ArgumentNullException("path"); - } - - if (!_fileSystem.DirectoryExists(path)) - { - throw new DirectoryNotFoundException("The path does not exist."); - } - - var rootFolderPath = ConfigurationManager.ApplicationPaths.DefaultUserViewsPath; - var virtualFolderPath = Path.Combine(rootFolderPath, virtualFolderName); - - var shortcutFilename = _fileSystem.GetFileNameWithoutExtension(path); - - var lnk = Path.Combine(virtualFolderPath, shortcutFilename + ShortcutFileExtension); - - while (_fileSystem.FileExists(lnk)) - { - shortcutFilename += "1"; - lnk = Path.Combine(virtualFolderPath, shortcutFilename + ShortcutFileExtension); - } - - _fileSystem.CreateShortcut(lnk, path); - - RemoveContentTypeOverrides(path); - } - private void RemoveContentTypeOverrides(string path) { if (string.IsNullOrWhiteSpace(path)) diff --git a/MediaBrowser.Server.Implementations/LiveTv/EmbyTV/EmbyTV.cs b/MediaBrowser.Server.Implementations/LiveTv/EmbyTV/EmbyTV.cs index a3ca54b4ac..e358f9d25c 100644 --- a/MediaBrowser.Server.Implementations/LiveTv/EmbyTV/EmbyTV.cs +++ b/MediaBrowser.Server.Implementations/LiveTv/EmbyTV/EmbyTV.cs @@ -143,9 +143,15 @@ namespace MediaBrowser.Server.Implementations.LiveTv.EmbyTV continue; } + var mediaPathInfos = pathsToCreate.Select(i => new MediaPathInfo { Path = i }).ToArray(); + + var libraryOptions = new LibraryOptions + { + PathInfos = mediaPathInfos + }; try { - _libraryManager.AddVirtualFolder(recordingFolder.Name, recordingFolder.CollectionType, pathsToCreate.ToArray(), new LibraryOptions(), true); + _libraryManager.AddVirtualFolder(recordingFolder.Name, recordingFolder.CollectionType, libraryOptions, true); } catch (Exception ex) { From 38e33c8e2986a5ff66cb8e186e2eefda27672246 Mon Sep 17 00:00:00 2001 From: Luke Pulverenti Date: Fri, 23 Sep 2016 02:57:24 -0400 Subject: [PATCH 8/9] update components --- MediaBrowser.WebDashboard/MediaBrowser.WebDashboard.csproj | 6 ------ 1 file changed, 6 deletions(-) diff --git a/MediaBrowser.WebDashboard/MediaBrowser.WebDashboard.csproj b/MediaBrowser.WebDashboard/MediaBrowser.WebDashboard.csproj index eebc0f20ed..00279fb050 100644 --- a/MediaBrowser.WebDashboard/MediaBrowser.WebDashboard.csproj +++ b/MediaBrowser.WebDashboard/MediaBrowser.WebDashboard.csproj @@ -470,9 +470,6 @@ PreserveNewest - - PreserveNewest - PreserveNewest @@ -977,9 +974,6 @@ PreserveNewest - - PreserveNewest - PreserveNewest From 1a8167889375b92734908bc1500b001518590b40 Mon Sep 17 00:00:00 2001 From: Luke Pulverenti Date: Fri, 23 Sep 2016 02:57:55 -0400 Subject: [PATCH 9/9] update metadata language normalization --- MediaBrowser.Providers/Manager/MetadataService.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MediaBrowser.Providers/Manager/MetadataService.cs b/MediaBrowser.Providers/Manager/MetadataService.cs index 4bd2971f3e..9bbba73e01 100644 --- a/MediaBrowser.Providers/Manager/MetadataService.cs +++ b/MediaBrowser.Providers/Manager/MetadataService.cs @@ -728,7 +728,7 @@ namespace MediaBrowser.Providers.Manager { if (string.IsNullOrWhiteSpace(language)) { - return "en-us"; + return "en"; } return language; }