示例#1
0
        public async Task <object> Post(OpenMediaSource request)
        {
            var authInfo = AuthorizationContext.GetAuthorizationInfo(Request);

            var result = await _mediaSourceManager.OpenLiveStream(request, false, CancellationToken.None).ConfigureAwait(false);

            var profile = request.DeviceProfile;

            if (profile == null)
            {
                var caps = _deviceManager.GetCapabilities(authInfo.DeviceId);
                if (caps != null)
                {
                    profile = caps.DeviceProfile;
                }
            }

            if (profile != null)
            {
                var item = _libraryManager.GetItemById(request.ItemId);

                SetDeviceSpecificData(item, result.MediaSource, profile, authInfo, request.MaxStreamingBitrate,
                                      request.StartTimeTicks ?? 0, result.MediaSource.Id, request.AudioStreamIndex,
                                      request.SubtitleStreamIndex, request.PlaySessionId);
            }
            else
            {
                if (!string.IsNullOrWhiteSpace(result.MediaSource.TranscodingUrl))
                {
                    result.MediaSource.TranscodingUrl += "&LiveStreamId=" + result.MediaSource.LiveStreamId;
                }
            }

            return(ToOptimizedResult(result));
        }
示例#2
0
        private async Task <LiveStreamResponse> OpenMediaSource(OpenMediaSource request)
        {
            var authInfo = _authContext.GetAuthorizationInfo(Request);

            var result = await _mediaSourceManager.OpenLiveStream(request, CancellationToken.None).ConfigureAwait(false);

            var profile = request.DeviceProfile;

            if (profile == null)
            {
                var caps = _deviceManager.GetCapabilities(authInfo.DeviceId);
                if (caps != null)
                {
                    profile = caps.DeviceProfile;
                }
            }

            if (profile != null)
            {
                var item = _libraryManager.GetItemById(request.ItemId);

                SetDeviceSpecificData(item, result.MediaSource, profile, authInfo, request.MaxStreamingBitrate,
                                      request.StartTimeTicks ?? 0, result.MediaSource.Id, request.AudioStreamIndex,
                                      request.SubtitleStreamIndex, request.MaxAudioChannels, request.PlaySessionId, request.UserId, request.EnableDirectPlay, request.ForceDirectPlayRemoteMediaSource, request.EnableDirectStream, true, true, true);
            }
            else
            {
                if (!string.IsNullOrWhiteSpace(result.MediaSource.TranscodingUrl))
                {
                    result.MediaSource.TranscodingUrl += "&LiveStreamId=" + result.MediaSource.LiveStreamId;
                }
            }

            return(result);
        }
示例#3
0
        public DeviceProfile GetDeviceProfile(SyncTarget target, string profile, string quality)
        {
            var caps = _deviceManager.GetCapabilities(target.Id);

            var deviceProfile = caps == null || caps.DeviceProfile == null ? new DeviceProfile() : caps.DeviceProfile;

            deviceProfile.MaxStaticBitrate = SyncHelper.AdjustBitrate(deviceProfile.MaxStaticBitrate, quality);

            return(deviceProfile);
        }
示例#4
0
        private static void ApplyDeviceProfileSettings(StreamState state, IDlnaManager dlnaManager, IDeviceManager deviceManager, HttpRequest request, string?deviceProfileId, bool? @static)
        {
            if (!string.IsNullOrWhiteSpace(deviceProfileId))
            {
                state.DeviceProfile = dlnaManager.GetProfile(deviceProfileId);

                if (state.DeviceProfile == null)
                {
                    var caps = deviceManager.GetCapabilities(deviceProfileId);
                    state.DeviceProfile = caps == null?dlnaManager.GetProfile(request.Headers) : caps.DeviceProfile;
                }
            }

            var profile = state.DeviceProfile;

            if (profile == null)
            {
                // Don't use settings from the default profile.
                // Only use a specific profile if it was requested.
                return;
            }

            var audioCodec = state.ActualOutputAudioCodec;
            var videoCodec = state.ActualOutputVideoCodec;

            var mediaProfile = !state.IsVideoRequest
                ? profile.GetAudioMediaProfile(state.OutputContainer, audioCodec, state.OutputAudioChannels, state.OutputAudioBitrate, state.OutputAudioSampleRate, state.OutputAudioBitDepth)
                : profile.GetVideoMediaProfile(
                state.OutputContainer,
                audioCodec,
                videoCodec,
                state.OutputWidth,
                state.OutputHeight,
                state.TargetVideoBitDepth,
                state.OutputVideoBitrate,
                state.TargetVideoProfile,
                state.TargetVideoLevel,
                state.TargetFramerate,
                state.TargetPacketLength,
                state.TargetTimestamp,
                state.IsTargetAnamorphic,
                state.IsTargetInterlaced,
                state.TargetRefFrames,
                state.TargetVideoStreamCount,
                state.TargetAudioStreamCount,
                state.TargetVideoCodecTag,
                state.IsTargetAVC);

            if (mediaProfile != null)
            {
                state.MimeType = mediaProfile.MimeType;
            }

            if (!(@static.HasValue && @static.Value))
            {
                var transcodingProfile = !state.IsVideoRequest ? profile.GetAudioTranscodingProfile(state.OutputContainer, audioCodec) : profile.GetVideoTranscodingProfile(state.OutputContainer, audioCodec, videoCodec);

                if (transcodingProfile != null)
                {
                    state.EstimateContentLength = transcodingProfile.EstimateContentLength;
                    // state.EnableMpegtsM2TsMode = transcodingProfile.EnableMpegtsM2TsMode;
                    state.TranscodeSeekInfo = transcodingProfile.TranscodeSeekInfo;

                    if (state.VideoRequest != null)
                    {
                        state.VideoRequest.CopyTimestamps            = transcodingProfile.CopyTimestamps;
                        state.VideoRequest.EnableSubtitlesInManifest = transcodingProfile.EnableSubtitlesInManifest;
                    }
                }
            }
        }
