shaka-player 4.4.3 → 4.6.0

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.
Files changed (307) hide show
  1. package/.github/ISSUE_TEMPLATE/bug_report.md +1 -1
  2. package/.github/workflows/release-please.yaml +2 -27
  3. package/AUTHORS +2 -0
  4. package/CHANGELOG.md +156 -39
  5. package/CODE_OF_CONDUCT.md +1 -1
  6. package/CONTRIBUTORS +2 -0
  7. package/README.md +54 -42
  8. package/demo/asset_card.js +18 -21
  9. package/demo/cast_receiver/index.html +0 -1
  10. package/demo/close_button.js +0 -3
  11. package/demo/common/asset.js +33 -22
  12. package/demo/common/assets.js +249 -60
  13. package/demo/config.js +219 -253
  14. package/demo/custom.js +88 -133
  15. package/demo/front.js +7 -10
  16. package/demo/index.html +19 -22
  17. package/demo/input.js +6 -11
  18. package/demo/input_container.js +8 -9
  19. package/demo/main.js +62 -126
  20. package/demo/search.js +29 -34
  21. package/demo/service_worker.js +0 -3
  22. package/demo/tooltip.js +3 -5
  23. package/demo/visualizer.js +3 -5
  24. package/demo/visualizer_button.js +1 -20
  25. package/dist/controls.css +1 -1
  26. package/dist/controls.css.map +1 -1
  27. package/dist/demo.compiled.debug.js +211 -228
  28. package/dist/demo.compiled.debug.map +4 -4
  29. package/dist/demo.compiled.js +211 -228
  30. package/dist/demo.compiled.map +4 -4
  31. package/dist/deps.js +42 -37
  32. package/dist/locales.js +34 -30
  33. package/dist/receiver.compiled.debug.js +64 -77
  34. package/dist/receiver.compiled.debug.map +4 -4
  35. package/dist/receiver.compiled.js +64 -77
  36. package/dist/receiver.compiled.map +4 -4
  37. package/dist/shaka-player.compiled.d.ts +343 -151
  38. package/dist/shaka-player.compiled.debug.d.ts +343 -151
  39. package/dist/shaka-player.compiled.debug.externs.js +356 -117
  40. package/dist/shaka-player.compiled.debug.js +952 -811
  41. package/dist/shaka-player.compiled.debug.map +4 -4
  42. package/dist/shaka-player.compiled.externs.js +356 -117
  43. package/dist/shaka-player.compiled.js +1165 -1078
  44. package/dist/shaka-player.compiled.map +4 -4
  45. package/dist/shaka-player.ui.d.ts +359 -153
  46. package/dist/shaka-player.ui.debug.d.ts +359 -153
  47. package/dist/shaka-player.ui.debug.externs.js +382 -117
  48. package/dist/shaka-player.ui.debug.js +1084 -918
  49. package/dist/shaka-player.ui.debug.map +4 -4
  50. package/dist/shaka-player.ui.externs.js +382 -117
  51. package/dist/shaka-player.ui.js +1377 -1274
  52. package/dist/shaka-player.ui.map +4 -4
  53. package/docs/design/lcevc-integration.md +14 -14
  54. package/docs/tutorials/ad_monetization.md +54 -0
  55. package/docs/tutorials/basic-usage.md +2 -1
  56. package/docs/tutorials/errors.md +2 -1
  57. package/docs/tutorials/faq.md +27 -55
  58. package/docs/tutorials/index.json +2 -1
  59. package/docs/tutorials/lcevc.md +118 -0
  60. package/docs/tutorials/offline.md +10 -8
  61. package/docs/tutorials/plugins.md +5 -0
  62. package/docs/tutorials/ui-customization.md +17 -0
  63. package/docs/tutorials/ui.md +2 -1
  64. package/docs/tutorials/upgrade.md +3 -0
  65. package/externs/css_style_declaration.js +19 -0
  66. package/externs/lcevc.js +37 -13
  67. package/externs/managedmediasource.js +24 -0
  68. package/externs/media_remote.js +68 -0
  69. package/externs/mediatailor.js +193 -0
  70. package/externs/pictureinpicture.js +11 -0
  71. package/externs/shaka/abr_manager.js +6 -2
  72. package/externs/shaka/ads.js +27 -0
  73. package/externs/shaka/cea.js +7 -0
  74. package/externs/shaka/codecs.js +5 -3
  75. package/externs/shaka/manifest.js +31 -10
  76. package/externs/shaka/manifest_parser.js +24 -1
  77. package/externs/shaka/net.js +2 -2
  78. package/externs/shaka/offline.js +13 -2
  79. package/externs/shaka/player.js +65 -8
  80. package/externs/shaka/text.js +3 -1
  81. package/externs/shaka/transmuxer.js +1 -1
  82. package/karma.conf.js +7 -3
  83. package/lib/abr/simple_abr_manager.js +66 -9
  84. package/lib/ads/ad_manager.js +104 -50
  85. package/lib/ads/media_tailor_ad.js +297 -0
  86. package/lib/ads/media_tailor_ad_manager.js +839 -0
  87. package/lib/cast/cast_receiver.js +1 -1
  88. package/lib/cea/cea_decoder.js +28 -0
  89. package/lib/cea/dummy_caption_decoder.js +5 -0
  90. package/lib/cea/ts_cea_parser.js +15 -2
  91. package/lib/config/codec_switching_strategy.js +24 -0
  92. package/lib/dash/content_protection.js +120 -2
  93. package/lib/dash/dash_parser.js +322 -93
  94. package/lib/dash/mpd_utils.js +62 -37
  95. package/lib/dash/segment_base.js +17 -10
  96. package/lib/dash/segment_list.js +18 -9
  97. package/lib/dash/segment_template.js +122 -107
  98. package/lib/dependencies/all.js +8 -7
  99. package/lib/hls/hls_classes.js +28 -43
  100. package/lib/hls/hls_parser.js +798 -658
  101. package/lib/hls/hls_utils.js +64 -5
  102. package/lib/hls/manifest_text_parser.js +7 -11
  103. package/lib/lcevc/lcevc_dec.js +220 -0
  104. package/lib/media/adaptation_set.js +32 -14
  105. package/lib/media/adaptation_set_criteria.js +86 -16
  106. package/lib/media/closed_caption_parser.js +13 -0
  107. package/lib/media/content_workarounds.js +6 -0
  108. package/lib/media/drm_engine.js +8 -13
  109. package/lib/media/manifest_parser.js +8 -113
  110. package/lib/media/media_source_capabilities.js +10 -3
  111. package/lib/media/media_source_engine.js +286 -44
  112. package/lib/media/play_rate_controller.js +8 -38
  113. package/lib/media/presentation_timeline.js +7 -1
  114. package/lib/media/quality_observer.js +1 -1
  115. package/lib/media/segment_index.js +6 -6
  116. package/lib/media/segment_prefetch.js +92 -24
  117. package/lib/media/segment_reference.js +73 -7
  118. package/lib/media/segment_utils.js +343 -0
  119. package/lib/media/stall_detector.js +0 -3
  120. package/lib/media/streaming_engine.js +73 -38
  121. package/lib/mss/mss_parser.js +19 -2
  122. package/lib/net/networking_engine.js +67 -12
  123. package/lib/net/networking_utils.js +95 -0
  124. package/lib/offline/indexeddb/v1_storage_cell.js +3 -0
  125. package/lib/offline/indexeddb/v2_storage_cell.js +3 -0
  126. package/lib/offline/manifest_converter.js +3 -0
  127. package/lib/offline/offline_manifest_parser.js +10 -0
  128. package/lib/offline/storage.js +14 -7
  129. package/lib/player.js +1098 -1537
  130. package/lib/polyfill/mediasource.js +22 -1
  131. package/lib/text/cue.js +15 -0
  132. package/lib/text/mp4_ttml_parser.js +2 -2
  133. package/lib/text/srt_text_parser.js +2 -2
  134. package/lib/text/stub_text_displayer.js +51 -0
  135. package/lib/text/text_engine.js +3 -2
  136. package/lib/text/ttml_text_parser.js +45 -5
  137. package/lib/text/ui_text_displayer.js +8 -0
  138. package/lib/text/vtt_text_parser.js +40 -22
  139. package/lib/transmuxer/aac_transmuxer.js +1 -1
  140. package/lib/transmuxer/ac3_transmuxer.js +1 -1
  141. package/lib/transmuxer/ec3_transmuxer.js +1 -1
  142. package/lib/transmuxer/h264.js +5 -4
  143. package/lib/transmuxer/h265.js +863 -0
  144. package/lib/transmuxer/mp3_transmuxer.js +1 -1
  145. package/lib/transmuxer/mpeg_ts_transmuxer.js +4 -3
  146. package/lib/transmuxer/mss_transmuxer.js +1 -1
  147. package/lib/transmuxer/ts_transmuxer.js +187 -22
  148. package/lib/util/buffer_utils.js +26 -4
  149. package/lib/util/content_steering_manager.js +358 -0
  150. package/lib/util/error.js +30 -15
  151. package/lib/util/exp_golomb.js +30 -2
  152. package/lib/util/fairplay_utils.js +1 -1
  153. package/lib/util/fake_event.js +8 -1
  154. package/lib/util/id3_utils.js +50 -1
  155. package/lib/util/manifest_parser_utils.js +12 -8
  156. package/lib/util/mp4_generator.js +6 -8
  157. package/lib/util/mutex.js +59 -0
  158. package/lib/util/object_utils.js +1 -1
  159. package/lib/util/periods.js +156 -179
  160. package/lib/util/platform.js +44 -3
  161. package/lib/util/player_configuration.js +43 -6
  162. package/lib/util/state_history.js +6 -2
  163. package/lib/util/stream_utils.js +206 -283
  164. package/lib/util/ts_parser.js +335 -98
  165. package/lib/util/uint8array_utils.js +5 -1
  166. package/lib/util/xml_utils.js +5 -0
  167. package/maintained-branches.md +3 -2
  168. package/package.json +4 -6
  169. package/roadmap.md +25 -5
  170. package/shaka-player.uncompiled.js +2 -2
  171. package/support.html +0 -1
  172. package/test/abr/simple_abr_manager_unit.js +33 -33
  173. package/test/ads/ad_manager_unit.js +3 -2
  174. package/test/cast/cast_receiver_integration.js +50 -4
  175. package/test/cast/cast_utils_unit.js +2 -0
  176. package/test/cea/cea_decoder_unit.js +7 -0
  177. package/test/codec_switching/codec_switching_integration.js +182 -0
  178. package/test/dash/dash_parser_content_protection_unit.js +2 -0
  179. package/test/dash/dash_parser_integration.js +74 -0
  180. package/test/dash/dash_parser_live_unit.js +2 -19
  181. package/test/dash/dash_parser_manifest_unit.js +536 -2
  182. package/test/dash/dash_parser_segment_base_unit.js +2 -0
  183. package/test/dash/dash_parser_segment_list_unit.js +2 -0
  184. package/test/dash/dash_parser_segment_template_unit.js +2 -0
  185. package/test/dash/mpd_utils_unit.js +61 -30
  186. package/test/demo/demo_unit.js +0 -16
  187. package/test/hls/hls_live_unit.js +14 -3
  188. package/test/hls/hls_parser_unit.js +385 -33
  189. package/test/hls/manifest_text_parser_unit.js +32 -99
  190. package/test/media/adaptation_set_criteria_unit.js +284 -15
  191. package/test/media/adaptation_set_unit.js +2 -0
  192. package/test/media/content_workarounds_unit.js +1 -1
  193. package/test/media/drm_engine_unit.js +3 -3
  194. package/test/media/media_source_engine_unit.js +166 -2
  195. package/test/media/play_rate_controller_unit.js +0 -48
  196. package/test/media/segment_index_unit.js +5 -4
  197. package/test/media/segment_prefetch_unit.js +1 -1
  198. package/test/media/streaming_engine_unit.js +17 -17
  199. package/test/mss/mss_parser_unit.js +2 -0
  200. package/test/mss/mss_player_integration.js +3 -2
  201. package/test/net/networking_engine_unit.js +3 -3
  202. package/test/{media/manifest_parser_unit.js → net/networking_utils_unit.js} +2 -2
  203. package/test/offline/manifest_convert_unit.js +14 -0
  204. package/test/offline/offline_integration.js +2 -1
  205. package/test/offline/storage_integration.js +22 -13
  206. package/test/player_external.js +4 -2
  207. package/test/player_integration.js +15 -4
  208. package/test/player_load_graph_integration.js +47 -151
  209. package/test/player_src_equals_external.js +1 -0
  210. package/test/player_src_equals_integration.js +71 -4
  211. package/test/player_unit.js +182 -158
  212. package/test/test/assets/dash-aes-128/Fragments(video=0,format=mpd-time-csf) +0 -0
  213. package/test/test/assets/dash-aes-128/Fragments(video=20000000,format=mpd-time-csf) +0 -0
  214. package/test/test/assets/dash-aes-128/Fragments(video=40000000,format=mpd-time-csf) +0 -0
  215. package/test/test/assets/dash-aes-128/Fragments(video=60000000,format=mpd-time-csf) +0 -0
  216. package/test/test/assets/dash-aes-128/Fragments(video=i,format=mpd-time-csf) +0 -0
  217. package/test/test/assets/dash-aes-128/dash.mpd +18 -0
  218. package/test/test/assets/dash-aes-128/license +1 -0
  219. package/test/test/assets/dash-multi-codec/audio_en_2c_128k_aac.mp4 +0 -0
  220. package/test/test/assets/dash-multi-codec/audio_es_2c_64k_opus.webm +0 -0
  221. package/test/test/assets/dash-multi-codec/dash.mpd +32 -0
  222. package/test/test/assets/dash-multi-codec/video_144p_108k_h264.mp4 +0 -0
  223. package/test/test/assets/hls-ts-h265/0.ts +0 -0
  224. package/test/test/assets/hls-ts-h265/hevc.m3u8 +6 -0
  225. package/test/test/assets/hls-ts-h265/index.m3u8 +7 -0
  226. package/test/test/assets/hls-ts-muxed-aac-h265/0.ts +0 -0
  227. package/test/test/assets/hls-ts-muxed-aac-h265/1.ts +0 -0
  228. package/test/test/assets/hls-ts-muxed-aac-h265/media.m3u8 +9 -0
  229. package/test/test/assets/hls-ts-muxed-ac3-h264/media.m3u8 +24 -0
  230. package/test/test/assets/hls-ts-muxed-ac3-h264/s_00000.ts +0 -0
  231. package/test/test/assets/hls-ts-muxed-ac3-h264/s_00001.ts +0 -0
  232. package/test/test/assets/hls-ts-muxed-ac3-h264/s_00002.ts +0 -0
  233. package/test/test/assets/hls-ts-muxed-ac3-h264/s_00003.ts +0 -0
  234. package/test/test/assets/hls-ts-muxed-ac3-h264/s_00004.ts +0 -0
  235. package/test/test/assets/hls-ts-muxed-ac3-h264/s_00005.ts +0 -0
  236. package/test/test/assets/hls-ts-muxed-ec3-h264/ChID_voices_1280x720p_25fps_h264_6ch_256kbps_ddp_sub_0000.ts +0 -0
  237. package/test/test/assets/hls-ts-muxed-ec3-h264/ChID_voices_1280x720p_25fps_h264_6ch_256kbps_ddp_sub_0001.ts +0 -0
  238. package/test/test/assets/hls-ts-muxed-ec3-h264/ChID_voices_1280x720p_25fps_h264_6ch_256kbps_ddp_sub_0002.ts +0 -0
  239. package/test/test/assets/hls-ts-muxed-ec3-h264/ChID_voices_1280x720p_25fps_h264_6ch_256kbps_ddp_sub_0003.ts +0 -0
  240. package/test/test/assets/hls-ts-muxed-ec3-h264/prog_index.m3u8 +14 -0
  241. package/test/test/assets/hls-ts-muxed-mp3-h264/index.m3u8 +23 -0
  242. package/test/test/assets/hls-ts-muxed-mp3-h264/seg-1-v1-a1.ts +0 -0
  243. package/test/test/assets/hls-ts-muxed-mp3-h264/seg-2-v1-a1.ts +0 -0
  244. package/test/test/assets/hls-ts-muxed-mp3-h264/seg-3-v1-a1.ts +0 -0
  245. package/test/test/assets/hls-ts-muxed-mp3-h264/seg-4-v1-a1.ts +0 -0
  246. package/test/test/assets/hls-ts-muxed-mp3-h264/seg-5-v1-a1.ts +0 -0
  247. package/test/test/assets/hls-ts-muxed-mp3-h264/seg-6-v1-a1.ts +0 -0
  248. package/test/test/assets/hls-ts-muxed-mp3-h264/seg-7-v1-a1.ts +0 -0
  249. package/test/test/assets/hls-ts-muxed-mp3-h264/seg-8-v1-a1.ts +0 -0
  250. package/test/test/util/dash_parser_util.js +4 -0
  251. package/test/test/util/fake_ad_manager.js +20 -0
  252. package/test/test/util/fake_media_source_engine.js +13 -2
  253. package/test/test/util/fake_networking_engine.js +9 -1
  254. package/test/test/util/fake_segment_prefetch.js +3 -0
  255. package/test/test/util/manifest_generator.js +11 -3
  256. package/test/test/util/manifest_parser_util.js +14 -2
  257. package/test/test/util/mss_parser_util.js +4 -0
  258. package/test/test/util/offline_utils.js +2 -0
  259. package/test/test/util/simple_fakes.js +2 -2
  260. package/test/test/util/streaming_engine_util.js +10 -4
  261. package/test/test/util/test_scheme.js +6 -0
  262. package/test/test/util/ui_utils.js +4 -3
  263. package/test/text/mp4_ttml_parser_unit.js +4 -4
  264. package/test/text/srt_text_parser_unit.js +1 -1
  265. package/test/text/text_displayer_layout_unit.js +1 -1
  266. package/test/text/text_engine_unit.js +6 -0
  267. package/test/text/ttml_text_parser_unit.js +85 -2
  268. package/test/text/vtt_text_parser_unit.js +103 -31
  269. package/test/transmuxer/transmuxer_engine_integration.js +9 -0
  270. package/test/transmuxer/transmuxer_integration.js +150 -3
  271. package/test/ui/ad_ui_unit.js +2 -2
  272. package/test/ui/ui_customization_unit.js +17 -16
  273. package/test/ui/ui_integration.js +30 -20
  274. package/test/ui/ui_unit.js +28 -29
  275. package/test/util/buffer_utils_unit.js +1 -1
  276. package/test/util/content_steering_manager_unit.js +427 -0
  277. package/test/util/id3_utils_unit.js +52 -0
  278. package/test/util/stream_utils_unit.js +207 -169
  279. package/test/util/ts_parser_unit.js +3 -3
  280. package/third_party/closure-uri/uri.js +13 -1
  281. package/ui/audio_language_selection.js +9 -2
  282. package/ui/controls.js +125 -0
  283. package/ui/externs/ui.js +24 -2
  284. package/ui/language_utils.js +43 -8
  285. package/ui/less/range_elements.less +33 -0
  286. package/ui/locales/en.json +1 -0
  287. package/ui/locales/es-419.json +1 -0
  288. package/ui/locales/es.json +1 -0
  289. package/ui/locales/source.json +4 -0
  290. package/ui/localization.js +10 -0
  291. package/ui/pip_button.js +22 -120
  292. package/ui/remote_button.js +203 -0
  293. package/ui/resolution_selection.js +47 -10
  294. package/ui/seek_bar.js +296 -3
  295. package/ui/text_selection.js +2 -1
  296. package/ui/ui.js +11 -4
  297. package/demo/common/message_ids.js +0 -309
  298. package/demo/locales/en.json +0 -288
  299. package/demo/locales/source.json +0 -1146
  300. package/externs/mux.js +0 -69
  301. package/lib/lcevc/lcevc_dil.js +0 -152
  302. package/lib/routing/node.js +0 -23
  303. package/lib/routing/payload.js +0 -43
  304. package/lib/routing/walker.js +0 -587
  305. package/lib/transmuxer/muxjs_transmuxer.js +0 -242
  306. package/test/routing/walker_unit.js +0 -504
  307. package/test/transmuxer/muxjs_transmuxer_integration.js +0 -177
