Skip to content

Commit

Permalink
feat(ll-hls): only request delta updates when server supports it
Browse files Browse the repository at this point in the history
We should only request playlist delta updates when the lowLatencyMode is
enabled, and when the server supports the feature. We can check if the
playlist has a "CAN-SKIP-UNTIL" tag to know if the server supports that.

Issue shaka-project#1525

Change-Id: I304a008aeb3a9e019f27304ba836d31538c94fbf
  • Loading branch information
michellezhuogg committed Apr 15, 2021
1 parent 7e50866 commit 4c97562
Show file tree
Hide file tree
Showing 2 changed files with 63 additions and 3 deletions.
14 changes: 12 additions & 2 deletions lib/hls/hls_parser.js
Expand Up @@ -302,7 +302,7 @@ shaka.hls.HlsParser = class {
const PresentationType = shaka.hls.HlsParser.PresentationType_;
const manifestUri = streamInfo.absoluteMediaPlaylistUri;
const uriObj = new goog.Uri(manifestUri);
if (this.lowLatencyMode_) {
if (this.lowLatencyMode_ && streamInfo.canSkipSegments) {
// Enable delta updates. This will replace older segments with
// 'EXT-X-SKIP' tag in the media playlist.
uriObj.setQueryData(new goog.Uri.QueryData('_HLS_skip=YES'));
Expand Down Expand Up @@ -1383,6 +1383,11 @@ shaka.hls.HlsParser = class {
}
}

const serverControlTag = shaka.hls.Utils.getFirstTagWithName(
playlist.tags, 'EXT-X-SERVER-CONTROL');
const canSkipSegments = serverControlTag ?
serverControlTag.getAttribute('CAN-SKIP-UNTIL') != null : false;

/** @type {shaka.extern.Stream} */
const stream = {
id: this.globalId_++,
Expand Down Expand Up @@ -1425,6 +1430,7 @@ shaka.hls.HlsParser = class {
maxTimestamp: lastEndTime,
mediaSequenceToStartTime,
discontinuityToMediaSequence,
canSkipSegments,
};
}

Expand Down Expand Up @@ -2658,7 +2664,8 @@ shaka.hls.HlsParser = class {
* minTimestamp: number,
* maxTimestamp: number,
* mediaSequenceToStartTime: !Map.<number, number>,
* discontinuityToMediaSequence: !Map.<number, number>
* discontinuityToMediaSequence: !Map.<number, number>,
* canSkipSegments: boolean
* }}
*
* @description
Expand All @@ -2683,6 +2690,9 @@ shaka.hls.HlsParser = class {
* @property {!Map.<number, number>} discontinuityToMediaSequence
* A map of discontinuity sequence numbers to the media sequence number of the
* segment starting with that discontinuity sequence number.
* @property {boolean} canSkipSegments
* True if the server supports delta playlist updates, and we can send a
* request for a playlist that can skip older media segments.
*/
shaka.hls.HlsParser.StreamInfo;

Expand Down
52 changes: 51 additions & 1 deletion test/hls/hls_live_unit.js
Expand Up @@ -907,6 +907,56 @@ describe('HlsParser live', () => {
partialEndByte); // partial segment request
});

it('request playlist delta updates to skip segments', async () => {
const mediaWithDeltaUpdates = [
'#EXTM3U\n',
'#EXT-X-PLAYLIST-TYPE:LIVE\n',
'#EXT-X-TARGETDURATION:5\n',
'#EXT-X-MEDIA-SEQUENCE:0\n',
'#EXT-X-MAP:URI="init.mp4",BYTERANGE="616@0"\n',
'#EXT-X-SERVER-CONTROL:CAN-SKIP-UNTIL=60.0\n',
'#EXTINF:2,\n',
'main.mp4\n',
'#EXTINF:2,\n',
'main2.mp4\n',
].join('');

const mediaWithSkippedSegments = [
'#EXTM3U\n',
'#EXT-X-TARGETDURATION:5\n',
'#EXT-X-MAP:URI="init.mp4",BYTERANGE="616@0"\n',
'#EXT-X-MEDIA-SEQUENCE:0\n',
'#EXT-X-SERVER-CONTROL:CAN-SKIP-UNTIL=60.0\n',
'#EXT-X-SKIP:SKIPPED-SEGMENTS=1\n',
'#EXTINF:2,\n',
'main2.mp4\n',
'#EXTINF:2,\n',
'main3.mp4\n',
].join('');

fakeNetEngine
.setResponseText('test:/master', master)
.setResponseText('test:/video', mediaWithDeltaUpdates)
.setResponseText('test:/video?_HLS_skip=YES',
mediaWithSkippedSegments)
.setResponseValue('test:/init.mp4', initSegmentData)
.setResponseValue('test:/main.mp4', segmentData)
.setResponseValue('test:/main2.mp4', segmentData)
.setResponseValue('test:/main3.mp4', segmentData);

playerInterface.isLowLatencyMode = () => true;
await parser.start('test:/master', playerInterface);
// Replace the entries with the updated values.

fakeNetEngine.request.calls.reset();
await delayForUpdatePeriod();

fakeNetEngine.expectRequest(
'test:/video?_HLS_skip=YES',
shaka.net.NetworkingEngine.RequestType.MANIFEST);
});


it('skips older segments', async () => {
const mediaWithSkippedSegments = [
'#EXTM3U\n',
Expand Down Expand Up @@ -935,7 +985,7 @@ describe('HlsParser live', () => {
it('skips older segments with discontinuity', async () => {
const mediaWithDiscontinuity2 = [
'#EXTM3U\n',
'#EXT-X-PLAYLIST-TYPE:EVENT\n',
'#EXT-X-PLAYLIST-TYPE:LIVE\n',
'#EXT-X-TARGETDURATION:5\n',
'#EXT-X-MAP:URI="init.mp4",BYTERANGE="616@0"\n',
'#EXT-X-DISCONTINUITY-SEQUENCE:30\n',
Expand Down

0 comments on commit 4c97562

Please sign in to comment.