فهرست منبع

Fix some warnings

Bond_009 3 سال پیش
والد
کامیت
637e86478f
31فایلهای تغییر یافته به همراه325 افزوده شده و 410 حذف شده
  1. 105 139
      Emby.Server.Implementations/ApplicationHost.cs
  2. 2 2
      Emby.Server.Implementations/Collections/CollectionManager.cs
  3. 3 14
      Emby.Server.Implementations/Data/SqliteItemRepository.cs
  4. 23 24
      Emby.Server.Implementations/Data/SqliteUserDataRepository.cs
  5. 7 7
      Emby.Server.Implementations/Dto/DtoService.cs
  6. 3 3
      Emby.Server.Implementations/IO/ManagedFileSystem.cs
  7. 1 1
      Emby.Server.Implementations/Images/BaseDynamicImageProvider.cs
  8. 10 12
      Emby.Server.Implementations/Library/LibraryManager.cs
  9. 3 2
      Emby.Server.Implementations/Library/MusicManager.cs
  10. 2 2
      Emby.Server.Implementations/Library/Resolvers/BaseVideoResolver.cs
  11. 3 1
      Emby.Server.Implementations/Library/UserDataManager.cs
  12. 13 13
      Emby.Server.Implementations/LiveTv/EmbyTV/EmbyTV.cs
  13. 25 30
      Emby.Server.Implementations/LiveTv/LiveTvManager.cs
  14. 1 1
      Emby.Server.Implementations/LiveTv/TunerHosts/BaseTunerHost.cs
  15. 30 34
      Emby.Server.Implementations/LiveTv/TunerHosts/HdHomerun/HdHomerunHost.cs
  16. 11 11
      Emby.Server.Implementations/LiveTv/TunerHosts/M3UTunerHost.cs
  17. 6 14
      Emby.Server.Implementations/Net/SocketFactory.cs
  18. 2 2
      Emby.Server.Implementations/Net/UdpSocket.cs
  19. 4 0
      Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteCacheFileTask.cs
  20. 9 9
      Emby.Server.Implementations/Session/SessionManager.cs
  21. 11 11
      Emby.Server.Implementations/TV/TVSeriesManager.cs
  22. 1 2
      MediaBrowser.Controller/Entities/CollectionFolder.cs
  23. 0 7
      MediaBrowser.Controller/IServerApplicationHost.cs
  24. 3 3
      MediaBrowser.Controller/Library/ILibraryManager.cs
  25. 3 3
      MediaBrowser.Controller/Library/IUserDataManager.cs
  26. 1 1
      MediaBrowser.Controller/LiveTv/ILiveTvManager.cs
  27. 2 2
      MediaBrowser.Controller/LiveTv/ILiveTvService.cs
  28. 4 4
      MediaBrowser.Controller/Persistence/IItemRepository.cs
  29. 1 1
      MediaBrowser.Controller/Session/ISessionManager.cs
  30. 30 55
      MediaBrowser.Model/Dlna/StreamInfo.cs
  31. 6 0
      jellyfin.ruleset

+ 105 - 139
Emby.Server.Implementations/ApplicationHost.cs

@@ -114,6 +114,11 @@ namespace Emby.Server.Implementations
         /// </summary>
         /// </summary>
         private static readonly string[] _relevantEnvVarPrefixes = { "JELLYFIN_", "DOTNET_", "ASPNETCORE_" };
         private static readonly string[] _relevantEnvVarPrefixes = { "JELLYFIN_", "DOTNET_", "ASPNETCORE_" };
 
 
+        /// <summary>
+        /// The disposable parts.
+        /// </summary>
+        private readonly List<IDisposable> _disposableParts = new List<IDisposable>();
+
         private readonly IFileSystem _fileSystemManager;
         private readonly IFileSystem _fileSystemManager;
         private readonly IConfiguration _startupConfig;
         private readonly IConfiguration _startupConfig;
         private readonly IXmlSerializer _xmlSerializer;
         private readonly IXmlSerializer _xmlSerializer;
@@ -125,6 +130,62 @@ namespace Emby.Server.Implementations
         private ISessionManager _sessionManager;
         private ISessionManager _sessionManager;
         private string[] _urlPrefixes;
         private string[] _urlPrefixes;
 
 
+        /// <summary>
+        /// Gets or sets all concrete types.
+        /// </summary>
+        /// <value>All concrete types.</value>
+        private Type[] _allConcreteTypes;
+
+        private DeviceId _deviceId;
+
+        private bool _disposed = false;
+
+        /// <summary>
+        /// Initializes a new instance of the <see cref="ApplicationHost"/> class.
+        /// </summary>
+        /// <param name="applicationPaths">Instance of the <see cref="IServerApplicationPaths"/> interface.</param>
+        /// <param name="loggerFactory">Instance of the <see cref="ILoggerFactory"/> interface.</param>
+        /// <param name="options">Instance of the <see cref="IStartupOptions"/> interface.</param>
+        /// <param name="startupConfig">The <see cref="IConfiguration" /> interface.</param>
+        /// <param name="fileSystem">Instance of the <see cref="IFileSystem"/> interface.</param>
+        /// <param name="serviceCollection">Instance of the <see cref="IServiceCollection"/> interface.</param>
+        public ApplicationHost(
+            IServerApplicationPaths applicationPaths,
+            ILoggerFactory loggerFactory,
+            IStartupOptions options,
+            IConfiguration startupConfig,
+            IFileSystem fileSystem,
+            IServiceCollection serviceCollection)
+        {
+            ApplicationPaths = applicationPaths;
+            LoggerFactory = loggerFactory;
+            _startupOptions = options;
+            _startupConfig = startupConfig;
+            _fileSystemManager = fileSystem;
+            ServiceCollection = serviceCollection;
+
+            Logger = LoggerFactory.CreateLogger<ApplicationHost>();
+            fileSystem.AddShortcutHandler(new MbLinkShortcutHandler(fileSystem));
+
+            ApplicationVersion = typeof(ApplicationHost).Assembly.GetName().Version;
+            ApplicationVersionString = ApplicationVersion.ToString(3);
+            ApplicationUserAgent = Name.Replace(' ', '-') + "/" + ApplicationVersionString;
+
+            _xmlSerializer = new MyXmlSerializer();
+            ConfigurationManager = new ServerConfigurationManager(ApplicationPaths, LoggerFactory, _xmlSerializer, _fileSystemManager);
+            _pluginManager = new PluginManager(
+                LoggerFactory.CreateLogger<PluginManager>(),
+                this,
+                ConfigurationManager.Configuration,
+                ApplicationPaths.PluginsPath,
+                ApplicationVersion);
+        }
+
+        /// <summary>
+        /// Occurs when [has pending restart changed].
+        /// </summary>
+        public event EventHandler HasPendingRestartChanged;
+
         /// <summary>
         /// <summary>
         /// Gets a value indicating whether this instance can self restart.
         /// Gets a value indicating whether this instance can self restart.
         /// </summary>
         /// </summary>
@@ -155,11 +216,6 @@ namespace Emby.Server.Implementations
         /// </summary>
         /// </summary>
         public INetworkManager NetManager { get; internal set; }
         public INetworkManager NetManager { get; internal set; }
 
 
-        /// <summary>
-        /// Occurs when [has pending restart changed].
-        /// </summary>
-        public event EventHandler HasPendingRestartChanged;
-
         /// <summary>
         /// <summary>
         /// Gets a value indicating whether this instance has changes that require the entire application to restart.
         /// Gets a value indicating whether this instance has changes that require the entire application to restart.
         /// </summary>
         /// </summary>
@@ -187,17 +243,6 @@ namespace Emby.Server.Implementations
         /// <value>The application paths.</value>
         /// <value>The application paths.</value>
         protected IServerApplicationPaths ApplicationPaths { get; set; }
         protected IServerApplicationPaths ApplicationPaths { get; set; }
 
 
-        /// <summary>
-        /// Gets or sets all concrete types.
-        /// </summary>
-        /// <value>All concrete types.</value>
-        private Type[] _allConcreteTypes;
-
-        /// <summary>
-        /// The disposable parts.
-        /// </summary>
-        private readonly List<IDisposable> _disposableParts = new List<IDisposable>();
-
         /// <summary>
         /// <summary>
         /// Gets or sets the configuration manager.
         /// Gets or sets the configuration manager.
         /// </summary>
         /// </summary>
@@ -224,47 +269,55 @@ namespace Emby.Server.Implementations
         /// </summary>
         /// </summary>
         public string PublishedServerUrl => _startupOptions.PublishedServerUrl ?? _startupConfig[UdpServer.AddressOverrideConfigKey];
         public string PublishedServerUrl => _startupOptions.PublishedServerUrl ?? _startupConfig[UdpServer.AddressOverrideConfigKey];
 
 
+        /// <inheritdoc />
+        public Version ApplicationVersion { get; }
+
+        /// <inheritdoc />
+        public string ApplicationVersionString { get; }
+
         /// <summary>
         /// <summary>
-        /// Initializes a new instance of the <see cref="ApplicationHost"/> class.
+        /// Gets the current application user agent.
         /// </summary>
         /// </summary>
-        /// <param name="applicationPaths">Instance of the <see cref="IServerApplicationPaths"/> interface.</param>
-        /// <param name="loggerFactory">Instance of the <see cref="ILoggerFactory"/> interface.</param>
-        /// <param name="options">Instance of the <see cref="IStartupOptions"/> interface.</param>
-        /// <param name="startupConfig">The <see cref="IConfiguration" /> interface.</param>
-        /// <param name="fileSystem">Instance of the <see cref="IFileSystem"/> interface.</param>
-        /// <param name="serviceCollection">Instance of the <see cref="IServiceCollection"/> interface.</param>
-        public ApplicationHost(
-            IServerApplicationPaths applicationPaths,
-            ILoggerFactory loggerFactory,
-            IStartupOptions options,
-            IConfiguration startupConfig,
-            IFileSystem fileSystem,
-            IServiceCollection serviceCollection)
-        {
-            ApplicationPaths = applicationPaths;
-            LoggerFactory = loggerFactory;
-            _startupOptions = options;
-            _startupConfig = startupConfig;
-            _fileSystemManager = fileSystem;
-            ServiceCollection = serviceCollection;
+        /// <value>The application user agent.</value>
+        public string ApplicationUserAgent { get; }
 
 
-            Logger = LoggerFactory.CreateLogger<ApplicationHost>();
-            fileSystem.AddShortcutHandler(new MbLinkShortcutHandler(fileSystem));
+        /// <summary>
+        /// Gets the email address for use within a comment section of a user agent field.
+        /// Presently used to provide contact information to MusicBrainz service.
+        /// </summary>
+        public string ApplicationUserAgentAddress => "team@jellyfin.org";
 
 
-            ApplicationVersion = typeof(ApplicationHost).Assembly.GetName().Version;
-            ApplicationVersionString = ApplicationVersion.ToString(3);
-            ApplicationUserAgent = Name.Replace(' ', '-') + "/" + ApplicationVersionString;
+        /// <summary>
+        /// Gets the current application name.
+        /// </summary>
+        /// <value>The application name.</value>
+        public string ApplicationProductName { get; } = FileVersionInfo.GetVersionInfo(Assembly.GetEntryAssembly().Location).ProductName;
 
 
-            _xmlSerializer = new MyXmlSerializer();
-            ConfigurationManager = new ServerConfigurationManager(ApplicationPaths, LoggerFactory, _xmlSerializer, _fileSystemManager);
-            _pluginManager = new PluginManager(
-                LoggerFactory.CreateLogger<PluginManager>(),
-                this,
-                ConfigurationManager.Configuration,
-                ApplicationPaths.PluginsPath,
-                ApplicationVersion);
+        public string SystemId
+        {
+            get
+            {
+                _deviceId ??= new DeviceId(ApplicationPaths, LoggerFactory);
+
+                return _deviceId.Value;
+            }
         }
         }
 
 
+        /// <inheritdoc/>
+        public string Name => ApplicationProductName;
+
+        private CertificateInfo CertificateInfo { get; set; }
+
+        public X509Certificate2 Certificate { get; private set; }
+
+        /// <inheritdoc/>
+        public bool ListenWithHttps => Certificate != null && ConfigurationManager.GetNetworkConfiguration().EnableHttps;
+
+        public string FriendlyName =>
+            string.IsNullOrEmpty(ConfigurationManager.Configuration.ServerName)
+                ? Environment.MachineName
+                : ConfigurationManager.Configuration.ServerName;
+
         /// <summary>
         /// <summary>
         /// Temporary function to migration network settings out of system.xml and into network.xml.
         /// Temporary function to migration network settings out of system.xml and into network.xml.
         /// TODO: remove at the point when a fixed migration path has been decided upon.
         /// TODO: remove at the point when a fixed migration path has been decided upon.
@@ -297,45 +350,6 @@ namespace Emby.Server.Implementations
                 .Replace(appPaths.InternalMetadataPath, appPaths.VirtualInternalMetadataPath, StringComparison.OrdinalIgnoreCase);
                 .Replace(appPaths.InternalMetadataPath, appPaths.VirtualInternalMetadataPath, StringComparison.OrdinalIgnoreCase);
         }
         }
 
 
