public async Task Execute(CancellationToken cancellationToken, IProgress <double> progress) { cancellationToken.ThrowIfCancellationRequested(); await Tracking.Track(_httpClient, _appHost, _serverConfigurationManager, "start", "refresh", cancellationToken).ConfigureAwait(false); progress.Report(2d); var items = (await GetBluRayReleaseItems(cancellationToken).ConfigureAwait(false)).List; progress.Report(6d); var config = await BlurNTasks.CheckIfResetDatabaseRequested(cancellationToken, _json, _appPaths, _fileSystem).ConfigureAwait(false); progress.Report(8d); string dataPath = Path.Combine(_appPaths.PluginConfigurationsPath, "MediaBrowser.Channels.BlurN.Data.json"); ConvertPostersFromW640ToOriginal(config, dataPath); Plugin.DebugLogger($"Found {items.Count} items in feed"); DateTime lastPublishDate = config.LastPublishDate; DateTime minAge = DateTime.Today.AddDays(0 - config.Age); DateTime newPublishDate = items[0].PublishDate; Dictionary <string, BaseItem> libDict = (config.AddItemsAlreadyInLibrary) ? Library.BuildLibraryDictionary(cancellationToken, _libraryManager, new InternalItemsQuery() { HasAnyProviderId = new[] { "Imdb" }, //SourceTypes = new SourceType[] { SourceType.Library } }) : new Dictionary <string, BaseItem>(); cancellationToken.ThrowIfCancellationRequested(); var insertList = new BlurNItems(); var failedList = new FailedBlurNList(); var existingData = new List <BlurNItem>(); //var finalItems = items.Where(i => i.PublishDate > lastPublishDate).GroupBy(x => new { x.Title, x.PublishDate }).Select(g => g.First()).Reverse().ToList(); var finalItems = items.GroupBy(x => new { x.Title, x.PublishDate }).Select(g => g.First()).Reverse().ToList(); string failedDataPath = AddPreviouslyFailedItemsToFinalItems(finalItems); Plugin.DebugLogger($"Checking {finalItems.Count} new items"); var genreExcludeList = GetGenreExcludeList(config); progress.Report(10d); bool itemAdded = false; if (_fileSystem.FileExists(dataPath)) { existingData = _json.DeserializeFromFile <List <BlurNItem> >(dataPath); if (config.ChannelRefreshCount < 6) { if (config.ChannelRefreshCount < 4) { existingData = existingData.GroupBy(p => p.ImdbId).Select(g => g.First()).ToList(); } config.ChannelRefreshCount = 6; Plugin.Instance.SaveConfiguration(); } } for (int i = 0; i < finalItems.Count(); i++) { cancellationToken.ThrowIfCancellationRequested(); progress.Report(10d + (86d * (Convert.ToDouble(i + 1) / Convert.ToDouble(finalItems.Count())))); Item item = finalItems[i]; int year = 0; if (item.Link == "Failed") // previously failed item { year = Convert.ToInt32(item.Content); } else // new item { Regex rgx = new Regex(@"\| (\d{4}) \|", RegexOptions.IgnoreCase); MatchCollection matches = rgx.Matches(item.Content); if (matches.Count > 0) { Match match = matches[matches.Count - 1]; Group group = match.Groups[match.Groups.Count - 1]; year = Convert.ToInt32(group.Value); } } string url; url = BuildOMDbApiUrl(item, year, false); BlurNItem blurNItem = await ParseOMDB(url, item.PublishDate, cancellationToken).ConfigureAwait(false); if (blurNItem != null && string.IsNullOrEmpty(blurNItem.ImdbId) && (item.Title.EndsWith(" 3D") || item.Title.EndsWith(" 4K")) && year > 0) { url = BuildOMDbApiUrl(item, year, true); blurNItem = await ParseOMDB(url, item.PublishDate, cancellationToken).ConfigureAwait(false); } if (blurNItem == null) { Plugin.DebugLogger($"Adding {item.Title} ({year}) to failed list"); failedList.List.Add(new FailedBlurNItem() { Title = item.Title, Year = year }); } else if (!string.IsNullOrEmpty(blurNItem.ImdbId) && (insertList.List.Any(x => x.ImdbId == blurNItem.ImdbId) || existingData.Select(d => d.ImdbId).Contains(blurNItem.ImdbId))) { Plugin.DebugLogger($"{blurNItem.ImdbId} is a duplicate, skipped."); } else if (!string.IsNullOrEmpty(blurNItem.ImdbId) && !config.AddItemsAlreadyInLibrary && libDict.ContainsKey(blurNItem.ImdbId)) { Plugin.DebugLogger($"{blurNItem.ImdbId} is already in the library, skipped."); } else if (!string.IsNullOrEmpty(blurNItem.ImdbId) && config.HidePlayedMovies && libDict.ContainsKey(blurNItem.ImdbId) && _userManager.Users.All(x => libDict[blurNItem.ImdbId].IsPlayed(x))) { Plugin.DebugLogger($"{blurNItem.ImdbId} is played by all users, skipped."); } else if (blurNItem.Type != "movie") { Plugin.DebugLogger($"{blurNItem.Title} is not of type 'movie', skipped."); } else if (genreExcludeList.Contains(blurNItem.FirstGenre)) { Plugin.DebugLogger($"{blurNItem.Title} has first genre '{blurNItem.FirstGenre}' which is not whitelisted, skipped."); } else if (blurNItem.ImdbRating < config.MinimumIMDBRating) { Plugin.DebugLogger($"{blurNItem.Title} has an IMDb rating of {blurNItem.ImdbRating} which is lower than the minimum setting of {config.MinimumIMDBRating}, skipped."); } else if (blurNItem.ImdbVotes < config.MinimumIMDBVotes) { Plugin.DebugLogger($"{blurNItem.Title} has a total of {blurNItem.ImdbVotes} IMDb votes which is lower than the minimum setting of {config.MinimumIMDBVotes} votes, skipped."); } else if (blurNItem.Released < minAge) { Plugin.DebugLogger($"{blurNItem.Title} was released on {blurNItem.Released.ToString("yyyy-MM-dd")} which is older than the setting of {config.Age} days, skipped."); } else // passed all filters, adding { await UpdateContentWithTmdbData(cancellationToken, blurNItem).ConfigureAwait(false); insertList.List.Add(blurNItem); await Plugin.NotificationManager.SendNotification(new NotificationRequest() { Date = DateTime.Now, Level = NotificationLevel.Normal, NotificationType = BlurNNotificationType.NewRelease, Url = blurNItem.ImdbUrl, Name = string.Format("[BlurN] New movie released: {0}", blurNItem.Title), Description = string.Format("Year: {0}, IMDb Rating: {1} ({2} votes)", blurNItem.Year, blurNItem.ImdbRating, blurNItem.ImdbVotes.ToString("#,##0")) }, cancellationToken).ConfigureAwait(false); Plugin.DebugLogger($"Adding {blurNItem.Title} to the BlurN channel."); itemAdded = true; } } if (existingData != null) { //insertList.List = insertList.List.Where(x => !existingData.Select(d => d.ImdbId).Contains(x.ImdbId)).ToList(); foreach (BlurNItem blurNItem in existingData.Where(o => !o.TmdbId.HasValue)) { await UpdateContentWithTmdbData(cancellationToken, blurNItem).ConfigureAwait(false); } insertList.List.AddRange(existingData); } insertList.List = insertList.List.OrderByDescending(i => i.BluRayReleaseDate).ThenByDescending(i => i.ImdbRating).ThenByDescending(i => i.ImdbVotes).ThenByDescending(i => i.Metascore).ThenBy(i => i.Title).ToList(); config.LastPublishDate = newPublishDate; if (config.DataVersion == "0" || itemAdded) { config.DataVersion = DateTime.Now.ToString("yyyyMMddHHmmss"); } Plugin.Instance.SaveConfiguration(); Plugin.DebugLogger($"Configuration saved. MediaBrowser.Channels.BlurN.Data.json path is {dataPath}"); progress.Report(97d); _json.SerializeToFile(insertList.List, dataPath); _json.SerializeToFile(failedList.List, failedDataPath); Plugin.DebugLogger($"JSON files saved to {dataPath}"); progress.Report(98d); await Tracking.Track(_httpClient, _appHost, _serverConfigurationManager, "end", "refresh", cancellationToken).ConfigureAwait(false); progress.Report(100); return; }
public async Task <ChannelItemResult> GetItems(bool inChannel, InternalChannelItemQuery query, CancellationToken cancellationToken) { cancellationToken.ThrowIfCancellationRequested(); var config = await BlurNTasks.CheckIfResetDatabaseRequested(cancellationToken, _json, _appPaths, _fileSystem).ConfigureAwait(false); if (inChannel) { Plugin.DebugLogger("Entered BlurN channel list"); } User user = query.UserId.Equals(Guid.Empty) ? null : _userManager.GetUserById(query.UserId); Dictionary <string, BaseItem> libDict = (user == null) ? new Dictionary <string, BaseItem>() : Library.BuildLibraryDictionary(cancellationToken, _libraryManager, new InternalItemsQuery() { HasAnyProviderId = new[] { "Imdb" }, User = user, //SourceTypes = new SourceType[] { SourceType.Library } }); Plugin.DebugLogger($"Found {libDict.Count} items in movies library"); BlurNItems items = new BlurNItems(); string dataPath = Path.Combine(_appPaths.PluginConfigurationsPath, "MediaBrowser.Channels.BlurN.Data.json"); if (_fileSystem.FileExists(dataPath)) { items.List = _json.DeserializeFromFile <List <BlurNItem> >(dataPath); } if (inChannel) { Plugin.DebugLogger("Retrieved items"); } if (items == null) { if (inChannel) { Plugin.DebugLogger("Items is null, set to new list"); } items = new BlurNItems(); Plugin.Instance.SaveConfiguration(); } for (int i = 0; i < items.List.Count; i++) { BlurNItem blurNItem = items.List[i]; BaseItem libraryItem; bool foundInLibrary = libDict.TryGetValue(blurNItem.ImdbId, out libraryItem); if (foundInLibrary) { if (config.HidePlayedMovies && user != null && libraryItem.IsPlayed(user)) { items.List.RemoveAt(i); i--; if (inChannel) { Plugin.DebugLogger($"Hiding movie '{blurNItem.Title}' from BlurN channel list as watched by user"); } } else if (!config.AddItemsAlreadyInLibrary) { items.List.RemoveAt(i); i--; if (inChannel) { Plugin.DebugLogger($"Hiding movie '{blurNItem.Title}' from BlurN channel list as availabile in library"); } } else { blurNItem.LibraryItem = libraryItem; } } } switch (query.SortBy) { case ChannelItemSortField.Name: if (query.SortDescending) { items.List.OrderByDescending(i => i.Title); } else { items.List.OrderBy(i => i.Title); } break; case ChannelItemSortField.DateCreated: if (query.SortDescending) { items.List.OrderByDescending(i => i.BluRayReleaseDate); } else { items.List.OrderBy(i => i.BluRayReleaseDate); } break; case ChannelItemSortField.CommunityRating: if (query.SortDescending) { items.List.OrderByDescending(i => i.ImdbRating).ThenByDescending(i => i.ImdbVotes); } else { items.List.OrderBy(i => i.ImdbRating).ThenBy(i => i.ImdbVotes); } break; case ChannelItemSortField.PremiereDate: if (query.SortDescending) { items.List.OrderByDescending(i => i.Released); } else { items.List.OrderBy(i => i.Released); } break; case ChannelItemSortField.Runtime: if (query.SortDescending) { items.List.OrderByDescending(i => i.RuntimeTicks); } else { items.List.OrderBy(i => i.RuntimeTicks); } break; default: if (query.SortDescending) { items.List.Reverse(); } break; } BlurNItems showList = new BlurNItems(); if (query.StartIndex.HasValue && query.Limit.HasValue && query.Limit.Value > 0) { int index = query.StartIndex.Value; int limit = query.Limit.Value; if (items.List.Count < index + limit) { limit = items.List.Count - index; } showList.List = items.List.GetRange(index, limit); if (inChannel) { Plugin.DebugLogger($"Showing range with index {index} and limit {limit}"); } } else { showList.List = items.List; if (inChannel) { Plugin.DebugLogger("Showing full list"); } } ChannelItemResult result = new ChannelItemResult() { TotalRecordCount = items.List.Count }; for (int i = 0; i < showList.List.Count; i++) { BlurNItem blurNItem = showList.List[i]; if (inChannel) { Plugin.DebugLogger($"Showing movie '{blurNItem.Title}' to BlurN channel list"); } var directors = CSVParse(blurNItem.Director); var writers = CSVParse(blurNItem.Writer); var actors = CSVParse(blurNItem.Actors); var people = new List <PersonInfo>(); foreach (var director in directors) { people.Add(new PersonInfo() { Name = director, Role = "Director" }); } foreach (var writer in writers) { people.Add(new PersonInfo() { Name = writer, Role = "Writer" }); } foreach (string actor in actors) { people.Add(new PersonInfo() { Name = actor, Role = "Actor" }); } var genres = CSVParse(blurNItem.Genre).ToList(); var cii = new ChannelItemInfo() { Id = $"{config.ChannelRefreshCount.ToString()}-{blurNItem.ImdbId}", IndexNumber = i, CommunityRating = (float)blurNItem.ImdbRating, ContentType = ChannelMediaContentType.Movie, DateCreated = blurNItem.BluRayReleaseDate, Genres = genres, ImageUrl = (blurNItem.Poster == "N/A") ? null : blurNItem.Poster, MediaType = ChannelMediaType.Video, Name = blurNItem.Title, OfficialRating = (blurNItem.Rated == "N/A") ? null : blurNItem.Rated, Overview = (blurNItem.Plot == "N/A") ? null : blurNItem.Plot, People = people, PremiereDate = blurNItem.Released, ProductionYear = blurNItem.Released.Year, RunTimeTicks = blurNItem.RuntimeTicks, Type = ChannelItemType.Media, DateModified = blurNItem.BluRayReleaseDate, IsLiveStream = false }; cii.SetProviderId(MetadataProviders.Imdb, blurNItem.ImdbId); if (blurNItem.TmdbId.HasValue) { cii.SetProviderId(MetadataProviders.Tmdb, blurNItem.TmdbId.Value.ToString()); } if (blurNItem.LibraryItem != null) { var mediaStreams = _mediaSourceManager.GetMediaStreams(blurNItem.LibraryItem.InternalId).ToList(); var audioStream = mediaStreams.FirstOrDefault(ms => ms.Type == MediaStreamType.Audio && ms.IsDefault); var videoStream = mediaStreams.FirstOrDefault(ms => ms.Type == MediaStreamType.Video && ms.IsDefault); ChannelMediaInfo cmi = new ChannelMediaInfo() { Path = _libraryManager.GetPathAfterNetworkSubstitution(blurNItem.LibraryItem.Path, blurNItem.LibraryItem), Container = blurNItem.LibraryItem.Container, RunTimeTicks = blurNItem.LibraryItem.RunTimeTicks, SupportsDirectPlay = true, Id = blurNItem.LibraryItem.Id.ToString(), Protocol = Model.MediaInfo.MediaProtocol.File }; if (audioStream != null) { cmi.AudioBitrate = audioStream.BitRate; cmi.AudioChannels = audioStream.Channels; cmi.AudioCodec = audioStream.Codec; cmi.AudioSampleRate = audioStream.SampleRate; } if (videoStream != null) { cmi.Framerate = videoStream.RealFrameRate; cmi.Height = videoStream.Height; cmi.IsAnamorphic = videoStream.IsAnamorphic; cmi.VideoBitrate = videoStream.BitRate; cmi.VideoCodec = videoStream.Codec; if (videoStream.Level.HasValue) { cmi.VideoLevel = (float)videoStream.Level.Value; } cmi.VideoProfile = videoStream.Profile; cmi.Width = videoStream.Width; } Plugin.DebugLogger($"Linked movie {blurNItem.Title} to library. Path: {blurNItem.LibraryItem.Path}, Substituted Path: {cmi.Path}"); cii.MediaSources = new List <MediaSourceInfo>() { cmi.ToMediaSource() }; } result.Items.Add(cii); if (inChannel) { Plugin.DebugLogger($"Added movie '{blurNItem.Title}' to BlurN channel list"); } } if (inChannel) { Plugin.DebugLogger($"Set total record count ({(int)result.TotalRecordCount})"); } return(result); }