update timeshifting

pull/702/head
Luke Pulverenti 8 years ago
parent 2023855a1f
commit 05edb9f4bd

@ -15,6 +15,7 @@ using System.Linq;
using System.Threading;
using System.Threading.Tasks;
using CommonIO;
using MediaBrowser.Model.Dto;
namespace MediaBrowser.Api
{
@ -187,7 +188,8 @@ namespace MediaBrowser.Api
CancellationTokenSource = cancellationTokenSource,
Id = transcodingJobId,
PlaySessionId = playSessionId,
LiveStreamId = liveStreamId
LiveStreamId = liveStreamId,
MediaSource = state.MediaSource
};
_activeTranscodingJobs.Add(job);
@ -281,6 +283,14 @@ namespace MediaBrowser.Api
}
}
public TranscodingJob GetTranscodingJob(string playSessionId)
{
lock (_activeTranscodingJobs)
{
return _activeTranscodingJobs.FirstOrDefault(j => string.Equals(j.PlaySessionId, playSessionId, StringComparison.OrdinalIgnoreCase));
}
}
/// <summary>
/// Called when [transcode begin request].
/// </summary>
@ -656,6 +666,7 @@ namespace MediaBrowser.Api
/// Gets or sets the path.
/// </summary>
/// <value>The path.</value>
public MediaSourceInfo MediaSource { get; set; }
public string Path { get; set; }
/// <summary>
/// Gets or sets the type.

@ -1847,18 +1847,30 @@ namespace MediaBrowser.Api.Playback
var archivable = item as IArchivable;
state.IsInputArchive = archivable != null && archivable.IsArchive;
MediaSourceInfo mediaSource;
MediaSourceInfo mediaSource = null;
if (string.IsNullOrWhiteSpace(request.LiveStreamId))
{
var mediaSources = (await MediaSourceManager.GetPlayackMediaSources(request.Id, null, false, new[] { MediaType.Audio, MediaType.Video }, cancellationToken).ConfigureAwait(false)).ToList();
//TranscodingJob currentJob = !string.IsNullOrWhiteSpace(request.PlaySessionId) ?
// ApiEntryPoint.Instance.GetTranscodingJob(request.PlaySessionId)
// : null;
mediaSource = string.IsNullOrEmpty(request.MediaSourceId)
? mediaSources.First()
: mediaSources.FirstOrDefault(i => string.Equals(i.Id, request.MediaSourceId));
//if (currentJob != null)
//{
// mediaSource = currentJob.MediaSource;
//}
if (mediaSource == null && string.Equals(request.Id, request.MediaSourceId, StringComparison.OrdinalIgnoreCase))
if (mediaSource == null)
{
mediaSource = mediaSources.First();
var mediaSources = (await MediaSourceManager.GetPlayackMediaSources(request.Id, null, false, new[] { MediaType.Audio, MediaType.Video }, cancellationToken).ConfigureAwait(false)).ToList();
mediaSource = string.IsNullOrEmpty(request.MediaSourceId)
? mediaSources.First()
: mediaSources.FirstOrDefault(i => string.Equals(i.Id, request.MediaSourceId));
if (mediaSource == null && string.Equals(request.Id, request.MediaSourceId, StringComparison.OrdinalIgnoreCase))
{
mediaSource = mediaSources.First();
}
}
}
else