-        /// <inheritdoc />
-        public Version ApplicationVersion { get; }
-
-        /// <inheritdoc />
-        public string ApplicationVersionString { get; }
-
-        /// <summary>
-        /// Gets the current application user agent.
-        /// </summary>
-        /// <value>The application user agent.</value>
-        public string ApplicationUserAgent { get; }
-
-        /// <summary>
-        /// Gets the email address for use within a comment section of a user agent field.
-        /// Presently used to provide contact information to MusicBrainz service.
-        /// </summary>
-        public string ApplicationUserAgentAddress => "team@jellyfin.org";
-
-        /// <summary>
-        /// Gets the current application name.
-        /// </summary>
-        /// <value>The application name.</value>
-        public string ApplicationProductName { get; } = FileVersionInfo.GetVersionInfo(Assembly.GetEntryAssembly().Location).ProductName;
-
-        private DeviceId _deviceId;
-
-        public string SystemId
-        {
-            get
-            {
-                _deviceId ??= new DeviceId(ApplicationPaths, LoggerFactory);
-
-                return _deviceId.Value;
-            }
-        }
-
-        /// <inheritdoc/>
-        public string Name => ApplicationProductName;
-
         /// <summary>
         /// <summary>
         /// Creates an instance of type and resolves all constructor dependencies.
         /// Creates an instance of type and resolves all constructor dependencies.
         /// </summary>
         /// </summary>
@@ -857,10 +871,6 @@ namespace Emby.Server.Implementations
             }
             }
         }
         }
 
 
-        private CertificateInfo CertificateInfo { get; set; }
-
-        public X509Certificate2 Certificate { get; private set; }
-
         private IEnumerable<string> GetUrlPrefixes()
         private IEnumerable<string> GetUrlPrefixes()
         {
         {
             var hosts = new[] { "+" };
             var hosts = new[] { "+" };
@@ -1114,9 +1124,6 @@ namespace Emby.Server.Implementations
             };
             };
         }
         }
 
 
-        /// <inheritdoc/>
-        public bool ListenWithHttps => Certificate != null && ConfigurationManager.GetNetworkConfiguration().EnableHttps;
-
         /// <inheritdoc/>
         /// <inheritdoc/>
         public string GetSmartApiUrl(IPAddress remoteAddr, int? port = null)
         public string GetSmartApiUrl(IPAddress remoteAddr, int? port = null)
         {
         {
@@ -1203,14 +1210,7 @@ namespace Emby.Server.Implementations
             }.ToString().TrimEnd('/');
             }.ToString().TrimEnd('/');
         }
         }
 
 
-        public string FriendlyName =>
-            string.IsNullOrEmpty(ConfigurationManager.Configuration.ServerName)
-                ? Environment.MachineName
-                : ConfigurationManager.Configuration.ServerName;
-
-        /// <summary>
-        /// Shuts down.
-        /// </summary>
+        /// <inheritdoc />
         public async Task Shutdown()
         public async Task Shutdown()
         {
         {
             if (IsShuttingDown)
             if (IsShuttingDown)
@@ -1248,41 +1248,7 @@ namespace Emby.Server.Implementations
             }
             }
         }
         }
 
 
-        public virtual void LaunchUrl(string url)
-        {
-            if (!CanLaunchWebBrowser)
-            {
-                throw new NotSupportedException();
-            }
-
-            var process = new Process
-            {
-                StartInfo = new ProcessStartInfo
-                {
-                    FileName = url,
-                    UseShellExecute = true,
-                    ErrorDialog = false
-                },
-                EnableRaisingEvents = true
-            };
-            process.Exited += (sender, args) => ((Process)sender).Dispose();
-
-            try
-            {
-                process.Start();
-            }
-            catch (Exception ex)
-            {
-                Logger.LogError(ex, "Error launching url: {url}", url);
-                throw;
-            }
-        }
-
-        private bool _disposed = false;
-
-        /// <summary>
-        /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
-        /// </summary>
+        /// <inheritdoc />
         public void Dispose()
         public void Dispose()
         {
         {
             Dispose(true);
             Dispose(true);

+ 2 - 2
Emby.Server.Implementations/Collections/CollectionManager.cs

@@ -196,8 +196,8 @@ namespace Emby.Server.Implementations.Collections
         }
         }
 
 
         /// <inheritdoc />
         /// <inheritdoc />
-        public Task AddToCollectionAsync(Guid collectionId, IEnumerable<Guid> ids)
-            => AddToCollectionAsync(collectionId, ids, true, new MetadataRefreshOptions(new DirectoryService(_fileSystem)));
+        public Task AddToCollectionAsync(Guid collectionId, IEnumerable<Guid> itemIds)
+            => AddToCollectionAsync(collectionId, itemIds, true, new MetadataRefreshOptions(new DirectoryService(_fileSystem)));
 
 
         private async Task AddToCollectionAsync(Guid collectionId, IEnumerable<Guid> ids, bool fireEvent, MetadataRefreshOptions refreshOptions)
         private async Task AddToCollectionAsync(Guid collectionId, IEnumerable<Guid> ids, bool fireEvent, MetadataRefreshOptions refreshOptions)
         {
         {

+ 3 - 14
Emby.Server.Implementations/Data/SqliteItemRepository.cs

@@ -1902,12 +1902,7 @@ namespace Emby.Server.Implementations.Data
             return result;
             return result;
         }
         }
 
 
-        /// <summary>
-        /// Gets chapters for an item.
-        /// </summary>
-        /// <param name="item">The item.</param>
-        /// <returns>IEnumerable{ChapterInfo}.</returns>
-        /// <exception cref="ArgumentNullException">id</exception>
+        /// <inheritdoc />
         public List<ChapterInfo> GetChapters(BaseItem item)
         public List<ChapterInfo> GetChapters(BaseItem item)
         {
         {
             CheckDisposed();
             CheckDisposed();
@@ -1930,13 +1925,7 @@ namespace Emby.Server.Implementations.Data
             }
             }
         }
         }
 
 
-        /// <summary>
-        /// Gets a single chapter for an item.
-        /// </summary>
-        /// <param name="item">The item.</param>
-        /// <param name="index">The index.</param>
-        /// <returns>ChapterInfo.</returns>
-        /// <exception cref="ArgumentNullException">id</exception>
+        /// <inheritdoc />
         public ChapterInfo GetChapter(BaseItem item, int index)
         public ChapterInfo GetChapter(BaseItem item, int index)
         {
         {
             CheckDisposed();
             CheckDisposed();
@@ -2048,7 +2037,7 @@ namespace Emby.Server.Implementations.Data
 
 
                 for (var i = startIndex; i < endIndex; i++)
                 for (var i = startIndex; i < endIndex; i++)
                 {
                 {
-                    insertText.AppendFormat("(@ItemId, @ChapterIndex{0}, @StartPositionTicks{0}, @Name{0}, @ImagePath{0}, @ImageDateModified{0}),", i.ToString(CultureInfo.InvariantCulture));
+                    insertText.AppendFormat(CultureInfo.InvariantCulture, "(@ItemId, @ChapterIndex{0}, @StartPositionTicks{0}, @Name{0}, @ImagePath{0}, @ImageDateModified{0}),", i.ToString(CultureInfo.InvariantCulture));
                 }
                 }
 
 
                 insertText.Length -= 1; // Remove last ,
                 insertText.Length -= 1; // Remove last ,

+ 23 - 24
Emby.Server.Implementations/Data/SqliteUserDataRepository.cs

@@ -129,19 +129,17 @@ namespace Emby.Server.Implementations.Data
             return list;
             return list;
         }
         }
 
 
-        /// <summary>
-        /// Saves the user data.
-        /// </summary>
-        public void SaveUserData(long internalUserId, string key, UserItemData userData, CancellationToken cancellationToken)
+        /// <inheritdoc />
+        public void SaveUserData(long userId, string key, UserItemData userData, CancellationToken cancellationToken)
         {
         {
             if (userData == null)
             if (userData == null)
             {
             {
                 throw new ArgumentNullException(nameof(userData));
                 throw new ArgumentNullException(nameof(userData));
             }
             }
 
 
-            if (internalUserId <= 0)
+            if (userId <= 0)
             {
             {
-                throw new ArgumentNullException(nameof(internalUserId));
+                throw new ArgumentNullException(nameof(userId));
             }
             }
 
 
             if (string.IsNullOrEmpty(key))
             if (string.IsNullOrEmpty(key))
@@ -149,22 +147,23 @@ namespace Emby.Server.Implementations.Data
                 throw new ArgumentNullException(nameof(key));
                 throw new ArgumentNullException(nameof(key));
             }
             }
 
 
-            PersistUserData(internalUserId, key, userData, cancellationToken);
+            PersistUserData(userId, key, userData, cancellationToken);
         }
         }
 
 
-        public void SaveAllUserData(long internalUserId, UserItemData[] userData, CancellationToken cancellationToken)
+        /// <inheritdoc />
+        public void SaveAllUserData(long userId, UserItemData[] userData, CancellationToken cancellationToken)
         {
         {
             if (userData == null)
             if (userData == null)
             {
             {
                 throw new ArgumentNullException(nameof(userData));
                 throw new ArgumentNullException(nameof(userData));
             }
             }
 
 
-            if (internalUserId <= 0)
+            if (userId <= 0)
             {
             {
-                throw new ArgumentNullException(nameof(internalUserId));
+                throw new ArgumentNullException(nameof(userId));
             }
             }
 
 
-            PersistAllUserData(internalUserId, userData, cancellationToken);
+            PersistAllUserData(userId, userData, cancellationToken);
         }
         }
 
 
         /// <summary>
         /// <summary>
@@ -263,19 +262,19 @@ namespace Emby.Server.Implementations.Data
         /// <summary>
         /// <summary>
         /// Gets the user data.
         /// Gets the user data.
         /// </summary>
         /// </summary>
-        /// <param name="internalUserId">The user id.</param>
+        /// <param name="userId">The user id.</param>
         /// <param name="key">The key.</param>
         /// <param name="key">The key.</param>
         /// <returns>Task{UserItemData}.</returns>
         /// <returns>Task{UserItemData}.</returns>
         /// <exception cref="ArgumentNullException">
         /// <exception cref="ArgumentNullException">
         /// userId
         /// userId
         /// or
         /// or
-        /// key
+        /// key.
         /// </exception>
         /// </exception>
