From 247f9c61e60ef774675cb4d6d1734d2ccdc6ee7a Mon Sep 17 00:00:00 2001 From: telans Date: Tue, 16 Jun 2020 09:43:52 +1200 Subject: [PATCH] fix SA1513/SA1516 --- DvdLib/Ifo/Cell.cs | 1 + DvdLib/Ifo/Chapter.cs | 2 + DvdLib/Ifo/Dvd.cs | 1 + DvdLib/Ifo/ProgramChain.cs | 4 + DvdLib/Ifo/Title.cs | 4 + Emby.Dlna/ContentDirectory/ControlHandler.cs | 1 + Emby.Dlna/Didl/DidlBuilder.cs | 3 + Emby.Dlna/DlnaManager.cs | 3 + Emby.Dlna/Eventing/EventManager.cs | 1 + Emby.Dlna/Eventing/EventSubscription.cs | 3 + Emby.Dlna/Main/DlnaEntryPoint.cs | 2 + Emby.Dlna/PlayTo/Device.cs | 2 + Emby.Dlna/PlayTo/PlayToController.cs | 5 + Emby.Dlna/PlayTo/PlayToManager.cs | 1 + Emby.Dlna/PlayTo/PlaybackStoppedEventArgs.cs | 1 + Emby.Dlna/PlayTo/uBaseObject.cs | 2 + Emby.Dlna/Server/DescriptionXmlBuilder.cs | 5 + Emby.Dlna/Service/BaseControlHandler.cs | 4 + Emby.Dlna/Service/ServiceXmlBuilder.cs | 1 + .../AudioBook/AudioBookFilePathParser.cs | 1 + .../Data/SqliteItemRepository.cs | 115 +++++++++++++++++ .../Data/SqliteUserDataRepository.cs | 3 + .../Devices/DeviceManager.cs | 1 + Emby.Server.Implementations/Dto/DtoService.cs | 11 ++ .../HttpServer/HttpListenerHost.cs | 1 + .../HttpServer/RangeRequestWriter.cs | 7 ++ .../HttpServer/Security/AuthService.cs | 1 + .../Security/AuthorizationContext.cs | 2 + .../IO/ManagedFileSystem.cs | 2 + .../Library/ExclusiveLiveStream.cs | 2 + .../Library/LibraryManager.cs | 2 + .../Library/MediaSourceManager.cs | 5 + .../Resolvers/SpecialFolderResolver.cs | 2 + .../Library/Resolvers/TV/EpisodeResolver.cs | 1 + .../Library/SearchEngine.cs | 1 + .../LiveTv/Listings/SchedulesDirect.cs | 118 ++++++++++++++++++ .../LiveTv/Listings/XmlTvListingsProvider.cs | 1 + .../LiveTv/LiveTvManager.cs | 12 ++ .../TunerHosts/HdHomerun/HdHomerunHost.cs | 19 +++ .../LiveTv/TunerHosts/LiveStream.cs | 3 + .../Playlists/PlaylistManager.cs | 1 + .../ScheduledTasks/ScheduledTaskWorker.cs | 5 + .../Services/ServiceMethod.cs | 1 + .../Services/ServicePath.cs | 3 + .../Services/StringMapTypeDeserializer.cs | 2 + .../Services/SwaggerService.cs | 34 +++++ .../Session/SessionWebSocketListener.cs | 1 + .../Sorting/PremiereDateComparer.cs | 1 + .../TV/TVSeriesManager.cs | 1 + Jellyfin.Data/Entities/Artwork.cs | 3 + Jellyfin.Data/Entities/BookMetadata.cs | 1 + Jellyfin.Data/Entities/Chapter.cs | 5 + Jellyfin.Data/Entities/Collection.cs | 2 + Jellyfin.Data/Entities/CollectionItem.cs | 1 + Jellyfin.Data/Entities/Company.cs | 1 + Jellyfin.Data/Entities/CompanyMetadata.cs | 4 + Jellyfin.Data/Entities/Episode.cs | 1 + Jellyfin.Data/Entities/EpisodeMetadata.cs | 3 + Jellyfin.Data/Entities/Genre.cs | 2 + Jellyfin.Data/Entities/Library.cs | 2 + Jellyfin.Data/Entities/LibraryItem.cs | 3 + Jellyfin.Data/Entities/LibraryRoot.cs | 3 + Jellyfin.Data/Entities/MediaFile.cs | 3 + Jellyfin.Data/Entities/MediaFileStream.cs | 2 + Jellyfin.Data/Entities/Metadata.cs | 8 ++ Jellyfin.Data/Entities/MetadataProvider.cs | 2 + Jellyfin.Data/Entities/MetadataProviderId.cs | 2 + Jellyfin.Data/Entities/MovieMetadata.cs | 4 + Jellyfin.Data/Entities/MusicAlbumMetadata.cs | 3 + Jellyfin.Data/Entities/Person.cs | 6 + Jellyfin.Data/Entities/PersonRole.cs | 3 + Jellyfin.Data/Entities/Rating.cs | 3 + Jellyfin.Data/Entities/RatingSource.cs | 4 + Jellyfin.Data/Entities/Release.cs | 2 + Jellyfin.Data/Entities/Season.cs | 1 + Jellyfin.Data/Entities/SeasonMetadata.cs | 1 + Jellyfin.Data/Entities/Series.cs | 3 + Jellyfin.Data/Entities/SeriesMetadata.cs | 4 + Jellyfin.Data/Entities/Track.cs | 1 + Jellyfin.Server.Implementations/JellyfinDb.cs | 39 ++++++ MediaBrowser.Api/EnvironmentService.cs | 1 + MediaBrowser.Api/FilterService.cs | 6 + MediaBrowser.Api/IHasDtoOptions.cs | 1 + MediaBrowser.Api/Library/LibraryService.cs | 11 ++ MediaBrowser.Api/LiveTv/LiveTvService.cs | 15 +++ .../Playback/BaseStreamingService.cs | 4 + .../Playback/Hls/BaseHlsService.cs | 1 + .../Playback/Hls/DynamicHlsService.cs | 2 + MediaBrowser.Api/Playback/MediaInfoService.cs | 2 + .../BaseProgressiveStreamingService.cs | 6 + .../Progressive/ProgressiveStreamWriter.cs | 2 + MediaBrowser.Api/Playback/StreamRequest.cs | 4 + .../Playback/UniversalAudioService.cs | 20 +++ MediaBrowser.Api/PluginService.cs | 9 ++ MediaBrowser.Api/SimilarItemsHelper.cs | 4 + MediaBrowser.Api/Subtitles/SubtitleService.cs | 2 + MediaBrowser.Api/SuggestionsService.cs | 5 + MediaBrowser.Api/TranscodingJob.cs | 8 ++ MediaBrowser.Api/TvShowsService.cs | 1 + .../UserLibrary/BaseItemsByNameService.cs | 1 + .../UserLibrary/BaseItemsRequest.cs | 3 + .../UserLibrary/UserViewsService.cs | 3 + .../Authentication/IAuthenticationProvider.cs | 3 + .../Authentication/IPasswordResetProvider.cs | 3 + .../Channels/ChannelItemInfo.cs | 11 ++ .../Collections/CollectionCreationOptions.cs | 1 + .../Drawing/ImageHelper.cs | 1 + .../Drawing/ImageProcessingOptions.cs | 7 ++ MediaBrowser.Controller/Dto/DtoOptions.cs | 6 + .../Entities/AggregateFolder.cs | 1 + .../Entities/Audio/Audio.cs | 2 + .../Entities/Audio/MusicAlbum.cs | 1 + .../Entities/Audio/MusicArtist.cs | 1 + .../Entities/Audio/MusicGenre.cs | 2 + MediaBrowser.Controller/Entities/AudioBook.cs | 2 + MediaBrowser.Controller/Entities/BaseItem.cs | 16 +++ .../Entities/CollectionFolder.cs | 3 + MediaBrowser.Controller/Entities/Folder.cs | 21 ++++ MediaBrowser.Controller/Entities/Genre.cs | 2 + .../Entities/IHasMediaSources.cs | 2 + .../Entities/IHasProgramAttributes.cs | 8 ++ .../Entities/IHasSeries.cs | 3 + .../Entities/InternalItemsQuery.cs | 103 +++++++++++++++ .../Entities/LinkedChild.cs | 3 + .../Entities/PeopleHelper.cs | 1 + MediaBrowser.Controller/Entities/Person.cs | 2 + MediaBrowser.Controller/Entities/Photo.cs | 11 ++ MediaBrowser.Controller/Entities/Share.cs | 1 + MediaBrowser.Controller/Entities/Studio.cs | 2 + .../Entities/TV/Episode.cs | 6 + MediaBrowser.Controller/Entities/TV/Season.cs | 1 + MediaBrowser.Controller/Entities/TV/Series.cs | 2 + .../Entities/UserItemData.cs | 1 + .../Entities/UserViewBuilder.cs | 2 + MediaBrowser.Controller/Entities/Video.cs | 10 ++ MediaBrowser.Controller/Entities/Year.cs | 1 + MediaBrowser.Controller/IO/FileData.cs | 3 + .../Library/DeleteOptions.cs | 1 + .../Library/ILiveStream.cs | 5 + .../Library/ItemResolveArgs.cs | 2 + .../Library/PlaybackProgressEventArgs.cs | 9 ++ MediaBrowser.Controller/Library/Profiler.cs | 1 + MediaBrowser.Controller/Library/TVUtils.cs | 1 + MediaBrowser.Controller/LiveTv/ChannelInfo.cs | 3 + .../LiveTv/ILiveTvManager.cs | 3 + MediaBrowser.Controller/LiveTv/ITunerHost.cs | 1 + .../LiveTv/LiveTvConflictException.cs | 1 + MediaBrowser.Controller/LiveTv/ProgramInfo.cs | 1 + .../LiveTv/SeriesTimerInfo.cs | 1 + MediaBrowser.Controller/LiveTv/TimerInfo.cs | 7 ++ .../LiveTv/TunerChannelMapping.cs | 3 + .../MediaEncoding/EncodingHelper.cs | 28 +++++ .../MediaEncoding/EncodingJobInfo.cs | 8 ++ .../MediaEncoding/EncodingJobOptions.cs | 10 ++ .../MediaEncoding/MediaInfoRequest.cs | 4 + .../Net/AuthenticatedAttribute.cs | 3 + .../Net/BasePeriodicWebSocketListener.cs | 2 + .../Net/StaticResultOptions.cs | 5 + .../Providers/ImageRefreshOptions.cs | 2 + .../Providers/MetadataResult.cs | 1 + .../Resolvers/IItemResolver.cs | 1 + .../Security/AuthenticationInfo.cs | 1 + .../Session/AuthenticationRequest.cs | 8 ++ .../Session/SessionInfo.cs | 5 + .../Subtitles/SubtitleResponse.cs | 3 + .../Subtitles/SubtitleSearchRequest.cs | 12 ++ .../Sync/SyncedFileInfo.cs | 1 + MediaBrowser.Controller/SyncPlay/GroupInfo.cs | 1 + .../Images/EpisodeLocalImageProvider.cs | 1 + .../Parsers/BaseItemXmlParser.cs | 48 +++++++ .../Parsers/BoxSetXmlParser.cs | 2 + .../Parsers/PlaylistXmlParser.cs | 2 + .../Savers/BaseXmlSaver.cs | 7 ++ .../Encoder/MediaEncoder.cs | 1 + .../Probing/ProbeResultNormalizer.cs | 13 ++ .../Subtitles/AssParser.cs | 4 + .../Subtitles/SrtParser.cs | 5 + .../Subtitles/SsaParser.cs | 4 + .../Subtitles/SubtitleEncoder.cs | 9 ++ .../Configuration/LibraryOptions.cs | 23 ++++ .../Configuration/UserConfiguration.cs | 4 + .../Configuration/XbmcMetadataOptions.cs | 1 + MediaBrowser.Model/Dlna/AudioOptions.cs | 1 + MediaBrowser.Model/Dlna/DeviceProfile.cs | 21 ++++ .../Dlna/MediaFormatProfileResolver.cs | 13 ++ MediaBrowser.Model/Dlna/StreamBuilder.cs | 21 ++++ MediaBrowser.Model/Dlna/StreamInfo.cs | 20 +++ MediaBrowser.Model/Dto/BaseItemDto.cs | 25 ++++ MediaBrowser.Model/Dto/MediaSourceInfo.cs | 21 ++++ MediaBrowser.Model/Dto/MetadataEditorInfo.cs | 4 + MediaBrowser.Model/Dto/NameIdPair.cs | 1 + MediaBrowser.Model/Entities/MediaStream.cs | 13 ++ MediaBrowser.Model/Entities/MediaUrl.cs | 1 + .../Entities/VirtualFolderInfo.cs | 1 + MediaBrowser.Model/LiveTv/BaseTimerInfoDto.cs | 1 + .../LiveTv/LiveTvChannelQuery.cs | 2 + MediaBrowser.Model/LiveTv/LiveTvOptions.cs | 34 +++++ MediaBrowser.Model/LiveTv/RecordingQuery.cs | 9 ++ .../MediaInfo/LiveStreamRequest.cs | 11 ++ MediaBrowser.Model/MediaInfo/MediaInfo.cs | 8 ++ .../MediaInfo/PlaybackInfoRequest.cs | 6 + .../Providers/RemoteSubtitleInfo.cs | 10 ++ .../Providers/SubtitleOptions.cs | 6 + .../Providers/SubtitleProviderInfo.cs | 1 + MediaBrowser.Model/Querying/QueryFilters.cs | 5 + MediaBrowser.Model/Search/SearchHint.cs | 1 + MediaBrowser.Model/Search/SearchQuery.cs | 7 ++ MediaBrowser.Model/Services/IRequest.cs | 4 + MediaBrowser.Model/Services/IService.cs | 2 + .../Session/ClientCapabilities.cs | 4 + MediaBrowser.Model/Session/PlayRequest.cs | 3 + .../Session/PlaybackProgressInfo.cs | 2 + .../Session/PlaybackStopInfo.cs | 1 + MediaBrowser.Model/Session/TranscodingInfo.cs | 8 ++ MediaBrowser.Model/Sync/SyncJob.cs | 2 + MediaBrowser.Model/Users/UserAction.cs | 6 + MediaBrowser.Model/Users/UserPolicy.cs | 20 +++ MediaBrowser.Providers/Manager/ImageSaver.cs | 5 + .../Manager/ItemImageProvider.cs | 3 + .../Manager/MetadataService.cs | 7 ++ .../Manager/ProviderManager.cs | 1 + .../Manager/ProviderUtils.cs | 1 + .../MediaInfo/AudioImageProvider.cs | 1 + .../MediaInfo/FFProbeVideoInfo.cs | 3 + .../MediaInfo/VideoImageProvider.cs | 2 + .../Movies/MovieMetadataService.cs | 2 + .../Movies/TrailerMetadataService.cs | 2 + .../Playlists/PlaylistItemsProvider.cs | 4 + .../Plugins/AudioDb/AlbumProvider.cs | 37 ++++++ .../Plugins/AudioDb/ArtistProvider.cs | 40 ++++++ .../Plugins/MusicBrainz/AlbumProvider.cs | 13 ++ .../Plugins/MusicBrainz/ArtistProvider.cs | 6 + .../Plugins/Omdb/OmdbItemProvider.cs | 22 ++++ .../Models/Collections/CollectionImages.cs | 1 + .../Models/Collections/CollectionResult.cs | 6 + .../Plugins/Tmdb/Models/Collections/Part.cs | 4 + .../Plugins/Tmdb/Models/General/Backdrop.cs | 6 + .../Plugins/Tmdb/Models/General/Crew.cs | 5 + .../Tmdb/Models/General/ExternalIds.cs | 4 + .../Plugins/Tmdb/Models/General/Genre.cs | 1 + .../Plugins/Tmdb/Models/General/Images.cs | 1 + .../Plugins/Tmdb/Models/General/Keyword.cs | 1 + .../Plugins/Tmdb/Models/General/Poster.cs | 6 + .../Plugins/Tmdb/Models/General/Profile.cs | 4 + .../Plugins/Tmdb/Models/General/Still.cs | 7 ++ .../Plugins/Tmdb/Models/General/Video.cs | 7 ++ .../Tmdb/Models/Movies/BelongsToCollection.cs | 3 + .../Plugins/Tmdb/Models/Movies/Cast.cs | 5 + .../Plugins/Tmdb/Models/Movies/Casts.cs | 1 + .../Plugins/Tmdb/Models/Movies/Country.cs | 2 + .../Plugins/Tmdb/Models/Movies/MovieResult.cs | 29 +++++ .../Tmdb/Models/Movies/ProductionCompany.cs | 1 + .../Tmdb/Models/Movies/ProductionCountry.cs | 1 + .../Tmdb/Models/Movies/SpokenLanguage.cs | 1 + .../Plugins/Tmdb/Models/Movies/Youtube.cs | 2 + .../Tmdb/Models/People/PersonResult.cs | 13 ++ .../Plugins/Tmdb/Models/Search/TvResult.cs | 8 ++ .../Plugins/Tmdb/Models/TV/Cast.cs | 5 + .../Plugins/Tmdb/Models/TV/ContentRating.cs | 1 + .../Plugins/Tmdb/Models/TV/CreatedBy.cs | 2 + .../Plugins/Tmdb/Models/TV/Credits.cs | 1 + .../Plugins/Tmdb/Models/TV/Episode.cs | 7 ++ .../Plugins/Tmdb/Models/TV/EpisodeCredits.cs | 2 + .../Plugins/Tmdb/Models/TV/EpisodeResult.cs | 13 ++ .../Plugins/Tmdb/Models/TV/GuestStar.cs | 5 + .../Plugins/Tmdb/Models/TV/Network.cs | 1 + .../Plugins/Tmdb/Models/TV/Season.cs | 4 + .../Plugins/Tmdb/Models/TV/SeasonResult.cs | 10 ++ .../Plugins/Tmdb/Models/TV/SeriesResult.cs | 29 +++++ .../Plugins/Tmdb/Movies/TmdbImageProvider.cs | 3 + .../Plugins/Tmdb/Movies/TmdbSettings.cs | 3 + .../Tmdb/People/TmdbPersonImageProvider.cs | 3 + .../Plugins/Tmdb/People/TmdbPersonProvider.cs | 1 + .../Subtitles/SubtitleManager.cs | 1 + .../TV/DummySeasonProvider.cs | 1 + .../TV/SeriesMetadataService.cs | 2 + RSSDP/DiscoveredSsdpDevice.cs | 1 + RSSDP/HttpParserBase.cs | 1 + RSSDP/SsdpCommunicationsServer.cs | 1 + RSSDP/SsdpDevice.cs | 4 + RSSDP/SsdpDeviceLocator.cs | 1 + RSSDP/SsdpDevicePublisher.cs | 3 + RSSDP/SsdpEmbeddedDevice.cs | 1 + 283 files changed, 1810 insertions(+) diff --git a/DvdLib/Ifo/Cell.cs b/DvdLib/Ifo/Cell.cs index 2eab400f7d..ea0b50e430 100644 --- a/DvdLib/Ifo/Cell.cs +++ b/DvdLib/Ifo/Cell.cs @@ -7,6 +7,7 @@ namespace DvdLib.Ifo public class Cell { public CellPlaybackInfo PlaybackInfo { get; private set; } + public CellPositionInfo PositionInfo { get; private set; } internal void ParsePlayback(BinaryReader br) diff --git a/DvdLib/Ifo/Chapter.cs b/DvdLib/Ifo/Chapter.cs index 1e69429f82..e786cb5536 100644 --- a/DvdLib/Ifo/Chapter.cs +++ b/DvdLib/Ifo/Chapter.cs @@ -5,7 +5,9 @@ namespace DvdLib.Ifo public class Chapter { public ushort ProgramChainNumber { get; private set; } + public ushort ProgramNumber { get; private set; } + public uint ChapterNumber { get; private set; } public Chapter(ushort pgcNum, ushort programNum, uint chapterNum) diff --git a/DvdLib/Ifo/Dvd.cs b/DvdLib/Ifo/Dvd.cs index ca20baa73f..1252bab503 100644 --- a/DvdLib/Ifo/Dvd.cs +++ b/DvdLib/Ifo/Dvd.cs @@ -125,6 +125,7 @@ namespace DvdLib.Ifo if (titleNum + 1 < numTitles && vtsFs.Position == (baseAddr + offsets[titleNum + 1])) break; chapNum++; } + while (vtsFs.Position < (baseAddr + endaddr)); } diff --git a/DvdLib/Ifo/ProgramChain.cs b/DvdLib/Ifo/ProgramChain.cs index 4860360afd..8048f4bbd6 100644 --- a/DvdLib/Ifo/ProgramChain.cs +++ b/DvdLib/Ifo/ProgramChain.cs @@ -22,7 +22,9 @@ namespace DvdLib.Ifo public readonly List Cells; public DvdTime PlaybackTime { get; private set; } + public UserOperation ProhibitedUserOperations { get; private set; } + public byte[] AudioStreamControl { get; private set; } // 8*2 entries public byte[] SubpictureStreamControl { get; private set; } // 32*4 entries @@ -33,9 +35,11 @@ namespace DvdLib.Ifo private ushort _goupProgramNumber; public ProgramPlaybackMode PlaybackMode { get; private set; } + public uint ProgramCount { get; private set; } public byte StillTime { get; private set; } + public byte[] Palette { get; private set; } // 16*4 entries private ushort _commandTableOffset; diff --git a/DvdLib/Ifo/Title.cs b/DvdLib/Ifo/Title.cs index abf806d2c0..4af3af754a 100644 --- a/DvdLib/Ifo/Title.cs +++ b/DvdLib/Ifo/Title.cs @@ -8,8 +8,11 @@ namespace DvdLib.Ifo public class Title { public uint TitleNumber { get; private set; } + public uint AngleCount { get; private set; } + public ushort ChapterCount { get; private set; } + public byte VideoTitleSetNumber { get; private set; } private ushort _parentalManagementMask; @@ -17,6 +20,7 @@ namespace DvdLib.Ifo private uint _vtsStartSector; // relative to start of entire disk public ProgramChain EntryProgramChain { get; private set; } + public readonly List ProgramChains; public readonly List Chapters; diff --git a/Emby.Dlna/ContentDirectory/ControlHandler.cs b/Emby.Dlna/ContentDirectory/ControlHandler.cs index de6b619ba5..291de5245b 100644 --- a/Emby.Dlna/ContentDirectory/ControlHandler.cs +++ b/Emby.Dlna/ContentDirectory/ControlHandler.cs @@ -1357,6 +1357,7 @@ namespace Emby.Dlna.ContentDirectory internal class ServerItem { public BaseItem Item { get; set; } + public StubType? StubType { get; set; } public ServerItem(BaseItem item) diff --git a/Emby.Dlna/Didl/DidlBuilder.cs b/Emby.Dlna/Didl/DidlBuilder.cs index 6ded76f7dd..aa7a118157 100644 --- a/Emby.Dlna/Didl/DidlBuilder.cs +++ b/Emby.Dlna/Didl/DidlBuilder.cs @@ -765,6 +765,7 @@ namespace Emby.Dlna.Didl { AddValue(writer, "dc", "rating", item.OfficialRating, NS_DC); } + if (filter.Contains("upnp:rating")) { AddValue(writer, "upnp", "rating", item.OfficialRating, NS_UPNP); @@ -1052,10 +1053,12 @@ namespace Emby.Dlna.Didl { return GetImageInfo(item, ImageType.Primary); } + if (item.HasImage(ImageType.Thumb)) { return GetImageInfo(item, ImageType.Thumb); } + if (item.HasImage(ImageType.Backdrop)) { if (item is Channel) diff --git a/Emby.Dlna/DlnaManager.cs b/Emby.Dlna/DlnaManager.cs index e5f4839508..ef8df854bb 100644 --- a/Emby.Dlna/DlnaManager.cs +++ b/Emby.Dlna/DlnaManager.cs @@ -438,6 +438,7 @@ namespace Emby.Dlna { throw new ArgumentException("Profile is missing Id"); } + if (string.IsNullOrEmpty(profile.Name)) { throw new ArgumentException("Profile is missing Name"); @@ -463,6 +464,7 @@ namespace Emby.Dlna { _profiles[path] = new Tuple(GetInternalProfileInfo(_fileSystem.GetFileInfo(path), type), profile); } + SerializeToXml(profile, path); } @@ -492,6 +494,7 @@ namespace Emby.Dlna class InternalProfileInfo { internal DeviceProfileInfo Info { get; set; } + internal string Path { get; set; } } diff --git a/Emby.Dlna/Eventing/EventManager.cs b/Emby.Dlna/Eventing/EventManager.cs index 5a51569e21..edccfd1909 100644 --- a/Emby.Dlna/Eventing/EventManager.cs +++ b/Emby.Dlna/Eventing/EventManager.cs @@ -150,6 +150,7 @@ namespace Emby.Dlna.Eventing builder.Append(""); builder.Append(""); } + builder.Append(""); var options = new HttpRequestOptions diff --git a/Emby.Dlna/Eventing/EventSubscription.cs b/Emby.Dlna/Eventing/EventSubscription.cs index 51eaee9d77..40d73ee0e5 100644 --- a/Emby.Dlna/Eventing/EventSubscription.cs +++ b/Emby.Dlna/Eventing/EventSubscription.cs @@ -7,10 +7,13 @@ namespace Emby.Dlna.Eventing public class EventSubscription { public string Id { get; set; } + public string CallbackUrl { get; set; } + public string NotificationType { get; set; } public DateTime SubscriptionTime { get; set; } + public int TimeoutSeconds { get; set; } public long TriggerCount { get; set; } diff --git a/Emby.Dlna/Main/DlnaEntryPoint.cs b/Emby.Dlna/Main/DlnaEntryPoint.cs index a7b1d384d2..b965a09b92 100644 --- a/Emby.Dlna/Main/DlnaEntryPoint.cs +++ b/Emby.Dlna/Main/DlnaEntryPoint.cs @@ -320,6 +320,7 @@ namespace Emby.Dlna.Main { guid = text.GetMD5(); } + return guid.ToString("N", CultureInfo.InvariantCulture); } @@ -388,6 +389,7 @@ namespace Emby.Dlna.Main { _logger.LogError(ex, "Error disposing PlayTo manager"); } + _manager = null; } } diff --git a/Emby.Dlna/PlayTo/Device.cs b/Emby.Dlna/PlayTo/Device.cs index 86b72e264d..12757a1233 100644 --- a/Emby.Dlna/PlayTo/Device.cs +++ b/Emby.Dlna/PlayTo/Device.cs @@ -37,6 +37,7 @@ namespace Emby.Dlna.PlayTo RefreshVolumeIfNeeded().GetAwaiter().GetResult(); return _volume; } + set => _volume = value; } @@ -494,6 +495,7 @@ namespace Emby.Dlna.PlayTo return; } } + RestartTimerInactive(); } } diff --git a/Emby.Dlna/PlayTo/PlayToController.cs b/Emby.Dlna/PlayTo/PlayToController.cs index f1c69196a1..92a93d4349 100644 --- a/Emby.Dlna/PlayTo/PlayToController.cs +++ b/Emby.Dlna/PlayTo/PlayToController.cs @@ -425,6 +425,7 @@ namespace Emby.Dlna.PlayTo await _device.SetAvTransport(newItem.StreamUrl, GetDlnaHeaders(newItem), newItem.Didl, CancellationToken.None).ConfigureAwait(false); return; } + await SeekAfterTransportChange(newPosition, CancellationToken.None).ConfigureAwait(false); } } @@ -713,6 +714,7 @@ namespace Emby.Dlna.PlayTo throw new ArgumentException("Volume argument cannot be null"); } + default: return Task.CompletedTask; } @@ -798,12 +800,15 @@ namespace Emby.Dlna.PlayTo public int? SubtitleStreamIndex { get; set; } public string DeviceProfileId { get; set; } + public string DeviceId { get; set; } public string MediaSourceId { get; set; } + public string LiveStreamId { get; set; } public BaseItem Item { get; set; } + private MediaSourceInfo MediaSource; private IMediaSourceManager _mediaSourceManager; diff --git a/Emby.Dlna/PlayTo/PlayToManager.cs b/Emby.Dlna/PlayTo/PlayToManager.cs index c0500eb68b..240c8a7d98 100644 --- a/Emby.Dlna/PlayTo/PlayToManager.cs +++ b/Emby.Dlna/PlayTo/PlayToManager.cs @@ -132,6 +132,7 @@ namespace Emby.Dlna.PlayTo usn = usn.Substring(index); found = true; } + index = usn.IndexOf("::", StringComparison.OrdinalIgnoreCase); if (index != -1) { diff --git a/Emby.Dlna/PlayTo/PlaybackStoppedEventArgs.cs b/Emby.Dlna/PlayTo/PlaybackStoppedEventArgs.cs index 3b169e5993..fa42b80e8b 100644 --- a/Emby.Dlna/PlayTo/PlaybackStoppedEventArgs.cs +++ b/Emby.Dlna/PlayTo/PlaybackStoppedEventArgs.cs @@ -12,6 +12,7 @@ namespace Emby.Dlna.PlayTo public class MediaChangedEventArgs : EventArgs { public uBaseObject OldMediaInfo { get; set; } + public uBaseObject NewMediaInfo { get; set; } } } diff --git a/Emby.Dlna/PlayTo/uBaseObject.cs b/Emby.Dlna/PlayTo/uBaseObject.cs index a8ed5692c9..05c19299f1 100644 --- a/Emby.Dlna/PlayTo/uBaseObject.cs +++ b/Emby.Dlna/PlayTo/uBaseObject.cs @@ -44,10 +44,12 @@ namespace Emby.Dlna.PlayTo { return MediaBrowser.Model.Entities.MediaType.Audio; } + if (classType.IndexOf(MediaBrowser.Model.Entities.MediaType.Video, StringComparison.Ordinal) != -1) { return MediaBrowser.Model.Entities.MediaType.Video; } + if (classType.IndexOf("image", StringComparison.Ordinal) != -1) { return MediaBrowser.Model.Entities.MediaType.Photo; diff --git a/Emby.Dlna/Server/DescriptionXmlBuilder.cs b/Emby.Dlna/Server/DescriptionXmlBuilder.cs index 5ecc81a2f1..7143c31094 100644 --- a/Emby.Dlna/Server/DescriptionXmlBuilder.cs +++ b/Emby.Dlna/Server/DescriptionXmlBuilder.cs @@ -134,6 +134,7 @@ namespace Emby.Dlna.Server return result; } } + return c.ToString(CultureInfo.InvariantCulture); } @@ -157,18 +158,22 @@ namespace Emby.Dlna.Server { break; } + if (stringBuilder == null) { stringBuilder = new StringBuilder(); } + stringBuilder.Append(str, num, num2 - num); stringBuilder.Append(GetEscapeSequence(str[num2])); num = num2 + 1; } + if (stringBuilder == null) { return str; } + stringBuilder.Append(str, num, length - num); return stringBuilder.ToString(); } diff --git a/Emby.Dlna/Service/BaseControlHandler.cs b/Emby.Dlna/Service/BaseControlHandler.cs index 161a3434c5..699d325eac 100644 --- a/Emby.Dlna/Service/BaseControlHandler.cs +++ b/Emby.Dlna/Service/BaseControlHandler.cs @@ -18,6 +18,7 @@ namespace Emby.Dlna.Service private const string NS_SOAPENV = "http://schemas.xmlsoap.org/soap/envelope/"; protected IServerConfigurationManager Config { get; } + protected ILogger Logger { get; } protected BaseControlHandler(IServerConfigurationManager config, ILogger logger) @@ -135,6 +136,7 @@ namespace Emby.Dlna.Service break; } + default: { await reader.SkipAsync().ConfigureAwait(false); @@ -211,7 +213,9 @@ namespace Emby.Dlna.Service private class ControlRequestInfo { public string LocalName { get; set; } + public string NamespaceURI { get; set; } + public Dictionary Headers { get; } = new Dictionary(StringComparer.OrdinalIgnoreCase); } diff --git a/Emby.Dlna/Service/ServiceXmlBuilder.cs b/Emby.Dlna/Service/ServiceXmlBuilder.cs index 62ffd9e42a..af557aa144 100644 --- a/Emby.Dlna/Service/ServiceXmlBuilder.cs +++ b/Emby.Dlna/Service/ServiceXmlBuilder.cs @@ -80,6 +80,7 @@ namespace Emby.Dlna.Service { builder.Append("" + DescriptionXmlBuilder.Escape(allowedValue) + ""); } + builder.Append(""); } diff --git a/Emby.Naming/AudioBook/AudioBookFilePathParser.cs b/Emby.Naming/AudioBook/AudioBookFilePathParser.cs index 5494df9d63..3c874c62ca 100644 --- a/Emby.Naming/AudioBook/AudioBookFilePathParser.cs +++ b/Emby.Naming/AudioBook/AudioBookFilePathParser.cs @@ -64,6 +64,7 @@ namespace Emby.Naming.AudioBook { result.ChapterNumber = int.Parse(matches[0].Groups[0].Value); } + if (matches.Count > 1) { result.PartNumber = int.Parse(matches[matches.Count - 1].Groups[0].Value); diff --git a/Emby.Server.Implementations/Data/SqliteItemRepository.cs b/Emby.Server.Implementations/Data/SqliteItemRepository.cs index d331256611..f09ecaa297 100644 --- a/Emby.Server.Implementations/Data/SqliteItemRepository.cs +++ b/Emby.Server.Implementations/Data/SqliteItemRepository.cs @@ -793,6 +793,7 @@ namespace Emby.Server.Implementations.Data { saveItemStatement.TryBindNull("@Width"); } + if (item.Height > 0) { saveItemStatement.TryBind("@Height", item.Height); @@ -932,6 +933,7 @@ namespace Emby.Server.Implementations.Data { saveItemStatement.TryBindNull("@SeriesName"); } + if (string.IsNullOrWhiteSpace(userDataKey)) { saveItemStatement.TryBindNull("@UserDataKey"); @@ -1007,6 +1009,7 @@ namespace Emby.Server.Implementations.Data { artists = string.Join("|", hasArtists.Artists); } + saveItemStatement.TryBind("@Artists", artists); string albumArtists = null; @@ -1106,6 +1109,7 @@ namespace Emby.Server.Implementations.Data { continue; } + str.Append(ToValueString(i) + "|"); } @@ -1366,6 +1370,7 @@ namespace Emby.Server.Implementations.Data hasStartDate.StartDate = reader[index].ReadDateTime(); } } + index++; } @@ -1373,12 +1378,14 @@ namespace Emby.Server.Implementations.Data { item.EndDate = reader[index].TryReadDateTime(); } + index++; if (!reader.IsDBNull(index)) { item.ChannelId = new Guid(reader.GetString(index)); } + index++; if (enableProgramAttributes) @@ -1389,24 +1396,28 @@ namespace Emby.Server.Implementations.Data { hasProgramAttributes.IsMovie = reader.GetBoolean(index); } + index++; if (!reader.IsDBNull(index)) { hasProgramAttributes.IsSeries = reader.GetBoolean(index); } + index++; if (!reader.IsDBNull(index)) { hasProgramAttributes.EpisodeTitle = reader.GetString(index); } + index++; if (!reader.IsDBNull(index)) { hasProgramAttributes.IsRepeat = reader.GetBoolean(index); } + index++; } else @@ -1419,6 +1430,7 @@ namespace Emby.Server.Implementations.Data { item.CommunityRating = reader.GetFloat(index); } + index++; if (HasField(query, ItemFields.CustomRating)) @@ -1427,6 +1439,7 @@ namespace Emby.Server.Implementations.Data { item.CustomRating = reader.GetString(index); } + index++; } @@ -1434,6 +1447,7 @@ namespace Emby.Server.Implementations.Data { item.IndexNumber = reader.GetInt32(index); } + index++; if (HasField(query, ItemFields.Settings)) @@ -1442,18 +1456,21 @@ namespace Emby.Server.Implementations.Data { item.IsLocked = reader.GetBoolean(index); } + index++; if (!reader.IsDBNull(index)) { item.PreferredMetadataLanguage = reader.GetString(index); } + index++; if (!reader.IsDBNull(index)) { item.PreferredMetadataCountryCode = reader.GetString(index); } + index++; } @@ -1463,6 +1480,7 @@ namespace Emby.Server.Implementations.Data { item.Width = reader.GetInt32(index); } + index++; } @@ -1472,6 +1490,7 @@ namespace Emby.Server.Implementations.Data { item.Height = reader.GetInt32(index); } + index++; } @@ -1481,6 +1500,7 @@ namespace Emby.Server.Implementations.Data { item.DateLastRefreshed = reader[index].ReadDateTime(); } + index++; } @@ -1488,18 +1508,21 @@ namespace Emby.Server.Implementations.Data { item.Name = reader.GetString(index); } + index++; if (!reader.IsDBNull(index)) { item.Path = RestorePath(reader.GetString(index)); } + index++; if (!reader.IsDBNull(index)) { item.PremiereDate = reader[index].TryReadDateTime(); } + index++; if (HasField(query, ItemFields.Overview)) @@ -1508,6 +1531,7 @@ namespace Emby.Server.Implementations.Data { item.Overview = reader.GetString(index); } + index++; } @@ -1515,18 +1539,21 @@ namespace Emby.Server.Implementations.Data { item.ParentIndexNumber = reader.GetInt32(index); } + index++; if (!reader.IsDBNull(index)) { item.ProductionYear = reader.GetInt32(index); } + index++; if (!reader.IsDBNull(index)) { item.OfficialRating = reader.GetString(index); } + index++; if (HasField(query, ItemFields.SortName)) @@ -1535,6 +1562,7 @@ namespace Emby.Server.Implementations.Data { item.ForcedSortName = reader.GetString(index); } + index++; } @@ -1542,12 +1570,14 @@ namespace Emby.Server.Implementations.Data { item.RunTimeTicks = reader.GetInt64(index); } + index++; if (!reader.IsDBNull(index)) { item.Size = reader.GetInt64(index); } + index++; if (HasField(query, ItemFields.DateCreated)) @@ -1556,6 +1586,7 @@ namespace Emby.Server.Implementations.Data { item.DateCreated = reader[index].ReadDateTime(); } + index++; } @@ -1563,6 +1594,7 @@ namespace Emby.Server.Implementations.Data { item.DateModified = reader[index].ReadDateTime(); } + index++; item.Id = reader.GetGuid(index); @@ -1574,6 +1606,7 @@ namespace Emby.Server.Implementations.Data { item.Genres = reader.GetString(index).Split(new[] { '|' }, StringSplitOptions.RemoveEmptyEntries); } + index++; } @@ -1581,6 +1614,7 @@ namespace Emby.Server.Implementations.Data { item.ParentId = reader.GetGuid(index); } + index++; if (!reader.IsDBNull(index)) @@ -1590,6 +1624,7 @@ namespace Emby.Server.Implementations.Data item.Audio = audio; } } + index++; // TODO: Even if not needed by apps, the server needs it internally @@ -1603,6 +1638,7 @@ namespace Emby.Server.Implementations.Data liveTvChannel.ServiceName = reader.GetString(index); } } + index++; } @@ -1610,6 +1646,7 @@ namespace Emby.Server.Implementations.Data { item.IsInMixedFolder = reader.GetBoolean(index); } + index++; if (HasField(query, ItemFields.DateLastSaved)) @@ -1618,6 +1655,7 @@ namespace Emby.Server.Implementations.Data { item.DateLastSaved = reader[index].ReadDateTime(); } + index++; } @@ -1635,8 +1673,10 @@ namespace Emby.Server.Implementations.Data } } } + item.LockedFields = GetLockedFields(reader.GetString(index)).ToArray(); } + index++; } @@ -1646,6 +1686,7 @@ namespace Emby.Server.Implementations.Data { item.Studios = reader.GetString(index).Split(new[] { '|' }, StringSplitOptions.RemoveEmptyEntries); } + index++; } @@ -1655,6 +1696,7 @@ namespace Emby.Server.Implementations.Data { item.Tags = reader.GetString(index).Split(new[] { '|' }, StringSplitOptions.RemoveEmptyEntries); } + index++; } @@ -1674,9 +1716,11 @@ namespace Emby.Server.Implementations.Data } } } + trailer.TrailerTypes = GetTrailerTypes(reader.GetString(index)).ToArray(); } } + index++; } @@ -1686,6 +1730,7 @@ namespace Emby.Server.Implementations.Data { item.OriginalTitle = reader.GetString(index); } + index++; } @@ -1696,6 +1741,7 @@ namespace Emby.Server.Implementations.Data video.PrimaryVersionId = reader.GetString(index); } } + index++; if (HasField(query, ItemFields.DateLastMediaAdded)) @@ -1704,6 +1750,7 @@ namespace Emby.Server.Implementations.Data { folder.DateLastMediaAdded = reader[index].TryReadDateTime(); } + index++; } @@ -1711,18 +1758,21 @@ namespace Emby.Server.Implementations.Data { item.Album = reader.GetString(index); } + index++; if (!reader.IsDBNull(index)) { item.CriticRating = reader.GetFloat(index); } + index++; if (!reader.IsDBNull(index)) { item.IsVirtualItem = reader.GetBoolean(index); } + index++; if (item is IHasSeries hasSeriesName) @@ -1732,6 +1782,7 @@ namespace Emby.Server.Implementations.Data hasSeriesName.SeriesName = reader.GetString(index); } } + index++; if (hasEpisodeAttributes) @@ -1742,6 +1793,7 @@ namespace Emby.Server.Implementations.Data { episode.SeasonName = reader.GetString(index); } + index++; if (!reader.IsDBNull(index)) { @@ -1752,6 +1804,7 @@ namespace Emby.Server.Implementations.Data { index++; } + index++; } @@ -1765,6 +1818,7 @@ namespace Emby.Server.Implementations.Data hasSeries.SeriesId = reader.GetGuid(index); } } + index++; } @@ -1774,6 +1828,7 @@ namespace Emby.Server.Implementations.Data { item.PresentationUniqueKey = reader.GetString(index); } + index++; } @@ -1783,6 +1838,7 @@ namespace Emby.Server.Implementations.Data { item.InheritedParentalRatingValue = reader.GetInt32(index); } + index++; } @@ -1792,6 +1848,7 @@ namespace Emby.Server.Implementations.Data { item.ExternalSeriesId = reader.GetString(index); } + index++; } @@ -1801,6 +1858,7 @@ namespace Emby.Server.Implementations.Data { item.Tagline = reader.GetString(index); } + index++; } @@ -1808,6 +1866,7 @@ namespace Emby.Server.Implementations.Data { DeserializeProviderIds(reader.GetString(index), item); } + index++; if (query.DtoOptions.EnableImages) @@ -1816,6 +1875,7 @@ namespace Emby.Server.Implementations.Data { DeserializeImages(reader.GetString(index), item); } + index++; } @@ -1825,6 +1885,7 @@ namespace Emby.Server.Implementations.Data { item.ProductionLocations = reader.GetString(index).Split(new[] { '|' }, StringSplitOptions.RemoveEmptyEntries).ToArray(); } + index++; } @@ -1834,6 +1895,7 @@ namespace Emby.Server.Implementations.Data { item.ExtraIds = SplitToGuids(reader.GetString(index)); } + index++; } @@ -1841,6 +1903,7 @@ namespace Emby.Server.Implementations.Data { item.TotalBitrate = reader.GetInt32(index); } + index++; if (!reader.IsDBNull(index)) @@ -1850,6 +1913,7 @@ namespace Emby.Server.Implementations.Data item.ExtraType = extraType; } } + index++; if (hasArtistFields) @@ -1858,12 +1922,14 @@ namespace Emby.Server.Implementations.Data { hasArtists.Artists = reader.GetString(index).Split(new[] { '|' }, StringSplitOptions.RemoveEmptyEntries); } + index++; if (item is IHasAlbumArtist hasAlbumArtists && !reader.IsDBNull(index)) { hasAlbumArtists.AlbumArtists = reader.GetString(index).Split(new[] { '|' }, StringSplitOptions.RemoveEmptyEntries); } + index++; } @@ -1871,6 +1937,7 @@ namespace Emby.Server.Implementations.Data { item.ExternalId = reader.GetString(index); } + index++; if (HasField(query, ItemFields.SeriesPresentationUniqueKey)) @@ -1882,6 +1949,7 @@ namespace Emby.Server.Implementations.Data hasSeries.SeriesPresentationUniqueKey = reader.GetString(index); } } + index++; } @@ -1891,6 +1959,7 @@ namespace Emby.Server.Implementations.Data { program.ShowId = reader.GetString(index); } + index++; } @@ -1898,6 +1967,7 @@ namespace Emby.Server.Implementations.Data { item.OwnerId = reader.GetGuid(index); } + index++; return item; @@ -2473,6 +2543,7 @@ namespace Emby.Server.Implementations.Data { statement.TryBind("@SearchTermStartsWith", searchTerm + "%"); } + if (commandText.IndexOf("@SearchTermContains", StringComparison.OrdinalIgnoreCase) != -1) { statement.TryBind("@SearchTermContains", "%" + searchTerm + "%"); @@ -2743,6 +2814,7 @@ namespace Emby.Server.Implementations.Data { items[i] = newItem; } + return; } } @@ -2835,6 +2907,7 @@ namespace Emby.Server.Implementations.Data { statementTexts.Add(commandText); } + if (query.EnableTotalRecordCount) { commandText = string.Empty; @@ -3239,6 +3312,7 @@ namespace Emby.Server.Implementations.Data { statementTexts.Add(commandText); } + if (query.EnableTotalRecordCount) { commandText = string.Empty; @@ -3592,11 +3666,13 @@ namespace Emby.Server.Implementations.Data whereClauses.Add("IndexNumber=@IndexNumber"); statement?.TryBind("@IndexNumber", query.IndexNumber.Value); } + if (query.ParentIndexNumber.HasValue) { whereClauses.Add("ParentIndexNumber=@ParentIndexNumber"); statement?.TryBind("@ParentIndexNumber", query.ParentIndexNumber.Value); } + if (query.ParentIndexNumberNotEquals.HasValue) { whereClauses.Add("(ParentIndexNumber<>@ParentIndexNumberNotEquals or ParentIndexNumber is null)"); @@ -3882,6 +3958,7 @@ namespace Emby.Server.Implementations.Data { statement.TryBind(paramName, artistId.ToByteArray()); } + index++; } @@ -3902,6 +3979,7 @@ namespace Emby.Server.Implementations.Data { statement.TryBind(paramName, artistId.ToByteArray()); } + index++; } @@ -3922,8 +4000,10 @@ namespace Emby.Server.Implementations.Data { statement.TryBind(paramName, artistId.ToByteArray()); } + index++; } + var clause = "(" + string.Join(" OR ", clauses) + ")"; whereClauses.Add(clause); } @@ -3941,8 +4021,10 @@ namespace Emby.Server.Implementations.Data { statement.TryBind(paramName, albumId.ToByteArray()); } + index++; } + var clause = "(" + string.Join(" OR ", clauses) + ")"; whereClauses.Add(clause); } @@ -3960,8 +4042,10 @@ namespace Emby.Server.Implementations.Data { statement.TryBind(paramName, artistId.ToByteArray()); } + index++; } + var clause = "(" + string.Join(" OR ", clauses) + ")"; whereClauses.Add(clause); } @@ -3979,8 +4063,10 @@ namespace Emby.Server.Implementations.Data { statement.TryBind(paramName, genreId.ToByteArray()); } + index++; } + var clause = "(" + string.Join(" OR ", clauses) + ")"; whereClauses.Add(clause); } @@ -3996,8 +4082,10 @@ namespace Emby.Server.Implementations.Data { statement.TryBind("@Genre" + index, GetCleanValue(item)); } + index++; } + var clause = "(" + string.Join(" OR ", clauses) + ")"; whereClauses.Add(clause); } @@ -4013,8 +4101,10 @@ namespace Emby.Server.Implementations.Data { statement.TryBind("@Tag" + index, GetCleanValue(item)); } + index++; } + var clause = "(" + string.Join(" OR ", clauses) + ")"; whereClauses.Add(clause); } @@ -4030,8 +4120,10 @@ namespace Emby.Server.Implementations.Data { statement.TryBind("@ExcludeTag" + index, GetCleanValue(item)); } + index++; } + var clause = "(" + string.Join(" OR ", clauses) + ")"; whereClauses.Add(clause); } @@ -4050,8 +4142,10 @@ namespace Emby.Server.Implementations.Data { statement.TryBind(paramName, studioId.ToByteArray()); } + index++; } + var clause = "(" + string.Join(" OR ", clauses) + ")"; whereClauses.Add(clause); } @@ -4067,8 +4161,10 @@ namespace Emby.Server.Implementations.Data { statement.TryBind("@OfficialRating" + index, item); } + index++; } + var clause = "(" + string.Join(" OR ", clauses) + ")"; whereClauses.Add(clause); } @@ -4243,6 +4339,7 @@ namespace Emby.Server.Implementations.Data statement.TryBind("@IsVirtualItem", isVirtualItem.Value); } } + if (query.IsSpecialSeason.HasValue) { if (query.IsSpecialSeason.Value) @@ -4254,6 +4351,7 @@ namespace Emby.Server.Implementations.Data whereClauses.Add("IndexNumber <> 0"); } } + if (query.IsUnaired.HasValue) { if (query.IsUnaired.Value) @@ -4265,6 +4363,7 @@ namespace Emby.Server.Implementations.Data whereClauses.Add("PremiereDate < DATETIME('now')"); } } + var queryMediaTypes = query.MediaTypes.Where(IsValidMediaType).ToArray(); if (queryMediaTypes.Length == 1) { @@ -4280,6 +4379,7 @@ namespace Emby.Server.Implementations.Data whereClauses.Add("MediaType in (" + val + ")"); } + if (query.ItemIds.Length > 0) { var includeIds = new List(); @@ -4292,11 +4392,13 @@ namespace Emby.Server.Implementations.Data { statement.TryBind("@IncludeId" + index, id); } + index++; } whereClauses.Add("(" + string.Join(" OR ", includeIds) + ")"); } + if (query.ExcludeItemIds.Length > 0) { var excludeIds = new List(); @@ -4309,6 +4411,7 @@ namespace Emby.Server.Implementations.Data { statement.TryBind("@ExcludeId" + index, id); } + index++; } @@ -4333,6 +4436,7 @@ namespace Emby.Server.Implementations.Data { statement.TryBind(paramName, "%" + pair.Key + "=" + pair.Value + "%"); } + index++; break; @@ -4375,6 +4479,7 @@ namespace Emby.Server.Implementations.Data { statement.TryBind(paramName, "%" + pair.Key + "=" + pair.Value + "%"); } + index++; break; @@ -4425,6 +4530,7 @@ namespace Emby.Server.Implementations.Data { whereClauses.Add("(TopParentId=@TopParentId)"); } + if (statement != null) { statement.TryBind("@TopParentId", queryTopParentIds[0].ToString("N", CultureInfo.InvariantCulture)); @@ -4462,11 +4568,13 @@ namespace Emby.Server.Implementations.Data statement.TryBind("@AncestorId", query.AncestorIds[0]); } } + if (query.AncestorIds.Length > 1) { var inClause = string.Join(",", query.AncestorIds.Select(i => "'" + i.ToString("N", CultureInfo.InvariantCulture) + "'")); whereClauses.Add(string.Format("Guid in (select itemId from AncestorIds where AncestorIdText in ({0}))", inClause)); } + if (!string.IsNullOrWhiteSpace(query.AncestorWithPresentationUniqueKey)) { var inClause = "select guid from TypedBaseItems where PresentationUniqueKey=@AncestorWithPresentationUniqueKey"; @@ -4495,6 +4603,7 @@ namespace Emby.Server.Implementations.Data statement.TryBind("@UnratedType", query.BlockUnratedItems[0].ToString()); } } + if (query.BlockUnratedItems.Length > 1) { var inClause = string.Join(",", query.BlockUnratedItems.Select(i => "'" + i.ToString() + "'")); @@ -4969,6 +5078,7 @@ where AncestorIdText not null and ItemValues.Value not null and ItemValues.Type statement.TryBind("@ItemId", query.ItemId.ToByteArray()); } } + if (!query.AppearsInItemId.Equals(Guid.Empty)) { whereClauses.Add("Name in (Select Name from People where ItemId=@AppearsInItemId)"); @@ -4977,6 +5087,7 @@ where AncestorIdText not null and ItemValues.Value not null and ItemValues.Type statement.TryBind("@AppearsInItemId", query.AppearsInItemId.ToByteArray()); } } + var queryPersonTypes = query.PersonTypes.Where(IsValidPersonType).ToList(); if (queryPersonTypes.Count == 1) @@ -4993,6 +5104,7 @@ where AncestorIdText not null and ItemValues.Value not null and ItemValues.Type whereClauses.Add("PersonType in (" + val + ")"); } + var queryExcludePersonTypes = query.ExcludePersonTypes.Where(IsValidPersonType).ToList(); if (queryExcludePersonTypes.Count == 1) @@ -5009,6 +5121,7 @@ where AncestorIdText not null and ItemValues.Value not null and ItemValues.Type whereClauses.Add("PersonType not in (" + val + ")"); } + if (query.MaxListOrder.HasValue) { whereClauses.Add("ListOrder<=@MaxListOrder"); @@ -5017,6 +5130,7 @@ where AncestorIdText not null and ItemValues.Value not null and ItemValues.Type statement.TryBind("@MaxListOrder", query.MaxListOrder.Value); } } + if (!string.IsNullOrWhiteSpace(query.NameContains)) { whereClauses.Add("Name like @NameContains"); @@ -5156,6 +5270,7 @@ where AncestorIdText not null and ItemValues.Value not null and ItemValues.Type var typeString = string.Join(",", withItemTypes.Select(i => "'" + i + "'")); commandText += " AND ItemId In (select guid from typedbaseitems where type in (" + typeString + "))"; } + if (excludeItemTypes.Count > 0) { var typeString = string.Join(",", excludeItemTypes.Select(i => "'" + i + "'")); diff --git a/Emby.Server.Implementations/Data/SqliteUserDataRepository.cs b/Emby.Server.Implementations/Data/SqliteUserDataRepository.cs index 7e66fa072e..023125c924 100644 --- a/Emby.Server.Implementations/Data/SqliteUserDataRepository.cs +++ b/Emby.Server.Implementations/Data/SqliteUserDataRepository.cs @@ -135,10 +135,12 @@ namespace Emby.Server.Implementations.Data { throw new ArgumentNullException(nameof(userData)); } + if (internalUserId <= 0) { throw new ArgumentNullException(nameof(internalUserId)); } + if (string.IsNullOrEmpty(key)) { throw new ArgumentNullException(nameof(key)); @@ -153,6 +155,7 @@ namespace Emby.Server.Implementations.Data { throw new ArgumentNullException(nameof(userData)); } + if (internalUserId <= 0) { throw new ArgumentNullException(nameof(internalUserId)); diff --git a/Emby.Server.Implementations/Devices/DeviceManager.cs b/Emby.Server.Implementations/Devices/DeviceManager.cs index 789cdfc119..e75745cc6e 100644 --- a/Emby.Server.Implementations/Devices/DeviceManager.cs +++ b/Emby.Server.Implementations/Devices/DeviceManager.cs @@ -169,6 +169,7 @@ namespace Emby.Server.Implementations.Devices { throw new ArgumentException("user not found"); } + if (string.IsNullOrEmpty(deviceId)) { throw new ArgumentNullException(nameof(deviceId)); diff --git a/Emby.Server.Implementations/Dto/DtoService.cs b/Emby.Server.Implementations/Dto/DtoService.cs index 41ff7e3abf..f5a58cc6d6 100644 --- a/Emby.Server.Implementations/Dto/DtoService.cs +++ b/Emby.Server.Implementations/Dto/DtoService.cs @@ -277,6 +277,7 @@ namespace Emby.Server.Implementations.Dto dto.EpisodeTitle = dto.Name; dto.Name = dto.SeriesName; } + liveTvManager.AddInfoToRecordingDto(item, dto, activeRecording, user); } @@ -292,6 +293,7 @@ namespace Emby.Server.Implementations.Dto { continue; } + var containers = container.Split(new[] { ',' }); if (containers.Length < 2) { @@ -456,6 +458,7 @@ namespace Emby.Server.Implementations.Dto { dto.SeriesName = item.SeriesName; } + private static void SetPhotoProperties(BaseItemDto dto, Photo item) { dto.CameraMake = item.CameraMake; @@ -554,22 +557,27 @@ namespace Emby.Server.Implementations.Dto { return 0; } + if (i.IsType(PersonType.GuestStar)) { return 1; } + if (i.IsType(PersonType.Director)) { return 2; } + if (i.IsType(PersonType.Writer)) { return 3; } + if (i.IsType(PersonType.Producer)) { return 4; } + if (i.IsType(PersonType.Composer)) { return 4; @@ -1346,6 +1354,7 @@ namespace Emby.Server.Implementations.Dto dto.ParentLogoImageTag = GetTagAndFillBlurhash(dto, parent, image); } } + if (artLimit > 0 && !(imageTags != null && imageTags.ContainsKey(ImageType.Art)) && dto.ParentArtItemId == null) { var image = allImages.FirstOrDefault(i => i.Type == ImageType.Art); @@ -1356,6 +1365,7 @@ namespace Emby.Server.Implementations.Dto dto.ParentArtImageTag = GetTagAndFillBlurhash(dto, parent, image); } } + if (thumbLimit > 0 && !(imageTags != null && imageTags.ContainsKey(ImageType.Thumb)) && (dto.ParentThumbItemId == null || parent is Series) && !(parent is ICollectionFolder) && !(parent is UserView)) { var image = allImages.FirstOrDefault(i => i.Type == ImageType.Thumb); @@ -1366,6 +1376,7 @@ namespace Emby.Server.Implementations.Dto dto.ParentThumbImageTag = GetTagAndFillBlurhash(dto, parent, image); } } + if (backdropLimit > 0 && !((dto.BackdropImageTags != null && dto.BackdropImageTags.Length > 0) || (dto.ParentBackdropImageTags != null && dto.ParentBackdropImageTags.Length > 0))) { var images = allImages.Where(i => i.Type == ImageType.Backdrop).Take(backdropLimit).ToList(); diff --git a/Emby.Server.Implementations/HttpServer/HttpListenerHost.cs b/Emby.Server.Implementations/HttpServer/HttpListenerHost.cs index 1b6e4b5547..e52acc5489 100644 --- a/Emby.Server.Implementations/HttpServer/HttpListenerHost.cs +++ b/Emby.Server.Implementations/HttpServer/HttpListenerHost.cs @@ -453,6 +453,7 @@ namespace Emby.Server.Implementations.HttpServer { httpRes.Headers.Add(key, value); } + httpRes.ContentType = "text/plain"; await httpRes.WriteAsync(string.Empty, cancellationToken).ConfigureAwait(false); return; diff --git a/Emby.Server.Implementations/HttpServer/RangeRequestWriter.cs b/Emby.Server.Implementations/HttpServer/RangeRequestWriter.cs index 8b9028f6bc..94cedb918f 100644 --- a/Emby.Server.Implementations/HttpServer/RangeRequestWriter.cs +++ b/Emby.Server.Implementations/HttpServer/RangeRequestWriter.cs @@ -20,15 +20,21 @@ namespace Emby.Server.Implementations.HttpServer /// /// The source stream. private Stream SourceStream { get; set; } + private string RangeHeader { get; set; } + private bool IsHeadRequest { get; set; } private long RangeStart { get; set; } + private long RangeEnd { get; set; } + private long RangeLength { get; set; } + private long TotalContentLength { get; set; } public Action OnComplete { get; set; } + private readonly ILogger _logger; private const int BufferSize = 81920; @@ -139,6 +145,7 @@ namespace Emby.Server.Implementations.HttpServer { start = long.Parse(vals[0], UsCulture); } + if (!string.IsNullOrEmpty(vals[1])) { end = long.Parse(vals[1], UsCulture); diff --git a/Emby.Server.Implementations/HttpServer/Security/AuthService.cs b/Emby.Server.Implementations/HttpServer/Security/AuthService.cs index 72959003a6..2e6ff65a6f 100644 --- a/Emby.Server.Implementations/HttpServer/Security/AuthService.cs +++ b/Emby.Server.Implementations/HttpServer/Security/AuthService.cs @@ -140,6 +140,7 @@ namespace Emby.Server.Implementations.HttpServer.Security { return true; } + if (authAttribtues.AllowLocalOnly && request.IsLocal) { return true; diff --git a/Emby.Server.Implementations/HttpServer/Security/AuthorizationContext.cs b/Emby.Server.Implementations/HttpServer/Security/AuthorizationContext.cs index 4dffcd92d4..bbade00ff3 100644 --- a/Emby.Server.Implementations/HttpServer/Security/AuthorizationContext.cs +++ b/Emby.Server.Implementations/HttpServer/Security/AuthorizationContext.cs @@ -71,6 +71,7 @@ namespace Emby.Server.Implementations.HttpServer.Security { token = httpReq.Headers["X-MediaBrowser-Token"]; } + if (string.IsNullOrEmpty(token)) { token = httpReq.QueryString["api_key"]; @@ -160,6 +161,7 @@ namespace Emby.Server.Implementations.HttpServer.Security _authRepo.Update(tokenInfo); } } + httpReq.Items["OriginalAuthenticationInfo"] = tokenInfo; } diff --git a/Emby.Server.Implementations/IO/ManagedFileSystem.cs b/Emby.Server.Implementations/IO/ManagedFileSystem.cs index a7bbf6acc8..a3a3f91b72 100644 --- a/Emby.Server.Implementations/IO/ManagedFileSystem.cs +++ b/Emby.Server.Implementations/IO/ManagedFileSystem.cs @@ -628,6 +628,7 @@ namespace Emby.Server.Implementations.IO { return false; } + return extensions.Contains(ext, StringComparer.OrdinalIgnoreCase); }); } @@ -682,6 +683,7 @@ namespace Emby.Server.Implementations.IO { return false; } + return extensions.Contains(ext, StringComparer.OrdinalIgnoreCase); }); } diff --git a/Emby.Server.Implementations/Library/ExclusiveLiveStream.cs b/Emby.Server.Implementations/Library/ExclusiveLiveStream.cs index 9a71868988..ab39a7223d 100644 --- a/Emby.Server.Implementations/Library/ExclusiveLiveStream.cs +++ b/Emby.Server.Implementations/Library/ExclusiveLiveStream.cs @@ -12,11 +12,13 @@ namespace Emby.Server.Implementations.Library public class ExclusiveLiveStream : ILiveStream { public int ConsumerCount { get; set; } + public string OriginalStreamId { get; set; } public string TunerHostId => null; public bool EnableStreamSharing { get; set; } + public MediaSourceInfo MediaSource { get; set; } public string UniqueId { get; private set; } diff --git a/Emby.Server.Implementations/Library/LibraryManager.cs b/Emby.Server.Implementations/Library/LibraryManager.cs index 1d4651da20..46f4332829 100644 --- a/Emby.Server.Implementations/Library/LibraryManager.cs +++ b/Emby.Server.Implementations/Library/LibraryManager.cs @@ -2784,10 +2784,12 @@ namespace Emby.Server.Implementations.Library { throw new ArgumentNullException(nameof(path)); } + if (string.IsNullOrWhiteSpace(from)) { throw new ArgumentNullException(nameof(from)); } + if (string.IsNullOrWhiteSpace(to)) { throw new ArgumentNullException(nameof(to)); diff --git a/Emby.Server.Implementations/Library/MediaSourceManager.cs b/Emby.Server.Implementations/Library/MediaSourceManager.cs index 919261027d..ceb36b389b 100644 --- a/Emby.Server.Implementations/Library/MediaSourceManager.cs +++ b/Emby.Server.Implementations/Library/MediaSourceManager.cs @@ -205,22 +205,27 @@ namespace Emby.Server.Implementations.Library { return MediaProtocol.Rtsp; } + if (path.StartsWith("Rtmp", StringComparison.OrdinalIgnoreCase)) { return MediaProtocol.Rtmp; } + if (path.StartsWith("Http", StringComparison.OrdinalIgnoreCase)) { return MediaProtocol.Http; } + if (path.StartsWith("rtp", StringComparison.OrdinalIgnoreCase)) { return MediaProtocol.Rtp; } + if (path.StartsWith("ftp", StringComparison.OrdinalIgnoreCase)) { return MediaProtocol.Ftp; } + if (path.StartsWith("udp", StringComparison.OrdinalIgnoreCase)) { return MediaProtocol.Udp; diff --git a/Emby.Server.Implementations/Library/Resolvers/SpecialFolderResolver.cs b/Emby.Server.Implementations/Library/Resolvers/SpecialFolderResolver.cs index 4819f2fc0f..99f3041909 100644 --- a/Emby.Server.Implementations/Library/Resolvers/SpecialFolderResolver.cs +++ b/Emby.Server.Implementations/Library/Resolvers/SpecialFolderResolver.cs @@ -41,10 +41,12 @@ namespace Emby.Server.Implementations.Library.Resolvers { return new AggregateFolder(); } + if (string.Equals(args.Path, _appPaths.DefaultUserViewsPath, StringComparison.OrdinalIgnoreCase)) { return new UserRootFolder(); // if we got here and still a root - must be user root } + if (args.IsVf) { return new CollectionFolder diff --git a/Emby.Server.Implementations/Library/Resolvers/TV/EpisodeResolver.cs b/Emby.Server.Implementations/Library/Resolvers/TV/EpisodeResolver.cs index 7f477a0f08..2f7af60c0d 100644 --- a/Emby.Server.Implementations/Library/Resolvers/TV/EpisodeResolver.cs +++ b/Emby.Server.Implementations/Library/Resolvers/TV/EpisodeResolver.cs @@ -55,6 +55,7 @@ namespace Emby.Server.Implementations.Library.Resolvers.TV episode.SeriesId = series.Id; episode.SeriesName = series.Name; } + if (season != null) { episode.SeasonId = season.Id; diff --git a/Emby.Server.Implementations/Library/SearchEngine.cs b/Emby.Server.Implementations/Library/SearchEngine.cs index b8c42cdf8a..3df9cc06f1 100644 --- a/Emby.Server.Implementations/Library/SearchEngine.cs +++ b/Emby.Server.Implementations/Library/SearchEngine.cs @@ -194,6 +194,7 @@ namespace Emby.Server.Implementations.Library { searchQuery.AncestorIds = new[] { searchQuery.ParentId }; } + searchQuery.ParentId = Guid.Empty; searchQuery.IncludeItemsByName = true; searchQuery.IncludeItemTypes = Array.Empty(); diff --git a/Emby.Server.Implementations/LiveTv/Listings/SchedulesDirect.cs b/Emby.Server.Implementations/LiveTv/Listings/SchedulesDirect.cs index fdd305f862..3709f8fe47 100644 --- a/Emby.Server.Implementations/LiveTv/Listings/SchedulesDirect.cs +++ b/Emby.Server.Implementations/LiveTv/Listings/SchedulesDirect.cs @@ -212,6 +212,7 @@ namespace Emby.Server.Implementations.LiveTv.Listings { channelNumber = map.channel; } + if (string.IsNullOrWhiteSpace(channelNumber)) { channelNumber = map.atscMajor + "." + map.atscMinor; @@ -400,6 +401,7 @@ namespace Emby.Server.Implementations.LiveTv.Listings { date = DateTime.SpecifyKind(date, DateTimeKind.Utc); } + return date; } @@ -622,6 +624,7 @@ namespace Emby.Server.Implementations.LiveTv.Listings _lastErrorResponse = DateTime.UtcNow; } } + throw; } finally @@ -805,11 +808,13 @@ namespace Emby.Server.Implementations.LiveTv.Listings { throw new ArgumentException("Username is required"); } + if (string.IsNullOrEmpty(info.Password)) { throw new ArgumentException("Password is required"); } } + if (validateListings) { if (string.IsNullOrEmpty(info.ListingsId)) @@ -932,24 +937,35 @@ namespace Emby.Server.Implementations.LiveTv.Listings public class Token { public int code { get; set; } + public string message { get; set; } + public string serverID { get; set; } + public string token { get; set; } } + public class Lineup { public string lineup { get; set; } + public string name { get; set; } + public string transport { get; set; } + public string location { get; set; } + public string uri { get; set; } } public class Lineups { public int code { get; set; } + public string serverID { get; set; } + public string datetime { get; set; } + public List lineups { get; set; } } @@ -957,8 +973,11 @@ namespace Emby.Server.Implementations.LiveTv.Listings public class Headends { public string headend { get; set; } + public string transport { get; set; } + public string location { get; set; } + public List lineups { get; set; } } @@ -967,59 +986,83 @@ namespace Emby.Server.Implementations.LiveTv.Listings public class Map { public string stationID { get; set; } + public string channel { get; set; } + public string logicalChannelNumber { get; set; } + public int uhfVhf { get; set; } + public int atscMajor { get; set; } + public int atscMinor { get; set; } } public class Broadcaster { public string city { get; set; } + public string state { get; set; } + public string postalcode { get; set; } + public string country { get; set; } } public class Logo { public string URL { get; set; } + public int height { get; set; } + public int width { get; set; } + public string md5 { get; set; } } public class Station { public string stationID { get; set; } + public string name { get; set; } + public string callsign { get; set; } + public List broadcastLanguage { get; set; } + public List descriptionLanguage { get; set; } + public Broadcaster broadcaster { get; set; } + public string affiliate { get; set; } + public Logo logo { get; set; } + public bool? isCommercialFree { get; set; } } public class Metadata { public string lineup { get; set; } + public string modified { get; set; } + public string transport { get; set; } } public class Channel { public List map { get; set; } + public List stations { get; set; } + public Metadata metadata { get; set; } } public class RequestScheduleForChannel { public string stationID { get; set; } + public List date { get; set; } } @@ -1029,29 +1072,43 @@ namespace Emby.Server.Implementations.LiveTv.Listings public class Rating { public string body { get; set; } + public string code { get; set; } } public class Multipart { public int partNumber { get; set; } + public int totalParts { get; set; } } public class Program { public string programID { get; set; } + public string airDateTime { get; set; } + public int duration { get; set; } + public string md5 { get; set; } + public List audioProperties { get; set; } + public List videoProperties { get; set; } + public List ratings { get; set; } + public bool? @new { get; set; } + public Multipart multipart { get; set; } + public string liveTapeDelay { get; set; } + public bool premiere { get; set; } + public bool repeat { get; set; } + public string isPremiereOrFinale { get; set; } } @@ -1060,16 +1117,22 @@ namespace Emby.Server.Implementations.LiveTv.Listings public class MetadataSchedule { public string modified { get; set; } + public string md5 { get; set; } + public string startDate { get; set; } + public string endDate { get; set; } + public int days { get; set; } } public class Day { public string stationID { get; set; } + public List programs { get; set; } + public MetadataSchedule metadata { get; set; } public Day() @@ -1092,24 +1155,28 @@ namespace Emby.Server.Implementations.LiveTv.Listings public class Description100 { public string descriptionLanguage { get; set; } + public string description { get; set; } } public class Description1000 { public string descriptionLanguage { get; set; } + public string description { get; set; } } public class DescriptionsProgram { public List description100 { get; set; } + public List description1000 { get; set; } } public class Gracenote { public int season { get; set; } + public int episode { get; set; } } @@ -1121,101 +1188,152 @@ namespace Emby.Server.Implementations.LiveTv.Listings public class ContentRating { public string body { get; set; } + public string code { get; set; } } public class Cast { public string billingOrder { get; set; } + public string role { get; set; } + public string nameId { get; set; } + public string personId { get; set; } + public string name { get; set; } + public string characterName { get; set; } } public class Crew { public string billingOrder { get; set; } + public string role { get; set; } + public string nameId { get; set; } + public string personId { get; set; } + public string name { get; set; } } public class QualityRating { public string ratingsBody { get; set; } + public string rating { get; set; } + public string minRating { get; set; } + public string maxRating { get; set; } + public string increment { get; set; } } public class Movie { public string year { get; set; } + public int duration { get; set; } + public List qualityRating { get; set; } } public class Recommendation { public string programID { get; set; } + public string title120 { get; set; } } public class ProgramDetails { public string audience { get; set; } + public string programID { get; set; } + public List titles { get; set; } + public EventDetails eventDetails { get; set; } + public DescriptionsProgram descriptions { get; set; } + public string originalAirDate { get; set; } + public List<string> genres { get; set; } + public string episodeTitle150 { get; set; } + public List<MetadataPrograms> metadata { get; set; } + public List<ContentRating> contentRating { get; set; } + public List<Cast> cast { get; set; } + public List<Crew> crew { get; set; } + public string entityType { get; set; } + public string showType { get; set; } + public bool hasImageArtwork { get; set; } + public string primaryImage { get; set; } + public string thumbImage { get; set; } + public string backdropImage { get; set; } + public string bannerImage { get; set; } + public string imageID { get; set; } + public string md5 { get; set; } + public List<string> contentAdvisory { get; set; } + public Movie movie { get; set; } + public List<Recommendation> recommendations { get; set; } } public class Caption { public string content { get; set; } + public string lang { get; set; } } public class ImageData { public string width { get; set; } + public string height { get; set; } + public string uri { get; set; } + public string size { get; set; } + public string aspect { get; set; } + public string category { get; set; } + public string text { get; set; } + public string primary { get; set; } + public string tier { get; set; } + public Caption caption { get; set; } } public class ShowImages { public string programID { get; set; } + public List<ImageData> data { get; set; } } } diff --git a/Emby.Server.Implementations/LiveTv/Listings/XmlTvListingsProvider.cs b/Emby.Server.Implementations/LiveTv/Listings/XmlTvListingsProvider.cs index 077b5c7e50..0a93c46748 100644 --- a/Emby.Server.Implementations/LiveTv/Listings/XmlTvListingsProvider.cs +++ b/Emby.Server.Implementations/LiveTv/Listings/XmlTvListingsProvider.cs @@ -224,6 +224,7 @@ namespace Emby.Server.Implementations.LiveTv.Listings { uniqueString = "-" + programInfo.SeasonNumber.Value.ToString(CultureInfo.InvariantCulture); } + if (programInfo.EpisodeNumber.HasValue) { uniqueString = "-" + programInfo.EpisodeNumber.Value.ToString(CultureInfo.InvariantCulture); diff --git a/Emby.Server.Implementations/LiveTv/LiveTvManager.cs b/Emby.Server.Implementations/LiveTv/LiveTvManager.cs index 42e93b7ff6..4c1de3bccf 100644 --- a/Emby.Server.Implementations/LiveTv/LiveTvManager.cs +++ b/Emby.Server.Implementations/LiveTv/LiveTvManager.cs @@ -556,6 +556,7 @@ namespace Emby.Server.Implementations.LiveTv { forceUpdate = true; } + item.ParentId = channel.Id; // item.ChannelType = channelType; @@ -575,6 +576,7 @@ namespace Emby.Server.Implementations.LiveTv { forceUpdate = true; } + item.ExternalSeriesId = seriesId; var isSeries = info.IsSeries || !string.IsNullOrEmpty(info.EpisodeTitle); @@ -589,30 +591,37 @@ namespace Emby.Server.Implementations.LiveTv { tags.Add("Live"); } + if (info.IsPremiere) { tags.Add("Premiere"); } + if (info.IsNews) { tags.Add("News"); } + if (info.IsSports) { tags.Add("Sports"); } + if (info.IsKids) { tags.Add("Kids"); } + if (info.IsRepeat) { tags.Add("Repeat"); } + if (info.IsMovie) { tags.Add("Movie"); } + if (isSeries) { tags.Add("Series"); @@ -635,6 +644,7 @@ namespace Emby.Server.Implementations.LiveTv { forceUpdate = true; } + item.IsSeries = isSeries; item.Name = info.Name; @@ -652,12 +662,14 @@ namespace Emby.Server.Implementations.LiveTv { forceUpdate = true; } + item.StartDate = info.StartDate; if (item.EndDate != info.EndDate) { forceUpdate = true; } + item.EndDate = info.EndDate; item.ProductionYear = info.ProductionYear; diff --git a/Emby.Server.Implementations/LiveTv/TunerHosts/HdHomerun/HdHomerunHost.cs b/Emby.Server.Implementations/LiveTv/TunerHosts/HdHomerun/HdHomerunHost.cs index f14fcde2a2..dff113a2a7 100644 --- a/Emby.Server.Implementations/LiveTv/TunerHosts/HdHomerun/HdHomerunHost.cs +++ b/Emby.Server.Implementations/LiveTv/TunerHosts/HdHomerun/HdHomerunHost.cs @@ -170,6 +170,7 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun _modelCache[cacheKey] = response; } } + return response; } @@ -201,6 +202,7 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun var name = line.Substring(0, index - 1); var currentChannel = line.Substring(index + 7); if (currentChannel != "none") { status = LiveTvTunerStatus.LiveTv; } else { status = LiveTvTunerStatus.Available; } + tuners.Add(new LiveTvTunerInfo { Name = name, @@ -229,11 +231,13 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun inside = true; continue; } + if (let == '>') { inside = false; continue; } + if (!inside) { buffer[bufferIndex] = let; @@ -331,12 +335,19 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun private class Channels { public string GuideNumber { get; set; } + public string GuideName { get; set; } + public string VideoCodec { get; set; } + public string AudioCodec { get; set; } + public string URL { get; set; } + public bool Favorite { get; set; } + public bool DRM { get; set; } + public int HD { get; set; } } @@ -657,13 +668,21 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun public class DiscoverResponse { public string FriendlyName { get; set; } + public string ModelNumber { get; set; } + public string FirmwareName { get; set; } + public string FirmwareVersion { get; set; } + public string DeviceID { get; set; } + public string DeviceAuth { get; set; } + public string BaseURL { get; set; } + public string LineupURL { get; set; } + public int TunerCount { get; set; } public bool SupportsTranscoding diff --git a/Emby.Server.Implementations/LiveTv/TunerHosts/LiveStream.cs b/Emby.Server.Implementations/LiveTv/TunerHosts/LiveStream.cs index 4decdc24f8..0333e723bc 100644 --- a/Emby.Server.Implementations/LiveTv/TunerHosts/LiveStream.cs +++ b/Emby.Server.Implementations/LiveTv/TunerHosts/LiveStream.cs @@ -58,12 +58,15 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts protected virtual int EmptyReadLimit => 1000; public MediaSourceInfo OriginalMediaSource { get; set; } + public MediaSourceInfo MediaSource { get; set; } public int ConsumerCount { get; set; } public string OriginalStreamId { get; set; } + public bool EnableStreamSharing { get; set; } + public string UniqueId { get; } public string TunerHostId { get; } diff --git a/Emby.Server.Implementations/Playlists/PlaylistManager.cs b/Emby.Server.Implementations/Playlists/PlaylistManager.cs index 184d64e608..ac816ccd93 100644 --- a/Emby.Server.Implementations/Playlists/PlaylistManager.cs +++ b/Emby.Server.Implementations/Playlists/PlaylistManager.cs @@ -401,6 +401,7 @@ namespace Emby.Server.Implementations.Playlists { entry.Duration = TimeSpan.FromTicks(child.RunTimeTicks.Value); } + playlist.PlaylistEntries.Add(entry); } diff --git a/Emby.Server.Implementations/ScheduledTasks/ScheduledTaskWorker.cs b/Emby.Server.Implementations/ScheduledTasks/ScheduledTaskWorker.cs index e58c335a85..2031a1c6db 100644 --- a/Emby.Server.Implementations/ScheduledTasks/ScheduledTaskWorker.cs +++ b/Emby.Server.Implementations/ScheduledTasks/ScheduledTaskWorker.cs @@ -143,12 +143,14 @@ namespace Emby.Server.Implementations.ScheduledTasks Logger.LogError(ex, "Error deserializing {File}", path); } } + _readFromFile = true; } } return _lastExecutionResult; } + private set { _lastExecutionResult = value; @@ -261,6 +263,7 @@ namespace Emby.Server.Implementations.ScheduledTasks var triggers = InternalTriggers; return triggers.Select(i => i.Item1).ToArray(); } + set { if (value == null) @@ -640,6 +643,7 @@ namespace Emby.Server.Implementations.ScheduledTasks Logger.LogError(ex, "Error calling CancellationToken.Cancel();"); } } + var task = _currentTask; if (task != null) { @@ -675,6 +679,7 @@ namespace Emby.Server.Implementations.ScheduledTasks Logger.LogError(ex, "Error calling CancellationToken.Dispose();"); } } + if (wassRunning) { OnTaskCompleted(startTime, DateTime.UtcNow, TaskCompletionStatus.Aborted, null); diff --git a/Emby.Server.Implementations/Services/ServiceMethod.cs b/Emby.Server.Implementations/Services/ServiceMethod.cs index 59ee5908fd..5116cc04fe 100644 --- a/Emby.Server.Implementations/Services/ServiceMethod.cs +++ b/Emby.Server.Implementations/Services/ServiceMethod.cs @@ -9,6 +9,7 @@ namespace Emby.Server.Implementations.Services public string Id { get; set; } public ActionInvokerFn ServiceAction { get; set; } + public MediaBrowser.Model.Services.IHasRequestFilter[] RequestFilters { get; set; } public static string Key(Type serviceType, string method, string requestDtoName) diff --git a/Emby.Server.Implementations/Services/ServicePath.cs b/Emby.Server.Implementations/Services/ServicePath.cs index 43869f98af..3b7ffaf2cd 100644 --- a/Emby.Server.Implementations/Services/ServicePath.cs +++ b/Emby.Server.Implementations/Services/ServicePath.cs @@ -62,7 +62,9 @@ namespace Emby.Server.Implementations.Services public string Path => this.restPath; public string Summary { get; private set; } + public string Description { get; private set; } + public bool IsHidden { get; private set; } public static string[] GetPathPartsForMatching(string pathInfo) @@ -159,6 +161,7 @@ namespace Emby.Server.Implementations.Services this.isWildcard[i] = true; variableName = variableName.Substring(0, variableName.Length - 1); } + this.variablesNames[i] = variableName; this.VariableArgsCount++; } diff --git a/Emby.Server.Implementations/Services/StringMapTypeDeserializer.cs b/Emby.Server.Implementations/Services/StringMapTypeDeserializer.cs index d3d27ae584..165bb0fc42 100644 --- a/Emby.Server.Implementations/Services/StringMapTypeDeserializer.cs +++ b/Emby.Server.Implementations/Services/StringMapTypeDeserializer.cs @@ -22,7 +22,9 @@ namespace Emby.Server.Implementations.Services } public Action<object, object> PropertySetFn { get; private set; } + public Func<string, object> PropertyParseStringFn { get; private set; } + public Type PropertyType { get; private set; } } diff --git a/Emby.Server.Implementations/Services/SwaggerService.cs b/Emby.Server.Implementations/Services/SwaggerService.cs index 16142a70df..4f011a678f 100644 --- a/Emby.Server.Implementations/Services/SwaggerService.cs +++ b/Emby.Server.Implementations/Services/SwaggerService.cs @@ -18,13 +18,21 @@ namespace Emby.Server.Implementations.Services public class SwaggerSpec { public string swagger { get; set; } + public string[] schemes { get; set; } + public SwaggerInfo info { get; set; } + public string host { get; set; } + public string basePath { get; set; } + public SwaggerTag[] tags { get; set; } + public IDictionary<string, Dictionary<string, SwaggerMethod>> paths { get; set; } + public Dictionary<string, SwaggerDefinition> definitions { get; set; } + public SwaggerComponents components { get; set; } } @@ -36,15 +44,20 @@ namespace Emby.Server.Implementations.Services public class SwaggerSecurityScheme { public string name { get; set; } + public string type { get; set; } + public string @in { get; set; } } public class SwaggerInfo { public string description { get; set; } + public string version { get; set; } + public string title { get; set; } + public string termsOfService { get; set; } public SwaggerConcactInfo contact { get; set; } @@ -53,36 +66,52 @@ namespace Emby.Server.Implementations.Services public class SwaggerConcactInfo { public string email { get; set; } + public string name { get; set; } + public string url { get; set; } } public class SwaggerTag { public string description { get; set; } + public string name { get; set; } } public class SwaggerMethod { public string summary { get; set; } + public string description { get; set; } + public string[] tags { get; set; } + public string operationId { get; set; } + public string[] consumes { get; set; } + public string[] produces { get; set; } + public SwaggerParam[] parameters { get; set; } + public Dictionary<string, SwaggerResponse> responses { get; set; } + public Dictionary<string, string[]>[] security { get; set; } } public class SwaggerParam { public string @in { get; set; } + public string name { get; set; } + public string description { get; set; } + public bool required { get; set; } + public string type { get; set; } + public string collectionFormat { get; set; } } @@ -97,15 +126,20 @@ namespace Emby.Server.Implementations.Services public class SwaggerDefinition { public string type { get; set; } + public Dictionary<string, SwaggerProperty> properties { get; set; } } public class SwaggerProperty { public string type { get; set; } + public string format { get; set; } + public string description { get; set; } + public string[] @enum { get; set; } + public string @default { get; set; } } diff --git a/Emby.Server.Implementations/Session/SessionWebSocketListener.cs b/Emby.Server.Implementations/Session/SessionWebSocketListener.cs index ef32c692c1..1e8b25e38e 100644 --- a/Emby.Server.Implementations/Session/SessionWebSocketListener.cs +++ b/Emby.Server.Implementations/Session/SessionWebSocketListener.cs @@ -167,6 +167,7 @@ namespace Emby.Server.Implementations.Session _logger.LogWarning("Multiple attempts to keep alive single WebSocket {0}", webSocket); return; } + webSocket.Closed += OnWebSocketClosed; webSocket.LastKeepAliveDate = DateTime.UtcNow; diff --git a/Emby.Server.Implementations/Sorting/PremiereDateComparer.cs b/Emby.Server.Implementations/Sorting/PremiereDateComparer.cs index 0c944a7a02..491057a851 100644 --- a/Emby.Server.Implementations/Sorting/PremiereDateComparer.cs +++ b/Emby.Server.Implementations/Sorting/PremiereDateComparer.cs @@ -44,6 +44,7 @@ namespace Emby.Server.Implementations.Sorting // Don't blow up if the item has a bad ProductionYear, just return MinValue } } + return DateTime.MinValue; } diff --git a/Emby.Server.Implementations/TV/TVSeriesManager.cs b/Emby.Server.Implementations/TV/TVSeriesManager.cs index db056cc38d..21c12ae79f 100644 --- a/Emby.Server.Implementations/TV/TVSeriesManager.cs +++ b/Emby.Server.Implementations/TV/TVSeriesManager.cs @@ -256,6 +256,7 @@ namespace Emby.Server.Implementations.TV { items = items.Skip(query.StartIndex.Value); } + if (query.Limit.HasValue) { items = items.Take(query.Limit.Value); diff --git a/Jellyfin.Data/Entities/Artwork.cs b/Jellyfin.Data/Entities/Artwork.cs index 214fb4cb1b..bebcc37d33 100644 --- a/Jellyfin.Data/Entities/Artwork.cs +++ b/Jellyfin.Data/Entities/Artwork.cs @@ -89,6 +89,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -127,6 +128,7 @@ namespace Jellyfin.Data.Entities GetPath(ref value); return (_Path = value); } + set { string oldValue = _Path; @@ -163,6 +165,7 @@ namespace Jellyfin.Data.Entities GetKind(ref value); return (_Kind = value); } + set { Enums.ArtKind oldValue = _Kind; diff --git a/Jellyfin.Data/Entities/BookMetadata.cs b/Jellyfin.Data/Entities/BookMetadata.cs index dd389b64a7..6c72c27322 100644 --- a/Jellyfin.Data/Entities/BookMetadata.cs +++ b/Jellyfin.Data/Entities/BookMetadata.cs @@ -84,6 +84,7 @@ namespace Jellyfin.Data.Entities GetISBN(ref value); return (_ISBN = value); } + set { long? oldValue = _ISBN; diff --git a/Jellyfin.Data/Entities/Chapter.cs b/Jellyfin.Data/Entities/Chapter.cs index 9b3a5e8275..3d59fe6b88 100644 --- a/Jellyfin.Data/Entities/Chapter.cs +++ b/Jellyfin.Data/Entities/Chapter.cs @@ -86,6 +86,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -123,6 +124,7 @@ namespace Jellyfin.Data.Entities GetName(ref value); return (_Name = value); } + set { string oldValue = _Name; @@ -163,6 +165,7 @@ namespace Jellyfin.Data.Entities GetLanguage(ref value); return (_Language = value); } + set { string oldValue = _Language; @@ -199,6 +202,7 @@ namespace Jellyfin.Data.Entities GetTimeStart(ref value); return (_TimeStart = value); } + set { long oldValue = _TimeStart; @@ -231,6 +235,7 @@ namespace Jellyfin.Data.Entities GetTimeEnd(ref value); return (_TimeEnd = value); } + set { long? oldValue = _TimeEnd; diff --git a/Jellyfin.Data/Entities/Collection.cs b/Jellyfin.Data/Entities/Collection.cs index c040cfe336..caf20f9169 100644 --- a/Jellyfin.Data/Entities/Collection.cs +++ b/Jellyfin.Data/Entities/Collection.cs @@ -49,6 +49,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -86,6 +87,7 @@ namespace Jellyfin.Data.Entities GetName(ref value); return (_Name = value); } + set { string oldValue = _Name; diff --git a/Jellyfin.Data/Entities/CollectionItem.cs b/Jellyfin.Data/Entities/CollectionItem.cs index c5e54c3a2d..1a10780500 100644 --- a/Jellyfin.Data/Entities/CollectionItem.cs +++ b/Jellyfin.Data/Entities/CollectionItem.cs @@ -93,6 +93,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; diff --git a/Jellyfin.Data/Entities/Company.cs b/Jellyfin.Data/Entities/Company.cs index 7d6f3b2076..eefc581c66 100644 --- a/Jellyfin.Data/Entities/Company.cs +++ b/Jellyfin.Data/Entities/Company.cs @@ -101,6 +101,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; diff --git a/Jellyfin.Data/Entities/CompanyMetadata.cs b/Jellyfin.Data/Entities/CompanyMetadata.cs index 1ad03b4f9c..6a601c6e35 100644 --- a/Jellyfin.Data/Entities/CompanyMetadata.cs +++ b/Jellyfin.Data/Entities/CompanyMetadata.cs @@ -85,6 +85,7 @@ namespace Jellyfin.Data.Entities GetDescription(ref value); return (_Description = value); } + set { string oldValue = _Description; @@ -122,6 +123,7 @@ namespace Jellyfin.Data.Entities GetHeadquarters(ref value); return (_Headquarters = value); } + set { string oldValue = _Headquarters; @@ -159,6 +161,7 @@ namespace Jellyfin.Data.Entities GetCountry(ref value); return (_Country = value); } + set { string oldValue = _Country; @@ -196,6 +199,7 @@ namespace Jellyfin.Data.Entities GetHomepage(ref value); return (_Homepage = value); } + set { string oldValue = _Homepage; diff --git a/Jellyfin.Data/Entities/Episode.cs b/Jellyfin.Data/Entities/Episode.cs index 88531205fc..6f4353a6f6 100644 --- a/Jellyfin.Data/Entities/Episode.cs +++ b/Jellyfin.Data/Entities/Episode.cs @@ -86,6 +86,7 @@ namespace Jellyfin.Data.Entities GetEpisodeNumber(ref value); return (_EpisodeNumber = value); } + set { int? oldValue = _EpisodeNumber; diff --git a/Jellyfin.Data/Entities/EpisodeMetadata.cs b/Jellyfin.Data/Entities/EpisodeMetadata.cs index 0aa4b42703..17057cb1db 100644 --- a/Jellyfin.Data/Entities/EpisodeMetadata.cs +++ b/Jellyfin.Data/Entities/EpisodeMetadata.cs @@ -85,6 +85,7 @@ namespace Jellyfin.Data.Entities GetOutline(ref value); return (_Outline = value); } + set { string oldValue = _Outline; @@ -122,6 +123,7 @@ namespace Jellyfin.Data.Entities GetPlot(ref value); return (_Plot = value); } + set { string oldValue = _Plot; @@ -159,6 +161,7 @@ namespace Jellyfin.Data.Entities GetTagline(ref value); return (_Tagline = value); } + set { string oldValue = _Tagline; diff --git a/Jellyfin.Data/Entities/Genre.cs b/Jellyfin.Data/Entities/Genre.cs index ff07106712..b56e356678 100644 --- a/Jellyfin.Data/Entities/Genre.cs +++ b/Jellyfin.Data/Entities/Genre.cs @@ -82,6 +82,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -120,6 +121,7 @@ namespace Jellyfin.Data.Entities GetName(ref value); return (_Name = value); } + set { string oldValue = _Name; diff --git a/Jellyfin.Data/Entities/Library.cs b/Jellyfin.Data/Entities/Library.cs index a5cc5c8da4..4c7f7e7b71 100644 --- a/Jellyfin.Data/Entities/Library.cs +++ b/Jellyfin.Data/Entities/Library.cs @@ -77,6 +77,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -115,6 +116,7 @@ namespace Jellyfin.Data.Entities GetName(ref value); return (_Name = value); } + set { string oldValue = _Name; diff --git a/Jellyfin.Data/Entities/LibraryItem.cs b/Jellyfin.Data/Entities/LibraryItem.cs index c2ba7059d9..bfc2f7ddbd 100644 --- a/Jellyfin.Data/Entities/LibraryItem.cs +++ b/Jellyfin.Data/Entities/LibraryItem.cs @@ -59,6 +59,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -96,6 +97,7 @@ namespace Jellyfin.Data.Entities GetUrlId(ref value); return (_UrlId = value); } + set { Guid oldValue = _UrlId; @@ -132,6 +134,7 @@ namespace Jellyfin.Data.Entities GetDateAdded(ref value); return (_DateAdded = value); } + internal set { DateTime oldValue = _DateAdded; diff --git a/Jellyfin.Data/Entities/LibraryRoot.cs b/Jellyfin.Data/Entities/LibraryRoot.cs index 7823db02a8..fa1e6f14c6 100644 --- a/Jellyfin.Data/Entities/LibraryRoot.cs +++ b/Jellyfin.Data/Entities/LibraryRoot.cs @@ -77,6 +77,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -116,6 +117,7 @@ namespace Jellyfin.Data.Entities GetPath(ref value); return (_Path = value); } + set { string oldValue = _Path; @@ -154,6 +156,7 @@ namespace Jellyfin.Data.Entities GetNetworkPath(ref value); return (_NetworkPath = value); } + set { string oldValue = _NetworkPath; diff --git a/Jellyfin.Data/Entities/MediaFile.cs b/Jellyfin.Data/Entities/MediaFile.cs index 94c39a28a5..1c14c6c874 100644 --- a/Jellyfin.Data/Entities/MediaFile.cs +++ b/Jellyfin.Data/Entities/MediaFile.cs @@ -90,6 +90,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -129,6 +130,7 @@ namespace Jellyfin.Data.Entities GetPath(ref value); return (_Path = value); } + set { string oldValue = _Path; @@ -165,6 +167,7 @@ namespace Jellyfin.Data.Entities GetKind(ref value); return (_Kind = value); } + set { Enums.MediaFileKind oldValue = _Kind; diff --git a/Jellyfin.Data/Entities/MediaFileStream.cs b/Jellyfin.Data/Entities/MediaFileStream.cs index 723977fdf1..8819ddcd0d 100644 --- a/Jellyfin.Data/Entities/MediaFileStream.cs +++ b/Jellyfin.Data/Entities/MediaFileStream.cs @@ -81,6 +81,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -117,6 +118,7 @@ namespace Jellyfin.Data.Entities GetStreamNumber(ref value); return (_StreamNumber = value); } + set { int oldValue = _StreamNumber; diff --git a/Jellyfin.Data/Entities/Metadata.cs b/Jellyfin.Data/Entities/Metadata.cs index 6558642cf1..4e5868e754 100644 --- a/Jellyfin.Data/Entities/Metadata.cs +++ b/Jellyfin.Data/Entities/Metadata.cs @@ -76,6 +76,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -115,6 +116,7 @@ namespace Jellyfin.Data.Entities GetTitle(ref value); return (_Title = value); } + set { string oldValue = _Title; @@ -152,6 +154,7 @@ namespace Jellyfin.Data.Entities GetOriginalTitle(ref value); return (_OriginalTitle = value); } + set { string oldValue = _OriginalTitle; @@ -189,6 +192,7 @@ namespace Jellyfin.Data.Entities GetSortTitle(ref value); return (_SortTitle = value); } + set { string oldValue = _SortTitle; @@ -229,6 +233,7 @@ namespace Jellyfin.Data.Entities GetLanguage(ref value); return (_Language = value); } + set { string oldValue = _Language; @@ -261,6 +266,7 @@ namespace Jellyfin.Data.Entities GetReleaseDate(ref value); return (_ReleaseDate = value); } + set { DateTimeOffset? oldValue = _ReleaseDate; @@ -297,6 +303,7 @@ namespace Jellyfin.Data.Entities GetDateAdded(ref value); return (_DateAdded = value); } + internal set { DateTime oldValue = _DateAdded; @@ -333,6 +340,7 @@ namespace Jellyfin.Data.Entities GetDateModified(ref value); return (_DateModified = value); } + internal set { DateTime oldValue = _DateModified; diff --git a/Jellyfin.Data/Entities/MetadataProvider.cs b/Jellyfin.Data/Entities/MetadataProvider.cs index bf9689709b..9b09fc5a6c 100644 --- a/Jellyfin.Data/Entities/MetadataProvider.cs +++ b/Jellyfin.Data/Entities/MetadataProvider.cs @@ -77,6 +77,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -115,6 +116,7 @@ namespace Jellyfin.Data.Entities GetName(ref value); return (_Name = value); } + set { string oldValue = _Name; diff --git a/Jellyfin.Data/Entities/MetadataProviderId.cs b/Jellyfin.Data/Entities/MetadataProviderId.cs index c49c6f42e4..bcd2bad54d 100644 --- a/Jellyfin.Data/Entities/MetadataProviderId.cs +++ b/Jellyfin.Data/Entities/MetadataProviderId.cs @@ -103,6 +103,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -141,6 +142,7 @@ namespace Jellyfin.Data.Entities GetProviderId(ref value); return (_ProviderId = value); } + set { string oldValue = _ProviderId; diff --git a/Jellyfin.Data/Entities/MovieMetadata.cs b/Jellyfin.Data/Entities/MovieMetadata.cs index 1f8f1c2a00..6c9156a2da 100644 --- a/Jellyfin.Data/Entities/MovieMetadata.cs +++ b/Jellyfin.Data/Entities/MovieMetadata.cs @@ -90,6 +90,7 @@ namespace Jellyfin.Data.Entities GetOutline(ref value); return (_Outline = value); } + set { string oldValue = _Outline; @@ -127,6 +128,7 @@ namespace Jellyfin.Data.Entities GetPlot(ref value); return (_Plot = value); } + set { string oldValue = _Plot; @@ -164,6 +166,7 @@ namespace Jellyfin.Data.Entities GetTagline(ref value); return (_Tagline = value); } + set { string oldValue = _Tagline; @@ -201,6 +204,7 @@ namespace Jellyfin.Data.Entities GetCountry(ref value); return (_Country = value); } + set { string oldValue = _Country; diff --git a/Jellyfin.Data/Entities/MusicAlbumMetadata.cs b/Jellyfin.Data/Entities/MusicAlbumMetadata.cs index 7743890a67..cf0363b7d7 100644 --- a/Jellyfin.Data/Entities/MusicAlbumMetadata.cs +++ b/Jellyfin.Data/Entities/MusicAlbumMetadata.cs @@ -90,6 +90,7 @@ namespace Jellyfin.Data.Entities GetBarcode(ref value); return (_Barcode = value); } + set { string oldValue = _Barcode; @@ -127,6 +128,7 @@ namespace Jellyfin.Data.Entities GetLabelNumber(ref value); return (_LabelNumber = value); } + set { string oldValue = _LabelNumber; @@ -164,6 +166,7 @@ namespace Jellyfin.Data.Entities GetCountry(ref value); return (_Country = value); } + set { string oldValue = _Country; diff --git a/Jellyfin.Data/Entities/Person.cs b/Jellyfin.Data/Entities/Person.cs index f714188190..9cc568e6e6 100644 --- a/Jellyfin.Data/Entities/Person.cs +++ b/Jellyfin.Data/Entities/Person.cs @@ -85,6 +85,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -121,6 +122,7 @@ namespace Jellyfin.Data.Entities GetUrlId(ref value); return (_UrlId = value); } + set { Guid oldValue = _UrlId; @@ -159,6 +161,7 @@ namespace Jellyfin.Data.Entities GetName(ref value); return (_Name = value); } + set { string oldValue = _Name; @@ -196,6 +199,7 @@ namespace Jellyfin.Data.Entities GetSourceId(ref value); return (_SourceId = value); } + set { string oldValue = _SourceId; @@ -232,6 +236,7 @@ namespace Jellyfin.Data.Entities GetDateAdded(ref value); return (_DateAdded = value); } + internal set { DateTime oldValue = _DateAdded; @@ -268,6 +273,7 @@ namespace Jellyfin.Data.Entities GetDateModified(ref value); return (_DateModified = value); } + internal set { DateTime oldValue = _DateModified; diff --git a/Jellyfin.Data/Entities/PersonRole.cs b/Jellyfin.Data/Entities/PersonRole.cs index a3d0471151..e0492ea6a5 100644 --- a/Jellyfin.Data/Entities/PersonRole.cs +++ b/Jellyfin.Data/Entities/PersonRole.cs @@ -91,6 +91,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -128,6 +129,7 @@ namespace Jellyfin.Data.Entities GetRole(ref value); return (_Role = value); } + set { string oldValue = _Role; @@ -164,6 +166,7 @@ namespace Jellyfin.Data.Entities GetType(ref value); return (_Type = value); } + set { Enums.PersonRoleType oldValue = _Type; diff --git a/Jellyfin.Data/Entities/Rating.cs b/Jellyfin.Data/Entities/Rating.cs index 0c8b99ca2c..490090bfa6 100644 --- a/Jellyfin.Data/Entities/Rating.cs +++ b/Jellyfin.Data/Entities/Rating.cs @@ -81,6 +81,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -117,6 +118,7 @@ namespace Jellyfin.Data.Entities GetValue(ref value); return (_Value = value); } + set { double oldValue = _Value; @@ -149,6 +151,7 @@ namespace Jellyfin.Data.Entities GetVotes(ref value); return (_Votes = value); } + set { int? oldValue = _Votes; diff --git a/Jellyfin.Data/Entities/RatingSource.cs b/Jellyfin.Data/Entities/RatingSource.cs index c829042b5c..cf8af2270c 100644 --- a/Jellyfin.Data/Entities/RatingSource.cs +++ b/Jellyfin.Data/Entities/RatingSource.cs @@ -88,6 +88,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -125,6 +126,7 @@ namespace Jellyfin.Data.Entities GetName(ref value); return (_Name = value); } + set { string oldValue = _Name; @@ -161,6 +163,7 @@ namespace Jellyfin.Data.Entities GetMaximumValue(ref value); return (_MaximumValue = value); } + set { double oldValue = _MaximumValue; @@ -197,6 +200,7 @@ namespace Jellyfin.Data.Entities GetMinimumValue(ref value); return (_MinimumValue = value); } + set { double oldValue = _MinimumValue; diff --git a/Jellyfin.Data/Entities/Release.cs b/Jellyfin.Data/Entities/Release.cs index 35fcbb4b76..6be524a0f9 100644 --- a/Jellyfin.Data/Entities/Release.cs +++ b/Jellyfin.Data/Entities/Release.cs @@ -113,6 +113,7 @@ namespace Jellyfin.Data.Entities GetId(ref value); return (_Id = value); } + protected set { int oldValue = _Id; @@ -151,6 +152,7 @@ namespace Jellyfin.Data.Entities GetName(ref value); return (_Name = value); } + set { string oldValue = _Name; diff --git a/Jellyfin.Data/Entities/Season.cs b/Jellyfin.Data/Entities/Season.cs index 2a861b660a..631adb12cb 100644 --- a/Jellyfin.Data/Entities/Season.cs +++ b/Jellyfin.Data/Entities/Season.cs @@ -86,6 +86,7 @@ namespace Jellyfin.Data.Entities GetSeasonNumber(ref value); return (_SeasonNumber = value); } + set { int? oldValue = _SeasonNumber; diff --git a/Jellyfin.Data/Entities/SeasonMetadata.cs b/Jellyfin.Data/Entities/SeasonMetadata.cs index 10320c6bbd..2efbf6467c 100644 --- a/Jellyfin.Data/Entities/SeasonMetadata.cs +++ b/Jellyfin.Data/Entities/SeasonMetadata.cs @@ -86,6 +86,7 @@ namespace Jellyfin.Data.Entities GetOutline(ref value); return (_Outline = value); } + set { string oldValue = _Outline; diff --git a/Jellyfin.Data/Entities/Series.cs b/Jellyfin.Data/Entities/Series.cs index cf1d6b781b..386d3a8acd 100644 --- a/Jellyfin.Data/Entities/Series.cs +++ b/Jellyfin.Data/Entities/Series.cs @@ -67,6 +67,7 @@ namespace Jellyfin.Data.Entities GetAirsDayOfWeek(ref value); return (_AirsDayOfWeek = value); } + set { DayOfWeek? oldValue = _AirsDayOfWeek; @@ -102,6 +103,7 @@ namespace Jellyfin.Data.Entities GetAirsTime(ref value); return (_AirsTime = value); } + set { DateTimeOffset? oldValue = _AirsTime; @@ -134,6 +136,7 @@ namespace Jellyfin.Data.Entities GetFirstAired(ref value); return (_FirstAired = value); } + set { DateTimeOffset? oldValue = _FirstAired; diff --git a/Jellyfin.Data/Entities/SeriesMetadata.cs b/Jellyfin.Data/Entities/SeriesMetadata.cs index bb31c2e4e8..f49c5a3b22 100644 --- a/Jellyfin.Data/Entities/SeriesMetadata.cs +++ b/Jellyfin.Data/Entities/SeriesMetadata.cs @@ -90,6 +90,7 @@ namespace Jellyfin.Data.Entities GetOutline(ref value); return (_Outline = value); } + set { string oldValue = _Outline; @@ -127,6 +128,7 @@ namespace Jellyfin.Data.Entities GetPlot(ref value); return (_Plot = value); } + set { string oldValue = _Plot; @@ -164,6 +166,7 @@ namespace Jellyfin.Data.Entities GetTagline(ref value); return (_Tagline = value); } + set { string oldValue = _Tagline; @@ -201,6 +204,7 @@ namespace Jellyfin.Data.Entities GetCountry(ref value); return (_Country = value); } + set { string oldValue = _Country; diff --git a/Jellyfin.Data/Entities/Track.cs b/Jellyfin.Data/Entities/Track.cs index c9e8fd1c3b..fc9dfb3707 100644 --- a/Jellyfin.Data/Entities/Track.cs +++ b/Jellyfin.Data/Entities/Track.cs @@ -86,6 +86,7 @@ namespace Jellyfin.Data.Entities GetTrackNumber(ref value); return (_TrackNumber = value); } + set { int? oldValue = _TrackNumber; diff --git a/Jellyfin.Server.Implementations/JellyfinDb.cs b/Jellyfin.Server.Implementations/JellyfinDb.cs index f574ebc66b..d77cd432bf 100644 --- a/Jellyfin.Server.Implementations/JellyfinDb.cs +++ b/Jellyfin.Server.Implementations/JellyfinDb.cs @@ -34,37 +34,69 @@ namespace Jellyfin.Server.Implementations public virtual DbSet<Preference> Preferences { get; set; } public virtual DbSet<User> Users { get; set; } + /*public virtual DbSet<Artwork> Artwork { get; set; } + public virtual DbSet<Book> Books { get; set; } + public virtual DbSet<BookMetadata> BookMetadata { get; set; } + public virtual DbSet<Chapter> Chapters { get; set; } + public virtual DbSet<Collection> Collections { get; set; } + public virtual DbSet<CollectionItem> CollectionItems { get; set; } + public virtual DbSet<Company> Companies { get; set; } + public virtual DbSet<CompanyMetadata> CompanyMetadata { get; set; } + public virtual DbSet<CustomItem> CustomItems { get; set; } + public virtual DbSet<CustomItemMetadata> CustomItemMetadata { get; set; } + public virtual DbSet<Episode> Episodes { get; set; } + public virtual DbSet<EpisodeMetadata> EpisodeMetadata { get; set; } + public virtual DbSet<Genre> Genres { get; set; } + public virtual DbSet<Group> Groups { get; set; } + public virtual DbSet<Library> Libraries { get; set; } + public virtual DbSet<LibraryItem> LibraryItems { get; set; } + public virtual DbSet<LibraryRoot> LibraryRoot { get; set; } + public virtual DbSet<MediaFile> MediaFiles { get; set; } + public virtual DbSet<MediaFileStream> MediaFileStream { get; set; } + public virtual DbSet<Metadata> Metadata { get; set; } + public virtual DbSet<MetadataProvider> MetadataProviders { get; set; } + public virtual DbSet<MetadataProviderId> MetadataProviderIds { get; set; } + public virtual DbSet<Movie> Movies { get; set; } + public virtual DbSet<MovieMetadata> MovieMetadata { get; set; } + public virtual DbSet<MusicAlbum> MusicAlbums { get; set; } + public virtual DbSet<MusicAlbumMetadata> MusicAlbumMetadata { get; set; } + public virtual DbSet<Person> People { get; set; } + public virtual DbSet<PersonRole> PersonRoles { get; set; } + public virtual DbSet<Photo> Photo { get; set; } + public virtual DbSet<PhotoMetadata> PhotoMetadata { get; set; } + public virtual DbSet<ProviderMapping> ProviderMappings { get; set; } + public virtual DbSet<Rating> Ratings { get; set; } /// <summary> @@ -72,12 +104,19 @@ namespace Jellyfin.Server.Implementations /// store review ratings, not age ratings /// </summary> public virtual DbSet<RatingSource> RatingSources { get; set; } + public virtual DbSet<Release> Releases { get; set; } + public virtual DbSet<Season> Seasons { get; set; } + public virtual DbSet<SeasonMetadata> SeasonMetadata { get; set; } + public virtual DbSet<Series> Series { get; set; } + public virtual DbSet<SeriesMetadata> SeriesMetadata { get; set; } + public virtual DbSet<Track> Tracks { get; set; } + public virtual DbSet<TrackMetadata> TrackMetadata { get; set; }*/ /// <inheritdoc/> diff --git a/MediaBrowser.Api/EnvironmentService.cs b/MediaBrowser.Api/EnvironmentService.cs index fddf784651..765774dee8 100644 --- a/MediaBrowser.Api/EnvironmentService.cs +++ b/MediaBrowser.Api/EnvironmentService.cs @@ -50,6 +50,7 @@ namespace MediaBrowser.Api public string Path { get; set; } public bool ValidateWriteable { get; set; } + public bool? IsFile { get; set; } } diff --git a/MediaBrowser.Api/FilterService.cs b/MediaBrowser.Api/FilterService.cs index 833a684a5d..1b736c77da 100644 --- a/MediaBrowser.Api/FilterService.cs +++ b/MediaBrowser.Api/FilterService.cs @@ -73,11 +73,17 @@ namespace MediaBrowser.Api } public bool? IsAiring { get; set; } + public bool? IsMovie { get; set; } + public bool? IsSports { get; set; } + public bool? IsKids { get; set; } + public bool? IsNews { get; set; } + public bool? IsSeries { get; set; } + public bool? Recursive { get; set; } } diff --git a/MediaBrowser.Api/IHasDtoOptions.cs b/MediaBrowser.Api/IHasDtoOptions.cs index 03d3b3692f..33d498e8bd 100644 --- a/MediaBrowser.Api/IHasDtoOptions.cs +++ b/MediaBrowser.Api/IHasDtoOptions.cs @@ -3,6 +3,7 @@ namespace MediaBrowser.Api public interface IHasDtoOptions : IHasItemFields { bool? EnableImages { get; set; } + bool? EnableUserData { get; set; } int? ImageTypeLimit { get; set; } diff --git a/MediaBrowser.Api/Library/LibraryService.cs b/MediaBrowser.Api/Library/LibraryService.cs index eb64abb4d4..46bc43605a 100644 --- a/MediaBrowser.Api/Library/LibraryService.cs +++ b/MediaBrowser.Api/Library/LibraryService.cs @@ -285,29 +285,38 @@ namespace MediaBrowser.Api.Library public class GetLibraryOptionsInfo : IReturn<LibraryOptionsResult> { public string LibraryContentType { get; set; } + public bool IsNewLibrary { get; set; } } public class LibraryOptionInfo { public string Name { get; set; } + public bool DefaultEnabled { get; set; } } public class LibraryOptionsResult { public LibraryOptionInfo[] MetadataSavers { get; set; } + public LibraryOptionInfo[] MetadataReaders { get; set; } + public LibraryOptionInfo[] SubtitleFetchers { get; set; } + public LibraryTypeOptions[] TypeOptions { get; set; } } public class LibraryTypeOptions { public string Type { get; set; } + public LibraryOptionInfo[] MetadataFetchers { get; set; } + public LibraryOptionInfo[] ImageFetchers { get; set; } + public ImageType[] SupportedImageTypes { get; set; } + public ImageOption[] DefaultImageOptions { get; set; } } @@ -1036,6 +1045,7 @@ namespace MediaBrowser.Api.Library { break; } + item = parent; } @@ -1093,6 +1103,7 @@ namespace MediaBrowser.Api.Library { break; } + item = parent; } diff --git a/MediaBrowser.Api/LiveTv/LiveTvService.cs b/MediaBrowser.Api/LiveTv/LiveTvService.cs index b00a5fec8c..84141e9ae4 100644 --- a/MediaBrowser.Api/LiveTv/LiveTvService.cs +++ b/MediaBrowser.Api/LiveTv/LiveTvService.cs @@ -200,10 +200,15 @@ namespace MediaBrowser.Api.LiveTv public bool? EnableUserData { get; set; } public bool? IsMovie { get; set; } + public bool? IsSeries { get; set; } + public bool? IsKids { get; set; } + public bool? IsSports { get; set; } + public bool? IsNews { get; set; } + public bool? IsLibraryItem { get; set; } public GetRecordings() @@ -348,6 +353,7 @@ namespace MediaBrowser.Api.LiveTv [ApiMember(Name = "HasAired", Description = "Optional. Filter by programs that have completed airing, or not.", IsRequired = false, DataType = "bool", ParameterType = "query", Verb = "GET")] public bool? HasAired { get; set; } + public bool? IsAiring { get; set; } [ApiMember(Name = "MaxStartDate", Description = "Optional. The maximum premiere date. Format = ISO", IsRequired = false, DataType = "string", ParameterType = "query", Verb = "GET,POST")] @@ -407,6 +413,7 @@ namespace MediaBrowser.Api.LiveTv public bool? EnableUserData { get; set; } public string SeriesTimerId { get; set; } + public Guid LibrarySeriesId { get; set; } /// <summary> @@ -601,7 +608,9 @@ namespace MediaBrowser.Api.LiveTv public class AddListingProvider : ListingsProviderInfo, IReturn<ListingsProviderInfo> { public bool ValidateLogin { get; set; } + public bool ValidateListings { get; set; } + public string Pw { get; set; } } @@ -650,15 +659,20 @@ namespace MediaBrowser.Api.LiveTv { [ApiMember(Name = "Id", Description = "Provider id", IsRequired = true, DataType = "string", ParameterType = "query")] public string ProviderId { get; set; } + public string TunerChannelId { get; set; } + public string ProviderChannelId { get; set; } } public class ChannelMappingOptions { public List<TunerChannelMapping> TunerChannels { get; set; } + public List<NameIdPair> ProviderChannels { get; set; } + public NameValuePair[] Mappings { get; set; } + public string ProviderName { get; set; } } @@ -666,6 +680,7 @@ namespace MediaBrowser.Api.LiveTv public class GetLiveStreamFile { public string Id { get; set; } + public string Container { get; set; } } diff --git a/MediaBrowser.Api/Playback/BaseStreamingService.cs b/MediaBrowser.Api/Playback/BaseStreamingService.cs index 2eb6198c00..009a957b65 100644 --- a/MediaBrowser.Api/Playback/BaseStreamingService.cs +++ b/MediaBrowser.Api/Playback/BaseStreamingService.cs @@ -303,6 +303,7 @@ namespace MediaBrowser.Api.Playback { StartThrottler(state, transcodingJob); } + Logger.LogDebug("StartFfMpeg() finished successfully"); return transcodingJob; @@ -608,6 +609,7 @@ namespace MediaBrowser.Api.Playback { throw new ArgumentException("Invalid timeseek header"); } + int index = value.IndexOf('-'); value = index == -1 ? value.Substring(Npt.Length) @@ -639,8 +641,10 @@ namespace MediaBrowser.Api.Playback { throw new ArgumentException("Invalid timeseek header"); } + timeFactor /= 60; } + return TimeSpan.FromSeconds(secondsSum).Ticks; } diff --git a/MediaBrowser.Api/Playback/Hls/BaseHlsService.cs b/MediaBrowser.Api/Playback/Hls/BaseHlsService.cs index c2d49a93b6..5a2bf2ea3d 100644 --- a/MediaBrowser.Api/Playback/Hls/BaseHlsService.cs +++ b/MediaBrowser.Api/Playback/Hls/BaseHlsService.cs @@ -146,6 +146,7 @@ namespace MediaBrowser.Api.Playback.Hls { ApiEntryPoint.Instance.OnTranscodeEndRequest(job); } + return ResultFactory.GetResult(GetLivePlaylistText(playlist, state.SegmentLength), MimeTypes.GetMimeType("playlist.m3u8"), new Dictionary<string, string>()); } diff --git a/MediaBrowser.Api/Playback/Hls/DynamicHlsService.cs b/MediaBrowser.Api/Playback/Hls/DynamicHlsService.cs index c0dfcf4c13..fe5f980b18 100644 --- a/MediaBrowser.Api/Playback/Hls/DynamicHlsService.cs +++ b/MediaBrowser.Api/Playback/Hls/DynamicHlsService.cs @@ -234,6 +234,7 @@ namespace MediaBrowser.Api.Playback.Hls Logger.LogDebug("Starting transcoding because segmentGap is {0} and max allowed gap is {1}. requestedIndex={2}", requestedIndex - currentTranscodingIndex.Value, segmentGapRequiringTranscodingChange, requestedIndex); startTranscoding = true; } + if (startTranscoding) { // If the playlist doesn't already exist, startup ffmpeg @@ -518,6 +519,7 @@ namespace MediaBrowser.Api.Playback.Hls { Logger.LogDebug("serving {0} as it's on disk and transcoding stopped", segmentPath); } + cancellationToken.ThrowIfCancellationRequested(); } else diff --git a/MediaBrowser.Api/Playback/MediaInfoService.cs b/MediaBrowser.Api/Playback/MediaInfoService.cs index 2dc62fda7c..b7ca1a031d 100644 --- a/MediaBrowser.Api/Playback/MediaInfoService.cs +++ b/MediaBrowser.Api/Playback/MediaInfoService.cs @@ -551,10 +551,12 @@ namespace MediaBrowser.Api.Playback { mediaSource.TranscodingUrl += "&allowVideoStreamCopy=false"; } + if (!allowAudioStreamCopy) { mediaSource.TranscodingUrl += "&allowAudioStreamCopy=false"; } + mediaSource.TranscodingContainer = streamInfo.Container; mediaSource.TranscodingSubProtocol = streamInfo.SubProtocol; } diff --git a/MediaBrowser.Api/Playback/Progressive/BaseProgressiveStreamingService.cs b/MediaBrowser.Api/Playback/Progressive/BaseProgressiveStreamingService.cs index 43cde440ce..85c7e0e7d6 100644 --- a/MediaBrowser.Api/Playback/Progressive/BaseProgressiveStreamingService.cs +++ b/MediaBrowser.Api/Playback/Progressive/BaseProgressiveStreamingService.cs @@ -88,14 +88,17 @@ namespace MediaBrowser.Api.Playback.Progressive { return ".ts"; } + if (string.Equals(videoCodec, "theora", StringComparison.OrdinalIgnoreCase)) { return ".ogv"; } + if (string.Equals(videoCodec, "vpx", StringComparison.OrdinalIgnoreCase)) { return ".webm"; } + if (string.Equals(videoCodec, "wmv", StringComparison.OrdinalIgnoreCase)) { return ".asf"; @@ -111,14 +114,17 @@ namespace MediaBrowser.Api.Playback.Progressive { return ".aac"; } + if (string.Equals("mp3", audioCodec, StringComparison.OrdinalIgnoreCase)) { return ".mp3"; } + if (string.Equals("vorbis", audioCodec, StringComparison.OrdinalIgnoreCase)) { return ".ogg"; } + if (string.Equals("wma", audioCodec, StringComparison.OrdinalIgnoreCase)) { return ".wma"; diff --git a/MediaBrowser.Api/Playback/Progressive/ProgressiveStreamWriter.cs b/MediaBrowser.Api/Playback/Progressive/ProgressiveStreamWriter.cs index ffc5e15542..b70fff128b 100644 --- a/MediaBrowser.Api/Playback/Progressive/ProgressiveStreamWriter.cs +++ b/MediaBrowser.Api/Playback/Progressive/ProgressiveStreamWriter.cs @@ -23,6 +23,7 @@ namespace MediaBrowser.Api.Playback.Progressive private long _bytesWritten = 0; public long StartPosition { get; set; } + public bool AllowEndOfFile = true; private readonly IDirectStreamProvider _directStreamProvider; @@ -105,6 +106,7 @@ namespace MediaBrowser.Api.Playback.Progressive { eofCount++; } + await Task.Delay(100, cancellationToken).ConfigureAwait(false); } else diff --git a/MediaBrowser.Api/Playback/StreamRequest.cs b/MediaBrowser.Api/Playback/StreamRequest.cs index 9ba8eda91f..397898a7ed 100644 --- a/MediaBrowser.Api/Playback/StreamRequest.cs +++ b/MediaBrowser.Api/Playback/StreamRequest.cs @@ -12,11 +12,15 @@ namespace MediaBrowser.Api.Playback public string DeviceProfileId { get; set; } public string Params { get; set; } + public string PlaySessionId { get; set; } + public string Tag { get; set; } + public string SegmentContainer { get; set; } public int? SegmentLength { get; set; } + public int? MinSegments { get; set; } } diff --git a/MediaBrowser.Api/Playback/UniversalAudioService.cs b/MediaBrowser.Api/Playback/UniversalAudioService.cs index b2d101a5b1..d5d78cf37a 100644 --- a/MediaBrowser.Api/Playback/UniversalAudioService.cs +++ b/MediaBrowser.Api/Playback/UniversalAudioService.cs @@ -37,10 +37,13 @@ namespace MediaBrowser.Api.Playback public string DeviceId { get; set; } public Guid UserId { get; set; } + public string AudioCodec { get; set; } + public string Container { get; set; } public int? MaxAudioChannels { get; set; } + public int? TranscodingAudioChannels { get; set; } public long? MaxStreamingBitrate { get; set; } @@ -49,12 +52,17 @@ namespace MediaBrowser.Api.Playback public long? StartTimeTicks { get; set; } public string TranscodingContainer { get; set; } + public string TranscodingProtocol { get; set; } + public int? MaxAudioSampleRate { get; set; } + public int? MaxAudioBitDepth { get; set; } public bool EnableRedirection { get; set; } + public bool EnableRemoteMedia { get; set; } + public bool BreakOnNonKeyFrames { get; set; } public BaseUniversalRequest() @@ -114,16 +122,27 @@ namespace MediaBrowser.Api.Playback } protected IHttpClient HttpClient { get; private set; } + protected IUserManager UserManager { get; private set; } + protected ILibraryManager LibraryManager { get; private set; } + protected IIsoManager IsoManager { get; private set; } + protected IMediaEncoder MediaEncoder { get; private set; } + protected IFileSystem FileSystem { get; private set; } + protected IDlnaManager DlnaManager { get; private set; } + protected IDeviceManager DeviceManager { get; private set; } + protected IMediaSourceManager MediaSourceManager { get; private set; } + protected IJsonSerializer JsonSerializer { get; private set; } + protected IAuthorizationContext AuthorizationContext { get; private set; } + protected INetworkManager NetworkManager { get; private set; } public Task<object> Get(GetUniversalAudioStream request) @@ -328,6 +347,7 @@ namespace MediaBrowser.Api.Playback { return await service.Head(newRequest).ConfigureAwait(false); } + return await service.Get(newRequest).ConfigureAwait(false); } else diff --git a/MediaBrowser.Api/PluginService.cs b/MediaBrowser.Api/PluginService.cs index fd10757272..1d092a5d43 100644 --- a/MediaBrowser.Api/PluginService.cs +++ b/MediaBrowser.Api/PluginService.cs @@ -115,24 +115,33 @@ namespace MediaBrowser.Api public class RegistrationInfo { public string Name { get; set; } + public DateTime ExpirationDate { get; set; } + public bool IsTrial { get; set; } + public bool IsRegistered { get; set; } } public class MBRegistrationRecord { public DateTime ExpirationDate { get; set; } + public bool IsRegistered { get; set; } + public bool RegChecked { get; set; } + public bool RegError { get; set; } + public bool TrialVersion { get; set; } + public bool IsValid { get; set; } } public class PluginSecurityInfo { public string SupporterKey { get; set; } + public bool IsMBSupporter { get; set; } } /// <summary> diff --git a/MediaBrowser.Api/SimilarItemsHelper.cs b/MediaBrowser.Api/SimilarItemsHelper.cs index 90c324ff3f..c4df0a7ed6 100644 --- a/MediaBrowser.Api/SimilarItemsHelper.cs +++ b/MediaBrowser.Api/SimilarItemsHelper.cs @@ -179,18 +179,22 @@ namespace MediaBrowser.Api { return 5; } + if (string.Equals(i.Type, PersonType.Actor, StringComparison.OrdinalIgnoreCase) || string.Equals(i.Role, PersonType.Actor, StringComparison.OrdinalIgnoreCase)) { return 3; } + if (string.Equals(i.Type, PersonType.Composer, StringComparison.OrdinalIgnoreCase) || string.Equals(i.Role, PersonType.Composer, StringComparison.OrdinalIgnoreCase)) { return 3; } + if (string.Equals(i.Type, PersonType.GuestStar, StringComparison.OrdinalIgnoreCase) || string.Equals(i.Role, PersonType.GuestStar, StringComparison.OrdinalIgnoreCase)) { return 3; } + if (string.Equals(i.Type, PersonType.Writer, StringComparison.OrdinalIgnoreCase) || string.Equals(i.Role, PersonType.Writer, StringComparison.OrdinalIgnoreCase)) { return 2; diff --git a/MediaBrowser.Api/Subtitles/SubtitleService.cs b/MediaBrowser.Api/Subtitles/SubtitleService.cs index f2968c6b5c..a70da8e56c 100644 --- a/MediaBrowser.Api/Subtitles/SubtitleService.cs +++ b/MediaBrowser.Api/Subtitles/SubtitleService.cs @@ -97,6 +97,7 @@ namespace MediaBrowser.Api.Subtitles [ApiMember(Name = "CopyTimestamps", Description = "CopyTimestamps", IsRequired = false, DataType = "bool", ParameterType = "query", Verb = "GET")] public bool CopyTimestamps { get; set; } + public bool AddVttTimeMap { get; set; } } @@ -214,6 +215,7 @@ namespace MediaBrowser.Api.Subtitles { request.Format = "json"; } + if (string.IsNullOrEmpty(request.Format)) { var item = (Video)_libraryManager.GetItemById(request.Id); diff --git a/MediaBrowser.Api/SuggestionsService.cs b/MediaBrowser.Api/SuggestionsService.cs index 32d3bde5cb..17afa8e79c 100644 --- a/MediaBrowser.Api/SuggestionsService.cs +++ b/MediaBrowser.Api/SuggestionsService.cs @@ -18,10 +18,15 @@ namespace MediaBrowser.Api public class GetSuggestedItems : IReturn<QueryResult<BaseItemDto>> { public string MediaType { get; set; } + public string Type { get; set; } + public Guid UserId { get; set; } + public bool EnableTotalRecordCount { get; set; } + public int? StartIndex { get; set; } + public int? Limit { get; set; } public string[] GetMediaTypes() diff --git a/MediaBrowser.Api/TranscodingJob.cs b/MediaBrowser.Api/TranscodingJob.cs index 8c24e3ce18..bfc311a272 100644 --- a/MediaBrowser.Api/TranscodingJob.cs +++ b/MediaBrowser.Api/TranscodingJob.cs @@ -32,6 +32,7 @@ namespace MediaBrowser.Api /// </summary> /// <value>The path.</value> public MediaSourceInfo MediaSource { get; set; } + public string Path { get; set; } /// <summary> /// Gets or sets the type. @@ -43,6 +44,7 @@ namespace MediaBrowser.Api /// </summary> /// <value>The process.</value> public Process Process { get; set; } + public ILogger Logger { get; private set; } /// <summary> /// Gets or sets the active request count. @@ -62,18 +64,23 @@ namespace MediaBrowser.Api public object ProcessLock = new object(); public bool HasExited { get; set; } + public bool IsUserPaused { get; set; } public string Id { get; set; } public float? Framerate { get; set; } + public double? CompletionPercentage { get; set; } public long? BytesDownloaded { get; set; } + public long? BytesTranscoded { get; set; } + public int? BitRate { get; set; } public long? TranscodingPositionTicks { get; set; } + public long? DownloadPositionTicks { get; set; } public TranscodingThrottler TranscodingThrottler { get; set; } @@ -81,6 +88,7 @@ namespace MediaBrowser.Api private readonly object _timerLock = new object(); public DateTime LastPingDate { get; set; } + public int PingTimeout { get; set; } public TranscodingJob(ILogger logger) diff --git a/MediaBrowser.Api/TvShowsService.cs b/MediaBrowser.Api/TvShowsService.cs index 23062b67b7..3e8daef033 100644 --- a/MediaBrowser.Api/TvShowsService.cs +++ b/MediaBrowser.Api/TvShowsService.cs @@ -73,6 +73,7 @@ namespace MediaBrowser.Api [ApiMember(Name = "EnableUserData", Description = "Optional, include user data", IsRequired = false, DataType = "boolean", ParameterType = "query", Verb = "GET")] public bool? EnableUserData { get; set; } + public bool EnableTotalRecordCount { get; set; } public GetNextUpEpisodes() diff --git a/MediaBrowser.Api/UserLibrary/BaseItemsByNameService.cs b/MediaBrowser.Api/UserLibrary/BaseItemsByNameService.cs index 4802849f48..3d9db90bd6 100644 --- a/MediaBrowser.Api/UserLibrary/BaseItemsByNameService.cs +++ b/MediaBrowser.Api/UserLibrary/BaseItemsByNameService.cs @@ -210,6 +210,7 @@ namespace MediaBrowser.Api.UserLibrary { SetItemCounts(dto, i.Item2); } + return dto; }); diff --git a/MediaBrowser.Api/UserLibrary/BaseItemsRequest.cs b/MediaBrowser.Api/UserLibrary/BaseItemsRequest.cs index 7561b5c892..d9b52b10ef 100644 --- a/MediaBrowser.Api/UserLibrary/BaseItemsRequest.cs +++ b/MediaBrowser.Api/UserLibrary/BaseItemsRequest.cs @@ -322,8 +322,11 @@ namespace MediaBrowser.Api.UserLibrary public bool? CollapseBoxSetItems { get; set; } public int? MinWidth { get; set; } + public int? MinHeight { get; set; } + public int? MaxWidth { get; set; } + public int? MaxHeight { get; set; } /// <summary> diff --git a/MediaBrowser.Api/UserLibrary/UserViewsService.cs b/MediaBrowser.Api/UserLibrary/UserViewsService.cs index 73d5ec6dec..6f1620dddf 100644 --- a/MediaBrowser.Api/UserLibrary/UserViewsService.cs +++ b/MediaBrowser.Api/UserLibrary/UserViewsService.cs @@ -27,6 +27,7 @@ namespace MediaBrowser.Api.UserLibrary [ApiMember(Name = "IncludeExternalContent", Description = "Whether or not to include external views such as channels or live tv", IsRequired = true, DataType = "boolean", ParameterType = "query", Verb = "GET")] public bool? IncludeExternalContent { get; set; } + public bool IncludeHidden { get; set; } public string PresetViews { get; set; } @@ -80,6 +81,7 @@ namespace MediaBrowser.Api.UserLibrary { query.IncludeExternalContent = request.IncludeExternalContent.Value; } + query.IncludeHidden = request.IncludeHidden; if (!string.IsNullOrWhiteSpace(request.PresetViews)) @@ -140,6 +142,7 @@ namespace MediaBrowser.Api.UserLibrary class SpecialViewOption { public string Name { get; set; } + public string Id { get; set; } } } diff --git a/MediaBrowser.Controller/Authentication/IAuthenticationProvider.cs b/MediaBrowser.Controller/Authentication/IAuthenticationProvider.cs index c0324a3841..b10233c71c 100644 --- a/MediaBrowser.Controller/Authentication/IAuthenticationProvider.cs +++ b/MediaBrowser.Controller/Authentication/IAuthenticationProvider.cs @@ -7,7 +7,9 @@ namespace MediaBrowser.Controller.Authentication public interface IAuthenticationProvider { string Name { get; } + bool IsEnabled { get; } + Task<ProviderAuthenticationResult> Authenticate(string username, string password); bool HasPassword(User user); Task ChangePassword(User user, string newPassword); @@ -28,6 +30,7 @@ namespace MediaBrowser.Controller.Authentication public class ProviderAuthenticationResult { public string Username { get; set; } + public string DisplayName { get; set; } } } diff --git a/MediaBrowser.Controller/Authentication/IPasswordResetProvider.cs b/MediaBrowser.Controller/Authentication/IPasswordResetProvider.cs index d9b814f694..693df80ac2 100644 --- a/MediaBrowser.Controller/Authentication/IPasswordResetProvider.cs +++ b/MediaBrowser.Controller/Authentication/IPasswordResetProvider.cs @@ -8,7 +8,9 @@ namespace MediaBrowser.Controller.Authentication public interface IPasswordResetProvider { string Name { get; } + bool IsEnabled { get; } + Task<ForgotPasswordResult> StartForgotPasswordProcess(User user, bool isInNetwork); Task<PinRedeemResult> RedeemPasswordResetPin(string pin); } @@ -16,6 +18,7 @@ namespace MediaBrowser.Controller.Authentication public class PasswordPinCreationResult { public string PinFile { get; set; } + public DateTime ExpirationDate { get; set; } } } diff --git a/MediaBrowser.Controller/Channels/ChannelItemInfo.cs b/MediaBrowser.Controller/Channels/ChannelItemInfo.cs index aff68883b8..00d4d9cb3e 100644 --- a/MediaBrowser.Controller/Channels/ChannelItemInfo.cs +++ b/MediaBrowser.Controller/Channels/ChannelItemInfo.cs @@ -24,7 +24,9 @@ namespace MediaBrowser.Controller.Channels public string Overview { get; set; } public List<string> Genres { get; set; } + public List<string> Studios { get; set; } + public List<string> Tags { get; set; } public List<PersonInfo> People { get; set; } @@ -34,26 +36,33 @@ namespace MediaBrowser.Controller.Channels public long? RunTimeTicks { get; set; } public string ImageUrl { get; set; } + public string OriginalTitle { get; set; } public ChannelMediaType MediaType { get; set; } + public ChannelFolderType FolderType { get; set; } public ChannelMediaContentType ContentType { get; set; } + public ExtraType ExtraType { get; set; } + public List<TrailerType> TrailerTypes { get; set; } public Dictionary<string, string> ProviderIds { get; set; } public DateTime? PremiereDate { get; set; } + public int? ProductionYear { get; set; } public DateTime? DateCreated { get; set; } public DateTime? StartDate { get; set; } + public DateTime? EndDate { get; set; } public int? IndexNumber { get; set; } + public int? ParentIndexNumber { get; set; } public List<MediaSourceInfo> MediaSources { get; set; } @@ -63,7 +72,9 @@ namespace MediaBrowser.Controller.Channels public List<string> Artists { get; set; } public List<string> AlbumArtists { get; set; } + public bool IsLiveStream { get; set; } + public string Etag { get; set; } public ChannelItemInfo() diff --git a/MediaBrowser.Controller/Collections/CollectionCreationOptions.cs b/MediaBrowser.Controller/Collections/CollectionCreationOptions.cs index 51fe4ce290..1e7549d2bc 100644 --- a/MediaBrowser.Controller/Collections/CollectionCreationOptions.cs +++ b/MediaBrowser.Controller/Collections/CollectionCreationOptions.cs @@ -15,6 +15,7 @@ namespace MediaBrowser.Controller.Collections public Dictionary<string, string> ProviderIds { get; set; } public string[] ItemIdList { get; set; } + public Guid[] UserIds { get; set; } public CollectionCreationOptions() diff --git a/MediaBrowser.Controller/Drawing/ImageHelper.cs b/MediaBrowser.Controller/Drawing/ImageHelper.cs index c87a248b58..e1273fe7f3 100644 --- a/MediaBrowser.Controller/Drawing/ImageHelper.cs +++ b/MediaBrowser.Controller/Drawing/ImageHelper.cs @@ -16,6 +16,7 @@ namespace MediaBrowser.Controller.Drawing return newSize; } + return GetSizeEstimate(options); } diff --git a/MediaBrowser.Controller/Drawing/ImageProcessingOptions.cs b/MediaBrowser.Controller/Drawing/ImageProcessingOptions.cs index 870e0278e4..31d2c1bd49 100644 --- a/MediaBrowser.Controller/Drawing/ImageProcessingOptions.cs +++ b/MediaBrowser.Controller/Drawing/ImageProcessingOptions.cs @@ -15,6 +15,7 @@ namespace MediaBrowser.Controller.Drawing } public Guid ItemId { get; set; } + public BaseItem Item { get; set; } public ItemImageInfo Image { get; set; } @@ -38,12 +39,15 @@ namespace MediaBrowser.Controller.Drawing public bool AddPlayedIndicator { get; set; } public int? UnplayedCount { get; set; } + public int? Blur { get; set; } public double PercentPlayed { get; set; } public string BackgroundColor { get; set; } + public string ForegroundLayer { get; set; } + public bool RequiresAutoOrientation { get; set; } private bool HasDefaultOptions(string originalImagePath) @@ -73,14 +77,17 @@ namespace MediaBrowser.Controller.Drawing { return false; } + if (Height.HasValue && !sizeValue.Height.Equals(Height.Value)) { return false; } + if (MaxWidth.HasValue && sizeValue.Width > MaxWidth.Value) { return false; } + if (MaxHeight.HasValue && sizeValue.Height > MaxHeight.Value) { return false; diff --git a/MediaBrowser.Controller/Dto/DtoOptions.cs b/MediaBrowser.Controller/Dto/DtoOptions.cs index cdaf95f5ce..cf301f1e44 100644 --- a/MediaBrowser.Controller/Dto/DtoOptions.cs +++ b/MediaBrowser.Controller/Dto/DtoOptions.cs @@ -14,11 +14,17 @@ namespace MediaBrowser.Controller.Dto }; public ItemFields[] Fields { get; set; } + public ImageType[] ImageTypes { get; set; } + public int ImageTypeLimit { get; set; } + public bool EnableImages { get; set; } + public bool AddProgramRecordingInfo { get; set; } + public bool EnableUserData { get; set; } + public bool AddCurrentProgram { get; set; } public DtoOptions() diff --git a/MediaBrowser.Controller/Entities/AggregateFolder.cs b/MediaBrowser.Controller/Entities/AggregateFolder.cs index 54540e8921..fd0dc31cc4 100644 --- a/MediaBrowser.Controller/Entities/AggregateFolder.cs +++ b/MediaBrowser.Controller/Entities/AggregateFolder.cs @@ -195,6 +195,7 @@ namespace MediaBrowser.Controller.Entities return child; } } + return null; } } diff --git a/MediaBrowser.Controller/Entities/Audio/Audio.cs b/MediaBrowser.Controller/Entities/Audio/Audio.cs index a8ea2157d5..7d10e68317 100644 --- a/MediaBrowser.Controller/Entities/Audio/Audio.cs +++ b/MediaBrowser.Controller/Entities/Audio/Audio.cs @@ -93,6 +93,7 @@ namespace MediaBrowser.Controller.Entities.Audio { songKey = ParentIndexNumber.Value.ToString("0000") + "-" + songKey; } + songKey += Name; if (!string.IsNullOrEmpty(Album)) @@ -117,6 +118,7 @@ namespace MediaBrowser.Controller.Entities.Audio { return UnratedItem.Music; } + return base.GetBlockUnratedType(); } diff --git a/MediaBrowser.Controller/Entities/Audio/MusicAlbum.cs b/MediaBrowser.Controller/Entities/Audio/MusicAlbum.cs index f7b2f95498..c3514e0f62 100644 --- a/MediaBrowser.Controller/Entities/Audio/MusicAlbum.cs +++ b/MediaBrowser.Controller/Entities/Audio/MusicAlbum.cs @@ -56,6 +56,7 @@ namespace MediaBrowser.Controller.Entities.Audio { return LibraryManager.GetArtist(name, options); } + return null; } diff --git a/MediaBrowser.Controller/Entities/Audio/MusicArtist.cs b/MediaBrowser.Controller/Entities/Audio/MusicArtist.cs index 63db3cfab2..cbba1914a5 100644 --- a/MediaBrowser.Controller/Entities/Audio/MusicArtist.cs +++ b/MediaBrowser.Controller/Entities/Audio/MusicArtist.cs @@ -135,6 +135,7 @@ namespace MediaBrowser.Controller.Entities.Audio list.Add("Artist-" + (item.Name ?? string.Empty).RemoveDiacritics()); return list; } + public override string CreatePresentationUniqueKey() { return "Artist-" + (Name ?? string.Empty).RemoveDiacritics(); diff --git a/MediaBrowser.Controller/Entities/Audio/MusicGenre.cs b/MediaBrowser.Controller/Entities/Audio/MusicGenre.cs index 537e9630be..61f35b9427 100644 --- a/MediaBrowser.Controller/Entities/Audio/MusicGenre.cs +++ b/MediaBrowser.Controller/Entities/Audio/MusicGenre.cs @@ -18,6 +18,7 @@ namespace MediaBrowser.Controller.Entities.Audio list.Insert(0, GetType().Name + "-" + (Name ?? string.Empty).RemoveDiacritics()); return list; } + public override string CreatePresentationUniqueKey() { return GetUserDataKeys()[0]; @@ -94,6 +95,7 @@ namespace MediaBrowser.Controller.Entities.Audio Logger.LogDebug("{0} path has changed from {1} to {2}", GetType().Name, Path, newPath); return true; } + return base.RequiresRefresh(); } diff --git a/MediaBrowser.Controller/Entities/AudioBook.cs b/MediaBrowser.Controller/Entities/AudioBook.cs index 4adaf4c6e6..11ff8a2573 100644 --- a/MediaBrowser.Controller/Entities/AudioBook.cs +++ b/MediaBrowser.Controller/Entities/AudioBook.cs @@ -24,10 +24,12 @@ namespace MediaBrowser.Controller.Entities { return SeriesName; } + public string FindSeriesName() { return SeriesName; } + public string FindSeriesPresentationUniqueKey() { return SeriesPresentationUniqueKey; diff --git a/MediaBrowser.Controller/Entities/BaseItem.cs b/MediaBrowser.Controller/Entities/BaseItem.cs index f2de1f2b19..d356cdfd69 100644 --- a/MediaBrowser.Controller/Entities/BaseItem.cs +++ b/MediaBrowser.Controller/Entities/BaseItem.cs @@ -108,6 +108,7 @@ namespace MediaBrowser.Controller.Entities public string PreferredMetadataLanguage { get; set; } public long? Size { get; set; } + public string Container { get; set; } [JsonIgnore] @@ -448,6 +449,7 @@ namespace MediaBrowser.Controller.Entities // hack alert return true; } + if (SourceType == SourceType.Channel) { // hack alert @@ -559,15 +561,25 @@ namespace MediaBrowser.Controller.Entities /// The logger /// </summary> public static ILoggerFactory LoggerFactory { get; set; } + public static ILogger<BaseItem> Logger { get; set; } + public static ILibraryManager LibraryManager { get; set; } + public static IServerConfigurationManager ConfigurationManager { get; set; } + public static IProviderManager ProviderManager { get; set; } + public static ILocalizationManager LocalizationManager { get; set; } + public static IItemRepository ItemRepository { get; set; } + public static IFileSystem FileSystem { get; set; } + public static IUserDataManager UserDataManager { get; set; } + public static IChannelManager ChannelManager { get; set; } + public static IMediaSourceManager MediaSourceManager { get; set; } /// <summary> @@ -644,8 +656,10 @@ namespace MediaBrowser.Controller.Entities _sortName = CreateSortName(); } } + return _sortName; } + set => _sortName = value; } @@ -814,6 +828,7 @@ namespace MediaBrowser.Controller.Entities return item; } } + return null; } @@ -837,6 +852,7 @@ namespace MediaBrowser.Controller.Entities { return null; } + return LibraryManager.GetItemById(id); } } diff --git a/MediaBrowser.Controller/Entities/CollectionFolder.cs b/MediaBrowser.Controller/Entities/CollectionFolder.cs index e5adf88d12..5023c16035 100644 --- a/MediaBrowser.Controller/Entities/CollectionFolder.cs +++ b/MediaBrowser.Controller/Entities/CollectionFolder.cs @@ -23,7 +23,9 @@ namespace MediaBrowser.Controller.Entities public class CollectionFolder : Folder, ICollectionFolder { public static IXmlSerializer XmlSerializer { get; set; } + public static IJsonSerializer JsonSerializer { get; set; } + public static IServerApplicationHost ApplicationHost { get; set; } public CollectionFolder() @@ -155,6 +157,7 @@ namespace MediaBrowser.Controller.Entities } public string[] PhysicalLocationsList { get; set; } + public Guid[] PhysicalFolderIds { get; set; } protected override FileSystemMetadata[] GetFileSystemChildren(IDirectoryService directoryService) diff --git a/MediaBrowser.Controller/Entities/Folder.cs b/MediaBrowser.Controller/Entities/Folder.cs index 3a01b43795..77551702a6 100644 --- a/MediaBrowser.Controller/Entities/Folder.cs +++ b/MediaBrowser.Controller/Entities/Folder.cs @@ -126,10 +126,12 @@ namespace MediaBrowser.Controller.Entities { return false; } + if (this is UserView) { return false; } + return true; } @@ -156,6 +158,7 @@ namespace MediaBrowser.Controller.Entities { item.DateCreated = DateTime.UtcNow; } + if (item.DateModified == DateTime.MinValue) { item.DateModified = DateTime.UtcNow; @@ -501,6 +504,7 @@ namespace MediaBrowser.Controller.Entities { await series.RefreshMetadata(refreshOptions, cancellationToken).ConfigureAwait(false); } + await container.RefreshAllMetadata(refreshOptions, progress, cancellationToken).ConfigureAwait(false); } @@ -939,6 +943,7 @@ namespace MediaBrowser.Controller.Entities { items = items.Where(i => string.Compare(query.NameStartsWithOrGreater, i.SortName, StringComparison.CurrentCultureIgnoreCase) < 1); } + if (!string.IsNullOrEmpty(query.NameStartsWith)) { items = items.Where(i => i.SortName.StartsWith(query.NameStartsWith, StringComparison.OrdinalIgnoreCase)); @@ -989,18 +994,22 @@ namespace MediaBrowser.Controller.Entities { return false; } + if (queryParent is Series) { return false; } + if (queryParent is Season) { return false; } + if (queryParent is MusicAlbum) { return false; } + if (queryParent is MusicArtist) { return false; @@ -1030,22 +1039,27 @@ namespace MediaBrowser.Controller.Entities { return false; } + if (request.IsFavoriteOrLiked.HasValue) { return false; } + if (request.IsLiked.HasValue) { return false; } + if (request.IsPlayed.HasValue) { return false; } + if (request.IsResumable.HasValue) { return false; } + if (request.IsFolder.HasValue) { return false; @@ -1391,6 +1405,7 @@ namespace MediaBrowser.Controller.Entities list.Add(child); } } + return list; } @@ -1413,6 +1428,7 @@ namespace MediaBrowser.Controller.Entities return true; } } + return false; } @@ -1665,22 +1681,27 @@ namespace MediaBrowser.Controller.Entities { return false; } + if (this is UserView) { return false; } + if (this is UserRootFolder) { return false; } + if (this is Channel) { return false; } + if (SourceType != SourceType.Library) { return false; } + var iItemByName = this as IItemByName; if (iItemByName != null) { diff --git a/MediaBrowser.Controller/Entities/Genre.cs b/MediaBrowser.Controller/Entities/Genre.cs index 773c7df341..55634aa5e3 100644 --- a/MediaBrowser.Controller/Entities/Genre.cs +++ b/MediaBrowser.Controller/Entities/Genre.cs @@ -19,6 +19,7 @@ namespace MediaBrowser.Controller.Entities list.Insert(0, GetType().Name + "-" + (Name ?? string.Empty).RemoveDiacritics()); return list; } + public override string CreatePresentationUniqueKey() { return GetUserDataKeys()[0]; @@ -92,6 +93,7 @@ namespace MediaBrowser.Controller.Entities Logger.LogDebug("{0} path has changed from {1} to {2}", GetType().Name, Path, newPath); return true; } + return base.RequiresRefresh(); } diff --git a/MediaBrowser.Controller/Entities/IHasMediaSources.cs b/MediaBrowser.Controller/Entities/IHasMediaSources.cs index 4635b90629..213c0a7946 100644 --- a/MediaBrowser.Controller/Entities/IHasMediaSources.cs +++ b/MediaBrowser.Controller/Entities/IHasMediaSources.cs @@ -13,7 +13,9 @@ namespace MediaBrowser.Controller.Entities List<MediaSourceInfo> GetMediaSources(bool enablePathSubstitution); List<MediaStream> GetMediaStreams(); Guid Id { get; set; } + long? RunTimeTicks { get; set; } + string Path { get; } } } diff --git a/MediaBrowser.Controller/Entities/IHasProgramAttributes.cs b/MediaBrowser.Controller/Entities/IHasProgramAttributes.cs index 777b408287..fd1c19c977 100644 --- a/MediaBrowser.Controller/Entities/IHasProgramAttributes.cs +++ b/MediaBrowser.Controller/Entities/IHasProgramAttributes.cs @@ -5,13 +5,21 @@ namespace MediaBrowser.Controller.Entities public interface IHasProgramAttributes { bool IsMovie { get; set; } + bool IsSports { get; } + bool IsNews { get; } + bool IsKids { get; } + bool IsRepeat { get; set; } + bool IsSeries { get; set; } + ProgramAudio? Audio { get; set; } + string EpisodeTitle { get; set; } + string ServiceName { get; set; } } } diff --git a/MediaBrowser.Controller/Entities/IHasSeries.cs b/MediaBrowser.Controller/Entities/IHasSeries.cs index 7da53f730a..475a2ab856 100644 --- a/MediaBrowser.Controller/Entities/IHasSeries.cs +++ b/MediaBrowser.Controller/Entities/IHasSeries.cs @@ -9,11 +9,14 @@ namespace MediaBrowser.Controller.Entities /// </summary> /// <value>The name of the series.</value> string SeriesName { get; set; } + string FindSeriesName(); string FindSeriesSortName(); Guid SeriesId { get; set; } + Guid FindSeriesId(); string SeriesPresentationUniqueKey { get; set; } + string FindSeriesPresentationUniqueKey(); } } diff --git a/MediaBrowser.Controller/Entities/InternalItemsQuery.cs b/MediaBrowser.Controller/Entities/InternalItemsQuery.cs index 496bee857e..466cda67cb 100644 --- a/MediaBrowser.Controller/Entities/InternalItemsQuery.cs +++ b/MediaBrowser.Controller/Entities/InternalItemsQuery.cs @@ -21,100 +21,167 @@ namespace MediaBrowser.Controller.Entities public BaseItem SimilarTo { get; set; } public bool? IsFolder { get; set; } + public bool? IsFavorite { get; set; } + public bool? IsFavoriteOrLiked { get; set; } + public bool? IsLiked { get; set; } + public bool? IsPlayed { get; set; } + public bool? IsResumable { get; set; } + public bool? IncludeItemsByName { get; set; } public string[] MediaTypes { get; set; } + public string[] IncludeItemTypes { get; set; } + public string[] ExcludeItemTypes { get; set; } + public string[] ExcludeTags { get; set; } + public string[] ExcludeInheritedTags { get; set; } + public string[] Genres { get; set; } public bool? IsSpecialSeason { get; set; } + public bool? IsMissing { get; set; } + public bool? IsUnaired { get; set; } + public bool? CollapseBoxSetItems { get; set; } public string NameStartsWithOrGreater { get; set; } + public string NameStartsWith { get; set; } + public string NameLessThan { get; set; } + public string NameContains { get; set; } + public string MinSortName { get; set; } public string PresentationUniqueKey { get; set; } + public string Path { get; set; } + public string Name { get; set; } public string Person { get; set; } + public Guid[] PersonIds { get; set; } + public Guid[] ItemIds { get; set; } + public Guid[] ExcludeItemIds { get; set; } + public string AdjacentTo { get; set; } + public string[] PersonTypes { get; set; } public bool? Is3D { get; set; } + public bool? IsHD { get; set; } + public bool? IsLocked { get; set; } + public bool? IsPlaceHolder { get; set; } public bool? HasImdbId { get; set; } + public bool? HasOverview { get; set; } + public bool? HasTmdbId { get; set; } + public bool? HasOfficialRating { get; set; } + public bool? HasTvdbId { get; set; } + public bool? HasThemeSong { get; set; } + public bool? HasThemeVideo { get; set; } + public bool? HasSubtitles { get; set; } + public bool? HasSpecialFeature { get; set; } + public bool? HasTrailer { get; set; } + public bool? HasParentalRating { get; set; } public Guid[] StudioIds { get; set; } + public Guid[] GenreIds { get; set; } + public ImageType[] ImageTypes { get; set; } + public VideoType[] VideoTypes { get; set; } + public UnratedItem[] BlockUnratedItems { get; set; } + public int[] Years { get; set; } + public string[] Tags { get; set; } + public string[] OfficialRatings { get; set; } public DateTime? MinPremiereDate { get; set; } + public DateTime? MaxPremiereDate { get; set; } + public DateTime? MinStartDate { get; set; } + public DateTime? MaxStartDate { get; set; } + public DateTime? MinEndDate { get; set; } + public DateTime? MaxEndDate { get; set; } + public bool? IsAiring { get; set; } public bool? IsMovie { get; set; } + public bool? IsSports { get; set; } + public bool? IsKids { get; set; } + public bool? IsNews { get; set; } + public bool? IsSeries { get; set; } + public int? MinIndexNumber { get; set; } + public int? AiredDuringSeason { get; set; } + public double? MinCriticRating { get; set; } + public double? MinCommunityRating { get; set; } public Guid[] ChannelIds { get; set; } public int? ParentIndexNumber { get; set; } + public int? ParentIndexNumberNotEquals { get; set; } + public int? IndexNumber { get; set; } + public int? MinParentalRating { get; set; } + public int? MaxParentalRating { get; set; } public bool? HasDeadParentId { get; set; } + public bool? IsVirtualItem { get; set; } public Guid ParentId { get; set; } + public string ParentType { get; set; } + public Guid[] AncestorIds { get; set; } + public Guid[] TopParentIds { get; set; } public BaseItem Parent @@ -135,41 +202,65 @@ namespace MediaBrowser.Controller.Entities } public string[] PresetViews { get; set; } + public TrailerType[] TrailerTypes { get; set; } + public SourceType[] SourceTypes { get; set; } public SeriesStatus[] SeriesStatuses { get; set; } + public string ExternalSeriesId { get; set; } + public string ExternalId { get; set; } public Guid[] AlbumIds { get; set; } + public Guid[] ArtistIds { get; set; } + public Guid[] ExcludeArtistIds { get; set; } + public string AncestorWithPresentationUniqueKey { get; set; } + public string SeriesPresentationUniqueKey { get; set; } public bool GroupByPresentationUniqueKey { get; set; } + public bool GroupBySeriesPresentationUniqueKey { get; set; } + public bool EnableTotalRecordCount { get; set; } + public bool ForceDirect { get; set; } + public Dictionary<string, string> ExcludeProviderIds { get; set; } + public bool EnableGroupByMetadataKey { get; set; } + public bool? HasChapterImages { get; set; } public IReadOnlyList<(string, SortOrder)> OrderBy { get; set; } public DateTime? MinDateCreated { get; set; } + public DateTime? MinDateLastSaved { get; set; } + public DateTime? MinDateLastSavedForUser { get; set; } public DtoOptions DtoOptions { get; set; } + public int MinSimilarityScore { get; set; } + public string HasNoAudioTrackWithLanguage { get; set; } + public string HasNoInternalSubtitleTrackWithLanguage { get; set; } + public string HasNoExternalSubtitleTrackWithLanguage { get; set; } + public string HasNoSubtitleTrackWithLanguage { get; set; } + public bool? IsDeadArtist { get; set; } + public bool? IsDeadStudio { get; set; } + public bool? IsDeadPerson { get; set; } public InternalItemsQuery() @@ -240,17 +331,29 @@ namespace MediaBrowser.Controller.Entities } public Dictionary<string, string> HasAnyProviderId { get; set; } + public Guid[] AlbumArtistIds { get; set; } + public Guid[] BoxSetLibraryFolders { get; set; } + public Guid[] ContributingArtistIds { get; set; } + public bool? HasAired { get; set; } + public bool? HasOwnerId { get; set; } + public bool? Is4K { get; set; } + public int? MaxHeight { get; set; } + public int? MaxWidth { get; set; } + public int? MinHeight { get; set; } + public int? MinWidth { get; set; } + public string SearchTerm { get; set; } + public string SeriesTimerId { get; set; } } } diff --git a/MediaBrowser.Controller/Entities/LinkedChild.cs b/MediaBrowser.Controller/Entities/LinkedChild.cs index d88c31007a..cb698794bf 100644 --- a/MediaBrowser.Controller/Entities/LinkedChild.cs +++ b/MediaBrowser.Controller/Entities/LinkedChild.cs @@ -9,7 +9,9 @@ namespace MediaBrowser.Controller.Entities public class LinkedChild { public string Path { get; set; } + public LinkedChildType Type { get; set; } + public string LibraryItemId { get; set; } [JsonIgnore] @@ -63,6 +65,7 @@ namespace MediaBrowser.Controller.Entities { return _fileSystem.AreEqual(x.Path, y.Path); } + return false; } diff --git a/MediaBrowser.Controller/Entities/PeopleHelper.cs b/MediaBrowser.Controller/Entities/PeopleHelper.cs index 2fb613768d..c394957593 100644 --- a/MediaBrowser.Controller/Entities/PeopleHelper.cs +++ b/MediaBrowser.Controller/Entities/PeopleHelper.cs @@ -113,6 +113,7 @@ namespace MediaBrowser.Controller.Entities return true; } } + return false; } } diff --git a/MediaBrowser.Controller/Entities/Person.cs b/MediaBrowser.Controller/Entities/Person.cs index 9e4f9d47ed..56106a266d 100644 --- a/MediaBrowser.Controller/Entities/Person.cs +++ b/MediaBrowser.Controller/Entities/Person.cs @@ -19,6 +19,7 @@ namespace MediaBrowser.Controller.Entities list.Insert(0, GetType().Name + "-" + (Name ?? string.Empty).RemoveDiacritics()); return list; } + public override string CreatePresentationUniqueKey() { return GetUserDataKeys()[0]; @@ -114,6 +115,7 @@ namespace MediaBrowser.Controller.Entities Logger.LogDebug("{0} path has changed from {1} to {2}", GetType().Name, Path, newPath); return true; } + return base.RequiresRefresh(); } diff --git a/MediaBrowser.Controller/Entities/Photo.cs b/MediaBrowser.Controller/Entities/Photo.cs index 5ebc9f16ad..82d0826c5a 100644 --- a/MediaBrowser.Controller/Entities/Photo.cs +++ b/MediaBrowser.Controller/Entities/Photo.cs @@ -29,6 +29,7 @@ namespace MediaBrowser.Controller.Entities return photoAlbum; } } + return null; } } @@ -68,17 +69,27 @@ namespace MediaBrowser.Controller.Entities } public string CameraMake { get; set; } + public string CameraModel { get; set; } + public string Software { get; set; } + public double? ExposureTime { get; set; } + public double? FocalLength { get; set; } + public ImageOrientation? Orientation { get; set; } + public double? Aperture { get; set; } + public double? ShutterSpeed { get; set; } public double? Latitude { get; set; } + public double? Longitude { get; set; } + public double? Altitude { get; set; } + public int? IsoSpeedRating { get; set; } } } diff --git a/MediaBrowser.Controller/Entities/Share.cs b/MediaBrowser.Controller/Entities/Share.cs index c17789ccc6..a51f2b4523 100644 --- a/MediaBrowser.Controller/Entities/Share.cs +++ b/MediaBrowser.Controller/Entities/Share.cs @@ -8,6 +8,7 @@ namespace MediaBrowser.Controller.Entities public class Share { public string UserId { get; set; } + public bool CanEdit { get; set; } } } diff --git a/MediaBrowser.Controller/Entities/Studio.cs b/MediaBrowser.Controller/Entities/Studio.cs index 068032317d..b5ee1e9527 100644 --- a/MediaBrowser.Controller/Entities/Studio.cs +++ b/MediaBrowser.Controller/Entities/Studio.cs @@ -18,6 +18,7 @@ namespace MediaBrowser.Controller.Entities list.Insert(0, GetType().Name + "-" + (Name ?? string.Empty).RemoveDiacritics()); return list; } + public override string CreatePresentationUniqueKey() { return GetUserDataKeys()[0]; @@ -93,6 +94,7 @@ namespace MediaBrowser.Controller.Entities Logger.LogDebug("{0} path has changed from {1} to {2}", GetType().Name, Path, newPath); return true; } + return base.RequiresRefresh(); } diff --git a/MediaBrowser.Controller/Entities/TV/Episode.cs b/MediaBrowser.Controller/Entities/TV/Episode.cs index 4ec60e7cd3..ec95c0e669 100644 --- a/MediaBrowser.Controller/Entities/TV/Episode.cs +++ b/MediaBrowser.Controller/Entities/TV/Episode.cs @@ -34,7 +34,9 @@ namespace MediaBrowser.Controller.Entities.TV /// </summary> /// <value>The aired season.</value> public int? AirsBeforeSeasonNumber { get; set; } + public int? AirsAfterSeasonNumber { get; set; } + public int? AirsBeforeEpisodeNumber { get; set; } /// <summary> @@ -94,6 +96,7 @@ namespace MediaBrowser.Controller.Entities.TV { take--; } + list.InsertRange(0, seriesUserDataKeys.Take(take).Select(i => i + ParentIndexNumber.Value.ToString("000") + IndexNumber.Value.ToString("000"))); } @@ -114,6 +117,7 @@ namespace MediaBrowser.Controller.Entities.TV { seriesId = FindSeriesId(); } + return !seriesId.Equals(Guid.Empty) ? (LibraryManager.GetItemById(seriesId) as Series) : null; } } @@ -128,6 +132,7 @@ namespace MediaBrowser.Controller.Entities.TV { seasonId = FindSeasonId(); } + return !seasonId.Equals(Guid.Empty) ? (LibraryManager.GetItemById(seasonId) as Season) : null; } } @@ -160,6 +165,7 @@ namespace MediaBrowser.Controller.Entities.TV { return "Season " + ParentIndexNumber.Value.ToString(CultureInfo.InvariantCulture); } + return "Season Unknown"; } diff --git a/MediaBrowser.Controller/Entities/TV/Season.cs b/MediaBrowser.Controller/Entities/TV/Season.cs index 7dfd1a7597..c96acf9ca0 100644 --- a/MediaBrowser.Controller/Entities/TV/Season.cs +++ b/MediaBrowser.Controller/Entities/TV/Season.cs @@ -81,6 +81,7 @@ namespace MediaBrowser.Controller.Entities.TV { seriesId = FindSeriesId(); } + return seriesId == Guid.Empty ? null : (LibraryManager.GetItemById(seriesId) as Series); } } diff --git a/MediaBrowser.Controller/Entities/TV/Series.cs b/MediaBrowser.Controller/Entities/TV/Series.cs index a519089b3e..315da7a3bf 100644 --- a/MediaBrowser.Controller/Entities/TV/Series.cs +++ b/MediaBrowser.Controller/Entities/TV/Series.cs @@ -30,6 +30,7 @@ namespace MediaBrowser.Controller.Entities.TV } public DayOfWeek[] AirDays { get; set; } + public string AirTime { get; set; } [JsonIgnore] @@ -150,6 +151,7 @@ namespace MediaBrowser.Controller.Entities.TV { query.IncludeItemTypes = new[] { typeof(Episode).Name }; } + query.IsVirtualItem = false; query.Limit = 0; var totalRecordCount = LibraryManager.GetCount(query); diff --git a/MediaBrowser.Controller/Entities/UserItemData.cs b/MediaBrowser.Controller/Entities/UserItemData.cs index ab425ee0f9..4d8db99c49 100644 --- a/MediaBrowser.Controller/Entities/UserItemData.cs +++ b/MediaBrowser.Controller/Entities/UserItemData.cs @@ -105,6 +105,7 @@ namespace MediaBrowser.Controller.Entities return null; } + set { if (value.HasValue) diff --git a/MediaBrowser.Controller/Entities/UserViewBuilder.cs b/MediaBrowser.Controller/Entities/UserViewBuilder.cs index dbfef07776..061e6001c9 100644 --- a/MediaBrowser.Controller/Entities/UserViewBuilder.cs +++ b/MediaBrowser.Controller/Entities/UserViewBuilder.cs @@ -960,6 +960,7 @@ namespace MediaBrowser.Controller.Entities .OfType<Folder>() .Where(UserView.IsEligibleForGrouping); } + return _libraryManager.GetUserRootFolder() .GetChildren(user, true) .OfType<Folder>() @@ -978,6 +979,7 @@ namespace MediaBrowser.Controller.Entities return folder != null && viewTypes.Contains(folder.CollectionType ?? string.Empty, StringComparer.OrdinalIgnoreCase); }).ToArray(); } + return GetMediaFolders(user) .Where(i => { diff --git a/MediaBrowser.Controller/Entities/Video.cs b/MediaBrowser.Controller/Entities/Video.cs index 4cfa0e74d6..8b534f05da 100644 --- a/MediaBrowser.Controller/Entities/Video.cs +++ b/MediaBrowser.Controller/Entities/Video.cs @@ -28,7 +28,9 @@ namespace MediaBrowser.Controller.Entities public string PrimaryVersionId { get; set; } public string[] AdditionalParts { get; set; } + public string[] LocalAlternateVersions { get; set; } + public LinkedChild[] LinkedAlternateVersions { get; set; } [JsonIgnore] @@ -52,15 +54,18 @@ namespace MediaBrowser.Controller.Entities { return false; } + if (extraType.Value == Model.Entities.ExtraType.ThemeVideo) { return false; } + if (extraType.Value == Model.Entities.ExtraType.Trailer) { return false; } } + return true; } } @@ -196,6 +201,7 @@ namespace MediaBrowser.Controller.Entities return video.MediaSourceCount; } } + return LinkedAlternateVersions.Length + LocalAlternateVersions.Length + 1; } } @@ -390,11 +396,13 @@ namespace MediaBrowser.Controller.Entities AdditionalParts = newVideo.AdditionalParts; updateType |= ItemUpdateType.MetadataImport; } + if (!LocalAlternateVersions.SequenceEqual(newVideo.LocalAlternateVersions, StringComparer.Ordinal)) { LocalAlternateVersions = newVideo.LocalAlternateVersions; updateType |= ItemUpdateType.MetadataImport; } + if (VideoType != newVideo.VideoType) { VideoType = newVideo.VideoType; @@ -416,6 +424,7 @@ namespace MediaBrowser.Controller.Entities .Select(i => i.FullName) .ToArray(); } + if (videoType == VideoType.BluRay) { return FileSystem.GetFiles(rootPath, new[] { ".m2ts" }, false, true) @@ -425,6 +434,7 @@ namespace MediaBrowser.Controller.Entities .Select(i => i.FullName) .ToArray(); } + return Array.Empty<string>(); } diff --git a/MediaBrowser.Controller/Entities/Year.cs b/MediaBrowser.Controller/Entities/Year.cs index a01ef5c316..d65b90c256 100644 --- a/MediaBrowser.Controller/Entities/Year.cs +++ b/MediaBrowser.Controller/Entities/Year.cs @@ -103,6 +103,7 @@ namespace MediaBrowser.Controller.Entities Logger.LogDebug("{0} path has changed from {1} to {2}", GetType().Name, Path, newPath); return true; } + return base.RequiresRefresh(); } diff --git a/MediaBrowser.Controller/IO/FileData.cs b/MediaBrowser.Controller/IO/FileData.cs index aa73738155..e655f50eb7 100644 --- a/MediaBrowser.Controller/IO/FileData.cs +++ b/MediaBrowser.Controller/IO/FileData.cs @@ -20,6 +20,7 @@ namespace MediaBrowser.Controller.IO { dict[file.FullName] = file; } + return dict; } @@ -49,6 +50,7 @@ namespace MediaBrowser.Controller.IO { throw new ArgumentNullException(nameof(path)); } + if (args == null) { throw new ArgumentNullException(nameof(args)); @@ -116,6 +118,7 @@ namespace MediaBrowser.Controller.IO returnResult[index] = value; index++; } + return returnResult; } } diff --git a/MediaBrowser.Controller/Library/DeleteOptions.cs b/MediaBrowser.Controller/Library/DeleteOptions.cs index 751b904816..2944d82592 100644 --- a/MediaBrowser.Controller/Library/DeleteOptions.cs +++ b/MediaBrowser.Controller/Library/DeleteOptions.cs @@ -3,6 +3,7 @@ namespace MediaBrowser.Controller.Library public class DeleteOptions { public bool DeleteFileLocation { get; set; } + public bool DeleteFromExternalProvider { get; set; } public DeleteOptions() diff --git a/MediaBrowser.Controller/Library/ILiveStream.cs b/MediaBrowser.Controller/Library/ILiveStream.cs index 734932f17c..7c9a9b20e0 100644 --- a/MediaBrowser.Controller/Library/ILiveStream.cs +++ b/MediaBrowser.Controller/Library/ILiveStream.cs @@ -9,10 +9,15 @@ namespace MediaBrowser.Controller.Library Task Open(CancellationToken openCancellationToken); Task Close(); int ConsumerCount { get; set; } + string OriginalStreamId { get; set; } + string TunerHostId { get; } + bool EnableStreamSharing { get; } + MediaSourceInfo MediaSource { get; set; } + string UniqueId { get; } } } diff --git a/MediaBrowser.Controller/Library/ItemResolveArgs.cs b/MediaBrowser.Controller/Library/ItemResolveArgs.cs index cca85cd3b9..096708ee3f 100644 --- a/MediaBrowser.Controller/Library/ItemResolveArgs.cs +++ b/MediaBrowser.Controller/Library/ItemResolveArgs.cs @@ -129,6 +129,7 @@ namespace MediaBrowser.Controller.Library return item != null; } + return false; } @@ -256,6 +257,7 @@ namespace MediaBrowser.Controller.Library if (args.Path == null && Path == null) return true; return args.Path != null && BaseItem.FileSystem.AreEqual(args.Path, Path); } + return false; } diff --git a/MediaBrowser.Controller/Library/PlaybackProgressEventArgs.cs b/MediaBrowser.Controller/Library/PlaybackProgressEventArgs.cs index b4e2051845..1ed69975ca 100644 --- a/MediaBrowser.Controller/Library/PlaybackProgressEventArgs.cs +++ b/MediaBrowser.Controller/Library/PlaybackProgressEventArgs.cs @@ -13,18 +13,27 @@ namespace MediaBrowser.Controller.Library public class PlaybackProgressEventArgs : EventArgs { public List<User> Users { get; set; } + public long? PlaybackPositionTicks { get; set; } + public BaseItem Item { get; set; } + public BaseItemDto MediaInfo { get; set; } + public string MediaSourceId { get; set; } + public bool IsPaused { get; set; } + public bool IsAutomated { get; set; } public string DeviceId { get; set; } + public string DeviceName { get; set; } + public string ClientName { get; set; } public string PlaySessionId { get; set; } + public SessionInfo Session { get; set; } public PlaybackProgressEventArgs() diff --git a/MediaBrowser.Controller/Library/Profiler.cs b/MediaBrowser.Controller/Library/Profiler.cs index 0febef3d3e..c4935868db 100644 --- a/MediaBrowser.Controller/Library/Profiler.cs +++ b/MediaBrowser.Controller/Library/Profiler.cs @@ -67,6 +67,7 @@ namespace MediaBrowser.Controller.Library message = string.Format("{0} took {1} seconds.", _name, ((float)_stopwatch.ElapsedMilliseconds / 1000).ToString("#0.000")); } + _logger.LogInformation(message); } } diff --git a/MediaBrowser.Controller/Library/TVUtils.cs b/MediaBrowser.Controller/Library/TVUtils.cs index fd5fb6748f..885488851f 100644 --- a/MediaBrowser.Controller/Library/TVUtils.cs +++ b/MediaBrowser.Controller/Library/TVUtils.cs @@ -40,6 +40,7 @@ namespace MediaBrowser.Controller.Library return new DayOfWeek[] { }; } + return null; } } diff --git a/MediaBrowser.Controller/LiveTv/ChannelInfo.cs b/MediaBrowser.Controller/LiveTv/ChannelInfo.cs index 70477fce73..384ca62aaa 100644 --- a/MediaBrowser.Controller/LiveTv/ChannelInfo.cs +++ b/MediaBrowser.Controller/LiveTv/ChannelInfo.cs @@ -67,8 +67,11 @@ namespace MediaBrowser.Controller.LiveTv public bool? IsFavorite { get; set; } public bool? IsHD { get; set; } + public string AudioCodec { get; set; } + public string VideoCodec { get; set; } + public string[] Tags { get; set; } } } diff --git a/MediaBrowser.Controller/LiveTv/ILiveTvManager.cs b/MediaBrowser.Controller/LiveTv/ILiveTvManager.cs index bc3bf78f01..4ac40fe88f 100644 --- a/MediaBrowser.Controller/LiveTv/ILiveTvManager.cs +++ b/MediaBrowser.Controller/LiveTv/ILiveTvManager.cs @@ -286,8 +286,11 @@ namespace MediaBrowser.Controller.LiveTv public class ActiveRecordingInfo { public string Id { get; set; } + public string Path { get; set; } + public TimerInfo Timer { get; set; } + public CancellationTokenSource CancellationTokenSource { get; set; } } } diff --git a/MediaBrowser.Controller/LiveTv/ITunerHost.cs b/MediaBrowser.Controller/LiveTv/ITunerHost.cs index 240ba8c239..3679e4f78f 100644 --- a/MediaBrowser.Controller/LiveTv/ITunerHost.cs +++ b/MediaBrowser.Controller/LiveTv/ITunerHost.cs @@ -50,6 +50,7 @@ namespace MediaBrowser.Controller.LiveTv get; } } + public interface IConfigurableTunerHost { /// <summary> diff --git a/MediaBrowser.Controller/LiveTv/LiveTvConflictException.cs b/MediaBrowser.Controller/LiveTv/LiveTvConflictException.cs index 92b8ee67ca..0e09d1aeba 100644 --- a/MediaBrowser.Controller/LiveTv/LiveTvConflictException.cs +++ b/MediaBrowser.Controller/LiveTv/LiveTvConflictException.cs @@ -10,6 +10,7 @@ namespace MediaBrowser.Controller.LiveTv public LiveTvConflictException() { } + public LiveTvConflictException(string message) : base(message) { diff --git a/MediaBrowser.Controller/LiveTv/ProgramInfo.cs b/MediaBrowser.Controller/LiveTv/ProgramInfo.cs index 5d0f13192d..aa7ad6ff7c 100644 --- a/MediaBrowser.Controller/LiveTv/ProgramInfo.cs +++ b/MediaBrowser.Controller/LiveTv/ProgramInfo.cs @@ -199,6 +199,7 @@ namespace MediaBrowser.Controller.LiveTv public string Etag { get; set; } public Dictionary<string, string> ProviderIds { get; set; } + public Dictionary<string, string> SeriesProviderIds { get; set; } public ProgramInfo() diff --git a/MediaBrowser.Controller/LiveTv/SeriesTimerInfo.cs b/MediaBrowser.Controller/LiveTv/SeriesTimerInfo.cs index 4fbd496c5d..6e7acaae39 100644 --- a/MediaBrowser.Controller/LiveTv/SeriesTimerInfo.cs +++ b/MediaBrowser.Controller/LiveTv/SeriesTimerInfo.cs @@ -57,6 +57,7 @@ namespace MediaBrowser.Controller.LiveTv public bool RecordAnyChannel { get; set; } public int KeepUpTo { get; set; } + public KeepUntil KeepUntil { get; set; } public bool SkipEpisodesInLibrary { get; set; } diff --git a/MediaBrowser.Controller/LiveTv/TimerInfo.cs b/MediaBrowser.Controller/LiveTv/TimerInfo.cs index 46774b2b7a..df98bb6af8 100644 --- a/MediaBrowser.Controller/LiveTv/TimerInfo.cs +++ b/MediaBrowser.Controller/LiveTv/TimerInfo.cs @@ -18,7 +18,9 @@ namespace MediaBrowser.Controller.LiveTv } public Dictionary<string, string> ProviderIds { get; set; } + public Dictionary<string, string> SeriesProviderIds { get; set; } + public string[] Tags { get; set; } /// <summary> @@ -146,10 +148,15 @@ namespace MediaBrowser.Controller.LiveTv public bool IsRepeat { get; set; } public string HomePageUrl { get; set; } + public float? CommunityRating { get; set; } + public string OfficialRating { get; set; } + public string[] Genres { get; set; } + public string RecordingPath { get; set; } + public KeepUntil KeepUntil { get; set; } } } diff --git a/MediaBrowser.Controller/LiveTv/TunerChannelMapping.cs b/MediaBrowser.Controller/LiveTv/TunerChannelMapping.cs index cb02da6352..df3f55c26c 100644 --- a/MediaBrowser.Controller/LiveTv/TunerChannelMapping.cs +++ b/MediaBrowser.Controller/LiveTv/TunerChannelMapping.cs @@ -3,8 +3,11 @@ namespace MediaBrowser.Controller.LiveTv public class TunerChannelMapping { public string Name { get; set; } + public string ProviderChannelName { get; set; } + public string ProviderChannelId { get; set; } + public string Id { get; set; } } } diff --git a/MediaBrowser.Controller/MediaEncoding/EncodingHelper.cs b/MediaBrowser.Controller/MediaEncoding/EncodingHelper.cs index ec90d28f7a..4fff46f4e0 100644 --- a/MediaBrowser.Controller/MediaEncoding/EncodingHelper.cs +++ b/MediaBrowser.Controller/MediaEncoding/EncodingHelper.cs @@ -1699,6 +1699,7 @@ namespace MediaBrowser.Controller.MediaEncoding { return (null, null); } + if (!videoHeight.HasValue && !requestedHeight.HasValue) { return (null, null); @@ -2569,8 +2570,10 @@ namespace MediaBrowser.Controller.MediaEncoding encodingOptions.HardwareDecodingCodecs = Array.Empty<string>(); return null; } + return "-c:v h264_qsv"; } + break; case "hevc": case "h265": @@ -2579,18 +2582,21 @@ namespace MediaBrowser.Controller.MediaEncoding return (isColorDepth10 && !encodingOptions.EnableDecodingColorDepth10Hevc) ? null : "-c:v hevc_qsv"; } + break; case "mpeg2video": if (_mediaEncoder.SupportsDecoder("mpeg2_qsv") && encodingOptions.HardwareDecodingCodecs.Contains("mpeg2video", StringComparer.OrdinalIgnoreCase)) { return "-c:v mpeg2_qsv"; } + break; case "vc1": if (_mediaEncoder.SupportsDecoder("vc1_qsv") && encodingOptions.HardwareDecodingCodecs.Contains("vc1", StringComparer.OrdinalIgnoreCase)) { return "-c:v vc1_qsv"; } + break; case "vp8": if (_mediaEncoder.SupportsDecoder("vp8_qsv") && encodingOptions.HardwareDecodingCodecs.Contains("vp8", StringComparer.OrdinalIgnoreCase)) @@ -2615,8 +2621,16 @@ namespace MediaBrowser.Controller.MediaEncoding case "h264": if (_mediaEncoder.SupportsDecoder("h264_cuvid") && encodingOptions.HardwareDecodingCodecs.Contains("h264", StringComparer.OrdinalIgnoreCase)) { + // cuvid decoder does not support 10-bit input. + if ((videoStream.BitDepth ?? 8) > 8) + { + encodingOptions.HardwareDecodingCodecs = Array.Empty<string>(); + return null; + } + return "-c:v h264_cuvid"; } + break; case "hevc": case "h265": @@ -2625,24 +2639,28 @@ namespace MediaBrowser.Controller.MediaEncoding return (isColorDepth10 && !encodingOptions.EnableDecodingColorDepth10Hevc) ? null : "-c:v hevc_cuvid"; } + break; case "mpeg2video": if (_mediaEncoder.SupportsDecoder("mpeg2_cuvid") && encodingOptions.HardwareDecodingCodecs.Contains("mpeg2video", StringComparer.OrdinalIgnoreCase)) { return "-c:v mpeg2_cuvid"; } + break; case "vc1": if (_mediaEncoder.SupportsDecoder("vc1_cuvid") && encodingOptions.HardwareDecodingCodecs.Contains("vc1", StringComparer.OrdinalIgnoreCase)) { return "-c:v vc1_cuvid"; } + break; case "mpeg4": if (_mediaEncoder.SupportsDecoder("mpeg4_cuvid") && encodingOptions.HardwareDecodingCodecs.Contains("mpeg4", StringComparer.OrdinalIgnoreCase)) { return "-c:v mpeg4_cuvid"; } + break; case "vp8": if (_mediaEncoder.SupportsDecoder("vp8_cuvid") && encodingOptions.HardwareDecodingCodecs.Contains("vp8", StringComparer.OrdinalIgnoreCase)) @@ -2669,6 +2687,7 @@ namespace MediaBrowser.Controller.MediaEncoding { return "-c:v h264_mediacodec"; } + break; case "hevc": case "h265": @@ -2677,24 +2696,28 @@ namespace MediaBrowser.Controller.MediaEncoding return (isColorDepth10 && !encodingOptions.EnableDecodingColorDepth10Hevc) ? null : "-c:v hevc_mediacodec"; } + break; case "mpeg2video": if (_mediaEncoder.SupportsDecoder("mpeg2_mediacodec") && encodingOptions.HardwareDecodingCodecs.Contains("mpeg2video", StringComparer.OrdinalIgnoreCase)) { return "-c:v mpeg2_mediacodec"; } + break; case "mpeg4": if (_mediaEncoder.SupportsDecoder("mpeg4_mediacodec") && encodingOptions.HardwareDecodingCodecs.Contains("mpeg4", StringComparer.OrdinalIgnoreCase)) { return "-c:v mpeg4_mediacodec"; } + break; case "vp8": if (_mediaEncoder.SupportsDecoder("vp8_mediacodec") && encodingOptions.HardwareDecodingCodecs.Contains("vp8", StringComparer.OrdinalIgnoreCase)) { return "-c:v vp8_mediacodec"; } + break; case "vp9": if (_mediaEncoder.SupportsDecoder("vp9_mediacodec") && encodingOptions.HardwareDecodingCodecs.Contains("vp9", StringComparer.OrdinalIgnoreCase)) @@ -2702,6 +2725,7 @@ namespace MediaBrowser.Controller.MediaEncoding return (isColorDepth10 && !encodingOptions.EnableDecodingColorDepth10Vp9) ? null : "-c:v vp9_mediacodec"; } + break; } } @@ -2715,24 +2739,28 @@ namespace MediaBrowser.Controller.MediaEncoding { return "-c:v h264_mmal"; } + break; case "mpeg2video": if (_mediaEncoder.SupportsDecoder("mpeg2_mmal") && encodingOptions.HardwareDecodingCodecs.Contains("mpeg2video", StringComparer.OrdinalIgnoreCase)) { return "-c:v mpeg2_mmal"; } + break; case "mpeg4": if (_mediaEncoder.SupportsDecoder("mpeg4_mmal") && encodingOptions.HardwareDecodingCodecs.Contains("mpeg4", StringComparer.OrdinalIgnoreCase)) { return "-c:v mpeg4_mmal"; } + break; case "vc1": if (_mediaEncoder.SupportsDecoder("vc1_mmal") && encodingOptions.HardwareDecodingCodecs.Contains("vc1", StringComparer.OrdinalIgnoreCase)) { return "-c:v vc1_mmal"; } + break; } } diff --git a/MediaBrowser.Controller/MediaEncoding/EncodingJobInfo.cs b/MediaBrowser.Controller/MediaEncoding/EncodingJobInfo.cs index acf1aae895..0d6654f851 100644 --- a/MediaBrowser.Controller/MediaEncoding/EncodingJobInfo.cs +++ b/MediaBrowser.Controller/MediaEncoding/EncodingJobInfo.cs @@ -127,13 +127,19 @@ namespace MediaBrowser.Controller.MediaEncoding public string AlbumCoverPath { get; set; } public string InputAudioSync { get; set; } + public string InputVideoSync { get; set; } + public TransportStreamTimestamp InputTimestamp { get; set; } public MediaStream AudioStream { get; set; } + public string[] SupportedAudioCodecs { get; set; } + public string[] SupportedVideoCodecs { get; set; } + public string InputContainer { get; set; } + public IsoType? IsoType { get; set; } public BaseEncodingJobOptions BaseRequest { get; set; } @@ -293,6 +299,7 @@ namespace MediaBrowser.Controller.MediaEncoding } public bool IsVideoRequest { get; set; } + public TranscodingJobType TranscodingType { get; set; } public EncodingJobInfo(TranscodingJobType jobType) @@ -672,6 +679,7 @@ namespace MediaBrowser.Controller.MediaEncoding } public IProgress<double> Progress { get; set; } + public virtual void ReportTranscodingProgress(TimeSpan? transcodingPosition, float? framerate, double? percentComplete, long? bytesTranscoded, int? bitRate) { Progress.Report(percentComplete.Value); diff --git a/MediaBrowser.Controller/MediaEncoding/EncodingJobOptions.cs b/MediaBrowser.Controller/MediaEncoding/EncodingJobOptions.cs index addc88174f..8f6fcb9ab1 100644 --- a/MediaBrowser.Controller/MediaEncoding/EncodingJobOptions.cs +++ b/MediaBrowser.Controller/MediaEncoding/EncodingJobOptions.cs @@ -9,9 +9,11 @@ namespace MediaBrowser.Controller.MediaEncoding public class EncodingJobOptions : BaseEncodingJobOptions { public string OutputDirectory { get; set; } + public string ItemId { get; set; } public string TempDirectory { get; set; } + public bool ReadInputAtNativeFramerate { get; set; } /// <summary> @@ -47,6 +49,7 @@ namespace MediaBrowser.Controller.MediaEncoding { SubtitleStreamIndex = info.SubtitleStreamIndex; } + StreamOptions = info.StreamOptions; } } @@ -81,7 +84,9 @@ namespace MediaBrowser.Controller.MediaEncoding public bool EnableAutoStreamCopy { get; set; } public bool AllowVideoStreamCopy { get; set; } + public bool AllowAudioStreamCopy { get; set; } + public bool BreakOnNonKeyFrames { get; set; } /// <summary> @@ -197,10 +202,15 @@ namespace MediaBrowser.Controller.MediaEncoding [ApiMember(Name = "MaxVideoBitDepth", Description = "Optional.", IsRequired = false, DataType = "int", ParameterType = "query", Verb = "GET")] public int? MaxVideoBitDepth { get; set; } + public bool RequireAvc { get; set; } + public bool DeInterlace { get; set; } + public bool RequireNonAnamorphic { get; set; } + public int? TranscodingMaxAudioChannels { get; set; } + public int? CpuCoreLimit { get; set; } public string LiveStreamId { get; set; } diff --git a/MediaBrowser.Controller/MediaEncoding/MediaInfoRequest.cs b/MediaBrowser.Controller/MediaEncoding/MediaInfoRequest.cs index b78ef0b806..39a47792ae 100644 --- a/MediaBrowser.Controller/MediaEncoding/MediaInfoRequest.cs +++ b/MediaBrowser.Controller/MediaEncoding/MediaInfoRequest.cs @@ -8,9 +8,13 @@ namespace MediaBrowser.Controller.MediaEncoding public class MediaInfoRequest { public MediaSourceInfo MediaSource { get; set; } + public bool ExtractChapters { get; set; } + public DlnaProfileType MediaType { get; set; } + public IIsoMount MountedIso { get; set; } + public string[] PlayableStreamFileNames { get; set; } public MediaInfoRequest() diff --git a/MediaBrowser.Controller/Net/AuthenticatedAttribute.cs b/MediaBrowser.Controller/Net/AuthenticatedAttribute.cs index 29fb81e32a..ba3c715b88 100644 --- a/MediaBrowser.Controller/Net/AuthenticatedAttribute.cs +++ b/MediaBrowser.Controller/Net/AuthenticatedAttribute.cs @@ -58,8 +58,11 @@ namespace MediaBrowser.Controller.Net public interface IAuthenticationAttributes { bool EscapeParentalControl { get; } + bool AllowBeforeStartupWizard { get; } + bool AllowLocal { get; } + bool AllowLocalOnly { get; } string[] GetRoles(); diff --git a/MediaBrowser.Controller/Net/BasePeriodicWebSocketListener.cs b/MediaBrowser.Controller/Net/BasePeriodicWebSocketListener.cs index df90c399b9..43016e1c9c 100644 --- a/MediaBrowser.Controller/Net/BasePeriodicWebSocketListener.cs +++ b/MediaBrowser.Controller/Net/BasePeriodicWebSocketListener.cs @@ -254,7 +254,9 @@ namespace MediaBrowser.Controller.Net public class WebSocketListenerState { public DateTime DateLastSendUtc { get; set; } + public long InitialDelayMs { get; set; } + public long IntervalMs { get; set; } } } diff --git a/MediaBrowser.Controller/Net/StaticResultOptions.cs b/MediaBrowser.Controller/Net/StaticResultOptions.cs index 071beaed19..85772e0368 100644 --- a/MediaBrowser.Controller/Net/StaticResultOptions.cs +++ b/MediaBrowser.Controller/Net/StaticResultOptions.cs @@ -8,8 +8,11 @@ namespace MediaBrowser.Controller.Net public class StaticResultOptions { public string ContentType { get; set; } + public TimeSpan? CacheDuration { get; set; } + public DateTime? DateLastModified { get; set; } + public Func<Task<Stream>> ContentFactory { get; set; } public bool IsHeadRequest { get; set; } @@ -17,9 +20,11 @@ namespace MediaBrowser.Controller.Net public IDictionary<string, string> ResponseHeaders { get; set; } public Action OnComplete { get; set; } + public Action OnError { get; set; } public string Path { get; set; } + public long? ContentLength { get; set; } public FileShare FileShare { get; set; } diff --git a/MediaBrowser.Controller/Providers/ImageRefreshOptions.cs b/MediaBrowser.Controller/Providers/ImageRefreshOptions.cs index aac41369c3..3f8c409f5c 100644 --- a/MediaBrowser.Controller/Providers/ImageRefreshOptions.cs +++ b/MediaBrowser.Controller/Providers/ImageRefreshOptions.cs @@ -7,11 +7,13 @@ namespace MediaBrowser.Controller.Providers public class ImageRefreshOptions { public MetadataRefreshMode ImageRefreshMode { get; set; } + public IDirectoryService DirectoryService { get; private set; } public bool ReplaceAllImages { get; set; } public ImageType[] ReplaceImages { get; set; } + public bool IsAutomated { get; set; } public ImageRefreshOptions(IDirectoryService directoryService) diff --git a/MediaBrowser.Controller/Providers/MetadataResult.cs b/MediaBrowser.Controller/Providers/MetadataResult.cs index 59adaedfa9..af955774f0 100644 --- a/MediaBrowser.Controller/Providers/MetadataResult.cs +++ b/MediaBrowser.Controller/Providers/MetadataResult.cs @@ -48,6 +48,7 @@ namespace MediaBrowser.Controller.Providers { People = new List<PersonInfo>(); } + People.Clear(); } diff --git a/MediaBrowser.Controller/Resolvers/IItemResolver.cs b/MediaBrowser.Controller/Resolvers/IItemResolver.cs index 16e37d2493..751ca8098c 100644 --- a/MediaBrowser.Controller/Resolvers/IItemResolver.cs +++ b/MediaBrowser.Controller/Resolvers/IItemResolver.cs @@ -35,6 +35,7 @@ namespace MediaBrowser.Controller.Resolvers public class MultiItemResolverResult { public List<BaseItem> Items { get; set; } + public List<FileSystemMetadata> ExtraFiles { get; set; } public MultiItemResolverResult() diff --git a/MediaBrowser.Controller/Security/AuthenticationInfo.cs b/MediaBrowser.Controller/Security/AuthenticationInfo.cs index 8282135884..1d0b959b73 100644 --- a/MediaBrowser.Controller/Security/AuthenticationInfo.cs +++ b/MediaBrowser.Controller/Security/AuthenticationInfo.cs @@ -65,6 +65,7 @@ namespace MediaBrowser.Controller.Security public DateTime? DateRevoked { get; set; } public DateTime DateLastActivity { get; set; } + public string UserName { get; set; } } } diff --git a/MediaBrowser.Controller/Session/AuthenticationRequest.cs b/MediaBrowser.Controller/Session/AuthenticationRequest.cs index a28f47a9c6..685ca3bddc 100644 --- a/MediaBrowser.Controller/Session/AuthenticationRequest.cs +++ b/MediaBrowser.Controller/Session/AuthenticationRequest.cs @@ -5,13 +5,21 @@ namespace MediaBrowser.Controller.Session public class AuthenticationRequest { public string Username { get; set; } + public Guid UserId { get; set; } + public string Password { get; set; } + public string PasswordSha1 { get; set; } + public string App { get; set; } + public string AppVersion { get; set; } + public string DeviceId { get; set; } + public string DeviceName { get; set; } + public string RemoteEndPoint { get; set; } } } diff --git a/MediaBrowser.Controller/Session/SessionInfo.cs b/MediaBrowser.Controller/Session/SessionInfo.cs index 2ba7c9fec0..36bc11be4f 100644 --- a/MediaBrowser.Controller/Session/SessionInfo.cs +++ b/MediaBrowser.Controller/Session/SessionInfo.cs @@ -61,6 +61,7 @@ namespace MediaBrowser.Controller.Session { return Array.Empty<string>(); } + return Capabilities.PlayableMediaTypes; } } @@ -154,6 +155,7 @@ namespace MediaBrowser.Controller.Session return true; } } + if (controllers.Length > 0) { return false; @@ -255,6 +257,7 @@ namespace MediaBrowser.Controller.Session return true; } } + return false; } @@ -292,6 +295,7 @@ namespace MediaBrowser.Controller.Session { return; } + if (progressInfo.IsPaused) { return; @@ -334,6 +338,7 @@ namespace MediaBrowser.Controller.Session _progressTimer.Dispose(); _progressTimer = null; } + _lastProgressInfo = null; } } diff --git a/MediaBrowser.Controller/Subtitles/SubtitleResponse.cs b/MediaBrowser.Controller/Subtitles/SubtitleResponse.cs index b8ba35a5fe..ad6025927c 100644 --- a/MediaBrowser.Controller/Subtitles/SubtitleResponse.cs +++ b/MediaBrowser.Controller/Subtitles/SubtitleResponse.cs @@ -5,8 +5,11 @@ namespace MediaBrowser.Controller.Subtitles public class SubtitleResponse { public string Language { get; set; } + public string Format { get; set; } + public bool IsForced { get; set; } + public Stream Stream { get; set; } } } diff --git a/MediaBrowser.Controller/Subtitles/SubtitleSearchRequest.cs b/MediaBrowser.Controller/Subtitles/SubtitleSearchRequest.cs index 61dc72258e..a202723b99 100644 --- a/MediaBrowser.Controller/Subtitles/SubtitleSearchRequest.cs +++ b/MediaBrowser.Controller/Subtitles/SubtitleSearchRequest.cs @@ -8,23 +8,35 @@ namespace MediaBrowser.Controller.Subtitles public class SubtitleSearchRequest : IHasProviderIds { public string Language { get; set; } + public string TwoLetterISOLanguageName { get; set; } public VideoContentType ContentType { get; set; } public string MediaPath { get; set; } + public string SeriesName { get; set; } + public string Name { get; set; } + public int? IndexNumber { get; set; } + public int? IndexNumberEnd { get; set; } + public int? ParentIndexNumber { get; set; } + public int? ProductionYear { get; set; } + public long? RuntimeTicks { get; set; } + public bool IsPerfectMatch { get; set; } + public Dictionary<string, string> ProviderIds { get; set; } public bool SearchAllProviders { get; set; } + public string[] DisabledSubtitleFetchers { get; set; } + public string[] SubtitleFetcherOrder { get; set; } public SubtitleSearchRequest() diff --git a/MediaBrowser.Controller/Sync/SyncedFileInfo.cs b/MediaBrowser.Controller/Sync/SyncedFileInfo.cs index 2ff40addb0..687a46d78f 100644 --- a/MediaBrowser.Controller/Sync/SyncedFileInfo.cs +++ b/MediaBrowser.Controller/Sync/SyncedFileInfo.cs @@ -10,6 +10,7 @@ namespace MediaBrowser.Controller.Sync /// </summary> /// <value>The path.</value> public string Path { get; set; } + public string[] PathParts { get; set; } /// <summary> /// Gets or sets the protocol. diff --git a/MediaBrowser.Controller/SyncPlay/GroupInfo.cs b/MediaBrowser.Controller/SyncPlay/GroupInfo.cs index ef8df7d027..d0fac1efa3 100644 --- a/MediaBrowser.Controller/SyncPlay/GroupInfo.cs +++ b/MediaBrowser.Controller/SyncPlay/GroupInfo.cs @@ -122,6 +122,7 @@ namespace MediaBrowser.Controller.SyncPlay { max = Math.Max(max, session.Ping); } + return max; } diff --git a/MediaBrowser.LocalMetadata/Images/EpisodeLocalImageProvider.cs b/MediaBrowser.LocalMetadata/Images/EpisodeLocalImageProvider.cs index 2f4cca5ff6..9d23d80b82 100644 --- a/MediaBrowser.LocalMetadata/Images/EpisodeLocalImageProvider.cs +++ b/MediaBrowser.LocalMetadata/Images/EpisodeLocalImageProvider.cs @@ -75,6 +75,7 @@ namespace MediaBrowser.LocalMetadata.Images } } } + return list; } } diff --git a/MediaBrowser.LocalMetadata/Parsers/BaseItemXmlParser.cs b/MediaBrowser.LocalMetadata/Parsers/BaseItemXmlParser.cs index 0ceb55c572..f954d4192f 100644 --- a/MediaBrowser.LocalMetadata/Parsers/BaseItemXmlParser.cs +++ b/MediaBrowser.LocalMetadata/Parsers/BaseItemXmlParser.cs @@ -24,6 +24,7 @@ namespace MediaBrowser.LocalMetadata.Parsers /// The logger /// </summary> protected ILogger<BaseItemXmlParser<T>> Logger { get; private set; } + protected IProviderManager ProviderManager { get; private set; } private Dictionary<string, string> _validProviderIds; @@ -150,6 +151,7 @@ namespace MediaBrowser.LocalMetadata.Parsers Logger.LogWarning("Invalid Added value found: " + val); } } + break; } @@ -161,6 +163,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.OriginalTitle = val; } + break; } @@ -191,6 +194,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.ForcedSortName = val; } + break; } @@ -274,6 +278,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { reader.Read(); } + break; } @@ -290,6 +295,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { reader.Read(); } + break; } @@ -302,6 +308,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.OfficialRating = rating; } + break; } @@ -313,6 +320,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.CustomRating = val; } + break; } @@ -327,6 +335,7 @@ namespace MediaBrowser.LocalMetadata.Parsers item.RunTimeTicks = TimeSpan.FromMinutes(runtime).Ticks; } } + break; } @@ -339,6 +348,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { hasAspectRatio.AspectRatio = val; } + break; } @@ -350,6 +360,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.IsLocked = string.Equals("true", val, StringComparison.OrdinalIgnoreCase); } + break; } @@ -361,8 +372,10 @@ namespace MediaBrowser.LocalMetadata.Parsers { continue; } + item.AddStudio(name); } + break; } @@ -374,8 +387,10 @@ namespace MediaBrowser.LocalMetadata.Parsers { continue; } + itemResult.AddPerson(p); } + break; } case "Writer": @@ -386,8 +401,10 @@ namespace MediaBrowser.LocalMetadata.Parsers { continue; } + itemResult.AddPerson(p); } + break; } @@ -411,9 +428,11 @@ namespace MediaBrowser.LocalMetadata.Parsers { continue; } + itemResult.AddPerson(p); } } + break; } @@ -425,8 +444,10 @@ namespace MediaBrowser.LocalMetadata.Parsers { continue; } + itemResult.AddPerson(p); } + break; } @@ -438,6 +459,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.AddTrailerUrl(val); } + break; } @@ -453,6 +475,7 @@ namespace MediaBrowser.LocalMetadata.Parsers hasDisplayOrder.DisplayOrder = val; } } + break; } @@ -469,6 +492,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { reader.Read(); } + break; } @@ -501,6 +525,7 @@ namespace MediaBrowser.LocalMetadata.Parsers item.CommunityRating = val; } } + break; } @@ -544,6 +569,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.SetProviderId(MetadataProvider.TmdbCollection, tmdbCollection); } + break; case "Genres": @@ -559,6 +585,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { reader.Read(); } + break; } @@ -575,6 +602,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { reader.Read(); } + break; } @@ -591,6 +619,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { reader.Read(); } + break; } @@ -607,6 +636,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { reader.Read(); } + break; } @@ -627,6 +657,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { reader.Read(); } + break; } @@ -659,6 +690,7 @@ namespace MediaBrowser.LocalMetadata.Parsers video.Video3DFormat = Video3DFormat.MVC; } } + break; } @@ -682,6 +714,7 @@ namespace MediaBrowser.LocalMetadata.Parsers } } } + private void FetchFromSharesNode(XmlReader reader, IHasShares item) { var list = new List<Share>(); @@ -716,6 +749,7 @@ namespace MediaBrowser.LocalMetadata.Parsers break; } + default: { reader.Skip(); @@ -791,6 +825,7 @@ namespace MediaBrowser.LocalMetadata.Parsers if (!string.IsNullOrWhiteSpace(val)) { } + break; } @@ -831,8 +866,10 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.Tagline = val; } + break; } + default: reader.Skip(); break; @@ -870,6 +907,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.AddGenre(genre); } + break; } @@ -907,6 +945,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { tags.Add(tag); } + break; } @@ -949,6 +988,7 @@ namespace MediaBrowser.LocalMetadata.Parsers reader.Read(); continue; } + using (var subtree = reader.ReadSubtree()) { foreach (var person in GetPersonsFromXmlNode(subtree)) @@ -957,9 +997,11 @@ namespace MediaBrowser.LocalMetadata.Parsers { continue; } + item.AddPerson(person); } } + break; } @@ -995,6 +1037,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.AddTrailerUrl(val); } + break; } @@ -1035,6 +1078,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { item.AddStudio(studio); } + break; } @@ -1084,6 +1128,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { type = val; } + break; } @@ -1095,6 +1140,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { role = val; } + break; } case "SortOrder": @@ -1108,6 +1154,7 @@ namespace MediaBrowser.LocalMetadata.Parsers sortOrder = intVal; } } + break; } @@ -1206,6 +1253,7 @@ namespace MediaBrowser.LocalMetadata.Parsers item.CanEdit = string.Equals(reader.ReadElementContentAsString(), "true", StringComparison.OrdinalIgnoreCase); break; } + default: { reader.Skip(); diff --git a/MediaBrowser.LocalMetadata/Parsers/BoxSetXmlParser.cs b/MediaBrowser.LocalMetadata/Parsers/BoxSetXmlParser.cs index ca11a079d2..dd4eefa500 100644 --- a/MediaBrowser.LocalMetadata/Parsers/BoxSetXmlParser.cs +++ b/MediaBrowser.LocalMetadata/Parsers/BoxSetXmlParser.cs @@ -26,6 +26,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { reader.Read(); } + break; default: @@ -69,6 +70,7 @@ namespace MediaBrowser.LocalMetadata.Parsers break; } + default: { reader.Skip(); diff --git a/MediaBrowser.LocalMetadata/Parsers/PlaylistXmlParser.cs b/MediaBrowser.LocalMetadata/Parsers/PlaylistXmlParser.cs index 54710cd825..941ed1b95c 100644 --- a/MediaBrowser.LocalMetadata/Parsers/PlaylistXmlParser.cs +++ b/MediaBrowser.LocalMetadata/Parsers/PlaylistXmlParser.cs @@ -35,6 +35,7 @@ namespace MediaBrowser.LocalMetadata.Parsers { reader.Read(); } + break; default: @@ -77,6 +78,7 @@ namespace MediaBrowser.LocalMetadata.Parsers break; } + default: { reader.Skip(); diff --git a/MediaBrowser.LocalMetadata/Savers/BaseXmlSaver.cs b/MediaBrowser.LocalMetadata/Savers/BaseXmlSaver.cs index 071902393f..70fd63ff32 100644 --- a/MediaBrowser.LocalMetadata/Savers/BaseXmlSaver.cs +++ b/MediaBrowser.LocalMetadata/Savers/BaseXmlSaver.cs @@ -32,10 +32,15 @@ namespace MediaBrowser.LocalMetadata.Savers } protected IFileSystem FileSystem { get; private set; } + protected IServerConfigurationManager ConfigurationManager { get; private set; } + protected ILibraryManager LibraryManager { get; private set; } + protected IUserManager UserManager { get; private set; } + protected IUserDataManager UserDataManager { get; private set; } + protected ILogger<BaseXmlSaver> Logger { get; private set; } public string Name => XmlProviderUtils.Name; @@ -185,6 +190,7 @@ namespace MediaBrowser.LocalMetadata.Savers { writer.WriteElementString("OriginalTitle", item.OriginalTitle); } + if (!string.IsNullOrEmpty(item.CustomRating)) { writer.WriteElementString("CustomRating", item.CustomRating); @@ -278,6 +284,7 @@ namespace MediaBrowser.LocalMetadata.Savers { writer.WriteElementString("Language", item.PreferredMetadataLanguage); } + if (!string.IsNullOrEmpty(item.PreferredMetadataCountryCode)) { writer.WriteElementString("CountryCode", item.PreferredMetadataCountryCode); diff --git a/MediaBrowser.MediaEncoding/Encoder/MediaEncoder.cs b/MediaBrowser.MediaEncoding/Encoder/MediaEncoder.cs index 82f6ce15ec..a8df27d38b 100644 --- a/MediaBrowser.MediaEncoding/Encoder/MediaEncoder.cs +++ b/MediaBrowser.MediaEncoding/Encoder/MediaEncoder.cs @@ -229,6 +229,7 @@ namespace MediaBrowser.MediaEncoding.Encoder { return inJellyfinPath; } + var values = Environment.GetEnvironmentVariable("PATH"); foreach (var path in values.Split(Path.PathSeparator)) diff --git a/MediaBrowser.MediaEncoding/Probing/ProbeResultNormalizer.cs b/MediaBrowser.MediaEncoding/Probing/ProbeResultNormalizer.cs index 7d57a691e6..918694e66e 100644 --- a/MediaBrowser.MediaEncoding/Probing/ProbeResultNormalizer.cs +++ b/MediaBrowser.MediaEncoding/Probing/ProbeResultNormalizer.cs @@ -93,6 +93,7 @@ namespace MediaBrowser.MediaEncoding.Probing { overview = FFProbeHelpers.GetDictionaryValue(tags, "description"); } + if (string.IsNullOrWhiteSpace(overview)) { overview = FFProbeHelpers.GetDictionaryValue(tags, "desc"); @@ -274,10 +275,12 @@ namespace MediaBrowser.MediaEncoding.Probing reader.Read(); continue; } + using (var subtree = reader.ReadSubtree()) { ReadFromDictNode(subtree, info); } + break; default: reader.Skip(); @@ -319,6 +322,7 @@ namespace MediaBrowser.MediaEncoding.Probing { ProcessPairs(currentKey, pairs, info); } + currentKey = reader.ReadElementContentAsString(); pairs = new List<NameValuePair>(); break; @@ -332,6 +336,7 @@ namespace MediaBrowser.MediaEncoding.Probing Value = value }); } + break; case "array": if (reader.IsEmptyElement) @@ -339,6 +344,7 @@ namespace MediaBrowser.MediaEncoding.Probing reader.Read(); continue; } + using (var subtree = reader.ReadSubtree()) { if (!string.IsNullOrWhiteSpace(currentKey)) @@ -346,6 +352,7 @@ namespace MediaBrowser.MediaEncoding.Probing pairs.AddRange(ReadValueArray(subtree)); } } + break; default: reader.Skip(); @@ -381,6 +388,7 @@ namespace MediaBrowser.MediaEncoding.Probing reader.Read(); continue; } + using (var subtree = reader.ReadSubtree()) { var dict = GetNameValuePair(subtree); @@ -389,6 +397,7 @@ namespace MediaBrowser.MediaEncoding.Probing pairs.Add(dict); } } + break; default: reader.Skip(); @@ -948,6 +957,7 @@ namespace MediaBrowser.MediaEncoding.Probing { peoples.Add(new BaseItemPerson { Name = person, Type = PersonType.Composer }); } + audio.People = peoples.ToArray(); } @@ -979,6 +989,7 @@ namespace MediaBrowser.MediaEncoding.Probing { peoples.Add(new BaseItemPerson { Name = person, Type = PersonType.Writer }); } + audio.People = peoples.ToArray(); } @@ -1012,6 +1023,7 @@ namespace MediaBrowser.MediaEncoding.Probing { albumArtist = FFProbeHelpers.GetDictionaryValue(tags, "album artist"); } + if (string.IsNullOrWhiteSpace(albumArtist)) { albumArtist = FFProbeHelpers.GetDictionaryValue(tags, "album_artist"); @@ -1175,6 +1187,7 @@ namespace MediaBrowser.MediaEncoding.Probing { continue; } + if (info.AlbumArtists.Contains(studio, StringComparer.OrdinalIgnoreCase)) { continue; diff --git a/MediaBrowser.MediaEncoding/Subtitles/AssParser.cs b/MediaBrowser.MediaEncoding/Subtitles/AssParser.cs index f44cf14523..0e2d70017c 100644 --- a/MediaBrowser.MediaEncoding/Subtitles/AssParser.cs +++ b/MediaBrowser.MediaEncoding/Subtitles/AssParser.cs @@ -23,6 +23,7 @@ namespace MediaBrowser.MediaEncoding.Subtitles string line; while (reader.ReadLine() != "[Events]") { } + var headers = ParseFieldHeaders(reader.ReadLine()); while ((line = reader.ReadLine()) != null) @@ -56,6 +57,7 @@ namespace MediaBrowser.MediaEncoding.Subtitles trackEvents.Add(subEvent); } } + trackInfo.TrackEvents = trackEvents.ToArray(); return trackInfo; } @@ -112,11 +114,13 @@ namespace MediaBrowser.MediaEncoding.Subtitles { pre = s.Substring(0, 5) + "}"; } + int indexOfEnd = p.Text.IndexOf('}'); p.Text = p.Text.Remove(indexOfBegin, (indexOfEnd - indexOfBegin) + 1); indexOfBegin = p.Text.IndexOf('{'); } + p.Text = pre + p.Text; } } diff --git a/MediaBrowser.MediaEncoding/Subtitles/SrtParser.cs b/MediaBrowser.MediaEncoding/Subtitles/SrtParser.cs index c98dd15024..a8d383a2ad 100644 --- a/MediaBrowser.MediaEncoding/Subtitles/SrtParser.cs +++ b/MediaBrowser.MediaEncoding/Subtitles/SrtParser.cs @@ -35,6 +35,7 @@ namespace MediaBrowser.MediaEncoding.Subtitles { continue; } + var subEvent = new SubtitleTrackEvent { Id = line }; line = reader.ReadLine(); @@ -52,6 +53,7 @@ namespace MediaBrowser.MediaEncoding.Subtitles _logger.LogWarning("Unrecognized line in srt: {0}", line); continue; } + subEvent.StartPositionTicks = GetTicks(time[0]); var endTime = time[1]; var idx = endTime.IndexOf(" ", StringComparison.Ordinal); @@ -65,8 +67,10 @@ namespace MediaBrowser.MediaEncoding.Subtitles { break; } + multiline.Add(line); } + subEvent.Text = string.Join(ParserValues.NewLine, multiline); subEvent.Text = subEvent.Text.Replace(@"\N", ParserValues.NewLine, StringComparison.OrdinalIgnoreCase); subEvent.Text = Regex.Replace(subEvent.Text, @"\{(?:\\\d?[\w.-]+(?:\([^\)]*\)|&H?[0-9A-Fa-f]+&|))+\}", string.Empty, RegexOptions.IgnoreCase); @@ -76,6 +80,7 @@ namespace MediaBrowser.MediaEncoding.Subtitles trackEvents.Add(subEvent); } } + trackInfo.TrackEvents = trackEvents.ToArray(); return trackInfo; } diff --git a/MediaBrowser.MediaEncoding/Subtitles/SsaParser.cs b/MediaBrowser.MediaEncoding/Subtitles/SsaParser.cs index bae2f54176..9a8fcc4316 100644 --- a/MediaBrowser.MediaEncoding/Subtitles/SsaParser.cs +++ b/MediaBrowser.MediaEncoding/Subtitles/SsaParser.cs @@ -135,6 +135,7 @@ namespace MediaBrowser.MediaEncoding.Subtitles // subtitle.Renumber(1); } + trackInfo.TrackEvents = trackEvents.ToArray(); return trackInfo; } @@ -302,6 +303,7 @@ namespace MediaBrowser.MediaEncoding.Subtitles return count; index = text.IndexOf(tag, index + 1); } + return count; } @@ -329,6 +331,7 @@ namespace MediaBrowser.MediaEncoding.Subtitles { rest = string.Empty; } + extraTags += " size=\"" + fontSize.Substring(2) + "\""; } else if (rest.StartsWith("fn") && rest.Length > 2) @@ -344,6 +347,7 @@ namespace MediaBrowser.MediaEncoding.Subtitles { rest = string.Empty; } + extraTags += " face=\"" + fontName.Substring(2) + "\""; } else if (rest.StartsWith("c") && rest.Length > 2) diff --git a/MediaBrowser.MediaEncoding/Subtitles/SubtitleEncoder.cs b/MediaBrowser.MediaEncoding/Subtitles/SubtitleEncoder.cs index e35a626d83..b9d526a223 100644 --- a/MediaBrowser.MediaEncoding/Subtitles/SubtitleEncoder.cs +++ b/MediaBrowser.MediaEncoding/Subtitles/SubtitleEncoder.cs @@ -115,6 +115,7 @@ namespace MediaBrowser.MediaEncoding.Subtitles { throw new ArgumentNullException(nameof(item)); } + if (string.IsNullOrWhiteSpace(mediaSourceId)) { throw new ArgumentNullException(nameof(mediaSourceId)); @@ -271,8 +272,11 @@ namespace MediaBrowser.MediaEncoding.Subtitles } public string Path { get; set; } + public MediaProtocol Protocol { get; set; } + public string Format { get; set; } + public bool IsExternal { get; set; } } @@ -287,10 +291,12 @@ namespace MediaBrowser.MediaEncoding.Subtitles { return new SrtParser(_logger); } + if (string.Equals(format, SubtitleFormat.SSA, StringComparison.OrdinalIgnoreCase)) { return new SsaParser(); } + if (string.Equals(format, SubtitleFormat.ASS, StringComparison.OrdinalIgnoreCase)) { return new AssParser(); @@ -315,14 +321,17 @@ namespace MediaBrowser.MediaEncoding.Subtitles { return new JsonWriter(); } + if (string.Equals(format, SubtitleFormat.SRT, StringComparison.OrdinalIgnoreCase)) { return new SrtWriter(); } + if (string.Equals(format, SubtitleFormat.VTT, StringComparison.OrdinalIgnoreCase)) { return new VttWriter(); } + if (string.Equals(format, SubtitleFormat.TTML, StringComparison.OrdinalIgnoreCase)) { return new TtmlWriter(); diff --git a/MediaBrowser.Model/Configuration/LibraryOptions.cs b/MediaBrowser.Model/Configuration/LibraryOptions.cs index 4229a4335b..890469d361 100644 --- a/MediaBrowser.Model/Configuration/LibraryOptions.cs +++ b/MediaBrowser.Model/Configuration/LibraryOptions.cs @@ -10,17 +10,27 @@ namespace MediaBrowser.Model.Configuration public class LibraryOptions { public bool EnablePhotos { get; set; } + public bool EnableRealtimeMonitor { get; set; } + public bool EnableChapterImageExtraction { get; set; } + public bool ExtractChapterImagesDuringLibraryScan { get; set; } + public bool DownloadImagesInAdvance { get; set; } + public MediaPathInfo[] PathInfos { get; set; } public bool SaveLocalMetadata { get; set; } + public bool EnableInternetProviders { get; set; } + public bool ImportMissingEpisodes { get; set; } + public bool EnableAutomaticSeriesGrouping { get; set; } + public bool EnableEmbeddedTitles { get; set; } + public bool EnableEmbeddedEpisodeInfos { get; set; } public int AutomaticRefreshIntervalDays { get; set; } @@ -38,17 +48,25 @@ namespace MediaBrowser.Model.Configuration public string MetadataCountryCode { get; set; } public string SeasonZeroDisplayName { get; set; } + public string[] MetadataSavers { get; set; } + public string[] DisabledLocalMetadataReaders { get; set; } + public string[] LocalMetadataReaderOrder { get; set; } public string[] DisabledSubtitleFetchers { get; set; } + public string[] SubtitleFetcherOrder { get; set; } public bool SkipSubtitlesIfEmbeddedSubtitlesPresent { get; set; } + public bool SkipSubtitlesIfAudioTrackMatches { get; set; } + public string[] SubtitleDownloadLanguages { get; set; } + public bool RequirePerfectSubtitleMatch { get; set; } + public bool SaveSubtitlesWithMedia { get; set; } public TypeOptions[] TypeOptions { get; set; } @@ -89,17 +107,22 @@ namespace MediaBrowser.Model.Configuration public class MediaPathInfo { public string Path { get; set; } + public string NetworkPath { get; set; } } public class TypeOptions { public string Type { get; set; } + public string[] MetadataFetchers { get; set; } + public string[] MetadataFetcherOrder { get; set; } public string[] ImageFetchers { get; set; } + public string[] ImageFetcherOrder { get; set; } + public ImageOption[] ImageOptions { get; set; } public ImageOption GetImageOptions(ImageType type) diff --git a/MediaBrowser.Model/Configuration/UserConfiguration.cs b/MediaBrowser.Model/Configuration/UserConfiguration.cs index 85d864eec4..a5179f3ca3 100644 --- a/MediaBrowser.Model/Configuration/UserConfiguration.cs +++ b/MediaBrowser.Model/Configuration/UserConfiguration.cs @@ -34,6 +34,7 @@ namespace MediaBrowser.Model.Configuration public string[] GroupedFolders { get; set; } public SubtitlePlaybackMode SubtitleMode { get; set; } + public bool DisplayCollectionsView { get; set; } public bool EnableLocalPassword { get; set; } @@ -41,12 +42,15 @@ namespace MediaBrowser.Model.Configuration public string[] OrderedViews { get; set; } public string[] LatestItemsExcludes { get; set; } + public string[] MyMediaExcludes { get; set; } public bool HidePlayedInLatest { get; set; } public bool RememberAudioSelections { get; set; } + public bool RememberSubtitleSelections { get; set; } + public bool EnableNextEpisodeAutoPlay { get; set; } /// <summary> diff --git a/MediaBrowser.Model/Configuration/XbmcMetadataOptions.cs b/MediaBrowser.Model/Configuration/XbmcMetadataOptions.cs index c48a381928..4d5f996f84 100644 --- a/MediaBrowser.Model/Configuration/XbmcMetadataOptions.cs +++ b/MediaBrowser.Model/Configuration/XbmcMetadataOptions.cs @@ -10,6 +10,7 @@ namespace MediaBrowser.Model.Configuration public string ReleaseDateFormat { get; set; } public bool SaveImagePathsInNfo { get; set; } + public bool EnablePathSubstitution { get; set; } public bool EnableExtraThumbsDuplication { get; set; } diff --git a/MediaBrowser.Model/Dlna/AudioOptions.cs b/MediaBrowser.Model/Dlna/AudioOptions.cs index fc555c5f70..1468b0414f 100644 --- a/MediaBrowser.Model/Dlna/AudioOptions.cs +++ b/MediaBrowser.Model/Dlna/AudioOptions.cs @@ -85,6 +85,7 @@ namespace MediaBrowser.Model.Dlna { return Profile.MaxStaticMusicBitrate; } + return Profile.MaxStaticBitrate; } diff --git a/MediaBrowser.Model/Dlna/DeviceProfile.cs b/MediaBrowser.Model/Dlna/DeviceProfile.cs index 6462ffdc13..7e921b1fdf 100644 --- a/MediaBrowser.Model/Dlna/DeviceProfile.cs +++ b/MediaBrowser.Model/Dlna/DeviceProfile.cs @@ -27,16 +27,25 @@ namespace MediaBrowser.Model.Dlna public DeviceIdentification Identification { get; set; } public string FriendlyName { get; set; } + public string Manufacturer { get; set; } + public string ManufacturerUrl { get; set; } + public string ModelName { get; set; } + public string ModelDescription { get; set; } + public string ModelNumber { get; set; } + public string ModelUrl { get; set; } + public string SerialNumber { get; set; } public bool EnableAlbumArtInDidl { get; set; } + public bool EnableSingleAlbumArtLimit { get; set; } + public bool EnableSingleSubtitleLimit { get; set; } public string SupportedMediaTypes { get; set; } @@ -46,15 +55,19 @@ namespace MediaBrowser.Model.Dlna public string AlbumArtPn { get; set; } public int MaxAlbumArtWidth { get; set; } + public int MaxAlbumArtHeight { get; set; } public int? MaxIconWidth { get; set; } + public int? MaxIconHeight { get; set; } public long? MaxStreamingBitrate { get; set; } + public long? MaxStaticBitrate { get; set; } public int? MusicStreamingTranscodingBitrate { get; set; } + public int? MaxStaticMusicBitrate { get; set; } /// <summary> @@ -65,10 +78,13 @@ namespace MediaBrowser.Model.Dlna public string ProtocolInfo { get; set; } public int TimelineOffsetSeconds { get; set; } + public bool RequiresPlainVideoItems { get; set; } + public bool RequiresPlainFolders { get; set; } public bool EnableMSMediaReceiverRegistrar { get; set; } + public bool IgnoreTranscodeByteRangeRequests { get; set; } public XmlAttribute[] XmlRootAttributes { get; set; } @@ -88,6 +104,7 @@ namespace MediaBrowser.Model.Dlna public ContainerProfile[] ContainerProfiles { get; set; } public CodecProfile[] CodecProfiles { get; set; } + public ResponseProfile[] ResponseProfiles { get; set; } public SubtitleProfile[] SubtitleProfiles { get; set; } @@ -169,6 +186,7 @@ namespace MediaBrowser.Model.Dlna return i; } + return null; } @@ -209,6 +227,7 @@ namespace MediaBrowser.Model.Dlna return i; } + return null; } @@ -254,6 +273,7 @@ namespace MediaBrowser.Model.Dlna return i; } + return null; } @@ -318,6 +338,7 @@ namespace MediaBrowser.Model.Dlna return i; } + return null; } } diff --git a/MediaBrowser.Model/Dlna/MediaFormatProfileResolver.cs b/MediaBrowser.Model/Dlna/MediaFormatProfileResolver.cs index c03a8060f6..47cc892107 100644 --- a/MediaBrowser.Model/Dlna/MediaFormatProfileResolver.cs +++ b/MediaBrowser.Model/Dlna/MediaFormatProfileResolver.cs @@ -107,6 +107,7 @@ namespace MediaBrowser.Model.Dlna return list.ToArray(); } + if (string.Equals(videoCodec, "h264", StringComparison.OrdinalIgnoreCase)) { if (string.Equals(audioCodec, "lpcm", StringComparison.OrdinalIgnoreCase)) @@ -150,8 +151,10 @@ namespace MediaBrowser.Model.Dlna { return new MediaFormatProfile[] { MediaFormatProfile.VC1_TS_AP_L2_AC3_ISO }; } + return new MediaFormatProfile[] { MediaFormatProfile.VC1_TS_AP_L1_AC3_ISO }; } + if (string.Equals(audioCodec, "dts", StringComparison.OrdinalIgnoreCase)) { suffix = string.Equals(suffix, "_ISO", StringComparison.OrdinalIgnoreCase) ? suffix : "_T"; @@ -190,10 +193,12 @@ namespace MediaBrowser.Model.Dlna { return MediaFormatProfile.AVC_MP4_MP_SD_AC3; } + if (string.Equals(audioCodec, "mp3", StringComparison.OrdinalIgnoreCase)) { return MediaFormatProfile.AVC_MP4_MP_SD_MPEG1_L3; } + if (width.HasValue && height.HasValue) { if ((width.Value <= 720) && (height.Value <= 576)) @@ -277,6 +282,7 @@ namespace MediaBrowser.Model.Dlna { return MediaFormatProfile.WMVMED_FULL; } + return MediaFormatProfile.WMVMED_PRO; } } @@ -285,6 +291,7 @@ namespace MediaBrowser.Model.Dlna { return MediaFormatProfile.WMVHIGH_FULL; } + return MediaFormatProfile.WMVHIGH_PRO; } @@ -342,6 +349,7 @@ namespace MediaBrowser.Model.Dlna { return MediaFormatProfile.WMA_BASE; } + return MediaFormatProfile.WMA_FULL; } @@ -353,14 +361,17 @@ namespace MediaBrowser.Model.Dlna { return MediaFormatProfile.LPCM16_44_MONO; } + if (frequency.Value == 44100 && channels.Value == 2) { return MediaFormatProfile.LPCM16_44_STEREO; } + if (frequency.Value == 48000 && channels.Value == 1) { return MediaFormatProfile.LPCM16_48_MONO; } + if (frequency.Value == 48000 && channels.Value == 2) { return MediaFormatProfile.LPCM16_48_STEREO; @@ -378,6 +389,7 @@ namespace MediaBrowser.Model.Dlna { return MediaFormatProfile.AAC_ISO_320; } + return MediaFormatProfile.AAC_ISO; } @@ -387,6 +399,7 @@ namespace MediaBrowser.Model.Dlna { return MediaFormatProfile.AAC_ADTS_320; } + return MediaFormatProfile.AAC_ADTS; } diff --git a/MediaBrowser.Model/Dlna/StreamBuilder.cs b/MediaBrowser.Model/Dlna/StreamBuilder.cs index 3fe5cf7741..06bd244763 100644 --- a/MediaBrowser.Model/Dlna/StreamBuilder.cs +++ b/MediaBrowser.Model/Dlna/StreamBuilder.cs @@ -627,10 +627,12 @@ namespace MediaBrowser.Model.Dlna { playlistItem.MinSegments = transcodingProfile.MinSegments; } + if (transcodingProfile.SegmentLength > 0) { playlistItem.SegmentLength = transcodingProfile.SegmentLength; } + playlistItem.SubProtocol = transcodingProfile.Protocol; if (!string.IsNullOrEmpty(transcodingProfile.MaxAudioChannels) @@ -947,6 +949,7 @@ namespace MediaBrowser.Model.Dlna { return (PlayMethod.DirectPlay, new List<TranscodeReason>()); } + if (options.ForceDirectStream) { return (PlayMethod.DirectStream, new List<TranscodeReason>()); @@ -1261,6 +1264,7 @@ namespace MediaBrowser.Model.Dlna return true; } } + return false; } @@ -1363,14 +1367,17 @@ namespace MediaBrowser.Model.Dlna { throw new ArgumentException("ItemId is required"); } + if (string.IsNullOrEmpty(options.DeviceId)) { throw new ArgumentException("DeviceId is required"); } + if (options.Profile == null) { throw new ArgumentException("Profile is required"); } + if (options.MediaSources == null) { throw new ArgumentException("MediaSources is required"); @@ -1418,6 +1425,7 @@ namespace MediaBrowser.Model.Dlna item.AudioBitrate = Math.Max(num, item.AudioBitrate ?? num); } } + break; } case ProfileConditionValue.AudioChannels: @@ -1452,6 +1460,7 @@ namespace MediaBrowser.Model.Dlna item.SetOption(qualifier, "audiochannels", Math.Max(num, item.GetTargetAudioChannels(qualifier) ?? num).ToString(CultureInfo.InvariantCulture)); } } + break; } case ProfileConditionValue.IsAvc: @@ -1472,6 +1481,7 @@ namespace MediaBrowser.Model.Dlna item.RequireAvc = true; } } + break; } case ProfileConditionValue.IsAnamorphic: @@ -1492,6 +1502,7 @@ namespace MediaBrowser.Model.Dlna item.RequireNonAnamorphic = true; } } + break; } case ProfileConditionValue.IsInterlaced: @@ -1522,6 +1533,7 @@ namespace MediaBrowser.Model.Dlna item.SetOption(qualifier, "deinterlace", "true"); } } + break; } case ProfileConditionValue.AudioProfile: @@ -1567,6 +1579,7 @@ namespace MediaBrowser.Model.Dlna item.SetOption(qualifier, "maxrefframes", Math.Max(num, item.GetTargetRefFrames(qualifier) ?? num).ToString(CultureInfo.InvariantCulture)); } } + break; } case ProfileConditionValue.VideoBitDepth: @@ -1601,6 +1614,7 @@ namespace MediaBrowser.Model.Dlna item.SetOption(qualifier, "videobitdepth", Math.Max(num, item.GetTargetVideoBitDepth(qualifier) ?? num).ToString(CultureInfo.InvariantCulture)); } } + break; } case ProfileConditionValue.VideoProfile: @@ -1623,6 +1637,7 @@ namespace MediaBrowser.Model.Dlna item.SetOption(qualifier, "profile", string.Join(",", values)); } } + break; } case ProfileConditionValue.Height: @@ -1647,6 +1662,7 @@ namespace MediaBrowser.Model.Dlna item.MaxHeight = Math.Max(num, item.MaxHeight ?? num); } } + break; } case ProfileConditionValue.VideoBitrate: @@ -1671,6 +1687,7 @@ namespace MediaBrowser.Model.Dlna item.VideoBitrate = Math.Max(num, item.VideoBitrate ?? num); } } + break; } case ProfileConditionValue.VideoFramerate: @@ -1695,6 +1712,7 @@ namespace MediaBrowser.Model.Dlna item.MaxFramerate = Math.Max(num, item.MaxFramerate ?? num); } } + break; } case ProfileConditionValue.VideoLevel: @@ -1719,6 +1737,7 @@ namespace MediaBrowser.Model.Dlna item.SetOption(qualifier, "level", Math.Max(num, item.GetTargetVideoLevel(qualifier) ?? num).ToString(CultureInfo.InvariantCulture)); } } + break; } case ProfileConditionValue.Width: @@ -1743,8 +1762,10 @@ namespace MediaBrowser.Model.Dlna item.MaxWidth = Math.Max(num, item.MaxWidth ?? num); } } + break; } + default: break; } diff --git a/MediaBrowser.Model/Dlna/StreamInfo.cs b/MediaBrowser.Model/Dlna/StreamInfo.cs index 2444638030..9e9d0b7e11 100644 --- a/MediaBrowser.Model/Dlna/StreamInfo.cs +++ b/MediaBrowser.Model/Dlna/StreamInfo.cs @@ -69,6 +69,7 @@ namespace MediaBrowser.Model.Dlna public Guid ItemId { get; set; } public PlayMethod PlayMethod { get; set; } + public EncodingContext Context { get; set; } public DlnaProfileType MediaType { get; set; } @@ -80,15 +81,23 @@ namespace MediaBrowser.Model.Dlna public long StartPositionTicks { get; set; } public int? SegmentLength { get; set; } + public int? MinSegments { get; set; } + public bool BreakOnNonKeyFrames { get; set; } public bool RequireAvc { get; set; } + public bool RequireNonAnamorphic { get; set; } + public bool CopyTimestamps { get; set; } + public bool EnableMpegtsM2TsMode { get; set; } + public bool EnableSubtitlesInManifest { get; set; } + public string[] AudioCodecs { get; set; } + public string[] VideoCodecs { get; set; } public int? AudioStreamIndex { get; set; } @@ -96,6 +105,7 @@ namespace MediaBrowser.Model.Dlna public int? SubtitleStreamIndex { get; set; } public int? TranscodingMaxAudioChannels { get; set; } + public int? GlobalMaxAudioChannels { get; set; } public int? AudioBitrate { get; set; } @@ -103,12 +113,15 @@ namespace MediaBrowser.Model.Dlna public int? VideoBitrate { get; set; } public int? MaxWidth { get; set; } + public int? MaxHeight { get; set; } public float? MaxFramerate { get; set; } public DeviceProfile DeviceProfile { get; set; } + public string DeviceProfileId { get; set; } + public string DeviceId { get; set; } public long? RunTimeTicks { get; set; } @@ -120,10 +133,13 @@ namespace MediaBrowser.Model.Dlna public MediaSourceInfo MediaSource { get; set; } public string[] SubtitleCodecs { get; set; } + public SubtitleDeliveryMethod SubtitleDeliveryMethod { get; set; } + public string SubtitleFormat { get; set; } public string PlaySessionId { get; set; } + public TranscodeReason[] TranscodeReasons { get; set; } public Dictionary<string, string> StreamOptions { get; private set; } @@ -160,11 +176,13 @@ namespace MediaBrowser.Model.Dlna { continue; } + if (string.Equals(pair.Name, "SubtitleStreamIndex", StringComparison.OrdinalIgnoreCase) && string.Equals(pair.Value, "-1", StringComparison.OrdinalIgnoreCase)) { continue; } + if (string.Equals(pair.Name, "Static", StringComparison.OrdinalIgnoreCase) && string.Equals(pair.Value, "false", StringComparison.OrdinalIgnoreCase)) { @@ -993,6 +1011,7 @@ namespace MediaBrowser.Model.Dlna { return GetMediaStreamCount(MediaStreamType.Video, int.MaxValue); } + return GetMediaStreamCount(MediaStreamType.Video, 1); } } @@ -1005,6 +1024,7 @@ namespace MediaBrowser.Model.Dlna { return GetMediaStreamCount(MediaStreamType.Audio, int.MaxValue); } + return GetMediaStreamCount(MediaStreamType.Audio, 1); } } diff --git a/MediaBrowser.Model/Dto/BaseItemDto.cs b/MediaBrowser.Model/Dto/BaseItemDto.cs index c7f8f05844..62005b901d 100644 --- a/MediaBrowser.Model/Dto/BaseItemDto.cs +++ b/MediaBrowser.Model/Dto/BaseItemDto.cs @@ -62,17 +62,23 @@ namespace MediaBrowser.Model.Dto public DateTime? DateCreated { get; set; } public DateTime? DateLastMediaAdded { get; set; } + public string ExtraType { get; set; } public int? AirsBeforeSeasonNumber { get; set; } + public int? AirsAfterSeasonNumber { get; set; } + public int? AirsBeforeEpisodeNumber { get; set; } + public bool? CanDelete { get; set; } + public bool? CanDownload { get; set; } public bool? HasSubtitles { get; set; } public string PreferredMetadataLanguage { get; set; } + public string PreferredMetadataCountryCode { get; set; } /// <summary> @@ -87,6 +93,7 @@ namespace MediaBrowser.Model.Dto /// </summary> /// <value>The name of the sort.</value> public string SortName { get; set; } + public string ForcedSortName { get; set; } /// <summary> @@ -146,6 +153,7 @@ namespace MediaBrowser.Model.Dto /// </summary> /// <value>The channel identifier.</value> public Guid ChannelId { get; set; } + public string ChannelName { get; set; } /// <summary> @@ -213,6 +221,7 @@ namespace MediaBrowser.Model.Dto /// </summary> /// <value>The number.</value> public string Number { get; set; } + public string ChannelNumber { get; set; } /// <summary> @@ -467,6 +476,7 @@ namespace MediaBrowser.Model.Dto /// </summary> /// <value>The part count.</value> public int? PartCount { get; set; } + public int? MediaSourceCount { get; set; } /// <summary> @@ -599,6 +609,7 @@ namespace MediaBrowser.Model.Dto /// </summary> /// <value>The series count.</value> public int? SeriesCount { get; set; } + public int? ProgramCount { get; set; } /// <summary> /// Gets or sets the episode count. @@ -615,6 +626,7 @@ namespace MediaBrowser.Model.Dto /// </summary> /// <value>The album count.</value> public int? AlbumCount { get; set; } + public int? ArtistCount { get; set; } /// <summary> /// Gets or sets the music video count. @@ -629,18 +641,31 @@ namespace MediaBrowser.Model.Dto public bool? LockData { get; set; } public int? Width { get; set; } + public int? Height { get; set; } + public string CameraMake { get; set; } + public string CameraModel { get; set; } + public string Software { get; set; } + public double? ExposureTime { get; set; } + public double? FocalLength { get; set; } + public ImageOrientation? ImageOrientation { get; set; } + public double? Aperture { get; set; } + public double? ShutterSpeed { get; set; } + public double? Latitude { get; set; } + public double? Longitude { get; set; } + public double? Altitude { get; set; } + public int? IsoSpeedRating { get; set; } /// <summary> diff --git a/MediaBrowser.Model/Dto/MediaSourceInfo.cs b/MediaBrowser.Model/Dto/MediaSourceInfo.cs index 74c2cb4f41..0c9e11f8f4 100644 --- a/MediaBrowser.Model/Dto/MediaSourceInfo.cs +++ b/MediaBrowser.Model/Dto/MediaSourceInfo.cs @@ -13,16 +13,19 @@ namespace MediaBrowser.Model.Dto public class MediaSourceInfo { public MediaProtocol Protocol { get; set; } + public string Id { get; set; } public string Path { get; set; } public string EncoderPath { get; set; } + public MediaProtocol? EncoderProtocol { get; set; } public MediaSourceType Type { get; set; } public string Container { get; set; } + public long? Size { get; set; } public string Name { get; set; } @@ -33,19 +36,33 @@ namespace MediaBrowser.Model.Dto public bool IsRemote { get; set; } public string ETag { get; set; } + public long? RunTimeTicks { get; set; } + public bool ReadAtNativeFramerate { get; set; } + public bool IgnoreDts { get; set; } + public bool IgnoreIndex { get; set; } + public bool GenPtsInput { get; set; } + public bool SupportsTranscoding { get; set; } + public bool SupportsDirectStream { get; set; } + public bool SupportsDirectPlay { get; set; } + public bool IsInfiniteStream { get; set; } + public bool RequiresOpening { get; set; } + public string OpenToken { get; set; } + public bool RequiresClosing { get; set; } + public string LiveStreamId { get; set; } + public int? BufferMs { get; set; } public bool RequiresLooping { get; set; } @@ -67,10 +84,13 @@ namespace MediaBrowser.Model.Dto public int? Bitrate { get; set; } public TransportStreamTimestamp? Timestamp { get; set; } + public Dictionary<string, string> RequiredHttpHeaders { get; set; } public string TranscodingUrl { get; set; } + public string TranscodingSubProtocol { get; set; } + public string TranscodingContainer { get; set; } public int? AnalyzeDurationMs { get; set; } @@ -118,6 +138,7 @@ namespace MediaBrowser.Model.Dto public TranscodeReason[] TranscodeReasons { get; set; } public int? DefaultAudioStreamIndex { get; set; } + public int? DefaultSubtitleStreamIndex { get; set; } public MediaStream GetDefaultAudioStream(int? defaultIndex) diff --git a/MediaBrowser.Model/Dto/MetadataEditorInfo.cs b/MediaBrowser.Model/Dto/MetadataEditorInfo.cs index 1d840a3000..e4f38d6af3 100644 --- a/MediaBrowser.Model/Dto/MetadataEditorInfo.cs +++ b/MediaBrowser.Model/Dto/MetadataEditorInfo.cs @@ -11,11 +11,15 @@ namespace MediaBrowser.Model.Dto public class MetadataEditorInfo { public ParentalRating[] ParentalRatingOptions { get; set; } + public CountryInfo[] Countries { get; set; } + public CultureDto[] Cultures { get; set; } + public ExternalIdInfo[] ExternalIdInfos { get; set; } public string ContentType { get; set; } + public NameValuePair[] ContentTypeOptions { get; set; } public MetadataEditorInfo() diff --git a/MediaBrowser.Model/Dto/NameIdPair.cs b/MediaBrowser.Model/Dto/NameIdPair.cs index efb2c157c2..45c2fb35db 100644 --- a/MediaBrowser.Model/Dto/NameIdPair.cs +++ b/MediaBrowser.Model/Dto/NameIdPair.cs @@ -23,6 +23,7 @@ namespace MediaBrowser.Model.Dto public class NameGuidPair { public string Name { get; set; } + public Guid Id { get; set; } } } diff --git a/MediaBrowser.Model/Entities/MediaStream.cs b/MediaBrowser.Model/Entities/MediaStream.cs index 3db72f78ac..f0f7bf838c 100644 --- a/MediaBrowser.Model/Entities/MediaStream.cs +++ b/MediaBrowser.Model/Entities/MediaStream.cs @@ -125,6 +125,7 @@ namespace MediaBrowser.Model.Entities { attributes.Add(StringHelper.FirstToUpper(Language)); } + if (!string.IsNullOrEmpty(Codec) && !string.Equals(Codec, "dca", StringComparison.OrdinalIgnoreCase)) { attributes.Add(AudioCodec.GetFriendlyName(Codec)); @@ -142,6 +143,7 @@ namespace MediaBrowser.Model.Entities { attributes.Add(Channels.Value.ToString(CultureInfo.InvariantCulture) + " ch"); } + if (IsDefault) { attributes.Add("Default"); @@ -227,30 +229,37 @@ namespace MediaBrowser.Model.Entities { return "4K"; } + if (width >= 2500) { if (i.IsInterlaced) { return "1440i"; } + return "1440p"; } + if (width >= 1900 || height >= 1000) { if (i.IsInterlaced) { return "1080i"; } + return "1080p"; } + if (width >= 1260 || height >= 700) { if (i.IsInterlaced) { return "720i"; } + return "720p"; } + if (width >= 700 || height >= 440) { @@ -258,11 +267,13 @@ namespace MediaBrowser.Model.Entities { return "480i"; } + return "480p"; } return "SD"; } + return null; } @@ -448,6 +459,7 @@ namespace MediaBrowser.Model.Entities { return false; } + if (string.Equals(fromCodec, "ssa", StringComparison.OrdinalIgnoreCase)) { return false; @@ -458,6 +470,7 @@ namespace MediaBrowser.Model.Entities { return false; } + if (string.Equals(toCodec, "ssa", StringComparison.OrdinalIgnoreCase)) { return false; diff --git a/MediaBrowser.Model/Entities/MediaUrl.cs b/MediaBrowser.Model/Entities/MediaUrl.cs index 74f982437f..80ceaa765a 100644 --- a/MediaBrowser.Model/Entities/MediaUrl.cs +++ b/MediaBrowser.Model/Entities/MediaUrl.cs @@ -6,6 +6,7 @@ namespace MediaBrowser.Model.Entities public class MediaUrl { public string Url { get; set; } + public string Name { get; set; } } } diff --git a/MediaBrowser.Model/Entities/VirtualFolderInfo.cs b/MediaBrowser.Model/Entities/VirtualFolderInfo.cs index 2de02e403c..f8df057618 100644 --- a/MediaBrowser.Model/Entities/VirtualFolderInfo.cs +++ b/MediaBrowser.Model/Entities/VirtualFolderInfo.cs @@ -52,6 +52,7 @@ namespace MediaBrowser.Model.Entities public string PrimaryImageItemId { get; set; } public double? RefreshProgress { get; set; } + public string RefreshStatus { get; set; } } } diff --git a/MediaBrowser.Model/LiveTv/BaseTimerInfoDto.cs b/MediaBrowser.Model/LiveTv/BaseTimerInfoDto.cs index 45970cf6b1..07e76d9600 100644 --- a/MediaBrowser.Model/LiveTv/BaseTimerInfoDto.cs +++ b/MediaBrowser.Model/LiveTv/BaseTimerInfoDto.cs @@ -124,6 +124,7 @@ namespace MediaBrowser.Model.LiveTv /// </summary> /// <value><c>true</c> if this instance is post padding required; otherwise, <c>false</c>.</value> public bool IsPostPaddingRequired { get; set; } + public KeepUntil KeepUntil { get; set; } } } diff --git a/MediaBrowser.Model/LiveTv/LiveTvChannelQuery.cs b/MediaBrowser.Model/LiveTv/LiveTvChannelQuery.cs index d1a94d8b30..fe23906898 100644 --- a/MediaBrowser.Model/LiveTv/LiveTvChannelQuery.cs +++ b/MediaBrowser.Model/LiveTv/LiveTvChannelQuery.cs @@ -64,6 +64,7 @@ namespace MediaBrowser.Model.LiveTv /// </summary> /// <value><c>true</c> if [add current program]; otherwise, <c>false</c>.</value> public bool AddCurrentProgram { get; set; } + public bool EnableUserData { get; set; } /// <summary> @@ -88,6 +89,7 @@ namespace MediaBrowser.Model.LiveTv /// </summary> /// <value><c>null</c> if [is sports] contains no value, <c>true</c> if [is sports]; otherwise, <c>false</c>.</value> public bool? IsSports { get; set; } + public bool? IsSeries { get; set; } public string[] SortBy { get; set; } diff --git a/MediaBrowser.Model/LiveTv/LiveTvOptions.cs b/MediaBrowser.Model/LiveTv/LiveTvOptions.cs index 69c43efd47..789de3198a 100644 --- a/MediaBrowser.Model/LiveTv/LiveTvOptions.cs +++ b/MediaBrowser.Model/LiveTv/LiveTvOptions.cs @@ -9,21 +9,29 @@ namespace MediaBrowser.Model.LiveTv public class LiveTvOptions { public int? GuideDays { get; set; } + public string RecordingPath { get; set; } + public string MovieRecordingPath { get; set; } + public string SeriesRecordingPath { get; set; } + public bool EnableRecordingSubfolders { get; set; } + public bool EnableOriginalAudioWithEncodedRecordings { get; set; } public TunerHostInfo[] TunerHosts { get; set; } + public ListingsProviderInfo[] ListingProviders { get; set; } public int PrePaddingSeconds { get; set; } + public int PostPaddingSeconds { get; set; } public string[] MediaLocationsCreated { get; set; } public string RecordingPostProcessor { get; set; } + public string RecordingPostProcessorArguments { get; set; } public LiveTvOptions() @@ -38,15 +46,25 @@ namespace MediaBrowser.Model.LiveTv public class TunerHostInfo { public string Id { get; set; } + public string Url { get; set; } + public string Type { get; set; } + public string DeviceId { get; set; } + public string FriendlyName { get; set; } + public bool ImportFavoritesOnly { get; set; } + public bool AllowHWTranscoding { get; set; } + public bool EnableStreamLooping { get; set; } + public string Source { get; set; } + public int TunerCount { get; set; } + public string UserAgent { get; set; } public TunerHostInfo() @@ -58,23 +76,39 @@ namespace MediaBrowser.Model.LiveTv public class ListingsProviderInfo { public string Id { get; set; } + public string Type { get; set; } + public string Username { get; set; } + public string Password { get; set; } + public string ListingsId { get; set; } + public string ZipCode { get; set; } + public string Country { get; set; } + public string Path { get; set; } public string[] EnabledTuners { get; set; } + public bool EnableAllTuners { get; set; } + public string[] NewsCategories { get; set; } + public string[] SportsCategories { get; set; } + public string[] KidsCategories { get; set; } + public string[] MovieCategories { get; set; } + public NameValuePair[] ChannelMappings { get; set; } + public string MoviePrefix { get; set; } + public string PreferredLanguage { get; set; } + public string UserAgent { get; set; } public ListingsProviderInfo() diff --git a/MediaBrowser.Model/LiveTv/RecordingQuery.cs b/MediaBrowser.Model/LiveTv/RecordingQuery.cs index 2649829300..25755483a7 100644 --- a/MediaBrowser.Model/LiveTv/RecordingQuery.cs +++ b/MediaBrowser.Model/LiveTv/RecordingQuery.cs @@ -65,14 +65,23 @@ namespace MediaBrowser.Model.LiveTv /// </summary> /// <value>The fields.</value> public ItemFields[] Fields { get; set; } + public bool? EnableImages { get; set; } + public bool? IsLibraryItem { get; set; } + public bool? IsNews { get; set; } + public bool? IsMovie { get; set; } + public bool? IsSeries { get; set; } + public bool? IsKids { get; set; } + public bool? IsSports { get; set; } + public int? ImageTypeLimit { get; set; } + public ImageType[] EnableImageTypes { get; set; } public bool EnableTotalRecordCount { get; set; } diff --git a/MediaBrowser.Model/MediaInfo/LiveStreamRequest.cs b/MediaBrowser.Model/MediaInfo/LiveStreamRequest.cs index cce508809b..83bda5d569 100644 --- a/MediaBrowser.Model/MediaInfo/LiveStreamRequest.cs +++ b/MediaBrowser.Model/MediaInfo/LiveStreamRequest.cs @@ -32,18 +32,29 @@ namespace MediaBrowser.Model.MediaInfo } public string OpenToken { get; set; } + public Guid UserId { get; set; } + public string PlaySessionId { get; set; } + public long? MaxStreamingBitrate { get; set; } + public long? StartTimeTicks { get; set; } + public int? AudioStreamIndex { get; set; } + public int? SubtitleStreamIndex { get; set; } + public int? MaxAudioChannels { get; set; } + public Guid ItemId { get; set; } + public DeviceProfile DeviceProfile { get; set; } public bool EnableDirectPlay { get; set; } + public bool EnableDirectStream { get; set; } + public MediaProtocol[] DirectPlayProtocols { get; set; } } } diff --git a/MediaBrowser.Model/MediaInfo/MediaInfo.cs b/MediaBrowser.Model/MediaInfo/MediaInfo.cs index 97b9799357..472055c22c 100644 --- a/MediaBrowser.Model/MediaInfo/MediaInfo.cs +++ b/MediaBrowser.Model/MediaInfo/MediaInfo.cs @@ -35,13 +35,21 @@ namespace MediaBrowser.Model.MediaInfo /// </summary> /// <value>The studios.</value> public string[] Studios { get; set; } + public string[] Genres { get; set; } + public string ShowName { get; set; } + public int? IndexNumber { get; set; } + public int? ParentIndexNumber { get; set; } + public int? ProductionYear { get; set; } + public DateTime? PremiereDate { get; set; } + public BaseItemPerson[] People { get; set; } + public Dictionary<string, string> ProviderIds { get; set; } /// <summary> diff --git a/MediaBrowser.Model/MediaInfo/PlaybackInfoRequest.cs b/MediaBrowser.Model/MediaInfo/PlaybackInfoRequest.cs index 82e13e0ebe..3216856777 100644 --- a/MediaBrowser.Model/MediaInfo/PlaybackInfoRequest.cs +++ b/MediaBrowser.Model/MediaInfo/PlaybackInfoRequest.cs @@ -29,11 +29,17 @@ namespace MediaBrowser.Model.MediaInfo public DeviceProfile DeviceProfile { get; set; } public bool EnableDirectPlay { get; set; } + public bool EnableDirectStream { get; set; } + public bool EnableTranscoding { get; set; } + public bool AllowVideoStreamCopy { get; set; } + public bool AllowAudioStreamCopy { get; set; } + public bool IsPlayback { get; set; } + public bool AutoOpenLiveStream { get; set; } public MediaProtocol[] DirectPlayProtocols { get; set; } diff --git a/MediaBrowser.Model/Providers/RemoteSubtitleInfo.cs b/MediaBrowser.Model/Providers/RemoteSubtitleInfo.cs index d9f7a852ca..a8d88d8a1b 100644 --- a/MediaBrowser.Model/Providers/RemoteSubtitleInfo.cs +++ b/MediaBrowser.Model/Providers/RemoteSubtitleInfo.cs @@ -8,15 +8,25 @@ namespace MediaBrowser.Model.Providers public class RemoteSubtitleInfo { public string ThreeLetterISOLanguageName { get; set; } + public string Id { get; set; } + public string ProviderName { get; set; } + public string Name { get; set; } + public string Format { get; set; } + public string Author { get; set; } + public string Comment { get; set; } + public DateTime? DateCreated { get; set; } + public float? CommunityRating { get; set; } + public int? DownloadCount { get; set; } + public bool? IsHashMatch { get; set; } } } diff --git a/MediaBrowser.Model/Providers/SubtitleOptions.cs b/MediaBrowser.Model/Providers/SubtitleOptions.cs index c073795704..5702c460b0 100644 --- a/MediaBrowser.Model/Providers/SubtitleOptions.cs +++ b/MediaBrowser.Model/Providers/SubtitleOptions.cs @@ -8,13 +8,19 @@ namespace MediaBrowser.Model.Providers public class SubtitleOptions { public bool SkipIfEmbeddedSubtitlesPresent { get; set; } + public bool SkipIfAudioTrackMatches { get; set; } + public string[] DownloadLanguages { get; set; } + public bool DownloadMovieSubtitles { get; set; } + public bool DownloadEpisodeSubtitles { get; set; } public string OpenSubtitlesUsername { get; set; } + public string OpenSubtitlesPasswordHash { get; set; } + public bool IsOpenSubtitleVipAccount { get; set; } public bool RequirePerfectMatch { get; set; } diff --git a/MediaBrowser.Model/Providers/SubtitleProviderInfo.cs b/MediaBrowser.Model/Providers/SubtitleProviderInfo.cs index ee25be4b6c..7a7e7b9ec3 100644 --- a/MediaBrowser.Model/Providers/SubtitleProviderInfo.cs +++ b/MediaBrowser.Model/Providers/SubtitleProviderInfo.cs @@ -6,6 +6,7 @@ namespace MediaBrowser.Model.Providers public class SubtitleProviderInfo { public string Name { get; set; } + public string Id { get; set; } } } diff --git a/MediaBrowser.Model/Querying/QueryFilters.cs b/MediaBrowser.Model/Querying/QueryFilters.cs index e04208f766..6e4d251818 100644 --- a/MediaBrowser.Model/Querying/QueryFilters.cs +++ b/MediaBrowser.Model/Querying/QueryFilters.cs @@ -9,8 +9,11 @@ namespace MediaBrowser.Model.Querying public class QueryFiltersLegacy { public string[] Genres { get; set; } + public string[] Tags { get; set; } + public string[] OfficialRatings { get; set; } + public int[] Years { get; set; } public QueryFiltersLegacy() @@ -21,9 +24,11 @@ namespace MediaBrowser.Model.Querying Years = Array.Empty<int>(); } } + public class QueryFilters { public NameGuidPair[] Genres { get; set; } + public string[] Tags { get; set; } public QueryFilters() diff --git a/MediaBrowser.Model/Search/SearchHint.cs b/MediaBrowser.Model/Search/SearchHint.cs index c7a721df6e..983dbd2bc0 100644 --- a/MediaBrowser.Model/Search/SearchHint.cs +++ b/MediaBrowser.Model/Search/SearchHint.cs @@ -100,6 +100,7 @@ namespace MediaBrowser.Model.Search public string MediaType { get; set; } public DateTime? StartDate { get; set; } + public DateTime? EndDate { get; set; } /// <summary> diff --git a/MediaBrowser.Model/Search/SearchQuery.cs b/MediaBrowser.Model/Search/SearchQuery.cs index 4470f1ad97..297199f61c 100644 --- a/MediaBrowser.Model/Search/SearchQuery.cs +++ b/MediaBrowser.Model/Search/SearchQuery.cs @@ -32,14 +32,21 @@ namespace MediaBrowser.Model.Search public int? Limit { get; set; } public bool IncludePeople { get; set; } + public bool IncludeMedia { get; set; } + public bool IncludeGenres { get; set; } + public bool IncludeStudios { get; set; } + public bool IncludeArtists { get; set; } public string[] MediaTypes { get; set; } + public string[] IncludeItemTypes { get; set; } + public string[] ExcludeItemTypes { get; set; } + public string ParentId { get; set; } public bool? IsMovie { get; set; } diff --git a/MediaBrowser.Model/Services/IRequest.cs b/MediaBrowser.Model/Services/IRequest.cs index f413f1e177..89622f3110 100644 --- a/MediaBrowser.Model/Services/IRequest.cs +++ b/MediaBrowser.Model/Services/IRequest.cs @@ -76,9 +76,13 @@ namespace MediaBrowser.Model.Services public interface IHttpFile { string Name { get; } + string FileName { get; } + long ContentLength { get; } + string ContentType { get; } + Stream InputStream { get; } } diff --git a/MediaBrowser.Model/Services/IService.cs b/MediaBrowser.Model/Services/IService.cs index a26d394558..5233f57abb 100644 --- a/MediaBrowser.Model/Services/IService.cs +++ b/MediaBrowser.Model/Services/IService.cs @@ -8,6 +8,8 @@ namespace MediaBrowser.Model.Services } public interface IReturn { } + public interface IReturn<T> : IReturn { } + public interface IReturnVoid : IReturn { } } diff --git a/MediaBrowser.Model/Session/ClientCapabilities.cs b/MediaBrowser.Model/Session/ClientCapabilities.cs index 51db66d212..d3878ca308 100644 --- a/MediaBrowser.Model/Session/ClientCapabilities.cs +++ b/MediaBrowser.Model/Session/ClientCapabilities.cs @@ -13,15 +13,19 @@ namespace MediaBrowser.Model.Session public string[] SupportedCommands { get; set; } public bool SupportsMediaControl { get; set; } + public bool SupportsContentUploading { get; set; } + public string MessageCallbackUrl { get; set; } public bool SupportsPersistentIdentifier { get; set; } + public bool SupportsSync { get; set; } public DeviceProfile DeviceProfile { get; set; } public string AppStoreUrl { get; set; } + public string IconUrl { get; set; } public ClientCapabilities() diff --git a/MediaBrowser.Model/Session/PlayRequest.cs b/MediaBrowser.Model/Session/PlayRequest.cs index 62b68b49ea..1a51e23c99 100644 --- a/MediaBrowser.Model/Session/PlayRequest.cs +++ b/MediaBrowser.Model/Session/PlayRequest.cs @@ -39,8 +39,11 @@ namespace MediaBrowser.Model.Session public Guid ControllingUserId { get; set; } public int? SubtitleStreamIndex { get; set; } + public int? AudioStreamIndex { get; set; } + public string MediaSourceId { get; set; } + public int? StartIndex { get; set; } } } diff --git a/MediaBrowser.Model/Session/PlaybackProgressInfo.cs b/MediaBrowser.Model/Session/PlaybackProgressInfo.cs index 6b4cfe4f0d..21bcabf1d9 100644 --- a/MediaBrowser.Model/Session/PlaybackProgressInfo.cs +++ b/MediaBrowser.Model/Session/PlaybackProgressInfo.cs @@ -105,6 +105,7 @@ namespace MediaBrowser.Model.Session public RepeatMode RepeatMode { get; set; } public QueueItem[] NowPlayingQueue { get; set; } + public string PlaylistItemId { get; set; } } @@ -118,6 +119,7 @@ namespace MediaBrowser.Model.Session public class QueueItem { public Guid Id { get; set; } + public string PlaylistItemId { get; set; } } } diff --git a/MediaBrowser.Model/Session/PlaybackStopInfo.cs b/MediaBrowser.Model/Session/PlaybackStopInfo.cs index b0827ac99c..aa29bb249e 100644 --- a/MediaBrowser.Model/Session/PlaybackStopInfo.cs +++ b/MediaBrowser.Model/Session/PlaybackStopInfo.cs @@ -62,6 +62,7 @@ namespace MediaBrowser.Model.Session public string NextMediaType { get; set; } public string PlaylistItemId { get; set; } + public QueueItem[] NowPlayingQueue { get; set; } } } diff --git a/MediaBrowser.Model/Session/TranscodingInfo.cs b/MediaBrowser.Model/Session/TranscodingInfo.cs index d6dc83413b..e832c2f6fa 100644 --- a/MediaBrowser.Model/Session/TranscodingInfo.cs +++ b/MediaBrowser.Model/Session/TranscodingInfo.cs @@ -8,17 +8,25 @@ namespace MediaBrowser.Model.Session public class TranscodingInfo { public string AudioCodec { get; set; } + public string VideoCodec { get; set; } + public string Container { get; set; } + public bool IsVideoDirect { get; set; } + public bool IsAudioDirect { get; set; } + public int? Bitrate { get; set; } public float? Framerate { get; set; } + public double? CompletionPercentage { get; set; } public int? Width { get; set; } + public int? Height { get; set; } + public int? AudioChannels { get; set; } public TranscodeReason[] TranscodeReasons { get; set; } diff --git a/MediaBrowser.Model/Sync/SyncJob.cs b/MediaBrowser.Model/Sync/SyncJob.cs index 3cc9ff7267..b9290b6e83 100644 --- a/MediaBrowser.Model/Sync/SyncJob.cs +++ b/MediaBrowser.Model/Sync/SyncJob.cs @@ -122,7 +122,9 @@ namespace MediaBrowser.Model.Sync public int ItemCount { get; set; } public string ParentName { get; set; } + public string PrimaryImageItemId { get; set; } + public string PrimaryImageTag { get; set; } public SyncJob() diff --git a/MediaBrowser.Model/Users/UserAction.cs b/MediaBrowser.Model/Users/UserAction.cs index 36b8e6ee52..7646db4a82 100644 --- a/MediaBrowser.Model/Users/UserAction.cs +++ b/MediaBrowser.Model/Users/UserAction.cs @@ -8,11 +8,17 @@ namespace MediaBrowser.Model.Users public class UserAction { public string Id { get; set; } + public string ServerId { get; set; } + public Guid UserId { get; set; } + public Guid ItemId { get; set; } + public UserActionType Type { get; set; } + public DateTime Date { get; set; } + public long? PositionTicks { get; set; } } } diff --git a/MediaBrowser.Model/Users/UserPolicy.cs b/MediaBrowser.Model/Users/UserPolicy.cs index 2fd27d3b9a..caf2e0f549 100644 --- a/MediaBrowser.Model/Users/UserPolicy.cs +++ b/MediaBrowser.Model/Users/UserPolicy.cs @@ -35,24 +35,37 @@ namespace MediaBrowser.Model.Users public int? MaxParentalRating { get; set; } public string[] BlockedTags { get; set; } + public bool EnableUserPreferenceAccess { get; set; } + public AccessSchedule[] AccessSchedules { get; set; } + public UnratedItem[] BlockUnratedItems { get; set; } + public bool EnableRemoteControlOfOtherUsers { get; set; } + public bool EnableSharedDeviceControl { get; set; } + public bool EnableRemoteAccess { get; set; } public bool EnableLiveTvManagement { get; set; } + public bool EnableLiveTvAccess { get; set; } public bool EnableMediaPlayback { get; set; } + public bool EnableAudioPlaybackTranscoding { get; set; } + public bool EnableVideoPlaybackTranscoding { get; set; } + public bool EnablePlaybackRemuxing { get; set; } + public bool ForceRemoteSourceTranscoding { get; set; } public bool EnableContentDeletion { get; set; } + public string[] EnableContentDeletionFromFolders { get; set; } + public bool EnableContentDownloading { get; set; } /// <summary> @@ -60,29 +73,36 @@ namespace MediaBrowser.Model.Users /// </summary> /// <value><c>true</c> if [enable synchronize]; otherwise, <c>false</c>.</value> public bool EnableSyncTranscoding { get; set; } + public bool EnableMediaConversion { get; set; } public string[] EnabledDevices { get; set; } + public bool EnableAllDevices { get; set; } public string[] EnabledChannels { get; set; } + public bool EnableAllChannels { get; set; } public string[] EnabledFolders { get; set; } + public bool EnableAllFolders { get; set; } public int InvalidLoginAttemptCount { get; set; } + public int LoginAttemptsBeforeLockout { get; set; } public bool EnablePublicSharing { get; set; } public string[] BlockedMediaFolders { get; set; } + public string[] BlockedChannels { get; set; } public int RemoteClientBitrateLimit { get; set; } [XmlElement(ElementName = "AuthenticationProviderId")] public string AuthenticationProviderId { get; set; } + public string PasswordResetProviderId { get; set; } /// <summary> diff --git a/MediaBrowser.Providers/Manager/ImageSaver.cs b/MediaBrowser.Providers/Manager/ImageSaver.cs index 3c94f62150..2f5aa18195 100644 --- a/MediaBrowser.Providers/Manager/ImageSaver.cs +++ b/MediaBrowser.Providers/Manager/ImageSaver.cs @@ -104,6 +104,7 @@ namespace MediaBrowser.Providers.Manager } } } + if (saveLocallyWithMedia.HasValue && !saveLocallyWithMedia.Value) { saveLocally = saveLocallyWithMedia.Value; @@ -147,6 +148,7 @@ namespace MediaBrowser.Providers.Manager { retryPath = retryPaths[currentPathIndex]; } + var savedPath = await SaveImageToLocation(source, path, retryPath, cancellationToken).ConfigureAwait(false); savedPaths.Add(savedPath); currentPathIndex++; @@ -460,6 +462,7 @@ namespace MediaBrowser.Providers.Manager { filename = folderName; } + path = Path.Combine(item.GetInternalMetadataPath(), filename + extension); } @@ -551,6 +554,7 @@ namespace MediaBrowser.Providers.Manager { list.Add(Path.Combine(item.ContainingFolderPath, "extrathumbs", "thumb" + outputIndex.ToString(UsCulture) + extension)); } + return list.ToArray(); } @@ -619,6 +623,7 @@ namespace MediaBrowser.Providers.Manager { imageFilename = "poster"; } + var folder = Path.GetDirectoryName(item.Path); return Path.Combine(folder, Path.GetFileNameWithoutExtension(item.Path) + "-" + imageFilename + extension); diff --git a/MediaBrowser.Providers/Manager/ItemImageProvider.cs b/MediaBrowser.Providers/Manager/ItemImageProvider.cs index 7901503d3f..3d60979f3e 100644 --- a/MediaBrowser.Providers/Manager/ItemImageProvider.cs +++ b/MediaBrowser.Providers/Manager/ItemImageProvider.cs @@ -58,6 +58,7 @@ namespace MediaBrowser.Providers.Manager { ClearImages(item, ImageType.Backdrop); } + if (refreshOptions.IsReplacingImage(ImageType.Screenshot)) { ClearImages(item, ImageType.Screenshot); @@ -472,6 +473,7 @@ namespace MediaBrowser.Providers.Manager { continue; } + break; } } @@ -585,6 +587,7 @@ namespace MediaBrowser.Providers.Manager { continue; } + break; } } diff --git a/MediaBrowser.Providers/Manager/MetadataService.cs b/MediaBrowser.Providers/Manager/MetadataService.cs index 73fb63743e..a3920d26f3 100644 --- a/MediaBrowser.Providers/Manager/MetadataService.cs +++ b/MediaBrowser.Providers/Manager/MetadataService.cs @@ -210,6 +210,7 @@ namespace MediaBrowser.Providers.Manager LibraryManager.UpdatePeople(baseItem, result.People); SavePeopleMetadata(result.People, libraryOptions, cancellationToken); } + result.Item.UpdateToRepository(reason, cancellationToken); } @@ -324,6 +325,7 @@ namespace MediaBrowser.Providers.Manager { return true; } + var folder = item as Folder; if (folder != null) { @@ -422,6 +424,7 @@ namespace MediaBrowser.Providers.Manager { dateLastMediaAdded = childDateCreated; } + any = true; } } @@ -726,6 +729,7 @@ namespace MediaBrowser.Providers.Manager { hasLocalMetadata = true; } + break; } @@ -874,6 +878,7 @@ namespace MediaBrowser.Providers.Manager { return "en"; } + return language; } @@ -924,7 +929,9 @@ namespace MediaBrowser.Providers.Manager public class RefreshResult { public ItemUpdateType UpdateType { get; set; } + public string ErrorMessage { get; set; } + public int Failures { get; set; } } } diff --git a/MediaBrowser.Providers/Manager/ProviderManager.cs b/MediaBrowser.Providers/Manager/ProviderManager.cs index 5853c77144..5b1192c305 100644 --- a/MediaBrowser.Providers/Manager/ProviderManager.cs +++ b/MediaBrowser.Providers/Manager/ProviderManager.cs @@ -787,6 +787,7 @@ namespace MediaBrowser.Providers.Manager { searchInfo.SearchInfo.MetadataLanguage = _configurationManager.Configuration.PreferredMetadataLanguage; } + if (string.IsNullOrWhiteSpace(searchInfo.SearchInfo.MetadataCountryCode)) { searchInfo.SearchInfo.MetadataCountryCode = _configurationManager.Configuration.MetadataCountryCode; diff --git a/MediaBrowser.Providers/Manager/ProviderUtils.cs b/MediaBrowser.Providers/Manager/ProviderUtils.cs index 60410032e5..4f49dc1c98 100644 --- a/MediaBrowser.Providers/Manager/ProviderUtils.cs +++ b/MediaBrowser.Providers/Manager/ProviderUtils.cs @@ -26,6 +26,7 @@ namespace MediaBrowser.Providers.Manager { throw new ArgumentNullException(nameof(source)); } + if (target == null) { throw new ArgumentNullException(nameof(target)); diff --git a/MediaBrowser.Providers/MediaInfo/AudioImageProvider.cs b/MediaBrowser.Providers/MediaInfo/AudioImageProvider.cs index ba87e05709..ef4e1dde9b 100644 --- a/MediaBrowser.Providers/MediaInfo/AudioImageProvider.cs +++ b/MediaBrowser.Providers/MediaInfo/AudioImageProvider.cs @@ -129,6 +129,7 @@ namespace MediaBrowser.Providers.MediaInfo { return false; } + if (!item.IsFileProtocol) { return false; diff --git a/MediaBrowser.Providers/MediaInfo/FFProbeVideoInfo.cs b/MediaBrowser.Providers/MediaInfo/FFProbeVideoInfo.cs index ccbe27c1ff..54847c8a9c 100644 --- a/MediaBrowser.Providers/MediaInfo/FFProbeVideoInfo.cs +++ b/MediaBrowser.Providers/MediaInfo/FFProbeVideoInfo.cs @@ -404,6 +404,7 @@ namespace MediaBrowser.Providers.MediaInfo video.ProductionYear = data.ProductionYear; } } + if (data.PremiereDate.HasValue) { if (!video.PremiereDate.HasValue || isFullRefresh) @@ -411,6 +412,7 @@ namespace MediaBrowser.Providers.MediaInfo video.PremiereDate = data.PremiereDate; } } + if (data.IndexNumber.HasValue) { if (!video.IndexNumber.HasValue || isFullRefresh) @@ -418,6 +420,7 @@ namespace MediaBrowser.Providers.MediaInfo video.IndexNumber = data.IndexNumber; } } + if (data.ParentIndexNumber.HasValue) { if (!video.ParentIndexNumber.HasValue || isFullRefresh) diff --git a/MediaBrowser.Providers/MediaInfo/VideoImageProvider.cs b/MediaBrowser.Providers/MediaInfo/VideoImageProvider.cs index 08e503a71b..7f4a8a372e 100644 --- a/MediaBrowser.Providers/MediaInfo/VideoImageProvider.cs +++ b/MediaBrowser.Providers/MediaInfo/VideoImageProvider.cs @@ -93,6 +93,7 @@ namespace MediaBrowser.Providers.MediaInfo { videoIndex++; } + if (mediaStream == imageStream) { break; @@ -132,6 +133,7 @@ namespace MediaBrowser.Providers.MediaInfo { return false; } + if (!item.IsFileProtocol) { return false; diff --git a/MediaBrowser.Providers/Movies/MovieMetadataService.cs b/MediaBrowser.Providers/Movies/MovieMetadataService.cs index 9faba47981..61d8c82632 100644 --- a/MediaBrowser.Providers/Movies/MovieMetadataService.cs +++ b/MediaBrowser.Providers/Movies/MovieMetadataService.cs @@ -28,10 +28,12 @@ namespace MediaBrowser.Providers.Movies { return false; } + if (!item.ProductionYear.HasValue) { return false; } + return base.IsFullLocalMetadata(item); } diff --git a/MediaBrowser.Providers/Movies/TrailerMetadataService.cs b/MediaBrowser.Providers/Movies/TrailerMetadataService.cs index b45d2b7450..09519c7a33 100644 --- a/MediaBrowser.Providers/Movies/TrailerMetadataService.cs +++ b/MediaBrowser.Providers/Movies/TrailerMetadataService.cs @@ -28,10 +28,12 @@ namespace MediaBrowser.Providers.Movies { return false; } + if (!item.ProductionYear.HasValue) { return false; } + return base.IsFullLocalMetadata(item); } diff --git a/MediaBrowser.Providers/Playlists/PlaylistItemsProvider.cs b/MediaBrowser.Providers/Playlists/PlaylistItemsProvider.cs index ed0601c00e..4ad4f890a0 100644 --- a/MediaBrowser.Providers/Playlists/PlaylistItemsProvider.cs +++ b/MediaBrowser.Providers/Playlists/PlaylistItemsProvider.cs @@ -61,18 +61,22 @@ namespace MediaBrowser.Providers.Playlists { return GetWplItems(stream); } + if (string.Equals(".zpl", extension, StringComparison.OrdinalIgnoreCase)) { return GetZplItems(stream); } + if (string.Equals(".m3u", extension, StringComparison.OrdinalIgnoreCase)) { return GetM3uItems(stream); } + if (string.Equals(".m3u8", extension, StringComparison.OrdinalIgnoreCase)) { return GetM3u8Items(stream); } + if (string.Equals(".pls", extension, StringComparison.OrdinalIgnoreCase)) { return GetPlsItems(stream); diff --git a/MediaBrowser.Providers/Plugins/AudioDb/AlbumProvider.cs b/MediaBrowser.Providers/Plugins/AudioDb/AlbumProvider.cs index b1a54f22ff..96224b366e 100644 --- a/MediaBrowser.Providers/Plugins/AudioDb/AlbumProvider.cs +++ b/MediaBrowser.Providers/Plugins/AudioDb/AlbumProvider.cs @@ -210,42 +210,79 @@ namespace MediaBrowser.Providers.Plugins.AudioDb public class Album { public string idAlbum { get; set; } + public string idArtist { get; set; } + public string strAlbum { get; set; } + public string strArtist { get; set; } + public string intYearReleased { get; set; } + public string strGenre { get; set; } + public string strSubGenre { get; set; } + public string strReleaseFormat { get; set; } + public string intSales { get; set; } + public string strAlbumThumb { get; set; } + public string strAlbumCDart { get; set; } + public string strDescriptionEN { get; set; } + public string strDescriptionDE { get; set; } + public string strDescriptionFR { get; set; } + public string strDescriptionCN { get; set; } + public string strDescriptionIT { get; set; } + public string strDescriptionJP { get; set; } + public string strDescriptionRU { get; set; } + public string strDescriptionES { get; set; } + public string strDescriptionPT { get; set; } + public string strDescriptionSE { get; set; } + public string strDescriptionNL { get; set; } + public string strDescriptionHU { get; set; } + public string strDescriptionNO { get; set; } + public string strDescriptionIL { get; set; } + public string strDescriptionPL { get; set; } + public object intLoved { get; set; } + public object intScore { get; set; } + public string strReview { get; set; } + public object strMood { get; set; } + public object strTheme { get; set; } + public object strSpeed { get; set; } + public object strLocation { get; set; } + public string strMusicBrainzID { get; set; } + public string strMusicBrainzArtistID { get; set; } + public object strItunesID { get; set; } + public object strAmazonID { get; set; } + public string strLocked { get; set; } } diff --git a/MediaBrowser.Providers/Plugins/AudioDb/ArtistProvider.cs b/MediaBrowser.Providers/Plugins/AudioDb/ArtistProvider.cs index fdba779be8..14bbcddcea 100644 --- a/MediaBrowser.Providers/Plugins/AudioDb/ArtistProvider.cs +++ b/MediaBrowser.Providers/Plugins/AudioDb/ArtistProvider.cs @@ -199,45 +199,85 @@ namespace MediaBrowser.Providers.Plugins.AudioDb public class Artist { public string idArtist { get; set; } + public string strArtist { get; set; } + public string strArtistAlternate { get; set; } + public object idLabel { get; set; } + public string intFormedYear { get; set; } + public string intBornYear { get; set; } + public object intDiedYear { get; set; } + public object strDisbanded { get; set; } + public string strGenre { get; set; } + public string strSubGenre { get; set; } + public string strWebsite { get; set; } + public string strFacebook { get; set; } + public string strTwitter { get; set; } + public string strBiographyEN { get; set; } + public string strBiographyDE { get; set; } + public string strBiographyFR { get; set; } + public string strBiographyCN { get; set; } + public string strBiographyIT { get; set; } + public string strBiographyJP { get; set; } + public string strBiographyRU { get; set; } + public string strBiographyES { get; set; } + public string strBiographyPT { get; set; } + public string strBiographySE { get; set; } + public string strBiographyNL { get; set; } + public string strBiographyHU { get; set; } + public string strBiographyNO { get; set; } + public string strBiographyIL { get; set; } + public string strBiographyPL { get; set; } + public string strGender { get; set; } + public string intMembers { get; set; } + public string strCountry { get; set; } + public string strCountryCode { get; set; } + public string strArtistThumb { get; set; } + public string strArtistLogo { get; set; } + public string strArtistFanart { get; set; } + public string strArtistFanart2 { get; set; } + public string strArtistFanart3 { get; set; } + public string strArtistBanner { get; set; } + public string strMusicBrainzID { get; set; } + public object strLastFMChart { get; set; } + public string strLocked { get; set; } } diff --git a/MediaBrowser.Providers/Plugins/MusicBrainz/AlbumProvider.cs b/MediaBrowser.Providers/Plugins/MusicBrainz/AlbumProvider.cs index 0a2c7c1241..78b5001991 100644 --- a/MediaBrowser.Providers/Plugins/MusicBrainz/AlbumProvider.cs +++ b/MediaBrowser.Providers/Plugins/MusicBrainz/AlbumProvider.cs @@ -361,6 +361,7 @@ namespace MediaBrowser.Providers.Music return ParseReleaseList(subReader).ToList(); } } + default: { reader.Skip(); @@ -396,6 +397,7 @@ namespace MediaBrowser.Providers.Music reader.Read(); continue; } + var releaseId = reader.GetAttribute("id"); using (var subReader = reader.ReadSubtree()) @@ -406,8 +408,10 @@ namespace MediaBrowser.Providers.Music yield return release; } } + break; } + default: { reader.Skip(); @@ -453,6 +457,7 @@ namespace MediaBrowser.Providers.Music { result.Year = date.Year; } + break; } case "annotation": @@ -480,6 +485,7 @@ namespace MediaBrowser.Providers.Music break; } + default: { reader.Skip(); @@ -518,6 +524,7 @@ namespace MediaBrowser.Providers.Music return ParseArtistNameCredit(subReader); } } + default: { reader.Skip(); @@ -556,6 +563,7 @@ namespace MediaBrowser.Providers.Music return ParseArtistArtistCredit(subReader, id); } } + default: { reader.Skip(); @@ -593,6 +601,7 @@ namespace MediaBrowser.Providers.Music name = reader.ReadElementContentAsString(); break; } + default: { reader.Skip(); @@ -680,11 +689,13 @@ namespace MediaBrowser.Providers.Music reader.Read(); continue; } + using (var subReader = reader.ReadSubtree()) { return GetFirstReleaseGroupId(subReader); } } + default: { reader.Skip(); @@ -719,6 +730,7 @@ namespace MediaBrowser.Providers.Music { return reader.GetAttribute("id"); } + default: { reader.Skip(); @@ -780,6 +792,7 @@ namespace MediaBrowser.Providers.Music // We retry a finite number of times, and only whilst MB is indicating 503 (throttling) } + while (attempts < MusicBrainzQueryAttempts && response.StatusCode == HttpStatusCode.ServiceUnavailable); // Log error if unable to query MB database due to throttling diff --git a/MediaBrowser.Providers/Plugins/MusicBrainz/ArtistProvider.cs b/MediaBrowser.Providers/Plugins/MusicBrainz/ArtistProvider.cs index 9d93dbdd1c..101af162d5 100644 --- a/MediaBrowser.Providers/Plugins/MusicBrainz/ArtistProvider.cs +++ b/MediaBrowser.Providers/Plugins/MusicBrainz/ArtistProvider.cs @@ -108,11 +108,13 @@ namespace MediaBrowser.Providers.Music reader.Read(); continue; } + using (var subReader = reader.ReadSubtree()) { return ParseArtistList(subReader).ToList(); } } + default: { reader.Skip(); @@ -150,6 +152,7 @@ namespace MediaBrowser.Providers.Music reader.Read(); continue; } + var mbzId = reader.GetAttribute("id"); using (var subReader = reader.ReadSubtree()) @@ -160,8 +163,10 @@ namespace MediaBrowser.Providers.Music yield return artist; } } + break; } + default: { reader.Skip(); @@ -202,6 +207,7 @@ namespace MediaBrowser.Providers.Music result.Overview = reader.ReadElementContentAsString(); break; } + default: { // there is sort-name if ever needed diff --git a/MediaBrowser.Providers/Plugins/Omdb/OmdbItemProvider.cs b/MediaBrowser.Providers/Plugins/Omdb/OmdbItemProvider.cs index 4a29ba4d06..b12d2a3885 100644 --- a/MediaBrowser.Providers/Plugins/Omdb/OmdbItemProvider.cs +++ b/MediaBrowser.Providers/Plugins/Omdb/OmdbItemProvider.cs @@ -286,27 +286,49 @@ namespace MediaBrowser.Providers.Plugins.Omdb class SearchResult { public string Title { get; set; } + public string Year { get; set; } + public string Rated { get; set; } + public string Released { get; set; } + public string Season { get; set; } + public string Episode { get; set; } + public string Runtime { get; set; } + public string Genre { get; set; } + public string Director { get; set; } + public string Writer { get; set; } + public string Actors { get; set; } + public string Plot { get; set; } + public string Language { get; set; } + public string Country { get; set; } + public string Awards { get; set; } + public string Poster { get; set; } + public string Metascore { get; set; } + public string imdbRating { get; set; } + public string imdbVotes { get; set; } + public string imdbID { get; set; } + public string seriesID { get; set; } + public string Type { get; set; } + public string Response { get; set; } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/CollectionImages.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/CollectionImages.cs index 2410ca16b5..4ebcaeeb6c 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/CollectionImages.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/CollectionImages.cs @@ -6,6 +6,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Collections public class CollectionImages { public List<Backdrop> Backdrops { get; set; } + public List<Poster> Posters { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/CollectionResult.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/CollectionResult.cs index 3437552df7..9228bec9ce 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/CollectionResult.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/CollectionResult.cs @@ -5,11 +5,17 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Collections public class CollectionResult { public int Id { get; set; } + public string Name { get; set; } + public string Overview { get; set; } + public string Poster_Path { get; set; } + public string Backdrop_Path { get; set; } + public List<Part> Parts { get; set; } + public CollectionImages Images { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/Part.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/Part.cs index 462fdab534..3a464e0537 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/Part.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Collections/Part.cs @@ -3,9 +3,13 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Collections public class Part { public string Title { get; set; } + public int Id { get; set; } + public string Release_Date { get; set; } + public string Poster_Path { get; set; } + public string Backdrop_Path { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Backdrop.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Backdrop.cs index 35e3e21126..add7a38d84 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Backdrop.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Backdrop.cs @@ -3,11 +3,17 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.General public class Backdrop { public double Aspect_Ratio { get; set; } + public string File_Path { get; set; } + public int Height { get; set; } + public string Iso_639_1 { get; set; } + public double Vote_Average { get; set; } + public int Vote_Count { get; set; } + public int Width { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Crew.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Crew.cs index 6a5e74ddbe..3f0fe7fad1 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Crew.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Crew.cs @@ -3,10 +3,15 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.General public class Crew { public int Id { get; set; } + public string Credit_Id { get; set; } + public string Name { get; set; } + public string Department { get; set; } + public string Job { get; set; } + public string Profile_Path { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/ExternalIds.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/ExternalIds.cs index a083f6e9c9..8082a5e586 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/ExternalIds.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/ExternalIds.cs @@ -3,9 +3,13 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.General public class ExternalIds { public string Imdb_Id { get; set; } + public object Freebase_Id { get; set; } + public string Freebase_Mid { get; set; } + public int Tvdb_Id { get; set; } + public int Tvrage_Id { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Genre.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Genre.cs index 7f1a394c36..d7b18ff8c7 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Genre.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Genre.cs @@ -3,6 +3,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.General public class Genre { public int Id { get; set; } + public string Name { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Images.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Images.cs index 166f9b7408..bbeac878a0 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Images.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Images.cs @@ -5,6 +5,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.General public class Images { public List<Backdrop> Backdrops { get; set; } + public List<Poster> Posters { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Keyword.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Keyword.cs index 72f417be5d..07cab86a04 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Keyword.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Keyword.cs @@ -3,6 +3,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.General public class Keyword { public int Id { get; set; } + public string Name { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Poster.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Poster.cs index 0cf04a6ce1..3ac89a77de 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Poster.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Poster.cs @@ -3,11 +3,17 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.General public class Poster { public double Aspect_Ratio { get; set; } + public string File_Path { get; set; } + public int Height { get; set; } + public string Iso_639_1 { get; set; } + public double Vote_Average { get; set; } + public int Vote_Count { get; set; } + public int Width { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Profile.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Profile.cs index b45cfc30f2..57edbe74c8 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Profile.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Profile.cs @@ -3,9 +3,13 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.General public class Profile { public string File_Path { get; set; } + public int Width { get; set; } + public int Height { get; set; } + public object Iso_639_1 { get; set; } + public double Aspect_Ratio { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Still.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Still.cs index 9fc82cfee7..1507c6577d 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Still.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Still.cs @@ -3,12 +3,19 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.General public class Still { public double Aspect_Ratio { get; set; } + public string File_Path { get; set; } + public int Height { get; set; } + public string Id { get; set; } + public string Iso_639_1 { get; set; } + public double Vote_Average { get; set; } + public int Vote_Count { get; set; } + public int Width { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Video.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Video.cs index 19bfd62f61..e0fef6cce5 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Video.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/General/Video.cs @@ -3,12 +3,19 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.General public class Video { public string Id { get; set; } + public string Iso_639_1 { get; set; } + public string Iso_3166_1 { get; set; } + public string Key { get; set; } + public string Name { get; set; } + public string Site { get; set; } + public string Size { get; set; } + public string Type { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/BelongsToCollection.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/BelongsToCollection.cs index aaca57f052..af5bc9282f 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/BelongsToCollection.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/BelongsToCollection.cs @@ -3,8 +3,11 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Movies public class BelongsToCollection { public int Id { get; set; } + public string Name { get; set; } + public string Poster_Path { get; set; } + public string Backdrop_Path { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Cast.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Cast.cs index d70f218aa7..6775350b71 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Cast.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Cast.cs @@ -3,10 +3,15 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Movies public class Cast { public int Id { get; set; } + public string Name { get; set; } + public string Character { get; set; } + public int Order { get; set; } + public int Cast_Id { get; set; } + public string Profile_Path { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Casts.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Casts.cs index c41699bc77..5601de85eb 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Casts.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Casts.cs @@ -6,6 +6,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Movies public class Casts { public List<Cast> Cast { get; set; } + public List<Crew> Crew { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Country.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Country.cs index 71d1f7c242..f4cbc41f6e 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Country.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Country.cs @@ -5,7 +5,9 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Movies public class Country { public string Iso_3166_1 { get; set; } + public string Certification { get; set; } + public DateTime Release_Date { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/MovieResult.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/MovieResult.cs index 2a9b9779af..8e25e4fb34 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/MovieResult.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/MovieResult.cs @@ -6,34 +6,63 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Movies public class MovieResult { public bool Adult { get; set; } + public string Backdrop_Path { get; set; } + public BelongsToCollection Belongs_To_Collection { get; set; } + public int Budget { get; set; } + public List<Genre> Genres { get; set; } + public string Homepage { get; set; } + public int Id { get; set; } + public string Imdb_Id { get; set; } + public string Original_Title { get; set; } + public string Original_Name { get; set; } + public string Overview { get; set; } + public double Popularity { get; set; } + public string Poster_Path { get; set; } + public List<ProductionCompany> Production_Companies { get; set; } + public List<ProductionCountry> Production_Countries { get; set; } + public string Release_Date { get; set; } + public int Revenue { get; set; } + public int Runtime { get; set; } + public List<SpokenLanguage> Spoken_Languages { get; set; } + public string Status { get; set; } + public string Tagline { get; set; } + public string Title { get; set; } + public string Name { get; set; } + public double Vote_Average { get; set; } + public int Vote_Count { get; set; } + public Casts Casts { get; set; } + public Releases Releases { get; set; } + public Images Images { get; set; } + public Keywords Keywords { get; set; } + public Trailers Trailers { get; set; } public string GetOriginalTitle() diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/ProductionCompany.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/ProductionCompany.cs index 11158ade5d..ba8e42fdde 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/ProductionCompany.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/ProductionCompany.cs @@ -3,6 +3,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Movies public class ProductionCompany { public string Name { get; set; } + public int Id { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/ProductionCountry.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/ProductionCountry.cs index 43d00fe7a2..a313605bd3 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/ProductionCountry.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/ProductionCountry.cs @@ -3,6 +3,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Movies public class ProductionCountry { public string Iso_3166_1 { get; set; } + public string Name { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/SpokenLanguage.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/SpokenLanguage.cs index 41defa9d08..9469a41f1f 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/SpokenLanguage.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/SpokenLanguage.cs @@ -3,6 +3,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Movies public class SpokenLanguage { public string Iso_639_1 { get; set; } + public string Name { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Youtube.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Youtube.cs index 6be4ef5b53..499e368a48 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Youtube.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Movies/Youtube.cs @@ -3,7 +3,9 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Movies public class Youtube { public string Name { get; set; } + public string Size { get; set; } + public string Source { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/People/PersonResult.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/People/PersonResult.cs index 50c47eefd0..076648a6cf 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/People/PersonResult.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/People/PersonResult.cs @@ -6,18 +6,31 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.People public class PersonResult { public bool Adult { get; set; } + public List<string> Also_Known_As { get; set; } + public string Biography { get; set; } + public string Birthday { get; set; } + public string Deathday { get; set; } + public string Homepage { get; set; } + public int Id { get; set; } + public string Imdb_Id { get; set; } + public string Name { get; set; } + public string Place_Of_Birth { get; set; } + public double Popularity { get; set; } + public string Profile_Path { get; set; } + public PersonImages Images { get; set; } + public ExternalIds External_Ids { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/Search/TvResult.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/Search/TvResult.cs index b7fbd294c2..c611bcd5f4 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/Search/TvResult.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/Search/TvResult.cs @@ -3,13 +3,21 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.Search public class TvResult { public string Backdrop_Path { get; set; } + public string First_Air_Date { get; set; } + public int Id { get; set; } + public string Original_Name { get; set; } + public string Poster_Path { get; set; } + public double Popularity { get; set; } + public string Name { get; set; } + public double Vote_Average { get; set; } + public int Vote_Count { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Cast.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Cast.cs index 9c770545c7..ebf7ba6e4c 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Cast.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Cast.cs @@ -3,10 +3,15 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class Cast { public string Character { get; set; } + public string Credit_Id { get; set; } + public int Id { get; set; } + public string Name { get; set; } + public string Profile_Path { get; set; } + public int Order { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/ContentRating.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/ContentRating.cs index bccb234e7d..9de674e7fb 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/ContentRating.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/ContentRating.cs @@ -3,6 +3,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class ContentRating { public string Iso_3166_1 { get; set; } + public string Rating { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/CreatedBy.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/CreatedBy.cs index 35e8eaecb8..1ef65bb986 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/CreatedBy.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/CreatedBy.cs @@ -3,7 +3,9 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class CreatedBy { public int Id { get; set; } + public string Name { get; set; } + public string Profile_Path { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Credits.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Credits.cs index ebf412c2df..836fbcbe51 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Credits.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Credits.cs @@ -6,6 +6,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class Credits { public List<Cast> Cast { get; set; } + public List<Crew> Crew { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Episode.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Episode.cs index 8203632b7c..a38012e31c 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Episode.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Episode.cs @@ -3,12 +3,19 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class Episode { public string Air_Date { get; set; } + public int Episode_Number { get; set; } + public int Id { get; set; } + public string Name { get; set; } + public string Overview { get; set; } + public string Still_Path { get; set; } + public double Vote_Average { get; set; } + public int Vote_Count { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/EpisodeCredits.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/EpisodeCredits.cs index f89859f85b..5068e8f9bc 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/EpisodeCredits.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/EpisodeCredits.cs @@ -6,7 +6,9 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class EpisodeCredits { public List<Cast> Cast { get; set; } + public List<Crew> Crew { get; set; } + public List<GuestStar> Guest_Stars { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/EpisodeResult.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/EpisodeResult.cs index e25b65d70a..a4d6a130ef 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/EpisodeResult.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/EpisodeResult.cs @@ -6,18 +6,31 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class EpisodeResult { public DateTime Air_Date { get; set; } + public int Episode_Number { get; set; } + public string Name { get; set; } + public string Overview { get; set; } + public int Id { get; set; } + public object Production_Code { get; set; } + public int Season_Number { get; set; } + public string Still_Path { get; set; } + public double Vote_Average { get; set; } + public int Vote_Count { get; set; } + public StillImages Images { get; set; } + public ExternalIds External_Ids { get; set; } + public EpisodeCredits Credits { get; set; } + public Tmdb.Models.General.Videos Videos { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/GuestStar.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/GuestStar.cs index 260f3f610f..da5e631717 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/GuestStar.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/GuestStar.cs @@ -3,10 +3,15 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class GuestStar { public int Id { get; set; } + public string Name { get; set; } + public string Credit_Id { get; set; } + public string Character { get; set; } + public int Order { get; set; } + public string Profile_Path { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Network.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Network.cs index 5ed3108276..0eba92ae27 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Network.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Network.cs @@ -3,6 +3,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class Network { public int Id { get; set; } + public string Name { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Season.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Season.cs index fddf950ee8..2e39c5901c 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Season.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/Season.cs @@ -3,9 +3,13 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class Season { public string Air_Date { get; set; } + public int Episode_Count { get; set; } + public int Id { get; set; } + public string Poster_Path { get; set; } + public int Season_Number { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/SeasonResult.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/SeasonResult.cs index 13b4c30f80..328bd1ebc7 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/SeasonResult.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/SeasonResult.cs @@ -7,15 +7,25 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class SeasonResult { public DateTime Air_Date { get; set; } + public List<Episode> Episodes { get; set; } + public string Name { get; set; } + public string Overview { get; set; } + public int Id { get; set; } + public string Poster_Path { get; set; } + public int Season_Number { get; set; } + public Credits Credits { get; set; } + public SeasonImages Images { get; set; } + public ExternalIds External_Ids { get; set; } + public General.Videos Videos { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/SeriesResult.cs b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/SeriesResult.cs index 5c1666c77c..499249b8ee 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/SeriesResult.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Models/TV/SeriesResult.cs @@ -7,34 +7,63 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Models.TV public class SeriesResult { public string Backdrop_Path { get; set; } + public List<CreatedBy> Created_By { get; set; } + public List<int> Episode_Run_Time { get; set; } + public DateTime First_Air_Date { get; set; } + public List<Genre> Genres { get; set; } + public string Homepage { get; set; } + public int Id { get; set; } + public bool In_Production { get; set; } + public List<string> Languages { get; set; } + public DateTime Last_Air_Date { get; set; } + public string Name { get; set; } + public List<Network> Networks { get; set; } + public int Number_Of_Episodes { get; set; } + public int Number_Of_Seasons { get; set; } + public string Original_Name { get; set; } + public List<string> Origin_Country { get; set; } + public string Overview { get; set; } + public string Popularity { get; set; } + public string Poster_Path { get; set; } + public List<Season> Seasons { get; set; } + public string Status { get; set; } + public double Vote_Average { get; set; } + public int Vote_Count { get; set; } + public Credits Credits { get; set; } + public Images Images { get; set; } + public Keywords Keywords { get; set; } + public ExternalIds External_Ids { get; set; } + public General.Videos Videos { get; set; } + public ContentRatings Content_Ratings { get; set; } + public string ResultLanguage { get; set; } } } diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Movies/TmdbImageProvider.cs b/MediaBrowser.Providers/Plugins/Tmdb/Movies/TmdbImageProvider.cs index a11c89459d..8ecd6b917e 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Movies/TmdbImageProvider.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Movies/TmdbImageProvider.cs @@ -107,6 +107,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Movies { return 3; } + if (!isLanguageEn) { if (string.Equals("en", i.Language, StringComparison.OrdinalIgnoreCase)) @@ -114,10 +115,12 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Movies return 2; } } + if (string.IsNullOrEmpty(i.Language)) { return isLanguageEn ? 3 : 2; } + return 0; }) .ThenByDescending(i => i.CommunityRating ?? 0) diff --git a/MediaBrowser.Providers/Plugins/Tmdb/Movies/TmdbSettings.cs b/MediaBrowser.Providers/Plugins/Tmdb/Movies/TmdbSettings.cs index 03669ca67c..3a45d4a559 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/Movies/TmdbSettings.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/Movies/TmdbSettings.cs @@ -5,8 +5,11 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.Movies internal class TmdbImageSettings { public List<string> backdrop_sizes { get; set; } + public string secure_base_url { get; set; } + public List<string> poster_sizes { get; set; } + public List<string> profile_sizes { get; set; } public string GetImageUrl(string image) diff --git a/MediaBrowser.Providers/Plugins/Tmdb/People/TmdbPersonImageProvider.cs b/MediaBrowser.Providers/Plugins/Tmdb/People/TmdbPersonImageProvider.cs index 525c0072b3..edd90475d2 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/People/TmdbPersonImageProvider.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/People/TmdbPersonImageProvider.cs @@ -98,6 +98,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.People { return 3; } + if (!isLanguageEn) { if (string.Equals("en", i.Language, StringComparison.OrdinalIgnoreCase)) @@ -105,10 +106,12 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.People return 2; } } + if (string.IsNullOrEmpty(i.Language)) { return isLanguageEn ? 3 : 2; } + return 0; }) .ThenByDescending(i => i.CommunityRating ?? 0) diff --git a/MediaBrowser.Providers/Plugins/Tmdb/People/TmdbPersonProvider.cs b/MediaBrowser.Providers/Plugins/Tmdb/People/TmdbPersonProvider.cs index 654e42a90c..a13d41dc22 100644 --- a/MediaBrowser.Providers/Plugins/Tmdb/People/TmdbPersonProvider.cs +++ b/MediaBrowser.Providers/Plugins/Tmdb/People/TmdbPersonProvider.cs @@ -173,6 +173,7 @@ namespace MediaBrowser.Providers.Plugins.Tmdb.People { item.ProductionLocations = new string[] { info.Place_Of_Birth }; } + item.Overview = info.Biography; if (DateTime.TryParseExact(info.Birthday, "yyyy-MM-dd", new CultureInfo("en-US"), DateTimeStyles.None, out var date)) diff --git a/MediaBrowser.Providers/Subtitles/SubtitleManager.cs b/MediaBrowser.Providers/Subtitles/SubtitleManager.cs index 8086533eb6..24c29a2199 100644 --- a/MediaBrowser.Providers/Subtitles/SubtitleManager.cs +++ b/MediaBrowser.Providers/Subtitles/SubtitleManager.cs @@ -104,6 +104,7 @@ namespace MediaBrowser.Providers.Subtitles _logger.LogError(ex, "Error downloading subtitles from {Provider}", provider.Name); } } + return Array.Empty<RemoteSubtitleInfo>(); } diff --git a/MediaBrowser.Providers/TV/DummySeasonProvider.cs b/MediaBrowser.Providers/TV/DummySeasonProvider.cs index 6e0511971b..92c42e9d8f 100644 --- a/MediaBrowser.Providers/TV/DummySeasonProvider.cs +++ b/MediaBrowser.Providers/TV/DummySeasonProvider.cs @@ -72,6 +72,7 @@ namespace MediaBrowser.Providers.TV { seasons = series.Children.OfType<Season>().ToList(); } + var existingSeason = seasons .FirstOrDefault(i => i.IndexNumber.HasValue && i.IndexNumber.Value == seasonNumber); diff --git a/MediaBrowser.Providers/TV/SeriesMetadataService.cs b/MediaBrowser.Providers/TV/SeriesMetadataService.cs index 7a753e8324..6d303fab10 100644 --- a/MediaBrowser.Providers/TV/SeriesMetadataService.cs +++ b/MediaBrowser.Providers/TV/SeriesMetadataService.cs @@ -67,10 +67,12 @@ namespace MediaBrowser.Providers.TV { return false; } + if (!item.ProductionYear.HasValue) { return false; } + return base.IsFullLocalMetadata(item); } diff --git a/RSSDP/DiscoveredSsdpDevice.cs b/RSSDP/DiscoveredSsdpDevice.cs index 1244ce523d..9093199dd6 100644 --- a/RSSDP/DiscoveredSsdpDevice.cs +++ b/RSSDP/DiscoveredSsdpDevice.cs @@ -45,6 +45,7 @@ namespace Rssdp public DateTimeOffset AsAt { get { return _AsAt; } + set { if (_AsAt != value) diff --git a/RSSDP/HttpParserBase.cs b/RSSDP/HttpParserBase.cs index c2eb0bf92f..e7172cb1c0 100644 --- a/RSSDP/HttpParserBase.cs +++ b/RSSDP/HttpParserBase.cs @@ -135,6 +135,7 @@ namespace Rssdp.Infrastructure ParseHeader(line, headers, contentHeaders); } + return lineIndex; } diff --git a/RSSDP/SsdpCommunicationsServer.cs b/RSSDP/SsdpCommunicationsServer.cs index 863f2b15c2..fe49fb7d36 100644 --- a/RSSDP/SsdpCommunicationsServer.cs +++ b/RSSDP/SsdpCommunicationsServer.cs @@ -311,6 +311,7 @@ namespace Rssdp.Infrastructure public bool IsShared { get { return _IsShared; } + set { _IsShared = value; } } diff --git a/RSSDP/SsdpDevice.cs b/RSSDP/SsdpDevice.cs index 691ba2a14a..f89bafb196 100644 --- a/RSSDP/SsdpDevice.cs +++ b/RSSDP/SsdpDevice.cs @@ -90,6 +90,7 @@ namespace Rssdp { return _DeviceType; } + set { _DeviceType = value; @@ -111,6 +112,7 @@ namespace Rssdp { return _DeviceTypeNamespace; } + set { _DeviceTypeNamespace = value; @@ -130,6 +132,7 @@ namespace Rssdp { return _DeviceVersion; } + set { _DeviceVersion = value; @@ -181,6 +184,7 @@ namespace Rssdp else return _Udn; } + set { _Udn = value; diff --git a/RSSDP/SsdpDeviceLocator.cs b/RSSDP/SsdpDeviceLocator.cs index a626e13b9a..9b48cf31ce 100644 --- a/RSSDP/SsdpDeviceLocator.cs +++ b/RSSDP/SsdpDeviceLocator.cs @@ -579,6 +579,7 @@ namespace Rssdp.Infrastructure return d; } } + return null; } diff --git a/RSSDP/SsdpDevicePublisher.cs b/RSSDP/SsdpDevicePublisher.cs index 5dfb6a8c20..b4cf2fb484 100644 --- a/RSSDP/SsdpDevicePublisher.cs +++ b/RSSDP/SsdpDevicePublisher.cs @@ -156,6 +156,7 @@ namespace Rssdp.Infrastructure public bool SupportPnpRootDevice { get { return _SupportPnpRootDevice; } + set { _SupportPnpRootDevice = value; @@ -564,7 +565,9 @@ namespace Rssdp.Infrastructure private class SearchRequest { public IPEndPoint EndPoint { get; set; } + public DateTime Received { get; set; } + public string SearchTarget { get; set; } public string Key diff --git a/RSSDP/SsdpEmbeddedDevice.cs b/RSSDP/SsdpEmbeddedDevice.cs index 4810703d74..ff644993b5 100644 --- a/RSSDP/SsdpEmbeddedDevice.cs +++ b/RSSDP/SsdpEmbeddedDevice.cs @@ -33,6 +33,7 @@ namespace Rssdp { return _RootDevice; } + internal set { _RootDevice = value;