@ -104,7 +104,7 @@ namespace MediaBrowser.Api.Playback.Hls
throw;
}
var waitForSegments = state.SegmentLength >= 10 ? 2 : 3;
var waitForSegments = state.SegmentLength >= 10 ? 2 : (state.SegmentLength > 3 || !isLive ? 3 : 4);
await WaitForMinimumSegmentCount(playlist, waitForSegments, cancellationTokenSource.Token).ConfigureAwait(false);
}
}
@ -128,10 +128,9 @@ namespace MediaBrowser.Api.Playback.Hls
var audioBitrate = state.OutputAudioBitrate ?? 0;
var videoBitrate = state.OutputVideoBitrate ?? 0;
var appendBaselineStream = false;
var baselineStreamBitrate = 64000;
var playlistText = GetMasterPlaylistFileText(playlist, videoBitrate + audioBitrate, appendBaselineStream, baselineStreamBitrate);
var playlistText = GetMasterPlaylistFileText(playlist, videoBitrate + audioBitrate, baselineStreamBitrate);
job = job ?? ApiEntryPoint.Instance.OnTranscodeBeginRequest(playlist, TranscodingJobType);
@ -161,7 +160,7 @@ namespace MediaBrowser.Api.Playback.Hls
}
}
private string GetMasterPlaylistFileText(string firstPlaylist, int bitrate, bool includeBaselineStream, int baselineStreamBitrate)
private string GetMasterPlaylistFileText(string firstPlaylist, int bitrate, int baselineStreamBitrate)
{
var builder = new StringBuilder();
@ -175,14 +174,6 @@ namespace MediaBrowser.Api.Playback.Hls
var playlistUrl = "hls/" + Path.GetFileName(firstPlaylist).Replace(".m3u8", "/stream.m3u8");
builder.AppendLine(playlistUrl);
// Low bitrate stream
if (includeBaselineStream)
{
builder.AppendLine("#EXT-X-STREAM-INF:PROGRAM-ID=1,BANDWIDTH=" + baselineStreamBitrate.ToString(UsCulture));
playlistUrl = "hls/" + Path.GetFileName(firstPlaylist).Replace(".m3u8", "-low/stream.m3u8");
builder.AppendLine(playlistUrl);
}
return builder.ToString();
}

@ -68,8 +68,6 @@ namespace MediaBrowser.Api.Playback.Hls
[Api(Description = "Gets an Http live streaming segment file. Internal use only.")]
public class GetHlsVideoSegmentLegacy : VideoStreamRequest
{
// TODO: Deprecate with new iOS app
public string PlaylistId { get; set; }
/// <summary>
@ -113,7 +111,7 @@ namespace MediaBrowser.Api.Playback.Hls
var file = request.SegmentId + Path.GetExtension(Request.PathInfo);
file = Path.Combine(_config.ApplicationPaths.TranscodingTempPath, file);
var normalizedPlaylistId = request.PlaylistId.Replace("-low", string.Empty);
var normalizedPlaylistId = request.PlaylistId;
var playlistPath = Directory.EnumerateFiles(_config.ApplicationPaths.TranscodingTempPath, "*")
.FirstOrDefault(i => string.Equals(Path.GetExtension(i), ".m3u8", StringComparison.OrdinalIgnoreCase) && i.IndexOf(normalizedPlaylistId, StringComparison.OrdinalIgnoreCase) != -1);

@ -88,6 +88,10 @@ namespace MediaBrowser.Api.Playback
return 10;
}
if (!RunTimeTicks.HasValue)
{
return 10;
}
return 6;
}

