From dd7a2dc5773fe23829b858cbc7b643652c24b1fe Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?/z=C9=92=CC=83ge/?= Date: Tue, 25 Apr 2023 09:36:07 +0200 Subject: [PATCH] fix: `config.streaming.preferNativeHls` only applies to HLS streams (#5167) Closes #5166 --- lib/player.js | 4 ++- lib/util/mime_utils.js | 11 +++++++ test/player_unit.js | 54 +++++++++++++++++++++++++++++++ test/test/util/fake_drm_engine.js | 3 ++ test/test/util/simple_fakes.js | 3 ++ test/util/mime_utils_unit.js | 10 ++++++ 6 files changed, 84 insertions(+), 1 deletion(-) diff --git a/lib/player.js b/lib/player.js index dfd67bf017..6558945dbc 100644 --- a/lib/player.js +++ b/lib/player.js @@ -1346,6 +1346,7 @@ shaka.Player = class extends shaka.util.FakeEventTarget { */ shouldUseSrcEquals_(payload) { const Platform = shaka.util.Platform; + const MimeUtils = shaka.util.MimeUtils; // If we are using a platform that does not support media source, we will // fall back to src= to handle all playback. @@ -1400,7 +1401,8 @@ shaka.Player = class extends shaka.util.FakeEventTarget { // version there. // Native HLS can be preferred on any platform via this flag: - if (this.config_.streaming.preferNativeHls) { + if (MimeUtils.isHlsType(mimeType) && + this.config_.streaming.preferNativeHls) { return true; } diff --git a/lib/util/mime_utils.js b/lib/util/mime_utils.js index 41b6808d87..5e17e031a9 100644 --- a/lib/util/mime_utils.js +++ b/lib/util/mime_utils.js @@ -193,6 +193,17 @@ shaka.util.MimeUtils = class { return value; } + /** + * Checks if the given MIME type is HLS MIME type. + * + * @param {string} mimeType + * @return {boolean} + */ + static isHlsType(mimeType) { + return mimeType === 'application/x-mpegurl' || + mimeType === 'application/vnd.apple.mpegurl'; + } + /** * Get the base and profile of a codec string. Where [0] will be the codec * base and [1] will be the profile. diff --git a/test/player_unit.js b/test/player_unit.js index 7f7caf2408..dbd14d6517 100644 --- a/test/player_unit.js +++ b/test/player_unit.js @@ -557,6 +557,60 @@ describe('Player', () => { expect(streamingEngine.unloadTextStream).not.toHaveBeenCalled(); }); }); + + describe('when config.streaming.preferNativeHls is set to true', () => { + beforeEach(() => { + shaka.media.ManifestParser.registerParserByMime( + 'application/x-mpegurl', + () => new shaka.test.FakeManifestParser(manifest)); + }); + + afterEach(() => { + shaka.media.ManifestParser.unregisterParserByMime( + 'application/x-mpegurl'); + video.canPlayType.calls.reset(); + }); + + it('only applies to HLS streams', async () => { + video.canPlayType.and.returnValue('maybe'); + spyOn(shaka.util.Platform, 'anyMediaElement').and.returnValue(video); + spyOn(shaka.util.Platform, 'supportsMediaSource').and.returnValue(true); + spyOn(shaka.util.Platform, 'isApple').and.returnValue(false); + // Make sure player.load() resolves for src= + spyOn(shaka.util.MediaReadyState, 'waitForReadyState').and.callFake( + (mediaElement, readyState, eventManager, callback) => { + callback(); + }); + + player.configure({ + streaming: { + preferNativeHls: true, + useNativeHlsOnSafari: false, + }, + }); + + await player.load(fakeManifestUri, undefined, 'application/x-mpegurl'); + + expect(player.getLoadMode()).toBe(shaka.Player.LoadMode.SRC_EQUALS); + }); + + it('does not apply to non-HLS streams', async () => { + video.canPlayType.and.returnValue('maybe'); + spyOn(shaka.util.Platform, 'supportsMediaSource').and.returnValue(true); + spyOn(shaka.util.Platform, 'isApple').and.returnValue(false); + + player.configure({ + streaming: { + preferNativeHls: true, + useNativeHlsOnSafari: false, + }, + }); + + await player.load(fakeManifestUri, 0, fakeMimeType); + + expect(player.getLoadMode()).toBe(shaka.Player.LoadMode.MEDIA_SOURCE); + }); + }); }); // describe('load/unload') describe('getConfiguration', () => { diff --git a/test/test/util/fake_drm_engine.js b/test/test/util/fake_drm_engine.js index 79140c5d43..85097bb417 100644 --- a/test/test/util/fake_drm_engine.js +++ b/test/test/util/fake_drm_engine.js @@ -81,6 +81,9 @@ shaka.test.FakeDrmEngine = class { /** @type {!jasmine.Spy} */ this.supportsVariant = jasmine.createSpy('supportsVariant'); this.supportsVariant.and.returnValue(true); + + /** @type {!jasmine.Spy} */ + this.setSrcEquals = jasmine.createSpy('setSrcEquals'); } /** diff --git a/test/test/util/simple_fakes.js b/test/test/util/simple_fakes.js index fe301338d0..edd5681333 100644 --- a/test/test/util/simple_fakes.js +++ b/test/test/util/simple_fakes.js @@ -228,6 +228,9 @@ shaka.test.FakeVideo = class { /** @type {!jasmine.Spy} */ this.dispatchEvent = jasmine.createSpy('dispatchEvent'); + + /** @type {!jasmine.Spy} */ + this.canPlayType = jasmine.createSpy('canPlayType'); } }; diff --git a/test/util/mime_utils_unit.js b/test/util/mime_utils_unit.js index 0364314ac1..3fe9799a99 100644 --- a/test/util/mime_utils_unit.js +++ b/test/util/mime_utils_unit.js @@ -51,4 +51,14 @@ describe('MimeUtils', () => { expect(getNormalizedCodec('dvh1.05')).toBe('dovi'); expect(getNormalizedCodec('dvhe.05')).toBe('dovi'); }); + + it('isHlsType', () => { + const isHlsType = (mimeType) => shaka.util.MimeUtils.isHlsType(mimeType); + + expect(isHlsType('application/x-mpegurl')).toBe(true); + expect(isHlsType('application/vnd.apple.mpegurl')).toBe(true); + expect(isHlsType('application/dash+xml')).toBe(false); + expect(isHlsType('application/vnd.ms-sstr+xml')).toBe(false); + expect(isHlsType('foo')).toBe(false); + }); });