-        public UserItemData GetUserData(long internalUserId, string key)
+        public UserItemData GetUserData(long userId, string key)
         {
         {
-            if (internalUserId <= 0)
+            if (userId <= 0)
             {
             {
-                throw new ArgumentNullException(nameof(internalUserId));
+                throw new ArgumentNullException(nameof(userId));
             }
             }
 
 
             if (string.IsNullOrEmpty(key))
             if (string.IsNullOrEmpty(key))
@@ -287,7 +286,7 @@ namespace Emby.Server.Implementations.Data
             {
             {
                 using (var statement = connection.PrepareStatement("select key,userid,rating,played,playCount,isFavorite,playbackPositionTicks,lastPlayedDate,AudioStreamIndex,SubtitleStreamIndex from UserDatas where key =@Key and userId=@UserId"))
                 using (var statement = connection.PrepareStatement("select key,userid,rating,played,playCount,isFavorite,playbackPositionTicks,lastPlayedDate,AudioStreamIndex,SubtitleStreamIndex from UserDatas where key =@Key and userId=@UserId"))
                 {
                 {
-                    statement.TryBind("@UserId", internalUserId);
+                    statement.TryBind("@UserId", userId);
                     statement.TryBind("@Key", key);
                     statement.TryBind("@Key", key);
 
 
                     foreach (var row in statement.ExecuteQuery())
                     foreach (var row in statement.ExecuteQuery())
@@ -300,7 +299,7 @@ namespace Emby.Server.Implementations.Data
             }
             }
         }
         }
 
 
-        public UserItemData GetUserData(long internalUserId, List<string> keys)
+        public UserItemData GetUserData(long userId, List<string> keys)
         {
         {
             if (keys == null)
             if (keys == null)
             {
             {
@@ -312,19 +311,19 @@ namespace Emby.Server.Implementations.Data
                 return null;
                 return null;
             }
             }
 
 
-            return GetUserData(internalUserId, keys[0]);
+            return GetUserData(userId, keys[0]);
         }
         }
 
 
         /// <summary>
         /// <summary>
         /// Return all user-data associated with the given user.
         /// Return all user-data associated with the given user.
         /// </summary>
         /// </summary>
-        /// <param name="internalUserId">The internal user id.</param>
+        /// <param name="userId">The internal user id.</param>
         /// <returns>The list of user item data.</returns>
         /// <returns>The list of user item data.</returns>
-        public List<UserItemData> GetAllUserData(long internalUserId)
+        public List<UserItemData> GetAllUserData(long userId)
         {
         {
-            if (internalUserId <= 0)
+            if (userId <= 0)
             {
             {
-                throw new ArgumentNullException(nameof(internalUserId));
+                throw new ArgumentNullException(nameof(userId));
             }
             }
 
 
             var list = new List<UserItemData>();
             var list = new List<UserItemData>();
@@ -333,7 +332,7 @@ namespace Emby.Server.Implementations.Data
             {
             {
                 using (var statement = connection.PrepareStatement("select key,userid,rating,played,playCount,isFavorite,playbackPositionTicks,lastPlayedDate,AudioStreamIndex,SubtitleStreamIndex from UserDatas where userId=@UserId"))
                 using (var statement = connection.PrepareStatement("select key,userid,rating,played,playCount,isFavorite,playbackPositionTicks,lastPlayedDate,AudioStreamIndex,SubtitleStreamIndex from UserDatas where userId=@UserId"))
                 {
                 {
-                    statement.TryBind("@UserId", internalUserId);
+                    statement.TryBind("@UserId", userId);
 
 
                     foreach (var row in statement.ExecuteQuery())
                     foreach (var row in statement.ExecuteQuery())
                     {
                     {

+ 7 - 7
Emby.Server.Implementations/Dto/DtoService.cs

@@ -51,8 +51,6 @@ namespace Emby.Server.Implementations.Dto
         private readonly IMediaSourceManager _mediaSourceManager;
         private readonly IMediaSourceManager _mediaSourceManager;
         private readonly Lazy<ILiveTvManager> _livetvManagerFactory;
         private readonly Lazy<ILiveTvManager> _livetvManagerFactory;
 
 
-        private ILiveTvManager LivetvManager => _livetvManagerFactory.Value;
-
         public DtoService(
         public DtoService(
             ILogger<DtoService> logger,
             ILogger<DtoService> logger,
             ILibraryManager libraryManager,
             ILibraryManager libraryManager,
@@ -75,6 +73,8 @@ namespace Emby.Server.Implementations.Dto
             _livetvManagerFactory = livetvManagerFactory;
             _livetvManagerFactory = livetvManagerFactory;
         }
         }
 
 
+        private ILiveTvManager LivetvManager => _livetvManagerFactory.Value;
+
         /// <inheritdoc />
         /// <inheritdoc />
         public IReadOnlyList<BaseItemDto> GetBaseItemDtos(IReadOnlyList<BaseItem> items, DtoOptions options, User user = null, BaseItem owner = null)
         public IReadOnlyList<BaseItemDto> GetBaseItemDtos(IReadOnlyList<BaseItem> items, DtoOptions options, User user = null, BaseItem owner = null)
         {
         {
@@ -507,7 +507,6 @@ namespace Emby.Server.Implementations.Dto
         /// </summary>
         /// </summary>
         /// <param name="dto">The dto.</param>
         /// <param name="dto">The dto.</param>
         /// <param name="item">The item.</param>
         /// <param name="item">The item.</param>
-        /// <returns>Task.</returns>
         private void AttachPeople(BaseItemDto dto, BaseItem item)
         private void AttachPeople(BaseItemDto dto, BaseItem item)
         {
         {
             // Ordering by person type to ensure actors and artists are at the front.
             // Ordering by person type to ensure actors and artists are at the front.
@@ -616,7 +615,6 @@ namespace Emby.Server.Implementations.Dto
         /// </summary>
         /// </summary>
         /// <param name="dto">The dto.</param>
         /// <param name="dto">The dto.</param>
         /// <param name="item">The item.</param>
         /// <param name="item">The item.</param>
-        /// <returns>Task.</returns>
         private void AttachStudios(BaseItemDto dto, BaseItem item)
         private void AttachStudios(BaseItemDto dto, BaseItem item)
         {
         {
             dto.Studios = item.Studios
             dto.Studios = item.Studios
@@ -1313,9 +1311,12 @@ namespace Emby.Server.Implementations.Dto
 
 
             var imageTags = dto.ImageTags;
             var imageTags = dto.ImageTags;
 
 
-            while (((!(imageTags != null && imageTags.ContainsKey(ImageType.Logo)) && logoLimit > 0) || (!(imageTags != null && imageTags.ContainsKey(ImageType.Art)) && artLimit > 0) || (!(imageTags != null && imageTags.ContainsKey(ImageType.Thumb)) && thumbLimit > 0) || parent is Series) &&
-                (parent ??= (isFirst ? GetImageDisplayParent(item, item) ?? owner : parent)) != null)
+            while ((!(imageTags != null && imageTags.ContainsKey(ImageType.Logo)) && logoLimit > 0)
+                || (!(imageTags != null && imageTags.ContainsKey(ImageType.Art)) && artLimit > 0)
+                || (!(imageTags != null && imageTags.ContainsKey(ImageType.Thumb)) && thumbLimit > 0)
+                || parent is Series)
             {
             {
+                parent ??= isFirst ? GetImageDisplayParent(item, item) ?? owner : parent;
                 if (parent == null)
                 if (parent == null)
                 {
                 {
                     break;
                     break;
@@ -1395,7 +1396,6 @@ namespace Emby.Server.Implementations.Dto
         /// </summary>
         /// </summary>
         /// <param name="dto">The dto.</param>
         /// <param name="dto">The dto.</param>
         /// <param name="item">The item.</param>
         /// <param name="item">The item.</param>
-        /// <returns>Task.</returns>
         public void AttachPrimaryImageAspectRatio(IItemDto dto, BaseItem item)
         public void AttachPrimaryImageAspectRatio(IItemDto dto, BaseItem item)
         {
         {
             dto.PrimaryImageAspectRatio = GetPrimaryImageAspectRatio(item);
             dto.PrimaryImageAspectRatio = GetPrimaryImageAspectRatio(item);

+ 3 - 3
Emby.Server.Implementations/IO/ManagedFileSystem.cs

@@ -423,7 +423,7 @@ namespace Emby.Server.Implementations.IO
             }
             }
         }
         }
 
 
-        public virtual void SetAttributes(string path, bool isHidden, bool isReadOnly)
+        public virtual void SetAttributes(string path, bool isHidden, bool readOnly)
         {
         {
             if (!OperatingSystem.IsWindows())
             if (!OperatingSystem.IsWindows())
             {
             {
@@ -437,14 +437,14 @@ namespace Emby.Server.Implementations.IO
                 return;
                 return;
             }
             }
 
 
-            if (info.IsReadOnly == isReadOnly && info.IsHidden == isHidden)
+            if (info.IsReadOnly == readOnly && info.IsHidden == isHidden)
             {
             {
                 return;
                 return;
             }
             }
 
 
             var attributes = File.GetAttributes(path);
             var attributes = File.GetAttributes(path);
 
 
-            if (isReadOnly)
+            if (readOnly)
             {
             {
                 attributes = attributes | FileAttributes.ReadOnly;
                 attributes = attributes | FileAttributes.ReadOnly;
             }
             }

+ 1 - 1
Emby.Server.Implementations/Images/BaseDynamicImageProvider.cs

@@ -51,7 +51,7 @@ namespace Emby.Server.Implementations.Images
 
 
         public int Order => 0;
         public int Order => 0;
 
 
-        protected virtual bool Supports(BaseItem _) => true;
+        protected virtual bool Supports(BaseItem item) => true;
 
 
         public async Task<ItemUpdateType> FetchAsync(T item, MetadataRefreshOptions options, CancellationToken cancellationToken)
         public async Task<ItemUpdateType> FetchAsync(T item, MetadataRefreshOptions options, CancellationToken cancellationToken)
         {
         {

+ 10 - 12
Emby.Server.Implementations/Library/LibraryManager.cs

@@ -1761,22 +1761,20 @@ namespace Emby.Server.Implementations.Library
             return orderedItems ?? items;
             return orderedItems ?? items;
         }
         }
 
 
-        public IEnumerable<BaseItem> Sort(IEnumerable<BaseItem> items, User user, IEnumerable<ValueTuple<string, SortOrder>> orderByList)
+        public IEnumerable<BaseItem> Sort(IEnumerable<BaseItem> items, User user, IEnumerable<ValueTuple<string, SortOrder>> orderBy)
         {
         {
             var isFirst = true;
             var isFirst = true;
 
 
             IOrderedEnumerable<BaseItem> orderedItems = null;
             IOrderedEnumerable<BaseItem> orderedItems = null;
 
 
-            foreach (var orderBy in orderByList)
+            foreach (var (name, sortOrder) in orderBy)
             {
             {
-                var comparer = GetComparer(orderBy.Item1, user);
+                var comparer = GetComparer(name, user);
                 if (comparer == null)
                 if (comparer == null)
                 {
                 {
                     continue;
                     continue;
                 }
                 }
 
 
-                var sortOrder = orderBy.Item2;
-
                 if (isFirst)
                 if (isFirst)
                 {
                 {
                     orderedItems = sortOrder == SortOrder.Descending ? items.OrderByDescending(i => i, comparer) : items.OrderBy(i => i, comparer);
                     orderedItems = sortOrder == SortOrder.Descending ? items.OrderByDescending(i => i, comparer) : items.OrderBy(i => i, comparer);
@@ -3076,9 +3074,9 @@ namespace Emby.Server.Implementations.Library
             });
             });
         }
         }
 
 
-        public void AddMediaPath(string virtualFolderName, MediaPathInfo pathInfo)
+        public void AddMediaPath(string virtualFolderName, MediaPathInfo mediaPath)
         {
         {
-            AddMediaPathInternal(virtualFolderName, pathInfo, true);
+            AddMediaPathInternal(virtualFolderName, mediaPath, true);
         }
         }
 
 
         private void AddMediaPathInternal(string virtualFolderName, MediaPathInfo pathInfo, bool saveLibraryOptions)
         private void AddMediaPathInternal(string virtualFolderName, MediaPathInfo pathInfo, bool saveLibraryOptions)
@@ -3131,11 +3129,11 @@ namespace Emby.Server.Implementations.Library
             }
             }
         }
         }
 
 
-        public void UpdateMediaPath(string virtualFolderName, MediaPathInfo pathInfo)
+        public void UpdateMediaPath(string virtualFolderName, MediaPathInfo mediaPath)
         {
         {
-            if (pathInfo == null)
+            if (mediaPath == null)
             {
             {
-                throw new ArgumentNullException(nameof(pathInfo));
+                throw new ArgumentNullException(nameof(mediaPath));
             }
             }
 
 
             var rootFolderPath = _configurationManager.ApplicationPaths.DefaultUserViewsPath;
             var rootFolderPath = _configurationManager.ApplicationPaths.DefaultUserViewsPath;
@@ -3148,9 +3146,9 @@ namespace Emby.Server.Implementations.Library
             var list = libraryOptions.PathInfos.ToList();
             var list = libraryOptions.PathInfos.ToList();
             foreach (var originalPathInfo in list)
             foreach (var originalPathInfo in list)
             {
             {
-                if (string.Equals(pathInfo.Path, originalPathInfo.Path, StringComparison.Ordinal))
+                if (string.Equals(mediaPath.Path, originalPathInfo.Path, StringComparison.Ordinal))
                 {
                 {
-                    originalPathInfo.NetworkPath = pathInfo.NetworkPath;
+                    originalPathInfo.NetworkPath = mediaPath.NetworkPath;
                     break;
                     break;
                 }
                 }
             }
             }

+ 3 - 2
Emby.Server.Implementations/Library/MusicManager.cs

@@ -36,9 +36,10 @@ namespace Emby.Server.Implementations.Library
             return list.Concat(GetInstantMixFromGenres(item.Genres, user, dtoOptions)).ToList();
             return list.Concat(GetInstantMixFromGenres(item.Genres, user, dtoOptions)).ToList();
         }
         }
 
 
-        public List<BaseItem> GetInstantMixFromArtist(MusicArtist item, User user, DtoOptions dtoOptions)
+        /// <inheritdoc />
+        public List<BaseItem> GetInstantMixFromArtist(MusicArtist artist, User user, DtoOptions dtoOptions)
         {
         {
-            return GetInstantMixFromGenres(item.Genres, user, dtoOptions);
+            return GetInstantMixFromGenres(artist.Genres, user, dtoOptions);
         }
         }
 
 
         public List<BaseItem> GetInstantMixFromAlbum(MusicAlbum item, User user, DtoOptions dtoOptions)
         public List<BaseItem> GetInstantMixFromAlbum(MusicAlbum item, User user, DtoOptions dtoOptions)

+ 2 - 2
Emby.Server.Implementations/Library/Resolvers/BaseVideoResolver.cs

@@ -21,13 +21,13 @@ namespace Emby.Server.Implementations.Library.Resolvers
     public abstract class BaseVideoResolver<T> : MediaBrowser.Controller.Resolvers.ItemResolver<T>
     public abstract class BaseVideoResolver<T> : MediaBrowser.Controller.Resolvers.ItemResolver<T>
         where T : Video, new()
         where T : Video, new()
     {
     {
-        protected readonly ILibraryManager LibraryManager;
-
         protected BaseVideoResolver(ILibraryManager libraryManager)
         protected BaseVideoResolver(ILibraryManager libraryManager)
         {
         {
             LibraryManager = libraryManager;
             LibraryManager = libraryManager;
         }
         }
 
 
+        protected ILibraryManager LibraryManager { get; }
+
         /// <summary>
         /// <summary>
         /// Resolves the specified args.
         /// Resolves the specified args.
         /// </summary>
         /// </summary>

+ 3 - 1
Emby.Server.Implementations/Library/UserDataManager.cs

@@ -177,6 +177,7 @@ namespace Emby.Server.Implementations.Library
             return dto;
             return dto;
         }
         }
 
 
+        /// <inheritdoc />
         public UserItemDataDto GetUserDataDto(BaseItem item, BaseItemDto itemDto, User user, DtoOptions options)
         public UserItemDataDto GetUserDataDto(BaseItem item, BaseItemDto itemDto, User user, DtoOptions options)
         {
         {
             var userData = GetUserData(user, item);
             var userData = GetUserData(user, item);
@@ -191,7 +192,7 @@ namespace Emby.Server.Implementations.Library
         /// </summary>
         /// </summary>
         /// <param name="data">The data.</param>
         /// <param name="data">The data.</param>
         /// <returns>DtoUserItemData.</returns>
         /// <returns>DtoUserItemData.</returns>
-        /// <exception cref="ArgumentNullException"></exception>
+        /// <exception cref="ArgumentNullException"><paramref name="data"/> is <c>null</c>.</exception>
         private UserItemDataDto GetUserItemDataDto(UserItemData data)
         private UserItemDataDto GetUserItemDataDto(UserItemData data)
         {
         {
             if (data == null)
             if (data == null)
@@ -212,6 +213,7 @@ namespace Emby.Server.Implementations.Library
             };
             };
         }
         }
 
 
+        /// <inheritdoc />
         public bool UpdatePlayState(BaseItem item, UserItemData data, long? reportedPositionTicks)
         public bool UpdatePlayState(BaseItem item, UserItemData data, long? reportedPositionTicks)
         {
         {
             var playedToCompletion = false;
             var playedToCompletion = false;

+ 13 - 13
Emby.Server.Implementations/LiveTv/EmbyTV/EmbyTV.cs

@@ -610,11 +610,11 @@ namespace Emby.Server.Implementations.LiveTv.EmbyTV
             throw new NotImplementedException();
             throw new NotImplementedException();
         }
         }
 
 
-        public Task<string> CreateTimer(TimerInfo timer, CancellationToken cancellationToken)
+        public Task<string> CreateTimer(TimerInfo info, CancellationToken cancellationToken)
         {
         {
-            var existingTimer = string.IsNullOrWhiteSpace(timer.ProgramId) ?
+            var existingTimer = string.IsNullOrWhiteSpace(info.ProgramId) ?
                 null :
                 null :
-                _timerProvider.GetTimerByProgramId(timer.ProgramId);
+                _timerProvider.GetTimerByProgramId(info.ProgramId);
 
 
             if (existingTimer != null)
             if (existingTimer != null)
             {
             {
@@ -632,32 +632,32 @@ namespace Emby.Server.Implementations.LiveTv.EmbyTV
                 }
                 }
             }
             }
 
 
-            timer.Id = Guid.NewGuid().ToString("N", CultureInfo.InvariantCulture);
+            info.Id = Guid.NewGuid().ToString("N", CultureInfo.InvariantCulture);
 
 
             LiveTvProgram programInfo = null;
             LiveTvProgram programInfo = null;
 
 
-            if (!string.IsNullOrWhiteSpace(timer.ProgramId))
+            if (!string.IsNullOrWhiteSpace(info.ProgramId))
             {
             {
-                programInfo = GetProgramInfoFromCache(timer);
+                programInfo = GetProgramInfoFromCache(info);
             }
             }
 
 
             if (programInfo == null)
             if (programInfo == null)
             {
             {
-                _logger.LogInformation("Unable to find program with Id {0}. Will search using start date", timer.ProgramId);
-                programInfo = GetProgramInfoFromCache(timer.ChannelId, timer.StartDate);
+                _logger.LogInformation("Unable to find program with Id {0}. Will search using start date", info.ProgramId);
+                programInfo = GetProgramInfoFromCache(info.ChannelId, info.StartDate);
             }
             }
 
 
             if (programInfo != null)
             if (programInfo != null)
             {
             {
-                CopyProgramInfoToTimerInfo(programInfo, timer);
+                CopyProgramInfoToTimerInfo(programInfo, info);
             }
             }
 
 
-            timer.IsManual = true;
-            _timerProvider.Add(timer);
+            info.IsManual = true;
+            _timerProvider.Add(info);
 
 
-            TimerCreated?.Invoke(this, new GenericEventArgs<TimerInfo>(timer));
+            TimerCreated?.Invoke(this, new GenericEventArgs<TimerInfo>(info));
 
 
-            return Task.FromResult(timer.Id);
+            return Task.FromResult(info.Id);
         }
         }
 
 
         public async Task<string> CreateSeriesTimer(SeriesTimerInfo info, CancellationToken cancellationToken)
         public async Task<string> CreateSeriesTimer(SeriesTimerInfo info, CancellationToken cancellationToken)

+ 25 - 30
Emby.Server.Implementations/LiveTv/LiveTvManager.cs

@@ -65,6 +65,8 @@ namespace Emby.Server.Implementations.LiveTv
         private ITunerHost[] _tunerHosts = Array.Empty<ITunerHost>();
         private ITunerHost[] _tunerHosts = Array.Empty<ITunerHost>();
         private IListingsProvider[] _listingProviders = Array.Empty<IListingsProvider>();
         private IListingsProvider[] _listingProviders = Array.Empty<IListingsProvider>();
 
 
+        private bool _disposed = false;
+
         public LiveTvManager(
         public LiveTvManager(
             IServerConfigurationManager config,
             IServerConfigurationManager config,
             ILogger<LiveTvManager> logger,
             ILogger<LiveTvManager> logger,
@@ -520,7 +522,7 @@ namespace Emby.Server.Implementations.LiveTv
             return item;
             return item;
         }
         }
 
 
-        private Tuple<LiveTvProgram, bool, bool> GetProgram(ProgramInfo info, Dictionary<Guid, LiveTvProgram> allExistingPrograms, LiveTvChannel channel, ChannelType channelType, string serviceName, CancellationToken cancellationToken)
+        private (LiveTvProgram item, bool isNew, bool isUpdated) GetProgram(ProgramInfo info, Dictionary<Guid, LiveTvProgram> allExistingPrograms, LiveTvChannel channel)
         {
         {
             var id = _tvDtoService.GetInternalProgramId(info.Id);
             var id = _tvDtoService.GetInternalProgramId(info.Id);
 
 
@@ -559,8 +561,6 @@ namespace Emby.Server.Implementations.LiveTv
 
 
             item.ParentId = channel.Id;
             item.ParentId = channel.Id;
 
 
-            // item.ChannelType = channelType;
-
             item.Audio = info.Audio;
             item.Audio = info.Audio;
             item.ChannelId = channel.Id;
             item.ChannelId = channel.Id;
             item.CommunityRating ??= info.CommunityRating;
             item.CommunityRating ??= info.CommunityRating;
@@ -772,7 +772,7 @@ namespace Emby.Server.Implementations.LiveTv
                 item.OnMetadataChanged();
                 item.OnMetadataChanged();
             }
             }
 
 
-            return new Tuple<LiveTvProgram, bool, bool>(item, isNew, isUpdated);
+            return (item, isNew, isUpdated);
         }
         }
 
 
         public async Task<BaseItemDto> GetProgram(string id, CancellationToken cancellationToken, User user = null)
         public async Task<BaseItemDto> GetProgram(string id, CancellationToken cancellationToken, User user = null)
@@ -1187,14 +1187,14 @@ namespace Emby.Server.Implementations.LiveTv
 
 
                     foreach (var program in channelPrograms)
                     foreach (var program in channelPrograms)
                     {
                     {
-                        var programTuple = GetProgram(program, existingPrograms, currentChannel, currentChannel.ChannelType, service.Name, cancellationToken);
-                        var programItem = programTuple.Item1;
+                        var programTuple = GetProgram(program, existingPrograms, currentChannel);
+                        var programItem = programTuple.item;
 
 
-                        if (programTuple.Item2)
+                        if (programTuple.isNew)
                         {
                         {
                             newPrograms.Add(programItem);
                             newPrograms.Add(programItem);
                         }
                         }
-                        else if (programTuple.Item3)
+                        else if (programTuple.isUpdated)
                         {
                         {
                             updatedPrograms.Add(programItem);
                             updatedPrograms.Add(programItem);
                         }
                         }
@@ -1385,10 +1385,10 @@ namespace Emby.Server.Implementations.LiveTv
                 // var items = allActivePaths.Select(i => _libraryManager.FindByPath(i, false)).Where(i => i != null).ToArray();
                 // var items = allActivePaths.Select(i => _libraryManager.FindByPath(i, false)).Where(i => i != null).ToArray();
 
 
                 // return new QueryResult<BaseItem>
                 // return new QueryResult<BaseItem>
-                //{
+                // {
                 //    Items = items,
                 //    Items = items,
                 //    TotalRecordCount = items.Length
                 //    TotalRecordCount = items.Length
-                //};
+                // };
 
 
                 dtoOptions.Fields = dtoOptions.Fields.Concat(new[] { ItemFields.Tags }).Distinct().ToArray();
                 dtoOptions.Fields = dtoOptions.Fields.Concat(new[] { ItemFields.Tags }).Distinct().ToArray();
             }
             }
@@ -1425,16 +1425,15 @@ namespace Emby.Server.Implementations.LiveTv
             return result;
             return result;
         }
         }
 
 
-        public Task AddInfoToProgramDto(IReadOnlyCollection<(BaseItem, BaseItemDto)> tuples, IReadOnlyList<ItemFields> fields, User user = null)
+        public Task AddInfoToProgramDto(IReadOnlyCollection<(BaseItem, BaseItemDto)> programs, IReadOnlyList<ItemFields> fields, User user = null)
         {
         {
             var programTuples = new List<Tuple<BaseItemDto, string, string>>();
             var programTuples = new List<Tuple<BaseItemDto, string, string>>();
             var hasChannelImage = fields.Contains(ItemFields.ChannelImage);
             var hasChannelImage = fields.Contains(ItemFields.ChannelImage);
             var hasChannelInfo = fields.Contains(ItemFields.ChannelInfo);
             var hasChannelInfo = fields.Contains(ItemFields.ChannelInfo);
 
 
-            foreach (var tuple in tuples)
+            foreach (var (item, dto) in programs)
             {
             {
-                var program = (LiveTvProgram)tuple.Item1;
-                var dto = tuple.Item2;
+                var program = (LiveTvProgram)item;
 
 
                 dto.StartDate = program.StartDate;
                 dto.StartDate = program.StartDate;
                 dto.EpisodeTitle = program.EpisodeTitle;
                 dto.EpisodeTitle = program.EpisodeTitle;
@@ -1871,11 +1870,11 @@ namespace Emby.Server.Implementations.LiveTv
             return _libraryManager.GetItemById(internalChannelId);
             return _libraryManager.GetItemById(internalChannelId);
         }
         }
 
 
-        public void AddChannelInfo(IReadOnlyCollection<(BaseItemDto, LiveTvChannel)> tuples, DtoOptions options, User user)
+        public void AddChannelInfo(IReadOnlyCollection<(BaseItemDto, LiveTvChannel)> items, DtoOptions options, User user)
         {
         {
             var now = DateTime.UtcNow;
             var now = DateTime.UtcNow;
 
 
-            var channelIds = tuples.Select(i => i.Item2.Id).Distinct().ToArray();
+            var channelIds = items.Select(i => i.Item2.Id).Distinct().ToArray();
 
 
             var programs = options.AddCurrentProgram ? _libraryManager.GetItemList(new InternalItemsQuery(user)
             var programs = options.AddCurrentProgram ? _libraryManager.GetItemList(new InternalItemsQuery(user)
             {
             {
@@ -1896,7 +1895,7 @@ namespace Emby.Server.Implementations.LiveTv
 
 
             var addCurrentProgram = options.AddCurrentProgram;
             var addCurrentProgram = options.AddCurrentProgram;
 
 
-            foreach (var tuple in tuples)
+            foreach (var tuple in items)
             {
             {
                 var dto = tuple.Item1;
                 var dto = tuple.Item1;
                 var channel = tuple.Item2;
                 var channel = tuple.Item2;
@@ -2118,17 +2117,13 @@ namespace Emby.Server.Implementations.LiveTv
             };
             };
         }
         }
 
 
-        /// <summary>
-        /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
-        /// </summary>
+        /// <inheritdoc />
         public void Dispose()
         public void Dispose()
         {
         {
             Dispose(true);
             Dispose(true);
             GC.SuppressFinalize(this);
             GC.SuppressFinalize(this);
         }
         }
 
 
-        private bool _disposed = false;
-
         /// <summary>
         /// <summary>
         /// Releases unmanaged and - optionally - managed resources.
         /// Releases unmanaged and - optionally - managed resources.
         /// </summary>
         /// </summary>
@@ -2324,20 +2319,20 @@ namespace Emby.Server.Implementations.LiveTv
             _taskManager.CancelIfRunningAndQueue<RefreshGuideScheduledTask>();
             _taskManager.CancelIfRunningAndQueue<RefreshGuideScheduledTask>();
         }
         }
 
 
-        public async Task<TunerChannelMapping> SetChannelMapping(string providerId, string tunerChannelId, string providerChannelId)
+        public async Task<TunerChannelMapping> SetChannelMapping(string providerId, string tunerChannelNumber, string providerChannelNumber)
         {
         {
             var config = GetConfiguration();
             var config = GetConfiguration();
 
 
             var listingsProviderInfo = config.ListingProviders.First(i => string.Equals(providerId, i.Id, StringComparison.OrdinalIgnoreCase));
             var listingsProviderInfo = config.ListingProviders.First(i => string.Equals(providerId, i.Id, StringComparison.OrdinalIgnoreCase));
-            listingsProviderInfo.ChannelMappings = listingsProviderInfo.ChannelMappings.Where(i => !string.Equals(i.Name, tunerChannelId, StringComparison.OrdinalIgnoreCase)).ToArray();
+            listingsProviderInfo.ChannelMappings = listingsProviderInfo.ChannelMappings.Where(i => !string.Equals(i.Name, tunerChannelNumber, StringComparison.OrdinalIgnoreCase)).ToArray();
 
 
-            if (!string.Equals(tunerChannelId, providerChannelId, StringComparison.OrdinalIgnoreCase))
+            if (!string.Equals(tunerChannelNumber, providerChannelNumber, StringComparison.OrdinalIgnoreCase))
             {
             {
                 var list = listingsProviderInfo.ChannelMappings.ToList();
                 var list = listingsProviderInfo.ChannelMappings.ToList();
                 list.Add(new NameValuePair
                 list.Add(new NameValuePair
                 {
                 {
-                    Name = tunerChannelId,
-                    Value = providerChannelId
+                    Name = tunerChannelNumber,
+                    Value = providerChannelNumber
                 });
                 });
                 listingsProviderInfo.ChannelMappings = list.ToArray();
                 listingsProviderInfo.ChannelMappings = list.ToArray();
             }
             }
@@ -2357,10 +2352,10 @@ namespace Emby.Server.Implementations.LiveTv
 
 
             _taskManager.CancelIfRunningAndQueue<RefreshGuideScheduledTask>();
             _taskManager.CancelIfRunningAndQueue<RefreshGuideScheduledTask>();
 
 
-            return tunerChannelMappings.First(i => string.Equals(i.Id, tunerChannelId, StringComparison.OrdinalIgnoreCase));
+            return tunerChannelMappings.First(i => string.Equals(i.Id, tunerChannelNumber, StringComparison.OrdinalIgnoreCase));
         }
         }
 
 
-        public TunerChannelMapping GetTunerChannelMapping(ChannelInfo tunerChannel, NameValuePair[] mappings, List<ChannelInfo> epgChannels)
+        public TunerChannelMapping GetTunerChannelMapping(ChannelInfo tunerChannel, NameValuePair[] mappings, List<ChannelInfo> providerChannels)
         {
         {
             var result = new TunerChannelMapping
             var result = new TunerChannelMapping
             {
             {
@@ -2373,7 +2368,7 @@ namespace Emby.Server.Implementations.LiveTv
                 result.Name = tunerChannel.Number + " " + result.Name;
                 result.Name = tunerChannel.Number + " " + result.Name;
             }
             }
 
 
-            var providerChannel = EmbyTV.EmbyTV.Current.GetEpgChannelFromTunerChannel(mappings, tunerChannel, epgChannels);
+            var providerChannel = EmbyTV.EmbyTV.Current.GetEpgChannelFromTunerChannel(mappings, tunerChannel, providerChannels);
 
 
             if (providerChannel != null)
             if (providerChannel != null)
             {
             {

+ 1 - 1
Emby.Server.Implementations/LiveTv/TunerHosts/BaseTunerHost.cs

@@ -158,7 +158,7 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts
             return new List<MediaSourceInfo>();
             return new List<MediaSourceInfo>();
         }
         }
 
 
-        protected abstract Task<ILiveStream> GetChannelStream(TunerHostInfo tuner, ChannelInfo channel, string streamId, List<ILiveStream> currentLiveStreams, CancellationToken cancellationToken);
+        protected abstract Task<ILiveStream> GetChannelStream(TunerHostInfo tunerHost, ChannelInfo channel, string streamId, List<ILiveStream> currentLiveStreams, CancellationToken cancellationToken);
 
 
         public async Task<ILiveStream> GetChannelStream(string channelId, string streamId, List<ILiveStream> currentLiveStreams, CancellationToken cancellationToken)
         public async Task<ILiveStream> GetChannelStream(string channelId, string streamId, List<ILiveStream> currentLiveStreams, CancellationToken cancellationToken)
         {
         {

+ 30 - 34
Emby.Server.Implementations/LiveTv/TunerHosts/HdHomerun/HdHomerunHost.cs

@@ -95,17 +95,17 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun
             public bool IsLegacyTuner { get; set; }
             public bool IsLegacyTuner { get; set; }
         }
         }
 
 
-        protected override async Task<List<ChannelInfo>> GetChannelsInternal(TunerHostInfo info, CancellationToken cancellationToken)
+        protected override async Task<List<ChannelInfo>> GetChannelsInternal(TunerHostInfo tuner, CancellationToken cancellationToken)
         {
         {
-            var lineup = await GetLineup(info, cancellationToken).ConfigureAwait(false);
+            var lineup = await GetLineup(tuner, cancellationToken).ConfigureAwait(false);
 
 
             return lineup.Select(i => new HdHomerunChannelInfo
             return lineup.Select(i => new HdHomerunChannelInfo
             {
             {
                 Name = i.GuideName,
                 Name = i.GuideName,
                 Number = i.GuideNumber,
                 Number = i.GuideNumber,
-                Id = GetChannelId(info, i),
+                Id = GetChannelId(tuner, i),
                 IsFavorite = i.Favorite,
                 IsFavorite = i.Favorite,
-                TunerHostId = info.Id,
+                TunerHostId = tuner.Id,
                 IsHD = i.HD,
                 IsHD = i.HD,
                 AudioCodec = i.AudioCodec,
                 AudioCodec = i.AudioCodec,
                 VideoCodec = i.VideoCodec,
                 VideoCodec = i.VideoCodec,
@@ -496,57 +496,53 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun
             return mediaSource;
             return mediaSource;
         }
         }
 
 
-        protected override async Task<List<MediaSourceInfo>> GetChannelStreamMediaSources(TunerHostInfo info, ChannelInfo channelInfo, CancellationToken cancellationToken)
+        protected override async Task<List<MediaSourceInfo>> GetChannelStreamMediaSources(TunerHostInfo tuner, ChannelInfo channel, CancellationToken cancellationToken)
         {
         {
             var list = new List<MediaSourceInfo>();
             var list = new List<MediaSourceInfo>();
 
 
-            var channelId = channelInfo.Id;
+            var channelId = channel.Id;
             var hdhrId = GetHdHrIdFromChannelId(channelId);
             var hdhrId = GetHdHrIdFromChannelId(channelId);
 
 
-            var hdHomerunChannelInfo = channelInfo as HdHomerunChannelInfo;
-
-            var isLegacyTuner = hdHomerunChannelInfo != null && hdHomerunChannelInfo.IsLegacyTuner;
-
-            if (isLegacyTuner)
+            if (channel is HdHomerunChannelInfo hdHomerunChannelInfo && hdHomerunChannelInfo.IsLegacyTuner)
             {
             {
-                list.Add(GetMediaSource(info, hdhrId, channelInfo, "native"));
+                list.Add(GetMediaSource(tuner, hdhrId, channel, "native"));
             }
             }
             else
             else
             {
             {
-                var modelInfo = await GetModelInfo(info, false, cancellationToken).ConfigureAwait(false);
+                var modelInfo = await GetModelInfo(tuner, false, cancellationToken).ConfigureAwait(false);
 
 
                 if (modelInfo != null && modelInfo.SupportsTranscoding)
                 if (modelInfo != null && modelInfo.SupportsTranscoding)
                 {
                 {
-                    if (info.AllowHWTranscoding)
+                    if (tuner.AllowHWTranscoding)
                     {
                     {
-                        list.Add(GetMediaSource(info, hdhrId, channelInfo, "heavy"));
+                        list.Add(GetMediaSource(tuner, hdhrId, channel, "heavy"));
 
 
-                        list.Add(GetMediaSource(info, hdhrId, channelInfo, "internet540"));
-                        list.Add(GetMediaSource(info, hdhrId, channelInfo, "internet480"));
-                        list.Add(GetMediaSource(info, hdhrId, channelInfo, "internet360"));
-                        list.Add(GetMediaSource(info, hdhrId, channelInfo, "internet240"));
-                        list.Add(GetMediaSource(info, hdhrId, channelInfo, "mobile"));
+                        list.Add(GetMediaSource(tuner, hdhrId, channel, "internet540"));
+                        list.Add(GetMediaSource(tuner, hdhrId, channel, "internet480"));
+                        list.Add(GetMediaSource(tuner, hdhrId, channel, "internet360"));
+                        list.Add(GetMediaSource(tuner, hdhrId, channel, "internet240"));
+                        list.Add(GetMediaSource(tuner, hdhrId, channel, "mobile"));
                     }
                     }
 
 
-                    list.Add(GetMediaSource(info, hdhrId, channelInfo, "native"));
+                    list.Add(GetMediaSource(tuner, hdhrId, channel, "native"));
                 }
                 }
 
 
                 if (list.Count == 0)
                 if (list.Count == 0)
                 {
                 {
-                    list.Add(GetMediaSource(info, hdhrId, channelInfo, "native"));
+                    list.Add(GetMediaSource(tuner, hdhrId, channel, "native"));
                 }
                 }
             }
             }
 
 
             return list;
             return list;
         }
         }
 
 
-        protected override async Task<ILiveStream> GetChannelStream(TunerHostInfo info, ChannelInfo channelInfo, string streamId, List<ILiveStream> currentLiveStreams, CancellationToken cancellationToken)
+        protected override async Task<ILiveStream> GetChannelStream(TunerHostInfo tunerHost, ChannelInfo channel, string streamId, List<ILiveStream> currentLiveStreams, CancellationToken cancellationToken)
         {
         {
-            var tunerCount = info.TunerCount;
+            var tunerCount = tunerHost.TunerCount;
 
 
             if (tunerCount > 0)
             if (tunerCount > 0)
             {
             {
-                var tunerHostId = info.Id;
+                var tunerHostId = tunerHost.Id;
                 var liveStreams = currentLiveStreams.Where(i => string.Equals(i.TunerHostId, tunerHostId, StringComparison.OrdinalIgnoreCase));
                 var liveStreams = currentLiveStreams.Where(i => string.Equals(i.TunerHostId, tunerHostId, StringComparison.OrdinalIgnoreCase));
 
 
                 if (liveStreams.Count() >= tunerCount)
                 if (liveStreams.Count() >= tunerCount)
@@ -557,26 +553,26 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun
 
 
             var profile = streamId.Split('_')[0];
             var profile = streamId.Split('_')[0];
 
 
-            Logger.LogInformation("GetChannelStream: channel id: {0}. stream id: {1} profile: {2}", channelInfo.Id, streamId, profile);
+            Logger.LogInformation("GetChannelStream: channel id: {0}. stream id: {1} profile: {2}", channel.Id, streamId, profile);
 
 
-            var hdhrId = GetHdHrIdFromChannelId(channelInfo.Id);
+            var hdhrId = GetHdHrIdFromChannelId(channel.Id);
 
 
-            var hdhomerunChannel = channelInfo as HdHomerunChannelInfo;
+            var hdhomerunChannel = channel as HdHomerunChannelInfo;
 
 
-            var modelInfo = await GetModelInfo(info, false, cancellationToken).ConfigureAwait(false);
+            var modelInfo = await GetModelInfo(tunerHost, false, cancellationToken).ConfigureAwait(false);
 
 
             if (!modelInfo.SupportsTranscoding)
             if (!modelInfo.SupportsTranscoding)
             {
             {
                 profile = "native";
                 profile = "native";
             }
             }
 
 
-            var mediaSource = GetMediaSource(info, hdhrId, channelInfo, profile);
+            var mediaSource = GetMediaSource(tunerHost, hdhrId, channel, profile);
 
 
             if (hdhomerunChannel != null && hdhomerunChannel.IsLegacyTuner)
             if (hdhomerunChannel != null && hdhomerunChannel.IsLegacyTuner)
             {
             {
                 return new HdHomerunUdpStream(
                 return new HdHomerunUdpStream(
                     mediaSource,
                     mediaSource,
-                    info,
+                    tunerHost,
                     streamId,
                     streamId,
                     new LegacyHdHomerunChannelCommands(hdhomerunChannel.Path),
                     new LegacyHdHomerunChannelCommands(hdhomerunChannel.Path),
                     modelInfo.TunerCount,
                     modelInfo.TunerCount,
@@ -592,7 +588,7 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun
             {
             {
                 mediaSource.Protocol = MediaProtocol.Http;
                 mediaSource.Protocol = MediaProtocol.Http;
 
 
-                var httpUrl = channelInfo.Path;
+                var httpUrl = channel.Path;
 
 
                 // If raw was used, the tuner doesn't support params
                 // If raw was used, the tuner doesn't support params
                 if (!string.IsNullOrWhiteSpace(profile) && !string.Equals(profile, "native", StringComparison.OrdinalIgnoreCase))
                 if (!string.IsNullOrWhiteSpace(profile) && !string.Equals(profile, "native", StringComparison.OrdinalIgnoreCase))
@@ -604,7 +600,7 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun
 
 
                 return new SharedHttpStream(
                 return new SharedHttpStream(
                     mediaSource,
                     mediaSource,
-                    info,
+                    tunerHost,
                     streamId,
                     streamId,
                     FileSystem,
                     FileSystem,
                     _httpClientFactory,
                     _httpClientFactory,
@@ -616,7 +612,7 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts.HdHomerun
 
 
             return new HdHomerunUdpStream(
             return new HdHomerunUdpStream(
                 mediaSource,
                 mediaSource,
-                info,
+                tunerHost,
                 streamId,
                 streamId,
                 new HdHomerunChannelCommands(hdhomerunChannel.Number, profile),
                 new HdHomerunChannelCommands(hdhomerunChannel.Number, profile),
                 modelInfo.TunerCount,
                 modelInfo.TunerCount,

+ 11 - 11
Emby.Server.Implementations/LiveTv/TunerHosts/M3UTunerHost.cs

@@ -71,12 +71,12 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts
             return ChannelIdPrefix + info.Url.GetMD5().ToString("N", CultureInfo.InvariantCulture);
             return ChannelIdPrefix + info.Url.GetMD5().ToString("N", CultureInfo.InvariantCulture);
         }
         }
 
 
-        protected override async Task<List<ChannelInfo>> GetChannelsInternal(TunerHostInfo info, CancellationToken cancellationToken)
+        protected override async Task<List<ChannelInfo>> GetChannelsInternal(TunerHostInfo tuner, CancellationToken cancellationToken)
         {
         {
-            var channelIdPrefix = GetFullChannelIdPrefix(info);
+            var channelIdPrefix = GetFullChannelIdPrefix(tuner);
 
 
             return await new M3uParser(Logger, _httpClientFactory)
             return await new M3uParser(Logger, _httpClientFactory)
-                .Parse(info, channelIdPrefix, cancellationToken)
+                .Parse(tuner, channelIdPrefix, cancellationToken)
                 .ConfigureAwait(false);
                 .ConfigureAwait(false);
         }
         }
 
 
@@ -96,13 +96,13 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts
             return Task.FromResult(list);
             return Task.FromResult(list);
         }
         }
 
 
-        protected override async Task<ILiveStream> GetChannelStream(TunerHostInfo info, ChannelInfo channelInfo, string streamId, List<ILiveStream> currentLiveStreams, CancellationToken cancellationToken)
+        protected override async Task<ILiveStream> GetChannelStream(TunerHostInfo tunerHost, ChannelInfo channel, string streamId, List<ILiveStream> currentLiveStreams, CancellationToken cancellationToken)
         {
         {
-            var tunerCount = info.TunerCount;
+            var tunerCount = tunerHost.TunerCount;
 
 
             if (tunerCount > 0)
             if (tunerCount > 0)
             {
             {
-                var tunerHostId = info.Id;
+                var tunerHostId = tunerHost.Id;
                 var liveStreams = currentLiveStreams.Where(i => string.Equals(i.TunerHostId, tunerHostId, StringComparison.OrdinalIgnoreCase));
                 var liveStreams = currentLiveStreams.Where(i => string.Equals(i.TunerHostId, tunerHostId, StringComparison.OrdinalIgnoreCase));
 
 
                 if (liveStreams.Count() >= tunerCount)
                 if (liveStreams.Count() >= tunerCount)
@@ -111,7 +111,7 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts
                 }
                 }
             }
             }
 
 
-            var sources = await GetChannelStreamMediaSources(info, channelInfo, cancellationToken).ConfigureAwait(false);
+            var sources = await GetChannelStreamMediaSources(tunerHost, channel, cancellationToken).ConfigureAwait(false);
 
 
             var mediaSource = sources[0];
             var mediaSource = sources[0];
 
 
@@ -121,11 +121,11 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts
 
 
                 if (!_disallowedSharedStreamExtensions.Contains(extension, StringComparer.OrdinalIgnoreCase))
                 if (!_disallowedSharedStreamExtensions.Contains(extension, StringComparer.OrdinalIgnoreCase))
                 {
                 {
-                    return new SharedHttpStream(mediaSource, info, streamId, FileSystem, _httpClientFactory, Logger, Config, _appHost, _streamHelper);
+                    return new SharedHttpStream(mediaSource, tunerHost, streamId, FileSystem, _httpClientFactory, Logger, Config, _appHost, _streamHelper);
                 }
                 }
             }
             }
 
 
-            return new LiveStream(mediaSource, info, FileSystem, Logger, Config, _streamHelper);
+            return new LiveStream(mediaSource, tunerHost, FileSystem, Logger, Config, _streamHelper);
         }
         }
 
 
         public async Task Validate(TunerHostInfo info)
         public async Task Validate(TunerHostInfo info)
@@ -135,9 +135,9 @@ namespace Emby.Server.Implementations.LiveTv.TunerHosts
             }
             }
         }
         }
 
 
-        protected override Task<List<MediaSourceInfo>> GetChannelStreamMediaSources(TunerHostInfo info, ChannelInfo channelInfo, CancellationToken cancellationToken)
+        protected override Task<List<MediaSourceInfo>> GetChannelStreamMediaSources(TunerHostInfo tuner, ChannelInfo channel, CancellationToken cancellationToken)
         {
         {
-            return Task.FromResult(new List<MediaSourceInfo> { CreateMediaSourceInfo(info, channelInfo) });
+            return Task.FromResult(new List<MediaSourceInfo> { CreateMediaSourceInfo(tuner, channel) });
         }
         }
 
 
         protected virtual MediaSourceInfo CreateMediaSourceInfo(TunerHostInfo info, ChannelInfo channel)
         protected virtual MediaSourceInfo CreateMediaSourceInfo(TunerHostInfo info, ChannelInfo channel)

+ 6 - 14
Emby.Server.Implementations/Net/SocketFactory.cs

@@ -11,6 +11,7 @@ namespace Emby.Server.Implementations.Net
 {
 {
     public class SocketFactory : ISocketFactory
     public class SocketFactory : ISocketFactory
     {
     {
+        /// <inheritdoc />
         public ISocket CreateUdpBroadcastSocket(int localPort)
         public ISocket CreateUdpBroadcastSocket(int localPort)
         {
         {
             if (localPort < 0)
             if (localPort < 0)
@@ -35,11 +36,8 @@ namespace Emby.Server.Implementations.Net
             }
             }
         }
         }
 
 
-        /// <summary>
-        /// Creates a new UDP acceptSocket that is a member of the SSDP multicast local admin group and binds it to the specified local port.
-        /// </summary>
-        /// <returns>An implementation of the <see cref="ISocket"/> interface used by RSSDP components to perform acceptSocket operations.</returns>
-        public ISocket CreateSsdpUdpSocket(IPAddress localIpAddress, int localPort)
+        /// <inheritdoc />
+        public ISocket CreateSsdpUdpSocket(IPAddress localIp, int localPort)
         {
         {
             if (localPort < 0)
             if (localPort < 0)
             {
             {
@@ -53,8 +51,8 @@ namespace Emby.Server.Implementations.Net
                 retVal.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
                 retVal.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
                 retVal.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.MulticastTimeToLive, 4);
                 retVal.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.MulticastTimeToLive, 4);
 
 
-                retVal.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.AddMembership, new MulticastOption(IPAddress.Parse("239.255.255.250"), localIpAddress));
-                return new UdpSocket(retVal, localPort, localIpAddress);
+                retVal.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.AddMembership, new MulticastOption(IPAddress.Parse("239.255.255.250"), localIp));
+                return new UdpSocket(retVal, localPort, localIp);
             }
             }
             catch
             catch
             {
             {
@@ -64,13 +62,7 @@ namespace Emby.Server.Implementations.Net
             }
             }
         }
         }
 
 
-        /// <summary>
-        /// Creates a new UDP acceptSocket that is a member of the specified multicast IP address, and binds it to the specified local port.
-        /// </summary>
-        /// <param name="ipAddress">The multicast IP address to make the acceptSocket a member of.</param>
-        /// <param name="multicastTimeToLive">The multicast time to live value for the acceptSocket.</param>
-        /// <param name="localPort">The number of the local port to bind to.</param>
-        /// <returns></returns>
+        /// <inheritdoc />
         public ISocket CreateUdpMulticastSocket(string ipAddress, int multicastTimeToLive, int localPort)
         public ISocket CreateUdpMulticastSocket(string ipAddress, int multicastTimeToLive, int localPort)
         {
         {
             if (ipAddress == null)
             if (ipAddress == null)

+ 2 - 2
Emby.Server.Implementations/Net/UdpSocket.cs

@@ -191,7 +191,7 @@ namespace Emby.Server.Implementations.Net
             return taskCompletion.Task;
             return taskCompletion.Task;
         }
         }
 
 
-        public Task SendToAsync(byte[] buffer, int offset, int size, IPEndPoint endPoint, CancellationToken cancellationToken)
+        public Task SendToAsync(byte[] buffer, int offset, int bytes, IPEndPoint endPoint, CancellationToken cancellationToken)
         {
         {
             ThrowIfDisposed();
             ThrowIfDisposed();
 
 
@@ -214,7 +214,7 @@ namespace Emby.Server.Implementations.Net
                 }
                 }
             };
             };
 
 
-            var result = BeginSendTo(buffer, offset, size, endPoint, new AsyncCallback(callback), null);
+            var result = BeginSendTo(buffer, offset, bytes, endPoint, new AsyncCallback(callback), null);
 
 
             if (result.CompletedSynchronously)
             if (result.CompletedSynchronously)
             {
             {

+ 4 - 0
Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteCacheFileTask.cs

@@ -29,6 +29,10 @@ namespace Emby.Server.Implementations.ScheduledTasks.Tasks
         /// <summary>
         /// <summary>
         /// Initializes a new instance of the <see cref="DeleteCacheFileTask" /> class.
         /// Initializes a new instance of the <see cref="DeleteCacheFileTask" /> class.
         /// </summary>
         /// </summary>
+        /// <param name="appPaths">Instance of the <see cref="IApplicationPaths"/> interface.</param>
+        /// <param name="logger">Instance of the <see cref="ILogger"/> interface.</param>
+        /// <param name="fileSystem">Instance of the <see cref="IFileSystem"/> interface.</param>
+        /// <param name="localization">Instance of the <see cref="ILocalizationManager"/> interface.</param>
         public DeleteCacheFileTask(
         public DeleteCacheFileTask(
             IApplicationPaths appPaths,
             IApplicationPaths appPaths,
             ILogger<DeleteCacheFileTask> logger,
             ILogger<DeleteCacheFileTask> logger,

+ 9 - 9
Emby.Server.Implementations/Session/SessionManager.cs

@@ -235,12 +235,12 @@ namespace Emby.Server.Implementations.Session
         }
         }
 
 
         /// <inheritdoc />
         /// <inheritdoc />
-        public void UpdateDeviceName(string sessionId, string deviceName)
+        public void UpdateDeviceName(string sessionId, string reportedDeviceName)
         {
         {
             var session = GetSession(sessionId);
             var session = GetSession(sessionId);
             if (session != null)
             if (session != null)
             {
             {
-                session.DeviceName = deviceName;
+                session.DeviceName = reportedDeviceName;
             }
             }
         }
         }
 
 
@@ -316,14 +316,14 @@ namespace Emby.Server.Implementations.Session
         }
         }
 
 
         /// <inheritdoc />
         /// <inheritdoc />
-        public void OnSessionControllerConnected(SessionInfo info)
+        public void OnSessionControllerConnected(SessionInfo session)
         {
         {
             EventHelper.QueueEventIfNotNull(
             EventHelper.QueueEventIfNotNull(
                 SessionControllerConnected,
                 SessionControllerConnected,
                 this,
                 this,
                 new SessionEventArgs
                 new SessionEventArgs
                 {
                 {
-                    SessionInfo = info
+                    SessionInfo = session
                 },
                 },
                 _logger);
                 _logger);
         }
         }
@@ -1581,16 +1581,16 @@ namespace Emby.Server.Implementations.Session
         }
         }
 
 
         /// <inheritdoc />
         /// <inheritdoc />
-        public async Task Logout(Device existing)
+        public async Task Logout(Device device)
         {
         {
             CheckDisposed();
             CheckDisposed();
 
 
-            _logger.LogInformation("Logging out access token {0}", existing.AccessToken);
+            _logger.LogInformation("Logging out access token {0}", device.AccessToken);
 
 
-            await _deviceManager.DeleteDevice(existing).ConfigureAwait(false);
+            await _deviceManager.DeleteDevice(device).ConfigureAwait(false);
 
 
             var sessions = Sessions
             var sessions = Sessions
-                .Where(i => string.Equals(i.DeviceId, existing.DeviceId, StringComparison.OrdinalIgnoreCase))
+                .Where(i => string.Equals(i.DeviceId, device.DeviceId, StringComparison.OrdinalIgnoreCase))
                 .ToList();
                 .ToList();
 
 
             foreach (var session in sessions)
             foreach (var session in sessions)
@@ -1601,7 +1601,7 @@ namespace Emby.Server.Implementations.Session
                 }
                 }
                 catch (Exception ex)
                 catch (Exception ex)
                 {
                 {
-                    _logger.LogError("Error reporting session ended", ex);
+                    _logger.LogError(ex, "Error reporting session ended");
                 }
                 }
             }
             }
         }
         }

+ 11 - 11
Emby.Server.Implementations/TV/TVSeriesManager.cs

@@ -33,9 +33,9 @@ namespace Emby.Server.Implementations.TV
             _configurationManager = configurationManager;
             _configurationManager = configurationManager;
         }
         }
 
 
-        public QueryResult<BaseItem> GetNextUp(NextUpQuery request, DtoOptions dtoOptions)
+        public QueryResult<BaseItem> GetNextUp(NextUpQuery query, DtoOptions options)
         {
         {
-            var user = _userManager.GetUserById(request.UserId);
+            var user = _userManager.GetUserById(query.UserId);
 
 
             if (user == null)
             if (user == null)
             {
             {
@@ -43,9 +43,9 @@ namespace Emby.Server.Implementations.TV
             }
             }
 
 
             string presentationUniqueKey = null;
             string presentationUniqueKey = null;
-            if (!string.IsNullOrEmpty(request.SeriesId))
+            if (!string.IsNullOrEmpty(query.SeriesId))
             {
             {
-                if (_libraryManager.GetItemById(request.SeriesId) is Series series)
+                if (_libraryManager.GetItemById(query.SeriesId) is Series series)
                 {
                 {
                     presentationUniqueKey = GetUniqueSeriesKey(series);
                     presentationUniqueKey = GetUniqueSeriesKey(series);
                 }
                 }
@@ -53,14 +53,14 @@ namespace Emby.Server.Implementations.TV
 
 
             if (!string.IsNullOrEmpty(presentationUniqueKey))
             if (!string.IsNullOrEmpty(presentationUniqueKey))
             {
             {
-                return GetResult(GetNextUpEpisodes(request, user, new[] { presentationUniqueKey }, dtoOptions), request);
+                return GetResult(GetNextUpEpisodes(query, user, new[] { presentationUniqueKey }, options), query);
             }
             }
 
 
             BaseItem[] parents;
             BaseItem[] parents;
 
 
-            if (request.ParentId.HasValue)
+            if (query.ParentId.HasValue)
             {
             {
-                var parent = _libraryManager.GetItemById(request.ParentId.Value);
+                var parent = _libraryManager.GetItemById(query.ParentId.Value);
 
 
                 if (parent != null)
                 if (parent != null)
                 {
                 {
@@ -79,10 +79,10 @@ namespace Emby.Server.Implementations.TV
                    .ToArray();
                    .ToArray();
             }
             }
 
 
-            return GetNextUp(request, parents, dtoOptions);
+            return GetNextUp(query, parents, options);
         }
         }
 
 
-        public QueryResult<BaseItem> GetNextUp(NextUpQuery request, BaseItem[] parentsFolders, DtoOptions dtoOptions)
+        public QueryResult<BaseItem> GetNextUp(NextUpQuery request, BaseItem[] parentsFolders, DtoOptions options)
         {
         {
             var user = _userManager.GetUserById(request.UserId);
             var user = _userManager.GetUserById(request.UserId);
 
 
@@ -104,7 +104,7 @@ namespace Emby.Server.Implementations.TV
 
 
             if (!string.IsNullOrEmpty(presentationUniqueKey))
             if (!string.IsNullOrEmpty(presentationUniqueKey))
             {
             {
-                return GetResult(GetNextUpEpisodes(request, user, new[] { presentationUniqueKey }, dtoOptions), request);
+                return GetResult(GetNextUpEpisodes(request, user, new[] { presentationUniqueKey }, options), request);
             }
             }
 
 
             if (limit.HasValue)
             if (limit.HasValue)
@@ -128,7 +128,7 @@ namespace Emby.Server.Implementations.TV
                 .Select(GetUniqueSeriesKey);
                 .Select(GetUniqueSeriesKey);
 
 
             // Avoid implicitly captured closure
             // Avoid implicitly captured closure
-            var episodes = GetNextUpEpisodes(request, user, items, dtoOptions);
+            var episodes = GetNextUpEpisodes(request, user, items, options);
 
 
             return GetResult(episodes, request);
             return GetResult(episodes, request);
         }
         }

+ 1 - 2
MediaBrowser.Controller/Entities/CollectionFolder.cs

@@ -97,8 +97,7 @@ namespace MediaBrowser.Controller.Entities
         {
         {
             try
             try
             {
             {
-                var result = XmlSerializer.DeserializeFromFile(typeof(LibraryOptions), GetLibraryOptionsPath(path)) as LibraryOptions;
-                if (result == null)
+                if (XmlSerializer.DeserializeFromFile(typeof(LibraryOptions), GetLibraryOptionsPath(path)) is not LibraryOptions result)
                 {
                 {
                     return new LibraryOptions();
                     return new LibraryOptions();
                 }
                 }

+ 0 - 7
MediaBrowser.Controller/IServerApplicationHost.cs

@@ -104,13 +104,6 @@ namespace MediaBrowser.Controller
         /// <returns>The API URL.</returns>
         /// <returns>The API URL.</returns>
         string GetLocalApiUrl(string hostname, string scheme = null, int? port = null);
         string GetLocalApiUrl(string hostname, string scheme = null, int? port = null);
 
 
-        /// <summary>
-        /// Open a URL in an external browser window.
-        /// </summary>
-        /// <param name="url">The URL to open.</param>
-        /// <exception cref="NotSupportedException"><see cref="CanLaunchWebBrowser"/> is false.</exception>
-        void LaunchUrl(string url);
-
         IEnumerable<WakeOnLanInfo> GetWakeOnLanInfo();
         IEnumerable<WakeOnLanInfo> GetWakeOnLanInfo();
 
 
         string ExpandVirtualPath(string path);
         string ExpandVirtualPath(string path);

+ 3 - 3
MediaBrowser.Controller/Library/ILibraryManager.cs

@@ -595,11 +595,11 @@ namespace MediaBrowser.Controller.Library
 
 
         Task RemoveVirtualFolder(string name, bool refreshLibrary);
         Task RemoveVirtualFolder(string name, bool refreshLibrary);
 
 
-        void AddMediaPath(string virtualFolderName, MediaPathInfo path);
+        void AddMediaPath(string virtualFolderName, MediaPathInfo mediaPath);
 
 
-        void UpdateMediaPath(string virtualFolderName, MediaPathInfo path);
+        void UpdateMediaPath(string virtualFolderName, MediaPathInfo mediaPath);
 
 
-        void RemoveMediaPath(string virtualFolderName, string path);
+        void RemoveMediaPath(string virtualFolderName, string mediaPath);
 
 
         QueryResult<(BaseItem, ItemCounts)> GetGenres(InternalItemsQuery query);
         QueryResult<(BaseItem, ItemCounts)> GetGenres(InternalItemsQuery query);
 
 

+ 3 - 3
MediaBrowser.Controller/Library/IUserDataManager.cs

@@ -47,7 +47,7 @@ namespace MediaBrowser.Controller.Library
         /// <returns>User data dto.</returns>
         /// <returns>User data dto.</returns>
         UserItemDataDto GetUserDataDto(BaseItem item, User user);
         UserItemDataDto GetUserDataDto(BaseItem item, User user);
 
 
-        UserItemDataDto GetUserDataDto(BaseItem item, BaseItemDto itemDto, User user, DtoOptions dto_options);
+        UserItemDataDto GetUserDataDto(BaseItem item, BaseItemDto itemDto, User user, DtoOptions options);
 
 
         /// <summary>
         /// <summary>
         /// Get all user data for the given user.
         /// Get all user data for the given user.
@@ -69,8 +69,8 @@ namespace MediaBrowser.Controller.Library
         /// </summary>
         /// </summary>
         /// <param name="item">Item to update.</param>
         /// <param name="item">Item to update.</param>
         /// <param name="data">Data to update.</param>
         /// <param name="data">Data to update.</param>
-        /// <param name="positionTicks">New playstate.</param>
+        /// <param name="reportedPositionTicks">New playstate.</param>
         /// <returns>True if playstate was updated.</returns>
         /// <returns>True if playstate was updated.</returns>
-        bool UpdatePlayState(BaseItem item, UserItemData data, long? positionTicks);
+        bool UpdatePlayState(BaseItem item, UserItemData data, long? reportedPositionTicks);
     }
     }
 }
 }

+ 1 - 1
MediaBrowser.Controller/LiveTv/ILiveTvManager.cs

@@ -274,7 +274,7 @@ namespace MediaBrowser.Controller.LiveTv
 
 
         Task<TunerChannelMapping> SetChannelMapping(string providerId, string tunerChannelNumber, string providerChannelNumber);
         Task<TunerChannelMapping> SetChannelMapping(string providerId, string tunerChannelNumber, string providerChannelNumber);
 
 
-        TunerChannelMapping GetTunerChannelMapping(ChannelInfo channel, NameValuePair[] mappings, List<ChannelInfo> providerChannels);
+        TunerChannelMapping GetTunerChannelMapping(ChannelInfo tunerChannel, NameValuePair[] mappings, List<ChannelInfo> providerChannels);
 
 
         /// <summary>
         /// <summary>
         /// Gets the lineups.
         /// Gets the lineups.

+ 2 - 2
MediaBrowser.Controller/LiveTv/ILiveTvService.cs

@@ -70,10 +70,10 @@ namespace MediaBrowser.Controller.LiveTv
         /// <summary>
         /// <summary>
         /// Updates the timer asynchronous.
         /// Updates the timer asynchronous.
         /// </summary>
         /// </summary>
-        /// <param name="info">The information.</param>
+        /// <param name="updatedTimer">The updated timer information.</param>
         /// <param name="cancellationToken">The cancellation token.</param>
         /// <param name="cancellationToken">The cancellation token.</param>
         /// <returns>Task.</returns>
         /// <returns>Task.</returns>
-        Task UpdateTimerAsync(TimerInfo info, CancellationToken cancellationToken);
+        Task UpdateTimerAsync(TimerInfo updatedTimer, CancellationToken cancellationToken);
 
 
         /// <summary>
         /// <summary>
         /// Updates the series timer asynchronous.
         /// Updates the series timer asynchronous.

+ 4 - 4
MediaBrowser.Controller/Persistence/IItemRepository.cs

@@ -49,17 +49,17 @@ namespace MediaBrowser.Controller.Persistence
         /// <summary>
         /// <summary>
         /// Gets chapters for an item.
         /// Gets chapters for an item.
         /// </summary>
         /// </summary>
-        /// <param name="id">The item.</param>
+        /// <param name="item">The item.</param>
         /// <returns>The list of chapter info.</returns>
         /// <returns>The list of chapter info.</returns>
-        List<ChapterInfo> GetChapters(BaseItem id);
+        List<ChapterInfo> GetChapters(BaseItem item);
 
 
         /// <summary>
         /// <summary>
         /// Gets a single chapter for an item.
         /// Gets a single chapter for an item.
         /// </summary>
         /// </summary>
-        /// <param name="id">The item.</param>
+        /// <param name="item">The item.</param>
         /// <param name="index">The chapter index.</param>
         /// <param name="index">The chapter index.</param>
         /// <returns>The chapter info at the specified index.</returns>
         /// <returns>The chapter info at the specified index.</returns>
-        ChapterInfo GetChapter(BaseItem id, int index);
+        ChapterInfo GetChapter(BaseItem item, int index);
 
 
         /// <summary>
         /// <summary>
         /// Saves the chapters.
         /// Saves the chapters.

+ 1 - 1
MediaBrowser.Controller/Session/ISessionManager.cs

@@ -344,7 +344,7 @@ namespace MediaBrowser.Controller.Session
         /// <returns>A <see cref="Task"/> representing the log out process.</returns>
         /// <returns>A <see cref="Task"/> representing the log out process.</returns>
         Task Logout(string accessToken);
         Task Logout(string accessToken);
 
 
-        Task Logout(Device accessToken);
+        Task Logout(Device device);
 
 
         /// <summary>
         /// <summary>
         /// Revokes the user tokens.
         /// Revokes the user tokens.

+ 30 - 55
MediaBrowser.Model/Dlna/StreamInfo.cs

@@ -133,7 +133,7 @@ namespace MediaBrowser.Model.Dlna
                 var stream = TargetAudioStream;
                 var stream = TargetAudioStream;
                 return AudioSampleRate.HasValue && !IsDirectStream
                 return AudioSampleRate.HasValue && !IsDirectStream
                     ? AudioSampleRate
                     ? AudioSampleRate
-                    : stream == null ? null : stream.SampleRate;
+                    : stream?.SampleRate;
             }
             }
         }
         }
 
 
@@ -146,7 +146,7 @@ namespace MediaBrowser.Model.Dlna
             {
             {
                 if (IsDirectStream)
                 if (IsDirectStream)
                 {
                 {
-                    return TargetAudioStream == null ? (int?)null : TargetAudioStream.BitDepth;
+                    return TargetAudioStream?.BitDepth;
                 }
                 }
 
 
                 var targetAudioCodecs = TargetAudioCodec;
                 var targetAudioCodecs = TargetAudioCodec;
@@ -156,7 +156,7 @@ namespace MediaBrowser.Model.Dlna
                     return GetTargetAudioBitDepth(audioCodec);
                     return GetTargetAudioBitDepth(audioCodec);
                 }
                 }
 
 
-                return TargetAudioStream == null ? (int?)null : TargetAudioStream.BitDepth;
+                return TargetAudioStream?.BitDepth;
             }
             }
         }
         }
 
 
@@ -169,7 +169,7 @@ namespace MediaBrowser.Model.Dlna
             {
             {
                 if (IsDirectStream)
                 if (IsDirectStream)
                 {
                 {
-                    return TargetVideoStream == null ? (int?)null : TargetVideoStream.BitDepth;
+                    return TargetVideoStream?.BitDepth;
                 }
                 }
 
 
                 var targetVideoCodecs = TargetVideoCodec;
                 var targetVideoCodecs = TargetVideoCodec;
@@ -179,7 +179,7 @@ namespace MediaBrowser.Model.Dlna
                     return GetTargetVideoBitDepth(videoCodec);
                     return GetTargetVideoBitDepth(videoCodec);
                 }
                 }
 
 
-                return TargetVideoStream == null ? (int?)null : TargetVideoStream.BitDepth;
+                return TargetVideoStream?.BitDepth;
             }
             }
         }
         }
 
 
@@ -193,7 +193,7 @@ namespace MediaBrowser.Model.Dlna
             {
             {
                 if (IsDirectStream)
                 if (IsDirectStream)
                 {
                 {
-                    return TargetVideoStream == null ? (int?)null : TargetVideoStream.RefFrames;
+                    return TargetVideoStream?.RefFrames;
                 }
                 }
 
 
                 var targetVideoCodecs = TargetVideoCodec;
                 var targetVideoCodecs = TargetVideoCodec;
@@ -203,7 +203,7 @@ namespace MediaBrowser.Model.Dlna
                     return GetTargetRefFrames(videoCodec);
                     return GetTargetRefFrames(videoCodec);
                 }
                 }
 
 
-                return TargetVideoStream == null ? (int?)null : TargetVideoStream.RefFrames;
+                return TargetVideoStream?.RefFrames;
             }
             }
         }
         }
 
 