@ -148,7 +148,7 @@ namespace MediaBrowser.Api.Subtitles
{
var item = (Video)_libraryManager.GetItemById(new Guid(request.Id));
var mediaSource = await _mediaSourceManager.GetMediaSource(item, request.MediaSourceId, false).ConfigureAwait(false);
var mediaSource = await _mediaSourceManager.GetMediaSource(item, request.MediaSourceId, null, false, CancellationToken.None).ConfigureAwait(false);
var builder = new StringBuilder();

@ -60,11 +60,8 @@ namespace MediaBrowser.Controller.Library
/// <summary>
/// Gets the static media source.
/// </summary>
/// <param name="item">The item.</param>
/// <param name="mediaSourceId">The media source identifier.</param>
/// <param name="enablePathSubstitution">if set to <c>true</c> [enable path substitution].</param>
/// <returns>MediaSourceInfo.</returns>
Task<MediaSourceInfo> GetMediaSource(IHasMediaSources item, string mediaSourceId, bool enablePathSubstitution);
Task<MediaSourceInfo> GetMediaSource(IHasMediaSources item, string mediaSourceId, string liveStreamId, bool enablePathSubstitution, CancellationToken cancellationToken);
/// <summary>
/// Opens the media source.

@ -827,6 +827,7 @@ namespace MediaBrowser.Dlna.PlayTo
public string DeviceId { get; set; }
public string MediaSourceId { get; set; }
public string LiveStreamId { get; set; }
public BaseItem Item { get; set; }
public MediaSourceInfo MediaSource { get; set; }
@ -910,6 +911,10 @@ namespace MediaBrowser.Dlna.PlayTo
{
request.StartPositionTicks = long.Parse(val, CultureInfo.InvariantCulture);
}
else if (i == 22)
{
request.LiveStreamId = val;
}
}
request.Item = string.IsNullOrWhiteSpace(request.ItemId)
@ -920,7 +925,7 @@ namespace MediaBrowser.Dlna.PlayTo
request.MediaSource = hasMediaSources == null
? null
: (await mediaSourceManager.GetMediaSource(hasMediaSources, request.MediaSourceId, false).ConfigureAwait(false));
: (await mediaSourceManager.GetMediaSource(hasMediaSources, request.MediaSourceId, request.LiveStreamId, false, CancellationToken.None).ConfigureAwait(false));
return request;
}

@ -221,8 +221,28 @@ namespace MediaBrowser.Server.Implementations.Library
}
}
public async Task<MediaSourceInfo> GetMediaSource(IHasMediaSources item, string mediaSourceId, bool enablePathSubstitution)
public async Task<MediaSourceInfo> GetMediaSource(IHasMediaSources item, string mediaSourceId, string liveStreamId, bool enablePathSubstitution, CancellationToken cancellationToken)
{
if (!string.IsNullOrWhiteSpace(liveStreamId))
{
return await GetLiveStream(liveStreamId, cancellationToken).ConfigureAwait(false);
}
//await _liveStreamSemaphore.WaitAsync(cancellationToken).ConfigureAwait(false);
//try
//{
// var stream = _openStreams.Values.FirstOrDefault(i => string.Equals(i.MediaSource.Id, mediaSourceId, StringComparison.OrdinalIgnoreCase));
// if (stream != null)
// {
// return stream.MediaSource;
// }
//}
//finally
//{
// _liveStreamSemaphore.Release();
//}
var sources = await GetPlayackMediaSources(item.Id.ToString("N"), null, enablePathSubstitution, new[] { MediaType.Audio, MediaType.Video },
CancellationToken.None).ConfigureAwait(false);

@ -763,7 +763,7 @@ namespace MediaBrowser.Server.Implementations.LiveTv.EmbyTV
throw new ApplicationException("Tuner not found.");
}
private async Task<Tuple<MediaSourceInfo, ITunerHost, SemaphoreSlim>> GetChannelStreamInternal(string channelId, string streamId, CancellationToken cancellationToken)
private async Task<Tuple<MediaSourceInfo, ITunerHost, SemaphoreSlim>> GetChannelStreamInternal(string channelId, CancellationToken cancellationToken)
{
_logger.Info("Streaming Channel " + channelId);
@ -771,7 +771,7 @@ namespace MediaBrowser.Server.Implementations.LiveTv.EmbyTV
{
try
{
var result = await hostInstance.GetChannelStream(channelId, streamId, cancellationToken).ConfigureAwait(false);
var result = await hostInstance.GetChannelStream(channelId, null, cancellationToken).ConfigureAwait(false);
return new Tuple<MediaSourceInfo, ITunerHost, SemaphoreSlim>(result.Item1, hostInstance, result.Item2);
}
@ -994,7 +994,7 @@ namespace MediaBrowser.Server.Implementations.LiveTv.EmbyTV
try
{
var result = await GetChannelStreamInternal(timer.ChannelId, null, CancellationToken.None).ConfigureAwait(false);
var result = await GetChannelStreamInternal(timer.ChannelId, CancellationToken.None).ConfigureAwait(false);
isResourceOpen = true;
semaphore = result.Item3;
var mediaStreamInfo = result.Item1;

@ -223,8 +223,7 @@ namespace MediaBrowser.Server.Implementations.LiveTv.TunerHosts
}
}
var stream =
await GetChannelStream(host, channelId, streamId, cancellationToken).ConfigureAwait(false);
var stream = await GetChannelStream(host, channelId, streamId, cancellationToken).ConfigureAwait(false);
if (EnableMediaProbing)
{

@ -319,18 +319,21 @@ namespace MediaBrowser.Server.Implementations.LiveTv.TunerHosts.HdHomerun
videoBitrate = 1000000;
}
if (string.IsNullOrWhiteSpace(videoCodec))
var channels = await GetChannels(info, true, CancellationToken.None).ConfigureAwait(false);
var channel = channels.FirstOrDefault(i => string.Equals(i.Number, channelId, StringComparison.OrdinalIgnoreCase));
if (channel != null)
{
var channels = await GetChannels(info, true, CancellationToken.None).ConfigureAwait(false);
var channel = channels.FirstOrDefault(i => string.Equals(i.Number, channelId, StringComparison.OrdinalIgnoreCase));
if (channel != null)
if (string.IsNullOrWhiteSpace(videoCodec))
{
videoCodec = channel.VideoCodec;
audioCodec = channel.AudioCodec;
}
audioCodec = channel.AudioCodec;
if (!videoBitrate.HasValue)
{
videoBitrate = (channel.IsHD ?? true) ? 15000000 : 2000000;
audioBitrate = (channel.IsHD ?? true) ? 448000 : 192000;
}
audioBitrate = (channel.IsHD ?? true) ? 448000 : 192000;
}
// normalize
@ -380,7 +383,7 @@ namespace MediaBrowser.Server.Implementations.LiveTv.TunerHosts.HdHomerun
BitRate = audioBitrate
}
},
RequiresOpening = false,
RequiresOpening = true,
RequiresClosing = false,
BufferMs = 0,
Container = "ts",

