From 6fb6b5f1766a1f37a61b9faaa40209bab995bf30 Mon Sep 17 00:00:00 2001 From: Cody Robibero Date: Sun, 14 Apr 2024 08:18:36 -0600 Subject: Validate item access (#11171) --- .../Controllers/UniversalAudioController.cs | 27 +++++++++++++++++----- 1 file changed, 21 insertions(+), 6 deletions(-) (limited to 'Jellyfin.Api/Controllers/UniversalAudioController.cs') diff --git a/Jellyfin.Api/Controllers/UniversalAudioController.cs b/Jellyfin.Api/Controllers/UniversalAudioController.cs index db78e9946..1d4adae06 100644 --- a/Jellyfin.Api/Controllers/UniversalAudioController.cs +++ b/Jellyfin.Api/Controllers/UniversalAudioController.cs @@ -9,7 +9,9 @@ using Jellyfin.Api.Helpers; using Jellyfin.Api.ModelBinders; using Jellyfin.Api.Models.StreamingDtos; using Jellyfin.Data.Enums; +using Jellyfin.Extensions; using MediaBrowser.Common.Extensions; +using MediaBrowser.Controller.Entities; using MediaBrowser.Controller.Library; using MediaBrowser.Controller.MediaEncoding; using MediaBrowser.Controller.Streaming; @@ -33,6 +35,7 @@ public class UniversalAudioController : BaseJellyfinApiController private readonly MediaInfoHelper _mediaInfoHelper; private readonly AudioHelper _audioHelper; private readonly DynamicHlsHelper _dynamicHlsHelper; + private readonly IUserManager _userManager; /// /// Initializes a new instance of the class. @@ -42,18 +45,21 @@ public class UniversalAudioController : BaseJellyfinApiController /// Instance of . /// Instance of . /// Instance of . + /// Instance of the interface. public UniversalAudioController( ILibraryManager libraryManager, ILogger logger, MediaInfoHelper mediaInfoHelper, AudioHelper audioHelper, - DynamicHlsHelper dynamicHlsHelper) + DynamicHlsHelper dynamicHlsHelper, + IUserManager userManager) { _libraryManager = libraryManager; _logger = logger; _mediaInfoHelper = mediaInfoHelper; _audioHelper = audioHelper; _dynamicHlsHelper = dynamicHlsHelper; + _userManager = userManager; } /// @@ -79,12 +85,14 @@ public class UniversalAudioController : BaseJellyfinApiController /// Whether to enable redirection. Defaults to true. /// Audio stream returned. /// Redirected to remote audio stream. + /// Item not found. /// A containing the audio file. [HttpGet("Audio/{itemId}/universal")] [HttpHead("Audio/{itemId}/universal", Name = "HeadUniversalAudioStream")] [Authorize] [ProducesResponseType(StatusCodes.Status200OK)] [ProducesResponseType(StatusCodes.Status302Found)] + [ProducesResponseType(StatusCodes.Status404NotFound)] [ProducesAudioFile] public async Task GetUniversalAudioStream( [FromRoute, Required] Guid itemId, @@ -106,20 +114,27 @@ public class UniversalAudioController : BaseJellyfinApiController [FromQuery] bool breakOnNonKeyFrames = false, [FromQuery] bool enableRedirection = true) { - var deviceProfile = GetDeviceProfile(container, transcodingContainer, audioCodec, transcodingProtocol, breakOnNonKeyFrames, transcodingAudioChannels, maxAudioSampleRate, maxAudioBitDepth, maxAudioChannels); userId = RequestHelpers.GetUserId(User, userId); + var user = userId.IsNullOrEmpty() + ? null + : _userManager.GetUserById(userId.Value); + var item = _libraryManager.GetItemById(itemId, user); + if (item is null) + { + return NotFound(); + } + + var deviceProfile = GetDeviceProfile(container, transcodingContainer, audioCodec, transcodingProtocol, breakOnNonKeyFrames, transcodingAudioChannels, maxAudioSampleRate, maxAudioBitDepth, maxAudioChannels); _logger.LogInformation("GetPostedPlaybackInfo profile: {@Profile}", deviceProfile); var info = await _mediaInfoHelper.GetPlaybackInfo( - itemId, - userId, + item, + user, mediaSourceId) .ConfigureAwait(false); // set device specific data - var item = _libraryManager.GetItemById(itemId); - foreach (var sourceInfo in info.MediaSources) { _mediaInfoHelper.SetDeviceSpecificData( -- cgit v1.2.3 From e4101128e011c089bad46a524856438154cfbd3d Mon Sep 17 00:00:00 2001 From: gnattu Date: Mon, 22 Apr 2024 06:19:17 +0800 Subject: feat: add audio remux to UniversalAudioController Signed-off-by: gnattu --- .../Controllers/UniversalAudioController.cs | 16 ++++-- Jellyfin.Api/Helpers/DynamicHlsHelper.cs | 8 +++ .../Transcoding/TranscodeManager.cs | 5 ++ MediaBrowser.Model/Dlna/StreamBuilder.cs | 63 +++++++++++++++++++++- 4 files changed, 86 insertions(+), 6 deletions(-) (limited to 'Jellyfin.Api/Controllers/UniversalAudioController.cs') diff --git a/Jellyfin.Api/Controllers/UniversalAudioController.cs b/Jellyfin.Api/Controllers/UniversalAudioController.cs index 1d4adae06..3115c4750 100644 --- a/Jellyfin.Api/Controllers/UniversalAudioController.cs +++ b/Jellyfin.Api/Controllers/UniversalAudioController.cs @@ -17,6 +17,7 @@ using MediaBrowser.Controller.MediaEncoding; using MediaBrowser.Controller.Streaming; using MediaBrowser.Model.Dlna; using MediaBrowser.Model.MediaInfo; +using MediaBrowser.Model.Session; using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc; @@ -137,6 +138,8 @@ public class UniversalAudioController : BaseJellyfinApiController // set device specific data foreach (var sourceInfo in info.MediaSources) { + sourceInfo.TranscodingContainer = transcodingContainer; + sourceInfo.TranscodingSubProtocol = transcodingProtocol ?? sourceInfo.TranscodingSubProtocol; _mediaInfoHelper.SetDeviceSpecificData( item, sourceInfo, @@ -171,27 +174,30 @@ public class UniversalAudioController : BaseJellyfinApiController return Redirect(mediaSource.Path); } + // This one is currently very misleading as the SupportsDirectStream is always false + // The definition of DirectStream also seems changed during development + // It used to mean HTTP direct streaming, but now HLS is used even for DirectStream var isStatic = mediaSource.SupportsDirectStream; - if (!isStatic && mediaSource.TranscodingSubProtocol == MediaStreamProtocol.hls) + if (mediaSource.TranscodingSubProtocol == MediaStreamProtocol.hls) { // hls segment container can only be mpegts or fmp4 per ffmpeg documentation // ffmpeg option -> file extension // mpegts -> ts // fmp4 -> mp4 - // TODO: remove this when we switch back to the segment muxer var supportedHlsContainers = new[] { "ts", "mp4" }; + // fallback to mpegts if device reports some weird value unsupported by hls + var segmentContainer = Array.Exists(supportedHlsContainers, element => element == transcodingContainer) ? transcodingContainer : "ts"; var dynamicHlsRequestDto = new HlsAudioRequestDto { Id = itemId, Container = ".m3u8", Static = isStatic, PlaySessionId = info.PlaySessionId, - // fallback to mpegts if device reports some weird value unsupported by hls - SegmentContainer = Array.Exists(supportedHlsContainers, element => element == transcodingContainer) ? transcodingContainer : "ts", + SegmentContainer = segmentContainer, MediaSourceId = mediaSourceId, DeviceId = deviceId, - AudioCodec = audioCodec, + AudioCodec = mediaSource.TranscodeReasons == TranscodeReason.ContainerNotSupported ? "copy" : audioCodec, EnableAutoStreamCopy = true, AllowAudioStreamCopy = true, AllowVideoStreamCopy = true, diff --git a/Jellyfin.Api/Helpers/DynamicHlsHelper.cs b/Jellyfin.Api/Helpers/DynamicHlsHelper.cs index f8d89119a..8df4caea5 100644 --- a/Jellyfin.Api/Helpers/DynamicHlsHelper.cs +++ b/Jellyfin.Api/Helpers/DynamicHlsHelper.cs @@ -151,6 +151,14 @@ public class DynamicHlsHelper var queryString = _httpContextAccessor.HttpContext.Request.QueryString.ToString(); + // from universal audio service, need to override the AudioCodec when the actual request differs from original query + if (!string.Equals(state.OutputAudioCodec, _httpContextAccessor.HttpContext.Request.Query["AudioCodec"].ToString(), StringComparison.OrdinalIgnoreCase)) + { + var newQuery = Microsoft.AspNetCore.WebUtilities.QueryHelpers.ParseQuery(_httpContextAccessor.HttpContext.Request.QueryString.ToString()); + newQuery["AudioCodec"] = state.OutputAudioCodec; + queryString = Microsoft.AspNetCore.WebUtilities.QueryHelpers.AddQueryString(string.Empty, newQuery); + } + // from universal audio service if (!string.IsNullOrWhiteSpace(state.Request.SegmentContainer) && !queryString.Contains("SegmentContainer", StringComparison.OrdinalIgnoreCase)) diff --git a/MediaBrowser.MediaEncoding/Transcoding/TranscodeManager.cs b/MediaBrowser.MediaEncoding/Transcoding/TranscodeManager.cs index ea5dbf7f7..e45e8507a 100644 --- a/MediaBrowser.MediaEncoding/Transcoding/TranscodeManager.cs +++ b/MediaBrowser.MediaEncoding/Transcoding/TranscodeManager.cs @@ -479,6 +479,11 @@ public sealed class TranscodeManager : ITranscodeManager, IDisposable : "FFmpeg.DirectStream-"; } + if (state.VideoRequest is null && EncodingHelper.IsCopyCodec(state.OutputAudioCodec)) + { + logFilePrefix = "FFmpeg.Remux-"; + } + var logFilePath = Path.Combine( _serverConfigurationManager.ApplicationPaths.LogDirectoryPath, $"{logFilePrefix}{DateTime.Now:yyyy-MM-dd_HH-mm-ss}_{state.Request.MediaSourceId}_{Guid.NewGuid().ToString()[..8]}.log"); diff --git a/MediaBrowser.Model/Dlna/StreamBuilder.cs b/MediaBrowser.Model/Dlna/StreamBuilder.cs index 55d1c3d51..f9fe7d351 100644 --- a/MediaBrowser.Model/Dlna/StreamBuilder.cs +++ b/MediaBrowser.Model/Dlna/StreamBuilder.cs @@ -108,7 +108,7 @@ namespace MediaBrowser.Model.Dlna var inputAudioSampleRate = audioStream?.SampleRate; var inputAudioBitDepth = audioStream?.BitDepth; - if (directPlayMethod.HasValue) + if (directPlayMethod is PlayMethod.DirectPlay) { var profile = options.Profile; var audioFailureConditions = GetProfileConditionsForAudio(profile.CodecProfiles, item.Container, audioStream?.Codec, inputAudioChannels, inputAudioBitrate, inputAudioSampleRate, inputAudioBitDepth, true); @@ -124,6 +124,41 @@ namespace MediaBrowser.Model.Dlna } } + if (directPlayMethod is PlayMethod.DirectStream) + { + var remuxContainer = item.TranscodingContainer ?? "ts"; + bool codeIsSupported; + if (item.TranscodingSubProtocol == MediaStreamProtocol.hls) + { + // Enforce HLS audio codec restrictions + if (string.Equals(remuxContainer, "mp4", StringComparison.OrdinalIgnoreCase)) + { + codeIsSupported = _supportedHlsAudioCodecsMp4.Contains(directPlayInfo.Profile?.AudioCodec ?? directPlayInfo.Profile?.Container); + } + else + { + codeIsSupported = _supportedHlsAudioCodecsTs.Contains(directPlayInfo.Profile?.AudioCodec ?? directPlayInfo.Profile?.Container); + } + } + else + { + // Let's assume the client has given a correct container for http + codeIsSupported = true; + } + + if (codeIsSupported) + { + playlistItem.PlayMethod = directPlayMethod.Value; + playlistItem.Container = remuxContainer; + playlistItem.TranscodeReasons = transcodeReasons; + playlistItem.SubProtocol = item.TranscodingSubProtocol; + return playlistItem; + } + + transcodeReasons |= TranscodeReason.AudioCodecNotSupported; + playlistItem.TranscodeReasons = transcodeReasons; + } + TranscodingProfile? transcodingProfile = null; foreach (var tcProfile in options.Profile.TranscodingProfiles) { @@ -387,6 +422,14 @@ namespace MediaBrowser.Model.Dlna item.Path ?? "Unknown path", audioStream.Codec ?? "Unknown codec"); + var directStreamProfile = options.Profile.DirectPlayProfiles + .FirstOrDefault(x => x.Type == DlnaProfileType.Audio && IsAudioDirectStreamSupported(x, item, audioStream)); + + if (directStreamProfile is not null) + { + return (directStreamProfile, PlayMethod.DirectStream, TranscodeReason.ContainerNotSupported); + } + return (null, null, GetTranscodeReasonsFromDirectPlayProfile(item, null, audioStream, options.Profile.DirectPlayProfiles)); } @@ -2129,5 +2172,23 @@ namespace MediaBrowser.Model.Dlna return true; } + + private static bool IsAudioDirectStreamSupported(DirectPlayProfile profile, MediaSourceInfo item, MediaStream audioStream) + { + // Check container type, this should NOT be supported + if (!profile.SupportsContainer(item.Container)) + { + // Check audio codec, we cannot use the SupportsAudioCodec here + // Because that one assumes empty container supports all codec, which is just useless + string? audioCodec = audioStream?.Codec; + if (string.Equals(profile.AudioCodec, audioCodec, StringComparison.OrdinalIgnoreCase) || + string.Equals(profile.Container, audioCodec, StringComparison.OrdinalIgnoreCase)) + { + return true; + } + } + + return false; + } } } -- cgit v1.2.3 From a16d3d488704be5a2e8b528c446f06588831246d Mon Sep 17 00:00:00 2001 From: gnattu Date: Mon, 22 Apr 2024 22:31:41 +0800 Subject: Allow clients to send audio container override for HLS This will improve flexibility due to overcome the complex compatibility situation of HLS Signed-off-by: gnattu --- Jellyfin.Api/Controllers/UniversalAudioController.cs | 3 ++- MediaBrowser.Model/Dlna/StreamBuilder.cs | 5 +++++ 2 files changed, 7 insertions(+), 1 deletion(-) (limited to 'Jellyfin.Api/Controllers/UniversalAudioController.cs') diff --git a/Jellyfin.Api/Controllers/UniversalAudioController.cs b/Jellyfin.Api/Controllers/UniversalAudioController.cs index 3115c4750..1305d1417 100644 --- a/Jellyfin.Api/Controllers/UniversalAudioController.cs +++ b/Jellyfin.Api/Controllers/UniversalAudioController.cs @@ -187,7 +187,8 @@ public class UniversalAudioController : BaseJellyfinApiController var supportedHlsContainers = new[] { "ts", "mp4" }; // fallback to mpegts if device reports some weird value unsupported by hls - var segmentContainer = Array.Exists(supportedHlsContainers, element => element == transcodingContainer) ? transcodingContainer : "ts"; + var requestedSegmentContainer = Array.Exists(supportedHlsContainers, element => element == transcodingContainer) ? transcodingContainer : "ts"; + var segmentContainer = Array.Exists(supportedHlsContainers, element => element == mediaSource.TranscodingContainer) ? mediaSource.TranscodingContainer : requestedSegmentContainer; var dynamicHlsRequestDto = new HlsAudioRequestDto { Id = itemId, diff --git a/MediaBrowser.Model/Dlna/StreamBuilder.cs b/MediaBrowser.Model/Dlna/StreamBuilder.cs index f9fe7d351..20d9cd8d5 100644 --- a/MediaBrowser.Model/Dlna/StreamBuilder.cs +++ b/MediaBrowser.Model/Dlna/StreamBuilder.cs @@ -127,6 +127,10 @@ namespace MediaBrowser.Model.Dlna if (directPlayMethod is PlayMethod.DirectStream) { var remuxContainer = item.TranscodingContainer ?? "ts"; + var supportedHlsContainers = new[] { "ts", "mp4" }; + // If the container specified for the profile is an HLS supported container, use that container instead, overriding the preference + // The client should be responsible to ensure this container is compatible + remuxContainer = Array.Exists(supportedHlsContainers, element => element == directPlayInfo.Profile?.Container) ? directPlayInfo.Profile?.Container : remuxContainer; bool codeIsSupported; if (item.TranscodingSubProtocol == MediaStreamProtocol.hls) { @@ -152,6 +156,7 @@ namespace MediaBrowser.Model.Dlna playlistItem.Container = remuxContainer; playlistItem.TranscodeReasons = transcodeReasons; playlistItem.SubProtocol = item.TranscodingSubProtocol; + item.TranscodingContainer = remuxContainer; return playlistItem; } -- cgit v1.2.3 From f840d9b60f886ce618e88efb5526532b620054bb Mon Sep 17 00:00:00 2001 From: gnattu Date: Sun, 5 May 2024 11:21:10 +0800 Subject: Fix direct play The SupportsDirectStream is a little bit misleading as it actually means "Supports Direct Play" Signed-off-by: gnattu --- Jellyfin.Api/Controllers/UniversalAudioController.cs | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'Jellyfin.Api/Controllers/UniversalAudioController.cs') diff --git a/Jellyfin.Api/Controllers/UniversalAudioController.cs b/Jellyfin.Api/Controllers/UniversalAudioController.cs index 1305d1417..3286105e3 100644 --- a/Jellyfin.Api/Controllers/UniversalAudioController.cs +++ b/Jellyfin.Api/Controllers/UniversalAudioController.cs @@ -174,11 +174,10 @@ public class UniversalAudioController : BaseJellyfinApiController return Redirect(mediaSource.Path); } - // This one is currently very misleading as the SupportsDirectStream is always false + // This one is currently very misleading as the SupportsDirectStream actually means "can direct play" // The definition of DirectStream also seems changed during development - // It used to mean HTTP direct streaming, but now HLS is used even for DirectStream var isStatic = mediaSource.SupportsDirectStream; - if (mediaSource.TranscodingSubProtocol == MediaStreamProtocol.hls) + if (!isStatic && mediaSource.TranscodingSubProtocol == MediaStreamProtocol.hls) { // hls segment container can only be mpegts or fmp4 per ffmpeg documentation // ffmpeg option -> file extension -- cgit v1.2.3 From d5eb8fc1219fb1566ee28a0cfe693c6e5da6f605 Mon Sep 17 00:00:00 2001 From: gnattu Date: Mon, 6 May 2024 13:16:06 +0800 Subject: Also make UniversalAudioController check client VBR settings Signed-off-by: gnattu --- Jellyfin.Api/Controllers/UniversalAudioController.cs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'Jellyfin.Api/Controllers/UniversalAudioController.cs') diff --git a/Jellyfin.Api/Controllers/UniversalAudioController.cs b/Jellyfin.Api/Controllers/UniversalAudioController.cs index 1d4adae06..c858c17ba 100644 --- a/Jellyfin.Api/Controllers/UniversalAudioController.cs +++ b/Jellyfin.Api/Controllers/UniversalAudioController.cs @@ -81,6 +81,7 @@ public class UniversalAudioController : BaseJellyfinApiController /// Optional. The maximum audio sample rate. /// Optional. The maximum audio bit depth. /// Optional. Whether to enable remote media. + /// Optional. Whether to enable Audio Encoding. /// Optional. Whether to break on non key frames. /// Whether to enable redirection. Defaults to true. /// Audio stream returned. @@ -111,6 +112,7 @@ public class UniversalAudioController : BaseJellyfinApiController [FromQuery] int? maxAudioSampleRate, [FromQuery] int? maxAudioBitDepth, [FromQuery] bool? enableRemoteMedia, + [FromQuery] bool? enableAudioVbrEncoding, [FromQuery] bool breakOnNonKeyFrames = false, [FromQuery] bool enableRedirection = true) { @@ -209,7 +211,8 @@ public class UniversalAudioController : BaseJellyfinApiController TranscodeReasons = mediaSource.TranscodeReasons == 0 ? null : mediaSource.TranscodeReasons.ToString(), Context = EncodingContext.Static, StreamOptions = new Dictionary(), - EnableAdaptiveBitrateStreaming = true + EnableAdaptiveBitrateStreaming = true, + EnableAudioVbrEncoding = enableAudioVbrEncoding ?? true }; return await _dynamicHlsHelper.GetMasterHlsPlaylist(TranscodingJobType.Hls, dynamicHlsRequestDto, true) -- cgit v1.2.3 From fd5df98616408fe54944ff39310aacd1751c45b5 Mon Sep 17 00:00:00 2001 From: gnattu Date: Wed, 17 Jul 2024 21:52:44 +0800 Subject: Move default value to api spec Signed-off-by: gnattu --- Jellyfin.Api/Controllers/AudioController.cs | 4 ++-- Jellyfin.Api/Controllers/DynamicHlsController.cs | 20 ++++++++++---------- Jellyfin.Api/Controllers/UniversalAudioController.cs | 4 ++-- Jellyfin.Api/Controllers/VideosController.cs | 6 +++--- 4 files changed, 17 insertions(+), 17 deletions(-) (limited to 'Jellyfin.Api/Controllers/UniversalAudioController.cs') diff --git a/Jellyfin.Api/Controllers/AudioController.cs b/Jellyfin.Api/Controllers/AudioController.cs index c62005735..8954c8ef5 100644 --- a/Jellyfin.Api/Controllers/AudioController.cs +++ b/Jellyfin.Api/Controllers/AudioController.cs @@ -307,7 +307,7 @@ public class AudioController : BaseJellyfinApiController [FromQuery] int? videoStreamIndex, [FromQuery] EncodingContext? context, [FromQuery] Dictionary? streamOptions, - [FromQuery] bool? enableAudioVbrEncoding) + [FromQuery] bool enableAudioVbrEncoding = true) { StreamingRequestDto streamingRequest = new StreamingRequestDto { @@ -359,7 +359,7 @@ public class AudioController : BaseJellyfinApiController VideoStreamIndex = videoStreamIndex, Context = context ?? EncodingContext.Static, StreamOptions = streamOptions, - EnableAudioVbrEncoding = enableAudioVbrEncoding ?? true + EnableAudioVbrEncoding = enableAudioVbrEncoding }; return await _audioHelper.GetAudioStream(_transcodingJobType, streamingRequest).ConfigureAwait(false); diff --git a/Jellyfin.Api/Controllers/DynamicHlsController.cs b/Jellyfin.Api/Controllers/DynamicHlsController.cs index a7fc9928e..429cc542c 100644 --- a/Jellyfin.Api/Controllers/DynamicHlsController.cs +++ b/Jellyfin.Api/Controllers/DynamicHlsController.cs @@ -215,7 +215,7 @@ public class DynamicHlsController : BaseJellyfinApiController [FromQuery] int? maxWidth, [FromQuery] int? maxHeight, [FromQuery] bool? enableSubtitlesInManifest, - [FromQuery] bool? enableAudioVbrEncoding) + [FromQuery] bool enableAudioVbrEncoding = true) { VideoRequestDto streamingRequest = new VideoRequestDto { @@ -270,7 +270,7 @@ public class DynamicHlsController : BaseJellyfinApiController MaxHeight = maxHeight, MaxWidth = maxWidth, EnableSubtitlesInManifest = enableSubtitlesInManifest ?? true, - EnableAudioVbrEncoding = enableAudioVbrEncoding ?? true + EnableAudioVbrEncoding = enableAudioVbrEncoding }; // CTS lifecycle is managed internally. @@ -796,7 +796,7 @@ public class DynamicHlsController : BaseJellyfinApiController [FromQuery] int? videoStreamIndex, [FromQuery] EncodingContext? context, [FromQuery] Dictionary streamOptions, - [FromQuery] bool? enableAudioVbrEncoding) + [FromQuery] bool enableAudioVbrEncoding = true) { using var cancellationTokenSource = new CancellationTokenSource(); var streamingRequest = new VideoRequestDto @@ -850,7 +850,7 @@ public class DynamicHlsController : BaseJellyfinApiController VideoStreamIndex = videoStreamIndex, Context = context ?? EncodingContext.Streaming, StreamOptions = streamOptions, - EnableAudioVbrEncoding = enableAudioVbrEncoding ?? true + EnableAudioVbrEncoding = enableAudioVbrEncoding }; return await GetVariantPlaylistInternal(streamingRequest, cancellationTokenSource) @@ -965,7 +965,7 @@ public class DynamicHlsController : BaseJellyfinApiController [FromQuery] int? videoStreamIndex, [FromQuery] EncodingContext? context, [FromQuery] Dictionary streamOptions, - [FromQuery] bool? enableAudioVbrEncoding) + [FromQuery] bool enableAudioVbrEncoding = true) { using var cancellationTokenSource = new CancellationTokenSource(); var streamingRequest = new StreamingRequestDto @@ -1017,7 +1017,7 @@ public class DynamicHlsController : BaseJellyfinApiController VideoStreamIndex = videoStreamIndex, Context = context ?? EncodingContext.Streaming, StreamOptions = streamOptions, - EnableAudioVbrEncoding = enableAudioVbrEncoding ?? true + EnableAudioVbrEncoding = enableAudioVbrEncoding }; return await GetVariantPlaylistInternal(streamingRequest, cancellationTokenSource) @@ -1145,7 +1145,7 @@ public class DynamicHlsController : BaseJellyfinApiController [FromQuery] int? videoStreamIndex, [FromQuery] EncodingContext? context, [FromQuery] Dictionary streamOptions, - [FromQuery] bool? enableAudioVbrEncoding) + [FromQuery] bool enableAudioVbrEncoding = true) { var streamingRequest = new VideoRequestDto { @@ -1201,7 +1201,7 @@ public class DynamicHlsController : BaseJellyfinApiController VideoStreamIndex = videoStreamIndex, Context = context ?? EncodingContext.Streaming, StreamOptions = streamOptions, - EnableAudioVbrEncoding = enableAudioVbrEncoding ?? true + EnableAudioVbrEncoding = enableAudioVbrEncoding }; return await GetDynamicSegment(streamingRequest, segmentId) @@ -1327,7 +1327,7 @@ public class DynamicHlsController : BaseJellyfinApiController [FromQuery] int? videoStreamIndex, [FromQuery] EncodingContext? context, [FromQuery] Dictionary streamOptions, - [FromQuery] bool? enableAudioVbrEncoding) + [FromQuery] bool enableAudioVbrEncoding = true) { var streamingRequest = new StreamingRequestDto { @@ -1381,7 +1381,7 @@ public class DynamicHlsController : BaseJellyfinApiController VideoStreamIndex = videoStreamIndex, Context = context ?? EncodingContext.Streaming, StreamOptions = streamOptions, - EnableAudioVbrEncoding = enableAudioVbrEncoding ?? true + EnableAudioVbrEncoding = enableAudioVbrEncoding }; return await GetDynamicSegment(streamingRequest, segmentId) diff --git a/Jellyfin.Api/Controllers/UniversalAudioController.cs b/Jellyfin.Api/Controllers/UniversalAudioController.cs index c858c17ba..908794512 100644 --- a/Jellyfin.Api/Controllers/UniversalAudioController.cs +++ b/Jellyfin.Api/Controllers/UniversalAudioController.cs @@ -112,7 +112,7 @@ public class UniversalAudioController : BaseJellyfinApiController [FromQuery] int? maxAudioSampleRate, [FromQuery] int? maxAudioBitDepth, [FromQuery] bool? enableRemoteMedia, - [FromQuery] bool? enableAudioVbrEncoding, + [FromQuery] bool enableAudioVbrEncoding = true, [FromQuery] bool breakOnNonKeyFrames = false, [FromQuery] bool enableRedirection = true) { @@ -212,7 +212,7 @@ public class UniversalAudioController : BaseJellyfinApiController Context = EncodingContext.Static, StreamOptions = new Dictionary(), EnableAdaptiveBitrateStreaming = true, - EnableAudioVbrEncoding = enableAudioVbrEncoding ?? true + EnableAudioVbrEncoding = enableAudioVbrEncoding }; return await _dynamicHlsHelper.GetMasterHlsPlaylist(TranscodingJobType.Hls, dynamicHlsRequestDto, true) diff --git a/Jellyfin.Api/Controllers/VideosController.cs b/Jellyfin.Api/Controllers/VideosController.cs index f6050bdf7..7f9608378 100644 --- a/Jellyfin.Api/Controllers/VideosController.cs +++ b/Jellyfin.Api/Controllers/VideosController.cs @@ -365,7 +365,7 @@ public class VideosController : BaseJellyfinApiController [FromQuery] int? videoStreamIndex, [FromQuery] EncodingContext? context, [FromQuery] Dictionary streamOptions, - [FromQuery] bool? enableAudioVbrEncoding) + [FromQuery] bool enableAudioVbrEncoding = true) { var isHeadRequest = Request.Method == System.Net.WebRequestMethods.Http.Head; // CTS lifecycle is managed internally. @@ -422,7 +422,7 @@ public class VideosController : BaseJellyfinApiController VideoStreamIndex = videoStreamIndex, Context = context ?? EncodingContext.Streaming, StreamOptions = streamOptions, - EnableAudioVbrEncoding = enableAudioVbrEncoding ?? true + EnableAudioVbrEncoding = enableAudioVbrEncoding }; var state = await StreamingHelpers.GetStreamingState( @@ -606,7 +606,7 @@ public class VideosController : BaseJellyfinApiController [FromQuery] int? videoStreamIndex, [FromQuery] EncodingContext? context, [FromQuery] Dictionary streamOptions, - [FromQuery] bool? enableAudioVbrEncoding) + [FromQuery] bool enableAudioVbrEncoding = true) { return GetVideoStream( itemId, -- cgit v1.2.3 From cb7714a32e8c544cacbe11b7999cfd8932443d16 Mon Sep 17 00:00:00 2001 From: gnattu Date: Thu, 18 Jul 2024 17:49:44 +0800 Subject: Code cleanup Co-authored-by: Bond-009 --- Jellyfin.Api/Controllers/UniversalAudioController.cs | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) (limited to 'Jellyfin.Api/Controllers/UniversalAudioController.cs') diff --git a/Jellyfin.Api/Controllers/UniversalAudioController.cs b/Jellyfin.Api/Controllers/UniversalAudioController.cs index 3286105e3..4e287abcb 100644 --- a/Jellyfin.Api/Controllers/UniversalAudioController.cs +++ b/Jellyfin.Api/Controllers/UniversalAudioController.cs @@ -186,8 +186,12 @@ public class UniversalAudioController : BaseJellyfinApiController var supportedHlsContainers = new[] { "ts", "mp4" }; // fallback to mpegts if device reports some weird value unsupported by hls - var requestedSegmentContainer = Array.Exists(supportedHlsContainers, element => element == transcodingContainer) ? transcodingContainer : "ts"; - var segmentContainer = Array.Exists(supportedHlsContainers, element => element == mediaSource.TranscodingContainer) ? mediaSource.TranscodingContainer : requestedSegmentContainer; + var requestedSegmentContainer = Array.Exists( + supportedHlsContainers, + element => string.Equals(element, transcodingContainer, StringComparison.OrdinalIgnoreCase)) ? transcodingContainer : "ts"; + var segmentContainer = Array.Exists( + supportedHlsContainers, + element => string.Equals(element, mediaSource.TranscodingContainer, StringComparison.OrdinalIgnoreCase)) ? mediaSource.TranscodingContainer : requestedSegmentContainer; var dynamicHlsRequestDto = new HlsAudioRequestDto { Id = itemId, -- cgit v1.2.3 From 59c18a7454074b3c2b7c67e0dc4071e3ffc5d704 Mon Sep 17 00:00:00 2001 From: gnattu Date: Thu, 18 Jul 2024 18:49:04 +0800 Subject: Remove space Signed-off-by: gnattu --- Jellyfin.Api/Controllers/UniversalAudioController.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Jellyfin.Api/Controllers/UniversalAudioController.cs') diff --git a/Jellyfin.Api/Controllers/UniversalAudioController.cs b/Jellyfin.Api/Controllers/UniversalAudioController.cs index 4e287abcb..07c22f68e 100644 --- a/Jellyfin.Api/Controllers/UniversalAudioController.cs +++ b/Jellyfin.Api/Controllers/UniversalAudioController.cs @@ -187,7 +187,7 @@ public class UniversalAudioController : BaseJellyfinApiController // fallback to mpegts if device reports some weird value unsupported by hls var requestedSegmentContainer = Array.Exists( - supportedHlsContainers, + supportedHlsContainers, element => string.Equals(element, transcodingContainer, StringComparison.OrdinalIgnoreCase)) ? transcodingContainer : "ts"; var segmentContainer = Array.Exists( supportedHlsContainers, -- cgit v1.2.3