@@ -230,7 +230,7 @@ namespace MediaBrowser.Model.Dlna
             {
             {
                 if (IsDirectStream)
                 if (IsDirectStream)
                 {
                 {
-                    return TargetVideoStream == null ? (double?)null : TargetVideoStream.Level;
+                    return TargetVideoStream?.Level;
                 }
                 }
 
 
                 var targetVideoCodecs = TargetVideoCodec;
                 var targetVideoCodecs = TargetVideoCodec;
@@ -240,7 +240,7 @@ namespace MediaBrowser.Model.Dlna
                     return GetTargetVideoLevel(videoCodec);
                     return GetTargetVideoLevel(videoCodec);
                 }
                 }
 
 
-                return TargetVideoStream == null ? (double?)null : TargetVideoStream.Level;
+                return TargetVideoStream?.Level;
             }
             }
         }
         }
 
 
@@ -254,7 +254,7 @@ namespace MediaBrowser.Model.Dlna
                 var stream = TargetVideoStream;
                 var stream = TargetVideoStream;
                 return !IsDirectStream
                 return !IsDirectStream
                     ? null
                     ? null
-                    : stream == null ? null : stream.PacketLength;
+                    : stream?.PacketLength;
             }
             }
         }
         }
 
 
@@ -267,7 +267,7 @@ namespace MediaBrowser.Model.Dlna
             {
             {
                 if (IsDirectStream)
                 if (IsDirectStream)
                 {
                 {
-                    return TargetVideoStream == null ? null : TargetVideoStream.Profile;
+                    return TargetVideoStream?.Profile;
                 }
                 }
 
 
                 var targetVideoCodecs = TargetVideoCodec;
                 var targetVideoCodecs = TargetVideoCodec;
@@ -277,7 +277,7 @@ namespace MediaBrowser.Model.Dlna
                     return GetOption(videoCodec, "profile");
                     return GetOption(videoCodec, "profile");
                 }
                 }
 
 
