public async Task <Either <BaseError, Unit> > ScanLibrary( string address, string apiKey, JellyfinLibrary library, string ffmpegPath, string ffprobePath, CancellationToken cancellationToken) { List <JellyfinPathReplacement> pathReplacements = await _mediaSourceRepository.GetJellyfinPathReplacements(library.MediaSourceId); string GetLocalPath(JellyfinMovie movie) { return(_pathReplacementService.GetReplacementJellyfinPath( pathReplacements, movie.GetHeadVersion().MediaFiles.Head().Path, false)); } return(await ScanLibrary( _jellyfinMovieRepository, new JellyfinConnectionParameters(address, apiKey, library.MediaSourceId), library, GetLocalPath, ffmpegPath, ffprobePath, false, cancellationToken)); }
public async Task <Either <BaseError, Unit> > ScanLibrary( string address, string apiKey, JellyfinLibrary library, string ffmpegPath, string ffprobePath, CancellationToken cancellationToken) { try { List <JellyfinItemEtag> existingShows = await _televisionRepository.GetExistingShows(library); // TODO: maybe get quick list of item ids and etags from api to compare first // TODO: paging? List <JellyfinPathReplacement> pathReplacements = await _mediaSourceRepository .GetJellyfinPathReplacements(library.MediaSourceId); Either <BaseError, List <JellyfinShow> > maybeShows = await _jellyfinApiClient.GetShowLibraryItems( address, apiKey, library.MediaSourceId, library.ItemId); foreach (BaseError error in maybeShows.LeftToSeq()) { _logger.LogWarning( "Error synchronizing jellyfin library {Path}: {Error}", library.Name, error.Value); } foreach (List <JellyfinShow> shows in maybeShows.RightToSeq()) { Either <BaseError, Unit> scanResult = await ProcessShows( address, apiKey, library, ffmpegPath, ffprobePath, pathReplacements, existingShows, shows, cancellationToken); foreach (ScanCanceled error in scanResult.LeftToSeq().OfType <ScanCanceled>()) { return(error); } foreach (Unit _ in scanResult.RightToSeq()) { var incomingShowIds = shows.Map(s => s.ItemId).ToList(); var showIds = existingShows .Filter(i => !incomingShowIds.Contains(i.ItemId)) .Map(m => m.ItemId) .ToList(); List <int> missingShowIds = await _televisionRepository.RemoveMissingShows(library, showIds); await _searchIndex.RemoveItems(missingShowIds); await _televisionRepository.DeleteEmptySeasons(library); List <int> emptyShowIds = await _televisionRepository.DeleteEmptyShows(library); await _searchIndex.RemoveItems(emptyShowIds); await _mediator.Publish(new LibraryScanProgress(library.Id, 0), cancellationToken); } } return(Unit.Default); } catch (Exception ex) when(ex is TaskCanceledException or OperationCanceledException) { return(new ScanCanceled()); } finally { _searchIndex.Commit(); } }