@ -307,9 +307,9 @@ namespace MediaBrowser.Server.Implementations.Session
}
}
private Task<MediaSourceInfo> GetMediaSource(IHasMediaSources item, string mediaSourceId)
private Task<MediaSourceInfo> GetMediaSource(IHasMediaSources item, string mediaSourceId, string liveStreamId)
{
return _mediaSourceManager.GetMediaSource(item, mediaSourceId, false);
return _mediaSourceManager.GetMediaSource(item, mediaSourceId, liveStreamId, false, CancellationToken.None);
}
/// <summary>
@ -337,7 +337,7 @@ namespace MediaBrowser.Server.Implementations.Session
var hasMediaSources = libraryItem as IHasMediaSources;
if (hasMediaSources != null)
{
mediaSource = await GetMediaSource(hasMediaSources, info.MediaSourceId).ConfigureAwait(false);
mediaSource = await GetMediaSource(hasMediaSources, info.MediaSourceId, info.LiveStreamId).ConfigureAwait(false);
if (mediaSource != null)
{
@ -792,7 +792,7 @@ namespace MediaBrowser.Server.Implementations.Session
var hasMediaSources = libraryItem as IHasMediaSources;
if (hasMediaSources != null)
{
mediaSource = await GetMediaSource(hasMediaSources, info.MediaSourceId).ConfigureAwait(false);
mediaSource = await GetMediaSource(hasMediaSources, info.MediaSourceId, info.LiveStreamId).ConfigureAwait(false);
}
info.Item = GetItemInfo(libraryItem, libraryItem, mediaSource);

Loading…
Cancel
Save