-                return TargetVideoStream == null ? null : TargetVideoStream.Profile;
+                return TargetVideoStream?.Profile;
             }
             }
         }
         }
 
 
@@ -292,7 +292,7 @@ namespace MediaBrowser.Model.Dlna
                 var stream = TargetVideoStream;
                 var stream = TargetVideoStream;
                 return !IsDirectStream
                 return !IsDirectStream
                     ? null
                     ? null
-                    : stream == null ? null : stream.CodecTag;
+                    : stream?.CodecTag;
             }
             }
         }
         }
 
 
@@ -306,7 +306,7 @@ namespace MediaBrowser.Model.Dlna
                 var stream = TargetAudioStream;
                 var stream = TargetAudioStream;
                 return AudioBitrate.HasValue && !IsDirectStream
                 return AudioBitrate.HasValue && !IsDirectStream
                     ? AudioBitrate
                     ? AudioBitrate
-                    : stream == null ? null : stream.BitRate;
+                    : stream?.BitRate;
             }
             }
         }
         }
 
 
@@ -319,7 +319,7 @@ namespace MediaBrowser.Model.Dlna
             {
             {
                 if (IsDirectStream)
                 if (IsDirectStream)
                 {
                 {
-                    return TargetAudioStream == null ? (int?)null : TargetAudioStream.Channels;
+                    return TargetAudioStream?.Channels;
                 }
                 }
 
 
                 var targetAudioCodecs = TargetAudioCodec;
                 var targetAudioCodecs = TargetAudioCodec;
@@ -329,7 +329,7 @@ namespace MediaBrowser.Model.Dlna
                     return GetTargetRefFrames(codec);
                     return GetTargetRefFrames(codec);
                 }
                 }
 
 
