@blockcast/mmt-container 0.1.0-main.0399efef1f07
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/README.md +432 -0
- package/dist/.build-stamp +0 -0
- package/dist/__tests__/test-utils.d.ts +71 -0
- package/dist/__tests__/test-utils.d.ts.map +1 -0
- package/dist/align.d.ts +152 -0
- package/dist/align.d.ts.map +1 -0
- package/dist/align.js +88 -0
- package/dist/align.js.map +7 -0
- package/dist/audio-init-parser.d.ts +66 -0
- package/dist/audio-init-parser.d.ts.map +1 -0
- package/dist/audio-init-parser.js +118 -0
- package/dist/audio-init-parser.js.map +7 -0
- package/dist/audio-ring-buffer.d.ts +50 -0
- package/dist/audio-ring-buffer.d.ts.map +1 -0
- package/dist/audio-ring-buffer.js +93 -0
- package/dist/audio-ring-buffer.js.map +7 -0
- package/dist/authored-timing.d.ts +32 -0
- package/dist/authored-timing.d.ts.map +1 -0
- package/dist/authored-timing.js +32 -0
- package/dist/authored-timing.js.map +7 -0
- package/dist/browser-runtime.js +20087 -0
- package/dist/browser-runtime.js.map +7 -0
- package/dist/carp-catalog.d.ts +318 -0
- package/dist/carp-catalog.d.ts.map +1 -0
- package/dist/carp-catalog.js +873 -0
- package/dist/carp-catalog.js.map +7 -0
- package/dist/catalog-fec-params.d.ts +202 -0
- package/dist/catalog-fec-params.d.ts.map +1 -0
- package/dist/catalog-fec-params.js +568 -0
- package/dist/catalog-fec-params.js.map +7 -0
- package/dist/catalog-network-source.d.ts +19 -0
- package/dist/catalog-network-source.d.ts.map +1 -0
- package/dist/catalog-network-source.js +22 -0
- package/dist/catalog-network-source.js.map +7 -0
- package/dist/catalog-validator.d.ts +18 -0
- package/dist/catalog-validator.d.ts.map +1 -0
- package/dist/catalog-validator.js +7747 -0
- package/dist/catalog-validator.js.map +7 -0
- package/dist/cmaf-block-assembler.d.ts +217 -0
- package/dist/cmaf-block-assembler.d.ts.map +1 -0
- package/dist/cmaf-block-assembler.js +1769 -0
- package/dist/cmaf-block-assembler.js.map +7 -0
- package/dist/cmaf-group-batcher.d.ts +38 -0
- package/dist/cmaf-group-batcher.d.ts.map +1 -0
- package/dist/cmaf-group-batcher.js +195 -0
- package/dist/cmaf-group-batcher.js.map +7 -0
- package/dist/cmcd-producer.d.ts +104 -0
- package/dist/cmcd-producer.d.ts.map +1 -0
- package/dist/cmcd-producer.js +207 -0
- package/dist/cmcd-producer.js.map +7 -0
- package/dist/codec-utils.d.ts +248 -0
- package/dist/codec-utils.d.ts.map +1 -0
- package/dist/codec-utils.js +1268 -0
- package/dist/codec-utils.js.map +7 -0
- package/dist/fec-codec.d.ts +32 -0
- package/dist/fec-codec.d.ts.map +1 -0
- package/dist/fec-codec.js +47 -0
- package/dist/fec-codec.js.map +7 -0
- package/dist/fec-manager.d.ts +307 -0
- package/dist/fec-manager.d.ts.map +1 -0
- package/dist/fec-manager.js +1530 -0
- package/dist/fec-manager.js.map +7 -0
- package/dist/fec-starvation-detector.d.ts +59 -0
- package/dist/fec-starvation-detector.d.ts.map +1 -0
- package/dist/fec-starvation-detector.js +75 -0
- package/dist/fec-starvation-detector.js.map +7 -0
- package/dist/fec-worker-setup.d.ts +88 -0
- package/dist/fec-worker-setup.d.ts.map +1 -0
- package/dist/fec-worker-setup.js +614 -0
- package/dist/fec-worker-setup.js.map +7 -0
- package/dist/fmp4-completion.d.ts +30 -0
- package/dist/fmp4-completion.d.ts.map +1 -0
- package/dist/fmp4-completion.js +21 -0
- package/dist/fmp4-completion.js.map +7 -0
- package/dist/fmp4-reader.d.ts +37 -0
- package/dist/fmp4-reader.d.ts.map +1 -0
- package/dist/fmp4-reader.js +100 -0
- package/dist/fmp4-reader.js.map +7 -0
- package/dist/index.d.ts +47 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +380 -0
- package/dist/index.js.map +7 -0
- package/dist/iso-bmff-timing.d.ts +78 -0
- package/dist/iso-bmff-timing.d.ts.map +1 -0
- package/dist/iso-bmff-timing.js +618 -0
- package/dist/iso-bmff-timing.js.map +7 -0
- package/dist/loc.d.ts +68 -0
- package/dist/loc.d.ts.map +1 -0
- package/dist/loc.js +143 -0
- package/dist/loc.js.map +7 -0
- package/dist/manifest-auth-plan.d.ts +30 -0
- package/dist/manifest-auth-plan.d.ts.map +1 -0
- package/dist/manifest-auth-plan.js +1285 -0
- package/dist/manifest-auth-plan.js.map +7 -0
- package/dist/media-router.d.ts +251 -0
- package/dist/media-router.d.ts.map +1 -0
- package/dist/media-router.js +624 -0
- package/dist/media-router.js.map +7 -0
- package/dist/mfu-reassembler.d.ts +396 -0
- package/dist/mfu-reassembler.d.ts.map +1 -0
- package/dist/mfu-reassembler.js +3085 -0
- package/dist/mfu-reassembler.js.map +7 -0
- package/dist/mfu-reassembly-policy.d.ts +24 -0
- package/dist/mfu-reassembly-policy.d.ts.map +1 -0
- package/dist/mfu-reassembly-policy.js +99 -0
- package/dist/mfu-reassembly-policy.js.map +7 -0
- package/dist/mmtp-container-parser.d.ts +434 -0
- package/dist/mmtp-container-parser.d.ts.map +1 -0
- package/dist/mmtp-container-parser.js +6164 -0
- package/dist/mmtp-container-parser.js.map +7 -0
- package/dist/mmtp-container-parser.no-modules.js +8999 -0
- package/dist/mmtp-container-parser.no-modules.js.map +7 -0
- package/dist/mmtp-decode-pipeline.d.ts +132 -0
- package/dist/mmtp-decode-pipeline.d.ts.map +1 -0
- package/dist/mmtp-decode-pipeline.js +6413 -0
- package/dist/mmtp-decode-pipeline.js.map +7 -0
- package/dist/mmtp-router.d.ts +390 -0
- package/dist/mmtp-router.d.ts.map +1 -0
- package/dist/mmtp-router.js +9242 -0
- package/dist/mmtp-router.js.map +7 -0
- package/dist/mmtp-to-cmaf.d.ts +181 -0
- package/dist/mmtp-to-cmaf.d.ts.map +1 -0
- package/dist/mmtp-to-cmaf.js +802 -0
- package/dist/mmtp-to-cmaf.js.map +7 -0
- package/dist/multicast-auth-catalog.d.ts +115 -0
- package/dist/multicast-auth-catalog.d.ts.map +1 -0
- package/dist/multicast-auth-catalog.js +202 -0
- package/dist/multicast-auth-catalog.js.map +7 -0
- package/dist/multicast-input.d.ts +107 -0
- package/dist/multicast-input.d.ts.map +1 -0
- package/dist/multicast-input.js +256 -0
- package/dist/multicast-input.js.map +7 -0
- package/dist/multicast-manager.d.ts +369 -0
- package/dist/multicast-manager.d.ts.map +1 -0
- package/dist/multicast-manager.js +13400 -0
- package/dist/multicast-manager.js.map +7 -0
- package/dist/multicast-transport.d.ts +61 -0
- package/dist/multicast-transport.d.ts.map +1 -0
- package/dist/multicast-transport.js +1665 -0
- package/dist/multicast-transport.js.map +7 -0
- package/dist/multicast-unwrap.d.ts +57 -0
- package/dist/multicast-unwrap.d.ts.map +1 -0
- package/dist/multicast-unwrap.js +384 -0
- package/dist/multicast-unwrap.js.map +7 -0
- package/dist/no-modules.d.ts +9 -0
- package/dist/no-modules.d.ts.map +1 -0
- package/dist/no-modules.js +8965 -0
- package/dist/no-modules.js.map +7 -0
- package/dist/phase14-catalog-override.d.ts +126 -0
- package/dist/phase14-catalog-override.d.ts.map +1 -0
- package/dist/phase14-catalog-override.js +155 -0
- package/dist/phase14-catalog-override.js.map +7 -0
- package/dist/repair-fetch.d.ts +58 -0
- package/dist/repair-fetch.d.ts.map +1 -0
- package/dist/repair-fetch.js +127 -0
- package/dist/repair-fetch.js.map +7 -0
- package/dist/repair-layers.d.ts +141 -0
- package/dist/repair-layers.d.ts.map +1 -0
- package/dist/repair-layers.js +303 -0
- package/dist/repair-layers.js.map +7 -0
- package/dist/sample-combiner.d.ts +212 -0
- package/dist/sample-combiner.d.ts.map +1 -0
- package/dist/sample-combiner.js +616 -0
- package/dist/sample-combiner.js.map +7 -0
- package/dist/signaling.d.ts +29 -0
- package/dist/signaling.d.ts.map +1 -0
- package/dist/signaling.js +232 -0
- package/dist/signaling.js.map +7 -0
- package/dist/source-auth.d.ts +2 -0
- package/dist/source-auth.d.ts.map +1 -0
- package/dist/source-auth.js +1238 -0
- package/dist/source-auth.js.map +7 -0
- package/dist/switching-set-alignment.d.ts +61 -0
- package/dist/switching-set-alignment.d.ts.map +1 -0
- package/dist/switching-set-alignment.js +85 -0
- package/dist/switching-set-alignment.js.map +7 -0
- package/dist/timestamp-codec.d.ts +34 -0
- package/dist/timestamp-codec.d.ts.map +1 -0
- package/dist/timestamp-codec.js +456 -0
- package/dist/timestamp-codec.js.map +7 -0
- package/dist/track-pipeline-setup.d.ts +72 -0
- package/dist/track-pipeline-setup.d.ts.map +1 -0
- package/dist/track-pipeline-setup.js +306 -0
- package/dist/track-pipeline-setup.js.map +7 -0
- package/dist/track-pipeline.d.ts +121 -0
- package/dist/track-pipeline.d.ts.map +1 -0
- package/dist/track-pipeline.js +229 -0
- package/dist/track-pipeline.js.map +7 -0
- package/dist/track-session.d.ts +398 -0
- package/dist/track-session.d.ts.map +1 -0
- package/dist/track-session.js +767 -0
- package/dist/track-session.js.map +7 -0
- package/dist/transport-pool.d.ts +69 -0
- package/dist/transport-pool.d.ts.map +1 -0
- package/dist/transport-pool.js +88 -0
- package/dist/transport-pool.js.map +7 -0
- package/dist/wasm-mfu-reassembler.d.ts +92 -0
- package/dist/wasm-mfu-reassembler.d.ts.map +1 -0
- package/dist/wasm-mfu-reassembler.js +2139 -0
- package/dist/wasm-mfu-reassembler.js.map +7 -0
- package/dist/wasm-mmtp-container-parser.d.ts +10 -0
- package/dist/wasm-mmtp-container-parser.d.ts.map +1 -0
- package/dist/wasm-mmtp-container-parser.js +6418 -0
- package/dist/wasm-mmtp-container-parser.js.map +7 -0
- package/node_modules/@blockcast/fec-worker/README.md +213 -0
- package/node_modules/@blockcast/fec-worker/dist/.build-stamp +0 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker-client.d.ts +87 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker-client.d.ts.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker-client.js +279 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker-client.js.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker-types.d.ts +252 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker-types.d.ts.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker-types.js +11 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker-types.js.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker.d.ts +14 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker.d.ts.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker.js +565 -0
- package/node_modules/@blockcast/fec-worker/dist/fec-worker.js.map +7 -0
- package/node_modules/@blockcast/fec-worker/dist/index.d.ts +10 -0
- package/node_modules/@blockcast/fec-worker/dist/index.d.ts.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/index.js +8 -0
- package/node_modules/@blockcast/fec-worker/dist/index.js.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-fec-worker.d.ts +20 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-fec-worker.d.ts.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-fec-worker.js +349 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-fec-worker.js.map +7 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-worker-client.d.ts +104 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-worker-client.d.ts.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-worker-client.js +181 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-worker-client.js.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-worker-types.d.ts +179 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-worker-types.d.ts.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-worker-types.js +47 -0
- package/node_modules/@blockcast/fec-worker/dist/shred-worker-types.js.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/transfer.d.ts +9 -0
- package/node_modules/@blockcast/fec-worker/dist/transfer.d.ts.map +1 -0
- package/node_modules/@blockcast/fec-worker/dist/transfer.js +13 -0
- package/node_modules/@blockcast/fec-worker/dist/transfer.js.map +1 -0
- package/node_modules/@blockcast/fec-worker/package.json +59 -0
- package/node_modules/@blockcast/fec-worker/src/fec-worker-client.ts +319 -0
- package/node_modules/@blockcast/fec-worker/src/fec-worker-types.ts +268 -0
- package/node_modules/@blockcast/fec-worker/src/fec-worker.ts +1048 -0
- package/node_modules/@blockcast/fec-worker/src/index.ts +32 -0
- package/node_modules/@blockcast/fec-worker/src/shred-fec-worker.ts +558 -0
- package/node_modules/@blockcast/fec-worker/src/shred-worker-client.ts +222 -0
- package/node_modules/@blockcast/fec-worker/src/shred-worker-types.ts +194 -0
- package/node_modules/@blockcast/fec-worker/src/transfer.ts +12 -0
- package/node_modules/@blockcast/mmt-alta-parse/README.md +181 -0
- package/node_modules/@blockcast/mmt-alta-parse/dist/.build-stamp +0 -0
- package/node_modules/@blockcast/mmt-alta-parse/dist/index.d.ts +57 -0
- package/node_modules/@blockcast/mmt-alta-parse/dist/index.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-alta-parse/dist/index.js +115 -0
- package/node_modules/@blockcast/mmt-alta-parse/dist/index.js.map +1 -0
- package/node_modules/@blockcast/mmt-alta-parse/package.json +50 -0
- package/node_modules/@blockcast/mmt-alta-parse/src/index.ts +136 -0
- package/node_modules/@blockcast/mmt-base/README.md +120 -0
- package/node_modules/@blockcast/mmt-base/dist/.build-stamp +0 -0
- package/node_modules/@blockcast/mmt-base/dist/index.d.ts +2 -0
- package/node_modules/@blockcast/mmt-base/dist/index.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-base/dist/index.js +2 -0
- package/node_modules/@blockcast/mmt-base/dist/index.js.map +1 -0
- package/node_modules/@blockcast/mmt-base/dist/mmtp.d.ts +276 -0
- package/node_modules/@blockcast/mmt-base/dist/mmtp.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-base/dist/mmtp.js +645 -0
- package/node_modules/@blockcast/mmt-base/dist/mmtp.js.map +1 -0
- package/node_modules/@blockcast/mmt-base/package.json +49 -0
- package/node_modules/@blockcast/mmt-base/src/index.ts +1 -0
- package/node_modules/@blockcast/mmt-base/src/mmtp.ts +899 -0
- package/node_modules/@blockcast/mmt-fec/README.md +270 -0
- package/node_modules/@blockcast/mmt-fec/dist/.build-stamp +0 -0
- package/node_modules/@blockcast/mmt-fec/dist/block-manager.d.ts +82 -0
- package/node_modules/@blockcast/mmt-fec/dist/block-manager.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/block-manager.js +296 -0
- package/node_modules/@blockcast/mmt-fec/dist/block-manager.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/block-processor.d.ts +72 -0
- package/node_modules/@blockcast/mmt-fec/dist/block-processor.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/block-processor.js +192 -0
- package/node_modules/@blockcast/mmt-fec/dist/block-processor.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/cmaf-recovery.d.ts +46 -0
- package/node_modules/@blockcast/mmt-fec/dist/cmaf-recovery.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/cmaf-recovery.js +96 -0
- package/node_modules/@blockcast/mmt-fec/dist/cmaf-recovery.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/cmaf-symbols.d.ts +33 -0
- package/node_modules/@blockcast/mmt-fec/dist/cmaf-symbols.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/cmaf-symbols.js +57 -0
- package/node_modules/@blockcast/mmt-fec/dist/cmaf-symbols.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/fec-block-mapper.d.ts +185 -0
- package/node_modules/@blockcast/mmt-fec/dist/fec-block-mapper.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/fec-block-mapper.js +273 -0
- package/node_modules/@blockcast/mmt-fec/dist/fec-block-mapper.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/index.d.ts +22 -0
- package/node_modules/@blockcast/mmt-fec/dist/index.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/index.js +22 -0
- package/node_modules/@blockcast/mmt-fec/dist/index.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/loc-symbols.d.ts +20 -0
- package/node_modules/@blockcast/mmt-fec/dist/loc-symbols.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/loc-symbols.js +28 -0
- package/node_modules/@blockcast/mmt-fec/dist/loc-symbols.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/oti.d.ts +172 -0
- package/node_modules/@blockcast/mmt-fec/dist/oti.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/oti.js +254 -0
- package/node_modules/@blockcast/mmt-fec/dist/oti.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/reorder-buffer.d.ts +41 -0
- package/node_modules/@blockcast/mmt-fec/dist/reorder-buffer.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/dist/reorder-buffer.js +81 -0
- package/node_modules/@blockcast/mmt-fec/dist/reorder-buffer.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-alta-parse/README.md +181 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-alta-parse/dist/.build-stamp +0 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-alta-parse/dist/index.d.ts +57 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-alta-parse/dist/index.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-alta-parse/dist/index.js +115 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-alta-parse/dist/index.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-alta-parse/package.json +50 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-alta-parse/src/index.ts +136 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/README.md +120 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/dist/.build-stamp +0 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/dist/index.d.ts +2 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/dist/index.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/dist/index.js +2 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/dist/index.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/dist/mmtp.d.ts +276 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/dist/mmtp.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/dist/mmtp.js +645 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/dist/mmtp.js.map +1 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/package.json +49 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/src/index.ts +1 -0
- package/node_modules/@blockcast/mmt-fec/node_modules/@blockcast/mmt-base/src/mmtp.ts +899 -0
- package/node_modules/@blockcast/mmt-fec/package.json +79 -0
- package/node_modules/@blockcast/mmt-fec/src/block-manager.ts +371 -0
- package/node_modules/@blockcast/mmt-fec/src/block-processor.ts +277 -0
- package/node_modules/@blockcast/mmt-fec/src/cmaf-recovery.ts +127 -0
- package/node_modules/@blockcast/mmt-fec/src/cmaf-symbols.ts +68 -0
- package/node_modules/@blockcast/mmt-fec/src/fec-block-mapper.ts +332 -0
- package/node_modules/@blockcast/mmt-fec/src/index.ts +77 -0
- package/node_modules/@blockcast/mmt-fec/src/loc-symbols.ts +34 -0
- package/node_modules/@blockcast/mmt-fec/src/oti.ts +317 -0
- package/node_modules/@blockcast/mmt-fec/src/reorder-buffer.ts +101 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/.build-stamp +0 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/admission.d.ts +28 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/admission.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/admission.js +128 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/admission.js.map +1 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/index.d.ts +4 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/index.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/index.js +4 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/index.js.map +1 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/source-auth.d.ts +37 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/source-auth.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/source-auth.js +179 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/source-auth.js.map +1 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/verifier.d.ts +99 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/verifier.d.ts.map +1 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/verifier.js +492 -0
- package/node_modules/@blockcast/mmt-manifest-verify/dist/verifier.js.map +1 -0
- package/node_modules/@blockcast/mmt-manifest-verify/package.json +45 -0
- package/node_modules/@blockcast/mmt-manifest-verify/src/admission.ts +171 -0
- package/node_modules/@blockcast/mmt-manifest-verify/src/index.ts +3 -0
- package/node_modules/@blockcast/mmt-manifest-verify/src/source-auth.ts +230 -0
- package/node_modules/@blockcast/mmt-manifest-verify/src/verifier.ts +669 -0
- package/node_modules/@noble/hashes/LICENSE +21 -0
- package/node_modules/@noble/hashes/README.md +521 -0
- package/node_modules/@noble/hashes/_assert.d.ts +17 -0
- package/node_modules/@noble/hashes/_assert.d.ts.map +1 -0
- package/node_modules/@noble/hashes/_assert.js +18 -0
- package/node_modules/@noble/hashes/_assert.js.map +1 -0
- package/node_modules/@noble/hashes/_blake.d.ts +14 -0
- package/node_modules/@noble/hashes/_blake.d.ts.map +1 -0
- package/node_modules/@noble/hashes/_blake.js +50 -0
- package/node_modules/@noble/hashes/_blake.js.map +1 -0
- package/node_modules/@noble/hashes/_md.d.ts +51 -0
- package/node_modules/@noble/hashes/_md.d.ts.map +1 -0
- package/node_modules/@noble/hashes/_md.js +162 -0
- package/node_modules/@noble/hashes/_md.js.map +1 -0
- package/node_modules/@noble/hashes/_u64.d.ts +55 -0
- package/node_modules/@noble/hashes/_u64.d.ts.map +1 -0
- package/node_modules/@noble/hashes/_u64.js +90 -0
- package/node_modules/@noble/hashes/_u64.js.map +1 -0
- package/node_modules/@noble/hashes/argon2.d.ts +32 -0
- package/node_modules/@noble/hashes/argon2.d.ts.map +1 -0
- package/node_modules/@noble/hashes/argon2.js +401 -0
- package/node_modules/@noble/hashes/argon2.js.map +1 -0
- package/node_modules/@noble/hashes/blake1.d.ts +106 -0
- package/node_modules/@noble/hashes/blake1.d.ts.map +1 -0
- package/node_modules/@noble/hashes/blake1.js +459 -0
- package/node_modules/@noble/hashes/blake1.js.map +1 -0
- package/node_modules/@noble/hashes/blake2.d.ts +116 -0
- package/node_modules/@noble/hashes/blake2.d.ts.map +1 -0
- package/node_modules/@noble/hashes/blake2.js +420 -0
- package/node_modules/@noble/hashes/blake2.js.map +1 -0
- package/node_modules/@noble/hashes/blake2b.d.ts +11 -0
- package/node_modules/@noble/hashes/blake2b.d.ts.map +1 -0
- package/node_modules/@noble/hashes/blake2b.js +14 -0
- package/node_modules/@noble/hashes/blake2b.js.map +1 -0
- package/node_modules/@noble/hashes/blake2s.d.ts +20 -0
- package/node_modules/@noble/hashes/blake2s.d.ts.map +1 -0
- package/node_modules/@noble/hashes/blake2s.js +24 -0
- package/node_modules/@noble/hashes/blake2s.js.map +1 -0
- package/node_modules/@noble/hashes/blake3.d.ts +54 -0
- package/node_modules/@noble/hashes/blake3.d.ts.map +1 -0
- package/node_modules/@noble/hashes/blake3.js +255 -0
- package/node_modules/@noble/hashes/blake3.js.map +1 -0
- package/node_modules/@noble/hashes/crypto.d.ts +2 -0
- package/node_modules/@noble/hashes/crypto.d.ts.map +1 -0
- package/node_modules/@noble/hashes/crypto.js +5 -0
- package/node_modules/@noble/hashes/crypto.js.map +1 -0
- package/node_modules/@noble/hashes/cryptoNode.d.ts +2 -0
- package/node_modules/@noble/hashes/cryptoNode.d.ts.map +1 -0
- package/node_modules/@noble/hashes/cryptoNode.js +18 -0
- package/node_modules/@noble/hashes/cryptoNode.js.map +1 -0
- package/node_modules/@noble/hashes/eskdf.d.ts +47 -0
- package/node_modules/@noble/hashes/eskdf.d.ts.map +1 -0
- package/node_modules/@noble/hashes/eskdf.js +166 -0
- package/node_modules/@noble/hashes/eskdf.js.map +1 -0
- package/node_modules/@noble/hashes/esm/_assert.d.ts +17 -0
- package/node_modules/@noble/hashes/esm/_assert.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/_assert.js +15 -0
- package/node_modules/@noble/hashes/esm/_assert.js.map +1 -0
- package/node_modules/@noble/hashes/esm/_blake.d.ts +14 -0
- package/node_modules/@noble/hashes/esm/_blake.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/_blake.js +45 -0
- package/node_modules/@noble/hashes/esm/_blake.js.map +1 -0
- package/node_modules/@noble/hashes/esm/_md.d.ts +51 -0
- package/node_modules/@noble/hashes/esm/_md.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/_md.js +155 -0
- package/node_modules/@noble/hashes/esm/_md.js.map +1 -0
- package/node_modules/@noble/hashes/esm/_u64.d.ts +55 -0
- package/node_modules/@noble/hashes/esm/_u64.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/_u64.js +67 -0
- package/node_modules/@noble/hashes/esm/_u64.js.map +1 -0
- package/node_modules/@noble/hashes/esm/argon2.d.ts +32 -0
- package/node_modules/@noble/hashes/esm/argon2.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/argon2.js +392 -0
- package/node_modules/@noble/hashes/esm/argon2.js.map +1 -0
- package/node_modules/@noble/hashes/esm/blake1.d.ts +106 -0
- package/node_modules/@noble/hashes/esm/blake1.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/blake1.js +452 -0
- package/node_modules/@noble/hashes/esm/blake1.js.map +1 -0
- package/node_modules/@noble/hashes/esm/blake2.d.ts +116 -0
- package/node_modules/@noble/hashes/esm/blake2.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/blake2.js +413 -0
- package/node_modules/@noble/hashes/esm/blake2.js.map +1 -0
- package/node_modules/@noble/hashes/esm/blake2b.d.ts +11 -0
- package/node_modules/@noble/hashes/esm/blake2b.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/blake2b.js +11 -0
- package/node_modules/@noble/hashes/esm/blake2b.js.map +1 -0
- package/node_modules/@noble/hashes/esm/blake2s.d.ts +20 -0
- package/node_modules/@noble/hashes/esm/blake2s.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/blake2s.js +21 -0
- package/node_modules/@noble/hashes/esm/blake2s.js.map +1 -0
- package/node_modules/@noble/hashes/esm/blake3.d.ts +54 -0
- package/node_modules/@noble/hashes/esm/blake3.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/blake3.js +251 -0
- package/node_modules/@noble/hashes/esm/blake3.js.map +1 -0
- package/node_modules/@noble/hashes/esm/crypto.d.ts +2 -0
- package/node_modules/@noble/hashes/esm/crypto.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/crypto.js +2 -0
- package/node_modules/@noble/hashes/esm/crypto.js.map +1 -0
- package/node_modules/@noble/hashes/esm/cryptoNode.d.ts +2 -0
- package/node_modules/@noble/hashes/esm/cryptoNode.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/cryptoNode.js +15 -0
- package/node_modules/@noble/hashes/esm/cryptoNode.js.map +1 -0
- package/node_modules/@noble/hashes/esm/eskdf.d.ts +47 -0
- package/node_modules/@noble/hashes/esm/eskdf.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/eskdf.js +160 -0
- package/node_modules/@noble/hashes/esm/eskdf.js.map +1 -0
- package/node_modules/@noble/hashes/esm/hkdf.d.ts +36 -0
- package/node_modules/@noble/hashes/esm/hkdf.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/hkdf.js +82 -0
- package/node_modules/@noble/hashes/esm/hkdf.js.map +1 -0
- package/node_modules/@noble/hashes/esm/hmac.d.ts +35 -0
- package/node_modules/@noble/hashes/esm/hmac.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/hmac.js +86 -0
- package/node_modules/@noble/hashes/esm/hmac.js.map +1 -0
- package/node_modules/@noble/hashes/esm/index.d.ts +2 -0
- package/node_modules/@noble/hashes/esm/index.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/index.js +33 -0
- package/node_modules/@noble/hashes/esm/index.js.map +1 -0
- package/node_modules/@noble/hashes/esm/legacy.d.ts +71 -0
- package/node_modules/@noble/hashes/esm/legacy.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/legacy.js +281 -0
- package/node_modules/@noble/hashes/esm/legacy.js.map +1 -0
- package/node_modules/@noble/hashes/esm/package.json +10 -0
- package/node_modules/@noble/hashes/esm/pbkdf2.d.ts +23 -0
- package/node_modules/@noble/hashes/esm/pbkdf2.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/pbkdf2.js +97 -0
- package/node_modules/@noble/hashes/esm/pbkdf2.js.map +1 -0
- package/node_modules/@noble/hashes/esm/ripemd160.d.ts +13 -0
- package/node_modules/@noble/hashes/esm/ripemd160.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/ripemd160.js +13 -0
- package/node_modules/@noble/hashes/esm/ripemd160.js.map +1 -0
- package/node_modules/@noble/hashes/esm/scrypt.d.ts +34 -0
- package/node_modules/@noble/hashes/esm/scrypt.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/scrypt.js +228 -0
- package/node_modules/@noble/hashes/esm/scrypt.js.map +1 -0
- package/node_modules/@noble/hashes/esm/sha1.d.ts +11 -0
- package/node_modules/@noble/hashes/esm/sha1.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/sha1.js +11 -0
- package/node_modules/@noble/hashes/esm/sha1.js.map +1 -0
- package/node_modules/@noble/hashes/esm/sha2.d.ts +159 -0
- package/node_modules/@noble/hashes/esm/sha2.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/sha2.js +375 -0
- package/node_modules/@noble/hashes/esm/sha2.js.map +1 -0
- package/node_modules/@noble/hashes/esm/sha256.d.ts +20 -0
- package/node_modules/@noble/hashes/esm/sha256.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/sha256.js +20 -0
- package/node_modules/@noble/hashes/esm/sha256.js.map +1 -0
- package/node_modules/@noble/hashes/esm/sha3-addons.d.ts +142 -0
- package/node_modules/@noble/hashes/esm/sha3-addons.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/sha3-addons.js +393 -0
- package/node_modules/@noble/hashes/esm/sha3-addons.js.map +1 -0
- package/node_modules/@noble/hashes/esm/sha3.d.ts +53 -0
- package/node_modules/@noble/hashes/esm/sha3.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/sha3.js +234 -0
- package/node_modules/@noble/hashes/esm/sha3.js.map +1 -0
- package/node_modules/@noble/hashes/esm/sha512.d.ts +26 -0
- package/node_modules/@noble/hashes/esm/sha512.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/sha512.js +26 -0
- package/node_modules/@noble/hashes/esm/sha512.js.map +1 -0
- package/node_modules/@noble/hashes/esm/utils.d.ts +161 -0
- package/node_modules/@noble/hashes/esm/utils.d.ts.map +1 -0
- package/node_modules/@noble/hashes/esm/utils.js +281 -0
- package/node_modules/@noble/hashes/esm/utils.js.map +1 -0
- package/node_modules/@noble/hashes/hkdf.d.ts +36 -0
- package/node_modules/@noble/hashes/hkdf.d.ts.map +1 -0
- package/node_modules/@noble/hashes/hkdf.js +88 -0
- package/node_modules/@noble/hashes/hkdf.js.map +1 -0
- package/node_modules/@noble/hashes/hmac.d.ts +35 -0
- package/node_modules/@noble/hashes/hmac.d.ts.map +1 -0
- package/node_modules/@noble/hashes/hmac.js +91 -0
- package/node_modules/@noble/hashes/hmac.js.map +1 -0
- package/node_modules/@noble/hashes/index.d.ts +1 -0
- package/node_modules/@noble/hashes/index.d.ts.map +1 -0
- package/node_modules/@noble/hashes/index.js +33 -0
- package/node_modules/@noble/hashes/index.js.map +1 -0
- package/node_modules/@noble/hashes/legacy.d.ts +71 -0
- package/node_modules/@noble/hashes/legacy.d.ts.map +1 -0
- package/node_modules/@noble/hashes/legacy.js +287 -0
- package/node_modules/@noble/hashes/legacy.js.map +1 -0
- package/node_modules/@noble/hashes/package.json +266 -0
- package/node_modules/@noble/hashes/pbkdf2.d.ts +23 -0
- package/node_modules/@noble/hashes/pbkdf2.d.ts.map +1 -0
- package/node_modules/@noble/hashes/pbkdf2.js +101 -0
- package/node_modules/@noble/hashes/pbkdf2.js.map +1 -0
- package/node_modules/@noble/hashes/ripemd160.d.ts +13 -0
- package/node_modules/@noble/hashes/ripemd160.d.ts.map +1 -0
- package/node_modules/@noble/hashes/ripemd160.js +16 -0
- package/node_modules/@noble/hashes/ripemd160.js.map +1 -0
- package/node_modules/@noble/hashes/scrypt.d.ts +34 -0
- package/node_modules/@noble/hashes/scrypt.d.ts.map +1 -0
- package/node_modules/@noble/hashes/scrypt.js +232 -0
- package/node_modules/@noble/hashes/scrypt.js.map +1 -0
- package/node_modules/@noble/hashes/sha1.d.ts +11 -0
- package/node_modules/@noble/hashes/sha1.d.ts.map +1 -0
- package/node_modules/@noble/hashes/sha1.js +14 -0
- package/node_modules/@noble/hashes/sha1.js.map +1 -0
- package/node_modules/@noble/hashes/sha2.d.ts +159 -0
- package/node_modules/@noble/hashes/sha2.d.ts.map +1 -0
- package/node_modules/@noble/hashes/sha2.js +384 -0
- package/node_modules/@noble/hashes/sha2.js.map +1 -0
- package/node_modules/@noble/hashes/sha256.d.ts +20 -0
- package/node_modules/@noble/hashes/sha256.d.ts.map +1 -0
- package/node_modules/@noble/hashes/sha256.js +23 -0
- package/node_modules/@noble/hashes/sha256.js.map +1 -0
- package/node_modules/@noble/hashes/sha3-addons.d.ts +142 -0
- package/node_modules/@noble/hashes/sha3-addons.d.ts.map +1 -0
- package/node_modules/@noble/hashes/sha3-addons.js +402 -0
- package/node_modules/@noble/hashes/sha3-addons.js.map +1 -0
- package/node_modules/@noble/hashes/sha3.d.ts +53 -0
- package/node_modules/@noble/hashes/sha3.d.ts.map +1 -0
- package/node_modules/@noble/hashes/sha3.js +239 -0
- package/node_modules/@noble/hashes/sha3.js.map +1 -0
- package/node_modules/@noble/hashes/sha512.d.ts +26 -0
- package/node_modules/@noble/hashes/sha512.d.ts.map +1 -0
- package/node_modules/@noble/hashes/sha512.js +29 -0
- package/node_modules/@noble/hashes/sha512.js.map +1 -0
- package/node_modules/@noble/hashes/src/_assert.ts +22 -0
- package/node_modules/@noble/hashes/src/_blake.ts +50 -0
- package/node_modules/@noble/hashes/src/_md.ts +176 -0
- package/node_modules/@noble/hashes/src/_u64.ts +91 -0
- package/node_modules/@noble/hashes/src/argon2.ts +497 -0
- package/node_modules/@noble/hashes/src/blake1.ts +534 -0
- package/node_modules/@noble/hashes/src/blake2.ts +486 -0
- package/node_modules/@noble/hashes/src/blake2b.ts +10 -0
- package/node_modules/@noble/hashes/src/blake2s.ts +20 -0
- package/node_modules/@noble/hashes/src/blake3.ts +272 -0
- package/node_modules/@noble/hashes/src/crypto.ts +9 -0
- package/node_modules/@noble/hashes/src/cryptoNode.ts +15 -0
- package/node_modules/@noble/hashes/src/eskdf.ts +187 -0
- package/node_modules/@noble/hashes/src/hkdf.ts +88 -0
- package/node_modules/@noble/hashes/src/hmac.ts +94 -0
- package/node_modules/@noble/hashes/src/index.ts +31 -0
- package/node_modules/@noble/hashes/src/legacy.ts +293 -0
- package/node_modules/@noble/hashes/src/pbkdf2.ts +122 -0
- package/node_modules/@noble/hashes/src/ripemd160.ts +12 -0
- package/node_modules/@noble/hashes/src/scrypt.ts +257 -0
- package/node_modules/@noble/hashes/src/sha1.ts +10 -0
- package/node_modules/@noble/hashes/src/sha2.ts +402 -0
- package/node_modules/@noble/hashes/src/sha256.ts +24 -0
- package/node_modules/@noble/hashes/src/sha3-addons.ts +499 -0
- package/node_modules/@noble/hashes/src/sha3.ts +258 -0
- package/node_modules/@noble/hashes/src/sha512.ts +34 -0
- package/node_modules/@noble/hashes/src/utils.ts +395 -0
- package/node_modules/@noble/hashes/utils.d.ts +161 -0
- package/node_modules/@noble/hashes/utils.d.ts.map +1 -0
- package/node_modules/@noble/hashes/utils.js +313 -0
- package/node_modules/@noble/hashes/utils.js.map +1 -0
- package/package.json +203 -0
- package/schemas/catalog.schema.json +360 -0
- package/src/align.ts +239 -0
- package/src/audio-init-parser.ts +189 -0
- package/src/audio-ring-buffer.ts +120 -0
- package/src/authored-timing.ts +63 -0
- package/src/carp-catalog.ts +845 -0
- package/src/catalog-fec-params.ts +535 -0
- package/src/catalog-network-source.ts +49 -0
- package/src/catalog-validator.ts +34 -0
- package/src/cmaf-block-assembler.ts +1167 -0
- package/src/cmaf-group-batcher.ts +104 -0
- package/src/cmcd-producer.ts +334 -0
- package/src/codec-utils.ts +1611 -0
- package/src/fec-codec.ts +61 -0
- package/src/fec-manager.ts +2081 -0
- package/src/fec-starvation-detector.ts +128 -0
- package/src/fec-worker-setup.ts +213 -0
- package/src/fmp4-completion.ts +47 -0
- package/src/fmp4-reader.ts +112 -0
- package/src/index.ts +486 -0
- package/src/iso-bmff-timing.ts +813 -0
- package/src/loc.ts +181 -0
- package/src/manifest-auth-plan.ts +107 -0
- package/src/media-router.ts +795 -0
- package/src/mfu-reassembler.ts +3741 -0
- package/src/mfu-reassembly-policy.ts +134 -0
- package/src/mmtp-container-parser.ts +1836 -0
- package/src/mmtp-decode-pipeline.ts +389 -0
- package/src/mmtp-router.ts +3136 -0
- package/src/mmtp-to-cmaf.ts +1024 -0
- package/src/multicast-auth-catalog.ts +340 -0
- package/src/multicast-input.ts +439 -0
- package/src/multicast-manager.ts +1720 -0
- package/src/multicast-transport.ts +321 -0
- package/src/multicast-unwrap.ts +132 -0
- package/src/no-modules.ts +20 -0
- package/src/phase14-catalog-override.ts +336 -0
- package/src/repair-fetch.ts +238 -0
- package/src/repair-layers.ts +490 -0
- package/src/sample-combiner.ts +938 -0
- package/src/signaling.ts +78 -0
- package/src/source-auth.ts +1 -0
- package/src/switching-set-alignment.ts +109 -0
- package/src/timestamp-codec.ts +265 -0
- package/src/track-pipeline-setup.ts +189 -0
- package/src/track-pipeline.ts +332 -0
- package/src/track-session.ts +994 -0
- package/src/transport-pool.ts +128 -0
- package/src/wasm-mfu-reassembler.ts +389 -0
- package/src/wasm-mmtp-container-parser.ts +23 -0
- package/test-vectors/align.json +199 -0
- package/test-vectors/catalog/README.md +40 -0
- package/test-vectors/catalog/negative/fec-enhancement-repair-removed.json +27 -0
- package/test-vectors/catalog/negative/fec-repair-layer-geometry.json +32 -0
- package/test-vectors/catalog/negative/fec-repair-layer-missing-symbols.json +30 -0
- package/test-vectors/catalog/negative/fec-repair-multiple-depends.json +31 -0
- package/test-vectors/catalog/negative/fec-repair-overlay-with-layer.json +33 -0
- package/test-vectors/catalog/negative/fec-repair-priority-out-of-band.json +23 -0
- package/test-vectors/catalog/negative/fec-repair-source-symbols-without-scope.json +32 -0
- package/test-vectors/catalog/negative/legacy-selection-params.json +15 -0
- package/test-vectors/catalog/negative/media-track-repair-layer.json +16 -0
- package/test-vectors/catalog/negative/missing-mmtp-fields.json +12 -0
- package/test-vectors/catalog/negative/multicast-auth-padded-key.json +37 -0
- package/test-vectors/catalog/negative/multicast-auth-reused-track-format.json +53 -0
- package/test-vectors/catalog/negative/multicast-auth-trailing-pad-bits.json +37 -0
- package/test-vectors/catalog/negative/multicast-endpoint-missing-protocol-and-source.json +24 -0
- package/test-vectors/catalog/negative/network-source-object.json +25 -0
- package/test-vectors/catalog/negative/raptorq-source-symbols-over-max.json +23 -0
- package/test-vectors/catalog/negative/raptorq-unaligned-symbol.json +26 -0
- package/test-vectors/catalog/negative/repair-track-legacy-shape.json +19 -0
- package/test-vectors/catalog/negative/track-role-empty.json +16 -0
- package/test-vectors/catalog/negative/track-role-non-string.json +16 -0
- package/test-vectors/catalog/positive/fec-layered-repair.json +104 -0
- package/test-vectors/catalog/positive/fec-multicast.json +51 -0
- package/test-vectors/catalog/positive/flat-av.json +30 -0
- package/test-vectors/catalog/positive/multicast-auth-rotation.json +55 -0
- package/test-vectors/catalog/positive/ticks-and-mixed-timescales.json +39 -0
- package/test-vectors/catalog/positive/track-role.json +49 -0
- package/test-vectors/catalog/releases/moqcast-native-v16-v1/catalog.json +65 -0
- package/test-vectors/catalog/releases/moqcast-native-v16-v1.archive.sha256 +1 -0
- package/test-vectors/catalog-multicast-auth-v1.json +26 -0
- package/test-vectors/catalog-validation.json +148 -0
- package/test-vectors/catalog-validator-public-api.mjs +25 -0
- package/test-vectors/generate-source-auth-fixture.mjs +114 -0
- package/test-vectors/source-auth-v1.json +61 -0
- package/test-vectors/source-contiguity-v1.json +131 -0
- package/test-vectors/subsample-placement-v1.json +230 -0
|
@@ -0,0 +1,535 @@
|
|
|
1
|
+
// Catalog → per-track FEC geometry resolution.
|
|
2
|
+
//
|
|
3
|
+
// Moved from hang-mmt-fec's js/watch/src/track-fec-params.ts so every player
|
|
4
|
+
// (moq-lib/hang, moqtail, shaka MSF) resolves catalog FEC semantics through
|
|
5
|
+
// one shared implementation — players keep only wiring, not MMT/catalog
|
|
6
|
+
// interpretation. Structural track shape ({ name, type }) keeps this module
|
|
7
|
+
// player-agnostic.
|
|
8
|
+
|
|
9
|
+
import { catalogFecInterleaveMs, type FecInterleaveCatalog } from "@blockcast/mmt-fec";
|
|
10
|
+
import { resolveGroupDurationMs } from "./carp-catalog.js";
|
|
11
|
+
import {
|
|
12
|
+
assembleRepairLayers,
|
|
13
|
+
assertRepairTrackReachable,
|
|
14
|
+
describeRepairTrack,
|
|
15
|
+
rejectRepairFieldsOnMediaTrack,
|
|
16
|
+
rejectRepairTrackGeometry,
|
|
17
|
+
repairReachability,
|
|
18
|
+
dependsTarget,
|
|
19
|
+
type RepairLayerParams,
|
|
20
|
+
type RepairLayersResolution,
|
|
21
|
+
type RepairOverlayParams,
|
|
22
|
+
type RepairSourceGeometry,
|
|
23
|
+
type RepairTrackDescriptor,
|
|
24
|
+
throwRepairContractError,
|
|
25
|
+
validateRepairTrackFields,
|
|
26
|
+
} from "./repair-layers.js";
|
|
27
|
+
|
|
28
|
+
export { catalogFecInterleaveMs, type FecInterleaveCatalog };
|
|
29
|
+
export {
|
|
30
|
+
assembleRepairLayers,
|
|
31
|
+
assertRepairTrackReachable,
|
|
32
|
+
repairReachability,
|
|
33
|
+
type AssembleRepairLayersOptions,
|
|
34
|
+
type RepairReachability,
|
|
35
|
+
dependsTarget,
|
|
36
|
+
describeRepairTrack,
|
|
37
|
+
rejectRepairFieldsOnMediaTrack,
|
|
38
|
+
rejectRepairTrackGeometry,
|
|
39
|
+
REPAIR_TRACK_GEOMETRY_KEYS,
|
|
40
|
+
REPAIR_TRACK_ONLY_KEYS,
|
|
41
|
+
validateRepairTrackFields,
|
|
42
|
+
DEFAULT_REPAIR_PRIORITY,
|
|
43
|
+
MAX_ENCODING_SYMBOL_ID,
|
|
44
|
+
MAX_RAPTORQ_SOURCE_SYMBOLS,
|
|
45
|
+
MAX_REPAIR_SYMBOLS,
|
|
46
|
+
REPAIR_PRIORITY_MAX,
|
|
47
|
+
REPAIR_PRIORITY_MIN,
|
|
48
|
+
RepairContractError,
|
|
49
|
+
type RepairContractCode,
|
|
50
|
+
type RepairContractFail,
|
|
51
|
+
type RepairLayerParams,
|
|
52
|
+
type RepairLayersResolution,
|
|
53
|
+
type RepairOverlayParams,
|
|
54
|
+
type RepairSourceGeometry,
|
|
55
|
+
type RepairTrackDescriptor,
|
|
56
|
+
} from "./repair-layers.js";
|
|
57
|
+
|
|
58
|
+
/**
|
|
59
|
+
* Minimal structural shape of a resolved endpoint track. Callers may carry
|
|
60
|
+
* extra fields (e.g. hang's ResolvedEndpointTrack adds `pid`) — the resolver
|
|
61
|
+
* only reads `name` and `type`.
|
|
62
|
+
*/
|
|
63
|
+
export type CatalogTrackRef = {
|
|
64
|
+
name: string;
|
|
65
|
+
type: "video" | "audio" | (string & {});
|
|
66
|
+
};
|
|
67
|
+
|
|
68
|
+
type FecCatalog = FecInterleaveCatalog & {
|
|
69
|
+
algorithm?: unknown;
|
|
70
|
+
sourceSymbols?: number;
|
|
71
|
+
repairSymbols?: number;
|
|
72
|
+
symbolSize?: number;
|
|
73
|
+
/** Signaled jitter/reorder allowance in ms (added to the block span). */
|
|
74
|
+
reorderToleranceMs?: number;
|
|
75
|
+
/** Layer 0 repair track. Further layers and overlays describe themselves
|
|
76
|
+
* (draft-ramadan-moq-fec §6.3): MSF `tracks[]` entries with
|
|
77
|
+
* `packaging: "fec-repair"`, or hang `repair.renditions` entries, that
|
|
78
|
+
* `depend` on this rendition. */
|
|
79
|
+
repairTrack?: string;
|
|
80
|
+
};
|
|
81
|
+
|
|
82
|
+
/** One self-describing repair rendition of the hang catalog's `repair` block
|
|
83
|
+
* (draft-ramadan-moq-fec §6.3). Mirrors the MSF fec-repair track fields. */
|
|
84
|
+
export type RepairRenditionCatalog = {
|
|
85
|
+
depends?: unknown;
|
|
86
|
+
repairLayer?: unknown;
|
|
87
|
+
repairSymbols?: unknown;
|
|
88
|
+
priority?: unknown;
|
|
89
|
+
scope?: unknown;
|
|
90
|
+
sourceSymbols?: unknown;
|
|
91
|
+
};
|
|
92
|
+
|
|
93
|
+
/** The container fields the FEC and group-duration readers consult. */
|
|
94
|
+
type ContainerCatalog = { kind?: unknown; timescale?: unknown };
|
|
95
|
+
|
|
96
|
+
type RenditionCatalog = KeyframeCadenceCatalog & {
|
|
97
|
+
container?: ContainerCatalog;
|
|
98
|
+
fec?: FecCatalog;
|
|
99
|
+
framerate?: unknown;
|
|
100
|
+
sampleRate?: unknown;
|
|
101
|
+
samplerate?: unknown;
|
|
102
|
+
};
|
|
103
|
+
|
|
104
|
+
type CatalogWithRenditions = {
|
|
105
|
+
video?: { renditions?: Record<string, RenditionCatalog> };
|
|
106
|
+
audio?: { renditions?: Record<string, RenditionCatalog> };
|
|
107
|
+
/** hang-native repair renditions: every repair track beyond layer 0. */
|
|
108
|
+
repair?: { renditions?: Record<string, RepairRenditionCatalog> };
|
|
109
|
+
};
|
|
110
|
+
|
|
111
|
+
/** An MSF/CMSF catalog: `tracks[]` entries, optionally with `commonTrackFields`. */
|
|
112
|
+
type CatalogWithTracks = {
|
|
113
|
+
tracks?: unknown;
|
|
114
|
+
commonTrackFields?: unknown;
|
|
115
|
+
};
|
|
116
|
+
|
|
117
|
+
/** Either catalog dialect `resolveRepairLayers` reads. */
|
|
118
|
+
export type RepairLayerCatalog = CatalogWithRenditions | CatalogWithTracks;
|
|
119
|
+
|
|
120
|
+
export type GroupDurationCatalog = {
|
|
121
|
+
groupDurationTicks?: number;
|
|
122
|
+
groupDurationMs?: number;
|
|
123
|
+
timescale?: number;
|
|
124
|
+
};
|
|
125
|
+
|
|
126
|
+
/** Rendition fields the group-duration reader consumes. */
|
|
127
|
+
export type GroupDurationRendition = GroupDurationCatalog & {
|
|
128
|
+
container?: ContainerCatalog;
|
|
129
|
+
};
|
|
130
|
+
|
|
131
|
+
/**
|
|
132
|
+
* Largest tick count per Hz of timescale whose millisecond duration
|
|
133
|
+
* `resolveGroupDurationMs` still accepts: `(ticks / timescale) * 1000` must not
|
|
134
|
+
* exceed `Number.MAX_SAFE_INTEGER`, so `ticks <= timescale * (MAX_SAFE / 1000)`
|
|
135
|
+
* (Hz times seconds is ticks).
|
|
136
|
+
*/
|
|
137
|
+
const MAX_SAFE_TICKS_PER_HZ = Number.MAX_SAFE_INTEGER / 1000;
|
|
138
|
+
|
|
139
|
+
/** A positive safe-integer Hz timescale, or undefined. */
|
|
140
|
+
function timescaleHz(value: unknown): number | undefined {
|
|
141
|
+
return typeof value === "number" && Number.isSafeInteger(value) && value > 0 ? value : undefined;
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
/**
|
|
145
|
+
* A rendition's publisher group duration in ms, or undefined when the catalog
|
|
146
|
+
* carries none.
|
|
147
|
+
*
|
|
148
|
+
* `groupDurationTicks` over a timescale wins when both are present, through
|
|
149
|
+
* `resolveGroupDurationMs` (draft-ramadan-moq-mmt-00 §4.4.4). The timescale is
|
|
150
|
+
* the MMTP container's when the rendition declares one, else the rendition's
|
|
151
|
+
* own `timescale`. Only the ticks are forwarded: a catalog `groupDurationMs`
|
|
152
|
+
* is often a rounded fraction (21.33 for 1024/48000), which the ticks path
|
|
153
|
+
* never reads but `resolveGroupDurationMs` would reject as a non-integral ms.
|
|
154
|
+
* Ticks with no usable timescale, and ticks that `resolveGroupDurationMs`
|
|
155
|
+
* would reject, fall back to `groupDurationMs` rather than guessing a clock.
|
|
156
|
+
* That rejection is on the product, not the operand: the count must be a safe
|
|
157
|
+
* integer and `(ticks / timescale) * 1000` must stay within
|
|
158
|
+
* `Number.MAX_SAFE_INTEGER`, which a safe-integer count can still exceed when
|
|
159
|
+
* `timescale < 1000`, so the guard below bounds the count by
|
|
160
|
+
* `timescale * (Number.MAX_SAFE_INTEGER / 1000)` and the reader never throws.
|
|
161
|
+
* The production catalog signals both fields on every rendition and no
|
|
162
|
+
* rendition-level timescale, so the `groupDurationMs` fallback is the path it
|
|
163
|
+
* takes.
|
|
164
|
+
*/
|
|
165
|
+
export function catalogGroupDurationMs(rendition: GroupDurationRendition | undefined): number | undefined {
|
|
166
|
+
if (!rendition) return undefined;
|
|
167
|
+
const ticks = numericField(rendition.groupDurationTicks);
|
|
168
|
+
const ms = numericField(rendition.groupDurationMs);
|
|
169
|
+
const timescale =
|
|
170
|
+
timescaleHz(rendition.container?.kind === "mmtp" ? rendition.container.timescale : undefined) ??
|
|
171
|
+
timescaleHz(rendition.timescale);
|
|
172
|
+
if (
|
|
173
|
+
ticks !== undefined &&
|
|
174
|
+
timescale !== undefined &&
|
|
175
|
+
Number.isSafeInteger(ticks) &&
|
|
176
|
+
ticks <= timescale * MAX_SAFE_TICKS_PER_HZ
|
|
177
|
+
) {
|
|
178
|
+
return resolveGroupDurationMs({ groupDurationTicks: ticks }, timescale);
|
|
179
|
+
}
|
|
180
|
+
return ms;
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
/**
|
|
184
|
+
* The group duration of the catalog rendition an endpoint track was resolved
|
|
185
|
+
* from, by type and name (the same lookup `resolveCatalogTrackFec` performs
|
|
186
|
+
* for FEC geometry). Undefined when the rendition is missing or carries no
|
|
187
|
+
* group duration, so a caller that needs one can fail closed by name.
|
|
188
|
+
*/
|
|
189
|
+
export function resolveCatalogTrackGroupDurationMs(
|
|
190
|
+
catalog: CatalogWithRenditions | undefined,
|
|
191
|
+
track: CatalogTrackRef,
|
|
192
|
+
): number | undefined {
|
|
193
|
+
const renditions = track.type === "audio" ? catalog?.audio?.renditions : catalog?.video?.renditions;
|
|
194
|
+
return catalogGroupDurationMs(renditions?.[track.name]);
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
export type KeyframeCadenceCatalog = GroupDurationCatalog & {
|
|
198
|
+
keyframeDurationTicks?: number;
|
|
199
|
+
keyframeDurationMs?: number;
|
|
200
|
+
keyframeIntervalTicks?: number;
|
|
201
|
+
keyframeIntervalMs?: number;
|
|
202
|
+
gopDurationTicks?: number;
|
|
203
|
+
gopDurationMs?: number;
|
|
204
|
+
};
|
|
205
|
+
|
|
206
|
+
export type TrackFecParams = {
|
|
207
|
+
fecK: number;
|
|
208
|
+
/** P_0: repair symbols per block on layer 0 (the track-level repairSymbols). */
|
|
209
|
+
fecRepairCount: number;
|
|
210
|
+
/** Total repair symbols per block across the BASE layers: the wire
|
|
211
|
+
* RSB_length on every base layer packet. Equals fecRepairCount on a
|
|
212
|
+
* single-layer track. A keyframe overlay is a separate FEC instance with
|
|
213
|
+
* its own RSB_length and is not included. */
|
|
214
|
+
fecTotalRepairCount: number;
|
|
215
|
+
fecSymbolSize: number;
|
|
216
|
+
fecInterleaveMs: number;
|
|
217
|
+
/** Catalog fec.reorderToleranceMs — signaled jitter/reorder allowance, ADDED
|
|
218
|
+
* to the block span to form a deadline. Deliberately `number | undefined`
|
|
219
|
+
* and NOT floored to 0: a declared 0 ("this path needs no slack") and an
|
|
220
|
+
* absent value ("the encoder never said") must stay distinguishable, or a
|
|
221
|
+
* consumer that wants to fail loud on absence silently reads a default
|
|
222
|
+
* instead — which is exactly how the magic 3.0 survived. */
|
|
223
|
+
fecReorderToleranceMs?: number;
|
|
224
|
+
repairTrackName?: string;
|
|
225
|
+
/** Every base repair layer in order, layer 0 first, with derived RS_ID
|
|
226
|
+
* offsets. Present whenever repairTrackName is. */
|
|
227
|
+
repairLayers?: readonly RepairLayerParams[];
|
|
228
|
+
/** Keyframe overlay instances declared for this track. Present (possibly
|
|
229
|
+
* empty) whenever repairLayers is. */
|
|
230
|
+
repairOverlays?: readonly RepairOverlayParams[];
|
|
231
|
+
fps?: number;
|
|
232
|
+
sampleRate?: number;
|
|
233
|
+
};
|
|
234
|
+
|
|
235
|
+
const NO_FEC: TrackFecParams = {
|
|
236
|
+
fecK: 0,
|
|
237
|
+
fecRepairCount: 0,
|
|
238
|
+
fecTotalRepairCount: 0,
|
|
239
|
+
fecSymbolSize: 0,
|
|
240
|
+
fecInterleaveMs: 0,
|
|
241
|
+
};
|
|
242
|
+
|
|
243
|
+
/**
|
|
244
|
+
* Repair symbols per block a receiver has actually joined: the sum of
|
|
245
|
+
* `repairSymbols` over the BASE layers whose repair track it joined
|
|
246
|
+
* (draft-ramadan-moq-fec 6.3). This is a symbol count, not a count of layers.
|
|
247
|
+
*
|
|
248
|
+
* A keyframe overlay is a separate FEC instance with its own K, its own
|
|
249
|
+
* RSB_length and its own RS_ID space, so it is never added here however it was
|
|
250
|
+
* joined. Counting it would overstate the base instance's P and misreport
|
|
251
|
+
* CMCD `x-bc-fec-p`.
|
|
252
|
+
*
|
|
253
|
+
* Falls back to P_0 when the track declares no layers, which is the
|
|
254
|
+
* single-layer identity rather than a default: with one layer, P_0 is the
|
|
255
|
+
* total.
|
|
256
|
+
*/
|
|
257
|
+
export function joinedRepairSymbolCount(
|
|
258
|
+
params: Pick<TrackFecParams, "fecRepairCount" | "repairLayers">,
|
|
259
|
+
joinedRepairTrackNames: Iterable<string>,
|
|
260
|
+
): number {
|
|
261
|
+
const layers = params.repairLayers;
|
|
262
|
+
if (layers === undefined || layers.length === 0) return params.fecRepairCount;
|
|
263
|
+
const joined = new Set(joinedRepairTrackNames);
|
|
264
|
+
let total = 0;
|
|
265
|
+
for (const layer of layers) {
|
|
266
|
+
if (joined.has(layer.repairTrackName)) total += layer.repairSymbols;
|
|
267
|
+
}
|
|
268
|
+
return total;
|
|
269
|
+
}
|
|
270
|
+
|
|
271
|
+
function recordOf(value: unknown): Record<string, unknown> | undefined {
|
|
272
|
+
return typeof value === "object" && value !== null && !Array.isArray(value) ? (value as Record<string, unknown>) : undefined;
|
|
273
|
+
}
|
|
274
|
+
|
|
275
|
+
/** The MSF `tracks[]` view of a catalog, or undefined for the hang dialect. */
|
|
276
|
+
function msfTracks(catalog: RepairLayerCatalog): { tracks: Record<string, unknown>[]; common: Record<string, unknown> } | undefined {
|
|
277
|
+
const raw = (catalog as CatalogWithTracks).tracks;
|
|
278
|
+
if (!Array.isArray(raw)) return undefined;
|
|
279
|
+
const common = recordOf((catalog as CatalogWithTracks).commonTrackFields) ?? {};
|
|
280
|
+
return { tracks: raw.map((t) => recordOf(t) ?? {}), common };
|
|
281
|
+
}
|
|
282
|
+
|
|
283
|
+
/**
|
|
284
|
+
* Resolve every repair track of one source track: base layers with derived
|
|
285
|
+
* RS_ID offsets and keyframe overlays (draft-ramadan-moq-fec §6.3), from either
|
|
286
|
+
* catalog dialect.
|
|
287
|
+
*
|
|
288
|
+
* - MSF `tracks[]`: the source is the entry named `source`; repair tracks are
|
|
289
|
+
* `packaging: "fec-repair"` entries. Layer 0 is the source's
|
|
290
|
+
* `fec.repairTrack`; layers 1..n and overlays `depend` on the source.
|
|
291
|
+
* - hang: the source is a `video`/`audio` rendition; repair tracks beyond
|
|
292
|
+
* layer 0 are `repair.renditions` entries that `depend` on it.
|
|
293
|
+
*
|
|
294
|
+
* Returns undefined when the source carries no FEC repair track and nothing
|
|
295
|
+
* depends on it. Throws `RepairContractError` (code + JSON path) on any
|
|
296
|
+
* violation, including a repair rendition whose `depends` names a rendition
|
|
297
|
+
* without FEC, so a player fails closed before joining any repair track.
|
|
298
|
+
*/
|
|
299
|
+
export function resolveRepairLayers(
|
|
300
|
+
catalog: RepairLayerCatalog | undefined,
|
|
301
|
+
source: string | CatalogTrackRef,
|
|
302
|
+
): RepairLayersResolution | undefined {
|
|
303
|
+
if (!catalog) return undefined;
|
|
304
|
+
const sourceName = typeof source === "string" ? source : source.name;
|
|
305
|
+
|
|
306
|
+
// hang dialect first. When a catalog carries hang-native rendition blocks
|
|
307
|
+
// beside a tracks[] switching-set index (the unified ABR ladder catalog),
|
|
308
|
+
// the rendition blocks are authoritative, exactly as they are for hang's own
|
|
309
|
+
// catalog decode. A typed ref resolves only within its own role.
|
|
310
|
+
const hang = catalog as CatalogWithRenditions;
|
|
311
|
+
const roles: Array<"video" | "audio"> =
|
|
312
|
+
typeof source === "string"
|
|
313
|
+
? ["video", "audio"]
|
|
314
|
+
: source.type === "audio"
|
|
315
|
+
? ["audio"]
|
|
316
|
+
: source.type === "video"
|
|
317
|
+
? ["video"]
|
|
318
|
+
: ["video", "audio"];
|
|
319
|
+
const role = roles.find((r) => recordOf(hang[r]?.renditions?.[sourceName]) !== undefined);
|
|
320
|
+
if (role !== undefined) {
|
|
321
|
+
const renditionPath = `$.${role}.renditions[${JSON.stringify(sourceName)}]`;
|
|
322
|
+
const rendition = recordOf(hang[role]!.renditions![sourceName])!;
|
|
323
|
+
rejectRepairFieldsOnMediaTrack(renditionPath, rendition, throwRepairContractError);
|
|
324
|
+
const repairRenditions = recordOf(hang.repair?.renditions) ?? {};
|
|
325
|
+
const descriptors: RepairTrackDescriptor[] = Object.entries(repairRenditions).map(([name, entry]) => {
|
|
326
|
+
const path = `$.repair.renditions[${JSON.stringify(name)}]`;
|
|
327
|
+
const fields = recordOf(entry);
|
|
328
|
+
if (fields === undefined) {
|
|
329
|
+
throwRepairContractError("track_repair_layer", path, "a repair rendition must be an object");
|
|
330
|
+
}
|
|
331
|
+
rejectRepairTrackGeometry(path, fields, throwRepairContractError);
|
|
332
|
+
return describeRepairTrack(name, path, fields);
|
|
333
|
+
});
|
|
334
|
+
const fecOfRendition = (entry: unknown): Record<string, unknown> | undefined => {
|
|
335
|
+
const fec = recordOf(recordOf(entry)?.["fec"]);
|
|
336
|
+
return fec !== undefined && fec["algorithm"] !== "none" ? fec : undefined;
|
|
337
|
+
};
|
|
338
|
+
const mediaRenditions = [
|
|
339
|
+
...Object.values(recordOf(hang.video?.renditions) ?? {}),
|
|
340
|
+
...Object.values(recordOf(hang.audio?.renditions) ?? {}),
|
|
341
|
+
];
|
|
342
|
+
const reachability = repairReachability(mediaRenditions.map((entry) => recordOf(entry)?.["fec"]));
|
|
343
|
+
for (const d of descriptors) {
|
|
344
|
+
validateRepairTrackFields(d, throwRepairContractError);
|
|
345
|
+
assertRepairTrackReachable(d, reachability, throwRepairContractError);
|
|
346
|
+
const target = dependsTarget(d);
|
|
347
|
+
if (target === undefined) continue;
|
|
348
|
+
const targetFec =
|
|
349
|
+
fecOfRendition(hang.video?.renditions?.[target]) ?? fecOfRendition(hang.audio?.renditions?.[target]);
|
|
350
|
+
if (targetFec === undefined) {
|
|
351
|
+
throwRepairContractError(
|
|
352
|
+
"track_repair_depends",
|
|
353
|
+
`${d.path}.depends`,
|
|
354
|
+
`${JSON.stringify(target)} is not a video or audio rendition with FEC`,
|
|
355
|
+
);
|
|
356
|
+
}
|
|
357
|
+
}
|
|
358
|
+
return assembleRepairLayers(
|
|
359
|
+
geometryOf(sourceName, `${renditionPath}.fec`, recordOf(rendition["fec"])),
|
|
360
|
+
descriptors,
|
|
361
|
+
throwRepairContractError,
|
|
362
|
+
);
|
|
363
|
+
}
|
|
364
|
+
|
|
365
|
+
const msf = msfTracks(catalog);
|
|
366
|
+
const msfIndex = msf ? msf.tracks.findIndex((t) => t["name"] === sourceName) : -1;
|
|
367
|
+
if (!msf || msfIndex < 0) return undefined;
|
|
368
|
+
const track = msf.tracks[msfIndex]!;
|
|
369
|
+
const fec = recordOf(track["fec"]);
|
|
370
|
+
const packagingOf = (t: Record<string, unknown>): unknown => t["packaging"] ?? msf.common["packaging"];
|
|
371
|
+
const fecOfTrack = (t: Record<string, unknown> | undefined): Record<string, unknown> | undefined => {
|
|
372
|
+
const trackFec = recordOf(t?.["fec"]);
|
|
373
|
+
return trackFec !== undefined && trackFec["algorithm"] !== "none" ? trackFec : undefined;
|
|
374
|
+
};
|
|
375
|
+
// Rule 8 on the resolver path too: a repair track carries no block geometry
|
|
376
|
+
// and a media track carries no repair-track fields. Without this a repair
|
|
377
|
+
// track with its own `fec` would count as a FEC source below and name
|
|
378
|
+
// itself as layer 0, so rule 9 would never see it.
|
|
379
|
+
const descriptors: RepairTrackDescriptor[] = [];
|
|
380
|
+
const mediaTracks: Record<string, unknown>[] = [];
|
|
381
|
+
msf.tracks.forEach((t, i) => {
|
|
382
|
+
const path = `$.tracks[${i}]`;
|
|
383
|
+
if (packagingOf(t) === "fec-repair") {
|
|
384
|
+
rejectRepairTrackGeometry(path, t, throwRepairContractError);
|
|
385
|
+
if (typeof t["name"] === "string") descriptors.push(describeRepairTrack(t["name"], path, t));
|
|
386
|
+
return;
|
|
387
|
+
}
|
|
388
|
+
rejectRepairFieldsOnMediaTrack(path, t, throwRepairContractError);
|
|
389
|
+
mediaTracks.push(t);
|
|
390
|
+
});
|
|
391
|
+
const reachability = repairReachability(mediaTracks.map((t) => t["fec"]));
|
|
392
|
+
for (const d of descriptors) {
|
|
393
|
+
validateRepairTrackFields(d, throwRepairContractError);
|
|
394
|
+
assertRepairTrackReachable(d, reachability, throwRepairContractError);
|
|
395
|
+
const target = dependsTarget(d);
|
|
396
|
+
if (target === undefined) continue;
|
|
397
|
+
const targetTrack = msf.tracks.find((t) => t["name"] === target);
|
|
398
|
+
if (targetTrack === undefined || packagingOf(targetTrack) !== "mmtp" || fecOfTrack(targetTrack) === undefined) {
|
|
399
|
+
throwRepairContractError(
|
|
400
|
+
"track_repair_depends",
|
|
401
|
+
`${d.path}.depends`,
|
|
402
|
+
`${JSON.stringify(target)} is not an mmtp track with FEC`,
|
|
403
|
+
);
|
|
404
|
+
}
|
|
405
|
+
}
|
|
406
|
+
return assembleRepairLayers(geometryOf(sourceName, `$.tracks[${msfIndex}].fec`, fec), descriptors, throwRepairContractError, {
|
|
407
|
+
layerZeroMustBeDeclared: true,
|
|
408
|
+
});
|
|
409
|
+
}
|
|
410
|
+
|
|
411
|
+
function geometryOf(name: string, path: string, fec: Record<string, unknown> | undefined): RepairSourceGeometry {
|
|
412
|
+
return {
|
|
413
|
+
name,
|
|
414
|
+
path,
|
|
415
|
+
algorithm: fec?.["algorithm"],
|
|
416
|
+
sourceSymbols: fec?.["sourceSymbols"],
|
|
417
|
+
repairSymbols: fec?.["repairSymbols"],
|
|
418
|
+
repairTrack: fec?.["repairTrack"],
|
|
419
|
+
};
|
|
420
|
+
}
|
|
421
|
+
|
|
422
|
+
function numericField(value: unknown): number | undefined {
|
|
423
|
+
const n = typeof value === "number" ? value : typeof value === "string" ? Number(value) : Number.NaN;
|
|
424
|
+
return Number.isFinite(n) && n > 0 ? n : undefined;
|
|
425
|
+
}
|
|
426
|
+
|
|
427
|
+
/** Like `numericField` but admits an explicit 0, and still rejects absent,
|
|
428
|
+
* negative and non-finite input. Absence returns undefined so callers can
|
|
429
|
+
* tell "declared none" from "never declared". */
|
|
430
|
+
function nonNegativeField(value: unknown): number | undefined {
|
|
431
|
+
const n = typeof value === "number" ? value : typeof value === "string" ? Number(value) : Number.NaN;
|
|
432
|
+
return Number.isFinite(n) && n >= 0 ? n : undefined;
|
|
433
|
+
}
|
|
434
|
+
|
|
435
|
+
/**
|
|
436
|
+
* Per-track FEC geometry, or `NO_FEC` when the rendition declares none.
|
|
437
|
+
*
|
|
438
|
+
* @throws RepairContractError from `resolveRepairLayers` when the rendition
|
|
439
|
+
* has FEC and the catalog's repair contract is malformed; see
|
|
440
|
+
* `resolveCatalogTrackFec`.
|
|
441
|
+
*/
|
|
442
|
+
function fecParams(
|
|
443
|
+
catalog: CatalogWithRenditions | undefined,
|
|
444
|
+
track: CatalogTrackRef | undefined,
|
|
445
|
+
rendition: RenditionCatalog | undefined,
|
|
446
|
+
fps?: number,
|
|
447
|
+
sampleRate?: number,
|
|
448
|
+
): TrackFecParams {
|
|
449
|
+
const mediaRate = sampleRate === undefined ? { fps } : { fps, sampleRate };
|
|
450
|
+
const fec = rendition?.fec;
|
|
451
|
+
if (!fec) return { ...NO_FEC, ...mediaRate };
|
|
452
|
+
const repair = track ? resolveRepairLayers(catalog, track) : undefined;
|
|
453
|
+
return {
|
|
454
|
+
fecK: fec.sourceSymbols ?? 0,
|
|
455
|
+
fecRepairCount: fec.repairSymbols ?? 0,
|
|
456
|
+
// The wire RSB_length: every base layer's packets carry the base total (§7.1).
|
|
457
|
+
fecTotalRepairCount: repair?.totalBaseRepairSymbols ?? fec.repairSymbols ?? 0,
|
|
458
|
+
fecSymbolSize: fec.symbolSize ?? 0,
|
|
459
|
+
// interleaveDepthMs is the FEC block span in MILLISECONDS (§5.1) — the
|
|
460
|
+
// only interleave key the catalog carries post-BLO-14526. Receivers
|
|
461
|
+
// derive D by positive round-half-up of span / GOP duration where needed.
|
|
462
|
+
fecInterleaveMs: catalogFecInterleaveMs(fec) ?? 0,
|
|
463
|
+
// Additive, never a multiplier on the span: jitter belongs to the network
|
|
464
|
+
// path and the span belongs to the encoder, so scaling one by the other
|
|
465
|
+
// hands one network different slack per track. `numericField` rejects 0,
|
|
466
|
+
// so it cannot be reused here — a declared 0 is a legitimate value.
|
|
467
|
+
fecReorderToleranceMs: nonNegativeField(fec.reorderToleranceMs),
|
|
468
|
+
repairTrackName: fec.repairTrack,
|
|
469
|
+
repairLayers: repair?.baseLayers,
|
|
470
|
+
repairOverlays: repair?.overlays,
|
|
471
|
+
...mediaRate,
|
|
472
|
+
};
|
|
473
|
+
}
|
|
474
|
+
|
|
475
|
+
/**
|
|
476
|
+
* Resolves per-track FEC geometry from the catalog for the active endpoint tracks.
|
|
477
|
+
*
|
|
478
|
+
* Invariant: expects at most one video track and one audio track. `forTrack`
|
|
479
|
+
* dispatches purely on `track.type`, so a second video track (e.g. a simulcast
|
|
480
|
+
* variant) would silently receive the first video rendition's geometry. Revisit
|
|
481
|
+
* the `track.type` dispatch before relaxing that one-per-type assumption.
|
|
482
|
+
*
|
|
483
|
+
* @throws RepairContractError when a rendition with FEC carries a repair
|
|
484
|
+
* contract that violates draft-ramadan-moq-fec 6.3 (a gap or duplicate in the
|
|
485
|
+
* layer chain, a bad `depends` target, an unreachable repair track, a bound
|
|
486
|
+
* violation). Because the hang dialect validates every `repair.renditions`
|
|
487
|
+
* entry of the catalog, resolving the video track fails on a malformed audio
|
|
488
|
+
* repair rendition too. This is deliberate: a player must fail closed before it
|
|
489
|
+
* joins any repair track. Callers that used to treat this function as total
|
|
490
|
+
* must catch it and surface the catalog error.
|
|
491
|
+
*/
|
|
492
|
+
export function resolveCatalogTrackFec(
|
|
493
|
+
catalog: CatalogWithRenditions | undefined,
|
|
494
|
+
tracks: readonly CatalogTrackRef[],
|
|
495
|
+
): {
|
|
496
|
+
videoTrackName?: string;
|
|
497
|
+
audioTrackName?: string;
|
|
498
|
+
missingVideoRendition?: string;
|
|
499
|
+
missingAudioRendition?: string;
|
|
500
|
+
videoForKeyframeRepair?: KeyframeCadenceCatalog;
|
|
501
|
+
catalogFps?: number;
|
|
502
|
+
video: TrackFecParams;
|
|
503
|
+
audio: TrackFecParams;
|
|
504
|
+
forTrack(track: CatalogTrackRef): TrackFecParams;
|
|
505
|
+
} {
|
|
506
|
+
const videoTrackName = tracks.find((t) => t.type === "video")?.name;
|
|
507
|
+
const audioTrackName = tracks.find((t) => t.type === "audio")?.name;
|
|
508
|
+
const videoRenditions = catalog?.video?.renditions;
|
|
509
|
+
const audioRenditions = catalog?.audio?.renditions;
|
|
510
|
+
const video = videoTrackName ? videoRenditions?.[videoTrackName] : undefined;
|
|
511
|
+
const audio = audioTrackName ? audioRenditions?.[audioTrackName] : undefined;
|
|
512
|
+
const catalogFps = numericField(video?.framerate);
|
|
513
|
+
const sampleRate = numericField(audio?.sampleRate ?? audio?.samplerate);
|
|
514
|
+
const audioFps = sampleRate ? sampleRate / 1024 : undefined;
|
|
515
|
+
const videoParams = fecParams(catalog, videoTrackName ? { name: videoTrackName, type: "video" } : undefined, video, catalogFps);
|
|
516
|
+
const audioParams = fecParams(
|
|
517
|
+
catalog,
|
|
518
|
+
audioTrackName ? { name: audioTrackName, type: "audio" } : undefined,
|
|
519
|
+
audio,
|
|
520
|
+
audioFps,
|
|
521
|
+
sampleRate,
|
|
522
|
+
);
|
|
523
|
+
|
|
524
|
+
return {
|
|
525
|
+
videoTrackName,
|
|
526
|
+
audioTrackName,
|
|
527
|
+
missingVideoRendition: videoTrackName && videoRenditions && !video ? videoTrackName : undefined,
|
|
528
|
+
missingAudioRendition: audioTrackName && audioRenditions && !audio ? audioTrackName : undefined,
|
|
529
|
+
videoForKeyframeRepair: video,
|
|
530
|
+
catalogFps,
|
|
531
|
+
video: videoParams,
|
|
532
|
+
audio: audioParams,
|
|
533
|
+
forTrack: (track) => (track.type === "audio" ? audioParams : videoParams),
|
|
534
|
+
};
|
|
535
|
+
}
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
// Catalog → AMT relay discovery (multicast.networkSource).
|
|
2
|
+
//
|
|
3
|
+
// Shared by every player (moq-lib/hang, moqtail, shaka MSF) so networkSource
|
|
4
|
+
// interpretation lives in one place — players keep only wiring, not
|
|
5
|
+
// MMT/catalog semantics.
|
|
6
|
+
//
|
|
7
|
+
// draft-ramadan-moq-multicast §4.1 carries relay discovery as
|
|
8
|
+
// `multicast.networkSource`. Publishers emit the canonical ARRAY form
|
|
9
|
+
// (hang-rs `Option<Vec<NetworkSource>>`; cast's bridge + ladder catalogs), but
|
|
10
|
+
// hang's zod RootSchema also accepts a bare object and older hand-authored
|
|
11
|
+
// catalogs used it — consume both.
|
|
12
|
+
|
|
13
|
+
/** One `networkSource[]` entry as published (`{type, relay, port?}`). */
|
|
14
|
+
export type CatalogNetworkSource = {
|
|
15
|
+
type?: string;
|
|
16
|
+
relay?: string;
|
|
17
|
+
port?: number;
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
/** Resolved AMT relay a player can hand to its multicast join/subscribe. */
|
|
21
|
+
export type AmtNetworkSource = {
|
|
22
|
+
relay: string;
|
|
23
|
+
port?: number;
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
function normalizePort(value: unknown): number | undefined {
|
|
27
|
+
const n = typeof value === "number" ? value : typeof value === "string" ? Number(value) : Number.NaN;
|
|
28
|
+
return Number.isInteger(n) && n > 0 && n <= 65535 ? n : undefined;
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
/**
|
|
32
|
+
* Resolve the AMT relay from a catalog `multicast` block's `networkSource`
|
|
33
|
+
* (array or bare-object form). Returns the first entry with `type: "amt"`
|
|
34
|
+
* and a non-blank relay, or `undefined` when the catalog advertises none —
|
|
35
|
+
* callers fall back to native multicast (or their own explicit relay config).
|
|
36
|
+
*/
|
|
37
|
+
export function catalogAmtNetworkSource(networkSource: unknown): AmtNetworkSource | undefined {
|
|
38
|
+
const entries = Array.isArray(networkSource) ? networkSource : networkSource ? [networkSource] : [];
|
|
39
|
+
for (const raw of entries) {
|
|
40
|
+
if (!raw || typeof raw !== "object") continue;
|
|
41
|
+
const ns = raw as CatalogNetworkSource;
|
|
42
|
+
if (ns.type !== "amt") continue;
|
|
43
|
+
const relay = typeof ns.relay === "string" ? ns.relay.trim() : "";
|
|
44
|
+
if (!relay) continue;
|
|
45
|
+
const port = normalizePort(ns.port);
|
|
46
|
+
return port !== undefined ? { relay, port } : { relay };
|
|
47
|
+
}
|
|
48
|
+
return undefined;
|
|
49
|
+
}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import Ajv2020 from 'ajv/dist/2020.js'
|
|
2
|
+
import addFormats from 'ajv-formats'
|
|
3
|
+
import { hasUniqueMulticastAuthTrackBindings } from './multicast-auth-catalog.js'
|
|
4
|
+
|
|
5
|
+
export interface CatalogSchemaValidationError {
|
|
6
|
+
instancePath: string
|
|
7
|
+
schemaPath: string
|
|
8
|
+
keyword: string
|
|
9
|
+
params: Record<string, unknown>
|
|
10
|
+
message?: string
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
export interface CatalogSchemaValidator {
|
|
14
|
+
(catalog: unknown): boolean
|
|
15
|
+
errors: CatalogSchemaValidationError[] | null
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* Compile the published catalog schema with every package-defined semantic
|
|
20
|
+
* keyword installed. Consumers must use this entry point instead of compiling
|
|
21
|
+
* `catalog.schema.json` with a bare JSON Schema validator.
|
|
22
|
+
*/
|
|
23
|
+
export function createCatalogSchemaValidator(schema: object): CatalogSchemaValidator {
|
|
24
|
+
const ajv = new Ajv2020({ allErrors: true, strict: true })
|
|
25
|
+
addFormats(ajv)
|
|
26
|
+
ajv.addKeyword({
|
|
27
|
+
keyword: 'uniqueMulticastAuthTrackBindings',
|
|
28
|
+
type: 'array',
|
|
29
|
+
schemaType: 'boolean',
|
|
30
|
+
validate: (enabled: boolean, tracks: unknown[]) =>
|
|
31
|
+
!enabled || hasUniqueMulticastAuthTrackBindings(tracks),
|
|
32
|
+
})
|
|
33
|
+
return ajv.compile(schema) as CatalogSchemaValidator
|
|
34
|
+
}
|