diff --git a/MediaBrowser.Api/ApiEntryPoint.cs b/MediaBrowser.Api/ApiEntryPoint.cs index a6958b95d3..9f4ad58937 100644 --- a/MediaBrowser.Api/ApiEntryPoint.cs +++ b/MediaBrowser.Api/ApiEntryPoint.cs @@ -187,7 +187,7 @@ namespace MediaBrowser.Api if (!string.IsNullOrWhiteSpace(deviceId)) { - var audioCodec = state.ActualOutputVideoCodec; + var audioCodec = state.ActualOutputAudioCodec; var videoCodec = state.ActualOutputVideoCodec; _sessionManager.ReportTranscodingInfo(deviceId, new TranscodingInfo diff --git a/MediaBrowser.Api/Playback/BaseStreamingService.cs b/MediaBrowser.Api/Playback/BaseStreamingService.cs index 5a4cdaaa93..34c5e5f7c8 100644 --- a/MediaBrowser.Api/Playback/BaseStreamingService.cs +++ b/MediaBrowser.Api/Playback/BaseStreamingService.cs @@ -1513,6 +1513,10 @@ namespace MediaBrowser.Api.Playback { request.StreamId = val; } + else if (i == 22) + { + request.LiveStreamId = val; + } } } diff --git a/MediaBrowser.Controller/LiveTv/LiveTvChannel.cs b/MediaBrowser.Controller/LiveTv/LiveTvChannel.cs index 1e13d8f3f4..cb10003ed8 100644 --- a/MediaBrowser.Controller/LiveTv/LiveTvChannel.cs +++ b/MediaBrowser.Controller/LiveTv/LiveTvChannel.cs @@ -82,6 +82,15 @@ namespace MediaBrowser.Controller.LiveTv /// null if [has image] contains no value, true if [has image]; otherwise, false. public bool? HasProviderImage { get; set; } + public override LocationType LocationType + { + get + { + // TODO: This should be removed + return LocationType.Remote; + } + } + protected override string CreateSortName() { double number = 0; diff --git a/MediaBrowser.Model/ApiClient/IApiClient.cs b/MediaBrowser.Model/ApiClient/IApiClient.cs index 19d6acf339..58af016150 100644 --- a/MediaBrowser.Model/ApiClient/IApiClient.cs +++ b/MediaBrowser.Model/ApiClient/IApiClient.cs @@ -1486,5 +1486,12 @@ namespace MediaBrowser.Model.ApiClient /// The query. /// Task<List<RecommendationDto>>. Task> GetMovieRecommendations(MovieRecommendationQuery query); + /// + /// Opens the live stream. + /// + /// The request. + /// The cancellation token. + /// Task<LiveStreamResponse>. + Task OpenLiveStream(LiveStreamRequest request, CancellationToken cancellationToken); } } \ No newline at end of file diff --git a/MediaBrowser.Model/Dlna/StreamInfo.cs b/MediaBrowser.Model/Dlna/StreamInfo.cs index 60615d1da9..dc24627960 100644 --- a/MediaBrowser.Model/Dlna/StreamInfo.cs +++ b/MediaBrowser.Model/Dlna/StreamInfo.cs @@ -210,6 +210,9 @@ namespace MediaBrowser.Model.Dlna list.Add(new NameValuePair("StreamId", streamId ?? string.Empty)); list.Add(new NameValuePair("api_key", accessToken ?? string.Empty)); + string liveStreamId = item.MediaSource == null ? null : item.MediaSource.LiveStreamId; + list.Add(new NameValuePair("LiveStreamId", liveStreamId ?? string.Empty)); + return list; } diff --git a/MediaBrowser.Model/MediaInfo/LiveStreamRequest.cs b/MediaBrowser.Model/MediaInfo/LiveStreamRequest.cs index 8078219d82..563006a4df 100644 --- a/MediaBrowser.Model/MediaInfo/LiveStreamRequest.cs +++ b/MediaBrowser.Model/MediaInfo/LiveStreamRequest.cs @@ -12,5 +12,24 @@ namespace MediaBrowser.Model.MediaInfo public int? SubtitleStreamIndex { get; set; } public string ItemId { get; set; } public DeviceProfile DeviceProfile { get; set; } + + public LiveStreamRequest() + { + + } + + public LiveStreamRequest(AudioOptions options) + { + MaxStreamingBitrate = options.MaxBitrate; + ItemId = options.ItemId; + DeviceProfile = options.Profile; + + VideoOptions videoOptions = options as VideoOptions; + if (videoOptions != null) + { + AudioStreamIndex = videoOptions.AudioStreamIndex; + SubtitleStreamIndex = videoOptions.SubtitleStreamIndex; + } + } } } diff --git a/MediaBrowser.Model/Session/PlaybackProgressInfo.cs b/MediaBrowser.Model/Session/PlaybackProgressInfo.cs index f04dea1eac..a029df4a93 100644 --- a/MediaBrowser.Model/Session/PlaybackProgressInfo.cs +++ b/MediaBrowser.Model/Session/PlaybackProgressInfo.cs @@ -78,5 +78,10 @@ namespace MediaBrowser.Model.Session /// /// The play method. public PlayMethod PlayMethod { get; set; } + /// + /// Gets or sets the live stream identifier. + /// + /// The live stream identifier. + public string LiveStreamId { get; set; } } } \ No newline at end of file diff --git a/MediaBrowser.Model/Session/PlaybackStopInfo.cs b/MediaBrowser.Model/Session/PlaybackStopInfo.cs index 38025f1832..a3bdc9a960 100644 --- a/MediaBrowser.Model/Session/PlaybackStopInfo.cs +++ b/MediaBrowser.Model/Session/PlaybackStopInfo.cs @@ -36,5 +36,10 @@ namespace MediaBrowser.Model.Session /// /// The position ticks. public long? PositionTicks { get; set; } + /// + /// Gets or sets the live stream identifier. + /// + /// The live stream identifier. + public string LiveStreamId { get; set; } } } \ No newline at end of file diff --git a/MediaBrowser.Server.Implementations/LiveTv/LiveTvManager.cs b/MediaBrowser.Server.Implementations/LiveTv/LiveTvManager.cs index 86b31e0e5d..b30db60927 100644 --- a/MediaBrowser.Server.Implementations/LiveTv/LiveTvManager.cs +++ b/MediaBrowser.Server.Implementations/LiveTv/LiveTvManager.cs @@ -356,7 +356,11 @@ namespace MediaBrowser.Server.Implementations.LiveTv _logger.Info("Opening channel stream from {0}, external channel Id: {1}", service.Name, channel.ExternalId); info = await service.GetChannelStream(channel.ExternalId, null, cancellationToken).ConfigureAwait(false); info.RequiresClosing = true; - info.LiveStreamId = info.Id; + + if (info.RequiresClosing) + { + info.LiveStreamId = info.Id; + } } else { @@ -367,7 +371,11 @@ namespace MediaBrowser.Server.Implementations.LiveTv _logger.Info("Opening recording stream from {0}, external recording Id: {1}", service.Name, recording.RecordingInfo.Id); info = await service.GetRecordingStream(recording.RecordingInfo.Id, null, cancellationToken).ConfigureAwait(false); info.RequiresClosing = true; - info.LiveStreamId = info.Id; + + if (info.RequiresClosing) + { + info.LiveStreamId = info.Id; + } } _logger.Info("Live stream info: {0}", _jsonSerializer.SerializeToString(info)); diff --git a/MediaBrowser.Server.Implementations/Session/SessionManager.cs b/MediaBrowser.Server.Implementations/Session/SessionManager.cs index 16fc420639..cc5aef54aa 100644 --- a/MediaBrowser.Server.Implementations/Session/SessionManager.cs +++ b/MediaBrowser.Server.Implementations/Session/SessionManager.cs @@ -679,6 +679,18 @@ namespace MediaBrowser.Server.Implementations.Session } } + if (!string.IsNullOrWhiteSpace(info.LiveStreamId)) + { + try + { + await _mediaSourceManager.PingLiveStream(info.LiveStreamId, CancellationToken.None).ConfigureAwait(false); + } + catch (Exception ex) + { + _logger.ErrorException("Error closing live stream", ex); + } + } + EventHelper.FireEventIfNotNull(PlaybackProgress, this, new PlaybackProgressEventArgs { Item = libraryItem, @@ -769,6 +781,18 @@ namespace MediaBrowser.Server.Implementations.Session } } + if (!string.IsNullOrWhiteSpace(info.LiveStreamId)) + { + try + { + await _mediaSourceManager.CloseLiveStream(info.LiveStreamId, CancellationToken.None).ConfigureAwait(false); + } + catch (Exception ex) + { + _logger.ErrorException("Error closing live stream", ex); + } + } + EventHelper.QueueEventIfNotNull(PlaybackStopped, this, new PlaybackStopEventArgs { Item = libraryItem, diff --git a/Nuget/MediaBrowser.Common.Internal.nuspec b/Nuget/MediaBrowser.Common.Internal.nuspec index e1659bfb28..ee3bdd2b6b 100644 --- a/Nuget/MediaBrowser.Common.Internal.nuspec +++ b/Nuget/MediaBrowser.Common.Internal.nuspec @@ -2,7 +2,7 @@ MediaBrowser.Common.Internal - 3.0.603 + 3.0.606 MediaBrowser.Common.Internal Luke ebr,Luke,scottisafool @@ -12,7 +12,7 @@ Contains common components shared by Emby Theater and Emby Server. Not intended for plugin developer consumption. Copyright © Emby 2013 - + diff --git a/Nuget/MediaBrowser.Common.nuspec b/Nuget/MediaBrowser.Common.nuspec index 294bc519eb..a8f3ea1f38 100644 --- a/Nuget/MediaBrowser.Common.nuspec +++ b/Nuget/MediaBrowser.Common.nuspec @@ -2,7 +2,7 @@ MediaBrowser.Common - 3.0.603 + 3.0.606 MediaBrowser.Common Emby Team ebr,Luke,scottisafool diff --git a/Nuget/MediaBrowser.Model.Signed.nuspec b/Nuget/MediaBrowser.Model.Signed.nuspec index bcbd1d5bea..7bd4a090dd 100644 --- a/Nuget/MediaBrowser.Model.Signed.nuspec +++ b/Nuget/MediaBrowser.Model.Signed.nuspec @@ -2,7 +2,7 @@ MediaBrowser.Model.Signed - 3.0.603 + 3.0.606 MediaBrowser.Model - Signed Edition Emby Team ebr,Luke,scottisafool diff --git a/Nuget/MediaBrowser.Server.Core.nuspec b/Nuget/MediaBrowser.Server.Core.nuspec index ee3925db5b..3f39ace9dd 100644 --- a/Nuget/MediaBrowser.Server.Core.nuspec +++ b/Nuget/MediaBrowser.Server.Core.nuspec @@ -2,7 +2,7 @@ MediaBrowser.Server.Core - 3.0.603 + 3.0.606 Media Browser.Server.Core Emby Team ebr,Luke,scottisafool @@ -12,7 +12,7 @@ Contains core components required to build plugins for Emby Server. Copyright © Emby 2013 - +