-                return TargetAudioStream == null ? (int?)null : TargetAudioStream.Channels;
+                return TargetAudioStream?.Channels;
             }
             }
         }
         }
 
 
@@ -425,7 +425,7 @@ namespace MediaBrowser.Model.Dlna
 
 
                 return VideoBitrate.HasValue && !IsDirectStream
                 return VideoBitrate.HasValue && !IsDirectStream
                     ? VideoBitrate
                     ? VideoBitrate
-                    : stream == null ? null : stream.BitRate;
+                    : stream?.BitRate;
             }
             }
         }
         }
 
 
@@ -451,7 +451,7 @@ namespace MediaBrowser.Model.Dlna
             {
             {
                 if (IsDirectStream)
                 if (IsDirectStream)
                 {
                 {
-                    return TargetVideoStream == null ? null : TargetVideoStream.IsAnamorphic;
+                    return TargetVideoStream?.IsAnamorphic;
                 }
                 }
 
 
                 return false;
                 return false;
@@ -464,7 +464,7 @@ namespace MediaBrowser.Model.Dlna
             {
             {
                 if (IsDirectStream)
                 if (IsDirectStream)
                 {
                 {
-                    return TargetVideoStream == null ? (bool?)null : TargetVideoStream.IsInterlaced;
+                    return TargetVideoStream?.IsInterlaced;
                 }
                 }
 
 
                 var targetVideoCodecs = TargetVideoCodec;
                 var targetVideoCodecs = TargetVideoCodec;
@@ -477,7 +477,7 @@ namespace MediaBrowser.Model.Dlna
                     }
                     }
                 }
                 }
 
 