示例#5
0
        public async Task <ActionResult <PlaybackInfoResponse> > GetPostedPlaybackInfo(
            [FromRoute, Required] Guid itemId,
            [FromQuery] Guid?userId,
            [FromQuery] int?maxStreamingBitrate,
            [FromQuery] long?startTimeTicks,
            [FromQuery] int?audioStreamIndex,
            [FromQuery] int?subtitleStreamIndex,
            [FromQuery] int?maxAudioChannels,
            [FromQuery] string?mediaSourceId,
            [FromQuery] string?liveStreamId,
            [FromQuery] bool?autoOpenLiveStream,
            [FromQuery] bool?enableDirectPlay,
            [FromQuery] bool?enableDirectStream,
            [FromQuery] bool?enableTranscoding,
            [FromQuery] bool?allowVideoStreamCopy,
            [FromQuery] bool?allowAudioStreamCopy,
            [FromBody(EmptyBodyBehavior = EmptyBodyBehavior.Allow)] PlaybackInfoDto?playbackInfoDto)
        {
            var authInfo = _authContext.GetAuthorizationInfo(Request);

            var profile = playbackInfoDto?.DeviceProfile;

            _logger.LogInformation("GetPostedPlaybackInfo profile: {@Profile}", profile);

            if (profile == null)
            {
                var caps = _deviceManager.GetCapabilities(authInfo.DeviceId);
                if (caps != null)
                {
                    profile = caps.DeviceProfile;
                }
            }

            // Copy params from posted body
            // TODO clean up when breaking API compatibility.
            userId ??= playbackInfoDto?.UserId;
            maxStreamingBitrate ??= playbackInfoDto?.MaxStreamingBitrate;
            startTimeTicks ??= playbackInfoDto?.StartTimeTicks;
            audioStreamIndex ??= playbackInfoDto?.AudioStreamIndex;
            subtitleStreamIndex ??= playbackInfoDto?.SubtitleStreamIndex;
            maxAudioChannels ??= playbackInfoDto?.MaxAudioChannels;
            mediaSourceId ??= playbackInfoDto?.MediaSourceId;
            liveStreamId ??= playbackInfoDto?.LiveStreamId;
            autoOpenLiveStream ??= playbackInfoDto?.AutoOpenLiveStream ?? false;
            enableDirectPlay ??= playbackInfoDto?.EnableDirectPlay ?? true;
            enableDirectStream ??= playbackInfoDto?.EnableDirectStream ?? true;
            enableTranscoding ??= playbackInfoDto?.EnableTranscoding ?? true;
            allowVideoStreamCopy ??= playbackInfoDto?.AllowVideoStreamCopy ?? true;
            allowAudioStreamCopy ??= playbackInfoDto?.AllowAudioStreamCopy ?? true;

            var info = await _mediaInfoHelper.GetPlaybackInfo(
                itemId,
                userId,
                mediaSourceId,
                liveStreamId)
                       .ConfigureAwait(false);

            if (profile != null)
            {
                // set device specific data
                var item = _libraryManager.GetItemById(itemId);

                foreach (var mediaSource in info.MediaSources)
                {
                    _mediaInfoHelper.SetDeviceSpecificData(
                        item,
                        mediaSource,
                        profile,
                        authInfo,
                        maxStreamingBitrate ?? profile.MaxStreamingBitrate,
                        startTimeTicks ?? 0,
                        mediaSourceId ?? string.Empty,
                        audioStreamIndex,
                        subtitleStreamIndex,
                        maxAudioChannels,
                        info !.PlaySessionId !,
                        userId ?? Guid.Empty,
                        enableDirectPlay.Value,
                        enableDirectStream.Value,
                        enableTranscoding.Value,
                        allowVideoStreamCopy.Value,
                        allowAudioStreamCopy.Value,
                        Request.HttpContext.GetNormalizedRemoteIp());
                }

                _mediaInfoHelper.SortMediaSources(info, maxStreamingBitrate);
            }

            if (autoOpenLiveStream.Value)
            {
                var mediaSource = string.IsNullOrWhiteSpace(mediaSourceId) ? info.MediaSources[0] : info.MediaSources.FirstOrDefault(i => string.Equals(i.Id, mediaSourceId, StringComparison.Ordinal));

                if (mediaSource != null && mediaSource.RequiresOpening && string.IsNullOrWhiteSpace(mediaSource.LiveStreamId))
                {
                    var openStreamResult = await _mediaInfoHelper.OpenMediaSource(
                        Request,
                        new LiveStreamRequest
                    {
                        AudioStreamIndex    = audioStreamIndex,
                        DeviceProfile       = playbackInfoDto?.DeviceProfile,
                        EnableDirectPlay    = enableDirectPlay.Value,
                        EnableDirectStream  = enableDirectStream.Value,
                        ItemId              = itemId,
                        MaxAudioChannels    = maxAudioChannels,
                        MaxStreamingBitrate = maxStreamingBitrate,
                        PlaySessionId       = info.PlaySessionId,
                        StartTimeTicks      = startTimeTicks,
                        SubtitleStreamIndex = subtitleStreamIndex,
                        UserId              = userId ?? Guid.Empty,
                        OpenToken           = mediaSource.OpenToken
                    }).ConfigureAwait(false);

                    info.MediaSources = new[] { openStreamResult.MediaSource };
                }
            }

            if (info.MediaSources != null)
            {
                foreach (var mediaSource in info.MediaSources)
                {
                    _mediaInfoHelper.NormalizeMediaSourceContainer(mediaSource, profile !, DlnaProfileType.Video);
                }
            }

            return(info);
        }
