From 24f53ef13e883e94e189eadcc90cca108d3587b5 Mon Sep 17 00:00:00 2001 From: Duncan Tourolle Date: Sun, 3 May 2026 10:40:11 +0200 Subject: [PATCH] Add support for Tizen via transcoding --- .../Controllers/StreamProxyController.cs | 5 +++-- .../Services/MediaSourceFactory.cs | 6 +++--- .../Services/StreamProxyService.cs | 15 --------------- 3 files changed, 6 insertions(+), 20 deletions(-) diff --git a/Jellyfin.Plugin.SRFPlay/Controllers/StreamProxyController.cs b/Jellyfin.Plugin.SRFPlay/Controllers/StreamProxyController.cs index fc7fed0..db5bceb 100644 --- a/Jellyfin.Plugin.SRFPlay/Controllers/StreamProxyController.cs +++ b/Jellyfin.Plugin.SRFPlay/Controllers/StreamProxyController.cs @@ -160,7 +160,8 @@ public class StreamProxyController : ControllerBase AddManifestCacheHeaders(actualItemId); _logger.LogDebug("Returning master manifest for item {ItemId} ({Length} bytes)", itemId, manifestContent.Length); - return Content(manifestContent, "application/vnd.apple.mpegurl; charset=utf-8"); + // Use application/x-mpegURL for broader compatibility (Samsung AVPlay requires it) + return Content(manifestContent, "application/x-mpegURL; charset=utf-8"); } catch (Exception ex) { @@ -231,7 +232,7 @@ public class StreamProxyController : ControllerBase AddManifestCacheHeaders(actualItemId, isVariantManifest: true); _logger.LogDebug("Returning variant manifest for item {ItemId} ({Length} bytes)", itemId, rewrittenContent.Length); - return Content(rewrittenContent, "application/vnd.apple.mpegurl; charset=utf-8"); + return Content(rewrittenContent, "application/x-mpegURL; charset=utf-8"); } catch (Exception ex) { diff --git a/Jellyfin.Plugin.SRFPlay/Services/MediaSourceFactory.cs b/Jellyfin.Plugin.SRFPlay/Services/MediaSourceFactory.cs index 51a57c8..c307b90 100644 --- a/Jellyfin.Plugin.SRFPlay/Services/MediaSourceFactory.cs +++ b/Jellyfin.Plugin.SRFPlay/Services/MediaSourceFactory.cs @@ -91,15 +91,15 @@ public class MediaSourceFactory : IMediaSourceFactory Protocol = MediaProtocol.Http, // Use "hls" to trigger hls.js player in web client Container = "hls", - SupportsDirectStream = true, + SupportsDirectStream = false, SupportsDirectPlay = true, - SupportsTranscoding = false, + SupportsTranscoding = true, IsRemote = true, Type = MediaSourceType.Default, RunTimeTicks = chapter.Duration > 0 ? TimeSpan.FromMilliseconds(chapter.Duration).Ticks : null, VideoType = VideoType.VideoFile, IsInfiniteStream = isLiveStream, - // Don't use RequiresOpening - it forces Jellyfin to transcode which breaks token auth + // RequiresOpening = false: proxy handles auth directly, no need for Jellyfin to open the stream RequiresOpening = false, RequiresClosing = false, // Disable probing - we provide stream info directly diff --git a/Jellyfin.Plugin.SRFPlay/Services/StreamProxyService.cs b/Jellyfin.Plugin.SRFPlay/Services/StreamProxyService.cs index fc00cd7..f8c50c4 100644 --- a/Jellyfin.Plugin.SRFPlay/Services/StreamProxyService.cs +++ b/Jellyfin.Plugin.SRFPlay/Services/StreamProxyService.cs @@ -656,21 +656,6 @@ public class StreamProxyService : IStreamProxyService // Rewrite the manifest to replace Akamai URLs with proxy URLs var rewrittenContent = RewriteManifestUrls(manifestContent, authenticatedUrl, baseProxyUrl); - // For live streams, inject #EXT-X-START to tell the player to start near the live edge - // Without this, players may start at the beginning of the sliding window and stutter - // as old segments get rotated out by the CDN - if (_streamMappings.TryGetValue(itemId, out var streamInfoForManifest) && streamInfoForManifest.IsLiveStream) - { - if (!rewrittenContent.Contains("#EXT-X-START", StringComparison.Ordinal)) - { - rewrittenContent = rewrittenContent.Replace( - "#EXTM3U", - "#EXTM3U\n#EXT-X-START:TIME-OFFSET=-6,PRECISE=NO", - StringComparison.Ordinal); - _logger.LogDebug("Injected #EXT-X-START tag for live stream {ItemId}", itemId); - } - } - _logger.LogDebug("Rewritten manifest for item {ItemId} ({Length} bytes):\n{Content}", itemId, rewrittenContent.Length, rewrittenContent); return rewrittenContent; }