-                return TargetVideoStream == null ? (bool?)null : TargetVideoStream.IsInterlaced;
+                return TargetVideoStream?.IsInterlaced;
             }
             }
         }
         }
 
 
@@ -487,7 +487,7 @@ namespace MediaBrowser.Model.Dlna
             {
             {
                 if (IsDirectStream)
                 if (IsDirectStream)
                 {
                 {
-                    return TargetVideoStream == null ? null : TargetVideoStream.IsAVC;
+                    return TargetVideoStream?.IsAVC;
                 }
                 }
 
 
                 return true;
                 return true;
@@ -618,20 +618,20 @@ namespace MediaBrowser.Model.Dlna
                 }
                 }
 
 
                 // Try to keep the url clean by omitting defaults
                 // Try to keep the url clean by omitting defaults
-                if (string.Equals(pair.Name, "StartTimeTicks", StringComparison.OrdinalIgnoreCase) &&
-                    string.Equals(pair.Value, "0", StringComparison.OrdinalIgnoreCase))
+                if (string.Equals(pair.Name, "StartTimeTicks", StringComparison.OrdinalIgnoreCase)
+                    && string.Equals(pair.Value, "0", StringComparison.OrdinalIgnoreCase))
                 {
                 {
                     continue;
                     continue;
                 }
                 }
 
 
