rx-player 4.5.0-dev.2026033100 → 4.5.0-dev.2026041501
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +22 -5
- package/VERSION +1 -1
- package/dist/commonjs/__GENERATED_CODE/embedded_dash_wasm.d.ts.map +1 -1
- package/dist/commonjs/__GENERATED_CODE/embedded_dash_wasm.js +1 -1
- package/dist/commonjs/__GENERATED_CODE/embedded_worker.d.ts.map +1 -1
- package/dist/commonjs/__GENERATED_CODE/embedded_worker.js +1 -1
- package/dist/commonjs/compat/can_patch_out_pssh.d.ts +42 -0
- package/dist/commonjs/compat/can_patch_out_pssh.d.ts.map +1 -0
- package/dist/commonjs/compat/can_patch_out_pssh.js +53 -0
- package/dist/commonjs/compat/env_detector.d.ts +2 -0
- package/dist/commonjs/compat/env_detector.d.ts.map +1 -1
- package/dist/commonjs/compat/env_detector.js +5 -0
- package/dist/commonjs/core/adaptive/network_analyzer.d.ts +1 -2
- package/dist/commonjs/core/adaptive/network_analyzer.d.ts.map +1 -1
- package/dist/commonjs/core/adaptive/network_analyzer.js +3 -3
- package/dist/commonjs/core/adaptive/utils/representation_score_calculator.js +2 -2
- package/dist/commonjs/core/cmcd/cmcd_data_builder.d.ts.map +1 -1
- package/dist/commonjs/core/cmcd/cmcd_data_builder.js +9 -3
- package/dist/commonjs/core/entry/content_preparer.d.ts.map +1 -1
- package/dist/commonjs/core/entry/content_preparer.js +5 -7
- package/dist/commonjs/core/entry/core_entry.d.ts.map +1 -1
- package/dist/commonjs/core/entry/core_entry.js +6 -2
- package/dist/commonjs/core/entry/core_text_displayer_interface.js +3 -3
- package/dist/commonjs/core/fetchers/manifest/manifest_fetcher.d.ts.map +1 -1
- package/dist/commonjs/core/fetchers/manifest/manifest_fetcher.js +12 -0
- package/dist/commonjs/core/fetchers/thumbnails/thumbnail_fetcher.js +1 -1
- package/dist/commonjs/core/fetchers/utils/schedule_request.d.ts.map +1 -1
- package/dist/commonjs/core/fetchers/utils/schedule_request.js +4 -3
- package/dist/commonjs/core/segment_sinks/garbage_collector.d.ts +0 -2
- package/dist/commonjs/core/segment_sinks/garbage_collector.d.ts.map +1 -1
- package/dist/commonjs/core/segment_sinks/garbage_collector.js +0 -3
- package/dist/commonjs/core/segment_sinks/implementations/text/text_segment_sink.d.ts +1 -1
- package/dist/commonjs/core/segment_sinks/implementations/text/text_segment_sink.d.ts.map +1 -1
- package/dist/commonjs/core/segment_sinks/implementations/text/text_segment_sink.js +2 -2
- package/dist/commonjs/core/stream/adaptation/adaptation_stream.d.ts.map +1 -1
- package/dist/commonjs/core/stream/adaptation/adaptation_stream.js +6 -6
- package/dist/commonjs/core/stream/orchestrator/stream_orchestrator.d.ts.map +1 -1
- package/dist/commonjs/core/stream/orchestrator/stream_orchestrator.js +37 -40
- package/dist/commonjs/default_config.d.ts +5 -0
- package/dist/commonjs/default_config.d.ts.map +1 -1
- package/dist/commonjs/default_config.js +5 -0
- package/dist/commonjs/main_thread/api/public_api.d.ts.map +1 -1
- package/dist/commonjs/main_thread/api/public_api.js +23 -16
- package/dist/commonjs/main_thread/decrypt/content_decryptor.d.ts.map +1 -1
- package/dist/commonjs/main_thread/decrypt/content_decryptor.js +4 -1
- package/dist/commonjs/main_thread/decrypt/session_events_listener.js +1 -1
- package/dist/commonjs/main_thread/decrypt/set_server_certificate.d.ts +2 -0
- package/dist/commonjs/main_thread/decrypt/set_server_certificate.d.ts.map +1 -1
- package/dist/commonjs/main_thread/decrypt/set_server_certificate.js +4 -0
- package/dist/commonjs/main_thread/init/media_source_content_initializer.d.ts +0 -8
- package/dist/commonjs/main_thread/init/media_source_content_initializer.d.ts.map +1 -1
- package/dist/commonjs/main_thread/init/media_source_content_initializer.js +58 -50
- package/dist/commonjs/main_thread/init/utils/stream_events_emitter/stream_events_emitter.d.ts +35 -5
- package/dist/commonjs/main_thread/init/utils/stream_events_emitter/stream_events_emitter.d.ts.map +1 -1
- package/dist/commonjs/main_thread/init/utils/stream_events_emitter/stream_events_emitter.js +60 -19
- package/dist/commonjs/main_thread/render_thumbnail.d.ts.map +1 -1
- package/dist/commonjs/main_thread/render_thumbnail.js +4 -0
- package/dist/commonjs/main_thread/tracks_store/media_element_tracks_store.d.ts.map +1 -1
- package/dist/commonjs/main_thread/tracks_store/media_element_tracks_store.js +1 -0
- package/dist/commonjs/main_thread/tracks_store/tracks_store.d.ts +1 -1
- package/dist/commonjs/main_thread/tracks_store/tracks_store.js +1 -1
- package/dist/{es2017/parsers/containers/isobmff/take_pssh_out.d.ts → commonjs/parsers/containers/isobmff/extract_pssh.d.ts} +6 -4
- package/dist/commonjs/parsers/containers/isobmff/extract_pssh.d.ts.map +1 -0
- package/dist/commonjs/parsers/containers/isobmff/{take_pssh_out.js → extract_pssh.js} +22 -17
- package/dist/commonjs/parsers/containers/isobmff/index.d.ts +2 -2
- package/dist/commonjs/parsers/containers/isobmff/index.d.ts.map +1 -1
- package/dist/commonjs/parsers/containers/isobmff/index.js +4 -4
- package/dist/commonjs/playback_observer/core_playback_observer.d.ts +4 -4
- package/dist/commonjs/playback_observer/core_playback_observer.d.ts.map +1 -1
- package/dist/commonjs/playback_observer/media_element_playback_observer.d.ts +1 -2
- package/dist/commonjs/playback_observer/media_element_playback_observer.d.ts.map +1 -1
- package/dist/commonjs/transports/dash/segment_parser.js +1 -1
- package/dist/commonjs/transports/local/segment_parser.js +1 -1
- package/dist/commonjs/utils/test-utils.d.ts +30 -0
- package/dist/commonjs/utils/test-utils.d.ts.map +1 -0
- package/dist/commonjs/utils/test-utils.js +79 -0
- package/dist/es2017/__GENERATED_CODE/embedded_dash_wasm.d.ts.map +1 -1
- package/dist/es2017/__GENERATED_CODE/embedded_dash_wasm.js +1 -1
- package/dist/es2017/__GENERATED_CODE/embedded_worker.d.ts.map +1 -1
- package/dist/es2017/__GENERATED_CODE/embedded_worker.js +1 -1
- package/dist/es2017/compat/can_patch_out_pssh.d.ts +42 -0
- package/dist/es2017/compat/can_patch_out_pssh.d.ts.map +1 -0
- package/dist/es2017/compat/can_patch_out_pssh.js +50 -0
- package/dist/es2017/compat/env_detector.d.ts +2 -0
- package/dist/es2017/compat/env_detector.d.ts.map +1 -1
- package/dist/es2017/compat/env_detector.js +5 -0
- package/dist/es2017/core/adaptive/network_analyzer.d.ts +1 -2
- package/dist/es2017/core/adaptive/network_analyzer.d.ts.map +1 -1
- package/dist/es2017/core/adaptive/network_analyzer.js +3 -3
- package/dist/es2017/core/adaptive/utils/representation_score_calculator.js +2 -2
- package/dist/es2017/core/cmcd/cmcd_data_builder.d.ts.map +1 -1
- package/dist/es2017/core/cmcd/cmcd_data_builder.js +9 -3
- package/dist/es2017/core/entry/content_preparer.d.ts.map +1 -1
- package/dist/es2017/core/entry/content_preparer.js +3 -5
- package/dist/es2017/core/entry/core_entry.d.ts.map +1 -1
- package/dist/es2017/core/entry/core_entry.js +6 -2
- package/dist/es2017/core/entry/core_text_displayer_interface.js +3 -3
- package/dist/es2017/core/fetchers/manifest/manifest_fetcher.d.ts.map +1 -1
- package/dist/es2017/core/fetchers/manifest/manifest_fetcher.js +12 -0
- package/dist/es2017/core/fetchers/thumbnails/thumbnail_fetcher.js +1 -1
- package/dist/es2017/core/fetchers/utils/schedule_request.d.ts.map +1 -1
- package/dist/es2017/core/fetchers/utils/schedule_request.js +2 -3
- package/dist/es2017/core/segment_sinks/garbage_collector.d.ts +0 -2
- package/dist/es2017/core/segment_sinks/garbage_collector.d.ts.map +1 -1
- package/dist/es2017/core/segment_sinks/garbage_collector.js +0 -3
- package/dist/es2017/core/segment_sinks/implementations/text/text_segment_sink.d.ts +1 -1
- package/dist/es2017/core/segment_sinks/implementations/text/text_segment_sink.d.ts.map +1 -1
- package/dist/es2017/core/segment_sinks/implementations/text/text_segment_sink.js +2 -2
- package/dist/es2017/core/stream/adaptation/adaptation_stream.d.ts.map +1 -1
- package/dist/es2017/core/stream/adaptation/adaptation_stream.js +6 -6
- package/dist/es2017/core/stream/orchestrator/stream_orchestrator.d.ts.map +1 -1
- package/dist/es2017/core/stream/orchestrator/stream_orchestrator.js +40 -39
- package/dist/es2017/default_config.d.ts +5 -0
- package/dist/es2017/default_config.d.ts.map +1 -1
- package/dist/es2017/default_config.js +5 -0
- package/dist/es2017/main_thread/api/public_api.d.ts.map +1 -1
- package/dist/es2017/main_thread/api/public_api.js +20 -13
- package/dist/es2017/main_thread/decrypt/content_decryptor.d.ts.map +1 -1
- package/dist/es2017/main_thread/decrypt/content_decryptor.js +4 -1
- package/dist/es2017/main_thread/decrypt/session_events_listener.js +1 -1
- package/dist/es2017/main_thread/decrypt/set_server_certificate.d.ts +2 -0
- package/dist/es2017/main_thread/decrypt/set_server_certificate.d.ts.map +1 -1
- package/dist/es2017/main_thread/decrypt/set_server_certificate.js +4 -0
- package/dist/es2017/main_thread/init/media_source_content_initializer.d.ts +0 -8
- package/dist/es2017/main_thread/init/media_source_content_initializer.d.ts.map +1 -1
- package/dist/es2017/main_thread/init/media_source_content_initializer.js +58 -50
- package/dist/es2017/main_thread/init/utils/stream_events_emitter/stream_events_emitter.d.ts +35 -5
- package/dist/es2017/main_thread/init/utils/stream_events_emitter/stream_events_emitter.d.ts.map +1 -1
- package/dist/es2017/main_thread/init/utils/stream_events_emitter/stream_events_emitter.js +60 -19
- package/dist/es2017/main_thread/render_thumbnail.d.ts.map +1 -1
- package/dist/es2017/main_thread/render_thumbnail.js +4 -0
- package/dist/es2017/main_thread/tracks_store/media_element_tracks_store.d.ts.map +1 -1
- package/dist/es2017/main_thread/tracks_store/media_element_tracks_store.js +1 -0
- package/dist/es2017/main_thread/tracks_store/tracks_store.d.ts +1 -1
- package/dist/es2017/main_thread/tracks_store/tracks_store.js +1 -1
- package/dist/{commonjs/parsers/containers/isobmff/take_pssh_out.d.ts → es2017/parsers/containers/isobmff/extract_pssh.d.ts} +6 -4
- package/dist/es2017/parsers/containers/isobmff/extract_pssh.d.ts.map +1 -0
- package/dist/es2017/parsers/containers/isobmff/{take_pssh_out.js → extract_pssh.js} +21 -16
- package/dist/es2017/parsers/containers/isobmff/index.d.ts +2 -2
- package/dist/es2017/parsers/containers/isobmff/index.d.ts.map +1 -1
- package/dist/es2017/parsers/containers/isobmff/index.js +2 -2
- package/dist/es2017/playback_observer/core_playback_observer.d.ts +4 -4
- package/dist/es2017/playback_observer/core_playback_observer.d.ts.map +1 -1
- package/dist/es2017/playback_observer/media_element_playback_observer.d.ts +1 -2
- package/dist/es2017/playback_observer/media_element_playback_observer.d.ts.map +1 -1
- package/dist/es2017/transports/dash/segment_parser.js +2 -2
- package/dist/es2017/transports/local/segment_parser.js +2 -2
- package/dist/es2017/utils/test-utils.d.ts +30 -0
- package/dist/es2017/utils/test-utils.d.ts.map +1 -0
- package/dist/es2017/utils/test-utils.js +36 -0
- package/dist/mpd-parser.wasm +0 -0
- package/dist/worker.js +6 -6
- package/package.json +4 -2
- package/src/README.md +7 -7
- package/src/__GENERATED_CODE/embedded_dash_wasm.ts +1 -1
- package/src/__GENERATED_CODE/embedded_worker.ts +1 -1
- package/src/compat/__tests__/can_patch_out_pssh.test.ts +40 -0
- package/src/compat/can_patch_out_pssh.ts +53 -0
- package/src/compat/env_detector.ts +4 -0
- package/src/core/README.md +1 -1
- package/src/core/adaptive/README.md +3 -3
- package/src/core/adaptive/__tests__/adaptive_representation_selector.test.ts +181 -110
- package/src/core/adaptive/__tests__/guess_based_chooser.test.ts +229 -123
- package/src/core/adaptive/__tests__/mocks.ts +100 -0
- package/src/core/adaptive/__tests__/network_analyzer.test.ts +152 -59
- package/src/core/adaptive/network_analyzer.ts +4 -4
- package/src/core/adaptive/utils/__tests__/filter_by_bitrate.test.ts +11 -19
- package/src/core/adaptive/utils/__tests__/filter_by_resolution.test.ts +12 -12
- package/src/core/adaptive/utils/__tests__/last_estimate_storage.test.ts +25 -12
- package/src/core/adaptive/utils/__tests__/pending_requests_store.test.ts +13 -9
- package/src/core/adaptive/utils/__tests__/representation_score_calculator.test.ts +11 -11
- package/src/core/adaptive/utils/__tests__/select_optimal_representation.test.ts +13 -23
- package/src/core/adaptive/utils/representation_score_calculator.ts +2 -2
- package/src/core/cmcd/__tests__/cmcd_data_builder.test.ts +60 -15
- package/src/core/cmcd/cmcd_data_builder.ts +9 -3
- package/src/core/entry/README.md +2 -2
- package/src/core/entry/__tests__/core_text_displayer_interface.test.ts +20 -0
- package/src/core/entry/content_preparer.ts +2 -5
- package/src/core/entry/core_entry.ts +6 -2
- package/src/core/entry/core_text_displayer_interface.ts +3 -3
- package/src/core/fetchers/manifest/__tests__/manifest_fetcher.test.ts +52 -3
- package/src/core/fetchers/manifest/manifest_fetcher.ts +12 -0
- package/src/core/fetchers/thumbnails/__tests__/thumbnail_fetcher.test.ts +70 -0
- package/src/core/fetchers/thumbnails/thumbnail_fetcher.ts +1 -1
- package/src/core/fetchers/utils/schedule_request.ts +5 -3
- package/src/core/segment_sinks/__tests__/garbage_collector.test.ts +434 -0
- package/src/core/segment_sinks/__tests__/mocks.ts +49 -0
- package/src/core/segment_sinks/garbage_collector.ts +0 -3
- package/src/core/segment_sinks/implementations/text/__tests__/text_segment_sink.test.ts +177 -0
- package/src/core/segment_sinks/implementations/text/text_segment_sink.ts +2 -2
- package/src/core/segment_sinks/inventory/__tests__/buffered_history.test.ts +215 -0
- package/src/core/segment_sinks/inventory/__tests__/segment_inventory.test.ts +448 -0
- package/src/core/stream/adaptation/__tests__/adaptation_stream.test.ts +973 -0
- package/src/core/stream/adaptation/__tests__/get_representations_switch_strategy.test.ts +283 -374
- package/src/core/stream/adaptation/adaptation_stream.ts +6 -8
- package/src/core/stream/orchestrator/README.md +4 -4
- package/src/core/stream/orchestrator/__tests__/stream_orchestrator.test.ts +707 -0
- package/src/core/stream/orchestrator/stream_orchestrator.ts +41 -46
- package/src/core/stream/period/utils/__tests__/get_adaptation_switch_strategy.test.ts +290 -220
- package/src/core/stream/representation/__tests__/encryption_data_notifier.test.ts +93 -63
- package/src/core/stream/representation/utils/__tests__/append_segment_to_buffer.test.ts +106 -63
- package/src/core/stream/representation/utils/__tests__/check_for_discontinuity.test.ts +179 -204
- package/src/core/stream/representation/utils/__tests__/get_segment_priority.test.ts +7 -7
- package/src/core/stream/representation/utils/__tests__/push_init_segment.test.ts +103 -60
- package/src/core/stream/representation/utils/__tests__/push_media_segment.test.ts +231 -165
- package/src/default_config.ts +6 -0
- package/src/experimental/README.md +1 -1
- package/src/features/README.md +3 -3
- package/src/main_thread/api/README.md +6 -7
- package/src/main_thread/api/public_api.ts +16 -10
- package/src/main_thread/decrypt/README.md +4 -4
- package/src/main_thread/decrypt/__tests__/__global__/content_decryptor.test.ts +135 -0
- package/src/main_thread/decrypt/__tests__/__global__/get_license.test.ts +70 -0
- package/src/main_thread/decrypt/__tests__/__global__/server_certificate.test.ts +44 -0
- package/src/main_thread/decrypt/__tests__/__global__/utils.ts +2 -2
- package/src/main_thread/decrypt/content_decryptor.ts +6 -1
- package/src/main_thread/decrypt/session_events_listener.ts +1 -1
- package/src/main_thread/decrypt/set_server_certificate.ts +5 -0
- package/src/main_thread/init/media_source_content_initializer.ts +69 -55
- package/src/main_thread/init/utils/__tests__/stream_events_emitter.test.ts +175 -0
- package/src/main_thread/init/utils/stream_events_emitter/stream_events_emitter.ts +90 -26
- package/src/main_thread/render_thumbnail.ts +4 -0
- package/src/main_thread/tracks_store/README.md +12 -0
- package/src/main_thread/tracks_store/__tests__/media_element_tracks_store.test.ts +25 -18
- package/src/main_thread/tracks_store/media_element_tracks_store.ts +1 -0
- package/src/main_thread/tracks_store/tracks_store.ts +1 -1
- package/src/manifest/classes/__tests__/mocks.ts +202 -0
- package/src/parsers/containers/isobmff/__tests__/extract_pssh.test.ts +199 -0
- package/src/parsers/containers/isobmff/{take_pssh_out.ts → extract_pssh.ts} +21 -17
- package/src/parsers/containers/isobmff/index.ts +2 -2
- package/src/parsers/manifest/dash/wasm-parser/README.md +9 -9
- package/src/playback_observer/__tests__/mocks.ts +152 -0
- package/src/playback_observer/core_playback_observer.ts +4 -4
- package/src/playback_observer/media_element_playback_observer.ts +1 -1
- package/src/tools/README.md +2 -2
- package/src/transports/README.md +5 -5
- package/src/transports/dash/segment_parser.ts +2 -2
- package/src/transports/local/segment_parser.ts +2 -2
- package/src/transports/metaplaylist/README.md +4 -4
- package/src/utils/README.md +3 -3
- package/src/utils/test-utils.ts +50 -0
- package/dist/commonjs/core/entry/synchronize_sinks_on_observation.d.ts +0 -11
- package/dist/commonjs/core/entry/synchronize_sinks_on_observation.d.ts.map +0 -1
- package/dist/commonjs/core/entry/synchronize_sinks_on_observation.js +0 -20
- package/dist/commonjs/parsers/containers/isobmff/take_pssh_out.d.ts.map +0 -1
- package/dist/es2017/core/entry/synchronize_sinks_on_observation.d.ts +0 -11
- package/dist/es2017/core/entry/synchronize_sinks_on_observation.d.ts.map +0 -1
- package/dist/es2017/core/entry/synchronize_sinks_on_observation.js +0 -17
- package/dist/es2017/parsers/containers/isobmff/take_pssh_out.d.ts.map +0 -1
- package/src/core/adaptive/utils/__tests__/bandwith_estimator.test.ts +0 -117
- package/src/core/entry/synchronize_sinks_on_observation.ts +0 -22
|
@@ -1,79 +1,143 @@
|
|
|
1
|
-
import { describe, it, expect, vi, beforeEach } from "vitest";
|
|
2
|
-
import
|
|
1
|
+
import { describe, it, expect, vi, beforeEach, afterEach } from "vitest";
|
|
2
|
+
import configHandler from "../../../../../config";
|
|
3
|
+
import { type Adaptation, type Period } from "../../../../../manifest/classes";
|
|
4
|
+
import {
|
|
5
|
+
DummyPeriod,
|
|
6
|
+
DummyAdaptation,
|
|
7
|
+
createSegment,
|
|
8
|
+
DummyRepresentation,
|
|
9
|
+
} from "../../../../../manifest/classes/__tests__/mocks";
|
|
10
|
+
import {
|
|
11
|
+
makeReadyOnlyPlaybackObserver,
|
|
12
|
+
DummyObservationPosition,
|
|
13
|
+
} from "../../../../../playback_observer/__tests__/mocks";
|
|
14
|
+
import type { IBufferedChunk, SegmentSink } from "../../../../segment_sinks";
|
|
15
|
+
import { ChunkStatus, SegmentSinkOperation } from "../../../../segment_sinks";
|
|
16
|
+
import { DummySegmentSink } from "../../../../segment_sinks/__tests__/mocks";
|
|
17
|
+
import type { IPeriodStreamPlaybackObservation } from "../../types";
|
|
3
18
|
import getAdaptationSwitchStrategy from "../get_adaptation_switch_strategy";
|
|
4
19
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
20
|
+
describe("getAdaptationSwitchStrategy", () => {
|
|
21
|
+
let mockSegmentSink: SegmentSink;
|
|
22
|
+
let mockPeriod: Period;
|
|
23
|
+
let mockAdaptation: Adaptation;
|
|
24
|
+
const mockedPlaybackObserver =
|
|
25
|
+
makeReadyOnlyPlaybackObserver<IPeriodStreamPlaybackObservation>({
|
|
26
|
+
position: new DummyObservationPosition({
|
|
27
|
+
getPolled: () => 15,
|
|
28
|
+
}),
|
|
29
|
+
readyState: 3,
|
|
30
|
+
paused: {
|
|
31
|
+
last: false,
|
|
32
|
+
pending: undefined,
|
|
33
|
+
},
|
|
34
|
+
duration: NaN,
|
|
35
|
+
speed: 1,
|
|
36
|
+
maximumPosition: Number.MAX_SAFE_INTEGER,
|
|
37
|
+
buffered: { video: null, audio: null, text: null },
|
|
38
|
+
canStream: true,
|
|
39
|
+
});
|
|
40
|
+
beforeEach(() => {
|
|
41
|
+
const originalConfig = configHandler.getCurrent();
|
|
42
|
+
vi.spyOn(configHandler, "getCurrent").mockReturnValue({
|
|
43
|
+
...originalConfig,
|
|
13
44
|
ADAP_REP_SWITCH_BUFFER_PADDINGS: {
|
|
14
45
|
video: { before: 0.5, after: 0.5 },
|
|
15
46
|
audio: { before: 0.5, after: 0.5 },
|
|
16
47
|
text: { before: 0, after: 0 },
|
|
17
48
|
},
|
|
18
|
-
})
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
let mockPeriod: any;
|
|
25
|
-
let mockAdaptation: any;
|
|
26
|
-
let mockPlaybackObserver: any;
|
|
27
|
-
|
|
28
|
-
beforeEach(() => {
|
|
29
|
-
// Create base mocks
|
|
30
|
-
mockSegmentSink = {
|
|
31
|
-
codec: undefined,
|
|
32
|
-
getLastKnownInventory: vi.fn(() => []),
|
|
33
|
-
getPendingOperations: vi.fn(() => []),
|
|
34
|
-
};
|
|
35
|
-
|
|
36
|
-
mockPeriod = {
|
|
49
|
+
});
|
|
50
|
+
mockSegmentSink = new DummySegmentSink({
|
|
51
|
+
getLastKnownInventory: () => [],
|
|
52
|
+
getPendingOperations: () => [],
|
|
53
|
+
});
|
|
54
|
+
mockPeriod = new DummyPeriod({
|
|
37
55
|
id: "period-1",
|
|
38
56
|
start: 10,
|
|
39
57
|
end: 20,
|
|
40
|
-
};
|
|
41
|
-
|
|
42
|
-
mockAdaptation = {
|
|
58
|
+
});
|
|
59
|
+
mockAdaptation = new DummyAdaptation({
|
|
43
60
|
id: "adaptation-1",
|
|
44
61
|
type: "video",
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
62
|
+
});
|
|
63
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getCurrentTime").mockImplementation(
|
|
64
|
+
() => 15,
|
|
65
|
+
);
|
|
66
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getReadyState").mockImplementation(
|
|
67
|
+
() => 3,
|
|
68
|
+
);
|
|
69
|
+
});
|
|
70
|
+
afterEach(() => {
|
|
71
|
+
mockedPlaybackObserver.reset();
|
|
72
|
+
vi.resetModules();
|
|
73
|
+
});
|
|
74
|
+
function makeBufferedChunk({
|
|
75
|
+
bufferedStart,
|
|
76
|
+
bufferedEnd,
|
|
77
|
+
start,
|
|
78
|
+
end,
|
|
79
|
+
periodId = "period-1",
|
|
80
|
+
periodStart = 0,
|
|
81
|
+
periodEnd,
|
|
82
|
+
adaptationId = "adaptation-1",
|
|
83
|
+
representationId = "rep-1",
|
|
84
|
+
}: {
|
|
85
|
+
bufferedStart: number | undefined;
|
|
86
|
+
bufferedEnd: number | undefined;
|
|
87
|
+
start: number;
|
|
88
|
+
end: number;
|
|
89
|
+
periodId?: string;
|
|
90
|
+
periodStart?: number;
|
|
91
|
+
periodEnd?: number | undefined;
|
|
92
|
+
adaptationId?: string;
|
|
93
|
+
representationId?: string;
|
|
94
|
+
}): IBufferedChunk {
|
|
95
|
+
return {
|
|
96
|
+
infos: {
|
|
97
|
+
period: new DummyPeriod({
|
|
98
|
+
id: periodId,
|
|
99
|
+
start: periodStart,
|
|
100
|
+
end: periodEnd,
|
|
101
|
+
}),
|
|
102
|
+
adaptation: new DummyAdaptation({ id: adaptationId }),
|
|
103
|
+
representation: new DummyRepresentation({
|
|
104
|
+
id: representationId,
|
|
56
105
|
}),
|
|
57
|
-
|
|
106
|
+
segment: createSegment({ time: start, end }),
|
|
107
|
+
},
|
|
108
|
+
bufferedStart,
|
|
109
|
+
bufferedEnd,
|
|
110
|
+
start,
|
|
111
|
+
end,
|
|
112
|
+
insertionTs: 0,
|
|
113
|
+
chunkSize: 1024,
|
|
114
|
+
precizeStart: true,
|
|
115
|
+
precizeEnd: true,
|
|
116
|
+
status: ChunkStatus.FullyLoaded,
|
|
117
|
+
splitted: false,
|
|
58
118
|
};
|
|
59
|
-
}
|
|
119
|
+
}
|
|
60
120
|
|
|
61
121
|
describe("codec compatibility", () => {
|
|
62
122
|
it("should return needs-reload when codec is incompatible and onCodecSwitch is reload", () => {
|
|
63
123
|
mockSegmentSink.codec = "avc1.64001f";
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
124
|
+
const currMockAdap = new DummyAdaptation({
|
|
125
|
+
id: "adaptation-1",
|
|
126
|
+
type: "video",
|
|
127
|
+
representations: [
|
|
128
|
+
new DummyRepresentation({
|
|
129
|
+
isPlayable: () => true,
|
|
130
|
+
getMimeTypeString: () => "video/mp4; codecs=hev1.1.6.L93.B0",
|
|
131
|
+
}),
|
|
132
|
+
],
|
|
133
|
+
});
|
|
70
134
|
|
|
71
135
|
const result = getAdaptationSwitchStrategy(
|
|
72
136
|
mockSegmentSink,
|
|
73
137
|
mockPeriod,
|
|
74
|
-
|
|
138
|
+
currMockAdap,
|
|
75
139
|
"seamless",
|
|
76
|
-
|
|
140
|
+
mockedPlaybackObserver.observer,
|
|
77
141
|
{ onCodecSwitch: "reload" },
|
|
78
142
|
);
|
|
79
143
|
|
|
@@ -82,19 +146,23 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
82
146
|
|
|
83
147
|
it("should continue when codec is compatible", () => {
|
|
84
148
|
mockSegmentSink.codec = "video/mp4;codecs=avc1.64001f";
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
149
|
+
const currMockAdap = new DummyAdaptation({
|
|
150
|
+
id: "adaptation-1",
|
|
151
|
+
type: "video",
|
|
152
|
+
representations: [
|
|
153
|
+
new DummyRepresentation({
|
|
154
|
+
isPlayable: () => true,
|
|
155
|
+
getMimeTypeString: () => "video/mp4;codecs=avc1.65001f",
|
|
156
|
+
}),
|
|
157
|
+
],
|
|
158
|
+
});
|
|
91
159
|
|
|
92
160
|
const result = getAdaptationSwitchStrategy(
|
|
93
161
|
mockSegmentSink,
|
|
94
162
|
mockPeriod,
|
|
95
|
-
|
|
163
|
+
currMockAdap,
|
|
96
164
|
"seamless",
|
|
97
|
-
|
|
165
|
+
mockedPlaybackObserver.observer,
|
|
98
166
|
{ onCodecSwitch: "reload" },
|
|
99
167
|
);
|
|
100
168
|
|
|
@@ -103,19 +171,23 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
103
171
|
|
|
104
172
|
it("should continue when onCodecSwitch is continue regardless of codec", () => {
|
|
105
173
|
mockSegmentSink.codec = "avc1.64001f";
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
174
|
+
const currMockAdap = new DummyAdaptation({
|
|
175
|
+
id: "adaptation-1",
|
|
176
|
+
type: "video",
|
|
177
|
+
representations: [
|
|
178
|
+
new DummyRepresentation({
|
|
179
|
+
isPlayable: () => true,
|
|
180
|
+
getMimeTypeString: () => "video/mp4; codecs=hev1.1.6.L93.B0",
|
|
181
|
+
}),
|
|
182
|
+
],
|
|
183
|
+
});
|
|
112
184
|
|
|
113
185
|
const result = getAdaptationSwitchStrategy(
|
|
114
186
|
mockSegmentSink,
|
|
115
187
|
mockPeriod,
|
|
116
|
-
|
|
188
|
+
currMockAdap,
|
|
117
189
|
"seamless",
|
|
118
|
-
|
|
190
|
+
mockedPlaybackObserver.observer,
|
|
119
191
|
{ onCodecSwitch: "continue" },
|
|
120
192
|
);
|
|
121
193
|
|
|
@@ -125,17 +197,15 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
125
197
|
|
|
126
198
|
describe("no unwanted segments", () => {
|
|
127
199
|
it("should return continue when no other adaptation is buffered", () => {
|
|
128
|
-
mockSegmentSink
|
|
129
|
-
{
|
|
200
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
201
|
+
makeBufferedChunk({
|
|
130
202
|
start: 10,
|
|
131
203
|
end: 15,
|
|
132
204
|
bufferedStart: 10,
|
|
133
205
|
bufferedEnd: 15,
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
},
|
|
138
|
-
},
|
|
206
|
+
periodId: "period-1",
|
|
207
|
+
adaptationId: "adaptation-1",
|
|
208
|
+
}),
|
|
139
209
|
]);
|
|
140
210
|
|
|
141
211
|
const result = getAdaptationSwitchStrategy(
|
|
@@ -143,7 +213,7 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
143
213
|
mockPeriod,
|
|
144
214
|
mockAdaptation,
|
|
145
215
|
"seamless",
|
|
146
|
-
|
|
216
|
+
mockedPlaybackObserver.observer,
|
|
147
217
|
{ onCodecSwitch: "continue" },
|
|
148
218
|
);
|
|
149
219
|
|
|
@@ -151,17 +221,15 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
151
221
|
});
|
|
152
222
|
|
|
153
223
|
it("should return continue when segments are from different period", () => {
|
|
154
|
-
mockSegmentSink
|
|
155
|
-
{
|
|
224
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
225
|
+
makeBufferedChunk({
|
|
156
226
|
start: 5,
|
|
157
227
|
end: 10,
|
|
158
228
|
bufferedStart: 5,
|
|
159
229
|
bufferedEnd: 10,
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
},
|
|
164
|
-
},
|
|
230
|
+
periodId: "period-0",
|
|
231
|
+
adaptationId: "adaptation-2",
|
|
232
|
+
}),
|
|
165
233
|
]);
|
|
166
234
|
|
|
167
235
|
const result = getAdaptationSwitchStrategy(
|
|
@@ -169,7 +237,7 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
169
237
|
mockPeriod,
|
|
170
238
|
mockAdaptation,
|
|
171
239
|
"seamless",
|
|
172
|
-
|
|
240
|
+
mockedPlaybackObserver.observer,
|
|
173
241
|
{ onCodecSwitch: "continue" },
|
|
174
242
|
);
|
|
175
243
|
|
|
@@ -179,17 +247,15 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
179
247
|
|
|
180
248
|
describe("unwanted segments in inventory", () => {
|
|
181
249
|
it("should detect unwanted segments from different adaptation in same period", () => {
|
|
182
|
-
mockSegmentSink
|
|
183
|
-
{
|
|
250
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
251
|
+
makeBufferedChunk({
|
|
184
252
|
start: 10,
|
|
185
253
|
end: 15,
|
|
186
254
|
bufferedStart: 10,
|
|
187
255
|
bufferedEnd: 15,
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
},
|
|
192
|
-
},
|
|
256
|
+
periodId: "period-1",
|
|
257
|
+
adaptationId: "adaptation-2", // Different adaptation
|
|
258
|
+
}),
|
|
193
259
|
]);
|
|
194
260
|
|
|
195
261
|
const result = getAdaptationSwitchStrategy(
|
|
@@ -197,7 +263,7 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
197
263
|
mockPeriod,
|
|
198
264
|
mockAdaptation,
|
|
199
265
|
"seamless",
|
|
200
|
-
|
|
266
|
+
mockedPlaybackObserver.observer,
|
|
201
267
|
{ onCodecSwitch: "continue" },
|
|
202
268
|
);
|
|
203
269
|
|
|
@@ -205,17 +271,15 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
205
271
|
});
|
|
206
272
|
|
|
207
273
|
it("should use bufferedStart/bufferedEnd when available", () => {
|
|
208
|
-
mockSegmentSink
|
|
209
|
-
{
|
|
274
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
275
|
+
makeBufferedChunk({
|
|
210
276
|
start: 10,
|
|
211
277
|
end: 15,
|
|
212
278
|
bufferedStart: 10.5,
|
|
213
279
|
bufferedEnd: 14.5,
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
},
|
|
218
|
-
},
|
|
280
|
+
periodId: "period-1",
|
|
281
|
+
adaptationId: "adaptation-2",
|
|
282
|
+
}),
|
|
219
283
|
]);
|
|
220
284
|
|
|
221
285
|
const result = getAdaptationSwitchStrategy(
|
|
@@ -223,7 +287,7 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
223
287
|
mockPeriod,
|
|
224
288
|
mockAdaptation,
|
|
225
289
|
"seamless",
|
|
226
|
-
|
|
290
|
+
mockedPlaybackObserver.observer,
|
|
227
291
|
{ onCodecSwitch: "continue" },
|
|
228
292
|
);
|
|
229
293
|
|
|
@@ -233,17 +297,30 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
233
297
|
|
|
234
298
|
describe("pending operations", () => {
|
|
235
299
|
it("should include unwanted segments from pending push operations", () => {
|
|
236
|
-
mockSegmentSink
|
|
300
|
+
vi.spyOn(mockSegmentSink, "getPendingOperations").mockReturnValue([
|
|
237
301
|
{
|
|
238
302
|
type: SegmentSinkOperation.Push,
|
|
239
303
|
value: {
|
|
240
304
|
inventoryInfos: {
|
|
241
|
-
period:
|
|
242
|
-
adaptation: {
|
|
243
|
-
|
|
305
|
+
period: mockPeriod,
|
|
306
|
+
adaptation: new DummyAdaptation({
|
|
307
|
+
id: "adaptation-2",
|
|
308
|
+
}),
|
|
309
|
+
representation: new DummyRepresentation(),
|
|
310
|
+
segment: createSegment({
|
|
244
311
|
time: 12,
|
|
245
312
|
duration: 3,
|
|
246
|
-
},
|
|
313
|
+
}),
|
|
314
|
+
chunkSize: 1024,
|
|
315
|
+
start: 0,
|
|
316
|
+
end: 1000,
|
|
317
|
+
},
|
|
318
|
+
data: {
|
|
319
|
+
initSegmentUniqueId: "a",
|
|
320
|
+
chunk: 4,
|
|
321
|
+
codec: "toto",
|
|
322
|
+
timestampOffset: 0,
|
|
323
|
+
appendWindow: [undefined, undefined],
|
|
247
324
|
},
|
|
248
325
|
},
|
|
249
326
|
},
|
|
@@ -253,7 +330,7 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
253
330
|
mockPeriod,
|
|
254
331
|
mockAdaptation,
|
|
255
332
|
"seamless",
|
|
256
|
-
|
|
333
|
+
mockedPlaybackObserver.observer,
|
|
257
334
|
{ onCodecSwitch: "continue" },
|
|
258
335
|
);
|
|
259
336
|
|
|
@@ -261,14 +338,19 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
261
338
|
});
|
|
262
339
|
|
|
263
340
|
it("should ignore non-push operations", () => {
|
|
264
|
-
mockSegmentSink
|
|
341
|
+
vi.spyOn(mockSegmentSink, "getPendingOperations").mockReturnValue([
|
|
265
342
|
{
|
|
266
343
|
type: SegmentSinkOperation.Remove,
|
|
267
344
|
value: { start: 10, end: 15 },
|
|
268
345
|
},
|
|
269
346
|
{
|
|
270
347
|
type: SegmentSinkOperation.SignalSegmentComplete,
|
|
271
|
-
value: {
|
|
348
|
+
value: {
|
|
349
|
+
adaptation: mockAdaptation,
|
|
350
|
+
period: mockPeriod,
|
|
351
|
+
representation: new DummyRepresentation(),
|
|
352
|
+
segment: createSegment(),
|
|
353
|
+
},
|
|
272
354
|
},
|
|
273
355
|
]);
|
|
274
356
|
|
|
@@ -277,7 +359,7 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
277
359
|
mockPeriod,
|
|
278
360
|
mockAdaptation,
|
|
279
361
|
"seamless",
|
|
280
|
-
|
|
362
|
+
mockedPlaybackObserver.observer,
|
|
281
363
|
{ onCodecSwitch: "continue" },
|
|
282
364
|
);
|
|
283
365
|
|
|
@@ -287,29 +369,26 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
287
369
|
|
|
288
370
|
describe("switching modes", () => {
|
|
289
371
|
beforeEach(() => {
|
|
290
|
-
mockSegmentSink
|
|
291
|
-
{
|
|
372
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
373
|
+
makeBufferedChunk({
|
|
292
374
|
start: 10,
|
|
293
375
|
end: 15,
|
|
294
376
|
bufferedStart: 10,
|
|
295
377
|
bufferedEnd: 15,
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
},
|
|
300
|
-
},
|
|
378
|
+
periodId: "period-1",
|
|
379
|
+
adaptationId: "adaptation-2",
|
|
380
|
+
}),
|
|
301
381
|
]);
|
|
302
382
|
});
|
|
303
383
|
|
|
304
384
|
it("should return needs-reload when switchingMode is reload and readyState > 1", () => {
|
|
305
|
-
|
|
306
|
-
|
|
385
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getReadyState").mockReturnValue(3);
|
|
307
386
|
const result = getAdaptationSwitchStrategy(
|
|
308
387
|
mockSegmentSink,
|
|
309
388
|
mockPeriod,
|
|
310
389
|
mockAdaptation,
|
|
311
390
|
"reload",
|
|
312
|
-
|
|
391
|
+
mockedPlaybackObserver.observer,
|
|
313
392
|
{ onCodecSwitch: "continue" },
|
|
314
393
|
);
|
|
315
394
|
|
|
@@ -317,14 +396,14 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
317
396
|
});
|
|
318
397
|
|
|
319
398
|
it("should not reload when readyState is 1 or less", () => {
|
|
320
|
-
|
|
399
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getReadyState").mockReturnValue(1);
|
|
321
400
|
|
|
322
401
|
const result = getAdaptationSwitchStrategy(
|
|
323
402
|
mockSegmentSink,
|
|
324
403
|
mockPeriod,
|
|
325
404
|
mockAdaptation,
|
|
326
405
|
"reload",
|
|
327
|
-
|
|
406
|
+
mockedPlaybackObserver.observer,
|
|
328
407
|
{ onCodecSwitch: "continue" },
|
|
329
408
|
);
|
|
330
409
|
|
|
@@ -337,7 +416,7 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
337
416
|
mockPeriod,
|
|
338
417
|
mockAdaptation,
|
|
339
418
|
"direct",
|
|
340
|
-
|
|
419
|
+
mockedPlaybackObserver.observer,
|
|
341
420
|
{ onCodecSwitch: "continue" },
|
|
342
421
|
);
|
|
343
422
|
|
|
@@ -347,14 +426,17 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
347
426
|
});
|
|
348
427
|
|
|
349
428
|
it("should clean-buffer for direct mode with text adaptation", () => {
|
|
350
|
-
|
|
429
|
+
const currMockAdap = new DummyAdaptation({
|
|
430
|
+
id: "adaptation-1",
|
|
431
|
+
type: "text",
|
|
432
|
+
});
|
|
351
433
|
|
|
352
434
|
const result = getAdaptationSwitchStrategy(
|
|
353
435
|
mockSegmentSink,
|
|
354
436
|
mockPeriod,
|
|
355
|
-
|
|
437
|
+
currMockAdap,
|
|
356
438
|
"direct",
|
|
357
|
-
|
|
439
|
+
mockedPlaybackObserver.observer,
|
|
358
440
|
{ onCodecSwitch: "continue" },
|
|
359
441
|
);
|
|
360
442
|
|
|
@@ -369,7 +451,7 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
369
451
|
mockPeriod,
|
|
370
452
|
mockAdaptation,
|
|
371
453
|
"seamless",
|
|
372
|
-
|
|
454
|
+
mockedPlaybackObserver.observer,
|
|
373
455
|
{ onCodecSwitch: "continue" },
|
|
374
456
|
);
|
|
375
457
|
|
|
@@ -379,42 +461,37 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
379
461
|
|
|
380
462
|
describe("range exclusion logic", () => {
|
|
381
463
|
beforeEach(() => {
|
|
382
|
-
mockSegmentSink
|
|
383
|
-
{
|
|
464
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
465
|
+
makeBufferedChunk({
|
|
384
466
|
start: 12,
|
|
385
467
|
end: 18,
|
|
386
468
|
bufferedStart: 12,
|
|
387
469
|
bufferedEnd: 18,
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
},
|
|
392
|
-
},
|
|
470
|
+
periodId: "period-1",
|
|
471
|
+
adaptationId: "adaptation-2",
|
|
472
|
+
}),
|
|
393
473
|
]);
|
|
394
474
|
});
|
|
395
475
|
|
|
396
476
|
it("should return continue when all unwanted ranges are excluded around current position", () => {
|
|
397
477
|
// Set up inventory with segments only around current time (which will be excluded)
|
|
398
|
-
mockSegmentSink
|
|
399
|
-
{
|
|
478
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
479
|
+
makeBufferedChunk({
|
|
400
480
|
start: 14.6,
|
|
401
481
|
end: 15.4,
|
|
402
482
|
bufferedStart: 14.6,
|
|
403
483
|
bufferedEnd: 15.4,
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
},
|
|
408
|
-
},
|
|
484
|
+
periodId: "period-1",
|
|
485
|
+
adaptationId: "adaptation-2",
|
|
486
|
+
}),
|
|
409
487
|
]);
|
|
410
|
-
|
|
411
|
-
|
|
488
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getCurrentTime").mockReturnValue(15);
|
|
412
489
|
const result = getAdaptationSwitchStrategy(
|
|
413
490
|
mockSegmentSink,
|
|
414
491
|
mockPeriod,
|
|
415
492
|
mockAdaptation,
|
|
416
493
|
"seamless",
|
|
417
|
-
|
|
494
|
+
mockedPlaybackObserver.observer,
|
|
418
495
|
{ onCodecSwitch: "continue" },
|
|
419
496
|
);
|
|
420
497
|
|
|
@@ -423,26 +500,25 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
423
500
|
|
|
424
501
|
it("should clean ranges that are far from period boundaries", () => {
|
|
425
502
|
// Segment in the middle of the period, away from boundaries
|
|
426
|
-
mockSegmentSink
|
|
427
|
-
{
|
|
503
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
504
|
+
makeBufferedChunk({
|
|
428
505
|
start: 13,
|
|
429
506
|
end: 17,
|
|
430
507
|
bufferedStart: 13,
|
|
431
508
|
bufferedEnd: 17,
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
},
|
|
436
|
-
},
|
|
509
|
+
periodId: "period-1",
|
|
510
|
+
adaptationId: "adaptation-2",
|
|
511
|
+
}),
|
|
437
512
|
]);
|
|
438
|
-
|
|
513
|
+
// Away from segment
|
|
514
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getCurrentTime").mockReturnValue(18);
|
|
439
515
|
|
|
440
516
|
const result = getAdaptationSwitchStrategy(
|
|
441
517
|
mockSegmentSink,
|
|
442
518
|
mockPeriod,
|
|
443
519
|
mockAdaptation,
|
|
444
520
|
"seamless",
|
|
445
|
-
|
|
521
|
+
mockedPlaybackObserver.observer,
|
|
446
522
|
{ onCodecSwitch: "continue" },
|
|
447
523
|
);
|
|
448
524
|
|
|
@@ -452,36 +528,32 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
452
528
|
|
|
453
529
|
it("should exclude range near period start when previous period segment is close", () => {
|
|
454
530
|
// Set up inventory where segment from period-1 exists
|
|
455
|
-
mockSegmentSink
|
|
456
|
-
{
|
|
531
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
532
|
+
makeBufferedChunk({
|
|
457
533
|
start: 8,
|
|
458
534
|
end: 9.5,
|
|
459
535
|
bufferedStart: 8,
|
|
460
536
|
bufferedEnd: 9.5, // Less than 1 second before period start (10)
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
},
|
|
466
|
-
{
|
|
537
|
+
periodId: "period-0",
|
|
538
|
+
adaptationId: "adaptation-1",
|
|
539
|
+
}),
|
|
540
|
+
makeBufferedChunk({
|
|
467
541
|
start: 10,
|
|
468
542
|
end: 10.5,
|
|
469
543
|
bufferedStart: 10,
|
|
470
544
|
bufferedEnd: 10.5,
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
},
|
|
475
|
-
},
|
|
545
|
+
periodId: "period-1",
|
|
546
|
+
adaptationId: "adaptation-2",
|
|
547
|
+
}),
|
|
476
548
|
]);
|
|
477
|
-
|
|
549
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getCurrentTime").mockReturnValue(18);
|
|
478
550
|
|
|
479
551
|
const result = getAdaptationSwitchStrategy(
|
|
480
552
|
mockSegmentSink,
|
|
481
553
|
mockPeriod,
|
|
482
554
|
mockAdaptation,
|
|
483
555
|
"seamless",
|
|
484
|
-
|
|
556
|
+
mockedPlaybackObserver.observer,
|
|
485
557
|
{ onCodecSwitch: "continue" },
|
|
486
558
|
);
|
|
487
559
|
|
|
@@ -491,36 +563,35 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
491
563
|
|
|
492
564
|
it("should exclude range near period end when next period segment is close", () => {
|
|
493
565
|
// Set up inventory where segment from next period exists
|
|
494
|
-
mockSegmentSink
|
|
495
|
-
{
|
|
566
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
567
|
+
makeBufferedChunk({
|
|
496
568
|
start: 19.5,
|
|
497
569
|
end: 20,
|
|
498
570
|
bufferedStart: 19.5,
|
|
499
571
|
bufferedEnd: 20,
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
},
|
|
505
|
-
{
|
|
572
|
+
periodId: "period-1",
|
|
573
|
+
periodStart: 0,
|
|
574
|
+
periodEnd: 20,
|
|
575
|
+
adaptationId: "adaptation-2",
|
|
576
|
+
}),
|
|
577
|
+
makeBufferedChunk({
|
|
506
578
|
start: 20,
|
|
507
579
|
end: 21,
|
|
508
580
|
bufferedStart: 20.5, // Less than 1 second after period end (20)
|
|
509
581
|
bufferedEnd: 21,
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
},
|
|
582
|
+
periodId: "period-2",
|
|
583
|
+
periodStart: 20,
|
|
584
|
+
adaptationId: "adaptation-1",
|
|
585
|
+
}),
|
|
515
586
|
]);
|
|
516
|
-
|
|
587
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getCurrentTime").mockReturnValue(12);
|
|
517
588
|
|
|
518
589
|
const result = getAdaptationSwitchStrategy(
|
|
519
590
|
mockSegmentSink,
|
|
520
591
|
mockPeriod,
|
|
521
592
|
mockAdaptation,
|
|
522
593
|
"seamless",
|
|
523
|
-
|
|
594
|
+
mockedPlaybackObserver.observer,
|
|
524
595
|
{ onCodecSwitch: "continue" },
|
|
525
596
|
);
|
|
526
597
|
|
|
@@ -530,26 +601,25 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
530
601
|
|
|
531
602
|
it("should not exclude period end range when period.end is undefined", () => {
|
|
532
603
|
mockPeriod.end = undefined;
|
|
533
|
-
mockSegmentSink
|
|
534
|
-
{
|
|
604
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
605
|
+
makeBufferedChunk({
|
|
535
606
|
start: 12,
|
|
536
607
|
end: 15,
|
|
537
608
|
bufferedStart: 12,
|
|
538
609
|
bufferedEnd: 15,
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
},
|
|
610
|
+
periodId: "period-1",
|
|
611
|
+
periodStart: 10,
|
|
612
|
+
adaptationId: "adaptation-2",
|
|
613
|
+
}),
|
|
544
614
|
]);
|
|
545
|
-
|
|
615
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getCurrentTime").mockReturnValue(18);
|
|
546
616
|
|
|
547
617
|
const result = getAdaptationSwitchStrategy(
|
|
548
618
|
mockSegmentSink,
|
|
549
619
|
mockPeriod,
|
|
550
620
|
mockAdaptation,
|
|
551
621
|
"seamless",
|
|
552
|
-
|
|
622
|
+
mockedPlaybackObserver.observer,
|
|
553
623
|
{ onCodecSwitch: "continue" },
|
|
554
624
|
);
|
|
555
625
|
|
|
@@ -558,26 +628,25 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
558
628
|
});
|
|
559
629
|
|
|
560
630
|
it("should exclude current position padding for seamless mode", () => {
|
|
561
|
-
mockSegmentSink
|
|
562
|
-
{
|
|
631
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
632
|
+
makeBufferedChunk({
|
|
563
633
|
start: 14.6,
|
|
564
634
|
end: 15.4,
|
|
565
635
|
bufferedStart: 14.6,
|
|
566
636
|
bufferedEnd: 15.4,
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
},
|
|
637
|
+
periodId: "period-1",
|
|
638
|
+
periodStart: 10,
|
|
639
|
+
adaptationId: "adaptation-2",
|
|
640
|
+
}),
|
|
572
641
|
]);
|
|
573
|
-
|
|
642
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getCurrentTime").mockReturnValue(15);
|
|
574
643
|
|
|
575
644
|
const result = getAdaptationSwitchStrategy(
|
|
576
645
|
mockSegmentSink,
|
|
577
646
|
mockPeriod,
|
|
578
647
|
mockAdaptation,
|
|
579
648
|
"seamless",
|
|
580
|
-
|
|
649
|
+
mockedPlaybackObserver.observer,
|
|
581
650
|
{ onCodecSwitch: "continue" },
|
|
582
651
|
);
|
|
583
652
|
|
|
@@ -586,26 +655,25 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
586
655
|
});
|
|
587
656
|
|
|
588
657
|
it("should not exclude current position padding for direct mode", () => {
|
|
589
|
-
mockSegmentSink
|
|
590
|
-
{
|
|
658
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
659
|
+
makeBufferedChunk({
|
|
591
660
|
start: 14.6,
|
|
592
661
|
end: 15.4,
|
|
593
662
|
bufferedStart: 14.6,
|
|
594
663
|
bufferedEnd: 15.4,
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
},
|
|
664
|
+
periodId: "period-1",
|
|
665
|
+
periodStart: 10,
|
|
666
|
+
adaptationId: "adaptation-2",
|
|
667
|
+
}),
|
|
600
668
|
]);
|
|
601
|
-
|
|
669
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getCurrentTime").mockReturnValue(15);
|
|
602
670
|
|
|
603
671
|
const result = getAdaptationSwitchStrategy(
|
|
604
672
|
mockSegmentSink,
|
|
605
673
|
mockPeriod,
|
|
606
674
|
mockAdaptation,
|
|
607
675
|
"direct",
|
|
608
|
-
|
|
676
|
+
mockedPlaybackObserver.observer,
|
|
609
677
|
{ onCodecSwitch: "continue" },
|
|
610
678
|
);
|
|
611
679
|
|
|
@@ -615,18 +683,20 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
615
683
|
});
|
|
616
684
|
|
|
617
685
|
it("should use polled position when getCurrentTime returns undefined", () => {
|
|
618
|
-
|
|
619
|
-
|
|
620
|
-
|
|
686
|
+
const mockGetRef = vi.spyOn(mockedPlaybackObserver.observer, "getReference");
|
|
687
|
+
vi.spyOn(mockedPlaybackObserver.observer, "getCurrentTime").mockReturnValue(
|
|
688
|
+
undefined,
|
|
689
|
+
);
|
|
690
|
+
vi.spyOn(mockSegmentSink, "getLastKnownInventory").mockReturnValue([
|
|
691
|
+
makeBufferedChunk({
|
|
621
692
|
start: 14.6,
|
|
622
693
|
end: 15.4,
|
|
623
694
|
bufferedStart: 14.6,
|
|
624
695
|
bufferedEnd: 15.4,
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
},
|
|
696
|
+
periodId: "period-1",
|
|
697
|
+
periodStart: 10,
|
|
698
|
+
adaptationId: "adaptation-2",
|
|
699
|
+
}),
|
|
630
700
|
]);
|
|
631
701
|
|
|
632
702
|
const result = getAdaptationSwitchStrategy(
|
|
@@ -634,11 +704,11 @@ describe("getAdaptationSwitchStrategy", () => {
|
|
|
634
704
|
mockPeriod,
|
|
635
705
|
mockAdaptation,
|
|
636
706
|
"seamless",
|
|
637
|
-
|
|
707
|
+
mockedPlaybackObserver.observer,
|
|
638
708
|
{ onCodecSwitch: "continue" },
|
|
639
709
|
);
|
|
640
710
|
|
|
641
|
-
expect(
|
|
711
|
+
expect(mockGetRef).toHaveBeenCalled();
|
|
642
712
|
// Should still exclude based on polled position (15)
|
|
643
713
|
expect(result).toEqual({ type: "continue", value: undefined });
|
|
644
714
|
});
|