示例#6
0
        public async Task <ActionResult> GetUniversalAudioStream(
            [FromRoute, Required] Guid itemId,
            [FromRoute, Required] string?container,
            [FromQuery] string?mediaSourceId,
            [FromQuery] string?deviceId,
            [FromQuery] Guid?userId,
            [FromQuery] string?audioCodec,
            [FromQuery] int?maxAudioChannels,
            [FromQuery] int?transcodingAudioChannels,
            [FromQuery] long?maxStreamingBitrate,
            [FromQuery] long?startTimeTicks,
            [FromQuery] string?transcodingContainer,
            [FromQuery] string?transcodingProtocol,
            [FromQuery] int?maxAudioSampleRate,
            [FromQuery] int?maxAudioBitDepth,
            [FromQuery] bool?enableRemoteMedia,
            [FromQuery] bool breakOnNonKeyFrames,
            [FromQuery] bool enableRedirection = true)
        {
            var deviceProfile = GetDeviceProfile(container, transcodingContainer, audioCodec, transcodingProtocol, breakOnNonKeyFrames, transcodingAudioChannels, maxAudioSampleRate, maxAudioBitDepth, maxAudioChannels);

            _authorizationContext.GetAuthorizationInfo(Request).DeviceId = deviceId;

            var authInfo = _authorizationContext.GetAuthorizationInfo(Request);

            _logger.LogInformation("GetPostedPlaybackInfo profile: {@Profile}", deviceProfile);

            if (deviceProfile == null)
            {
                var clientCapabilities = _deviceManager.GetCapabilities(authInfo.DeviceId);
                if (clientCapabilities != null)
                {
                    deviceProfile = clientCapabilities.DeviceProfile;
                }
            }

            var info = await _mediaInfoHelper.GetPlaybackInfo(
                itemId,
                userId,
                mediaSourceId)
                       .ConfigureAwait(false);

            if (deviceProfile != null)
            {
                // set device specific data
                var item = _libraryManager.GetItemById(itemId);

                foreach (var sourceInfo in info.MediaSources)
                {
                    _mediaInfoHelper.SetDeviceSpecificData(
                        item,
                        sourceInfo,
                        deviceProfile,
                        authInfo,
                        maxStreamingBitrate ?? deviceProfile.MaxStreamingBitrate,
                        startTimeTicks ?? 0,
                        mediaSourceId ?? string.Empty,
                        null,
                        null,
                        maxAudioChannels,
                        info !.PlaySessionId !,
                        userId ?? Guid.Empty,
                        true,
                        true,
                        true,
                        true,
                        true,
                        Request.HttpContext.Connection.RemoteIpAddress.ToString());
                }

                _mediaInfoHelper.SortMediaSources(info, maxStreamingBitrate);
            }

            if (info.MediaSources != null)
            {
                foreach (var source in info.MediaSources)
                {
                    _mediaInfoHelper.NormalizeMediaSourceContainer(source, deviceProfile !, DlnaProfileType.Video);
                }
            }

            var mediaSource = info.MediaSources ![0];
示例#7
0
        public DeviceProfile GetDeviceProfile(SyncTarget target)
        {
            var caps = _deviceManager.GetCapabilities(target.Id);

            return(caps == null || caps.DeviceProfile == null ? new DeviceProfile() : caps.DeviceProfile);
        }
示例#8
0
 public object Get(GetDeviceCapabilities request)
 {
     return(ToOptimizedResult(_deviceManager.GetCapabilities(request.Id)));
 }
示例#9
0
        public async Task <ActionResult <PlaybackInfoResponse> > GetPostedPlaybackInfo(
            [FromRoute] Guid itemId,
            [FromQuery] Guid?userId,
            [FromQuery] long?maxStreamingBitrate,
            [FromQuery] long?startTimeTicks,
            [FromQuery] int?audioStreamIndex,
            [FromQuery] int?subtitleStreamIndex,
            [FromQuery] int?maxAudioChannels,
            [FromQuery] string?mediaSourceId,
            [FromQuery] string?liveStreamId,
            [FromBody] DeviceProfileDto?deviceProfile,
            [FromQuery] bool autoOpenLiveStream   = false,
            [FromQuery] bool enableDirectPlay     = true,
            [FromQuery] bool enableDirectStream   = true,
            [FromQuery] bool enableTranscoding    = true,
            [FromQuery] bool allowVideoStreamCopy = true,
            [FromQuery] bool allowAudioStreamCopy = true)
        {
            var authInfo = _authContext.GetAuthorizationInfo(Request);

            var profile = deviceProfile?.DeviceProfile;

            _logger.LogInformation("GetPostedPlaybackInfo profile: {@Profile}", profile);

            if (profile == null)
            {
                var caps = _deviceManager.GetCapabilities(authInfo.DeviceId);
                if (caps != null)
                {
                    profile = caps.DeviceProfile;
                }
            }

            var info = await GetPlaybackInfoInternal(itemId, userId, mediaSourceId, liveStreamId).ConfigureAwait(false);

            if (profile != null)
            {
                // set device specific data
                var item = _libraryManager.GetItemById(itemId);

                foreach (var mediaSource in info.MediaSources)
                {
                    SetDeviceSpecificData(
                        item,
                        mediaSource,
                        profile,
                        authInfo,
                        maxStreamingBitrate ?? profile.MaxStreamingBitrate,
                        startTimeTicks ?? 0,
                        mediaSourceId ?? string.Empty,
                        audioStreamIndex,
                        subtitleStreamIndex,
                        maxAudioChannels,
                        info !.PlaySessionId !,
                        userId ?? Guid.Empty,
                        enableDirectPlay,
                        enableDirectStream,
                        enableTranscoding,
                        allowVideoStreamCopy,
                        allowAudioStreamCopy);
                }

                SortMediaSources(info, maxStreamingBitrate);
            }

            if (autoOpenLiveStream)
            {
                var mediaSource = string.IsNullOrWhiteSpace(mediaSourceId) ? info.MediaSources[0] : info.MediaSources.FirstOrDefault(i => string.Equals(i.Id, mediaSourceId, StringComparison.Ordinal));

                if (mediaSource != null && mediaSource.RequiresOpening && string.IsNullOrWhiteSpace(mediaSource.LiveStreamId))
                {
                    var openStreamResult = await OpenMediaSource(new LiveStreamRequest
                    {
                        AudioStreamIndex    = audioStreamIndex,
                        DeviceProfile       = deviceProfile?.DeviceProfile,
                        EnableDirectPlay    = enableDirectPlay,
                        EnableDirectStream  = enableDirectStream,
                        ItemId              = itemId,
                        MaxAudioChannels    = maxAudioChannels,
                        MaxStreamingBitrate = maxStreamingBitrate,
                        PlaySessionId       = info.PlaySessionId,
                        StartTimeTicks      = startTimeTicks,
                        SubtitleStreamIndex = subtitleStreamIndex,
                        UserId              = userId ?? Guid.Empty,
                        OpenToken           = mediaSource.OpenToken
                    }).ConfigureAwait(false);

                    info.MediaSources = new[] { openStreamResult.MediaSource };
                }
            }

            if (info.MediaSources != null)
            {
                foreach (var mediaSource in info.MediaSources)
                {
                    NormalizeMediaSourceContainer(mediaSource, profile !, DlnaProfileType.Video);
                }
            }

            return(info);
        }