@@ -0,0 +1,427 @@
1
+ /*! @license
2
+ * Shaka Player
3
+ * Copyright 2016 Google LLC
4
+ * SPDX-License-Identifier: Apache-2.0
5
+ */
6
+
7
+ describe('ContentSteeringManager', () => {
8
+ /** @type {!shaka.test.FakeNetworkingEngine} */
9
+ let fakeNetEngine;
10
+
11
+ /** @type {!shaka.util.ContentSteeringManager} */
12
+ let manager;
13
+
14
+ beforeEach(() => {
15
+ fakeNetEngine = new shaka.test.FakeNetworkingEngine();
16
+ const playerInterface = {
17
+ networkingEngine: fakeNetEngine,
18
+ modifyManifestRequest: fail,
19
+ modifySegmentRequest: fail,
20
+ filter: fail,
21
+ makeTextStreamsForClosedCaptions: fail,
22
+ onTimelineRegionAdded: fail,
23
+ onEvent: fail,
24
+ onError: fail,
25
+ isLowLatencyMode: fail,
26
+ isAutoLowLatencyMode: fail,
27
+ enableLowLatencyMode: fail,
28
+ updateDuration: fail,
29
+ newDrmInfo: fail,
30
+ onManifestUpdated: fail,
31
+ getBandwidthEstimate: () => 1e6,
32
+ };
33
+ const config = shaka.util.PlayerConfiguration.createDefault().manifest;
34
+ manager = new shaka.util.ContentSteeringManager(playerInterface);
35
+ manager.configure(config);
36
+ manager.setBaseUris([
37
+ 'http://default',
38
+ ]);
39
+ manager.addLocation('foo', 'cdn-a', 'http://cdn-a');
40
+ manager.addLocation('foo', 'cdn-b', 'http://cdn-b');
41
+ manager.addLocation('foo', 'cdn-c', 'http://cdn-c');
42
+ });
43
+
44
+ afterEach(async () => {
45
+ await manager.destroy();
46
+ });
47
+
48
+ describe('defaultPathwayId', () => {
49
+ it('allows no value', () => {
50
+ manager.setDefaultPathwayId(null);
51
+
52
+ const locations = manager.getLocations('foo');
53
+ expect(locations.length).toBe(3);
54
+ expect(locations[0]).toBe('http://cdn-a');
55
+ expect(locations[1]).toBe('http://cdn-b');
56
+ expect(locations[2]).toBe('http://cdn-c');
57
+ });
58
+
59
+ it('allows one value', () => {
60
+ manager.setDefaultPathwayId('cdn-b');
61
+
62
+ const locations = manager.getLocations('foo');
63
+ expect(locations.length).toBe(1);
64
+ expect(locations[0]).toBe('http://cdn-b');
65
+ });
66
+
67
+ it('allows multiple values', () => {
68
+ manager.setDefaultPathwayId('cdn-b,cdn-a,cdn-c');
69
+
70
+ const locations = manager.getLocations('foo');
71
+ expect(locations.length).toBe(3);
72
+ expect(locations[0]).toBe('http://cdn-b');
73
+ expect(locations[1]).toBe('http://cdn-a');
74
+ expect(locations[2]).toBe('http://cdn-c');
75
+ });
76
+ });
77
+
78
+ describe('queryParams', () => {
79
+ it('send the correct value for DASH', async () => {
80
+ manager.setManifestType(shaka.media.ManifestParser.DASH);
81
+ const manifest = JSON.stringify({
82
+ 'VERSION': 1,
83
+ 'TTL': 1,
84
+ 'RELOAD-URI': 'http://foo.bar/update',
85
+ 'PATHWAY-PRIORITY': [
86
+ 'cdn-b',
87
+ 'cdn-a',
88
+ ],
89
+ });
90
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifest);
91
+
92
+ await manager.requestInfo('http://foo.bar/manifest');
93
+
94
+ const locations = manager.getLocations('foo');
95
+ expect(locations.length).toBe(2);
96
+ expect(locations[0]).toBe('http://cdn-b');
97
+ expect(locations[1]).toBe('http://cdn-a');
98
+
99
+ const manifestUpdate = JSON.stringify({
100
+ 'VERSION': 1,
101
+ 'TTL': 1,
102
+ 'RELOAD-URI': 'http://foo.bar/update',
103
+ 'PATHWAY-PRIORITY': [
104
+ 'cdn-b',
105
+ ],
106
+ });
107
+ const updateUrl = 'http://foo.bar/update?_DASH_pathway=cdn-b&_DASH_throughput=1000000';
108
+ fakeNetEngine.setResponseText(updateUrl, manifestUpdate);
109
+
110
+ await shaka.test.Util.delay(1);
111
+
112
+ const newLocations = manager.getLocations('foo');
113
+ expect(newLocations.length).toBe(1);
114
+ expect(newLocations[0]).toBe('http://cdn-b');
115
+ });
116
+
117
+ it('send the correct value for HLS', async () => {
118
+ manager.setManifestType(shaka.media.ManifestParser.HLS);
119
+ const manifest = JSON.stringify({
120
+ 'VERSION': 1,
121
+ 'TTL': 1,
122
+ 'RELOAD-URI': 'http://foo.bar/update',
123
+ 'PATHWAY-PRIORITY': [
124
+ 'cdn-b',
125
+ 'cdn-a',
126
+ ],
127
+ });
128
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifest);
129
+
130
+ await manager.requestInfo('http://foo.bar/manifest');
131
+
132
+ const locations = manager.getLocations('foo');
133
+ expect(locations.length).toBe(2);
134
+ expect(locations[0]).toBe('http://cdn-b');
135
+ expect(locations[1]).toBe('http://cdn-a');
136
+
137
+ const manifestUpdate = JSON.stringify({
138
+ 'VERSION': 1,
139
+ 'TTL': 1,
140
+ 'RELOAD-URI': 'http://foo.bar/update',
141
+ 'PATHWAY-PRIORITY': [
142
+ 'cdn-b',
143
+ ],
144
+ });
145
+ const updateUrl = 'http://foo.bar/update?_HLS_pathway=cdn-b&_HLS_throughput=1000000';
146
+ fakeNetEngine.setResponseText(updateUrl, manifestUpdate);
147
+
148
+ await shaka.test.Util.delay(1);
149
+
150
+ const newLocations = manager.getLocations('foo');
151
+ expect(newLocations.length).toBe(1);
152
+ expect(newLocations[0]).toBe('http://cdn-b');
153
+ });
154
+
155
+ it('not send value for unknown manifest', async () => {
156
+ const manifest = JSON.stringify({
157
+ 'VERSION': 1,
158
+ 'TTL': 1,
159
+ 'RELOAD-URI': 'http://foo.bar/update',
160
+ 'PATHWAY-PRIORITY': [
161
+ 'cdn-b',
162
+ 'cdn-a',
163
+ ],
164
+ });
165
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifest);
166
+
167
+ await manager.requestInfo('http://foo.bar/manifest');
168
+
169
+ const locations = manager.getLocations('foo');
170
+ expect(locations.length).toBe(2);
171
+ expect(locations[0]).toBe('http://cdn-b');
172
+ expect(locations[1]).toBe('http://cdn-a');
173
+
174
+ const manifestUpdate = JSON.stringify({
175
+ 'VERSION': 1,
176
+ 'TTL': 1,
177
+ 'RELOAD-URI': 'http://foo.bar/update',
178
+ 'PATHWAY-PRIORITY': [
179
+ 'cdn-b',
180
+ ],
181
+ });
182
+ fakeNetEngine.setResponseText('http://foo.bar/update', manifestUpdate);
183
+
184
+ await shaka.test.Util.delay(1);
185
+
186
+ const newLocations = manager.getLocations('foo');
187
+ expect(newLocations.length).toBe(1);
188
+ expect(newLocations[0]).toBe('http://cdn-b');
189
+ });
190
+ });
191
+
192
+ describe('steeringManifest', () => {
193
+ it('ignores manifest with a version different than 1', async () => {
194
+ const manifest = JSON.stringify({
195
+ 'VERSION': 35,
196
+ 'TTL': 10,
197
+ 'RELOAD-URI': 'http://foo.bar/update',
198
+ 'PATHWAY-PRIORITY': [
199
+ 'cdn-b',
200
+ 'cdn-a',
201
+ ],
202
+ });
203
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifest);
204
+
205
+ await manager.requestInfo('http://foo.bar/manifest');
206
+
207
+ const locations = manager.getLocations('foo');
208
+ expect(locations.length).toBe(3);
209
+ expect(locations[0]).toBe('http://cdn-a');
210
+ expect(locations[1]).toBe('http://cdn-b');
211
+ expect(locations[2]).toBe('http://cdn-c');
212
+ });
213
+
214
+ it('honors RELOAD-URI', async () => {
215
+ const manifest = JSON.stringify({
216
+ 'VERSION': 1,
217
+ 'TTL': 1,
218
+ 'RELOAD-URI': 'http://foo.bar/update',
219
+ 'PATHWAY-PRIORITY': [
220
+ 'cdn-b',
221
+ 'cdn-a',
222
+ ],
223
+ });
224
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifest);
225
+
226
+ await manager.requestInfo('http://foo.bar/manifest');
227
+
228
+ const locations = manager.getLocations('foo');
229
+ expect(locations.length).toBe(2);
230
+ expect(locations[0]).toBe('http://cdn-b');
231
+ expect(locations[1]).toBe('http://cdn-a');
232
+
233
+ const manifestUpdate = JSON.stringify({
234
+ 'VERSION': 1,
235
+ 'TTL': 1,
236
+ 'RELOAD-URI': 'http://foo.bar/update',
237
+ 'PATHWAY-PRIORITY': [
238
+ 'cdn-b',
239
+ ],
240
+ });
241
+ fakeNetEngine.setResponseText('http://foo.bar/update', manifestUpdate);
242
+
243
+ await shaka.test.Util.delay(1);
244
+
245
+ const newLocations = manager.getLocations('foo');
246
+ expect(newLocations.length).toBe(1);
247
+ expect(newLocations[0]).toBe('http://cdn-b');
248
+ });
249
+
250
+ it('fallback for no RELOAD-URI', async () => {
251
+ const manifest = JSON.stringify({
252
+ 'VERSION': 1,
253
+ 'TTL': 1,
254
+ 'PATHWAY-PRIORITY': [
255
+ 'cdn-b',
256
+ 'cdn-a',
257
+ ],
258
+ });
259
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifest);
260
+
261
+ await manager.requestInfo('http://foo.bar/manifest');
262
+
263
+ const locations = manager.getLocations('foo');
264
+ expect(locations.length).toBe(2);
265
+ expect(locations[0]).toBe('http://cdn-b');
266
+ expect(locations[1]).toBe('http://cdn-a');
267
+
268
+ const manifestUpdate = JSON.stringify({
269
+ 'VERSION': 1,
270
+ 'TTL': 1,
271
+ 'PATHWAY-PRIORITY': [
272
+ 'cdn-b',
273
+ ],
274
+ });
275
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifestUpdate);
276
+
277
+ await shaka.test.Util.delay(1);
278
+
279
+ const newLocations = manager.getLocations('foo');
280
+ expect(newLocations.length).toBe(1);
281
+ expect(newLocations[0]).toBe('http://cdn-b');
282
+ });
283
+
284
+ it('honors TTL', async () => {
285
+ const manifest = JSON.stringify({
286
+ 'VERSION': 1,
287
+ 'TTL': 1,
288
+ 'RELOAD-URI': 'http://foo.bar/update',
289
+ 'PATHWAY-PRIORITY': [
290
+ 'cdn-b',
291
+ 'cdn-a',
292
+ ],
293
+ });
294
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifest);
295
+
296
+ await manager.requestInfo('http://foo.bar/manifest');
297
+
298
+ const locations = manager.getLocations('foo');
299
+ expect(locations.length).toBe(2);
300
+ expect(locations[0]).toBe('http://cdn-b');
301
+ expect(locations[1]).toBe('http://cdn-a');
302
+
303
+ const manifestUpdate = JSON.stringify({
304
+ 'VERSION': 1,
305
+ 'TTL': 2,
306
+ 'RELOAD-URI': 'http://foo.bar/update',
307
+ 'PATHWAY-PRIORITY': [
308
+ 'cdn-b',
309
+ ],
310
+ });
311
+ fakeNetEngine.setResponseText('http://foo.bar/update', manifestUpdate);
312
+
313
+ await shaka.test.Util.delay(2);
314
+
315
+ const newLocations = manager.getLocations('foo');
316
+ expect(newLocations.length).toBe(1);
317
+ expect(newLocations[0]).toBe('http://cdn-b');
318
+ });
319
+ });
320
+
321
+ describe('get correct locations', () => {
322
+ it('with PATHWAY-PRIORITY', async () => {
323
+ const manifest = JSON.stringify({
324
+ 'VERSION': 1,
325
+ 'TTL': 10,
326
+ 'RELOAD-URI': 'http://foo.bar/update',
327
+ 'PATHWAY-PRIORITY': [
328
+ 'cdn-b',
329
+ 'cdn-a',
330
+ 'cdn-c',
331
+ ],
332
+ });
333
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifest);
334
+
335
+ await manager.requestInfo('http://foo.bar/manifest');
336
+
337
+ const locations = manager.getLocations('foo');
338
+ expect(locations.length).toBe(3);
339
+ expect(locations[0]).toBe('http://cdn-b');
340
+ expect(locations[1]).toBe('http://cdn-a');
341
+ expect(locations[2]).toBe('http://cdn-c');
342
+ });
343
+
344
+ it('with PATHWAY-PRIORITY and PATHWAY-CLONES', async () => {
345
+ const manifest = JSON.stringify({
346
+ 'VERSION': 1,
347
+ 'TTL': 10,
348
+ 'RELOAD-URI': 'http://foo.bar/update',
349
+ 'PATHWAY-PRIORITY': [
350
+ 'cdn-d',
351
+ 'cdn-b',
352
+ 'cdn-a',
353
+ 'cdn-c',
354
+ ],
355
+ 'PATHWAY-CLONES': [
356
+ {
357
+ 'BASE-ID': 'cdn-c',
358
+ 'ID': 'cdn-d',
359
+ 'URI-REPLACEMENT': {
360
+ 'HOST': 'cdn-d',
361
+ },
362
+ },
363
+ ],
364
+ });
365
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifest);
366
+
367
+ await manager.requestInfo('http://foo.bar/manifest');
368
+
369
+ const locations = manager.getLocations('foo');
370
+ expect(locations.length).toBe(4);
371
+ expect(locations[0]).toBe('http://cdn-d');
372
+ expect(locations[1]).toBe('http://cdn-b');
373
+ expect(locations[2]).toBe('http://cdn-a');
374
+ expect(locations[3]).toBe('http://cdn-c');
375
+ });
376
+
377
+ it('without PATHWAY-PRIORITY but with defaultPathwayId', () => {
378
+ manager.setDefaultPathwayId('cdn-b,cdn-a,cdn-c');
379
+
380
+ const locations = manager.getLocations('foo');
381
+ expect(locations.length).toBe(3);
382
+ expect(locations[0]).toBe('http://cdn-b');
383
+ expect(locations[1]).toBe('http://cdn-a');
384
+ expect(locations[2]).toBe('http://cdn-c');
385
+ });
386
+
387
+ it('without PATHWAY-PRIORITY neither defaultPathwayId', () => {
388
+ const locations = manager.getLocations('foo');
389
+ expect(locations.length).toBe(3);
390
+ expect(locations[0]).toBe('http://cdn-a');
391
+ expect(locations[1]).toBe('http://cdn-b');
392
+ expect(locations[2]).toBe('http://cdn-c');
393
+ });
394
+
395
+ it('use baseuris if no locations', () => {
396
+ manager.clearPreviousLocations();
397
+ const locations = manager.getLocations('foo');
398
+ expect(locations.length).toBe(1);
399
+ expect(locations[0]).toBe('http://default');
400
+ });
401
+ });
402
+
403
+ describe('allow ban locations', () => {
404
+ it('with PATHWAY-PRIORITY', async () => {
405
+ const manifest = JSON.stringify({
406
+ 'VERSION': 1,
407
+ 'TTL': 10,
408
+ 'RELOAD-URI': 'http://foo.bar/update',
409
+ 'PATHWAY-PRIORITY': [
410
+ 'cdn-b',
411
+ 'cdn-a',
412
+ 'cdn-c',
413
+ ],
414
+ });
415
+ fakeNetEngine.setResponseText('http://foo.bar/manifest', manifest);
416
+
417
+ await manager.requestInfo('http://foo.bar/manifest');
418
+
419
+ manager.banLocation('http://cdn-b');
420
+
421
+ const locations = manager.getLocations('foo');
422
+ expect(locations.length).toBe(2);
423
+ expect(locations[0]).toBe('http://cdn-a');
424
+ expect(locations[1]).toBe('http://cdn-c');
425
+ });
426
+ });
427
+ });
@@ -13,6 +13,44 @@ describe('Id3Utils', () => {
13
13
  expect(Id3Utils.getID3Frames(new Uint8Array([]))).toEqual([]);
14
14
  });