-                if (string.Equals(pair.Name, "SubtitleStreamIndex", StringComparison.OrdinalIgnoreCase) &&
-                    string.Equals(pair.Value, "-1", StringComparison.OrdinalIgnoreCase))
+                if (string.Equals(pair.Name, "SubtitleStreamIndex", StringComparison.OrdinalIgnoreCase)
+                    && string.Equals(pair.Value, "-1", StringComparison.OrdinalIgnoreCase))
                 {
                 {
                     continue;
                     continue;
                 }
                 }
 
 
-                if (string.Equals(pair.Name, "Static", StringComparison.OrdinalIgnoreCase) &&
-                    string.Equals(pair.Value, "false", StringComparison.OrdinalIgnoreCase))
+                if (string.Equals(pair.Name, "Static", StringComparison.OrdinalIgnoreCase)
+                    && string.Equals(pair.Value, "false", StringComparison.OrdinalIgnoreCase))
                 {
                 {
                     continue;
                     continue;
                 }
                 }
@@ -641,7 +641,7 @@ namespace MediaBrowser.Model.Dlna
                 list.Add(string.Format(CultureInfo.InvariantCulture, "{0}={1}", pair.Name, encodedValue));
                 list.Add(string.Format(CultureInfo.InvariantCulture, "{0}={1}", pair.Name, encodedValue));
             }
             }
 
 
-            string queryString = string.Join("&", list.ToArray());
+            string queryString = string.Join('&', list);
 
 
             return GetUrl(baseUrl, queryString);
             return GetUrl(baseUrl, queryString);
         }
         }
@@ -681,11 +681,11 @@ namespace MediaBrowser.Model.Dlna
 
 
             string audioCodecs = item.AudioCodecs.Length == 0 ?
             string audioCodecs = item.AudioCodecs.Length == 0 ?
                 string.Empty :
                 string.Empty :
-                string.Join(",", item.AudioCodecs);
+                string.Join(',', item.AudioCodecs);
 
 
             string videoCodecs = item.VideoCodecs.Length == 0 ?
             string videoCodecs = item.VideoCodecs.Length == 0 ?
                 string.Empty :
                 string.Empty :
-                string.Join(",", item.VideoCodecs);
+                string.Join(',', item.VideoCodecs);
 
 
             list.Add(new NameValuePair("DeviceProfileId", item.DeviceProfileId ?? string.Empty));
             list.Add(new NameValuePair("DeviceProfileId", item.DeviceProfileId ?? string.Empty));
             list.Add(new NameValuePair("DeviceId", item.DeviceId ?? string.Empty));
             list.Add(new NameValuePair("DeviceId", item.DeviceId ?? string.Empty));
@@ -1024,30 +1024,5 @@ namespace MediaBrowser.Model.Dlna
 
 
             return count;
             return count;
         }
         }
-
-        public List<MediaStream> GetSelectableAudioStreams()
-        {
-            return GetSelectableStreams(MediaStreamType.Audio);
-        }
-
-        public List<MediaStream> GetSelectableSubtitleStreams()
-        {
-            return GetSelectableStreams(MediaStreamType.Subtitle);
-        }
-
-        public List<MediaStream> GetSelectableStreams(MediaStreamType type)
-        {
-            var list = new List<MediaStream>();
-
-            foreach (var stream in MediaSource.MediaStreams)
-            {
-                if (type == stream.Type)
-                {
-                    list.Add(stream);
-                }
-            }
-
-            return list;
-        }
     }
     }
 }
 }

+ 6 - 0
jellyfin.ruleset

@@ -12,6 +12,8 @@
     <Rule Id="SA1101" Action="None" />
     <Rule Id="SA1101" Action="None" />
     <!-- disable warning SA1108: Block statements should not contain embedded comments -->
     <!-- disable warning SA1108: Block statements should not contain embedded comments -->
     <Rule Id="SA1108" Action="None" />
     <Rule Id="SA1108" Action="None" />
+    <!-- disable warning SA1118: Parameter must not span multiple lines. -->
+    <Rule Id="SA1118" Action="None" />
     <!-- disable warning SA1128:: Put constructor initializers on their own line -->
     <!-- disable warning SA1128:: Put constructor initializers on their own line -->
     <Rule Id="SA1128" Action="None" />
     <Rule Id="SA1128" Action="None" />
     <!-- disable warning SA1130: Use lambda syntax -->
     <!-- disable warning SA1130: Use lambda syntax -->
@@ -39,6 +41,10 @@
   </Rules>
   </Rules>
 
 
   <Rules AnalyzerId="Microsoft.CodeAnalysis.NetAnalyzers" RuleNamespace="Microsoft.Design">
   <Rules AnalyzerId="Microsoft.CodeAnalysis.NetAnalyzers" RuleNamespace="Microsoft.Design">
+    <!-- error on CA1305: Specify IFormatProvider -->
+    <Rule Id="CA1305" Action="Error" />
+    <!-- error on CA1725: Parameter names should match base declaration -->
+    <Rule Id="CA1725" Action="Error" />
     <!-- error on CA2016: Forward the CancellationToken parameter to methods that take one
     <!-- error on CA2016: Forward the CancellationToken parameter to methods that take one
         or pass in 'CancellationToken.None' explicitly to indicate intentionally not propagating the token -->
         or pass in 'CancellationToken.None' explicitly to indicate intentionally not propagating the token -->
     <Rule Id="CA2016" Action="Error" />
     <Rule Id="CA2016" Action="Error" />