15
15
 
16
+ it('parse an APIC frame with image data', () => {
17
+ const apicValue = new Uint8Array([
18
+ 3, 105, 109, 97, 103, 101, 47, 106, 112, 101, 103, 0, 3, 83, 104, 97,
19
+ 107, 97, 0, 1, 2, 3,
20
+ ]);
21
+ const apicFrame = Id3Generator.generateId3Frame('APIC', apicValue);
22
+ const apicID3 = Id3Generator.generateId3(apicFrame);
23
+ const expectedID3 = [
24
+ {
25
+ key: 'APIC',
26
+ mimeType: 'image/jpeg',
27
+ pictureType: 3,
28
+ description: 'Shaka',
29
+ data: BufferUtils.toArrayBuffer(new Uint8Array([1, 2, 3])),
30
+ },
31
+ ];
32
+ expect(Id3Utils.getID3Frames(apicID3)).toEqual(expectedID3);
33
+ });
34
+
35
+ it('parse an APIC frame with image URL', () => {
36
+ const apicValue = new Uint8Array([
37
+ 3, 45, 45, 62, 0, 3, 83, 104, 97, 107, 97, 0, 103, 111, 111, 103, 108,
38
+ 101, 46, 99, 111, 109,
39
+ ]);
40
+ const apicFrame = Id3Generator.generateId3Frame('APIC', apicValue);
41
+ const apicID3 = Id3Generator.generateId3(apicFrame);
42
+ const expectedID3 = [
43
+ {
44
+ key: 'APIC',
45
+ mimeType: '-->',
46
+ pictureType: 3,
47
+ description: 'Shaka',
48
+ data: 'google.com',
49
+ },
50
+ ];
51
+ expect(Id3Utils.getID3Frames(apicID3)).toEqual(expectedID3);
52
+ });
53
+
16
54
  it('parse a TXXX frame', () => {
17
55
  const txxxValue = new Uint8Array([3, 65, 0, 83, 104, 97, 107, 97]);
18
56
  const txxxFrame = Id3Generator.generateId3Frame('TXXX', txxxValue);
@@ -22,6 +60,8 @@ describe('Id3Utils', () => {
22
60
  key: 'TXXX',
23
61
  description: 'A',
24
62
  data: 'Shaka',
63
+ mimeType: null,
64
+ pictureType: null,
25
65
  },
26
66
  ];
27
67
  expect(Id3Utils.getID3Frames(txxxID3)).toEqual(expectedID3);
@@ -36,6 +76,8 @@ describe('Id3Utils', () => {
36
76
  key: 'TXXX',
37
77
  description: 'A',
38
78
  data: 'Shaka',
79
+ mimeType: null,
80
+ pictureType: null,
39
81
  },
40
82
  ];
41
83
  expect(Id3Utils.getID3Frames(txxxID3)).toEqual(expectedID3);
@@ -51,6 +93,8 @@ describe('Id3Utils', () => {
51
93
  key: 'TCOP',
52
94
  description: '',
53
95
  data: 'Shaka 2016',
96
+ mimeType: null,
97
+ pictureType: null,
54
98
  },
55
99
  ];
56
100
  expect(Id3Utils.getID3Frames(tcopID3)).toEqual(expectedID3);
@@ -66,6 +110,8 @@ describe('Id3Utils', () => {
66
110
  key: 'WXXX',
67
111
  description: 'A',
68
112
  data: 'google.com',
113
+ mimeType: null,
114
+ pictureType: null,
69
115
  },
70
116
  ];
71
117
  expect(Id3Utils.getID3Frames(wxxxID3)).toEqual(expectedID3);
@@ -81,6 +127,8 @@ describe('Id3Utils', () => {
81
127
  key: 'WCOP',
82
128
  description: '',
83
129
  data: 'google.com',
130
+ mimeType: null,
131
+ pictureType: null,
84
132
  },
85
133
  ];
86
134
  expect(Id3Utils.getID3Frames(wcopID3)).toEqual(expectedID3);
@@ -95,6 +143,8 @@ describe('Id3Utils', () => {
95
143
  key: 'PRIV',
96
144
  description: 'A',
97
145
  data: BufferUtils.toArrayBuffer(new Uint8Array([83, 104, 97, 107])),
146
+ mimeType: null,
147
+ pictureType: null,
98
148
  },
99
149
  ];
100
150
  expect(Id3Utils.getID3Frames(privID3)).toEqual(expectedID3);
@@ -109,6 +159,8 @@ describe('Id3Utils', () => {
109
159
  key: 'XXXX',
110
160
  description: '',
111
161
  data: BufferUtils.toArrayBuffer(new Uint8Array([83, 104, 97, 107])),
162
+ mimeType: null,
163
+ pictureType: null,
112
164
  },
113
165
  ];
114
166
  expect(Id3Utils.getID3Frames(unknownID3)).toEqual(expectedID3);